dataset=read.csv("Database_PF.csv")
library(ggplot2)

Universidad Galileo red

Postgrado en inteligencia de negocios

Proyecto Final Estadística

Miguel Angel Jolon 20003411 | Cristhella Santizo 20032365

Introduccion

Guatemala es un pais con variedad climatica, volcanes y montañas, siendo considerado el pais de la eterna primavera, un foco potencial para el turismo y calidad de vida alta, sin embargo esto se ve afectado por indice de criminalidad, grupos organizados y no organizados se han apoderado cada vez del pais siendo considerado uno de los paises a evitar según ABC, ocupando el puesto 49 de los paises mas peligrosos del mundo. El presente documento muestra los indicadores mas importantes para conocer las regiones y sectores mas afectadas por la criminalidad

Definicion del problema

  1. Reconocer los departamentos y municipios mas vulnerables por los Delitos dentro de Guatemala
  2. Reconocer cual es el departamento/municipio con menor cantidad de Delitos
  3. Estadistica por edad
  4. Reconocer si los delitos suceden con mayores de edad o menores de edad
  5. Reconocer los delitos por sexo
  6. La probabilidad de ocurrencia según sexo, edad y dia en que se comete los delitos
  7. Obtener si existe un patron en la hora en que suceden los delitos
  8. Que dia es el que mas delitos hay
  9. Evaluar si existe un incremento de delitos en los meses de bono 14 y Aguinaldo
  10. Cuanto de los delitos son por tema de extorsiones en buses (urbanos y extraurbanos )
  11. Analisis probabilistico XXXXXXXXXXXXXXX

Analisis

1.Reconocer los departamentos y municipios mas vulnerables por los Delitos dentro de Guatemala

dataset%>%
  group_by(Departmento) %>%
  summarise(cantidad=n())%>%
  arrange(-cantidad)

Grafica de Cantidad de Delitos por Departamento

dataset%>%
  group_by(Departmento) %>%
  summarise(cantidad=n())%>%
  arrange(-cantidad)%>%
  ggplot(aes(x=reorder(Departmento,cantidad), y=cantidad))+
  geom_bar(stat="identity",color = 'darkslategray', fill = 'steelblue') + 
  ggtitle ("Cantidad de Delitos por Departamento") + # Título del gráfico
  theme (plot.title = element_text(size=rel(2), #Tamaño relativo de la letra del título
                                  vjust=2, #Justificación vertical, para separarlo del gráfico
                                  face="bold", 
                                  color="blue", #Color del texto
                                  lineheight=1.5))+
 geom_text(aes(label=cantidad), position=position_dodge(width=0.5), vjust=0.5)+
  coord_flip()

Analisis Descriptivo

dataset %>%
    group_by(Departmento) %>%
  summarise(cantidad=n())%>%
  summary()
 Departmento           cantidad      
 Length:22          Min.   :  223.0  
 Class :character   1st Qu.:  682.5  
 Mode  :character   Median :  768.0  
                    Mean   : 1565.9  
                    3rd Qu.:  991.8  
                    Max.   :15744.0  

Municipios mas peligrosos de Guatemala

dataset%>%
  group_by(Municipio) %>%
  summarise(cantidad=n())%>%
  arrange(-cantidad)

Grafica de Cantidad de Delitos por Municipio

dataset%>%
  group_by(Municipio) %>%
  summarise(cantidad=n())%>%
  arrange(-cantidad)%>%
  head(10) %>%
  ggplot(aes(x=reorder(Municipio,cantidad), y=cantidad))+
  geom_bar(stat="identity",color = 'darkslategray', fill = 'steelblue') + 
  ggtitle ("Cantidad de Delitos por Municipio") + # Título del gráfico
  theme (plot.title = element_text(size=rel(2), #Tamaño relativo de la letra del título
                                  vjust=2, #Justificación vertical, para separarlo del gráfico
                                  face="bold", 
                                  color="blue", #Color del texto
                                  lineheight=1.5))+
 geom_text(aes(label=cantidad), position=position_dodge(width=0.5), vjust=0.5)+
  coord_flip()

NA
NA
NA
NA
NA

Analisis Descriptivo

dataset %>%
    group_by(Municipio) %>%
  summarise(cantidad=n())%>%
  summary()
  Municipio            cantidad     
 Length:333         Min.   :   1.0  
 Class :character   1st Qu.:  13.0  
 Mode  :character   Median :  29.0  
                    Mean   : 103.5  
                    3rd Qu.:  59.0  
                    Max.   :7535.0  

*Conclusion 1: El departamento y Municipio de Guatemala son los lugares mas peligrosos, estando en el ranking como el 1er lugar en ambas evaluaciones. En la poblacion a nivel Departamental tenemos una mediana de 768 delitos por departamento y de 29 por municipio, tomamos la mediana dado que los datos son muy dispersos por la diferencia que tenemos respecto al departamento/Municipio de Guatemala y el resto de areas.

2.Reconocer cual es el departamento/municipio con menor cantidad de Delitos

dataset%>%
  group_by(Departmento) %>%
  summarise(cantidad=n())%>%
  arrange(cantidad)

Grafica de Cantidad de Delitos por Departamento

dataset%>%
  group_by(Departmento) %>%
  summarise(cantidad=n())%>%
  arrange(cantidad)%>%
  head(10) %>%
  ggplot(aes(x=reorder(Departmento,-cantidad), y=cantidad))+
  geom_bar(stat="identity",color = 'darkslategray', fill = 'steelblue') + 
  ggtitle ("Cantidad de Delitos por Departamento") + # Título del gráfico
  theme (plot.title = element_text(size=rel(2), #Tamaño relativo de la letra del título
                                  vjust=2, #Justificación vertical, para separarlo del gráfico
                                  face="bold", 
                                  color="blue", #Color del texto
                                  lineheight=1.5))+
 geom_text(aes(label=cantidad), position=position_dodge(width=0.2), vjust=0.5)+
  coord_flip()

dataset%>%
  group_by(Municipio) %>%
  summarise(cantidad=n())%>%
  arrange(cantidad)

Grafica de Cantidad de Delitos por Municipio

dataset%>%
  group_by(Municipio) %>%
  summarise(cantidad=n())%>%
  arrange(cantidad)%>%
  head(10) %>%
  ggplot(aes(x=reorder(Municipio,-cantidad), y=cantidad))+
  geom_bar(stat="identity",color = 'darkslategray', fill = 'steelblue') + 
  ggtitle ("Cantidad de Delitos por Municipio") + # Título del gráfico
  theme (plot.title = element_text(size=rel(2), #Tamaño relativo de la letra del título
                                  vjust=2, #Justificación vertical, para separarlo del gráfico
                                  face="bold", 
                                  color="blue", #Color del texto
                                  lineheight=1.5))+
 geom_text(aes(label=cantidad), position=position_dodge(width=0.2), vjust=0.5)+
  coord_flip()

Conclusion 2: El departamento mas seguro es Totonicapan y el Municipio mas seguro es Tectitan, municipio de Huehuetenango

3. Estadistica por edad

mean (dataset$edad_per,trim = 0.1)
[1] 44.47179
median(dataset$edad_per)
[1] 34
Moda= table(dataset$G_Edad_Quincenal)[which.max(table(dataset$G_Edad_Quincenal))]
Moda
25-29 
 4908 

Conclusion 3: La edad promedio de las personas victimas de hechos delectivos durante el 2019 es de 44 años, y el rango de edades de las personal mas afectadas oscila entre los 25 y 29 años de edad.

4. Reconocer si los delitos suceden con mayores de edad o menores de edad

