1 Functions

library(stringi)
source_from_github(repositoy = "DEG_functions",version = "0.2.47")
source_from_github(repositoy = "cNMF_functions",version = "0.4.0",script_name = "cnmf_functions_V3.R")
source_from_github(repositoy = "sc_general_functions",version = "0.1.28",script_name = "functions.R")

2 Data

source_from_github(repositoy = "DEG_functions",version = "0.2.47")
ℹ SHA-1 hash of file is f5bb1cd741d13bded83fe3b6fd43169e29731216

3 ACC all cells UMAP

DimPlot(acc_all)

4 Neuronal signatures

for (neural_name in colnames(neuronal_signatures)) {
  genes = neuronal_signatures[,neural_name,drop=T]
  # Assuming df is your data frame

  
  pathways_scores = FetchData(object = acc_all,vars = genes,slot = "data") %>% 
    mutate_all(~ 2^.)%>% mutate_all(~ .-1) %>%  #covert log(TPM+1) to TPM
    rowwise() %>% mutate(score = mean(c_across(everything()))) #mean
  acc_all  %<>% AddMetaData(metadata = pathways_scores$score,col.name = neural_name)
}

Warning in FetchData.Seurat(object = acc_all, vars = genes, slot = “data”) : The following requested variables were not found: SNHG29, NOP53 Warning in FetchData.Seurat(object = acc_all, vars = genes, slot = “data”) : The following requested variables were not found: NOP53 Warning in FetchData.Seurat(object = acc_all, vars = genes, slot = “data”) : The following requested variables were not found: NOP53

plt = VlnPlot(object = acc_all,features = colnames(neuronal_signatures))
plt[[1]] = plt[[1]]+ ylab("TPM")
plt[[4]] = plt[[4]]+ ylab("TPM")
plt[[7]] = plt[[7]]+ ylab("TPM")
plt
Warning in grSoftVersion() :
  unable to load shared object '/usr/local/lib/R/modules//R_X11.so':
  libXt.so.6: cannot open shared object file: No such file or directory

4.1 Neuronal signatures expression

for (neural_name in colnames(neuronal_signatures)) {
  genes = neuronal_signatures[,neural_name,drop=T]
  # Assuming df is your data frame
  print_tab(
    DoHeatmap(object = acc_tpm,features = genes,slot = "counts",combine = T,disp.max = 5000)+ labs(fill = "TPM") 
  ,title = neural_name,subtitle_num = 3)
}

Sympathetic_cholinergic_neuron

Sympathetic_noradrenergic_neuron

Peripheral_nervous_system_neuron_

