1. load libraries

2. Load Seurat Object


#Load Seurat Object merged from cell lines and a control(PBMC) after filtration
load("../../../0-IMP-OBJECTS/All_Samples_Merged_with_10x_Azitmuth_Annotated_SCT_HPC_without_harmony_integration.robj")

All_samples_Merged

3. Data PREPARATION and Harmony Integration-1


library(harmony)

All_samples_Merged <- RunHarmony(
  object = All_samples_Merged,
  group.by.vars = "cell_line",  # Replace with the metadata column specifying batch or cell line
  dims.use = 1:22,  # Use the same dimensions as PCA
  assay.use = "SCT",
plot_convergence = TRUE
  )

# Run UMAP on the new Harmony reduction
All_samples_Merged <- RunUMAP(All_samples_Merged, reduction = "harmony", dims = 1:22, reduction.name = "umap.harmony")

# Find neighbors and clusters using the Harmony reduction
All_samples_Merged <- FindNeighbors(All_samples_Merged, reduction = "harmony", dims = 1:22)
All_samples_Merged <- FindClusters(All_samples_Merged, resolution = 0.5)

# Visualize results
p1 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line") + 
  ggtitle("Harmony Integration - By Cell Line")
p2 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters") + 
  ggtitle("Harmony Integration - By Clusters")

# Compare with original UMAP
p3 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "cell_line") + 
  ggtitle("Original Integration - By Cell Line")
p4 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "seurat_clusters") + 
  ggtitle("Original Integration - By Clusters")

# Print the plots
print(p1 + p2)
print(p3 + p4)

Harmony Visualization-1


# Visualize results
p1 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line", label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Cell Line")
p2 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Clusters")

# Compare with original UMAP
p3 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "cell_line",label = T, label.box = T) + 
  ggtitle("Original Integration - By Cell Line")
p4 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Original Integration - By Clusters")

# Print the plots
print(p1 + p2)
print(p3 + p4)

4. Data PREPARATION and Harmony Integration-2


library(harmony)

All_samples_Merged <- RunHarmony(
  object = All_samples_Merged,
  group.by.vars = "cell_line",  # Replace with the metadata column specifying batch or cell line
  dims.use = 1:22,  # Use the same dimensions as PCA
  assay.use = "SCT",
  Theta = 0.5,
  lambda =0.5,
  plot_convergence = TRUE
  )

# Run UMAP on the new Harmony reduction
All_samples_Merged <- RunUMAP(All_samples_Merged, reduction = "harmony", dims = 1:22, reduction.name = "umap.harmony")

# Find neighbors and clusters using the Harmony reduction
All_samples_Merged <- FindNeighbors(All_samples_Merged, reduction = "harmony", dims = 1:22)
All_samples_Merged <- FindClusters(All_samples_Merged, resolution = 0.5)

Harmony Visualization-2


# Visualize results
p1 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line", label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Cell Line")
p2 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Clusters")

# Compare with original UMAP
p3 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "cell_line",label = T, label.box = T) + 
  ggtitle("Original Integration - By Cell Line")
p4 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Original Integration - By Clusters")

# Print the plots
print(p1 + p2)
print(p3 + p4)
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line", label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Cell Line")
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Clusters")
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "predicted.celltype.l2",label = T, label.box = T) + 
  ggtitle("Harmony Integration - Annotations")

5. Data PREPARATION and Harmony Integration-3


# Create a new metadata column for grouping
All_samples_Merged$sample_group <- case_when(
  grepl("^L", All_samples_Merged$cell_line) ~ "Cell_Line",
  All_samples_Merged$cell_line == "PBMC" ~ "PBMC",
  All_samples_Merged$cell_line == "PBMC_10x" ~ "PBMC_10x",
  TRUE ~ "Other"
)

# Create the cell line grouping correctly
All_samples_Merged$cell_line_group <- case_when(
  grepl("^L[1-2]", All_samples_Merged$cell_line) ~ "P1",
  grepl("^L[3-4]", All_samples_Merged$cell_line) ~ "P2",
  grepl("^L[5-7]", All_samples_Merged$cell_line) ~ "P3",
  All_samples_Merged$cell_line == "PBMC" ~ "PBMC",
  All_samples_Merged$cell_line == "PBMC_10x" ~ "PBMC_10x",
  TRUE ~ "Other"  # This catches any unexpected values
)

library(harmony)

All_samples_Merged <- RunHarmony(
  object = All_samples_Merged,
  group.by.vars = "sample_group",
  dims.use = 1:22,  # Increased to capture more variation
  theta = c(0.5),  # Adjust these values as needed
  plot_convergence = TRUE
)

# Run UMAP on the new Harmony reduction
All_samples_Merged <- RunUMAP(All_samples_Merged, reduction = "harmony", dims = 1:22, reduction.name = "umap.harmony")

# Find neighbors and clusters using the Harmony reduction
All_samples_Merged <- FindNeighbors(All_samples_Merged, reduction = "harmony", dims = 1:22)
All_samples_Merged <- FindClusters(All_samples_Merged, resolution = 0.5)

Harmony Visualization-3



p1 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "sample_group", label = T, label.box = T)
p2 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line_group",label = T, label.box = T)
p3 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line",label = T, label.box = T)

p1 + p2 + p3

DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "sample_group",label = T, label.box = T)
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line_group",label = T, label.box = T)
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line",label = T, label.box = T)



# Compare with original UMAP
p4 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "cell_line",label = T, label.box = T) + 
  ggtitle("Original Integration - By Cell Line")
p5 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Original Integration - By Clusters")

# Print the plots
print(p4 + p5)

DimPlot(All_samples_Merged, reduction = "umap", group.by = "cell_line",label = T, label.box = T) + 
  ggtitle("Original Integration - By Cell Line")
DimPlot(All_samples_Merged, reduction = "umap", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Original Integration - By Clusters")

# Visualize results
p6 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line", label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Cell Line")
p7 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Clusters")
# Print the plots
print(p6 + p7)

DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line", label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Cell Line")
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Clusters")
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "predicted.celltype.l2",label = T, label.box = T) + 
  ggtitle("Harmony Integration - Annotations")

6. Data PREPARATION and Harmony Integration-4