Mayor=dataset %>%
filter (MayorOMenordeEdad=="Mayor de edad") %>%
summarise(Mayor_de_edad=n()) %>%
arrange (-Mayor_de_edad)
Mayor
PorcentajeMenor=(Menor)/(Mayor+Menor)
PorcentajeMenor

Conclusion 4: Al agrupar los menores de 18 años y los mayores de 18 años, se concluye que los mas afectados son los mayores de edad, es importante mencionar que el 8% de los afectados son Menores de edad

5. Reconocer los delitos por sexo

VictimaH=
  dataset %>%
  filter(Sexo =="Hombre")
Error in dataset %>% filter(Sexo == "Hombre") : 
  no se pudo encontrar la función "%>%"

*Conclusion 5: La probabilidad de las deVictimas de Hechos Delictivos por sexo, en general se muestra con la siguiente proporcion: 68.8% Hombres, 30% mujeres y en 1.2% de los casos el genero es omitido. Segun la grafica, en los tipo de delito: Contra y Libertad y otras causas, no se cumple la proporcion general.

6. La probabilidad de ocurrencia según sexo, edad se comete los delitos

VicHombreMy=
  dataset %>%
  filter (MayorOMenordeEdad == "Mayor de edad", Sexo == "Hombre")
nrow(VicHombreMy)/nrow(VictimaH)
[1] 0.8677264
VicMujerMy=
  dataset %>%
  filter (MayorOMenordeEdad == "Mayor de edad" , Sexo == "Mujer")
nrow(VicMujerMy)/nrow(VictimaM)
[1] 0.7524781
VicHombreME=
  dataset %>%
  filter (Sexo == "Hombre" , MayorOMenordeEdad == "Menor de edad")
nrow(VicHombreME)/nrow(VictimaH)
[1] 0.04667735
VicMujerME=
  dataset %>%
  filter (Sexo == "Mujer" , MayorOMenordeEdad == "Menor de edad")
  nrow(VicMujerME)/nrow(VictimaM)
[1] 0.1562891
  
DiaVictima =
dataset %>%
  group_by(NombredelDia, Sexo) %>%
  summarise(Cantidad = n()) %>%
  arrange(-Cantidad)
ggplot(DiaVictima, aes(x=NombredelDia, y=Cantidad, group = Sexo, colour =Sexo )) + 
  geom_line()  + 
  geom_point( size=1, shape=10, fill="blue") + 
  theme_gray()

*Conclusion 6: La probabilidad de ocurrencia de hechos delictivos para para victimas mayores de edad es: Hombre 86.77% y Mujeres 75.24%. Para victimas Menores de Edad: Hombre 4.66% y Mujeres 15.63%. Los dias de la semana en que ocurren los hechos delictivos gruardan relacion segun el sexo, como se observa en la grafica.

7. Obtener si existe un patron en la hora en que suceden los delitos

Hora=dataset[(dataset$HoraOcurrencia<99), 7]
Warning messages:
1: In readChar(file, size, TRUE) : truncating string with embedded nuls
2: In readChar(file, size, TRUE) : truncating string with embedded nuls
3: In readChar(file, size, TRUE) : truncating string with embedded nuls
4: In readChar(file, size, TRUE) : truncating string with embedded nuls
hist(Hora,
        col=blues9,
        xlab= "Hora",
        ylab= "Cantidad",
        main= "Grafica de delitos cometidos por X hora",
        las=2)

Conclusion 7: Segun muestra la grafica, la mayor parte de los hechos delictivos son cometidos entre las 9 y las 21 horas de dia

8. Que dia es el que mas delitos hay

dataset%>%
  group_by(NombredelDia) %>%
  summarise(cantidad=n())%>%
  arrange(-cantidad)%>%
    ggplot(aes(y=reorder(NombredelDia,cantidad), x=cantidad))+
  geom_point(color = 'red', fill = 'red', size = 4, shape = 18, alpha = 0.5) +
  xlab('Delito') + 
  ylab('Dias de la semana') +
  ggtitle ("Cantidad total por Dia") + # Título del gráfico
  theme (plot.title = element_text(size=rel(2), #Tamaño relativo de la letra del título
                                  vjust=2, #Justificación vertical, para separarlo del gráfico
                                  face="bold", 
                                  color="blue", #Color del texto
                                  lineheight=1.5))+
 geom_text(aes(label=cantidad), position=position_dodge(width=0.5), vjust=-.5)+
  coord_flip()

Conclusion 8: El dia con mas delitos son los dias Lunes y Martes, y el dia con menos delitos son los dias Domingo

9. Evaluar si existe un incremento de delitos en los meses de bono 14 y Aguinaldo

Hechosxmes= as.data.frame(prop.table(table(dataset$Mes, dataset$GrupoDelito), 2)*100)
colnames(Hechosxmes)<-c("MES", "Delito","PCT")
gr4 <- ggplot(Hechosxmes, aes(x=MES, y=PCT)) + geom_bar(stat="identity", fill = 'steelblue')
gr4

gr4 + coord_flip() + facet_wrap(~ Delito)

*Conclusion 9: ### La siguiente grafica muestra la ocurrencia de hechos delictivos por mes, evidenciando que apartir del Mes de julio (bono 14) se incrementan: Las extorsiones y los Homicidios. Mientras que durante el mes de diciembre solo se denota un incremento en los los Hechos delictivos en contra el patrimonio.

10. Cuanto de los delitos son por tema de extorsiones en buses (urbanos y extraurbanos )

buses= dataset%>%
  filter((Delito=="Extorsión a buses urbanos") | (Delito=="Extorsión a buses extraurbanos"))%>%
  nrow()
  buses
[1] 447
  
TotalDelitos=dataset%>%
  group_by(Delito)%>%
  nrow()
  TotalDelitos
[1] 34449

% de Delitos que son Extorsiones a buses urbanos

(buses/TotalDelitos)
[1] 0.0129757

Conclusion 10: El 1% de los delitos se deben a extorsiones a buses urbanos y extraurbanos

Analisis PDF

Definicion del problema

ACAAAAAAAAAA definir el problema: Tenemos un registro de 654 Homicidios de los cuales 112 son de Mujeres y 542 son de hombres, cual es la funcion de densidad de que sean Mujeres y cual es la densidad que sean Hombre (siendo 1 Hombres y 0 Mujeres)

x=c(0,1)
ncol((combn(542,1)))
[1] 542
PMF1=function(x){
  num1=ncol(combn(112,x))
  num2=ncol(combn(542,1-x))
  denom=ncol(combn(654,1))
  salida=(num1*num2)/(denom)
  return(salida)
}
PMF1 (0)
[1] 0.8287462
PMF1 (1)
[1] 0.1712538

pdf=sapply(x, FUN=PMF1)
pdf
[1] 0.8287462 0.1712538
datos=data.frame(x=x,px=pdf)
datos

Conclusion PDF: La densidad de probabilidad que una mujer sea victima de homicidio en el municipio de Guatemala es el 17.12%

Obtener el CDF

cdf=cumsum(pdf)
cdf
datos=data.frame(datos,Fx=cdf)
datos
valor_esperado=function(df){
x=df[ ,1]
px=df [ ,2]
VE=sum(x*px)
return(VE)}
valor_esperado(datos) #media ponderada

Obtener la Varianza

varianza=function(df){
  media=valor_esperado(df)
  x=df [ ,1]
  px=df [ ,2]
  varX=sum(((x-media)^2)*(px))
  return(varX)
  
}
varianza(datos)