Warning in DoHeatmap(object = acc_tpm, features = genes, slot = “counts”, : The following features were omitted as they were not found in the counts slot for the RNA assay: NOP53, SNHG29

Autonomic_neuron

Peripheral_neuron

Sensory_neuron

Warning in DoHeatmap(object = acc_tpm, features = genes, slot = “counts”, : The following features were omitted as they were not found in the counts slot for the RNA assay: NOP53

Adrenergic_neuron_tabula_sapiens

Warning in DoHeatmap(object = acc_tpm, features = genes, slot = “counts”, : The following features were omitted as they were not found in the counts slot for the RNA assay: NOP53

Peripheral_sensory_neuron

Parasympathetic_neuron

NA

4.2 WBC

wbc_cells = subset(acc_all, subset = cell.type == "WBC")
wbc_cells <- FindNeighbors(wbc_cells, dims = 1:10,verbose = F) %>%  FindClusters(resolution = 0.5) %>%  RunUMAP(dims = 1:10,verbose = F)
Modularity Optimizer version 1.3.0 by Ludo Waltman and Nees Jan van Eck

Number of nodes: 33
Number of edges: 528

Running Louvain algorithm...
0%   10   20   30   40   50   60   70   80   90   100%
[----|----|----|----|----|----|----|----|----|----|
**************************************************|
Maximum modularity in 10 random starts: 0.5572
Number of communities: 2
Elapsed time: 0 seconds
DimPlot(wbc_cells)

WBC devided into 2 clusters:

VlnPlot(object = wbc_cells,features = c("CD79A","PTPRC"))

4.3 WBC Neuronal signatures

4.4 CD79A neuronal_signatures correlation

library(ggpubr)
for (neural_name in colnames(neuronal_signatures)) {
  wbc_cells = subset(acc_all, subset = cell.type == "WBC")
  data = FetchData(object = wbc_cells,vars = c(neural_name,"CD79A"))
  p = ggplot(data, aes_string(x=neural_name, y="CD79A")) + 
           geom_point()+
           geom_smooth(method=lm) +
           stat_cor()
  print_tab(p,title  = neural_name,subtitle_num = 3)
}

Sympathetic_cholinergic_neuron

geom_smooth() using formula ‘y ~ x’

Sympathetic_noradrenergic_neuron

geom_smooth() using formula ‘y ~ x’

Peripheral_nervous_system_neuron_

geom_smooth() using formula ‘y ~ x’

Autonomic_neuron

geom_smooth() using formula ‘y ~ x’

Peripheral_neuron

geom_smooth() using formula ‘y ~ x’

Sensory_neuron

geom_smooth() using formula ‘y ~ x’

Adrenergic_neuron_tabula_sapiens

geom_smooth() using formula ‘y ~ x’

Peripheral_sensory_neuron

geom_smooth() using formula ‘y ~ x’

Parasympathetic_neuron

geom_smooth() using formula ‘y ~ x’

NA

4.5 PTPRC neuronal_signatures correlation

library(ggpubr)
for (neural_name in colnames(neuronal_signatures)) {
  wbc_cells = subset(acc_all, subset = cell.type == "WBC")
  data = FetchData(object = wbc_cells,vars = c(neural_name,"PTPRC"))
  p = ggplot(data, aes_string(x=neural_name, y="PTPRC")) + 
           geom_point()+
           geom_smooth(method=lm) +
           stat_cor()
  print_tab(p,title  = neural_name,subtitle_num = 3)
}

Sympathetic_cholinergic_neuron

geom_smooth() using formula ‘y ~ x’

Sympathetic_noradrenergic_neuron

geom_smooth() using formula ‘y ~ x’

Peripheral_nervous_system_neuron_

geom_smooth() using formula ‘y ~ x’

Autonomic_neuron

geom_smooth() using formula ‘y ~ x’

Peripheral_neuron

geom_smooth() using formula ‘y ~ x’

Sensory_neuron

geom_smooth() using formula ‘y ~ x’

Adrenergic_neuron_tabula_sapiens

geom_smooth() using formula ‘y ~ x’

Peripheral_sensory_neuron

geom_smooth() using formula ‘y ~ x’

Parasympathetic_neuron

geom_smooth() using formula ‘y ~ x’

NA

6 Neuronal pathways in ACC cancer cells

6.1 dim reduction

acc_cancer <- RunPCA(acc_cancer, features = VariableFeatures(object = acc_cancer),verbose = F)
ElbowPlot(acc_cancer)
acc_cancer <- FindNeighbors(acc_cancer, dims = 1:10,verbose = F) %>%  FindClusters(resolution = 0.5) %>%  RunUMAP(dims = 1:10,verbose = F)
DimPlot(acc_cancer,group.by = "patient.ident")
for (pathway_name in names(neuronal_pathways)) {
  genes = neuronal_pathways[[pathway_name]]
  pathways_scores = FetchData(object = acc_cancer,vars = genes,slot = "data") %>% 
    mutate_all(~ 2^.)%>% mutate_all(~ .-1) %>%  #covert log(TPM+1) to TPM
    rowwise() %>% mutate(score = mean(c_across(everything()))) #mean
  acc_cancer  %<>% AddMetaData(metadata = pathways_scores$score,col.name = pathway_name)
}

6.2 Scores UMAP


plt = FeaturePlot(object = acc_cancer,features = names(neuronal_pathways))
for (i in 1:(length(plt$patches$plots)+1)) {
  plt[[i]] = plt[[i]] + theme(plot.title = element_text(size=10.5))+ labs(color='TPM')
}
print_tab(plt,title = "UMAP" ,subtitle_num = 3)

UMAP

plt = FeaturePlot(object = acc_cancer,features = names(neuronal_pathways),max.cutoff = 50)
for (i in 1:(length(plt$patches$plots)+1)) {
  plt[[i]] = plt[[i]] + theme(plot.title = element_text(size=10.5))+ labs(color='TPM')
}
print_tab(plt,title = "UMAP max=50" ,subtitle_num = 3)

UMAP max=50

plt = FeaturePlot(object = acc_cancer,features = names(neuronal_pathways),max.cutoff = 250)
for (i in 1:(length(plt$patches$plots)+1)) {
  plt[[i]] = plt[[i]] + theme(plot.title = element_text(size=10.5))+ labs(color='TPM')
}
print_tab(plt,title = "UMAP max=250" ,subtitle_num = 3)

UMAP max=250

plt = FeaturePlot(object = acc_cancer,features = names(neuronal_pathways))
for (i in 1:(length(plt$patches$plots)+1)) {
  plt[[i]] = plt[[i]] + theme(plot.title = element_text(size=10.5))+ labs(color='TPM') + scale_color_gradientn(colours = rainbow(5))
}

Scale for ‘colour’ is already present. Adding another scale for ‘colour’, which will replace the existing scale. Scale for ‘colour’ is already present. Adding another scale for ‘colour’, which will replace the existing scale. Scale for ‘colour’ is already present. Adding another scale for ‘colour’, which will replace the existing scale. Scale for ‘colour’ is already present. Adding another scale for ‘colour’, which will replace the existing scale. Scale for ‘colour’ is already present. Adding another scale for ‘colour’, which will replace the existing scale. Scale for ‘colour’ is already present. Adding another scale for ‘colour’, which will replace the existing scale. Scale for ‘colour’ is already present. Adding another scale for ‘colour’, which will replace the existing scale. Scale for ‘colour’ is already present. Adding another scale for ‘colour’, which will replace the existing scale.

print_tab(plt,title = "UMAP rainbow" ,subtitle_num = 3)

UMAP rainbow

NA

6.3 Scores violin

 plt = VlnPlot(object = acc_cancer,features = names(neuronal_pathways),group.by = "patient.ident")+theme(plot.title = element_text(size = 3))
 
for (i in 1:(length(plt$patches$plots)+1)) {
  plt[[i]] = plt[[i]] + theme(plot.title = element_text(size=9.5))
  if (i %in% c(1,4,7)) {
    plt[[i]] = plt[[i]]+ylab("TPM")
  }
}
print(plt)

7 ACC2 DEG

acc_cancer_pri = SetIdent(object = acc_cancer_pri,value = "patient.ident")
markers = FindMarkers(object = acc_cancer_pri,ident.1 = "ACC2",features = VariableFeatures(acc_cancer_pri),densify = T)
volcano_plot(de_genes = markers,max_names = 10,title = "",ident1 = "ACC2",ident2 = "PNI patients",show_graph = F,log2fc_cutoff = 1)

7.1 GSEA- canonical pathways

up = up in ACC2

library(hypeR)
genesets <- msigdb_download("Homo sapiens",category="H") %>% append( msigdb_download("Homo sapiens",category="C2",subcategory = "CP"))
all_genes = markers  %>%  arrange(desc(avg_log2FC)) %>% select("avg_log2FC") 
ranked_list   <- setNames(all_genes$avg_log2FC, rownames(all_genes))
hyp_obj <- hypeR_fgsea(signature = ranked_list,genesets =  genesets,up_only = F)
hyp_dots(hyp_obj)

7.2 GSEA- GO BP

genesets <- msigdb_download("Homo sapiens",category="H") %>% append( msigdb_download("Homo sapiens",category="C5",subcategory = "GO:BP"))
all_genes = markers  %>%  arrange(desc(avg_log2FC)) %>% select("avg_log2FC") 
ranked_list   <- setNames(all_genes$avg_log2FC, rownames(all_genes))
hyp_obj <- hypeR_fgsea(signature = ranked_list,genesets =  genesets,up_only = F)
hyp_dots(hyp_obj)

8 Neuronal pathways in ACC primary cancer cells

lum_score = FetchData(acc_cancer_pri,"luminal_over_myo")
lum_score  %<>% mutate (lum_or_myo = case_when(
         luminal_over_myo > 1 ~ "luminal",
         luminal_over_myo < (-1) ~ "myo",
         TRUE ~ "unknown"))
acc_cancer_pri  %<>% AddMetaData(metadata = lum_score$lum_or_myo,col.name = "lum_or_myo")
for (pathway_name in names(neuronal_pathways)) {
  genes = neuronal_pathways[[pathway_name]]
 pathways_scores = FetchData(object = acc_cancer_pri,vars = genes,slot = "data") %>% 
    mutate_all(~ 2^.)%>% mutate_all(~ .-1) %>%  #covert log(TPM+1) to TPM
    rowwise() %>% mutate(score = mean(c_across(everything()))) #mean
  acc_cancer_pri  %<>% AddMetaData(metadata = pathways_scores$score,col.name = pathway_name)
}
plt = FeaturePlot(object = acc_cancer_pri,features =  names(neuronal_pathways))

for (i in 1:(length(plt$patches$plots)+1)) {
  plt[[i]] = plt[[i]] + theme(plot.title = element_text(size=10.5))+ labs(color='TPM') 
}
print(plt)

9 Lum vs Myo

library(ggpubr)
for (pathway in names(neuronal_pathways)) {
  data = FetchData(object = acc_cancer_pri,vars = c("lum_or_myo",pathway)) %>% filter(lum_or_myo != "unknown")
  p = ggboxplot(data, x = "lum_or_myo", y =pathway,
                palette = "jco",
                add = "jitter")+ 
    stat_compare_means(method = "wilcox.test",comparisons = list(c("luminal","myo")))+ stat_summary(fun.data = function(x) data.frame(y=max(x)*1.2, label = paste("Mean=",round(mean(x),digits = 2))), geom="text") +ylab("TPM")+ggtitle(pathway)
  print_tab(p,title = pathway)
}

GOBP_NOREPINEPHRINE_SECRETION

GOBP_NOREPINEPHRINE_TRANSPORT

GOBP_NORADRENERGIC_NEURON_DEVELOPMENT

GOBP_NORADRENERGIC_NEURON_DIFFERENTIATION

GOBP_AUTONOMIC_NERVOUS_SYSTEM_DEVELOPMENT

GOBP_PARASYMPATHETIC_NERVOUS_SYSTEM_DEVELOPMENT

GOBP_ADRENERGIC_RECEPTOR_SIGNALING_PATHWAY

GOMF_BETA_2_ADRENERGIC_RECEPTOR_BINDING

NA

LS0tCnRpdGxlOiAnYHIgcnN0dWRpb2FwaTo6Z2V0U291cmNlRWRpdG9yQ29udGV4dCgpJHBhdGggJT4lIGJhc2VuYW1lKCkgJT4lIGdzdWIocGF0dGVybiA9ICJcXC5SbWQiLHJlcGxhY2VtZW50ID0gIiIpYCcgCmF1dGhvcjogIkF2aXNoYWkgV2l6ZWwiCmRhdGU6ICdgciBTeXMudGltZSgpYCcKb3V0cHV0OiAKICBodG1sX25vdGVib29rOiAKICAgIGNvZGVfZm9sZGluZzogaGlkZQogICAgdG9jOiB5ZXMKICAgIHRvY19jb2xsYXBzZTogeWVzCiAgICB0b2NfZmxvYXQ6IAogICAgICBjb2xsYXBzZWQ6IHRydWUKICAgIG51bWJlcl9zZWN0aW9uczogdHJ1ZQogICAgdG9jX2RlcHRoOiA0Ci0tLQoKIyBGdW5jdGlvbnMKCmBgYHtyIHdhcm5pbmc9RkFMU0V9CmxpYnJhcnkoc3RyaW5naSkKc291cmNlX2Zyb21fZ2l0aHViKHJlcG9zaXRveSA9ICJERUdfZnVuY3Rpb25zIix2ZXJzaW9uID0gIjAuMi40NyIpCnNvdXJjZV9mcm9tX2dpdGh1YihyZXBvc2l0b3kgPSAiY05NRl9mdW5jdGlvbnMiLHZlcnNpb24gPSAiMC40LjAiLHNjcmlwdF9uYW1lID0gImNubWZfZnVuY3Rpb25zX1YzLlIiKQpzb3VyY2VfZnJvbV9naXRodWIocmVwb3NpdG95ID0gInNjX2dlbmVyYWxfZnVuY3Rpb25zIix2ZXJzaW9uID0gIjAuMS4yOCIsc2NyaXB0X25hbWUgPSAiZnVuY3Rpb25zLlIiKQpgYGAKCiMgRGF0YQoKYGBge3J9CmxpYnJhcnkoInJlYWR4bCIpCmFjY19hbGwgPSByZWFkUkRTKGZpbGUgPSAiLi9EYXRhL2FjY190cG1fbkNvdW50X21pdG9fbm8xNDZfMTVrX2FsbGRhdGEucmRzIikKYWNjX2NhbmNlcl9wcmkgPSByZWFkUkRTKGZpbGUgPSAiLi9EYXRhL2FjY19jYW5jZXJfbm8xNDZfcHJpbWFyeW9ubHkxNWtfY2FuY2VyY2VsbHMucmRzIikKYWNjX2NhbmNlciA9IHJlYWRSRFMoZmlsZSA9ICIuL0RhdGEvYWNjX3RwbV9uQ291bnRfbWl0b19ubzE0Nl8xNWtfY2FuY2VyY2VsbHMucmRzIikKCgpuZXVyb25hbF9zaWduYXR1cmVzIDwtIHJlYWRfZXhjZWwoIi4vRGF0YS9OZXVyb25hbCBTaWduYXR1cmVzLnhsc3giLGNvbF9uYW1lcyA9RikKbmV1cm9uYWxfc2lnbmF0dXJlcyAgJTw+JSAgdCgpICU+JSBhcy5kYXRhLmZyYW1lKCkgJT4lIGphbml0b3I6OnJvd190b19uYW1lcygxKSAlPiUgIGZpbHRlcighcm93X251bWJlcigpID09IDEpCnJvd25hbWVzKG5ldXJvbmFsX3NpZ25hdHVyZXMpIDwtIE5VTEwKY29sbmFtZXMobmV1cm9uYWxfc2lnbmF0dXJlcykgICAlPD4lICBnc3ViKHJlcGxhY2VtZW50ID0gIiIsIHBhdHRlcm4gPSAiX1xcZC4qIikgI3JlbW92ZSBhbnkgX251bWJlcnMKY29sbmFtZXMobmV1cm9uYWxfc2lnbmF0dXJlcykgICAlPD4lICBnc3ViKHJlcGxhY2VtZW50ID0gIiIsIHBhdHRlcm4gPSAiXFwoLioiKSAjcmVuYW1lICIoIiB0byB0aGUgZW5kCmNvbG5hbWVzKG5ldXJvbmFsX3NpZ25hdHVyZXMpICAgJTw+JSAgZ3N1YihyZXBsYWNlbWVudCA9ICJfIiwgcGF0dGVybiA9ICIgIikgI3JlbmFtZSBhbGwgc3BhY2VzCgpuZXVyb25hbF9wYXRod2F5cyA8LSByZWFkX2V4Y2VsKCIuL0RhdGEvUGF0aHdheSBhbmFseXNpcyBHZW5lIHNldHMueGxzeCIsY29sX25hbWVzID1GKQpuZXVyb25hbF9wYXRod2F5cyAgJTw+JSAgdCgpICU+JSBhcy5kYXRhLmZyYW1lKCkgJT4lIGphbml0b3I6OnJvd190b19uYW1lcygxKSAlPiUgIGZpbHRlcighcm93X251bWJlcigpID09IDEpICAlPiUgIGFzLmxpc3QoKSAKbmV1cm9uYWxfcGF0aHdheXMgPSBsYXBwbHkobmV1cm9uYWxfcGF0aHdheXMsIG5hLm9taXQpCm5ldXJvbmFsX3BhdGh3YXlzID0gbGFwcGx5KG5ldXJvbmFsX3BhdGh3YXlzLCBhcy5jaGFyYWN0ZXIpCgpgYGAKCiMgQUNDIGFsbCBjZWxscyBVTUFQCgpgYGB7cn0KRGltUGxvdChhY2NfYWxsKQpgYGAKCiMgTmV1cm9uYWwgc2lnbmF0dXJlcwoKYGBge3IgcmVzdWx0cz0nYXNpcyd9CmZvciAobmV1cmFsX25hbWUgaW4gY29sbmFtZXMobmV1cm9uYWxfc2lnbmF0dXJlcykpIHsKICBnZW5lcyA9IG5ldXJvbmFsX3NpZ25hdHVyZXNbLG5ldXJhbF9uYW1lLGRyb3A9VF0KICAjIEFzc3VtaW5nIGRmIGlzIHlvdXIgZGF0YSBmcmFtZQoKICAKICBwYXRod2F5c19zY29yZXMgPSBGZXRjaERhdGEob2JqZWN0ID0gYWNjX2FsbCx2YXJzID0gZ2VuZXMsc2xvdCA9ICJkYXRhIikgJT4lIAogICAgbXV0YXRlX2FsbCh+IDJeLiklPiUgbXV0YXRlX2FsbCh+IC4tMSkgJT4lICAjY292ZXJ0IGxvZyhUUE0rMSkgdG8gVFBNCiAgICByb3d3aXNlKCkgJT4lIG11dGF0ZShzY29yZSA9IG1lYW4oY19hY3Jvc3MoZXZlcnl0aGluZygpKSkpICNtZWFuCiAgYWNjX2FsbCAgJTw+JSBBZGRNZXRhRGF0YShtZXRhZGF0YSA9IHBhdGh3YXlzX3Njb3JlcyRzY29yZSxjb2wubmFtZSA9IG5ldXJhbF9uYW1lKQp9CmBgYAoKYGBge3IgZmlnLmhlaWdodD0xMiwgZmlnLndpZHRoPTEyfQpwbHQgPSBWbG5QbG90KG9iamVjdCA9IGFjY19hbGwsZmVhdHVyZXMgPSBjb2xuYW1lcyhuZXVyb25hbF9zaWduYXR1cmVzKSkKcGx0W1sxXV0gPSBwbHRbWzFdXSsgeWxhYigiVFBNIikKcGx0W1s0XV0gPSBwbHRbWzRdXSsgeWxhYigiVFBNIikKcGx0W1s3XV0gPSBwbHRbWzddXSsgeWxhYigiVFBNIikKcGx0CmBgYAoKIyMgTmV1cm9uYWwgc2lnbmF0dXJlcyBleHByZXNzaW9uIHsudGFic2V0fQoKYGBge3IgZmlnLmhlaWdodD04LCBmaWcud2lkdGg9OCwgcmVzdWx0cz0nYXNpcyd9CmNvdW50LmRhdGEgPC0gR2V0QXNzYXlEYXRhKG9iamVjdCA9IGFjY19hbGxbWyJSTkEiXV0sIHNsb3QgPSAiZGF0YSIpCmNvdW50LmRhdGEgPC0gYXMubWF0cml4KHggPSAoMioqY291bnQuZGF0YSkgLSAxKQphY2NfdHBtIDwtIFNldEFzc2F5RGF0YSgKICAgIG9iamVjdCA9IGFjY19hbGwsCiAgICBzbG90ID0gImNvdW50cyIsCiAgICBuZXcuZGF0YSA9IGNvdW50LmRhdGEsCiAgICBhc3NheSA9ICJSTkEiCikKCmZvciAobmV1cmFsX25hbWUgaW4gY29sbmFtZXMobmV1cm9uYWxfc2lnbmF0dXJlcykpIHsKICBnZW5lcyA9IG5ldXJvbmFsX3NpZ25hdHVyZXNbLG5ldXJhbF9uYW1lLGRyb3A9VF0KICAjIEFzc3VtaW5nIGRmIGlzIHlvdXIgZGF0YSBmcmFtZQogIHByaW50X3RhYigKICAgIERvSGVhdG1hcChvYmplY3QgPSBhY2NfdHBtLGZlYXR1cmVzID0gZ2VuZXMsc2xvdCA9ICJjb3VudHMiLGNvbWJpbmUgPSBULGRpc3AubWF4ID0gNTAwMCkrIGxhYnMoZmlsbCA9ICJUUE0iKSAKICAsdGl0bGUgPSBuZXVyYWxfbmFtZSxzdWJ0aXRsZV9udW0gPSAzKQp9CmBgYAoKIyMgV0JDIAoKYGBge3J9CndiY19jZWxscyA9IHN1YnNldChhY2NfYWxsLCBzdWJzZXQgPSBjZWxsLnR5cGUgPT0gIldCQyIpCndiY19jZWxscyA8LSBGaW5kTmVpZ2hib3JzKHdiY19jZWxscywgZGltcyA9IDE6MTAsdmVyYm9zZSA9IEYpICU+JSAgRmluZENsdXN0ZXJzKHJlc29sdXRpb24gPSAwLjUpICU+JSAgUnVuVU1BUChkaW1zID0gMToxMCx2ZXJib3NlID0gRikKCkRpbVBsb3Qod2JjX2NlbGxzKQpgYGAKCldCQyBkZXZpZGVkIGludG8gMiBjbHVzdGVyczoKCmBgYHtyfQpWbG5QbG90KG9iamVjdCA9IHdiY19jZWxscyxmZWF0dXJlcyA9IGMoIkNENzlBIiwiUFRQUkMiKSkKYGBgCgojIyBXQkMgTmV1cm9uYWwgc2lnbmF0dXJlcwoKYGBge3IgZmlnLmhlaWdodD0xMiwgZmlnLndpZHRoPTEzfQphY2NfYWxsJGNsdXN0ZXJfaWRlbnRzID0gYWNjX2FsbEBhY3RpdmUuaWRlbnQKZGF0YSA9IEZldGNoRGF0YShvYmplY3QgPSBhY2NfYWxsLHZhcnMgPSBjKCJjbHVzdGVyX2lkZW50cyIpKSAlPiUgbXV0YXRlKGNsdXN0ZXJfaWRlbnRzID0gYXMuY2hhcmFjdGVyKGNsdXN0ZXJfaWRlbnRzKSkKY2x1c3Rlcl8wX2NlbGxzID0gc3Vic2V0KHdiY19jZWxscywgc3Vic2V0ID0gc2V1cmF0X2NsdXN0ZXJzID09IDApICU+JSBjb2xuYW1lcygpCmNsdXN0ZXJfMV9jZWxscyA9IHN1YnNldCh3YmNfY2VsbHMsIHN1YnNldCA9IHNldXJhdF9jbHVzdGVycyA9PSAxKSAlPiUgY29sbmFtZXMoKQoKZGF0YVtyb3duYW1lcyhkYXRhKSAlaW4lIGNsdXN0ZXJfMF9jZWxscyxdID0iV0JDX2NsdXN0ZXJfMCIKZGF0YVtyb3duYW1lcyhkYXRhKSAlaW4lIGNsdXN0ZXJfMV9jZWxscyxdID0iV0JDX2NsdXN0ZXJfMSIKYWNjX2FsbCRjbHVzdGVyX2lkZW50cyA9IGRhdGEKCnBsdCA9IFZsblBsb3Qob2JqZWN0ID0gYWNjX2FsbCxmZWF0dXJlcyA9IGNvbG5hbWVzKG5ldXJvbmFsX3NpZ25hdHVyZXMpLGdyb3VwLmJ5ID0gImNsdXN0ZXJfaWRlbnRzIikKcGx0W1sxXV0gPSBwbHRbWzFdXSsgeWxhYigiVFBNIikKcGx0W1s0XV0gPSBwbHRbWzRdXSsgeWxhYigiVFBNIikKcGx0W1s3XV0gPSBwbHRbWzddXSsgeWxhYigiVFBNIikKcGx0CmBgYAoKIyMgQ0Q3OUEgbmV1cm9uYWxfc2lnbmF0dXJlcyBjb3JyZWxhdGlvbiB7LnRhYnNldH0KCmBgYHtyIHJlc3VsdHM9J2FzaXMnfQpsaWJyYXJ5KGdncHVicikKZm9yIChuZXVyYWxfbmFtZSBpbiBjb2xuYW1lcyhuZXVyb25hbF9zaWduYXR1cmVzKSkgewogIHdiY19jZWxscyA9IHN1YnNldChhY2NfYWxsLCBzdWJzZXQgPSBjZWxsLnR5cGUgPT0gIldCQyIpCiAgZGF0YSA9IEZldGNoRGF0YShvYmplY3QgPSB3YmNfY2VsbHMsdmFycyA9IGMobmV1cmFsX25hbWUsIkNENzlBIikpCiAgcCA9IGdncGxvdChkYXRhLCBhZXNfc3RyaW5nKHg9bmV1cmFsX25hbWUsIHk9IkNENzlBIikpICsgCiAgICAgICAgICAgZ2VvbV9wb2ludCgpKwogICAgICAgICAgIGdlb21fc21vb3RoKG1ldGhvZD1sbSkgKwogICAgICAgICAgIHN0YXRfY29yKCkKICBwcmludF90YWIocCx0aXRsZSAgPSBuZXVyYWxfbmFtZSxzdWJ0aXRsZV9udW0gPSAzKQp9CgpgYGAKCiMjIFBUUFJDIG5ldXJvbmFsX3NpZ25hdHVyZXMgY29ycmVsYXRpb24gey50YWJzZXR9CgpgYGB7ciByZXN1bHRzPSdhc2lzJ30KbGlicmFyeShnZ3B1YnIpCmZvciAobmV1cmFsX25hbWUgaW4gY29sbmFtZXMobmV1cm9uYWxfc2lnbmF0dXJlcykpIHsKICB3YmNfY2VsbHMgPSBzdWJzZXQoYWNjX2FsbCwgc3Vic2V0ID0gY2VsbC50eXBlID09ICJXQkMiKQogIGRhdGEgPSBGZXRjaERhdGEob2JqZWN0ID0gd2JjX2NlbGxzLHZhcnMgPSBjKG5ldXJhbF9uYW1lLCJQVFBSQyIpKQogIHAgPSBnZ3Bsb3QoZGF0YSwgYWVzX3N0cmluZyh4PW5ldXJhbF9uYW1lLCB5PSJQVFBSQyIpKSArIAogICAgICAgICAgIGdlb21fcG9pbnQoKSsKICAgICAgICAgICBnZW9tX3Ntb290aChtZXRob2Q9bG0pICsKICAgICAgICAgICBzdGF0X2NvcigpCiAgcHJpbnRfdGFiKHAsdGl0bGUgID0gbmV1cmFsX25hbWUsc3VidGl0bGVfbnVtID0gMykKfQpgYGAKCiMgQ1NGMwoKW1NpbmdsZS1jZWxsIFJOQSBzZXF1ZW5jaW5nIHJldmVhbHMgaW50cmF0dW1vcmFsIGhldGVyb2dlbmVpdHkgYW5kIHBvdGVudGlhbCBtZWNoYW5pc21zIG9mIG1hbGlnbmFudCBwcm9ncmVzc2lvbiBpbiBwcm9zdGF0ZSBjYW5jZXIgd2l0aCBwZXJpbmV1cmFsIGludmFzaW9uXShodHRwczovL3d3dy5uY2JpLm5sbS5uaWguZ292L3BtYy9hcnRpY2xlcy9QTUM5ODc1Nzk5LykKCmBgYHtyfQpWbG5QbG90KG9iamVjdCA9IGFjY19hbGwsZmVhdHVyZXMgPSAiQ1NGMyIsZ3JvdXAuYnkgPSAicGF0aWVudC5pZGVudCIpKyB5bGFiKCJsb2cyIChUUE0rMSkiKQpgYGAKCiMgTmV1cm9uYWwgcGF0aHdheXMgaW4gQUNDIGNhbmNlciBjZWxscwoKIyMgZGltIHJlZHVjdGlvbgoKYGBge3J9CmFjY19jYW5jZXIgPC0gUnVuUENBKGFjY19jYW5jZXIsIGZlYXR1cmVzID0gVmFyaWFibGVGZWF0dXJlcyhvYmplY3QgPSBhY2NfY2FuY2VyKSx2ZXJib3NlID0gRikKRWxib3dQbG90KGFjY19jYW5jZXIpCmFjY19jYW5jZXIgPC0gRmluZE5laWdoYm9ycyhhY2NfY2FuY2VyLCBkaW1zID0gMToxMCx2ZXJib3NlID0gRikgJT4lICBGaW5kQ2x1c3RlcnMocmVzb2x1dGlvbiA9IDAuNSkgJT4lICBSdW5VTUFQKGRpbXMgPSAxOjEwLHZlcmJvc2UgPSBGKQpgYGAKCmBgYHtyfQpEaW1QbG90KGFjY19jYW5jZXIsZ3JvdXAuYnkgPSAicGF0aWVudC5pZGVudCIpCmBgYAoKYGBge3J9CmZvciAocGF0aHdheV9uYW1lIGluIG5hbWVzKG5ldXJvbmFsX3BhdGh3YXlzKSkgewogIGdlbmVzID0gbmV1cm9uYWxfcGF0aHdheXNbW3BhdGh3YXlfbmFtZV1dCiAgcGF0aHdheXNfc2NvcmVzID0gRmV0Y2hEYXRhKG9iamVjdCA9IGFjY19jYW5jZXIsdmFycyA9IGdlbmVzLHNsb3QgPSAiZGF0YSIpICU+JSAKICAgIG11dGF0ZV9hbGwofiAyXi4pJT4lIG11dGF0ZV9hbGwofiAuLTEpICU+JSAgI2NvdmVydCBsb2coVFBNKzEpIHRvIFRQTQogICAgcm93d2lzZSgpICU+JSBtdXRhdGUoc2NvcmUgPSBtZWFuKGNfYWNyb3NzKGV2ZXJ5dGhpbmcoKSkpKSAjbWVhbgogIGFjY19jYW5jZXIgICU8PiUgQWRkTWV0YURhdGEobWV0YWRhdGEgPSBwYXRod2F5c19zY29yZXMkc2NvcmUsY29sLm5hbWUgPSBwYXRod2F5X25hbWUpCn0KYGBgCgojIyBTY29yZXMgVU1BUCB7LnRhYnNldH0KCmBgYHtyIGZpZy5oZWlnaHQ9MTMsIGZpZy53aWR0aD0xMywgcmVzdWx0cz0nYXNpcyd9CgpwbHQgPSBGZWF0dXJlUGxvdChvYmplY3QgPSBhY2NfY2FuY2VyLGZlYXR1cmVzID0gbmFtZXMobmV1cm9uYWxfcGF0aHdheXMpKQpmb3IgKGkgaW4gMToobGVuZ3RoKHBsdCRwYXRjaGVzJHBsb3RzKSsxKSkgewogIHBsdFtbaV1dID0gcGx0W1tpXV0gKyB0aGVtZShwbG90LnRpdGxlID0gZWxlbWVudF90ZXh0KHNpemU9MTAuNSkpKyBsYWJzKGNvbG9yPSdUUE0nKQp9CnByaW50X3RhYihwbHQsdGl0bGUgPSAiVU1BUCIgLHN1YnRpdGxlX251bSA9IDMpCgpwbHQgPSBGZWF0dXJlUGxvdChvYmplY3QgPSBhY2NfY2FuY2VyLGZlYXR1cmVzID0gbmFtZXMobmV1cm9uYWxfcGF0aHdheXMpLG1heC5jdXRvZmYgPSA1MCkKZm9yIChpIGluIDE6KGxlbmd0aChwbHQkcGF0Y2hlcyRwbG90cykrMSkpIHsKICBwbHRbW2ldXSA9IHBsdFtbaV1dICsgdGhlbWUocGxvdC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplPTEwLjUpKSsgbGFicyhjb2xvcj0nVFBNJykKfQpwcmludF90YWIocGx0LHRpdGxlID0gIlVNQVAgbWF4PTUwIiAsc3VidGl0bGVfbnVtID0gMykKCnBsdCA9IEZlYXR1cmVQbG90KG9iamVjdCA9IGFjY19jYW5jZXIsZmVhdHVyZXMgPSBuYW1lcyhuZXVyb25hbF9wYXRod2F5cyksbWF4LmN1dG9mZiA9IDI1MCkKZm9yIChpIGluIDE6KGxlbmd0aChwbHQkcGF0Y2hlcyRwbG90cykrMSkpIHsKICBwbHRbW2ldXSA9IHBsdFtbaV1dICsgdGhlbWUocGxvdC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplPTEwLjUpKSsgbGFicyhjb2xvcj0nVFBNJykKfQpwcmludF90YWIocGx0LHRpdGxlID0gIlVNQVAgbWF4PTI1MCIgLHN1YnRpdGxlX251bSA9IDMpCgpwbHQgPSBGZWF0dXJlUGxvdChvYmplY3QgPSBhY2NfY2FuY2VyLGZlYXR1cmVzID0gbmFtZXMobmV1cm9uYWxfcGF0aHdheXMpKQpmb3IgKGkgaW4gMToobGVuZ3RoKHBsdCRwYXRjaGVzJHBsb3RzKSsxKSkgewogIHBsdFtbaV1dID0gcGx0W1tpXV0gKyB0aGVtZShwbG90LnRpdGxlID0gZWxlbWVudF90ZXh0KHNpemU9MTAuNSkpKyBsYWJzKGNvbG9yPSdUUE0nKSArIHNjYWxlX2NvbG9yX2dyYWRpZW50bihjb2xvdXJzID0gcmFpbmJvdyg1KSkKfQpwcmludF90YWIocGx0LHRpdGxlID0gIlVNQVAgcmFpbmJvdyIgLHN1YnRpdGxlX251bSA9IDMpCgpgYGAKCmBgYHtyIGZpZy5oZWlnaHQ9MTMsIGZpZy53aWR0aD0xMywgcmVzdWx0cz0nYXNpcyd9CgpgYGAKCiMjIFNjb3JlcyB2aW9saW4KCmBgYHtyIGZpZy5oZWlnaHQ9MTIsIGZpZy53aWR0aD0xMn0KIHBsdCA9IFZsblBsb3Qob2JqZWN0ID0gYWNjX2NhbmNlcixmZWF0dXJlcyA9IG5hbWVzKG5ldXJvbmFsX3BhdGh3YXlzKSxncm91cC5ieSA9ICJwYXRpZW50LmlkZW50IikrdGhlbWUocGxvdC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplID0gMykpCiAKZm9yIChpIGluIDE6KGxlbmd0aChwbHQkcGF0Y2hlcyRwbG90cykrMSkpIHsKICBwbHRbW2ldXSA9IHBsdFtbaV1dICsgdGhlbWUocGxvdC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplPTkuNSkpCiAgaWYgKGkgJWluJSBjKDEsNCw3KSkgewogICAgcGx0W1tpXV0gPSBwbHRbW2ldXSt5bGFiKCJUUE0iKQogIH0KfQpwcmludChwbHQpCmBgYAoKIyBBQ0MyIERFRwoKYGBge3J9CmFjY19jYW5jZXJfcHJpID0gU2V0SWRlbnQob2JqZWN0ID0gYWNjX2NhbmNlcl9wcmksdmFsdWUgPSAicGF0aWVudC5pZGVudCIpCm1hcmtlcnMgPSBGaW5kTWFya2VycyhvYmplY3QgPSBhY2NfY2FuY2VyX3ByaSxpZGVudC4xID0gIkFDQzIiLGZlYXR1cmVzID0gVmFyaWFibGVGZWF0dXJlcyhhY2NfY2FuY2VyX3ByaSksZGVuc2lmeSA9IFQpCnZvbGNhbm9fcGxvdChkZV9nZW5lcyA9IG1hcmtlcnMsbWF4X25hbWVzID0gMTAsdGl0bGUgPSAiIixpZGVudDEgPSAiQUNDMiIsaWRlbnQyID0gIlBOSSBwYXRpZW50cyIsc2hvd19ncmFwaCA9IEYsbG9nMmZjX2N1dG9mZiA9IDEpCmBgYAoKIyMgR1NFQS0gY2Fub25pY2FsIHBhdGh3YXlzCgp1cCA9IHVwIGluIEFDQzIKCmBgYHtyfQpsaWJyYXJ5KGh5cGVSKQpnZW5lc2V0cyA8LSBtc2lnZGJfZG93bmxvYWQoIkhvbW8gc2FwaWVucyIsY2F0ZWdvcnk9IkgiKSAlPiUgYXBwZW5kKCBtc2lnZGJfZG93bmxvYWQoIkhvbW8gc2FwaWVucyIsY2F0ZWdvcnk9IkMyIixzdWJjYXRlZ29yeSA9ICJDUCIpKQphbGxfZ2VuZXMgPSBtYXJrZXJzICAlPiUgIGFycmFuZ2UoZGVzYyhhdmdfbG9nMkZDKSkgJT4lIHNlbGVjdCgiYXZnX2xvZzJGQyIpIApyYW5rZWRfbGlzdCAgIDwtIHNldE5hbWVzKGFsbF9nZW5lcyRhdmdfbG9nMkZDLCByb3duYW1lcyhhbGxfZ2VuZXMpKQpoeXBfb2JqIDwtIGh5cGVSX2Znc2VhKHNpZ25hdHVyZSA9IHJhbmtlZF9saXN0LGdlbmVzZXRzID0gIGdlbmVzZXRzLHVwX29ubHkgPSBGKQpoeXBfZG90cyhoeXBfb2JqKQpgYGAKCiMjIEdTRUEtIEdPIEJQCgpgYGB7cn0KZ2VuZXNldHMgPC0gbXNpZ2RiX2Rvd25sb2FkKCJIb21vIHNhcGllbnMiLGNhdGVnb3J5PSJIIikgJT4lIGFwcGVuZCggbXNpZ2RiX2Rvd25sb2FkKCJIb21vIHNhcGllbnMiLGNhdGVnb3J5PSJDNSIsc3ViY2F0ZWdvcnkgPSAiR086QlAiKSkKYWxsX2dlbmVzID0gbWFya2VycyAgJT4lICBhcnJhbmdlKGRlc2MoYXZnX2xvZzJGQykpICU+JSBzZWxlY3QoImF2Z19sb2cyRkMiKSAKcmFua2VkX2xpc3QgICA8LSBzZXROYW1lcyhhbGxfZ2VuZXMkYXZnX2xvZzJGQywgcm93bmFtZXMoYWxsX2dlbmVzKSkKaHlwX29iaiA8LSBoeXBlUl9mZ3NlYShzaWduYXR1cmUgPSByYW5rZWRfbGlzdCxnZW5lc2V0cyA9ICBnZW5lc2V0cyx1cF9vbmx5ID0gRikKaHlwX2RvdHMoaHlwX29iaikKYGBgCgpgYGB7PWh0bWx9CjxzY3JpcHQgc3JjPSJodHRwczovL2h5cG90aGVzLmlzL2VtYmVkLmpzIiBhc3luYz48L3NjcmlwdD4KYGBgCiMgTmV1cm9uYWwgcGF0aHdheXMgaW4gQUNDIHByaW1hcnkgY2FuY2VyIGNlbGxzCgpgYGB7cn0KbHVtX3Njb3JlID0gRmV0Y2hEYXRhKGFjY19jYW5jZXJfcHJpLCJsdW1pbmFsX292ZXJfbXlvIikKbHVtX3Njb3JlICAlPD4lIG11dGF0ZSAobHVtX29yX215byA9IGNhc2Vfd2hlbigKICAgICAgICAgbHVtaW5hbF9vdmVyX215byA+IDEgfiAibHVtaW5hbCIsCiAgICAgICAgIGx1bWluYWxfb3Zlcl9teW8gPCAoLTEpIH4gIm15byIsCiAgICAgICAgIFRSVUUgfiAidW5rbm93biIpKQphY2NfY2FuY2VyX3ByaSAgJTw+JSBBZGRNZXRhRGF0YShtZXRhZGF0YSA9IGx1bV9zY29yZSRsdW1fb3JfbXlvLGNvbC5uYW1lID0gImx1bV9vcl9teW8iKQpgYGAKCmBgYHtyfQpmb3IgKHBhdGh3YXlfbmFtZSBpbiBuYW1lcyhuZXVyb25hbF9wYXRod2F5cykpIHsKICBnZW5lcyA9IG5ldXJvbmFsX3BhdGh3YXlzW1twYXRod2F5X25hbWVdXQogcGF0aHdheXNfc2NvcmVzID0gRmV0Y2hEYXRhKG9iamVjdCA9IGFjY19jYW5jZXJfcHJpLHZhcnMgPSBnZW5lcyxzbG90ID0gImRhdGEiKSAlPiUgCiAgICBtdXRhdGVfYWxsKH4gMl4uKSU+JSBtdXRhdGVfYWxsKH4gLi0xKSAlPiUgICNjb3ZlcnQgbG9nKFRQTSsxKSB0byBUUE0KICAgIHJvd3dpc2UoKSAlPiUgbXV0YXRlKHNjb3JlID0gbWVhbihjX2Fjcm9zcyhldmVyeXRoaW5nKCkpKSkgI21lYW4KICBhY2NfY2FuY2VyX3ByaSAgJTw+JSBBZGRNZXRhRGF0YShtZXRhZGF0YSA9IHBhdGh3YXlzX3Njb3JlcyRzY29yZSxjb2wubmFtZSA9IHBhdGh3YXlfbmFtZSkKfQpgYGAKCmBgYHtyIGZpZy5oZWlnaHQ9MTMsIGZpZy53aWR0aD0xM30KcGx0ID0gRmVhdHVyZVBsb3Qob2JqZWN0ID0gYWNjX2NhbmNlcl9wcmksZmVhdHVyZXMgPSAgbmFtZXMobmV1cm9uYWxfcGF0aHdheXMpKQoKZm9yIChpIGluIDE6KGxlbmd0aChwbHQkcGF0Y2hlcyRwbG90cykrMSkpIHsKICBwbHRbW2ldXSA9IHBsdFtbaV1dICsgdGhlbWUocGxvdC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplPTEwLjUpKSsgbGFicyhjb2xvcj0nVFBNJykgCn0KcHJpbnQocGx0KQpgYGAKCiMgTHVtIHZzIE15byB7LnRhYnNldH0KCmBgYHtyIHJlc3VsdHM9J2FzaXMnfQpsaWJyYXJ5KGdncHVicikKZm9yIChwYXRod2F5IGluIG5hbWVzKG5ldXJvbmFsX3BhdGh3YXlzKSkgewogIGRhdGEgPSBGZXRjaERhdGEob2JqZWN0ID0gYWNjX2NhbmNlcl9wcmksdmFycyA9IGMoImx1bV9vcl9teW8iLHBhdGh3YXkpKSAlPiUgZmlsdGVyKGx1bV9vcl9teW8gIT0gInVua25vd24iKQogIHAgPSBnZ2JveHBsb3QoZGF0YSwgeCA9ICJsdW1fb3JfbXlvIiwgeSA9cGF0aHdheSwKICAgICAgICAgICAgICAgIHBhbGV0dGUgPSAiamNvIiwKICAgICAgICAgICAgICAgIGFkZCA9ICJqaXR0ZXIiKSsgCiAgICBzdGF0X2NvbXBhcmVfbWVhbnMobWV0aG9kID0gIndpbGNveC50ZXN0Iixjb21wYXJpc29ucyA9IGxpc3QoYygibHVtaW5hbCIsIm15byIpKSkrIHN0YXRfc3VtbWFyeShmdW4uZGF0YSA9IGZ1bmN0aW9uKHgpIGRhdGEuZnJhbWUoeT1tYXgoeCkqMS4yLCBsYWJlbCA9IHBhc3RlKCJNZWFuPSIscm91bmQobWVhbih4KSxkaWdpdHMgPSAyKSkpLCBnZW9tPSJ0ZXh0IikgK3lsYWIoIlRQTSIpK2dndGl0bGUocGF0aHdheSkKICBwcmludF90YWIocCx0aXRsZSA9IHBhdGh3YXkpCn0KCmBgYAo=