# Create a new metadata column for grouping
All_samples_Merged$sample_group <- case_when(
  grepl("^L", All_samples_Merged$cell_line) ~ "Cell_Line",
  All_samples_Merged$cell_line == "PBMC" ~ "PBMC",
  All_samples_Merged$cell_line == "PBMC_10x" ~ "PBMC_10x",
  TRUE ~ "Other"
)

# Create the cell line grouping correctly
All_samples_Merged$cell_line_group <- case_when(
  grepl("^L[1-2]", All_samples_Merged$cell_line) ~ "P1",
  grepl("^L[3-4]", All_samples_Merged$cell_line) ~ "P2",
  grepl("^L[5-7]", All_samples_Merged$cell_line) ~ "P3",
  All_samples_Merged$cell_line == "PBMC" ~ "PBMC",
  All_samples_Merged$cell_line == "PBMC_10x" ~ "PBMC_10x",
  TRUE ~ "Other"  # This catches any unexpected values
)

library(harmony)

All_samples_Merged <- RunHarmony(
  object = All_samples_Merged,
  group.by.vars = "cell_line_group",
  dims.use = 1:22,  # Increased to capture more variation
  theta = c(0.5),  # Adjust these values as needed
  plot_convergence = TRUE
)

# Run UMAP on the new Harmony reduction
All_samples_Merged <- RunUMAP(All_samples_Merged, reduction = "harmony", dims = 1:22, reduction.name = "umap.harmony")

# Find neighbors and clusters using the Harmony reduction
All_samples_Merged <- FindNeighbors(All_samples_Merged, reduction = "harmony", dims = 1:22)
All_samples_Merged <- FindClusters(All_samples_Merged, resolution = 0.5)

Harmony Visualization-4



p1 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "sample_group", label = T, label.box = T)
p2 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line_group",label = T, label.box = T)
p3 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line",label = T, label.box = T)

p1 + p2 + p3

DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "sample_group",label = T, label.box = T)
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line_group",label = T, label.box = T)
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line",label = T, label.box = T)



# Compare with original UMAP
p4 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "cell_line",label = T, label.box = T) + 
  ggtitle("Original Integration - By Cell Line")
p5 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Original Integration - By Clusters")

# Print the plots
print(p4 + p5)

DimPlot(All_samples_Merged, reduction = "umap", group.by = "cell_line",label = T, label.box = T) + 
  ggtitle("Original Integration - By Cell Line")
DimPlot(All_samples_Merged, reduction = "umap", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Original Integration - By Clusters")

# Visualize results
p6 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line", label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Cell Line")
p7 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Clusters")
# Print the plots
print(p6 + p7)

DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line", label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Cell Line")
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Clusters")
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "predicted.celltype.l2",label = T, label.box = T) + 
  ggtitle("Harmony Integration - Annotations")

7. Data PREPARATION and Harmony Integration-5


# Create a new metadata column for grouping
All_samples_Merged$sample_group <- case_when(
  grepl("^L", All_samples_Merged$cell_line) ~ "Cell_Line",
  All_samples_Merged$cell_line == "PBMC" ~ "PBMC",
  All_samples_Merged$cell_line == "PBMC_10x" ~ "PBMC_10x",
  TRUE ~ "Other"
)

# Create the cell line grouping correctly
All_samples_Merged$cell_line_group <- case_when(
  grepl("^L[1-2]", All_samples_Merged$cell_line) ~ "P1",
  grepl("^L[3-4]", All_samples_Merged$cell_line) ~ "P2",
  grepl("^L[5-7]", All_samples_Merged$cell_line) ~ "P3",
  All_samples_Merged$cell_line == "PBMC" ~ "PBMC",
  All_samples_Merged$cell_line == "PBMC_10x" ~ "PBMC_10x",
  TRUE ~ "Other"  # This catches any unexpected values
)

library(harmony)

All_samples_Merged <- RunHarmony(
  object = All_samples_Merged,
  group.by.vars = "cell_line",
  dims.use = 1:22,  # Increased to capture more variation
  theta = c(0.5),  # Adjust these values as needed
  plot_convergence = TRUE
)

# Run UMAP on the new Harmony reduction
All_samples_Merged <- RunUMAP(All_samples_Merged, reduction = "harmony", dims = 1:22, reduction.name = "umap.harmony")

# Find neighbors and clusters using the Harmony reduction
All_samples_Merged <- FindNeighbors(All_samples_Merged, reduction = "harmony", dims = 1:22)
All_samples_Merged <- FindClusters(All_samples_Merged, resolution = 0.5)

Harmony Visualization-5



p1 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "sample_group", label = T, label.box = T)
p2 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line_group",label = T, label.box = T)
p3 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line",label = T, label.box = T)

p1 + p2 + p3

DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "sample_group",label = T, label.box = T)
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line_group",label = T, label.box = T)
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line",label = T, label.box = T)



# Compare with original UMAP
p4 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "cell_line",label = T, label.box = T) + 
  ggtitle("Original Integration - By Cell Line")
p5 <- DimPlot(All_samples_Merged, reduction = "umap", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Original Integration - By Clusters")

# Print the plots
print(p4 + p5)

DimPlot(All_samples_Merged, reduction = "umap", group.by = "cell_line",label = T, label.box = T) + 
  ggtitle("Original Integration - By Cell Line")
DimPlot(All_samples_Merged, reduction = "umap", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Original Integration - By Clusters")

# Visualize results
p6 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line", label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Cell Line")
p7 <- DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Clusters")
# Print the plots
print(p6 + p7)

DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "cell_line", label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Cell Line")
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "seurat_clusters",label = T, label.box = T) + 
  ggtitle("Harmony Integration - By Clusters")
DimPlot(All_samples_Merged, reduction = "umap.harmony", group.by = "predicted.celltype.l2",label = T, label.box = T) + 
  ggtitle("Harmony Integration - Annotations")

Marker Gene Visualization