Conclusion CDF Podemos observar la variabilidad de los datos a un 0.14, la cual indica la distancia que hay hacia la media

Best Fit, tomando en cuenta la Edad

dataset$edad_per
EdadCorrecta=dataset[(dataset$edad_per<999), 20]
TablaEdad=data_frame(table(EdadCorrecta))
TablaEdad
descdist(EdadCorrecta, discrete = FALSE)
hist(EdadCorrecta,
        col=blues9,
        xlab= "Edad",
        ylab= "Cantidad de Delitos",
        main= "Grafica de delitos por edad",
        las=2)

Conclusion BEST FIT: Al analizar la cantidad de Delitos por edad podemos concluir que se apega a una distribucion normal, misma se valido realizando un histograma de frecuencia por edad el cual se puede ver un leve sesgo hacia la derecha, siendo las edades mas vulnerables entre los 20 y 40 años.

LS0tDQp0aXRsZTogIkVzdGFkaXN0aWNhIC0gRGVsaXRvcyBlbiBHdWF0ZW1hbGEgMjAxOSINCm91dHB1dDogaHRtbF9ub3RlYm9vaw0KLS0tDQpgYGB7cn0NCmRhdGFzZXQ9cmVhZC5jc3YoIkRhdGFiYXNlX1BGLmNzdiIpDQpsaWJyYXJ5KGdncGxvdDIpDQoNCmBgYA0KIyMjIyAqKlVuaXZlcnNpZGFkIEdhbGlsZW8qKiByZWQNCiMjIyMgKipQb3N0Z3JhZG8gZW4gaW50ZWxpZ2VuY2lhIGRlIG5lZ29jaW9zKioNCiMjIyMgKipQcm95ZWN0byBGaW5hbCBFc3RhZMOtc3RpY2EqKg0KIyMjIyAqKk1pZ3VlbCBBbmdlbCBKb2xvbiAgMjAwMDM0MTEgfCBDcmlzdGhlbGxhIFNhbnRpem8gMjAwMzIzNjUqKg0KDQojICoqSW50cm9kdWNjaW9uKioNCkd1YXRlbWFsYSBlcyB1biBwYWlzIGNvbiB2YXJpZWRhZCBjbGltYXRpY2EsIHZvbGNhbmVzIHkgbW9udGHDsWFzLCBzaWVuZG8gY29uc2lkZXJhZG8gZWwgcGFpcyBkZSBsYSBldGVybmEgcHJpbWF2ZXJhLCB1biBmb2NvIHBvdGVuY2lhbCBwYXJhIGVsIHR1cmlzbW8geSBjYWxpZGFkIGRlIHZpZGEgYWx0YSwgc2luIGVtYmFyZ28gZXN0byBzZSB2ZSBhZmVjdGFkbyBwb3IgaW5kaWNlIGRlIGNyaW1pbmFsaWRhZCwgZ3J1cG9zIG9yZ2FuaXphZG9zIHkgbm8gb3JnYW5pemFkb3Mgc2UgaGFuIGFwb2RlcmFkbyBjYWRhIHZleiBkZWwgcGFpcyBzaWVuZG8gY29uc2lkZXJhZG8gdW5vIGRlIGxvcyBwYWlzZXMgYSBldml0YXIgc2Vnw7puIEFCQywgb2N1cGFuZG8gZWwgcHVlc3RvIDQ5IGRlIGxvcyBwYWlzZXMgbWFzIHBlbGlncm9zb3MgZGVsIG11bmRvLiBFbCBwcmVzZW50ZSBkb2N1bWVudG8gbXVlc3RyYSBsb3MgaW5kaWNhZG9yZXMgbWFzIGltcG9ydGFudGVzIHBhcmEgY29ub2NlciBsYXMgcmVnaW9uZXMgeSBzZWN0b3JlcyBtYXMgYWZlY3RhZGFzIHBvciBsYSBjcmltaW5hbGlkYWQNCg0KIyAqKkRlZmluaWNpb24gZGVsIHByb2JsZW1hKioNCjEuIFJlY29ub2NlciBsb3MgZGVwYXJ0YW1lbnRvcyB5IG11bmljaXBpb3MgbWFzIHZ1bG5lcmFibGVzIHBvciBsb3MgRGVsaXRvcyBkZW50cm8gZGUgR3VhdGVtYWxhIA0KMi4gUmVjb25vY2VyIGN1YWwgZXMgZWwgZGVwYXJ0YW1lbnRvL211bmljaXBpbyBjb24gbWVub3IgY2FudGlkYWQgZGUgRGVsaXRvcw0KMy4gRXN0YWRpc3RpY2EgcG9yIGVkYWQNCjQuIFJlY29ub2NlciBzaSBsb3MgZGVsaXRvcyBzdWNlZGVuIGNvbiBtYXlvcmVzIGRlIGVkYWQgbyBtZW5vcmVzIGRlIGVkYWQNCjUuIFJlY29ub2NlciBsb3MgZGVsaXRvcyBwb3Igc2V4bw0KNi4gTGEgcHJvYmFiaWxpZGFkIGRlIG9jdXJyZW5jaWEgc2Vnw7puIHNleG8sIGVkYWQgeSBkaWEgZW4gcXVlIHNlIGNvbWV0ZSBsb3MgZGVsaXRvcw0KNy4gT2J0ZW5lciBzaSBleGlzdGUgdW4gcGF0cm9uIGVuIGxhIGhvcmEgZW4gcXVlIHN1Y2VkZW4gbG9zIGRlbGl0b3MNCjguIFF1ZSBkaWEgZXMgZWwgcXVlIG1hcyBkZWxpdG9zIGhheQ0KOS4gRXZhbHVhciBzaSBleGlzdGUgdW4gaW5jcmVtZW50byBkZSBkZWxpdG9zIGVuIGxvcyBtZXNlcyBkZSBib25vIDE0IHkgQWd1aW5hbGRvDQoxMC4JQ3VhbnRvIGRlIGxvcyBkZWxpdG9zIHNvbiBwb3IgdGVtYSBkZSBleHRvcnNpb25lcyBlbiBidXNlcyAodXJiYW5vcyB5IGV4dHJhdXJiYW5vcyApDQoxMS4JQW5hbGlzaXMgcHJvYmFiaWxpc3RpY28gWFhYWFhYWFhYWFhYWFhYDQoNCiMgKipBbmFsaXNpcyoqDQojIyMgMS5SZWNvbm9jZXIgbG9zIGRlcGFydGFtZW50b3MgeSBtdW5pY2lwaW9zIG1hcyB2dWxuZXJhYmxlcyBwb3IgbG9zIERlbGl0b3MgZGVudHJvIGRlIEd1YXRlbWFsYSANCmBgYHtyfQ0KZGF0YXNldCU+JQ0KICBncm91cF9ieShEZXBhcnRtZW50bykgJT4lDQogIHN1bW1hcmlzZShjYW50aWRhZD1uKCkpJT4lDQogIGFycmFuZ2UoLWNhbnRpZGFkKQ0KYGBgDQojIyMgR3JhZmljYSBkZSBDYW50aWRhZCBkZSBEZWxpdG9zIHBvciBEZXBhcnRhbWVudG8NCg0KYGBge3J9DQpkYXRhc2V0JT4lDQogIGdyb3VwX2J5KERlcGFydG1lbnRvKSAlPiUNCiAgc3VtbWFyaXNlKGNhbnRpZGFkPW4oKSklPiUNCiAgYXJyYW5nZSgtY2FudGlkYWQpJT4lDQogIGdncGxvdChhZXMoeD1yZW9yZGVyKERlcGFydG1lbnRvLGNhbnRpZGFkKSwgeT1jYW50aWRhZCkpKw0KICBnZW9tX2JhcihzdGF0PSJpZGVudGl0eSIsY29sb3IgPSAnZGFya3NsYXRlZ3JheScsIGZpbGwgPSAnc3RlZWxibHVlJykgKyANCiAgZ2d0aXRsZSAoIkNhbnRpZGFkIGRlIERlbGl0b3MgcG9yIERlcGFydGFtZW50byIpICsgIyBUw610dWxvIGRlbCBncsOhZmljbw0KICB0aGVtZSAocGxvdC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplPXJlbCgyKSwgI1RhbWHDsW8gcmVsYXRpdm8gZGUgbGEgbGV0cmEgZGVsIHTDrXR1bG8NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2anVzdD0yLCAjSnVzdGlmaWNhY2nDs24gdmVydGljYWwsIHBhcmEgc2VwYXJhcmxvIGRlbCBncsOhZmljbw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZhY2U9ImJvbGQiLCANCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb2xvcj0iYmx1ZSIsICNDb2xvciBkZWwgdGV4dG8NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBsaW5laGVpZ2h0PTEuNSkpKw0KIGdlb21fdGV4dChhZXMobGFiZWw9Y2FudGlkYWQpLCBwb3NpdGlvbj1wb3NpdGlvbl9kb2RnZSh3aWR0aD0wLjUpLCB2anVzdD0wLjUpKw0KICBjb29yZF9mbGlwKCkNCg0KYGBgDQojIyMgQW5hbGlzaXMgRGVzY3JpcHRpdm8NCg0KYGBge3J9DQpkYXRhc2V0ICU+JQ0KICAgIGdyb3VwX2J5KERlcGFydG1lbnRvKSAlPiUNCiAgc3VtbWFyaXNlKGNhbnRpZGFkPW4oKSklPiUNCiAgc3VtbWFyeSgpDQoNCmBgYA0KDQojIyMgTXVuaWNpcGlvcyBtYXMgcGVsaWdyb3NvcyBkZSBHdWF0ZW1hbGEgIA0KYGBge3J9DQpkYXRhc2V0JT4lDQogIGdyb3VwX2J5KE11bmljaXBpbykgJT4lDQogIHN1bW1hcmlzZShjYW50aWRhZD1uKCkpJT4lDQogIGFycmFuZ2UoLWNhbnRpZGFkKQ0KYGBgDQojIyMgR3JhZmljYSBkZSBDYW50aWRhZCBkZSBEZWxpdG9zIHBvciBNdW5pY2lwaW8NCg0KYGBge3J9DQpkYXRhc2V0JT4lDQogIGdyb3VwX2J5KE11bmljaXBpbykgJT4lDQogIHN1bW1hcmlzZShjYW50aWRhZD1uKCkpJT4lDQogIGFycmFuZ2UoLWNhbnRpZGFkKSU+JQ0KICBoZWFkKDEwKSAlPiUNCiAgZ2dwbG90KGFlcyh4PXJlb3JkZXIoTXVuaWNpcGlvLGNhbnRpZGFkKSwgeT1jYW50aWRhZCkpKw0KICBnZW9tX2JhcihzdGF0PSJpZGVudGl0eSIsY29sb3IgPSAnZGFya3NsYXRlZ3JheScsIGZpbGwgPSAnc3RlZWxibHVlJykgKyANCiAgZ2d0aXRsZSAoIkNhbnRpZGFkIGRlIERlbGl0b3MgcG9yIE11bmljaXBpbyIpICsgIyBUw610dWxvIGRlbCBncsOhZmljbw0KICB0aGVtZSAocGxvdC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplPXJlbCgyKSwgI1RhbWHDsW8gcmVsYXRpdm8gZGUgbGEgbGV0cmEgZGVsIHTDrXR1bG8NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2anVzdD0yLCAjSnVzdGlmaWNhY2nDs24gdmVydGljYWwsIHBhcmEgc2VwYXJhcmxvIGRlbCBncsOhZmljbw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZhY2U9ImJvbGQiLCANCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb2xvcj0iYmx1ZSIsICNDb2xvciBkZWwgdGV4dG8NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBsaW5laGVpZ2h0PTEuNSkpKw0KIGdlb21fdGV4dChhZXMobGFiZWw9Y2FudGlkYWQpLCBwb3NpdGlvbj1wb3NpdGlvbl9kb2RnZSh3aWR0aD0wLjUpLCB2anVzdD0wLjUpKw0KICBjb29yZF9mbGlwKCkNCg0KDQogDQogIA0KDQpgYGANCiMjIyBBbmFsaXNpcyBEZXNjcmlwdGl2bw0KDQpgYGB7cn0NCmRhdGFzZXQgJT4lDQogICAgZ3JvdXBfYnkoTXVuaWNpcGlvKSAlPiUNCiAgc3VtbWFyaXNlKGNhbnRpZGFkPW4oKSklPiUNCiAgc3VtbWFyeSgpDQoNCmBgYA0KIyMjICpDb25jbHVzaW9uIDE6IEVsIGRlcGFydGFtZW50byB5IE11bmljaXBpbyBkZSBHdWF0ZW1hbGEgc29uIGxvcyBsdWdhcmVzIG1hcyBwZWxpZ3Jvc29zLCBlc3RhbmRvIGVuIGVsIHJhbmtpbmcgY29tbyBlbCAxZXIgbHVnYXIgZW4gYW1iYXMgZXZhbHVhY2lvbmVzLiBFbiBsYSBwb2JsYWNpb24gYSBuaXZlbCBEZXBhcnRhbWVudGFsIHRlbmVtb3MgdW5hIG1lZGlhbmEgZGUgNzY4IGRlbGl0b3MgcG9yIGRlcGFydGFtZW50byB5IGRlIDI5IHBvciBtdW5pY2lwaW8sIHRvbWFtb3MgbGEgbWVkaWFuYSBkYWRvIHF1ZSBsb3MgZGF0b3Mgc29uIG11eSBkaXNwZXJzb3MgcG9yIGxhIGRpZmVyZW5jaWEgcXVlIHRlbmVtb3MgcmVzcGVjdG8gYWwgZGVwYXJ0YW1lbnRvL011bmljaXBpbyBkZSBHdWF0ZW1hbGEgeSBlbCByZXN0byBkZSBhcmVhcy4NCg0KDQoNCiMjIyAyLlJlY29ub2NlciBjdWFsIGVzIGVsIGRlcGFydGFtZW50by9tdW5pY2lwaW8gY29uIG1lbm9yIGNhbnRpZGFkIGRlIERlbGl0b3MNCg0KYGBge3J9DQpkYXRhc2V0JT4lDQogIGdyb3VwX2J5KERlcGFydG1lbnRvKSAlPiUNCiAgc3VtbWFyaXNlKGNhbnRpZGFkPW4oKSklPiUNCiAgYXJyYW5nZShjYW50aWRhZCkNCmBgYA0KDQojIyMgR3JhZmljYSBkZSBDYW50aWRhZCBkZSBEZWxpdG9zIHBvciBEZXBhcnRhbWVudG8NCg0KYGBge3J9DQpkYXRhc2V0JT4lDQogIGdyb3VwX2J5KERlcGFydG1lbnRvKSAlPiUNCiAgc3VtbWFyaXNlKGNhbnRpZGFkPW4oKSklPiUNCiAgYXJyYW5nZShjYW50aWRhZCklPiUNCiAgaGVhZCgxMCkgJT4lDQogIGdncGxvdChhZXMoeD1yZW9yZGVyKERlcGFydG1lbnRvLC1jYW50aWRhZCksIHk9Y2FudGlkYWQpKSsNCiAgZ2VvbV9iYXIoc3RhdD0iaWRlbnRpdHkiLGNvbG9yID0gJ2RhcmtzbGF0ZWdyYXknLCBmaWxsID0gJ3N0ZWVsYmx1ZScpICsgDQogIGdndGl0bGUgKCJDYW50aWRhZCBkZSBEZWxpdG9zIHBvciBEZXBhcnRhbWVudG8iKSArICMgVMOtdHVsbyBkZWwgZ3LDoWZpY28NCiAgdGhlbWUgKHBsb3QudGl0bGUgPSBlbGVtZW50X3RleHQoc2l6ZT1yZWwoMiksICNUYW1hw7FvIHJlbGF0aXZvIGRlIGxhIGxldHJhIGRlbCB0w610dWxvDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdmp1c3Q9MiwgI0p1c3RpZmljYWNpw7NuIHZlcnRpY2FsLCBwYXJhIHNlcGFyYXJsbyBkZWwgZ3LDoWZpY28NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmYWNlPSJib2xkIiwgDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29sb3I9ImJsdWUiLCAjQ29sb3IgZGVsIHRleHRvDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbGluZWhlaWdodD0xLjUpKSsNCiBnZW9tX3RleHQoYWVzKGxhYmVsPWNhbnRpZGFkKSwgcG9zaXRpb249cG9zaXRpb25fZG9kZ2Uod2lkdGg9MC4yKSwgdmp1c3Q9MC41KSsNCiAgY29vcmRfZmxpcCgpDQoNCmBgYA0KDQpgYGB7cn0NCmRhdGFzZXQlPiUNCiAgZ3JvdXBfYnkoTXVuaWNpcGlvKSAlPiUNCiAgc3VtbWFyaXNlKGNhbnRpZGFkPW4oKSklPiUNCiAgYXJyYW5nZShjYW50aWRhZCkNCmBgYA0KIyMjIEdyYWZpY2EgZGUgQ2FudGlkYWQgZGUgRGVsaXRvcyBwb3IgTXVuaWNpcGlvDQoNCmBgYHtyfQ0KZGF0YXNldCU+JQ0KICBncm91cF9ieShNdW5pY2lwaW8pICU+JQ0KICBzdW1tYXJpc2UoY2FudGlkYWQ9bigpKSU+JQ0KICBhcnJhbmdlKGNhbnRpZGFkKSU+JQ0KICBoZWFkKDEwKSAlPiUNCiAgZ2dwbG90KGFlcyh4PXJlb3JkZXIoTXVuaWNpcGlvLC1jYW50aWRhZCksIHk9Y2FudGlkYWQpKSsNCiAgZ2VvbV9iYXIoc3RhdD0iaWRlbnRpdHkiLGNvbG9yID0gJ2RhcmtzbGF0ZWdyYXknLCBmaWxsID0gJ3N0ZWVsYmx1ZScpICsgDQogIGdndGl0bGUgKCJDYW50aWRhZCBkZSBEZWxpdG9zIHBvciBNdW5pY2lwaW8iKSArICMgVMOtdHVsbyBkZWwgZ3LDoWZpY28NCiAgdGhlbWUgKHBsb3QudGl0bGUgPSBlbGVtZW50X3RleHQoc2l6ZT1yZWwoMiksICNUYW1hw7FvIHJlbGF0aXZvIGRlIGxhIGxldHJhIGRlbCB0w610dWxvDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdmp1c3Q9MiwgI0p1c3RpZmljYWNpw7NuIHZlcnRpY2FsLCBwYXJhIHNlcGFyYXJsbyBkZWwgZ3LDoWZpY28NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmYWNlPSJib2xkIiwgDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29sb3I9ImJsdWUiLCAjQ29sb3IgZGVsIHRleHRvDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbGluZWhlaWdodD0xLjUpKSsNCiBnZW9tX3RleHQoYWVzKGxhYmVsPWNhbnRpZGFkKSwgcG9zaXRpb249cG9zaXRpb25fZG9kZ2Uod2lkdGg9MC4yKSwgdmp1c3Q9MC41KSsNCiAgY29vcmRfZmxpcCgpDQoNCmBgYA0KDQojIyMgKkNvbmNsdXNpb24gMjogRWwgZGVwYXJ0YW1lbnRvIG1hcyBzZWd1cm8gZXMgVG90b25pY2FwYW4geSBlbCBNdW5pY2lwaW8gbWFzIHNlZ3VybyBlcyBUZWN0aXRhbiwgbXVuaWNpcGlvIGRlIEh1ZWh1ZXRlbmFuZ28gKg0KDQoNCiMjIyAzLiBFc3RhZGlzdGljYSBwb3IgZWRhZA0KDQpgYGB7cn0NCm1lYW4gKGRhdGFzZXQkZWRhZF9wZXIsdHJpbSA9IDAuMSkNCm1lZGlhbihkYXRhc2V0JGVkYWRfcGVyKQ0KTW9kYT0gdGFibGUoZGF0YXNldCRHX0VkYWRfUXVpbmNlbmFsKVt3aGljaC5tYXgodGFibGUoZGF0YXNldCRHX0VkYWRfUXVpbmNlbmFsKSldDQpNb2RhDQpgYGANCiMjIyAqQ29uY2x1c2lvbiAzOiBMYSBlZGFkIHByb21lZGlvIGRlIGxhcyBwZXJzb25hcyB2aWN0aW1hcyBkZSBoZWNob3MgZGVsZWN0aXZvcyBkdXJhbnRlIGVsIDIwMTkgZXMgZGUgNDQgYcOxb3MsIHkgZWwgcmFuZ28gZGUgZWRhZGVzIGRlIGxhcyBwZXJzb25hbCBtYXMgYWZlY3RhZGFzIG9zY2lsYSBlbnRyZSBsb3MgMjUgeSAyOSBhw7FvcyBkZSBlZGFkLioNCg0KDQojIyMgNC4gUmVjb25vY2VyIHNpIGxvcyBkZWxpdG9zIHN1Y2VkZW4gY29uIG1heW9yZXMgZGUgZWRhZCBvIG1lbm9yZXMgZGUgZWRhZA0KDQpgYGB7cn0NCk1heW9yPWRhdGFzZXQgJT4lDQpmaWx0ZXIgKE1heW9yT01lbm9yZGVFZGFkPT0iTWF5b3IgZGUgZWRhZCIpICU+JQ0Kc3VtbWFyaXNlKE1heW9yX2RlX2VkYWQ9bigpKSAlPiUNCmFycmFuZ2UgKC1NYXlvcl9kZV9lZGFkKQ0KTWF5b3INCg0KYGBgDQoNCmBgYHtyfQ0KTWVub3I9ZGF0YXNldCAlPiUNCmZpbHRlciAoTWF5b3JPTWVub3JkZUVkYWQ9PSJNZW5vciBkZSBlZGFkIikgJT4lDQpzdW1tYXJpc2UoTWVub3JfZGVfZWRhZD1uKCkpICU+JQ0KYXJyYW5nZSAoLU1lbm9yX2RlX2VkYWQpDQpNZW5vcg0KYGBgDQoNCmBgYHtyfQ0KUG9yY2VudGFqZU1lbm9yPShNZW5vcikvKE1heW9yK01lbm9yKQ0KUG9yY2VudGFqZU1lbm9yDQpgYGANCg0KIyMjICpDb25jbHVzaW9uIDQ6IEFsIGFncnVwYXIgbG9zIG1lbm9yZXMgZGUgMTggYcOxb3MgeSBsb3MgbWF5b3JlcyBkZSAxOCBhw7Fvcywgc2UgY29uY2x1eWUgcXVlIGxvcyBtYXMgYWZlY3RhZG9zIHNvbiBsb3MgbWF5b3JlcyBkZSBlZGFkLCBlcyBpbXBvcnRhbnRlIG1lbmNpb25hciBxdWUgZWwgOCUgZGUgbG9zIGFmZWN0YWRvcyBzb24gTWVub3JlcyBkZSBlZGFkKg0KDQoNCiMjIyA1LiBSZWNvbm9jZXIgbG9zIGRlbGl0b3MgcG9yIHNleG8NCmBgYHtyfQ0KVmljdGltYUg9DQogIGRhdGFzZXQgJT4lDQogIGZpbHRlcihTZXhvID09IkhvbWJyZSIpDQpucm93KFZpY3RpbWFIKS9ucm93KGRhdGFzZXQpDQoNClZpY3RpbWFNPQ0KICBkYXRhc2V0ICU+JQ0KICBmaWx0ZXIoU2V4byA9PSJNdWplciIpDQpucm93KFZpY3RpbWFNKS9ucm93KERhdGFzZXQpDQoNCkRlbGl0b3NYU2V4bz0gDQogIGRhdGFzZXQgJT4lDQogIGdyb3VwX2J5KFNleG8sIEdydXBvRGVsaXRvKSAlPiUNCiAgc3VtbWFyaXNlKENhbnRpZGFkID0gbigpKSAlPiUNCiAgYXJyYW5nZSgtQ2FudGlkYWQpDQpjb2xuYW1lcyhEZWxpdG9zWFNleG8pPC1jKCJTZXhvIiwgIkRlbGl0byIsIkNhbnRpZGFkIikNCkRlbGl0b3NYU2V4bw0KZ3IyIDwtIGdncGxvdChEZWxpdG9zWFNleG8sIGFlcyh4PVNleG8sIHk9Q2FudGlkYWQpKSArIGdlb21fYmFyKHN0YXQ9ImlkZW50aXR5IiwgY29sb3IgPSAnZGFya3NsYXRlZ3JheScsIGZpbGwgPSAnc3RlZWxibHVlJykgKw0KICBnZ3RpdGxlKCJWaWN0aW1hcyBkZSBIZWNob3MgRGVsaWNpdGl2b3MgYWdydXBhZG9zIHBvciBTZXhvIikgKyB0aGVtZV9idygpDQpncjIgKyBmYWNldF93cmFwKH4gRGVsaXRvKQ0KYGBgDQojIyMgKkNvbmNsdXNpb24gNTogTGEgcHJvYmFiaWxpZGFkIGRlIGxhcyBkZVZpY3RpbWFzIGRlIEhlY2hvcyBEZWxpY3Rpdm9zIHBvciBzZXhvLCBlbiBnZW5lcmFsIHNlIG11ZXN0cmEgY29uIGxhIHNpZ3VpZW50ZSBwcm9wb3JjaW9uOiA2OC44JSBIb21icmVzLCAzMCUgbXVqZXJlcyB5IGVuIDEuMiUgZGUgbG9zIGNhc29zIGVsIGdlbmVybyBlcyBvbWl0aWRvLiAgU2VndW4gbGEgZ3JhZmljYSwgZW4gbG9zIHRpcG8gZGUgZGVsaXRvOiBDb250cmEgeSBMaWJlcnRhZCB5IG90cmFzIGNhdXNhcywgbm8gc2UgY3VtcGxlIGxhIHByb3BvcmNpb24gZ2VuZXJhbC4gDQoNCg0KIyMjIDYuIExhIHByb2JhYmlsaWRhZCBkZSBvY3VycmVuY2lhIHNlZ8O6biBzZXhvLCBlZGFkIHNlIGNvbWV0ZSBsb3MgZGVsaXRvcw0KDQpgYGB7cn0NClZpY0hvbWJyZU15PQ0KICBkYXRhc2V0ICU+JQ0KICBmaWx0ZXIgKE1heW9yT01lbm9yZGVFZGFkID09ICJNYXlvciBkZSBlZGFkIiwgU2V4byA9PSAiSG9tYnJlIikNCm5yb3coVmljSG9tYnJlTXkpL25yb3coVmljdGltYUgpDQoNClZpY011amVyTXk9DQogIGRhdGFzZXQgJT4lDQogIGZpbHRlciAoTWF5b3JPTWVub3JkZUVkYWQgPT0gIk1heW9yIGRlIGVkYWQiICwgU2V4byA9PSAiTXVqZXIiKQ0KbnJvdyhWaWNNdWplck15KS9ucm93KFZpY3RpbWFNKQ0KDQpWaWNIb21icmVNRT0NCiAgZGF0YXNldCAlPiUNCiAgZmlsdGVyIChTZXhvID09ICJIb21icmUiICwgTWF5b3JPTWVub3JkZUVkYWQgPT0gIk1lbm9yIGRlIGVkYWQiKQ0KbnJvdyhWaWNIb21icmVNRSkvbnJvdyhWaWN0aW1hSCkNCg0KVmljTXVqZXJNRT0NCiAgZGF0YXNldCAlPiUNCiAgZmlsdGVyIChTZXhvID09ICJNdWplciIgLCBNYXlvck9NZW5vcmRlRWRhZCA9PSAiTWVub3IgZGUgZWRhZCIpDQogIG5yb3coVmljTXVqZXJNRSkvbnJvdyhWaWN0aW1hTSkNCiAgDQpEaWFWaWN0aW1hID0NCmRhdGFzZXQgJT4lDQogIGdyb3VwX2J5KE5vbWJyZWRlbERpYSwgU2V4bykgJT4lDQogIHN1bW1hcmlzZShDYW50aWRhZCA9IG4oKSkgJT4lDQogIGFycmFuZ2UoLUNhbnRpZGFkKQ0KZ2dwbG90KERpYVZpY3RpbWEsIGFlcyh4PU5vbWJyZWRlbERpYSwgeT1DYW50aWRhZCwgZ3JvdXAgPSBTZXhvLCBjb2xvdXIgPVNleG8gKSkgKyANCiAgZ2VvbV9saW5lKCkgICsgDQogIGdlb21fcG9pbnQoIHNpemU9MSwgc2hhcGU9MTAsIGZpbGw9ImJsdWUiKSArIA0KICB0aGVtZV9ncmF5KCkNCg0KYGBgDQojIyMgKkNvbmNsdXNpb24gNjogTGEgcHJvYmFiaWxpZGFkIGRlIG9jdXJyZW5jaWEgZGUgaGVjaG9zIGRlbGljdGl2b3MgcGFyYSBwYXJhIHZpY3RpbWFzIG1heW9yZXMgZGUgZWRhZCBlczogSG9tYnJlIDg2Ljc3JSB5IE11amVyZXMgNzUuMjQlLiAgIFBhcmEgdmljdGltYXMgTWVub3JlcyBkZSBFZGFkOiBIb21icmUgNC42NiUgeSBNdWplcmVzIDE1LjYzJS4gTG9zIGRpYXMgZGUgbGEgc2VtYW5hIGVuIHF1ZSBvY3VycmVuIGxvcyBoZWNob3MgZGVsaWN0aXZvcyBncnVhcmRhbiByZWxhY2lvbiBzZWd1biBlbCBzZXhvLCBjb21vIHNlIG9ic2VydmEgZW4gbGEgZ3JhZmljYS4NCg0KDQojIyMgNy4gT2J0ZW5lciBzaSBleGlzdGUgdW4gcGF0cm9uIGVuIGxhIGhvcmEgZW4gcXVlIHN1Y2VkZW4gbG9zIGRlbGl0b3MNCmBgYHtyfQ0KSG9yYT1kYXRhc2V0WyhkYXRhc2V0JEhvcmFPY3VycmVuY2lhPDk5KSwgN10NCmhpc3QoSG9yYSwNCiAgICAgICAgY29sPWJsdWVzOSwNCiAgICAgICAgeGxhYj0gIkhvcmEiLA0KICAgICAgICB5bGFiPSAiQ2FudGlkYWQiLA0KICAgICAgICBtYWluPSAiR3JhZmljYSBkZSBkZWxpdG9zIGNvbWV0aWRvcyBwb3IgWCBob3JhIiwNCiAgICAgICAgbGFzPTIpDQpgYGANCiMjIyAqQ29uY2x1c2lvbiA3OiBTZWd1biBtdWVzdHJhIGxhIGdyYWZpY2EsIGxhIG1heW9yIHBhcnRlIGRlIGxvcyBoZWNob3MgZGVsaWN0aXZvcyBzb24gY29tZXRpZG9zIGVudHJlIGxhcyA5IHkgbGFzIDIxIGhvcmFzIGRlIGRpYSoNCg0KDQojIyMgOC4gUXVlIGRpYSBlcyBlbCBxdWUgbWFzIGRlbGl0b3MgaGF5DQpgYGB7cn0NCmRhdGFzZXQlPiUNCiAgZ3JvdXBfYnkoTm9tYnJlZGVsRGlhKSAlPiUNCiAgc3VtbWFyaXNlKGNhbnRpZGFkPW4oKSklPiUNCiAgYXJyYW5nZSgtY2FudGlkYWQpJT4lDQogICAgZ2dwbG90KGFlcyh5PXJlb3JkZXIoTm9tYnJlZGVsRGlhLGNhbnRpZGFkKSwgeD1jYW50aWRhZCkpKw0KICBnZW9tX3BvaW50KGNvbG9yID0gJ3JlZCcsIGZpbGwgPSAncmVkJywgc2l6ZSA9IDQsIHNoYXBlID0gMTgsIGFscGhhID0gMC41KSArDQogIHhsYWIoJ0RlbGl0bycpICsgDQogIHlsYWIoJ0RpYXMgZGUgbGEgc2VtYW5hJykgKw0KICBnZ3RpdGxlICgiQ2FudGlkYWQgdG90YWwgcG9yIERpYSIpICsgIyBUw610dWxvIGRlbCBncsOhZmljbw0KICB0aGVtZSAocGxvdC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplPXJlbCgyKSwgI1RhbWHDsW8gcmVsYXRpdm8gZGUgbGEgbGV0cmEgZGVsIHTDrXR1bG8NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2anVzdD0yLCAjSnVzdGlmaWNhY2nDs24gdmVydGljYWwsIHBhcmEgc2VwYXJhcmxvIGRlbCBncsOhZmljbw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZhY2U9ImJvbGQiLCANCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb2xvcj0iYmx1ZSIsICNDb2xvciBkZWwgdGV4dG8NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBsaW5laGVpZ2h0PTEuNSkpKw0KIGdlb21fdGV4dChhZXMobGFiZWw9Y2FudGlkYWQpLCBwb3NpdGlvbj1wb3NpdGlvbl9kb2RnZSh3aWR0aD0wLjUpLCB2anVzdD0tLjUpKw0KICBjb29yZF9mbGlwKCkNCmBgYA0KDQoNCiMjIyAqQ29uY2x1c2lvbiA4OiBFbCBkaWEgY29uIG1hcyBkZWxpdG9zIHNvbiBsb3MgZGlhcyBMdW5lcyB5IE1hcnRlcywgeSBlbCBkaWEgY29uIG1lbm9zIGRlbGl0b3Mgc29uIGxvcyBkaWFzIERvbWluZ28qDQoNCg0KDQojIyMgOS4gRXZhbHVhciBzaSBleGlzdGUgdW4gaW5jcmVtZW50byBkZSBkZWxpdG9zIGVuIGxvcyBtZXNlcyBkZSBib25vIDE0IHkgQWd1aW5hbGRvDQoNCmBgYHtyfQ0KSGVjaG9zeG1lcz0gYXMuZGF0YS5mcmFtZShwcm9wLnRhYmxlKHRhYmxlKGRhdGFzZXQkTWVzLCBkYXRhc2V0JEdydXBvRGVsaXRvKSwgMikqMTAwKQ0KY29sbmFtZXMoSGVjaG9zeG1lcyk8LWMoIk1FUyIsICJEZWxpdG8iLCJQQ1QiKQ0KZ3I0IDwtIGdncGxvdChIZWNob3N4bWVzLCBhZXMoeD1NRVMsIHk9UENUKSkgKyBnZW9tX2JhcihzdGF0PSJpZGVudGl0eSIsIGZpbGwgPSAnc3RlZWxibHVlJykNCmdyNA0KZ3I0ICsgY29vcmRfZmxpcCgpICsgZmFjZXRfd3JhcCh+IERlbGl0bykNCmBgYA0KDQoNCiMjIyAqQ29uY2x1c2lvbiA5OiAjIyMgTGEgc2lndWllbnRlIGdyYWZpY2EgbXVlc3RyYSBsYSBvY3VycmVuY2lhIGRlIGhlY2hvcyBkZWxpY3Rpdm9zIHBvciBtZXMsIGV2aWRlbmNpYW5kbyBxdWUgYXBhcnRpciBkZWwgTWVzIGRlIGp1bGlvIChib25vIDE0KSBzZSBpbmNyZW1lbnRhbjogTGFzIGV4dG9yc2lvbmVzIHkgbG9zIEhvbWljaWRpb3MuICBNaWVudHJhcyBxdWUgZHVyYW50ZSBlbCBtZXMgZGUgZGljaWVtYnJlIHNvbG8gc2UgZGVub3RhIHVuIGluY3JlbWVudG8gZW4gbG9zIGxvcyBIZWNob3MgZGVsaWN0aXZvcyBlbiBjb250cmEgZWwgcGF0cmltb25pby4NCg0KDQoNCiMjIyAxMC4JQ3VhbnRvIGRlIGxvcyBkZWxpdG9zIHNvbiBwb3IgdGVtYSBkZSBleHRvcnNpb25lcyBlbiBidXNlcyAodXJiYW5vcyB5IGV4dHJhdXJiYW5vcyApDQoNCmBgYHtyfQ0KYnVzZXM9IGRhdGFzZXQlPiUNCiAgZmlsdGVyKChEZWxpdG89PSJFeHRvcnNpw7NuIGEgYnVzZXMgdXJiYW5vcyIpIHwgKERlbGl0bz09IkV4dG9yc2nDs24gYSBidXNlcyBleHRyYXVyYmFub3MiKSklPiUNCiAgbnJvdygpDQogIGJ1c2VzDQogIA0KYGBgDQoNCmBgYHtyfQ0KVG90YWxEZWxpdG9zPWRhdGFzZXQlPiUNCiAgZ3JvdXBfYnkoRGVsaXRvKSU+JQ0KICBucm93KCkNCiAgVG90YWxEZWxpdG9zDQpgYGANCg0KIyMjICUgZGUgRGVsaXRvcyBxdWUgc29uIEV4dG9yc2lvbmVzIGEgYnVzZXMgdXJiYW5vcw0KYGBge3J9DQooYnVzZXMvVG90YWxEZWxpdG9zKQ0KYGBgDQoNCiMjIyAqQ29uY2x1c2lvbiAxMDogRWwgMSUgZGUgbG9zIGRlbGl0b3Mgc2UgZGViZW4gYSBleHRvcnNpb25lcyBhIGJ1c2VzIHVyYmFub3MgeSBleHRyYXVyYmFub3MqDQoNCg0KIyAqKkFuYWxpc2lzIFBERioqDQojICoqRGVmaW5pY2lvbiBkZWwgcHJvYmxlbWEqKg0KIyMjICpBQ0FBQUFBQUFBQUEgZGVmaW5pciBlbCBwcm9ibGVtYTogVGVuZW1vcyB1biByZWdpc3RybyBkZSA2NTQgSG9taWNpZGlvcyBkZSBsb3MgY3VhbGVzIDExMiBzb24gZGUgTXVqZXJlcyB5IDU0MiBzb24gZGUgaG9tYnJlcywgY3VhbCBlcyBsYSBmdW5jaW9uIGRlIGRlbnNpZGFkIGRlIHF1ZSBzZWFuIE11amVyZXMgeSBjdWFsIGVzIGxhIGRlbnNpZGFkIHF1ZSBzZWFuIEhvbWJyZSAoc2llbmRvIDEgSG9tYnJlcyB5IDAgTXVqZXJlcykqDQoNCg0KYGBge3J9DQp4PWMoMCwxKQ0KbmNvbCgoY29tYm4oNTQyLDEpKSkNCg0KYGBgDQoNCmBgYHtyfQ0KUE1GMT1mdW5jdGlvbih4KXsNCiAgbnVtMT1uY29sKGNvbWJuKDExMix4KSkNCiAgbnVtMj1uY29sKGNvbWJuKDU0MiwxLXgpKQ0KICBkZW5vbT1uY29sKGNvbWJuKDY1NCwxKSkNCiAgc2FsaWRhPShudW0xKm51bTIpLyhkZW5vbSkNCiAgcmV0dXJuKHNhbGlkYSkNCn0NClBNRjEgKDApDQpgYGANCg0KYGBge3J9DQpQTUYxICgxKQ0KYGBgDQojDQoNCmBgYHtyfQ0KcGRmPXNhcHBseSh4LCBGVU49UE1GMSkNCnBkZg0KYGBgDQoNCmBgYHtyfQ0KZGF0b3M9ZGF0YS5mcmFtZSh4PXgscHg9cGRmKQ0KZGF0b3MNCmBgYA0KIyMjICpDb25jbHVzaW9uIFBERjogTGEgZGVuc2lkYWQgZGUgcHJvYmFiaWxpZGFkIHF1ZSB1bmEgbXVqZXIgc2VhIHZpY3RpbWEgZGUgaG9taWNpZGlvIGVuIGVsIG11bmljaXBpbyBkZSBHdWF0ZW1hbGEgZXMgZWwgMTcuMTIlKg0KDQoNCiMjIyBPYnRlbmVyIGVsIENERg0KDQpgYGB7cn0NCmNkZj1jdW1zdW0ocGRmKQ0KY2RmDQpgYGANCmBgYHtyfQ0KZGF0b3M9ZGF0YS5mcmFtZShkYXRvcyxGeD1jZGYpDQpkYXRvcw0KYGBgDQpgYGB7cn0NCnZhbG9yX2VzcGVyYWRvPWZ1bmN0aW9uKGRmKXsNCng9ZGZbICwxXQ0KcHg9ZGYgWyAsMl0NClZFPXN1bSh4KnB4KQ0KcmV0dXJuKFZFKX0NCmBgYA0KYGBge3J9DQp2YWxvcl9lc3BlcmFkbyhkYXRvcykgI21lZGlhIHBvbmRlcmFkYQ0KYGBgDQojIyMgT2J0ZW5lciBsYSBWYXJpYW56YQ0KYGBge3J9DQp2YXJpYW56YT1mdW5jdGlvbihkZil7DQogIG1lZGlhPXZhbG9yX2VzcGVyYWRvKGRmKQ0KICB4PWRmIFsgLDFdDQogIHB4PWRmIFsgLDJdDQogIHZhclg9c3VtKCgoeC1tZWRpYSleMikqKHB4KSkNCiAgcmV0dXJuKHZhclgpDQogIA0KfQ0KYGBgDQoNCmBgYHtyfQ0KdmFyaWFuemEoZGF0b3MpDQpgYGANCg0KIyMjICpDb25jbHVzaW9uIENERiBQb2RlbW9zIG9ic2VydmFyIGxhIHZhcmlhYmlsaWRhZCBkZSBsb3MgZGF0b3MgYSB1biAwLjE0LCBsYSBjdWFsIGluZGljYSBsYSBkaXN0YW5jaWEgcXVlIGhheSBoYWNpYSBsYSBtZWRpYSoNCg0KDQojIyMgKipCZXN0IEZpdCwgdG9tYW5kbyBlbiBjdWVudGEgbGEgRWRhZCoqDQoNCmBgYHtyfQ0KZGF0YXNldCRlZGFkX3Blcg0KYGBgDQoNCg0KYGBge3J9DQpFZGFkQ29ycmVjdGE9ZGF0YXNldFsoZGF0YXNldCRlZGFkX3Blcjw5OTkpLCAyMF0NCmBgYA0KDQpgYGB7cn0NClRhYmxhRWRhZD1kYXRhX2ZyYW1lKHRhYmxlKEVkYWRDb3JyZWN0YSkpDQpgYGANCmBgYHtyfQ0KVGFibGFFZGFkDQpgYGANCg0KYGBge3J9DQpkZXNjZGlzdChFZGFkQ29ycmVjdGEsIGRpc2NyZXRlID0gRkFMU0UpDQpgYGANCg0KYGBge3J9DQpoaXN0KEVkYWRDb3JyZWN0YSwNCiAgICAgICAgY29sPWJsdWVzOSwNCiAgICAgICAgeGxhYj0gIkVkYWQiLA0KICAgICAgICB5bGFiPSAiQ2FudGlkYWQgZGUgRGVsaXRvcyIsDQogICAgICAgIG1haW49ICJHcmFmaWNhIGRlIGRlbGl0b3MgcG9yIGVkYWQiLA0KICAgICAgICBsYXM9MikNCmBgYA0KDQojIyMgKkNvbmNsdXNpb24gQkVTVCBGSVQ6IEFsIGFuYWxpemFyIGxhIGNhbnRpZGFkIGRlIERlbGl0b3MgcG9yIGVkYWQgIHBvZGVtb3MgY29uY2x1aXIgcXVlIHNlIGFwZWdhIGEgdW5hIGRpc3RyaWJ1Y2lvbiBub3JtYWwsIG1pc21hIHNlIHZhbGlkbyByZWFsaXphbmRvIHVuIGhpc3RvZ3JhbWEgZGUgZnJlY3VlbmNpYSBwb3IgZWRhZCBlbCBjdWFsIHNlIHB1ZWRlIHZlciB1biBsZXZlIHNlc2dvIGhhY2lhIGxhIGRlcmVjaGEsIHNpZW5kbyBsYXMgZWRhZGVzIG1hcyB2dWxuZXJhYmxlcyBlbnRyZSBsb3MgMjAgeSA0MCBhw7Fvcy4gICoNCg0K