# Set marker genes specific to requested immune cell types
myfeatures <- c("CD19", "CD79A", "MS4A1", # B cells
                "CD14", "LYZ", "FCGR3A", # Monocytes
                "CSF1R", "CD68", # Macrophages
                "NKG7", "GNLY", "KIR3DL1", # NK cells
                "MKI67", # Proliferating NK cells
                "CD34", "KIT", # HSPCs
                "CD3E", "CCR7", # T cells
                "SELL", "CD45RO", # Tnaive, Tcm
                "CD44", "CD45RA") # Tem, Temra
# Visualize marker genes for Harmony
FeaturePlot(All_samples_Merged, features = myfeatures, reduction = "umap.harmony", ncol = 4) + 
  ggtitle("Marker Gene Expression - Harmony Integration") +
  NoLegend()

6. Save the Seurat object as an Robj file


#save(All_samples_Merged, file = "integrated_All_samples_Merged_with_PBMC10x.Robj")
LS0tCnRpdGxlOiAiTXVsdGlwbGUgSGFybW9ueSBpbnRlZ3JhdGlvbnMgb2YgUEJNQzEweC1wYXJ0MyIKYXV0aG9yOiBOYXNpciBNYWhtb29kIEFiYmFzaQpkYXRlOiAiYHIgU3lzLkRhdGUoKWAiCm91dHB1dDoKICAjcm1kZm9ybWF0czo6cmVhZHRoZWRvd24KICBodG1sX25vdGVib29rOgogICAgdG9jOiB0cnVlCiAgICB0b2NfZmxvYXQ6IHRydWUKICAgIHRvY19jb2xsYXBzZWQ6IHRydWUKLS0tCgojIDEuIGxvYWQgbGlicmFyaWVzCmBgYHtyIHNldHVwLCBpbmNsdWRlPUZBTFNFfQpsaWJyYXJ5KFNldXJhdCkKbGlicmFyeShTZXVyYXRXcmFwcGVycykKbGlicmFyeShTZXVyYXRPYmplY3QpCmxpYnJhcnkoU2V1cmF0RGF0YSkKbGlicmFyeShwYXRjaHdvcmspCmxpYnJhcnkoaGFybW9ueSkKbGlicmFyeShnZ3Bsb3QyKQpsaWJyYXJ5KHJldGljdWxhdGUpCmxpYnJhcnkoQXppbXV0aCkKbGlicmFyeShkcGx5cikKbGlicmFyeShSdHNuZSkKbGlicmFyeShoYXJtb255KQoKb3B0aW9ucyhmdXR1cmUuZ2xvYmFscy5tYXhTaXplID0gMWU5KQoKYGBgCgoKCgojIDIuIExvYWQgU2V1cmF0IE9iamVjdCAKYGBge3IgbG9hZF9zZXVyYXR9CgojTG9hZCBTZXVyYXQgT2JqZWN0IG1lcmdlZCBmcm9tIGNlbGwgbGluZXMgYW5kIGEgY29udHJvbChQQk1DKSBhZnRlciBmaWx0cmF0aW9uCmxvYWQoIi4uLy4uLy4uLzAtSU1QLU9CSkVDVFMvQWxsX1NhbXBsZXNfTWVyZ2VkX3dpdGhfMTB4X0F6aXRtdXRoX0Fubm90YXRlZF9TQ1RfSFBDX3dpdGhvdXRfaGFybW9ueV9pbnRlZ3JhdGlvbi5yb2JqIikKCkFsbF9zYW1wbGVzX01lcmdlZAoKYGBgCgojIDMuIERhdGEgUFJFUEFSQVRJT04gYW5kIEhhcm1vbnkgSW50ZWdyYXRpb24tMQpgYGB7ciBkYXRhLCBmaWcuaGVpZ2h0PTgsIGZpZy53aWR0aD0xMn0KCmxpYnJhcnkoaGFybW9ueSkKCkFsbF9zYW1wbGVzX01lcmdlZCA8LSBSdW5IYXJtb255KAogIG9iamVjdCA9IEFsbF9zYW1wbGVzX01lcmdlZCwKICBncm91cC5ieS52YXJzID0gImNlbGxfbGluZSIsICAjIFJlcGxhY2Ugd2l0aCB0aGUgbWV0YWRhdGEgY29sdW1uIHNwZWNpZnlpbmcgYmF0Y2ggb3IgY2VsbCBsaW5lCiAgZGltcy51c2UgPSAxOjIyLCAgIyBVc2UgdGhlIHNhbWUgZGltZW5zaW9ucyBhcyBQQ0EKICBhc3NheS51c2UgPSAiU0NUIiwKcGxvdF9jb252ZXJnZW5jZSA9IFRSVUUKICApCgojIFJ1biBVTUFQIG9uIHRoZSBuZXcgSGFybW9ueSByZWR1Y3Rpb24KQWxsX3NhbXBsZXNfTWVyZ2VkIDwtIFJ1blVNQVAoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAiaGFybW9ueSIsIGRpbXMgPSAxOjIyLCByZWR1Y3Rpb24ubmFtZSA9ICJ1bWFwLmhhcm1vbnkiKQoKIyBGaW5kIG5laWdoYm9ycyBhbmQgY2x1c3RlcnMgdXNpbmcgdGhlIEhhcm1vbnkgcmVkdWN0aW9uCkFsbF9zYW1wbGVzX01lcmdlZCA8LSBGaW5kTmVpZ2hib3JzKEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gImhhcm1vbnkiLCBkaW1zID0gMToyMikKQWxsX3NhbXBsZXNfTWVyZ2VkIDwtIEZpbmRDbHVzdGVycyhBbGxfc2FtcGxlc19NZXJnZWQsIHJlc29sdXRpb24gPSAwLjUpCgojIFZpc3VhbGl6ZSByZXN1bHRzCnAxIDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lIikgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQnkgQ2VsbCBMaW5lIikKcDIgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJzZXVyYXRfY2x1c3RlcnMiKSArIAogIGdndGl0bGUoIkhhcm1vbnkgSW50ZWdyYXRpb24gLSBCeSBDbHVzdGVycyIpCgojIENvbXBhcmUgd2l0aCBvcmlnaW5hbCBVTUFQCnAzIDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcCIsIGdyb3VwLmJ5ID0gImNlbGxfbGluZSIpICsgCiAgZ2d0aXRsZSgiT3JpZ2luYWwgSW50ZWdyYXRpb24gLSBCeSBDZWxsIExpbmUiKQpwNCA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAiLCBncm91cC5ieSA9ICJzZXVyYXRfY2x1c3RlcnMiKSArIAogIGdndGl0bGUoIk9yaWdpbmFsIEludGVncmF0aW9uIC0gQnkgQ2x1c3RlcnMiKQoKIyBQcmludCB0aGUgcGxvdHMKcHJpbnQocDEgKyBwMikKcHJpbnQocDMgKyBwNCkKCgpgYGAKCiMjICBIYXJtb255IFZpc3VhbGl6YXRpb24tMQpgYGB7ciBoYXJtb255LXZpc3VhbGl6YXRpb24xLCBmaWcuaGVpZ2h0PTgsIGZpZy53aWR0aD0xMn0KCiMgVmlzdWFsaXplIHJlc3VsdHMKcDEgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLCBsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiSGFybW9ueSBJbnRlZ3JhdGlvbiAtIEJ5IENlbGwgTGluZSIpCnAyIDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAic2V1cmF0X2NsdXN0ZXJzIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiSGFybW9ueSBJbnRlZ3JhdGlvbiAtIEJ5IENsdXN0ZXJzIikKCiMgQ29tcGFyZSB3aXRoIG9yaWdpbmFsIFVNQVAKcDMgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwIiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiT3JpZ2luYWwgSW50ZWdyYXRpb24gLSBCeSBDZWxsIExpbmUiKQpwNCA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAiLCBncm91cC5ieSA9ICJzZXVyYXRfY2x1c3RlcnMiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJPcmlnaW5hbCBJbnRlZ3JhdGlvbiAtIEJ5IENsdXN0ZXJzIikKCiMgUHJpbnQgdGhlIHBsb3RzCnByaW50KHAxICsgcDIpCnByaW50KHAzICsgcDQpCgpgYGAKCgojIDQuIERhdGEgUFJFUEFSQVRJT04gYW5kIEhhcm1vbnkgSW50ZWdyYXRpb24tMgpgYGB7ciBkYXRhMiwgZmlnLmhlaWdodD04LCBmaWcud2lkdGg9MTJ9CgpsaWJyYXJ5KGhhcm1vbnkpCgpBbGxfc2FtcGxlc19NZXJnZWQgPC0gUnVuSGFybW9ueSgKICBvYmplY3QgPSBBbGxfc2FtcGxlc19NZXJnZWQsCiAgZ3JvdXAuYnkudmFycyA9ICJjZWxsX2xpbmUiLCAgIyBSZXBsYWNlIHdpdGggdGhlIG1ldGFkYXRhIGNvbHVtbiBzcGVjaWZ5aW5nIGJhdGNoIG9yIGNlbGwgbGluZQogIGRpbXMudXNlID0gMToyMiwgICMgVXNlIHRoZSBzYW1lIGRpbWVuc2lvbnMgYXMgUENBCiAgYXNzYXkudXNlID0gIlNDVCIsCiAgVGhldGEgPSAwLjUsCiAgbGFtYmRhID0wLjUsCiAgcGxvdF9jb252ZXJnZW5jZSA9IFRSVUUKICApCgojIFJ1biBVTUFQIG9uIHRoZSBuZXcgSGFybW9ueSByZWR1Y3Rpb24KQWxsX3NhbXBsZXNfTWVyZ2VkIDwtIFJ1blVNQVAoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAiaGFybW9ueSIsIGRpbXMgPSAxOjIyLCByZWR1Y3Rpb24ubmFtZSA9ICJ1bWFwLmhhcm1vbnkiKQoKIyBGaW5kIG5laWdoYm9ycyBhbmQgY2x1c3RlcnMgdXNpbmcgdGhlIEhhcm1vbnkgcmVkdWN0aW9uCkFsbF9zYW1wbGVzX01lcmdlZCA8LSBGaW5kTmVpZ2hib3JzKEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gImhhcm1vbnkiLCBkaW1zID0gMToyMikKQWxsX3NhbXBsZXNfTWVyZ2VkIDwtIEZpbmRDbHVzdGVycyhBbGxfc2FtcGxlc19NZXJnZWQsIHJlc29sdXRpb24gPSAwLjUpCmBgYAoKIyMgIEhhcm1vbnkgVmlzdWFsaXphdGlvbi0yCmBgYHtyIGhhcm1vbnktdmlzdWFsaXphdGlvbjIsIGZpZy5oZWlnaHQ9OCwgZmlnLndpZHRoPTEyfQoKIyBWaXN1YWxpemUgcmVzdWx0cwpwMSA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAuaGFybW9ueSIsIGdyb3VwLmJ5ID0gImNlbGxfbGluZSIsIGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQnkgQ2VsbCBMaW5lIikKcDIgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJzZXVyYXRfY2x1c3RlcnMiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQnkgQ2x1c3RlcnMiKQoKIyBDb21wYXJlIHdpdGggb3JpZ2luYWwgVU1BUApwMyA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJPcmlnaW5hbCBJbnRlZ3JhdGlvbiAtIEJ5IENlbGwgTGluZSIpCnA0IDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcCIsIGdyb3VwLmJ5ID0gInNldXJhdF9jbHVzdGVycyIsbGFiZWwgPSBULCBsYWJlbC5ib3ggPSBUKSArIAogIGdndGl0bGUoIk9yaWdpbmFsIEludGVncmF0aW9uIC0gQnkgQ2x1c3RlcnMiKQoKIyBQcmludCB0aGUgcGxvdHMKcHJpbnQocDEgKyBwMikKcHJpbnQocDMgKyBwNCkKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLCBsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiSGFybW9ueSBJbnRlZ3JhdGlvbiAtIEJ5IENlbGwgTGluZSIpCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAic2V1cmF0X2NsdXN0ZXJzIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiSGFybW9ueSBJbnRlZ3JhdGlvbiAtIEJ5IENsdXN0ZXJzIikKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJwcmVkaWN0ZWQuY2VsbHR5cGUubDIiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQW5ub3RhdGlvbnMiKQoKYGBgCgojIDUuIERhdGEgUFJFUEFSQVRJT04gYW5kIEhhcm1vbnkgSW50ZWdyYXRpb24tMwpgYGB7ciBkYXRhMywgZmlnLmhlaWdodD04LCBmaWcud2lkdGg9MTJ9CgojIENyZWF0ZSBhIG5ldyBtZXRhZGF0YSBjb2x1bW4gZm9yIGdyb3VwaW5nCkFsbF9zYW1wbGVzX01lcmdlZCRzYW1wbGVfZ3JvdXAgPC0gY2FzZV93aGVuKAogIGdyZXBsKCJeTCIsIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUpIH4gIkNlbGxfTGluZSIsCiAgQWxsX3NhbXBsZXNfTWVyZ2VkJGNlbGxfbGluZSA9PSAiUEJNQyIgfiAiUEJNQyIsCiAgQWxsX3NhbXBsZXNfTWVyZ2VkJGNlbGxfbGluZSA9PSAiUEJNQ18xMHgiIH4gIlBCTUNfMTB4IiwKICBUUlVFIH4gIk90aGVyIgopCgojIENyZWF0ZSB0aGUgY2VsbCBsaW5lIGdyb3VwaW5nIGNvcnJlY3RseQpBbGxfc2FtcGxlc19NZXJnZWQkY2VsbF9saW5lX2dyb3VwIDwtIGNhc2Vfd2hlbigKICBncmVwbCgiXkxbMS0yXSIsIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUpIH4gIlAxIiwKICBncmVwbCgiXkxbMy00XSIsIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUpIH4gIlAyIiwKICBncmVwbCgiXkxbNS03XSIsIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUpIH4gIlAzIiwKICBBbGxfc2FtcGxlc19NZXJnZWQkY2VsbF9saW5lID09ICJQQk1DIiB+ICJQQk1DIiwKICBBbGxfc2FtcGxlc19NZXJnZWQkY2VsbF9saW5lID09ICJQQk1DXzEweCIgfiAiUEJNQ18xMHgiLAogIFRSVUUgfiAiT3RoZXIiICAjIFRoaXMgY2F0Y2hlcyBhbnkgdW5leHBlY3RlZCB2YWx1ZXMKKQoKbGlicmFyeShoYXJtb255KQoKQWxsX3NhbXBsZXNfTWVyZ2VkIDwtIFJ1bkhhcm1vbnkoCiAgb2JqZWN0ID0gQWxsX3NhbXBsZXNfTWVyZ2VkLAogIGdyb3VwLmJ5LnZhcnMgPSAic2FtcGxlX2dyb3VwIiwKICBkaW1zLnVzZSA9IDE6MjIsICAjIEluY3JlYXNlZCB0byBjYXB0dXJlIG1vcmUgdmFyaWF0aW9uCiAgdGhldGEgPSBjKDAuNSksICAjIEFkanVzdCB0aGVzZSB2YWx1ZXMgYXMgbmVlZGVkCiAgcGxvdF9jb252ZXJnZW5jZSA9IFRSVUUKKQoKIyBSdW4gVU1BUCBvbiB0aGUgbmV3IEhhcm1vbnkgcmVkdWN0aW9uCkFsbF9zYW1wbGVzX01lcmdlZCA8LSBSdW5VTUFQKEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gImhhcm1vbnkiLCBkaW1zID0gMToyMiwgcmVkdWN0aW9uLm5hbWUgPSAidW1hcC5oYXJtb255IikKCiMgRmluZCBuZWlnaGJvcnMgYW5kIGNsdXN0ZXJzIHVzaW5nIHRoZSBIYXJtb255IHJlZHVjdGlvbgpBbGxfc2FtcGxlc19NZXJnZWQgPC0gRmluZE5laWdoYm9ycyhBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJoYXJtb255IiwgZGltcyA9IDE6MjIpCkFsbF9zYW1wbGVzX01lcmdlZCA8LSBGaW5kQ2x1c3RlcnMoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZXNvbHV0aW9uID0gMC41KQoKYGBgCgojIyAgSGFybW9ueSBWaXN1YWxpemF0aW9uLTMKYGBge3IgaGFybW9ueS12aXN1YWxpemF0aW9uMywgZmlnLmhlaWdodD04LCBmaWcud2lkdGg9MTJ9CgoKcDEgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJzYW1wbGVfZ3JvdXAiLCBsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCnAyIDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lX2dyb3VwIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCnAzIDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCgpwMSArIHAyICsgcDMKCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAic2FtcGxlX2dyb3VwIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lX2dyb3VwIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCgoKCiMgQ29tcGFyZSB3aXRoIG9yaWdpbmFsIFVNQVAKcDQgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwIiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiT3JpZ2luYWwgSW50ZWdyYXRpb24gLSBCeSBDZWxsIExpbmUiKQpwNSA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAiLCBncm91cC5ieSA9ICJzZXVyYXRfY2x1c3RlcnMiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJPcmlnaW5hbCBJbnRlZ3JhdGlvbiAtIEJ5IENsdXN0ZXJzIikKCiMgUHJpbnQgdGhlIHBsb3RzCnByaW50KHA0ICsgcDUpCgpEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJPcmlnaW5hbCBJbnRlZ3JhdGlvbiAtIEJ5IENlbGwgTGluZSIpCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcCIsIGdyb3VwLmJ5ID0gInNldXJhdF9jbHVzdGVycyIsbGFiZWwgPSBULCBsYWJlbC5ib3ggPSBUKSArIAogIGdndGl0bGUoIk9yaWdpbmFsIEludGVncmF0aW9uIC0gQnkgQ2x1c3RlcnMiKQoKIyBWaXN1YWxpemUgcmVzdWx0cwpwNiA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAuaGFybW9ueSIsIGdyb3VwLmJ5ID0gImNlbGxfbGluZSIsIGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQnkgQ2VsbCBMaW5lIikKcDcgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJzZXVyYXRfY2x1c3RlcnMiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQnkgQ2x1c3RlcnMiKQojIFByaW50IHRoZSBwbG90cwpwcmludChwNiArIHA3KQoKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLCBsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiSGFybW9ueSBJbnRlZ3JhdGlvbiAtIEJ5IENlbGwgTGluZSIpCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAic2V1cmF0X2NsdXN0ZXJzIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiSGFybW9ueSBJbnRlZ3JhdGlvbiAtIEJ5IENsdXN0ZXJzIikKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJwcmVkaWN0ZWQuY2VsbHR5cGUubDIiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQW5ub3RhdGlvbnMiKQoKYGBgCiMgNi4gRGF0YSBQUkVQQVJBVElPTiBhbmQgSGFybW9ueSBJbnRlZ3JhdGlvbi00CmBgYHtyIGRhdGE0LCBmaWcuaGVpZ2h0PTgsIGZpZy53aWR0aD0xMn0KCiMgQ3JlYXRlIGEgbmV3IG1ldGFkYXRhIGNvbHVtbiBmb3IgZ3JvdXBpbmcKQWxsX3NhbXBsZXNfTWVyZ2VkJHNhbXBsZV9ncm91cCA8LSBjYXNlX3doZW4oCiAgZ3JlcGwoIl5MIiwgQWxsX3NhbXBsZXNfTWVyZ2VkJGNlbGxfbGluZSkgfiAiQ2VsbF9MaW5lIiwKICBBbGxfc2FtcGxlc19NZXJnZWQkY2VsbF9saW5lID09ICJQQk1DIiB+ICJQQk1DIiwKICBBbGxfc2FtcGxlc19NZXJnZWQkY2VsbF9saW5lID09ICJQQk1DXzEweCIgfiAiUEJNQ18xMHgiLAogIFRSVUUgfiAiT3RoZXIiCikKCiMgQ3JlYXRlIHRoZSBjZWxsIGxpbmUgZ3JvdXBpbmcgY29ycmVjdGx5CkFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmVfZ3JvdXAgPC0gY2FzZV93aGVuKAogIGdyZXBsKCJeTFsxLTJdIiwgQWxsX3NhbXBsZXNfTWVyZ2VkJGNlbGxfbGluZSkgfiAiUDEiLAogIGdyZXBsKCJeTFszLTRdIiwgQWxsX3NhbXBsZXNfTWVyZ2VkJGNlbGxfbGluZSkgfiAiUDIiLAogIGdyZXBsKCJeTFs1LTddIiwgQWxsX3NhbXBsZXNfTWVyZ2VkJGNlbGxfbGluZSkgfiAiUDMiLAogIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUgPT0gIlBCTUMiIH4gIlBCTUMiLAogIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUgPT0gIlBCTUNfMTB4IiB+ICJQQk1DXzEweCIsCiAgVFJVRSB+ICJPdGhlciIgICMgVGhpcyBjYXRjaGVzIGFueSB1bmV4cGVjdGVkIHZhbHVlcwopCgpsaWJyYXJ5KGhhcm1vbnkpCgpBbGxfc2FtcGxlc19NZXJnZWQgPC0gUnVuSGFybW9ueSgKICBvYmplY3QgPSBBbGxfc2FtcGxlc19NZXJnZWQsCiAgZ3JvdXAuYnkudmFycyA9ICJjZWxsX2xpbmVfZ3JvdXAiLAogIGRpbXMudXNlID0gMToyMiwgICMgSW5jcmVhc2VkIHRvIGNhcHR1cmUgbW9yZSB2YXJpYXRpb24KICB0aGV0YSA9IGMoMC41KSwgICMgQWRqdXN0IHRoZXNlIHZhbHVlcyBhcyBuZWVkZWQKICBwbG90X2NvbnZlcmdlbmNlID0gVFJVRQopCgojIFJ1biBVTUFQIG9uIHRoZSBuZXcgSGFybW9ueSByZWR1Y3Rpb24KQWxsX3NhbXBsZXNfTWVyZ2VkIDwtIFJ1blVNQVAoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAiaGFybW9ueSIsIGRpbXMgPSAxOjIyLCByZWR1Y3Rpb24ubmFtZSA9ICJ1bWFwLmhhcm1vbnkiKQoKIyBGaW5kIG5laWdoYm9ycyBhbmQgY2x1c3RlcnMgdXNpbmcgdGhlIEhhcm1vbnkgcmVkdWN0aW9uCkFsbF9zYW1wbGVzX01lcmdlZCA8LSBGaW5kTmVpZ2hib3JzKEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gImhhcm1vbnkiLCBkaW1zID0gMToyMikKQWxsX3NhbXBsZXNfTWVyZ2VkIDwtIEZpbmRDbHVzdGVycyhBbGxfc2FtcGxlc19NZXJnZWQsIHJlc29sdXRpb24gPSAwLjUpCgpgYGAKCiMjICBIYXJtb255IFZpc3VhbGl6YXRpb24tNApgYGB7ciBoYXJtb255LXZpc3VhbGl6YXRpb240LCBmaWcuaGVpZ2h0PTgsIGZpZy53aWR0aD0xMn0KCgpwMSA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAuaGFybW9ueSIsIGdyb3VwLmJ5ID0gInNhbXBsZV9ncm91cCIsIGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkKcDIgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJjZWxsX2xpbmVfZ3JvdXAiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkKcDMgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkKCnAxICsgcDIgKyBwMwoKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJzYW1wbGVfZ3JvdXAiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJjZWxsX2xpbmVfZ3JvdXAiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkKCgoKIyBDb21wYXJlIHdpdGggb3JpZ2luYWwgVU1BUApwNCA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJPcmlnaW5hbCBJbnRlZ3JhdGlvbiAtIEJ5IENlbGwgTGluZSIpCnA1IDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcCIsIGdyb3VwLmJ5ID0gInNldXJhdF9jbHVzdGVycyIsbGFiZWwgPSBULCBsYWJlbC5ib3ggPSBUKSArIAogIGdndGl0bGUoIk9yaWdpbmFsIEludGVncmF0aW9uIC0gQnkgQ2x1c3RlcnMiKQoKIyBQcmludCB0aGUgcGxvdHMKcHJpbnQocDQgKyBwNSkKCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcCIsIGdyb3VwLmJ5ID0gImNlbGxfbGluZSIsbGFiZWwgPSBULCBsYWJlbC5ib3ggPSBUKSArIAogIGdndGl0bGUoIk9yaWdpbmFsIEludGVncmF0aW9uIC0gQnkgQ2VsbCBMaW5lIikKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwIiwgZ3JvdXAuYnkgPSAic2V1cmF0X2NsdXN0ZXJzIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiT3JpZ2luYWwgSW50ZWdyYXRpb24gLSBCeSBDbHVzdGVycyIpCgojIFZpc3VhbGl6ZSByZXN1bHRzCnA2IDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lIiwgbGFiZWwgPSBULCBsYWJlbC5ib3ggPSBUKSArIAogIGdndGl0bGUoIkhhcm1vbnkgSW50ZWdyYXRpb24gLSBCeSBDZWxsIExpbmUiKQpwNyA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAuaGFybW9ueSIsIGdyb3VwLmJ5ID0gInNldXJhdF9jbHVzdGVycyIsbGFiZWwgPSBULCBsYWJlbC5ib3ggPSBUKSArIAogIGdndGl0bGUoIkhhcm1vbnkgSW50ZWdyYXRpb24gLSBCeSBDbHVzdGVycyIpCiMgUHJpbnQgdGhlIHBsb3RzCnByaW50KHA2ICsgcDcpCgpEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAuaGFybW9ueSIsIGdyb3VwLmJ5ID0gImNlbGxfbGluZSIsIGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQnkgQ2VsbCBMaW5lIikKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJzZXVyYXRfY2x1c3RlcnMiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQnkgQ2x1c3RlcnMiKQpEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAuaGFybW9ueSIsIGdyb3VwLmJ5ID0gInByZWRpY3RlZC5jZWxsdHlwZS5sMiIsbGFiZWwgPSBULCBsYWJlbC5ib3ggPSBUKSArIAogIGdndGl0bGUoIkhhcm1vbnkgSW50ZWdyYXRpb24gLSBBbm5vdGF0aW9ucyIpCgpgYGAKCgojIDcuIERhdGEgUFJFUEFSQVRJT04gYW5kIEhhcm1vbnkgSW50ZWdyYXRpb24tNQpgYGB7ciBkYXRhNSwgZmlnLmhlaWdodD04LCBmaWcud2lkdGg9MTJ9CgojIENyZWF0ZSBhIG5ldyBtZXRhZGF0YSBjb2x1bW4gZm9yIGdyb3VwaW5nCkFsbF9zYW1wbGVzX01lcmdlZCRzYW1wbGVfZ3JvdXAgPC0gY2FzZV93aGVuKAogIGdyZXBsKCJeTCIsIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUpIH4gIkNlbGxfTGluZSIsCiAgQWxsX3NhbXBsZXNfTWVyZ2VkJGNlbGxfbGluZSA9PSAiUEJNQyIgfiAiUEJNQyIsCiAgQWxsX3NhbXBsZXNfTWVyZ2VkJGNlbGxfbGluZSA9PSAiUEJNQ18xMHgiIH4gIlBCTUNfMTB4IiwKICBUUlVFIH4gIk90aGVyIgopCgojIENyZWF0ZSB0aGUgY2VsbCBsaW5lIGdyb3VwaW5nIGNvcnJlY3RseQpBbGxfc2FtcGxlc19NZXJnZWQkY2VsbF9saW5lX2dyb3VwIDwtIGNhc2Vfd2hlbigKICBncmVwbCgiXkxbMS0yXSIsIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUpIH4gIlAxIiwKICBncmVwbCgiXkxbMy00XSIsIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUpIH4gIlAyIiwKICBncmVwbCgiXkxbNS03XSIsIEFsbF9zYW1wbGVzX01lcmdlZCRjZWxsX2xpbmUpIH4gIlAzIiwKICBBbGxfc2FtcGxlc19NZXJnZWQkY2VsbF9saW5lID09ICJQQk1DIiB+ICJQQk1DIiwKICBBbGxfc2FtcGxlc19NZXJnZWQkY2VsbF9saW5lID09ICJQQk1DXzEweCIgfiAiUEJNQ18xMHgiLAogIFRSVUUgfiAiT3RoZXIiICAjIFRoaXMgY2F0Y2hlcyBhbnkgdW5leHBlY3RlZCB2YWx1ZXMKKQoKbGlicmFyeShoYXJtb255KQoKQWxsX3NhbXBsZXNfTWVyZ2VkIDwtIFJ1bkhhcm1vbnkoCiAgb2JqZWN0ID0gQWxsX3NhbXBsZXNfTWVyZ2VkLAogIGdyb3VwLmJ5LnZhcnMgPSAiY2VsbF9saW5lIiwKICBkaW1zLnVzZSA9IDE6MjIsICAjIEluY3JlYXNlZCB0byBjYXB0dXJlIG1vcmUgdmFyaWF0aW9uCiAgdGhldGEgPSBjKDAuNSksICAjIEFkanVzdCB0aGVzZSB2YWx1ZXMgYXMgbmVlZGVkCiAgcGxvdF9jb252ZXJnZW5jZSA9IFRSVUUKKQoKIyBSdW4gVU1BUCBvbiB0aGUgbmV3IEhhcm1vbnkgcmVkdWN0aW9uCkFsbF9zYW1wbGVzX01lcmdlZCA8LSBSdW5VTUFQKEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gImhhcm1vbnkiLCBkaW1zID0gMToyMiwgcmVkdWN0aW9uLm5hbWUgPSAidW1hcC5oYXJtb255IikKCiMgRmluZCBuZWlnaGJvcnMgYW5kIGNsdXN0ZXJzIHVzaW5nIHRoZSBIYXJtb255IHJlZHVjdGlvbgpBbGxfc2FtcGxlc19NZXJnZWQgPC0gRmluZE5laWdoYm9ycyhBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJoYXJtb255IiwgZGltcyA9IDE6MjIpCkFsbF9zYW1wbGVzX01lcmdlZCA8LSBGaW5kQ2x1c3RlcnMoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZXNvbHV0aW9uID0gMC41KQoKYGBgCgojIyAgSGFybW9ueSBWaXN1YWxpemF0aW9uLTUKYGBge3IgaGFybW9ueS12aXN1YWxpemF0aW9uNSwgZmlnLmhlaWdodD04LCBmaWcud2lkdGg9MTJ9CgoKcDEgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJzYW1wbGVfZ3JvdXAiLCBsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCnAyIDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lX2dyb3VwIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCnAzIDwtIERpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCgpwMSArIHAyICsgcDMKCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAic2FtcGxlX2dyb3VwIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lX2dyb3VwIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpCgoKCiMgQ29tcGFyZSB3aXRoIG9yaWdpbmFsIFVNQVAKcDQgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwIiwgZ3JvdXAuYnkgPSAiY2VsbF9saW5lIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiT3JpZ2luYWwgSW50ZWdyYXRpb24gLSBCeSBDZWxsIExpbmUiKQpwNSA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAiLCBncm91cC5ieSA9ICJzZXVyYXRfY2x1c3RlcnMiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJPcmlnaW5hbCBJbnRlZ3JhdGlvbiAtIEJ5IENsdXN0ZXJzIikKCiMgUHJpbnQgdGhlIHBsb3RzCnByaW50KHA0ICsgcDUpCgpEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJPcmlnaW5hbCBJbnRlZ3JhdGlvbiAtIEJ5IENlbGwgTGluZSIpCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcCIsIGdyb3VwLmJ5ID0gInNldXJhdF9jbHVzdGVycyIsbGFiZWwgPSBULCBsYWJlbC5ib3ggPSBUKSArIAogIGdndGl0bGUoIk9yaWdpbmFsIEludGVncmF0aW9uIC0gQnkgQ2x1c3RlcnMiKQoKIyBWaXN1YWxpemUgcmVzdWx0cwpwNiA8LSBEaW1QbG90KEFsbF9zYW1wbGVzX01lcmdlZCwgcmVkdWN0aW9uID0gInVtYXAuaGFybW9ueSIsIGdyb3VwLmJ5ID0gImNlbGxfbGluZSIsIGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQnkgQ2VsbCBMaW5lIikKcDcgPC0gRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJzZXVyYXRfY2x1c3RlcnMiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQnkgQ2x1c3RlcnMiKQojIFByaW50IHRoZSBwbG90cwpwcmludChwNiArIHA3KQoKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJjZWxsX2xpbmUiLCBsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiSGFybW9ueSBJbnRlZ3JhdGlvbiAtIEJ5IENlbGwgTGluZSIpCkRpbVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCByZWR1Y3Rpb24gPSAidW1hcC5oYXJtb255IiwgZ3JvdXAuYnkgPSAic2V1cmF0X2NsdXN0ZXJzIixsYWJlbCA9IFQsIGxhYmVsLmJveCA9IFQpICsgCiAgZ2d0aXRsZSgiSGFybW9ueSBJbnRlZ3JhdGlvbiAtIEJ5IENsdXN0ZXJzIikKRGltUGxvdChBbGxfc2FtcGxlc19NZXJnZWQsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBncm91cC5ieSA9ICJwcmVkaWN0ZWQuY2VsbHR5cGUubDIiLGxhYmVsID0gVCwgbGFiZWwuYm94ID0gVCkgKyAKICBnZ3RpdGxlKCJIYXJtb255IEludGVncmF0aW9uIC0gQW5ub3RhdGlvbnMiKQoKYGBgCgojIyAgTWFya2VyIEdlbmUgVmlzdWFsaXphdGlvbgpgYGB7ciBmZWF0dXJlcGxvdC1oYXJtb255LCBmaWcuaGVpZ2h0PTE0LCBmaWcud2lkdGg9MTh9CgoKIyBTZXQgbWFya2VyIGdlbmVzIHNwZWNpZmljIHRvIHJlcXVlc3RlZCBpbW11bmUgY2VsbCB0eXBlcwpteWZlYXR1cmVzIDwtIGMoIkNEMTkiLCAiQ0Q3OUEiLCAiTVM0QTEiLCAjIEIgY2VsbHMKICAgICAgICAgICAgICAgICJDRDE0IiwgIkxZWiIsICJGQ0dSM0EiLCAjIE1vbm9jeXRlcwogICAgICAgICAgICAgICAgIkNTRjFSIiwgIkNENjgiLCAjIE1hY3JvcGhhZ2VzCiAgICAgICAgICAgICAgICAiTktHNyIsICJHTkxZIiwgIktJUjNETDEiLCAjIE5LIGNlbGxzCiAgICAgICAgICAgICAgICAiTUtJNjciLCAjIFByb2xpZmVyYXRpbmcgTksgY2VsbHMKICAgICAgICAgICAgICAgICJDRDM0IiwgIktJVCIsICMgSFNQQ3MKICAgICAgICAgICAgICAgICJDRDNFIiwgIkNDUjciLCAjIFQgY2VsbHMKICAgICAgICAgICAgICAgICJTRUxMIiwgIkNENDVSTyIsICMgVG5haXZlLCBUY20KICAgICAgICAgICAgICAgICJDRDQ0IiwgIkNENDVSQSIpICMgVGVtLCBUZW1yYQojIFZpc3VhbGl6ZSBtYXJrZXIgZ2VuZXMgZm9yIEhhcm1vbnkKRmVhdHVyZVBsb3QoQWxsX3NhbXBsZXNfTWVyZ2VkLCBmZWF0dXJlcyA9IG15ZmVhdHVyZXMsIHJlZHVjdGlvbiA9ICJ1bWFwLmhhcm1vbnkiLCBuY29sID0gNCkgKyAKICBnZ3RpdGxlKCJNYXJrZXIgR2VuZSBFeHByZXNzaW9uIC0gSGFybW9ueSBJbnRlZ3JhdGlvbiIpICsKICBOb0xlZ2VuZCgpCmBgYAoKIyA2LiBTYXZlIHRoZSBTZXVyYXQgb2JqZWN0IGFzIGFuIFJvYmogZmlsZQpgYGB7ciBzYXZlUk9CSn0KCiNzYXZlKEFsbF9zYW1wbGVzX01lcmdlZCwgZmlsZSA9ICJpbnRlZ3JhdGVkX0FsbF9zYW1wbGVzX01lcmdlZF93aXRoX1BCTUMxMHguUm9iaiIpCgpgYGAKCgoKCg==