Introducción

En el presente trabajo se abordará el tema de interpolación de datos, en esta ocasión se realizarán los métodos y análisis correspondientes para un conjunto de datos de precipitación que cubren el departamento de Caquetá. Se hará la recopilación de varios cuadernos realizados durante el primer semestre de 2020, cuyas gráficas serán un apoyo para describir la zona de estudio, que es el departamento de Caquetá. Se hizo uso de la herramienta QGIS, la cual se trabajó en algunas de las clases del curso de geomática básica, además de consultar datos en el DANE o CHIRPS.

La interpolación de datos es muy importante para distintas carreras, entre ellas la Ingeniería Agronómica, donde el conocimiento de herramientas y métodos permite realizar importantes estudios de distintas variables como la degradación de suelos en una zona determinada, índice de vegetación, humedad del suelo, precipitación, entre otras. Estos datos permiten no sólo entender en contexto del momento, también predecir qué puede ocurrir en un futuro y, de ser posible, tomar medidas al respecto. Este trabajo fue elaborado para la materia de geomática básica, cuyo objetivo es entender distintas funcionalidades geoespaciales, generadas por el ambiente, en el programa de RStudio. Se hablará sobre qué es la interpolación, algunos conceptos básicos de la misma, explicación de tres técnicas diferentes para interpolación de datos de precipitación y su respectivo análisis, y algunas conclusiones.

Descripción de la zona

El departamento de Caquetá fue fundado el 02 de Mayo de 1845, se encuentra localizado al Sur de Colombia, tiene una extensión de 88.965 km2 aproximadamente y juega un papel importante en la biodiversidad debido a que un porcentaje importante de su territorio pertenece al sistema Amazónico, piedemonte Amazónico, se encuentran asentamientos humanos, y por ende la dinámica sociopolítica y económica (Gobernación de Caquetá, s.f).

Ubicación

Se encuentra ubicado hacia el sur del territorio colombiano, Su capital es Florencia y limita por el norte con el departamento del Huila y Meta, por el oriente con Vaupés y Guaviare, por el sur con Amazonas y Putumayo, y por el Occidente con Cauca y Huila (IGAC, 2008). Está dividido en diesiseis municipios, donde se encuentran muchos caseríos y sitios poblados.

Figura 1. Ubicación del departamento de Caquetá en Colombia. Mapa realizado en QGIS con datos de diva-GIS. Autoría propia. Se puede apreciar la ubicación del departamento de Caquetá, en color amarilo, al sur del país. Departamentos del departamento de Caquetá Figura 2. Ubicación del departamento de Caquetá en Colombia. Mapa realizado en QGIS con datos de diva-GIS. Autoría propia. Se pueden apreciar los diesiseis municipios que conforman el departamento de Caquetá: Albania, Belén de los Andaquíes, Cartagena de Chaira, Curillo, El Doncello, El Paujil, Florencia, Milán, Montañita, Morelia, Puerto Rico, San José del Fragua, San Vicente del Caguán, Solano, Solita y Valparaiso.

Clima y población

La mayoría del departamento presenta un clima cálido que oscila entre los 27°C y los 29°C, alta pluviosidad, donde el verano generalmente se presenta en los meses de Diciembre a Febrero y los meses restantes son de invierno (López, 2006).

Necesidades Básicas Insatisfechas

Las Necesidades Básicas Insatisfechas (NBI) que presentan los habitantes de cada municipio y producción en el año 2018 de algunos cultivos en Caquetá.

Tabla 1. Datos de NBI que presentan los municipios de Caqueta. Los municipios se encuentran en orden descendente acorde con su respectivo porcentaje de NBI, donde el municipio de Milán es el que mayor porcentaje de NBI presenta, donde aproximadamente el 47% de la población tiene Necesidades Basicas Instatisfechas, mientras que el municipio con menor porcentaje de NBI es Florencia, donde cerca del 14.5% de su población presenta Necesidades Basicas Instafisfechas. Fuente: Autoria propia con datos recopilados por el DANE.

Reading layer `MGN_MPIO_POLITICO' from data source `D:\Documentos\Geomática\ADMINISTRATIVO1\MGN_MPIO_POLITICO.shp' using driver `ESRI Shapefile'
Simple feature collection with 16 features and 9 fields
geometry type:  POLYGON
dimension:      XY
bbox:           xmin: -76.30622 ymin: -0.70584 xmax: -71.25385 ymax: 2.964148
geographic CRS: WGS 84
Simple feature collection with 6 features and 3 fields
geometry type:  POLYGON
dimension:      XY
bbox:           xmin: -76.1027 ymin: 0.9764735 xmax: -74.89527 ymax: 2.326755
geographic CRS: WGS 84
               MUNICIPIO MPIO_CCDGO      NBI                       geometry
1              FLORENCIA      18001 14.44902 POLYGON ((-75.42074 2.19413...
2                ALBANIA      18029 19.80289 POLYGON ((-75.89506 1.36569...
3 BELÉN DE LOS ANDAQUIES      18094 28.28503 POLYGON ((-75.78705 1.74982...
4            EL DONCELLO      18247 20.37901 POLYGON ((-75.36167 2.32142...
5              EL PAUJIL      18256 23.33489 POLYGON ((-75.36691 2.21234...
6           LA MONTAÑITA      18410 32.51475 POLYGON ((-75.40404 1.76944...
Simple feature collection with 6 features and 21 fields
geometry type:  POLYGON
dimension:      XY
bbox:           xmin: 774588.2 ymin: 599751.7 xmax: 908977.8 ymax: 749113.8
projected CRS:  MAGNA-SIRGAS / Colombia Bogota zone
  DPTO_CCDGO MPIO_CCDGO             MPIO_CNMBR
1         18      18001              FLORENCIA
2         18      18029                ALBANIA
3         18      18094 BELÉN DE LOS ANDAQUÍES
4         18      18247            EL DONCELLO
5         18      18256              EL PAUJIL
6         18      18410           LA MONTAÑITA
                             MPIO_CRSLC MPIO_NAREA MPIO_NANO
1       Decreto 642 de Junio 17 de 1912   2547.638      2017
2   Ordenanza 3 de Noviembre 12 de 1985    414.122      2017
3       Decreto 963 de Marzo 14 de 1950   1191.619      2017
4  Decreto 1678 de Septiembre 7 de 1967   1105.803      2017
5 Decreto 1678 de Septiembret 7 de 1967   1234.743      2017
6         Decreto 83 de Julio 6 de 1955   1701.052      2017
  DPTO_CNMBR Shape_Leng Shape_Area COD_DEPTO   DEPTO COD_MUN
1    CAQUETÁ   2.942508 0.20692777        18 CAQUETÁ     001
2    CAQUETÁ   1.112829 0.03361758        18 CAQUETÁ     029
3    CAQUETÁ   2.234657 0.09674460        18 CAQUETÁ     094
4    CAQUETÁ   3.154370 0.08986744        18 CAQUETÁ     247
5    CAQUETÁ   3.529316 0.10030928        18 CAQUETÁ     256
6    CAQUETÁ   3.402939 0.13817351        18 CAQUETÁ     410
               MUNICIPIO      NBI  MISERIA  VIVIENDA
1              FLORENCIA 14.44902 2.774899  5.224497
2                ALBANIA 19.80289 4.400642  9.832684
3 BELÉN DE LOS ANDAQUIES 28.28503 7.091305 12.143430
4            EL DONCELLO 20.37901 3.898247 10.300478
5              EL PAUJIL 23.33489 5.170800 13.718609
6           LA MONTAÑITA 32.51475 8.972579 17.086081
  SERVICIOS HACINAMIENTO INASISTENCIA  ECONOMIA
1  1.488778     4.434199     2.077731  4.529297
2  3.208801     4.606922     1.260601  6.119642
3  3.906519     5.602016     4.926108 10.654141
4  1.473936     3.704758     2.025950  7.608696
5  2.823273     5.186398     2.737482  5.357978
6  7.150295     5.128428     2.724748 11.315515
                        geometry    Pobreza
1 POLYGON ((850567.7 734450.4... Intermedia
2 POLYGON ((797693.6 642855.1... Intermedia
3 POLYGON ((809754.1 685340, ...       Alta
4 POLYGON ((857152.4 748524, ... Intermedia
5 POLYGON ((856558 736458.9, ...       Alta
6 POLYGON ((852387.3 687475.8...       Alta
opar <- par(mar = c(0,0,1.2,0))
par(bg="white")
plot(st_geometry(nbi_munic_2), col = "#e4e9de", border = "darkseagreen4", 
     bg = "grey85", lwd = 0.5)
choroLayer(
  x = nbi_munic_new, 
  var = "NBI",
  method = "geom",
  nclass=5,
  col = carto.pal(pal1 = "orange.pal", n1 = 5),
  border = "Black", 
  lwd = 0.2,
  legend.pos = "topleft", 
  legend.title.txt = "NBI",
  add = TRUE
) 

labelLayer(
  x = nbi_munic_2, 
  txt = "MUNICIPIO", 
  col= "white", 
  cex = 0.4, 
  font = 4,
  halo = TRUE, 
  bg = "black", 
  r = 0.1, 
  overlap = FALSE, 
  show.lines = FALSE
)
layoutLayer(
  title = "Municipios del departamento de Caqueta", 
  sources = "Fuente: DANE, 2018",  
  author = "Sandra Katteryne Rodríguez Hurtado", 
  frame = TRUE,
  north = TRUE, 
  tabtitle = TRUE, 
  theme = "taupe.pal"
) 

Figura 3. Mapa del porcentaje de NBI de los municipios de Caquetá. El mapa refleja los datos de la tabla 1, donde cada municipio lleva la etiqueta de su nombre correspondiente, cuando el color se torna más oscuro, mayor será el porcentade de NBI que presenta esa población. Fuente: Autoria propia con datos recopilados por el DANE.

Economía

Dentro de las principales actividades económicas que se encuentran en el departamento sobresale la ganadería y la agricultura, en esta última se encuentran cereales, flores y follajes, forestales, frutales, hortalizas, leguminosas, oleaginosas, otros permanentes, tubérculos y plátanos (DANE, 2017). Se debe tener en cuenta que, pese a que en las tablas no se dan unidades, las de área son hectáreas (Ha), y las unidades de rendimientos son toneladas/Ha.

Parsed with column specification:
cols(
  COD_DEP = col_double(),
  DEPARTAMENTO = col_character(),
  COD_MUN = col_double(),
  MUNICIPIO = col_character(),
  GRUPO = col_character(),
  SUBGRUPO = col_character(),
  CULTIVO = col_character(),
  YEAR = col_double(),
  Area_Siembra = col_double(),
  Area_cosechada = col_double(),
  Produccion = col_double(),
  Rendimiento = col_double(),
  ESTADO = col_character(),
  CICLO = col_character()
)
`summarise()` regrouping output by 'GRUPO' (override with `.groups` argument)

Tabla 2. Municipios con mayor área cosechada en el año 2018. Se puede apreciar que el municipio San Vicente del Caguán fue el de mayor área sembrada en el grupo de cereales, seguido de Cartagena del Chaira para el grupo de Tubérculos y plátanos, y Florencia, para el grupo de otros permanentes. Fuente: Autoria propia con datos recopilados por el DANE.

Tabla 3. Producción del cultivo de Maiz, perteneciente al grupo de cereales, para el Municipio de San Vicente del Caguán (en toneladas).

g + ggtitle("Evolución de la producción de Maiz en San Vicente del Caguán de 2007 a 2018") + labs(caption= "Basado en los datos de EMA (DANE, 2018)")

Gráfico 1. Evolución de la producción de Maiz en San Vicente del Caguán de 2007 a 2018. Se puede apreciar que para el año 2018 se obtuvo una producción de Maiz, en el municipio de San Vicente del Caguán, de cerca de cinco mil toneladas. La producción máxima de maiz fue para el año de 2013, con cerca de siete mil toneladas, lo anterior se puede corroborar con la información de la tabla 3.

Tabla 4. Producción del cultivo de plátano, perteneciente al grupo de Tubérculos y plátanos, para el Municipio de Cartagena del Chaira (en toneladas).

g + ggtitle("Evolución de la producción de Plátano en Milán de 2007 a 2018") + labs(caption= "Basado en los datos de EMA (DANE, 2018)")

Gráfico 2. Evolución de la producción de Plátano en Milán de 2007 a 2018. Se puede apreciar que la producción de plátano en el municipio de Milán ha ido aumentando en los últimos años, donde en este último año tuvo una producción de cerca de 22 toneladas de plátano.

`summarise()` ungrouping output (override with `.groups` argument)

Tabla 5. Rendimientos para cultivos del departamento de Caquetá en 2018. La siguiente tabla muestra los grupos de cultivo con el total de rendimientos (Tonelada/ha) de manera descendente, donde los frutales, tubérculos y plátanos, y hortalizas ocuán los primeros lugares.

g+ ggtitle("Rendimiento por grupos de cultivos en Caquetá para 2018") + theme(plot.title = element_text(hjust = 0.5)) +
   labs(caption= "Basado en los datos de EMA (DANE, 2018)")

Gráfico 3. Rendimientos por grupos de cultivos en Caquetá para el año 2018. Se puede apreciar que los grupos de cultivos que presentaron mayores rendimientos para el año 2018 fueron los frutales, tubérculos y plátanos, hortalizas y otros permanentes.

`summarise()` regrouping output by 'CULTIVO' (override with `.groups` argument)

Tabla 6. Municipios con mayores rendimientos en Frutales. Se pueden apreciar los municipios con mayores rendimientos (Tonelada/ha) en los cultivos que componen el grupo de Frutales, en el departamento de Caquetá. Se realizó con el grupo de frutales debido a que es el grupo que presentó los mayores rendimientos en el año 2018 en Caquetá. Los municipios de San Vicente del Caguán y Valparaiso tuvieron los mayores rendimientos con los cultivos de Fresa y Arazá respectivamente.

datos %>% 
  filter(YEAR==2018 & GRUPO=="TUBERCULOS Y PLATANOS") %>% 
  group_by(CULTIVO, MUNICIPIO) %>%
  summarize(Rendimiento = max(Rendimiento, na.rm = TRUE)) %>%
    slice(which.max(Rendimiento)) -> Rendimiento
`summarise()` regrouping output by 'CULTIVO' (override with `.groups` argument)
Rendimiento

Tabla 7. Municipios con mayores rendimientos en Tubérculos y plátanos. Se puede apreciar que los municipios de Cartagena del Chaira, Milán y Solano fueron los que tuvieron mayores rendimientos en los cultivos de yuca, plátano y Ñame respectivamente.

png("D:/Documentos/Geomática/platano_2018p.png", width = 1024, height = 763)

opar <- par(mar = c(2,2,5,5))

plot(st_geometry(rep_platano), col="darkseagreen", border="darkseagreen4",  
     bg = "white", lwd = 0.6)

propSymbolsChoroLayer(x = rep_platano, var = "Produccion", var2 = "Rendimiento",
                      col = carto.pal(pal1 = "turquoise.pal", n1 = 3,
                                      pal2 = "pink.pal", n2 = 3),
                      inches = 0.5, method = "q6",
                      border = "black", lwd = 1,
                      legend.title.cex = 1.3,
                      legend.values.cex = 1.3,
                      legend.var.pos = "topright", 
                      legend.var2.pos = "topleft",
                      legend.var2.values.rnd = 2,
                      legend.var2.title.txt = "Rendimiento\n(en Ton/Ha)",
                      legend.var.title.txt = "Producción de Plátano, 2018",
                      legend.var.style = "e")

labelLayer(
  x = rep_platano, 
  txt = "MPIO_CNMBR", 
  col= "black", 
  cex = 1, 
  font = 18,
  halo = FALSE, 
  bg = "white", 
  r = 0.1, 
  overlap = FALSE, 
  show.lines = FALSE
)

layoutLayer(title="Producción y rendimiento de Plátano en Caquetá, 2018",
            author = "Sandra Katteryne Rodríguez Hurtado", 
            sources = "Fuentes: MADR & DANE, 2018", 
            scale = 50, tabtitle = FALSE, frame = TRUE)

north(pos = "top")

title(main="Producción y rendimiento de Plátano en Caquetá, 2018", cex.main=3,
      sub= "Fuentes: MADR & DANE, 2018", cex.sub=2)

graticule = TRUE

par(opar)

dev.off()
Producción y rendimiento de plátano en Caquetá para el año 2018

Producción y rendimiento de plátano en Caquetá para el año 2018

Figura 4. Producción y rendimiento de plátano en Caquetá para el año 2018 por municipios. Se pueden apreciar que los municipios de mayor producción de plátano son Milán, San Vicente del Caguán y Cartagena del Chaira.

Descripción de datos y métodos

Datos

Carreras tales como la ingeniería Agronómica necesitan recolectar datos en puntos específicos y partiendo de ellos hacer representaciones continuas de una zona determinada, y para ello es necesario hacer interpolación (Lizarazo, 2020). La interpolación o modelación, toma datos recolectados en puntos finitos específicos para volverlos datos continuos, representaciones de mapas útiles y con sentido, estos últimos puntos predicen características similares a las de los puntos muestreados para áreas no muestreadas, predicen valores para celdas de un ráster (ArcGIS, s.f). Las superficies ráster presentan una forma de cuadrícula, donde a menor tamaño de las celdas, mayor será su precisión.

Para poder interpolar datos, estos deben ser cuantitativos, analizando variables como pH, precipitación, humedad, índice de vegetación, no cuantitativos. Los datos pueden ser recolectados en una estación meteorológica, en el caso de Colombia estas estaciones no son muchas y no abarcan todo el territorio nacional, pues algunas se encuentran en los principales aeropuertos y otras pertenecen a gremios, donde el acceso no es público (Lizarazo, 2020).

En este trabajo se usaron los datos del CHIRPS (Climate Hazards Group InfraRed Precipitation with Station Data), que son datos de estimaciones globales de precipitación, basadas en satélites de la NASA y NOAA, y observaciones sobre la tierra. Los datos tienen una resolución de 0,05 y 0,25 grados (5,5 y 28 km) en formatos BIL, TIF o NetCDF (Grupo Kraken, 2019). Se expanden de 50°S a 50°N y a lo largo de todas las latitudes, comprendiendo datos desde 1981 hasta la actualidad, tienen alta resolución y un largo periodo de registro.

Tienen la capacidad de incorporar imágenes satelitales a datos obtenidos de estaciones meteorológicas para crear series de cuadrículas pluviométricas con unidades en milímetros, que permiten realizar estudios como tendencias o sequías (IRI, 2015). CHIRPS incorpora datos de estimaciones de precipitación diarias, pentadales y mensuales; hay seis pentads en un mes calendario, cinco pentads de 5 días y un pentad con los 3 a 5 días restantes del mes (Funk et al., 2015). Los datos fueron descargados del siguiente link http://data.chc.ucsb.edu/products/CHIRPS-2.0/, directorio global_pentad, posteriormente entrar a tifs y seleccionar la fecha más reciente, que fue el 18/05/2020.

Métodos

Existen dos tipos de técnicas para generar superficies de interpolación: modelos deterministas, que usan funciones matemáticas para predecir valores desconocidos, y técnicas estadísticas, que producen límites para determinar la precisión de una predicción. Se explicarán tres métodos diferentes para interpolar datos, siendo IDW, primer orden polinomial y Kriging.

Inverse Distance Weighting (IDW)

El método de IDW (Inverse Distance Weighting) pertenece a la técnica determinista, es matemático, donde los valores más cercanos están más relacionados con la variable que se esté estudiando, es decir que los puntos más cercanos comparten características similares a diferencia de los puntos lejanos (GIS Geography, s.f.). Por ejemplo, al llover en un punto determinado, se puede predecir que cerca de este punto también está lloviendo, a diferencia de un punto lejano, donde no se podría hacer esta afirmación (autocorrelación espacial). Se pueden estimar valores desconocidos de celda raster a partir de valores conocidos tomados en puntos de muestra.

Al tener un área de estudio y determinados puntos de muestra con valores conocidos, si se quisiera medir un punto en específico, es necesario tomar los puntos más cercanos dentro del radio de la zona de interés para poder realizar la interpolación, puede ser un número fijo o variable de puntos (GIS Geography, s.f.). Los puntos desconocidos se estiman partiendo de los valores conocidos de los puntos muestreados, el valor de potencia le permite controlar la significancia de los puntos desconocidos (ArcGIS, s.f.), donde el valor de 2 es el más usado. Su fórmula es: Fórmula de IDW

Figura 5. Fórmula de IDW. Esta fórmula tiene el número sigma, que es el número de puntos que se interpolarán, z: Variable de estudio, zp: punto desconocido, n: número de puntos que están dentro del radio de búsqueda, zi: valor conocido del punto en el radio de búsqueda, di^p: Distancia entre el punto y el punto desconocido, p: Potencia. Se considera determinístico ya que está basado en los valores medidos y en fórmula matemática, que determinan la suavidad de la superficie generada (ArcGIS, s.f).

Kriging

Es un método de interpolación geoestadístico para crear superficies estimadas en base a unos puntos con valores conocidos de la variable de estudio, se basa en modelos estadísticos, es decir que los puntos muestreados se relacionan con la estadística. Lo anterior permite que resulte una superficie de predicción y medidas de precisión de las estimaciones (ArcGIS, s.f).

Al igual que IDW, el kriging utiliza valores de puntos muestreados dentro de un radio, ajustándolos a una función matemática. El kriging se basa en un variograma que determinan la autocorrelación, acorde con el geógrafo Tobler: “Todo está relacionado con todo lo demás, pero las cosas cercanas están más relacionadas que las distantes”, esto quiere decir la autocorrelación es el grado de similitud entre un objeto y los objetos cercanos al mismo (GIS Geography, 2020), representando gráficamente la varianza de los datos acorde con su distancia. Si los puntos están más cercanos, tendrán una varianza pequeña, mientras que si los puntos están más alejados, probablemente se tendrá una varianza alta. De lo anterior se puede hacer una gráfica que tiene un rango y un umbral, donde el último se alcanza al nivelarse la variación, no habría autocorrelación espacial entre los datos (GIS Geography, 2020).
Fórmula de Kriging

Figura 6. Fórmula de Kriging. z(si): Valor medido en la ubicación i, Lamda i: ponderación desconocida para el valor medido en la ubicación i, s0: Ubicación de la predicción, N: cantidad de valores medidos. Tomado de: https://desktop.arcgis.com/es/arcmap/10.3/tools/spatial-analyst-toolbox/how-kriging-works.htm

Un semivariograma puede ser superficial, exponencial, circular, gaussiano o lineal; esto después de haber ajustado la superficie como un polinomio. Para usar este método, los datos deben tener una distribución normal, deben ser estacionarios y no tener ninguna tendencia (ArcGIS, s.f). Se dice que los datos tienen una distribución normal si los puntos están sobre una línea de 45°, los datos son estacionarios si la variación local de estos no cambia en diferentes áreas del mapa, es decir que no hay cambios abruptos o líneas discontinuas, se puede verificar mediante un mapa de voronoi, que refleja la desviación estándar. Según las predicciones que la técnica de Kriging haga, generará también una medida de incertidumbre o error, estimando la confianza de la superficie.

Los gráficos de los semivariogramas pueden ser calculados con la ecuación:

Semivariograma(distanciah) = 0.5 * promedio((valori – valorj)^2)

dando como resultado un gráfico de los valores de semivariograma promediados ubicados en el eje Y, y la distancia o intervalo en el eje X. Entonces, la ubicación de los puntos proyectados en este gráfico permite conocer si son valores similares o no, si los puntos están uno cerca del otro, significa que comparten características similares, a diferencia de si se encuentran separados uno del otro, significando que son distintos (ArcGIS, s.f).

Polígonos de Thiessen o Diagramas de Voronoi

Son uno de los métodos para interpolar más sencillos ya que hay, están basados en una construcción geométrica que permiten hacer particiones de un plano que representará el área de interés. Su nombre fue puesto en honor al meteorólogo Alfred Thiessen, aunque también fueron estudiados por el matemático Georgy Voronoi, método denominado también Diagramas de Voronoi en honor al matemático (Bravo, s.f).

Este método tiene múltiples funciones, dentro de ellas se encuentra el análisis de datos meteorológicos o determinar áreas de influencia en una zona, por ejemplo iglesias o centros comerciales. Para el caso de precipitación, es necesario saber dónde se encuentran ubicadas las estaciones pluviométricas para identificar el área de influencia de dicha estación. Al unirse los puntos entre sí, se van trazando a su vez mediatrices (líneas perpendiculares a un segmento que pasa por su punto medio) de los segmentos de unión, creando una serie de polígonos en un espacio de dos dimensiones alrededor de un conjunto finito de puntos (Bravo, s.f). Forman triángulos que unen las estaciones, por medio de líneas rectas sin que estas se entrecortan (Gimond, 2019). Una limitante que presenta este método es que no se puede estimar el valor de incertidumbre o error debido a que un solo polígono se obtiene de un solo punto. El tamaño y la forma de cada polígono depende de la distribución de los puntos. Estas estructuras son de vital importancia en la geometría computacional, son capaces de guardar información referente a una proximidad entre puntos.

Presentación de resultados

Una vez descargados los datos y cargadas las librerías, se procedió a leerlos, presentaron una resolución de celda de 0.05 y fue una capa ráster. Son datos globales, tienen un sistema de coordenadas geográficas WGS84.

class      : RasterLayer 
dimensions : 2000, 7200, 14400000  (nrow, ncol, ncell)
resolution : 0.05, 0.05  (x, y)
extent     : -180, 180, -50, 50  (xmin, xmax, ymin, ymax)
crs        : +proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0 
source     : D:/Escritorio/chirps-v2.0.2020.04.6.tif 
names      : chirps.v2.0.2020.04.6 

Se importará un archivo de formato shapefile para el área que se desea estudiar, en este caso el departamento de Caquetá, el cual se compone de 16 municipios, sistema de coordenadas WGS84 y nueve variables.

class       : SpatialPolygonsDataFrame 
features    : 16 
extent      : -76.30622, -71.25385, -0.70584, 2.964148  (xmin, xmax, ymin, ymax)
crs         : +proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0 
variables   : 9
names       : DPTO_CCDGO, MPIO_CCDGO,  MPIO_CNMBR,                           MPIO_CRSLC,    MPIO_NAREA, MPIO_NANO, DPTO_CNMBR,    Shape_Leng,      Shape_Area 
min values  :         18,      18001,     ALBANIA, Decreto 1678 de Septiembre 7 de 1967,  403.35827433,      2017,   CAQUETÁ,  1.1128288978, 0.0327393194813 
max values  :         18,      18860, VALPARAÍSO,  Ordenanza 3 de Noviembre 12 de 1985, 42312.7997376,      2017,   CAQUETÁ, 20.0458589874,   3.43579026269 

Para dar valores nulos a las áreas que se encuentran fuera de los límites del departamento se usó la función mask, siendo una capa raster.

class      : RasterLayer 
dimensions : 19, 26, 494  (nrow, ncol, ncell)
resolution : 0.2, 0.2  (x, y)
extent     : -76.4, -71.2, -0.8000008, 2.999999  (xmin, xmax, ymin, ymax)
crs        : +proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0 
source     : memory
names      : chirps.v2.0.2020.04.6 
values     : 18.95572, 73.44761  (min, max)
plot(precip.mask, main= "CHIRPS de Precipitación en Caquetá desde 18/05/2020 hasta 23/05/2020 [mm]")
plot(aoi, add=TRUE)

Figura 7. Mapa de vista del precipitación del departamento de Caquetá.

pal <- colorNumeric(c("red", "orange", "yellow", "blue", "darkblue"), values(precip.mask),
  na.color = "transparent")

leaflet() %>% addTiles() %>%
  addRasterImage(precip.mask, colors = pal, opacity = 0.6) %>%
  addLegend(pal = pal, values = values(precip.mask),
    title = "CHIRPS de Precipitación en Caquetá\n desde 18/05/2020 hasta 23/05/2020 [mm]")
Some values were outside the color scale and will be treated as NA

Figura 8. Mapa interactivo de precipitación en Caquetá.

class       : SpatialPointsDataFrame 
features    : 183 
extent      : -76.1, -71.3, -0.5000008, 2.899999  (xmin, xmax, ymin, ymax)
crs         : +proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0 
variables   : 1
names       : chirps.v2.0.2020.04.6 
min values  :      18.9557183384895 
max values  :      73.4476075172424 
class       : SpatialPointsDataFrame 
features    : 183 
extent      : -76.1, -71.3, -0.5000008, 2.899999  (xmin, xmax, ymin, ymax)
crs         : +proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0 
variables   : 1
names       :           Lluvia 
min values  : 18.9557183384895 
max values  : 73.4476075172424 
Formal class 'SpatialPointsDataFrame' [package "sp"] with 5 slots
  ..@ data       :'data.frame': 183 obs. of  1 variable:
  .. ..$ Lluvia: num [1:183] 34.7 37 44.5 47.8 49.4 ...
  ..@ coords.nrs : num(0) 
  ..@ coords     : num [1:183, 1:2] -74.9 -75.1 -74.9 -74.7 -75.1 ...
  .. ..- attr(*, "dimnames")=List of 2
  .. .. ..$ : NULL
  .. .. ..$ : chr [1:2] "x" "y"
  ..@ bbox       : num [1:2, 1:2] -76.1 -0.5 -71.3 2.9
  .. ..- attr(*, "dimnames")=List of 2
  .. .. ..$ : chr [1:2] "x" "y"
  .. .. ..$ : chr [1:2] "min" "max"
  ..@ proj4string:Formal class 'CRS' [package "sp"] with 1 slot
  .. .. ..@ projargs: chr "+proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0"

Plotear los puntos para llevar a cabo la interpolación.

plot(precip.mask, main= "CHIRPS Lluvia desde 18/05/2020 hasta 23/05/2020 [mm]")
plot(aoi, add=TRUE)
points(precip.points$x, precip.points$y, col = "purple", cex = .1)

Figura 9.Departamento de Caquetá con los puntos para la interpolación.

class       : SpatialPointsDataFrame 
features    : 183 
extent      : -76.1, -71.3, -0.5000008, 2.899999  (xmin, xmax, ymin, ymax)
CRS object has comment, which is lost in output
crs         : +proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0 
variables   : 1
names       :           Lluvia 
min values  : 18.9557183384895 
max values  : 73.4476075172424 

Es necesario pasar los datos a coordenadas planas porque no es recomendable hacer interpolación con los datos en coordenadas geográficas (datumWGS84).

class       : SpatialPolygonsDataFrame 
features    : 16 
extent      : -76.30622, -71.25385, -0.70584, 2.964148  (xmin, xmax, ymin, ymax)
crs         : +proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0 
variables   : 9
names       : DPTO_CCDGO, MPIO_CCDGO,  MPIO_CNMBR,                           MPIO_CRSLC,    MPIO_NAREA, MPIO_NANO, DPTO_CNMBR,    Shape_Leng,      Shape_Area 
min values  :         18,      18001,     ALBANIA, Decreto 1678 de Septiembre 7 de 1967,  403.35827433,      2017,   CAQUETÁ,  1.1128288978, 0.0327393194813 
max values  :         18,      18860, VALPARAÍSO,  Ordenanza 3 de Noviembre 12 de 1985, 42312.7997376,      2017,   CAQUETÁ, 20.0458589874,   3.43579026269 
class       : SpatialPolygonsDataFrame 
features    : 1 
extent      : -76.30622, -71.25385, -0.70584, 2.964148  (xmin, xmax, ymin, ymax)
CRS object has comment, which is lost in output
crs         : +proj=longlat +ellps=WGS84 +towgs84=0,0,0,0,0,0,0 +no_defs 
variables   : 1
names       :           area 
value       : 90103.00816646 

Polígonos

Simple feature collection with 16 features and 2 fields
geometry type:  POLYGON
dimension:      XY
bbox:           xmin: -76.30622 ymin: -0.70584 xmax: -71.25385 ymax: 2.964148
CRS:            +proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0
First 10 features:
                      MUNIC CODIGO
1                 FLORENCIA  18001
2                   ALBANIA  18029
3  BELÉN DE LOS ANDAQUÃ\u008dES  18094
4               EL DONCELLO  18247
5                 EL PAUJIL  18256
6             LA MONTAÑITA  18410
7               MILÃ\u0081N  18460
8                   MORELIA  18479
9      SAN JOSÉ DEL FRAGUA  18610
10         VALPARAÃ\u008dSO  18860
                         geometry
1  POLYGON ((-75.42074 2.19413...
2  POLYGON ((-75.89506 1.36569...
3  POLYGON ((-75.78705 1.74982...
4  POLYGON ((-75.36167 2.32142...
5  POLYGON ((-75.36691 2.21234...
6  POLYGON ((-75.40404 1.76944...
7  POLYGON ((-75.39362 1.35738...
8  POLYGON ((-75.77185 1.57991...
9  POLYGON ((-76.16722 1.58752...
10 POLYGON ((-75.73128 1.32740...

Una intersección de datos es una operación geométrica entre dos elementos distintos, cuyo resultado busca que por cada elemento que se intercepte y arroje un elemento, donde queden los atributos de ambos objetos en uno solo. En este caso, en un elemento quedaron consignados los elementos municipio (polígonos) y la precipitación (puntos.)

although coordinates are longitude/latitude, st_intersection assumes that they are planar
attribute variables are assumed to be spatially constant throughout all geometries
Simple feature collection with 183 features and 3 fields
geometry type:  POINT
dimension:      XY
bbox:           xmin: -76.1 ymin: -0.5000008 xmax: -71.3 ymax: 2.899999
CRS:            +proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0
First 10 features:
                       MUNIC CODIGO   Lluvia
12   SAN VICENTE DEL CAGUÃ\u0081N  18753 34.66168
12.1 SAN VICENTE DEL CAGUÃ\u0081N  18753 36.99089
12.2 SAN VICENTE DEL CAGUÃ\u0081N  18753 44.50369
12.3 SAN VICENTE DEL CAGUÃ\u0081N  18753 47.77253
16               PUERTO RICO  18592 49.42595
12.4 SAN VICENTE DEL CAGUÃ\u0081N  18753 48.35983
12.5 SAN VICENTE DEL CAGUÃ\u0081N  18753 48.97882
16.1             PUERTO RICO  18592 32.69428
16.2             PUERTO RICO  18592 51.43533
12.6 SAN VICENTE DEL CAGUÃ\u0081N  18753 51.31482
                   geometry
12   POINT (-74.9 2.899999)
12.1 POINT (-75.1 2.699999)
12.2 POINT (-74.9 2.699999)
12.3 POINT (-74.7 2.699999)
16   POINT (-75.1 2.499999)
12.4 POINT (-74.9 2.499999)
12.5 POINT (-74.7 2.499999)
16.1 POINT (-75.3 2.299999)
16.2 POINT (-75.1 2.299999)
12.6 POINT (-74.9 2.299999)

Dos tareas de reprotección: Dos maneras para reproyección, convirtiendo un objeto de característica simple (simplefeature), a un objeto espacial, pues las librerías requieren estos objetos.

class       : SpatialPointsDataFrame 
features    : 183 
extent      : 774851.6, 1309312, 436453.5, 812468.8  (xmin, xmax, ymin, ymax)
CRS object has comment, which is lost in output
crs         : +proj=tmerc +lat_0=4.59620041666667 +lon_0=-74.0775079166667 +k=1 +x_0=1000000 +y_0=1000000 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs 
variables   : 3
names       :       MUNIC, CODIGO,           Lluvia 
min values  :     ALBANIA,  18001, 18.9557183384895 
max values  : VALPARAÍSO,  18860, 73.4476075172424 

Eliminar cifras decimales de la variable Lluvia, que representa la preciítación en Caquetá.

#Esta instrucción es útil para que los valores de lluvia no reflejen tantas cifras decimales en el mapa.
precip2$Lluvia <- round(precip2$Lluvia, 1)
class       : SpatialPointsDataFrame 
features    : 183 
extent      : 774851.6, 1309312, 436453.5, 812468.8  (xmin, xmax, ymin, ymax)
CRS object has comment, which is lost in output
crs         : +proj=tmerc +lat_0=4.59620041666667 +lon_0=-74.0775079166667 +k=1 +x_0=1000000 +y_0=1000000 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs 
variables   : 3
names       :       MUNIC, CODIGO, Lluvia 
min values  :     ALBANIA,  18001,     19 
max values  : VALPARAÍSO,  18860,   73.4 
class       : SpatialPolygonsDataFrame 
features    : 16 
extent      : 751894.5, 1314457, 413692, 819562.9  (xmin, xmax, ymin, ymax)
CRS object has comment, which is lost in output
crs         : +proj=tmerc +lat_0=4.59620041666667 +lon_0=-74.0775079166667 +k=1 +x_0=1000000 +y_0=1000000 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs 
variables   : 2
names       :       MUNIC, CODIGO 
min values  :     ALBANIA,  18001 
max values  : VALPARAÍSO,  18860 

Trazar los datos con tmap: La libreía tmap permite hacer mapas, en este caso con los datos de precipitación y municipio del departamento de Caquetá.

tm_shape(caqueta2) + tm_polygons() +
There were 13 warnings (use warnings() to see them)
  tm_shape(precip2) +
  tm_dots(col="Lluvia", palette = "RdBu", midpoint = 3.0,
             title="Precipitación muestreada \n(en mm)", size=0.2) +
  tm_text("Lluvia", just="center", xmod=.1, size = 0.5) +
  tm_legend(legend.outside=TRUE)
CRS object has comment, which is lost in outputCRS object has comment, which is lost in output

Figura 10. Mapa con los puntos y sus respectivos valores de precipitación, en este caso variando en intervalos de a 10 mm. ### Métodos para interpolar datos de precipitación A continuación se representarán algunos de los métodos trabajados para la interpolación de datos de precipitación. #### 1. Polígonos de Thiessen Estos polígonos son (o polígnos de proximidad) se pueden crear utilizando la función dirichlet de spatstat. Arman unos polígonos que contienen todas las zonas que están más cerca de un punto que de otro

crs(th) <- crs(precip2)
crs(caqueta2) <- crs(precip2)
CRS arguments:
 +proj=tmerc +lat_0=4.59620041666667
+lon_0=-74.0775079166667 +k=1 +x_0=1000000
+y_0=1000000 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0
+units=m +no_defs 
CRS object has comment, which is lost in output
CRS arguments:
 +proj=tmerc +lat_0=4.59620041666667
+lon_0=-74.0775079166667 +k=1 +x_0=1000000
+y_0=1000000 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0
+units=m +no_defs 

Mapa

Figura 11. Mapa de polígonos de Thiessen. #### Interpolación ponderada de distancia inversa (IDW). La función IDW está presente en dos paquetes spatstat y gstat. Se debe crear primero una grilla con celdas que aún no tienen valores, esa grilla tiene 100.000 celdas, las cuales van a cubrir un territorio determinado, este último será el ráster de salida.

CRS object has comment, which is lost in outputCRS object has comment, which is lost in output
[inverse distance weighted interpolation]
class      : RasterLayer 
dimensions : 224, 311, 69664  (nrow, ncol, ncell)
resolution : 1806.052, 1806.052  (x, y)
extent     : 752544.8, 1314227, 414359.5, 818915.1  (xmin, xmax, ymin, ymax)
crs        : +proj=tmerc +lat_0=4.59620041666667 +lon_0=-74.0775079166667 +k=1 +x_0=1000000 +y_0=1000000 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs 
source     : memory
names      : var1.pred 
values     : 19.12434, 72.96179  (min, max)
class       : SpatialPolygonsDataFrame 
features    : 16 
extent      : 751894.5, 1314457, 413692, 819562.9  (xmin, xmax, ymin, ymax)
crs         : +proj=tmerc +lat_0=4.59620041666667 +lon_0=-74.0775079166667 +k=1 +x_0=1000000 +y_0=1000000 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs 
variables   : 2
names       :       MUNIC, CODIGO 
min values  :     ALBANIA,  18001 
max values  : VALPARAÍSO,  18860 
class      : RasterLayer 
dimensions : 224, 311, 69664  (nrow, ncol, ncell)
resolution : 1806.052, 1806.052  (x, y)
extent     : 752544.8, 1314227, 414359.5, 818915.1  (xmin, xmax, ymin, ymax)
crs        : +proj=tmerc +lat_0=4.59620041666667 +lon_0=-74.0775079166667 +k=1 +x_0=1000000 +y_0=1000000 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs 
source     : memory
names      : var1.pred 
values     : 19.12434, 72.96179  (min, max)

Plotear.

tm_shape(r.m) + 
  tm_raster(n=8,palette = "RdBu", auto.palette.mapping = FALSE,
            title="Distancia Inversa Poderada\nPrecipitación prevista\n(en mm)") + 
  tm_shape(precip2) + tm_dots(size=0.2) +
  tm_legend(legend.outside=TRUE)
The argument auto.palette.mapping is deprecated. Please use midpoint for numeric data and stretch.palette for categorical data to control the palette mapping.CRS object has comment, which is lost in output

Figura 12. Mapa de IDW sin la vista de los valores.

pal <- colorNumeric(c("red", "orange", "yellow", "blue", "darkblue"), values(precip.mask),
  na.color = "transparent")

leaflet() %>% addTiles() %>%
  addRasterImage(r.m, colors = pal, opacity = 0.6) %>%
  addLegend(pal = pal, values = values(r.m),
    title = "Precipitación interpolada IDW en Caquetá\n desde 18/05/2020 hasta 23/05/2020 en [mm]")

Figura 13. Mapa de interpolación IDW de precipitación.

class       : SpatialPointsDataFrame 
features    : 183 
extent      : 751894.5, 1314457, 413692, 819562.9  (xmin, xmax, ymin, ymax)
CRS object has comment, which is lost in output
crs         : +proj=tmerc +lat_0=4.59620041666667 +lon_0=-74.0775079166667 +k=1 +x_0=1000000 +y_0=1000000 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs 
variables   : 3
names       :       MUNIC, CODIGO, Lluvia 
min values  :     ALBANIA,  18001,     19 
max values  : VALPARAÍSO,  18860,   73.4 

Cálcular el error en los datos interpolados.

OP <- par(pty="s", mar=c(4,3,0,0))
  plot(IDW.out ~ P$Lluvia, asp=1, xlab="Observada", ylab="Prevista", pch=16,
       col=rgb(0,0,0,0.5))
  abline(lm(IDW.out ~ P$Lluvia), col="red", lw=2,lty=2)
  abline(0,1)

Gráfico 3. Semivariograma

Error medio cuadrático.

sqrt( sum((IDW.out - P$Lluvia)^2) / length(P))
[1] 6.650464

Validación cruzada.

r <- raster(img.sig, layer="v")
r.m <- raster::mask(r, caqueta2)

tm_shape(r.m) + tm_raster(n=8,title="IDW\n95% intervalo de confianza \n(en mm)") +
  tm_shape(P) + tm_dots(size=0.2) +
  
  tm_legend(legend.outside=TRUE)
CRS object has comment, which is lost in output

Figura 14. Mapa de intervalo de confianza de 95% del modelo de interpolación.

The argument auto.palette.mapping is deprecated. Please use midpoint for numeric data and stretch.palette for categorical data to control the palette mapping.CRS object has comment, which is lost in output

Kriging

# The following plot allows us to assess the fit
plot(var.smpl, dat.fit, xlim=c(0,130000))

Gráfico 4. Semivariograma.

r.m

Mapa.

# Plot the map
tm_shape(r.m) + 
  tm_raster(n=10, palette="RdBu", auto.palette.mapping=FALSE, 
            title="Kriging Universal\nPrecipitación prevista \n(en mm)") +
  tm_shape(P) + tm_dots(size=0.2) +
  tm_legend(legend.outside=TRUE)
The argument auto.palette.mapping is deprecated. Please use midpoint for numeric data and stretch.palette for categorical data to control the palette mapping.CRS object has comment, which is lost in output

Figura 15. Mapa de kriging de precipitación.

library(leaflet)
library(RColorBrewer)
pal <- colorNumeric(c("red", "orange", "yellow", "blue", "darkblue"), values(precip.mask),
  na.color = "transparent")

leaflet() %>% addTiles() %>%
  addRasterImage(r.m, colors = pal, opacity = 0.6) %>%
  addLegend(pal = pal, values = values(r.m),
    title = "Kriging Precipitación Interpolada en Caquetá\n desde 18/05/2020 hasta 23/05/2020 [mm]")
Some values were outside the color scale and will be treated as NASome values were outside the color scale and will be treated as NA

Figura 16. Mapa interactivo Kriging de la precipitación interpolada. Generar los mapas de varianza e intervalo de confianza.

r   <- raster(dat.krg, layer="var1.var")
r.m <- raster::mask(r, caqueta2)

tm_shape(r.m) + 
  tm_raster(n=5, palette ="Reds",
            title="Interpolación de Kriging\nMapa de variación \n(en squared mm)") +tm_shape(P) + tm_dots(size=0.2) +
  tm_legend(legend.outside=TRUE)
CRS object has comment, which is lost in output

Figura 17. Mapa de variación en Kriging.

r   <- sqrt(raster(dat.krg, layer="var1.var")) * 1.96
There were 23 warnings (use warnings() to see them)
r.m <- raster::mask(r, caqueta2)

tm_shape(r.m) + 
  tm_raster(n=5, palette ="Reds",
            title="Interpolación Kriging\n Mapa de intervalo de confianza al 95% \n(en mm)") +tm_shape(P) + tm_dots(size=0.2) +
  tm_legend(legend.outside=TRUE)
CRS object has comment, which is lost in output

Figura 18. Mapa de intervalo de confianza de kriging.

sessionInfo()

Análisis de resultados

En base a los resultados anteriores, se puede ver que los métodos para la interpolación de datos presentan diferencias y unos son mejores que otros dependiendo del tipo de variable que se quiera estudiar. También presentan diferencias en cuanto a la manera de calcularlos, de tomar las medidas, creación de las estructuras y resolución de los mapas.

En las figuras 7 y 8 se puede apreciar una vista del departamento de caquetá, se puede ver una capa ráster compuesta de varias celdas de diferentes colores, donde cada color representa la cantidad de precipitación en milímetros (mm) que tuvo el departamento, donde los municipios de Cartagena del Chaira, San José del Fragua, Valparaíso y Milan fueron los que presentaron mayor precipitación, a comparación de los municipios de El Paujil, Florencia y San Vicente del Caguán, donde sus niveles de precipitación fueron menores. En ambos mapas se pueden ver una serie de celdas de forma cuadrada cuya resolución es de 0.2 * 0.2. Algunas diferencias entre ambos mapas es que el de la figura 7 tiene una vista del departamento son los límites de cada uno de sus municipios, no es interactivo y su color de celdas varía de rojo a verde; mientras que el mapa de la figura 8 es interactivo (OpenStreetMap) y más detallado, permite identificar el departamento desde una vista del mapa de Colombia, en el que se pueden apreciar con cuáles departamentos limita, una vista simple de las zonas en las que hay presencia de vegetación, maneja una paleta de color que va del rojo al azul y no muestra los límites entre sus municipios. La resolución de las celdas que presentan, no es muy precisa, sin embargo se trabajó con esta resolución debido a que más adelante se requerirá, para la vista de los mapas, puntos no tan concentrados. Requirió hacer varias operaciones para volver los datos espaciales. En la figura 9 se pueden apreciar las celdas de la capa raster con un punto color morado en el centro de cada una, estos serán los puntos para hacer la interpolación.

Los datos también se trabajaron por medio del formato Geojson, el cual está diseñado para generar, visualizar y editar datos geográficos (geodatos)GeoJson.io es una herramienta pública y virtual que permite importar y exportar geodatos, y una de sus funciones es reproyectar capas de geodatos (Viloria, s.f). Los puntos fueron pasados a polígonos con el fin de convertir la característica precipitación en un marco de datos espacial. Vale aclarar que los valores de los datos de precipitación presentaron muchas cifras decimales, lo que dificulta la visualización de los puntos en el mapa, para ello fue necesario redondear las cifras para que apareciera solo un decimal.

La figura 9 representa el mapa de Caquetá con intervalos de precipitación de 10 mm. Cada punto representa el nivel de precipitación muestreada en cada uno de los puntos, variando de blanco claro a oscuro, donde a mayor nivel de precipitación, la tonalidad azul de cada punto se va tornando más oscura. Los polígonos de Thiessen se pueden apreciar en la figura 11 polígonos cuadrados, esto debido a que la posición de sus puntos tiene la misma distancia en el eje X y Y. Los polígonos formados en este mapa no cumplen el propósito de este este método ya que los polígonos están distribuidos de forma regular, entonces no proporciona una información clara respecto de la lluvia en el departamento. Algo que se puede deducir del mapa es que este departamento presenta precipitaciones que cubren toda la zona, esto en concordancia con los mapas anteriores.

La interpolación de distancia inversa (IDW) se puede apreciar en la figura 12, donde se ven celdas ráster que están sobrepuestas en los puntos de muestreo, sin embargo no se ve la presencia de los valores (expresados en números) sobre los puntos. Presenta una paleta de colores que varía entre el rojo y el azul, donde los valores más cercanos, están más relacionados con la variable, que es la precipitación, es decir que los puntos más cercanos comparten características similares a diferencia de los puntos lejanos. Lo anterior se puede ver reflejado en el agrupamiento de puntos por colores que varían entre tonalidades azules y rojas, unas más claras claras y otras oscuras, cada agrupamiento significa que los puntos que se encuentran dentro del mismo comparten características similares. Por ejemplo se pueden ver tonalidades azules oscuras en la zona a la que pertenecen los municipios de Cartagena del Chaira, Solano y Milán, presentando mayores precipitaciones en esta zona, el los puntos que se encuentran agrupados en el color azul oscuro, tienen en común que hay precipitaciones fuerte allí, y a medida que se van alejando, los puntos se van agrupando en coloraciones más claras, lo que significa que comparten la característica de que hay precipitaciones, pero más leves. Los agrupamientos de color rojizo, significan que los puntos contenidos ahí, comparten la característica de una baja precipitación, perteneciendo a los municipios de Florencia, Belén de los Andaquíes, una parte de San Vicente del Caguán y el sur del municipio de Solano. La figura 13 presenta una visión más detallada del mapa, con las características de la figura 8, pero esta vez representando el método IDW.

El método IDW permite calcular el valor de error cuadrático medio (RMSE) de los datos interpolados. El gráfico 3, muestra cuál es el valor de precipitación observada en el eje X y cuál fue la prevista en el eje Y. Si los datos coincidieran perfectamente, estarían alineados con la línea de color negro, que es de 45°; sin embargo los resultados muestran que los puntos están sobre la línea roja, la cual puede variar si el exponente fuera distinto a dos (2.2, 2,4), pero no muy lejano a dos. Se trabajó con una potencia IDW de 2, que es la que generalmente se usa.

Al calcular el error medio cuadrático de los datos, arrojó un resultado de 6.650, y proviene de la fórmula:

(sum((IDW.out - P$Lluvia)^2) / length(P))

Sum: Sumatoria, IDW.out: Longitud del vector, P$Lluvia: valor de precipitación en el punto length(P): Longitud.

La validación cruzada puede determinar cuál es la incertidumbre de los resultados, donde se creó un mapa de intervalo de confianza de 95% del modelo de interpolación, que corresponde a la figura 14. Esta figura permite apreciar que en la mayoría de los puntos interpolados del departamento de Caquetá, el rango de incertidumbre es muy bajo, tal como lo indica el color. Entonces, se puede decir en base al mapa, que los intervalos de error más alto se presentan en una pequeña área del municipio de Solano.

En el método de Kriging, se calculó un semivariograma lineal porque se usa la fórmula de primer orden polinomial, siendo precip=línea+aX+bY. Para ajustar los valores se realiza el semivariograma, dando como resultado un gráfico donde los valores de semivarianza promediados, los cuales están ubicados en el eje Y, y la distancia o intervalo está ubicada en el eje X, además tiene un nugget igual a cero. Se pueden ver algunos puntos sobre una recta, habiendo una correlación espacial entre dichos puntos, donde están más relacionados entre sí los puntos que se encuentran uno más cerca de otro. Las diferencias no presenta variaciones altas, entonces ese modelo de variograma se ajusta con los puntos de muestreo.

La figura 15 presenta un mapa con mejor resolución, una paleta de color que varía entre el rojo y el azul, reflejando zonas con menor precipitación, y zonas con mayor precipitación respectivamente. Los datos están agrupados por colores según la similitud de precipitación que estos presenten, como se había mencionado en anteriormente, las agrupaciones en tonalidades de color azul son similares en cuanto al nivel de precipitación en el departamento, y las zonas con coloraciones rojizas son aquellas en las que los puntos son parecidos en cuanto a su nivel de precipitación, presentando intervalos menores que los de la zona azul.

La figura 16 muestra un mapa interactivo de la precipitación interpolada por el método de Kriging, presentando representando la información de la figura 15, pero en esta ocasión es el mapa con mejor resolución en comparación de todos los anteriores, esto se dice porque no se ven las celdas tan marcadas, presenta una coloración que varía de una forma adecuada y coherente.

La figura 17 permite observar el intervalo de variación respecto a los datos obtenidos, donde se puede ver que este intervalo presenta valores mayores en los bordes del departamento, permitiendo deducir que sus valores tienen cierto grado de incertidumbre, mientras que los datos cubren el interior del departamento presentan un intervalo de variación entre 10 y 20 mm, pero menor a comparación de los límites.

La figura 18 representa el intervalo de confianza de los datos de precipitación a través de la interpolación por el método de kriging. Se puede apreciar que la mayoría de sus resultados presentan coloraciones correspondientes a intervalos entre 6 y 12 mm, donde el nivel de confianza es favorable.

Conclusiones

La interpolación es una herramienta de vital importancia para muchas carreras debido a que permite realizar estudios de diferentes variales como la precipitación, que fue la que se trabajó en el informe, sin tener que ir directamente a la zona que se quiere estudiar, representa también importancia en cuanto a costos ya que se pueden obtener y representar datos de diferentes variables partiendo de un número limitado de puntos que termiten crear estructuras ráster.

Existen varios métodos para poder realizar interpolación, presentando diferencias como la manera de calcularlos, las estructuras que forman, las variables a las que cada uno se acomoda mejor para estudiar, la manera de interpretar y leer los datos, algunos proporcionan información adicional como la incertidumbre de los datos.

La herramienta RStudio ofrece a sus usuarios una amplia gama de librerías con diferentes funciones, brindando diferentes alternativas para representar, en base a datos descargados de plataformas confiables, tablas, gráficos, realizar mapas que representen gráficamente valores de los gráficos, tales como mapas temáticos, interactivos, entre otros, permitiendo hacer análisis de todo tipo, por ejemplo análisis de las necesidades básicas insatisfechas de una región, nivel de escolaridad, nivel de natalidad, niveles de producción y rendimiento de determinados cultivos, entre otros.

Dentro de las herramientas de R se encuentra la interpolación de datos, permitiendo realizar análisis de precipitación y así poder realizar, en base a literatura y estadísticas, estimaciones sobre impactos de sequías o inundaciones.

Bibliografía

Bravo, L. s.f. Diagrama de Voronoi. Recuperado de: http://matematicas.unex.es/~trinidad/mui/voronoi.pdf;consulta: Junio de 2020.

Funk, C. P, Peterson. M, Landsfeld. D, Pedreros. J, Verdin. S, Shukla. G, Husak.J, Rowland. L, Harrison. A, Hoell y J Michaelsen. 2015. The climate hazards infrared precipitation with stations—a new environmental record for monitoring extremes. Recuperado de: https://www.nature.com/articles/sdata201566; consulta: Junio de 2020.

Gimond, M. 2019. Intro to GIS and Spatial Analysis. Recuperado de: https://mgimond.github.io/Spatial/interpolation-in-r.htm; consulta: Junio de 2020.

GISGeography. s.f.Inverse Distance Weighting (IDW) Interpolation. Recuperado de: https://gisgeography.com/inverse-distance-weighting-idw-interpolation/; consulta: Junio de 2020.

Grupo Kraken IDE. 2019. Global Precipitation Data (CHIRPS). Recuperado de: http://ide.unex.es/conocimiento/index.php?/article/AA-31745/0/Datos-globales-de-precipitacin-CHIRPS.htm; Consulta: Junio de 2020

Ministerio de Agricultura. 2014. Principales Cultivos por Área sembrada en el año 2014. Recuperado de: http://www.agronet.gov.co/Documents/Caquet%C3%A1.pdf; consulta Junio de 2020.

Viloria, J. s.f.GeoJson.io, herramienta para generar geodatos.Recuperado de: https://geoinnova.org/blog-territorio/geojson-io-herramienta-para-generar-geodatos/; consulta: Junio de 2020.

LS0tDQp0aXRsZTogIkludGVycG9sYWNpw7NuIGRlIGRhdG9zIGRlbCBkZXBhcnRhbWVudG8gZGUgQ2FxdWV0w6EiDQphdXRob3I6ICJTYW5kcmEgS2F0dGVyeW5lIFJvZHLDrWd1ZXogSHVydGFkbyINCmRhdGU6ICJKdW5pbyBkZSAyMDIwIg0Kb3V0cHV0OiBodG1sX25vdGVib29rDQotLS0NCmBgYHtyIGVjaG8gPSBGQUxTRX0NCmxpYnJhcnkoa25pdHIpDQpsaWJyYXJ5KHJnZGFsKQ0KbGlicmFyeShyYXN0ZXIpDQpsaWJyYXJ5KHNmKQ0KbGlicmFyeShyZWFkeGwpDQpsaWJyYXJ5KHJnZW9zKQ0KbGlicmFyeShvc21kYXRhKQ0KbGlicmFyeShjYXJ0b2dyYXBoeSkNCmBgYA0KDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpsaWJyYXJ5KHRpZHl2ZXJzZSkNCmxpYnJhcnkodG1hcCkNCmxpYnJhcnkoZ3N0YXQpDQpsaWJyYXJ5KHNwKQ0KbGlicmFyeShyYXN0ZXIpDQpsaWJyYXJ5KGdncmVwZWwpDQpsaWJyYXJ5KGNvd3Bsb3QpDQpsaWJyYXJ5KEdTT0RSKQ0KbGlicmFyeShtYXB0b29scykNCmxpYnJhcnkobHdnZW9tKQ0KYGBgDQojIyBJbnRyb2R1Y2Npw7NuIA0KRW4gZWwgcHJlc2VudGUgdHJhYmFqbyBzZSBhYm9yZGFyw6EgZWwgdGVtYSBkZSBpbnRlcnBvbGFjacOzbiBkZSBkYXRvcywgZW4gZXN0YSBvY2FzacOzbiBzZSByZWFsaXphcsOhbiBsb3MgbcOpdG9kb3MgeSBhbsOhbGlzaXMgY29ycmVzcG9uZGllbnRlcyBwYXJhIHVuIGNvbmp1bnRvIGRlIGRhdG9zIGRlIHByZWNpcGl0YWNpw7NuIHF1ZSBjdWJyZW4gZWwgZGVwYXJ0YW1lbnRvIGRlIENhcXVldMOhLiBTZSBoYXLDoSBsYSByZWNvcGlsYWNpw7NuIGRlIHZhcmlvcyBjdWFkZXJub3MgcmVhbGl6YWRvcyBkdXJhbnRlIGVsIHByaW1lciBzZW1lc3RyZSBkZSAyMDIwLCBjdXlhcyBncsOhZmljYXMgc2Vyw6FuIHVuIGFwb3lvIHBhcmEgZGVzY3JpYmlyIGxhIHpvbmEgZGUgZXN0dWRpbywgcXVlIGVzIGVsIGRlcGFydGFtZW50byBkZSBDYXF1ZXTDoS4gU2UgaGl6byB1c28gZGUgbGEgaGVycmFtaWVudGEgUUdJUywgbGEgY3VhbCBzZSB0cmFiYWrDsyBlbiBhbGd1bmFzIGRlIGxhcyBjbGFzZXMgZGVsIGN1cnNvIGRlIGdlb23DoXRpY2EgYsOhc2ljYSwgYWRlbcOhcyBkZSBjb25zdWx0YXIgZGF0b3MgZW4gZWwgREFORSBvIENISVJQUy4gICANCg0KTGEgaW50ZXJwb2xhY2nDs24gZGUgZGF0b3MgZXMgbXV5IGltcG9ydGFudGUgcGFyYSBkaXN0aW50YXMgY2FycmVyYXMsIGVudHJlIGVsbGFzIGxhIEluZ2VuaWVyw61hIEFncm9uw7NtaWNhLCBkb25kZSBlbCBjb25vY2ltaWVudG8gZGUgaGVycmFtaWVudGFzIHkgbcOpdG9kb3MgcGVybWl0ZSByZWFsaXphciBpbXBvcnRhbnRlcyBlc3R1ZGlvcyBkZSBkaXN0aW50YXMgdmFyaWFibGVzIGNvbW8gbGEgZGVncmFkYWNpw7NuIGRlIHN1ZWxvcyBlbiB1bmEgem9uYSBkZXRlcm1pbmFkYSwgw61uZGljZSBkZSB2ZWdldGFjacOzbiwgaHVtZWRhZCBkZWwgc3VlbG8sIHByZWNpcGl0YWNpw7NuLCBlbnRyZSBvdHJhcy4gRXN0b3MgZGF0b3MgcGVybWl0ZW4gbm8gc8OzbG8gZW50ZW5kZXIgZW4gY29udGV4dG8gZGVsIG1vbWVudG8sIHRhbWJpw6luIHByZWRlY2lyIHF1w6kgcHVlZGUgb2N1cnJpciBlbiB1biBmdXR1cm8geSwgZGUgc2VyIHBvc2libGUsIHRvbWFyIG1lZGlkYXMgYWwgcmVzcGVjdG8uIEVzdGUgdHJhYmFqbyBmdWUgZWxhYm9yYWRvIHBhcmEgbGEgbWF0ZXJpYSBkZSBnZW9tw6F0aWNhIGLDoXNpY2EsIGN1eW8gb2JqZXRpdm8gZXMgZW50ZW5kZXIgZGlzdGludGFzIGZ1bmNpb25hbGlkYWRlcyBnZW9lc3BhY2lhbGVzLCBnZW5lcmFkYXMgcG9yIGVsIGFtYmllbnRlLCBlbiBlbCBwcm9ncmFtYSBkZSBSU3R1ZGlvLiBTZSBoYWJsYXLDoSBzb2JyZSBxdcOpIGVzIGxhIGludGVycG9sYWNpw7NuLCBhbGd1bm9zIGNvbmNlcHRvcyBiw6FzaWNvcyBkZSBsYSBtaXNtYSwgZXhwbGljYWNpw7NuIGRlIHRyZXMgdMOpY25pY2FzIGRpZmVyZW50ZXMgcGFyYSBpbnRlcnBvbGFjacOzbiBkZSBkYXRvcyBkZSBwcmVjaXBpdGFjacOzbiB5IHN1IHJlc3BlY3Rpdm8gYW7DoWxpc2lzLCB5IGFsZ3VuYXMgY29uY2x1c2lvbmVzLiAgICAgDQoNCiMjIERlc2NyaXBjacOzbiBkZSBsYSB6b25hDQpFbCBkZXBhcnRhbWVudG8gZGUgQ2FxdWV0w6EgZnVlIGZ1bmRhZG8gZWwgMDIgZGUgTWF5byBkZSAxODQ1LCBzZSBlbmN1ZW50cmEgbG9jYWxpemFkbyBhbCBTdXIgZGUgQ29sb21iaWEsIHRpZW5lIHVuYSBleHRlbnNpw7NuIGRlIDg4Ljk2NSBrbTIgYXByb3hpbWFkYW1lbnRlIHkganVlZ2EgdW4gcGFwZWwgaW1wb3J0YW50ZSBlbiBsYSBiaW9kaXZlcnNpZGFkIGRlYmlkbyBhIHF1ZSB1biBwb3JjZW50YWplIGltcG9ydGFudGUgZGUgc3UgdGVycml0b3JpbyBwZXJ0ZW5lY2UgYWwgc2lzdGVtYSBBbWF6w7NuaWNvLCBwaWVkZW1vbnRlIEFtYXrDs25pY28sIHNlIGVuY3VlbnRyYW4gYXNlbnRhbWllbnRvcyBodW1hbm9zLCB5IHBvciBlbmRlIGxhIGRpbsOhbWljYSBzb2Npb3BvbMOtdGljYSB5IGVjb27Ds21pY2EgKEdvYmVybmFjacOzbiBkZSBDYXF1ZXTDoSwgcy5mKS4NCg0KIyMjIyBVYmljYWNpw7NuDQpTZSBlbmN1ZW50cmEgdWJpY2FkbyBoYWNpYSBlbCBzdXIgZGVsIHRlcnJpdG9yaW8gY29sb21iaWFubywgU3UgY2FwaXRhbCBlcyBGbG9yZW5jaWEgeSBsaW1pdGEgcG9yIGVsIG5vcnRlIGNvbiBlbCBkZXBhcnRhbWVudG8gZGVsIEh1aWxhIHkgTWV0YSwgcG9yIGVsIG9yaWVudGUgY29uIFZhdXDDqXMgeSBHdWF2aWFyZSwgcG9yIGVsIHN1ciBjb24gIEFtYXpvbmFzIHkgUHV0dW1heW8sIHkgcG9yIGVsIE9jY2lkZW50ZSBjb24gQ2F1Y2EgeSBIdWlsYSAoSUdBQywgMjAwOCkuIEVzdMOhIGRpdmlkaWRvIGVuIGRpZXNpc2VpcyBtdW5pY2lwaW9zLCBkb25kZSBzZSBlbmN1ZW50cmFuIG11Y2hvcyBjYXNlcsOtb3MgeSBzaXRpb3MgcG9ibGFkb3MuDQpgYGB7ciBlY2hvID0gRkFMU0V9DQp7b3BhciAgPSIxMDAlIn0NCmxpYnJhcnkoZ2dwbG90MikNCmxpYnJhcnkoa25pdHIpDQppbmNsdWRlX2dyYXBoaWNzKCJEOi9JbWFnZW5lcy9DT0xjYS5wbmciKQ0KYGBgDQpGaWd1cmEgMS4gVWJpY2FjacOzbiBkZWwgZGVwYXJ0YW1lbnRvIGRlIENhcXVldMOhIGVuIENvbG9tYmlhLiBNYXBhIHJlYWxpemFkbyBlbiBRR0lTIGNvbiBkYXRvcyBkZSBkaXZhLUdJUy4gQXV0b3LDrWEgcHJvcGlhLiBTZSBwdWVkZSBhcHJlY2lhciBsYSB1YmljYWNpw7NuIGRlbCBkZXBhcnRhbWVudG8gZGUgQ2FxdWV0w6EsIGVuIGNvbG9yIGFtYXJpbG8sIGFsIHN1ciBkZWwgcGHDrXMuIA0KIVtEZXBhcnRhbWVudG9zIGRlbCBkZXBhcnRhbWVudG8gZGUgQ2FxdWV0w6FdKEQ6L0ltYWdlbmVzL011bmljaXBpb3NDYXEucG5nKQ0KRmlndXJhIDIuIFViaWNhY2nDs24gZGVsIGRlcGFydGFtZW50byBkZSBDYXF1ZXTDoSBlbiBDb2xvbWJpYS4gTWFwYSByZWFsaXphZG8gZW4gUUdJUyBjb24gZGF0b3MgZGUgZGl2YS1HSVMuIEF1dG9yw61hIHByb3BpYS4gU2UgcHVlZGVuIGFwcmVjaWFyIGxvcyBkaWVzaXNlaXMgbXVuaWNpcGlvcyBxdWUgY29uZm9ybWFuIGVsIGRlcGFydGFtZW50byBkZSBDYXF1ZXTDoTogQWxiYW5pYSwgQmVsw6luIGRlIGxvcyBBbmRhcXXDrWVzLCBDYXJ0YWdlbmEgZGUgQ2hhaXJhLCBDdXJpbGxvLCBFbCBEb25jZWxsbywgRWwgUGF1amlsLCBGbG9yZW5jaWEsIE1pbMOhbiwgTW9udGHDsWl0YSwgTW9yZWxpYSwgUHVlcnRvIFJpY28sIFNhbiBKb3PDqSBkZWwgRnJhZ3VhLCBTYW4gVmljZW50ZSBkZWwgQ2FndcOhbiwgU29sYW5vLCBTb2xpdGEgeSBWYWxwYXJhaXNvLiAgDQoNCiMjIyMgQ2xpbWEgeSBwb2JsYWNpw7NuDQoNCkxhIG1heW9yw61hIGRlbCBkZXBhcnRhbWVudG8gcHJlc2VudGEgdW4gY2xpbWEgY8OhbGlkbyBxdWUgb3NjaWxhIGVudHJlIGxvcyAyN8KwQyB5IGxvcyAyOcKwQywgYWx0YSBwbHV2aW9zaWRhZCwgZG9uZGUgZWwgdmVyYW5vIGdlbmVyYWxtZW50ZSBzZSBwcmVzZW50YSBlbiBsb3MgbWVzZXMgZGUgRGljaWVtYnJlIGEgRmVicmVybyB5IGxvcyBtZXNlcyByZXN0YW50ZXMgc29uIGRlIGludmllcm5vIChMw7NwZXosIDIwMDYpLiAgDQoNCiMjIyMgTmVjZXNpZGFkZXMgQsOhc2ljYXMgSW5zYXRpc2ZlY2hhcw0KTGFzIE5lY2VzaWRhZGVzIELDoXNpY2FzIEluc2F0aXNmZWNoYXMgKE5CSSkgcXVlIHByZXNlbnRhbiBsb3MgaGFiaXRhbnRlcyBkZSBjYWRhIG11bmljaXBpbyB5IHByb2R1Y2Npw7NuIGVuIGVsIGHDsW8gMjAxOCBkZSBhbGd1bm9zIGN1bHRpdm9zIGVuIENhcXVldMOhLiANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCm5iaSA8LSByZWFkX2V4Y2VsKCJEOi9Eb2N1bWVudG9zL0dlb23DoXRpY2EvTkJJX0NhcXVldGEueGxzeCIpDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCm5iaSAlPiUgDQogIGFycmFuZ2UoZGVzYyhOQkkpKSAgLT4gZGVzY19uYmkNCmRlc2NfbmJpDQpgYGANClRhYmxhIDEuIERhdG9zIGRlIE5CSSBxdWUgcHJlc2VudGFuIGxvcyBtdW5pY2lwaW9zIGRlIENhcXVldGEuIExvcyBtdW5pY2lwaW9zIHNlIGVuY3VlbnRyYW4gZW4gb3JkZW4gZGVzY2VuZGVudGUgYWNvcmRlIGNvbiBzdSByZXNwZWN0aXZvIHBvcmNlbnRhamUgZGUgTkJJLCBkb25kZSBlbCBtdW5pY2lwaW8gZGUgTWlsw6FuIGVzIGVsIHF1ZSBtYXlvciBwb3JjZW50YWplIGRlIE5CSSBwcmVzZW50YSwgZG9uZGUgYXByb3hpbWFkYW1lbnRlIGVsIDQ3JSBkZSBsYSBwb2JsYWNpw7NuIHRpZW5lIE5lY2VzaWRhZGVzIEJhc2ljYXMgSW5zdGF0aXNmZWNoYXMsIG1pZW50cmFzIHF1ZSBlbCBtdW5pY2lwaW8gY29uIG1lbm9yIHBvcmNlbnRhamUgZGUgTkJJIGVzIEZsb3JlbmNpYSwgZG9uZGUgY2VyY2EgZGVsIDE0LjUlIGRlIHN1IHBvYmxhY2nDs24gcHJlc2VudGEgTmVjZXNpZGFkZXMgQmFzaWNhcyBJbnN0YWZpc2ZlY2hhcy4gRnVlbnRlOiBBdXRvcmlhIHByb3BpYSBjb24gZGF0b3MgcmVjb3BpbGFkb3MgcG9yIGVsIERBTkUuDQoNCmBgYHtyIGVjaG8gPSBGQUxTRX0NCm11bmljIDwtIHN0X3JlYWQoIkQ6L0RvY3VtZW50b3MvR2VvbcOhdGljYS9BRE1JTklTVFJBVElWTzEvTUdOX01QSU9fUE9MSVRJQ08uc2hwIikNCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KbmJpX211bmljID0gbGVmdF9qb2luKG11bmljLCBuYmksIGJ5PWMoIk1QSU9fQ0NER08iPSJDT0RJR08iKSkNCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KbmJpX211bmljICU+JQ0KICBkcGx5cjo6c2VsZWN0KE1VTklDSVBJTywgTVBJT19DQ0RHTywgTkJJKSAgLT4gIGNoZWNrX25iaV9tdW5pYw0KaGVhZChjaGVja19uYmlfbXVuaWMpDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCm5iaV9tdW5pY19uZXcgPC0gc3RfdHJhbnNmb3JtKG5iaV9tdW5pYywgY3JzID0gMzExNikNCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KbmJpX211bmljXzIgPC0gZHBseXI6Om11dGF0ZShuYmlfbXVuaWNfbmV3LCBQb2JyZXphID0gaWZlbHNlKE1JU0VSSUEgPiAyMCwgIkV4dHJlbWEiLCANCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmZWxzZShIQUNJTkFNSUVOVE8gPiA1LCAiQWx0YSIsICJJbnRlcm1lZGlhIikpKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpoZWFkKG5iaV9tdW5pY18yKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQptdW4ub3NtIDwtIGdldFRpbGVzKA0KeCA9IG5iaV9tdW5pY19uZXcsIA0KdHlwZSA9ICJPcGVuU3RyZWV0TWFwIiwgDQp6b29tID0gOCwNCmNhY2hlZGlyID0gVFJVRSwNCmNyb3AgPSBGQUxTRQ0KKQ0KYGBgDQoNCmBgYHtyfQ0Kb3BhciA8LSBwYXIobWFyID0gYygwLDAsMS4yLDApKQ0KcGFyKGJnPSJ3aGl0ZSIpDQpwbG90KHN0X2dlb21ldHJ5KG5iaV9tdW5pY18yKSwgY29sID0gIiNlNGU5ZGUiLCBib3JkZXIgPSAiZGFya3NlYWdyZWVuNCIsIA0KICAgICBiZyA9ICJncmV5ODUiLCBsd2QgPSAwLjUpDQpjaG9yb0xheWVyKA0KICB4ID0gbmJpX211bmljX25ldywgDQogIHZhciA9ICJOQkkiLA0KICBtZXRob2QgPSAiZ2VvbSIsDQogIG5jbGFzcz01LA0KICBjb2wgPSBjYXJ0by5wYWwocGFsMSA9ICJvcmFuZ2UucGFsIiwgbjEgPSA1KSwNCiAgYm9yZGVyID0gIkJsYWNrIiwgDQogIGx3ZCA9IDAuMiwNCiAgbGVnZW5kLnBvcyA9ICJ0b3BsZWZ0IiwgDQogIGxlZ2VuZC50aXRsZS50eHQgPSAiTkJJIiwNCiAgYWRkID0gVFJVRQ0KKSANCg0KbGFiZWxMYXllcigNCiAgeCA9IG5iaV9tdW5pY18yLCANCiAgdHh0ID0gIk1VTklDSVBJTyIsIA0KICBjb2w9ICJ3aGl0ZSIsIA0KICBjZXggPSAwLjQsIA0KICBmb250ID0gNCwNCiAgaGFsbyA9IFRSVUUsIA0KICBiZyA9ICJibGFjayIsIA0KICByID0gMC4xLCANCiAgb3ZlcmxhcCA9IEZBTFNFLCANCiAgc2hvdy5saW5lcyA9IEZBTFNFDQopDQpsYXlvdXRMYXllcigNCiAgdGl0bGUgPSAiTXVuaWNpcGlvcyBkZWwgZGVwYXJ0YW1lbnRvIGRlIENhcXVldGEiLCANCiAgc291cmNlcyA9ICJGdWVudGU6IERBTkUsIDIwMTgiLCAgDQogIGF1dGhvciA9ICJTYW5kcmEgS2F0dGVyeW5lIFJvZHLDrWd1ZXogSHVydGFkbyIsIA0KICBmcmFtZSA9IFRSVUUsDQogIG5vcnRoID0gVFJVRSwgDQogIHRhYnRpdGxlID0gVFJVRSwgDQogIHRoZW1lID0gInRhdXBlLnBhbCINCikgDQpgYGANCkZpZ3VyYSAzLiBNYXBhIGRlbCBwb3JjZW50YWplIGRlIE5CSSBkZSBsb3MgbXVuaWNpcGlvcyBkZSBDYXF1ZXTDoS4gRWwgbWFwYSByZWZsZWphIGxvcyBkYXRvcyBkZSBsYSB0YWJsYSAxLCBkb25kZSBjYWRhIG11bmljaXBpbyBsbGV2YSBsYSBldGlxdWV0YSBkZSBzdSBub21icmUgY29ycmVzcG9uZGllbnRlLCBjdWFuZG8gZWwgY29sb3Igc2UgdG9ybmEgbcOhcyBvc2N1cm8sIG1heW9yIHNlcsOhIGVsIHBvcmNlbnRhZGUgZGUgTkJJIHF1ZSBwcmVzZW50YSBlc2EgcG9ibGFjacOzbi4gRnVlbnRlOiBBdXRvcmlhIHByb3BpYSBjb24gZGF0b3MgcmVjb3BpbGFkb3MgcG9yIGVsIERBTkUuDQoNCiMjIyBFY29ub23DrWENCg0KRGVudHJvIGRlIGxhcyBwcmluY2lwYWxlcyBhY3RpdmlkYWRlcyBlY29uw7NtaWNhcyBxdWUgc2UgZW5jdWVudHJhbiBlbiBlbCBkZXBhcnRhbWVudG8gc29icmVzYWxlIGxhIGdhbmFkZXLDrWEgeSBsYSBhZ3JpY3VsdHVyYSwgZW4gZXN0YSDDumx0aW1hIHNlIGVuY3VlbnRyYW4gY2VyZWFsZXMsIGZsb3JlcyB5IGZvbGxhamVzLCBmb3Jlc3RhbGVzLCBmcnV0YWxlcywgaG9ydGFsaXphcywgbGVndW1pbm9zYXMsIG9sZWFnaW5vc2FzLCBvdHJvcyBwZXJtYW5lbnRlcywgdHViw6lyY3Vsb3MgeSBwbMOhdGFub3MgKERBTkUsIDIwMTcpLiBTZSBkZWJlIHRlbmVyIGVuIGN1ZW50YSBxdWUsIHBlc2UgYSBxdWUgZW4gbGFzIHRhYmxhcyBubyBzZSBkYW4gdW5pZGFkZXMsIGxhcyBkZSDDoXJlYSBzb24gaGVjdMOhcmVhcyAoSGEpLCB5IGxhcyB1bmlkYWRlcyBkZSByZW5kaW1pZW50b3Mgc29uIHRvbmVsYWRhcy9IYS4gDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpkYXRvcyA8LSByZWFkX2NzdigiRDovRG9jdW1lbnRvcy9HZW9tw6F0aWNhL0VWQV9DYXF1ZXTDoTIuY3N2IikNCmBgYA0KDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpkYXRvcyAlPiUgDQogIGZpbHRlcihZRUFSPT0yMDE4KSAlPiUgDQogIGdyb3VwX2J5KEdSVVBPLCBNVU5JQ0lQSU8pICU+JQ0KICBzdW1tYXJpemUobWF4X2FyZWFfY29zZWNoYSA9IG1heChBcmVhX2Nvc2VjaGFkYSwgbmEucm0gPSBUUlVFKSkgJT4lDQogICAgc2xpY2Uod2hpY2gubWF4KG1heF9hcmVhX2Nvc2VjaGEpKSAtPiBhcmVhX2Nvc2VjaGFfbWF4DQoNCmFyZWFfY29zZWNoYV9tYXgNCmBgYA0KVGFibGEgMi4gTXVuaWNpcGlvcyBjb24gbWF5b3Igw6FyZWEgY29zZWNoYWRhIGVuIGVsIGHDsW8gMjAxOC4gU2UgcHVlZGUgYXByZWNpYXIgcXVlIGVsIG11bmljaXBpbyBTYW4gVmljZW50ZSBkZWwgQ2FndcOhbiBmdWUgZWwgZGUgbWF5b3Igw6FyZWEgc2VtYnJhZGEgZW4gZWwgZ3J1cG8gZGUgY2VyZWFsZXMsIHNlZ3VpZG8gZGUgQ2FydGFnZW5hIGRlbCBDaGFpcmEgcGFyYSBlbCBncnVwbyBkZSBUdWLDqXJjdWxvcyB5IHBsw6F0YW5vcywgeSBGbG9yZW5jaWEsIHBhcmEgZWwgZ3J1cG8gZGUgb3Ryb3MgcGVybWFuZW50ZXMuIEZ1ZW50ZTogQXV0b3JpYSBwcm9waWEgY29uIGRhdG9zIHJlY29waWxhZG9zIHBvciBlbCBEQU5FLg0KYGBge3IgZWNobyA9IEZBTFNFfQ0KZGF0b3MgJT4lIA0KICBmaWx0ZXIoTVVOSUNJUElPPT0iU0FOIFZJQ0VOVEUgREVMIENBR1VBTiIgJiBTVUJHUlVQTz09Ik1BSVoiKSAlPiUgDQogIGdyb3VwX2J5KFlFQVIsIENVTFRJVk8pIC0+ICBzYW52aWNlbnRlZGVsY2FndWFuX21haXoNCg0Kc2FudmljZW50ZWRlbGNhZ3Vhbl9tYWl6DQpgYGANClRhYmxhIDMuIFByb2R1Y2Npw7NuIGRlbCBjdWx0aXZvIGRlIE1haXosIHBlcnRlbmVjaWVudGUgYWwgZ3J1cG8gZGUgY2VyZWFsZXMsIHBhcmEgZWwgTXVuaWNpcGlvIGRlIFNhbiBWaWNlbnRlIGRlbCBDYWd1w6FuIChlbiB0b25lbGFkYXMpLg0KYGBge3IgZWNobyA9IEZBTFNFfQ0KZyA8LSBnZ3Bsb3QoYWVzKHg9WUVBUiwgeT1Qcm9kdWNjaW9uLzEwMDApLCBkYXRhID0gc2FudmljZW50ZWRlbGNhZ3Vhbl9tYWl6KSArIGdlb21fYmFyKHN0YXQ9J2lkZW50aXR5JykgKyBsYWJzKHk9J1Byb2R1Y2Npw7NuIGRlIE1haXogW1RvbiB4IDEwMDBdJykNCmBgYA0KDQpgYGB7cn0NCmcgKyBnZ3RpdGxlKCJFdm9sdWNpw7NuIGRlIGxhIHByb2R1Y2Npw7NuIGRlIE1haXogZW4gU2FuIFZpY2VudGUgZGVsIENhZ3XDoW4gZGUgMjAwNyBhIDIwMTgiKSArIGxhYnMoY2FwdGlvbj0gIkJhc2FkbyBlbiBsb3MgZGF0b3MgZGUgRU1BIChEQU5FLCAyMDE4KSIpDQpgYGANCkdyw6FmaWNvIDEuIEV2b2x1Y2nDs24gZGUgbGEgcHJvZHVjY2nDs24gZGUgTWFpeiBlbiBTYW4gVmljZW50ZSBkZWwgQ2FndcOhbiBkZSAyMDA3IGEgMjAxOC4gU2UgcHVlZGUgYXByZWNpYXIgcXVlIHBhcmEgZWwgYcOxbyAyMDE4IHNlIG9idHV2byB1bmEgcHJvZHVjY2nDs24gZGUgTWFpeiwgZW4gZWwgbXVuaWNpcGlvIGRlIFNhbiBWaWNlbnRlIGRlbCBDYWd1w6FuLCBkZSBjZXJjYSBkZSBjaW5jbyBtaWwgdG9uZWxhZGFzLiBMYSBwcm9kdWNjacOzbiBtw6F4aW1hIGRlIG1haXogZnVlIHBhcmEgZWwgYcOxbyBkZSAyMDEzLCBjb24gY2VyY2EgZGUgc2lldGUgbWlsIHRvbmVsYWRhcywgbG8gYW50ZXJpb3Igc2UgcHVlZGUgY29ycm9ib3JhciBjb24gbGEgaW5mb3JtYWNpw7NuIGRlIGxhIHRhYmxhIDMuDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpkYXRvcyAlPiUgDQogIGZpbHRlcihNVU5JQ0lQSU89PSJNSUxBTiIgJiBTVUJHUlVQTz09IlBMQVRBTk8iKSAlPiUgDQogIGdyb3VwX2J5KFlFQVIsIENVTFRJVk8pIC0+ICBtaWxhbl9wbGF0YW5vDQoNCm1pbGFuX3BsYXRhbm8NCmBgYA0KVGFibGEgNC4gUHJvZHVjY2nDs24gZGVsIGN1bHRpdm8gZGUgcGzDoXRhbm8sIHBlcnRlbmVjaWVudGUgYWwgZ3J1cG8gZGUgVHViw6lyY3Vsb3MgeSBwbMOhdGFub3MsIHBhcmEgZWwgTXVuaWNpcGlvIGRlIENhcnRhZ2VuYSBkZWwgQ2hhaXJhIChlbiB0b25lbGFkYXMpLg0KYGBge3IgZWNobyA9IEZBTFNFfQ0KZyA8LSBnZ3Bsb3QoYWVzKHg9WUVBUiwgeT1Qcm9kdWNjaW9uLzEwMDApLCBkYXRhID0gbWlsYW5fcGxhdGFubykgKyBnZW9tX2JhcihzdGF0PSdpZGVudGl0eScpICsgbGFicyh5PSdQcm9kdWNjacOzbiBkZSBQbMOhdGFubyBbVG9uIHggMTAwMF0nKQ0KYGBgDQoNCmBgYHtyfQ0KZyArIGdndGl0bGUoIkV2b2x1Y2nDs24gZGUgbGEgcHJvZHVjY2nDs24gZGUgUGzDoXRhbm8gZW4gTWlsw6FuIGRlIDIwMDcgYSAyMDE4IikgKyBsYWJzKGNhcHRpb249ICJCYXNhZG8gZW4gbG9zIGRhdG9zIGRlIEVNQSAoREFORSwgMjAxOCkiKQ0KYGBgDQpHcsOhZmljbyAyLiBFdm9sdWNpw7NuIGRlIGxhIHByb2R1Y2Npw7NuIGRlIFBsw6F0YW5vIGVuIE1pbMOhbiBkZSAyMDA3IGEgMjAxOC4gU2UgcHVlZGUgYXByZWNpYXIgcXVlIGxhIHByb2R1Y2Npw7NuIGRlIHBsw6F0YW5vIGVuIGVsIG11bmljaXBpbyBkZSBNaWzDoW4gaGEgaWRvIGF1bWVudGFuZG8gZW4gbG9zIMO6bHRpbW9zIGHDsW9zLCBkb25kZSBlbiBlc3RlIMO6bHRpbW8gYcOxbyB0dXZvIHVuYSBwcm9kdWNjacOzbiBkZSBjZXJjYSBkZSAyMiB0b25lbGFkYXMgZGUgcGzDoXRhbm8uDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpkYXRvcyAlPiUgDQogIGZpbHRlcihZRUFSPT0yMDE4KSAlPiUgDQogIGdyb3VwX2J5KEdSVVBPKSAlPiUNCiAgc3VtbWFyaXplKHN1bV9yZW5kaW1pZW50byA9IHN1bShSZW5kaW1pZW50bywgbmEucm0gPSBUUlVFKSkgJT4lDQogICAgIGFycmFuZ2UoZGVzYyhzdW1fcmVuZGltaWVudG8pKSAtPiB0b3RhbF9yZW5kaW1pZW50bw0KDQp0b3RhbF9yZW5kaW1pZW50bw0KYGBgDQpUYWJsYSA1LiBSZW5kaW1pZW50b3MgcGFyYSBjdWx0aXZvcyBkZWwgZGVwYXJ0YW1lbnRvIGRlIENhcXVldMOhIGVuIDIwMTguIExhIHNpZ3VpZW50ZSB0YWJsYSBtdWVzdHJhIGxvcyBncnVwb3MgZGUgY3VsdGl2byBjb24gZWwgdG90YWwgZGUgcmVuZGltaWVudG9zIChUb25lbGFkYS9oYSkgZGUgbWFuZXJhIGRlc2NlbmRlbnRlLCBkb25kZSBsb3MgZnJ1dGFsZXMsIHR1YsOpcmN1bG9zIHkgcGzDoXRhbm9zLCB5IGhvcnRhbGl6YXMgb2N1w6FuIGxvcyBwcmltZXJvcyBsdWdhcmVzLg0KYGBge3IgZWNobyA9IEZBTFNFfQ0KZyA8LSBnZ3Bsb3QoYWVzKHg9R1JVUE8sIHk9c3VtX3JlbmRpbWllbnRvKSwgZGF0YSA9IHRvdGFsX3JlbmRpbWllbnRvKSArIGdlb21fYmFyKHN0YXQ9J2lkZW50aXR5JykgKyBsYWJzKHk9J1JlbmRpbWllbnRvcyBbVG9uL0hhXScpDQpgYGANCmBgYHtyfQ0KZysgZ2d0aXRsZSgiUmVuZGltaWVudG8gcG9yIGdydXBvcyBkZSBjdWx0aXZvcyBlbiBDYXF1ZXTDoSBwYXJhIDIwMTgiKSArIHRoZW1lKHBsb3QudGl0bGUgPSBlbGVtZW50X3RleHQoaGp1c3QgPSAwLjUpKSArDQogICBsYWJzKGNhcHRpb249ICJCYXNhZG8gZW4gbG9zIGRhdG9zIGRlIEVNQSAoREFORSwgMjAxOCkiKQ0KDQpgYGANCkdyw6FmaWNvIDMuIFJlbmRpbWllbnRvcyBwb3IgZ3J1cG9zIGRlIGN1bHRpdm9zIGVuIENhcXVldMOhIHBhcmEgZWwgYcOxbyAyMDE4LiBTZSBwdWVkZSBhcHJlY2lhciBxdWUgbG9zIGdydXBvcyBkZSBjdWx0aXZvcyBxdWUgcHJlc2VudGFyb24gbWF5b3JlcyByZW5kaW1pZW50b3MgcGFyYSBlbCBhw7FvIDIwMTggZnVlcm9uIGxvcyBmcnV0YWxlcywgdHViw6lyY3Vsb3MgeSBwbMOhdGFub3MsIGhvcnRhbGl6YXMgeSBvdHJvcyBwZXJtYW5lbnRlcy4gDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpkYXRvcyAlPiUgDQogIGZpbHRlcihZRUFSPT0yMDE4ICYgR1JVUE89PSJGUlVUQUxFUyIpICU+JSANCiAgZ3JvdXBfYnkoQ1VMVElWTywgTVVOSUNJUElPKSAlPiUNCiAgc3VtbWFyaXplKFJlbmRpbWllbnRvID0gbWF4KFJlbmRpbWllbnRvLCBuYS5ybSA9IFRSVUUpKSAlPiUNCiAgICBzbGljZSh3aGljaC5tYXgoUmVuZGltaWVudG8pKSAtPiBSZW5kaW1pZW50bw0KDQpSZW5kaW1pZW50bw0KYGBgDQpUYWJsYSA2LiBNdW5pY2lwaW9zIGNvbiBtYXlvcmVzIHJlbmRpbWllbnRvcyBlbiBGcnV0YWxlcy4gU2UgcHVlZGVuIGFwcmVjaWFyIGxvcyBtdW5pY2lwaW9zIGNvbiBtYXlvcmVzIHJlbmRpbWllbnRvcyAoVG9uZWxhZGEvaGEpIGVuIGxvcyBjdWx0aXZvcyBxdWUgY29tcG9uZW4gZWwgZ3J1cG8gZGUgRnJ1dGFsZXMsIGVuIGVsIGRlcGFydGFtZW50byBkZSBDYXF1ZXTDoS4gU2UgcmVhbGl6w7MgY29uIGVsIGdydXBvIGRlIGZydXRhbGVzIGRlYmlkbyBhIHF1ZSBlcyBlbCBncnVwbyBxdWUgcHJlc2VudMOzIGxvcyBtYXlvcmVzIHJlbmRpbWllbnRvcyBlbiBlbCBhw7FvIDIwMTggZW4gQ2FxdWV0w6EuIExvcyBtdW5pY2lwaW9zIGRlICBTYW4gVmljZW50ZSBkZWwgQ2FndcOhbiB5IFZhbHBhcmFpc28gdHV2aWVyb24gbG9zIG1heW9yZXMgcmVuZGltaWVudG9zIGNvbiBsb3MgY3VsdGl2b3MgZGUgRnJlc2EgeSBBcmF6w6EgcmVzcGVjdGl2YW1lbnRlLg0KYGBge3J9DQpkYXRvcyAlPiUgDQogIGZpbHRlcihZRUFSPT0yMDE4ICYgR1JVUE89PSJUVUJFUkNVTE9TIFkgUExBVEFOT1MiKSAlPiUgDQogIGdyb3VwX2J5KENVTFRJVk8sIE1VTklDSVBJTykgJT4lDQogIHN1bW1hcml6ZShSZW5kaW1pZW50byA9IG1heChSZW5kaW1pZW50bywgbmEucm0gPSBUUlVFKSkgJT4lDQogICAgc2xpY2Uod2hpY2gubWF4KFJlbmRpbWllbnRvKSkgLT4gUmVuZGltaWVudG8NCg0KUmVuZGltaWVudG8NCmBgYA0KVGFibGEgNy4gTXVuaWNpcGlvcyBjb24gbWF5b3JlcyByZW5kaW1pZW50b3MgZW4gVHViw6lyY3Vsb3MgeSBwbMOhdGFub3MuIFNlIHB1ZWRlIGFwcmVjaWFyIHF1ZSBsb3MgbXVuaWNpcGlvcyBkZSBDYXJ0YWdlbmEgZGVsIENoYWlyYSwgIE1pbMOhbiB5IFNvbGFubyBmdWVyb24gbG9zIHF1ZSB0dXZpZXJvbiBtYXlvcmVzIHJlbmRpbWllbnRvcyBlbiBsb3MgY3VsdGl2b3MgZGUgeXVjYSwgcGzDoXRhbm8geSDDkWFtZSByZXNwZWN0aXZhbWVudGUuICANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCmN1bHRpdm9zMjAxOCA8LSByZWFkX2V4Y2VsKCJEOi9Eb2N1bWVudG9zL0dlb23DoXRpY2EvUEVWQV9DYXF1ZXRhMi54bHN4IikNCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KY3VsdGl2b3MyMDE4ICU+JQ0KICBmaWx0ZXIoQ1VMVElWTyA9PSAiUExBVEFOTyIpIC0+IHBsYXRhbm8yMDE4DQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnBsYXRhbm8yMDE4JFRFTVAgPC0gIGFzLmNoYXJhY3RlcihwbGF0YW5vMjAxOCRDT0RfTVVOKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpwbGF0YW5vMjAxOCRNUElPX0NDREdPIDwtIGFzLmZhY3RvcihwYXN0ZShwbGF0YW5vMjAxOCRURU1QLCBzZXA9IiIpKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpwbGF0YW5vX211bmljID0gbGVmdF9qb2luKG11bmljLCBwbGF0YW5vMjAxOCwgYnk9Ik1QSU9fQ0NER08iKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpyZXBfcGxhdGFubyA8LSBzdF90cmFuc2Zvcm0ocGxhdGFub19tdW5pYywgY3JzID0gMzExNikNCmBgYA0KDQpgYGB7cn0NCnBuZygiRDovRG9jdW1lbnRvcy9HZW9tw6F0aWNhL3BsYXRhbm9fMjAxOHAucG5nIiwgd2lkdGggPSAxMDI0LCBoZWlnaHQgPSA3NjMpDQoNCm9wYXIgPC0gcGFyKG1hciA9IGMoMiwyLDUsNSkpDQoNCnBsb3Qoc3RfZ2VvbWV0cnkocmVwX3BsYXRhbm8pLCBjb2w9ImRhcmtzZWFncmVlbiIsIGJvcmRlcj0iZGFya3NlYWdyZWVuNCIsICANCiAgICAgYmcgPSAid2hpdGUiLCBsd2QgPSAwLjYpDQoNCnByb3BTeW1ib2xzQ2hvcm9MYXllcih4ID0gcmVwX3BsYXRhbm8sIHZhciA9ICJQcm9kdWNjaW9uIiwgdmFyMiA9ICJSZW5kaW1pZW50byIsDQogICAgICAgICAgICAgICAgICAgICAgY29sID0gY2FydG8ucGFsKHBhbDEgPSAidHVycXVvaXNlLnBhbCIsIG4xID0gMywNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGFsMiA9ICJwaW5rLnBhbCIsIG4yID0gMyksDQogICAgICAgICAgICAgICAgICAgICAgaW5jaGVzID0gMC41LCBtZXRob2QgPSAicTYiLA0KICAgICAgICAgICAgICAgICAgICAgIGJvcmRlciA9ICJibGFjayIsIGx3ZCA9IDEsDQogICAgICAgICAgICAgICAgICAgICAgbGVnZW5kLnRpdGxlLmNleCA9IDEuMywNCiAgICAgICAgICAgICAgICAgICAgICBsZWdlbmQudmFsdWVzLmNleCA9IDEuMywNCiAgICAgICAgICAgICAgICAgICAgICBsZWdlbmQudmFyLnBvcyA9ICJ0b3ByaWdodCIsIA0KICAgICAgICAgICAgICAgICAgICAgIGxlZ2VuZC52YXIyLnBvcyA9ICJ0b3BsZWZ0IiwNCiAgICAgICAgICAgICAgICAgICAgICBsZWdlbmQudmFyMi52YWx1ZXMucm5kID0gMiwNCiAgICAgICAgICAgICAgICAgICAgICBsZWdlbmQudmFyMi50aXRsZS50eHQgPSAiUmVuZGltaWVudG9cbihlbiBUb24vSGEpIiwNCiAgICAgICAgICAgICAgICAgICAgICBsZWdlbmQudmFyLnRpdGxlLnR4dCA9ICJQcm9kdWNjacOzbiBkZSBQbMOhdGFubywgMjAxOCIsDQogICAgICAgICAgICAgICAgICAgICAgbGVnZW5kLnZhci5zdHlsZSA9ICJlIikNCg0KbGFiZWxMYXllcigNCiAgeCA9IHJlcF9wbGF0YW5vLCANCiAgdHh0ID0gIk1QSU9fQ05NQlIiLCANCiAgY29sPSAiYmxhY2siLCANCiAgY2V4ID0gMSwgDQogIGZvbnQgPSAxOCwNCiAgaGFsbyA9IEZBTFNFLCANCiAgYmcgPSAid2hpdGUiLCANCiAgciA9IDAuMSwgDQogIG92ZXJsYXAgPSBGQUxTRSwgDQogIHNob3cubGluZXMgPSBGQUxTRQ0KKQ0KDQpsYXlvdXRMYXllcih0aXRsZT0iUHJvZHVjY2nDs24geSByZW5kaW1pZW50byBkZSBQbMOhdGFubyBlbiBDYXF1ZXTDoSwgMjAxOCIsDQogICAgICAgICAgICBhdXRob3IgPSAiU2FuZHJhIEthdHRlcnluZSBSb2Ryw61ndWV6IEh1cnRhZG8iLCANCiAgICAgICAgICAgIHNvdXJjZXMgPSAiRnVlbnRlczogTUFEUiAmIERBTkUsIDIwMTgiLCANCiAgICAgICAgICAgIHNjYWxlID0gNTAsIHRhYnRpdGxlID0gRkFMU0UsIGZyYW1lID0gVFJVRSkNCg0Kbm9ydGgocG9zID0gInRvcCIpDQoNCnRpdGxlKG1haW49IlByb2R1Y2Npw7NuIHkgcmVuZGltaWVudG8gZGUgUGzDoXRhbm8gZW4gQ2FxdWV0w6EsIDIwMTgiLCBjZXgubWFpbj0zLA0KICAgICAgc3ViPSAiRnVlbnRlczogTUFEUiAmIERBTkUsIDIwMTgiLCBjZXguc3ViPTIpDQoNCmdyYXRpY3VsZSA9IFRSVUUNCg0KcGFyKG9wYXIpDQoNCmRldi5vZmYoKQ0KYGBgDQohW1Byb2R1Y2Npw7NuIHkgcmVuZGltaWVudG8gZGUgcGzDoXRhbm8gZW4gQ2FxdWV0w6EgcGFyYSBlbCBhw7FvIDIwMThdKEQ6L0RvY3VtZW50b3MvR2VvbcOhdGljYS9wbGF0YW5vXzIwMThwLnBuZykNCg0KRmlndXJhIDQuIFByb2R1Y2Npw7NuIHkgcmVuZGltaWVudG8gZGUgcGzDoXRhbm8gZW4gQ2FxdWV0w6EgcGFyYSBlbCBhw7FvIDIwMTggcG9yIG11bmljaXBpb3MuIFNlIHB1ZWRlbiBhcHJlY2lhciBxdWUgbG9zIG11bmljaXBpb3MgZGUgbWF5b3IgcHJvZHVjY2nDs24gZGUgcGzDoXRhbm8gc29uIE1pbMOhbiwgU2FuIFZpY2VudGUgZGVsIENhZ3XDoW4geSBDYXJ0YWdlbmEgZGVsIENoYWlyYS4NCg0KIyMgRGVzY3JpcGNpw7NuIGRlIGRhdG9zIHkgbcOpdG9kb3MNCg0KIyMjIERhdG9zIA0KQ2FycmVyYXMgdGFsZXMgY29tbyBsYSBpbmdlbmllcsOtYSBBZ3JvbsOzbWljYSBuZWNlc2l0YW4gcmVjb2xlY3RhciBkYXRvcyBlbiBwdW50b3MgZXNwZWPDrWZpY29zIHkgcGFydGllbmRvIGRlIGVsbG9zIGhhY2VyIHJlcHJlc2VudGFjaW9uZXMgY29udGludWFzIGRlIHVuYSB6b25hIGRldGVybWluYWRhLCB5IHBhcmEgZWxsbyBlcyBuZWNlc2FyaW8gaGFjZXIgaW50ZXJwb2xhY2nDs24gKExpemFyYXpvLCAyMDIwKS4gIExhIGludGVycG9sYWNpw7NuIG8gbW9kZWxhY2nDs24sIHRvbWEgZGF0b3MgcmVjb2xlY3RhZG9zIGVuIHB1bnRvcyBmaW5pdG9zIGVzcGVjw61maWNvcyBwYXJhIHZvbHZlcmxvcyBkYXRvcyBjb250aW51b3MsIHJlcHJlc2VudGFjaW9uZXMgZGUgbWFwYXMgw7p0aWxlcyB5IGNvbiBzZW50aWRvLCBlc3RvcyDDumx0aW1vcyBwdW50b3MgcHJlZGljZW4gY2FyYWN0ZXLDrXN0aWNhcyBzaW1pbGFyZXMgYSBsYXMgZGUgbG9zIHB1bnRvcyBtdWVzdHJlYWRvcyBwYXJhIMOhcmVhcyBubyBtdWVzdHJlYWRhcywgcHJlZGljZW4gdmFsb3JlcyBwYXJhIGNlbGRhcyBkZSB1biByw6FzdGVyIChBcmNHSVMsIHMuZikuIExhcyBzdXBlcmZpY2llcyByw6FzdGVyIHByZXNlbnRhbiB1bmEgZm9ybWEgZGUgY3VhZHLDrWN1bGEsIGRvbmRlIGEgbWVub3IgdGFtYcOxbyBkZSBsYXMgY2VsZGFzLCBtYXlvciBzZXLDoSBzdSBwcmVjaXNpw7NuLiANCg0KUGFyYSBwb2RlciBpbnRlcnBvbGFyIGRhdG9zLCBlc3RvcyBkZWJlbiBzZXIgY3VhbnRpdGF0aXZvcywgYW5hbGl6YW5kbyB2YXJpYWJsZXMgY29tbyBwSCwgcHJlY2lwaXRhY2nDs24sIGh1bWVkYWQsIMOtbmRpY2UgZGUgdmVnZXRhY2nDs24sIG5vIGN1YW50aXRhdGl2b3MuIExvcyBkYXRvcyBwdWVkZW4gc2VyIHJlY29sZWN0YWRvcyBlbiB1bmEgZXN0YWNpw7NuIG1ldGVvcm9sw7NnaWNhLCBlbiBlbCBjYXNvIGRlIENvbG9tYmlhICBlc3RhcyBlc3RhY2lvbmVzIG5vIHNvbiBtdWNoYXMgeSBubyBhYmFyY2FuIHRvZG8gZWwgdGVycml0b3JpbyBuYWNpb25hbCwgcHVlcyBhbGd1bmFzIHNlIGVuY3VlbnRyYW4gZW4gbG9zIHByaW5jaXBhbGVzIGFlcm9wdWVydG9zIHkgb3RyYXMgcGVydGVuZWNlbiBhIGdyZW1pb3MsIGRvbmRlIGVsIGFjY2VzbyBubyBlcyBww7pibGljbyAoTGl6YXJhem8sIDIwMjApLiANCg0KRW4gZXN0ZSB0cmFiYWpvIHNlIHVzYXJvbiBsb3MgZGF0b3MgZGVsIENISVJQUyAoQ2xpbWF0ZSBIYXphcmRzIEdyb3VwIEluZnJhUmVkIFByZWNpcGl0YXRpb24gd2l0aCBTdGF0aW9uIERhdGEpLCBxdWUgc29uIGRhdG9zIGRlIGVzdGltYWNpb25lcyBnbG9iYWxlcyBkZSBwcmVjaXBpdGFjacOzbiwgYmFzYWRhcyBlbiBzYXTDqWxpdGVzIGRlIGxhIE5BU0EgeSBOT0FBLCB5IG9ic2VydmFjaW9uZXMgc29icmUgbGEgdGllcnJhLiBMb3MgZGF0b3MgdGllbmVuIHVuYSByZXNvbHVjacOzbiBkZSAwLDA1IHkgMCwyNSBncmFkb3MgKDUsNSB5IDI4IGttKSBlbiBmb3JtYXRvcyBCSUwsIFRJRiBvIE5ldENERiAoR3J1cG8gS3Jha2VuLCAyMDE5KS4gU2UgZXhwYW5kZW4gZGUgNTDCsFMgYSA1MMKwTiB5IGEgbG8gbGFyZ28gZGUgdG9kYXMgbGFzIGxhdGl0dWRlcywgY29tcHJlbmRpZW5kbyBkYXRvcyBkZXNkZSAxOTgxIGhhc3RhIGxhIGFjdHVhbGlkYWQsIHRpZW5lbiBhbHRhIHJlc29sdWNpw7NuIHkgdW4gbGFyZ28gcGVyaW9kbyBkZSByZWdpc3Ryby4gDQoNClRpZW5lbiBsYSBjYXBhY2lkYWQgZGUgaW5jb3Jwb3JhciBpbcOhZ2VuZXMgc2F0ZWxpdGFsZXMgYSBkYXRvcyBvYnRlbmlkb3MgZGUgZXN0YWNpb25lcyBtZXRlb3JvbMOzZ2ljYXMgcGFyYSBjcmVhciBzZXJpZXMgZGUgY3VhZHLDrWN1bGFzIHBsdXZpb23DqXRyaWNhcyBjb24gdW5pZGFkZXMgZW4gbWlsw61tZXRyb3MsIHF1ZSBwZXJtaXRlbiByZWFsaXphciBlc3R1ZGlvcyBjb21vIHRlbmRlbmNpYXMgbyBzZXF1w61hcyAoSVJJLCAyMDE1KS4gQ0hJUlBTIGluY29ycG9yYSBkYXRvcyBkZSBlc3RpbWFjaW9uZXMgZGUgcHJlY2lwaXRhY2nDs24gZGlhcmlhcywgcGVudGFkYWxlcyB5IG1lbnN1YWxlczsgaGF5IHNlaXMgcGVudGFkcyBlbiB1biBtZXMgY2FsZW5kYXJpbywgY2luY28gcGVudGFkcyBkZSA1IGTDrWFzIHkgdW4gcGVudGFkIGNvbiBsb3MgMyBhIDUgZMOtYXMgcmVzdGFudGVzIGRlbCBtZXMgKEZ1bmsgZXQgYWwuLCAyMDE1KS4gTG9zIGRhdG9zIGZ1ZXJvbiBkZXNjYXJnYWRvcyBkZWwgc2lndWllbnRlIGxpbmsgPGh0dHA6Ly9kYXRhLmNoYy51Y3NiLmVkdS9wcm9kdWN0cy9DSElSUFMtMi4wLz4sIGRpcmVjdG9yaW8gZ2xvYmFsX3BlbnRhZCwgcG9zdGVyaW9ybWVudGUgZW50cmFyIGEgdGlmcyB5IHNlbGVjY2lvbmFyIGxhIGZlY2hhIG3DoXMgcmVjaWVudGUsIHF1ZSBmdWUgZWwgMTgvMDUvMjAyMC4NCg0KIyMjIE3DqXRvZG9zDQpFeGlzdGVuIGRvcyB0aXBvcyBkZSB0w6ljbmljYXMgcGFyYSBnZW5lcmFyIHN1cGVyZmljaWVzIGRlIGludGVycG9sYWNpw7NuOiBtb2RlbG9zIGRldGVybWluaXN0YXMsIHF1ZSB1c2FuIGZ1bmNpb25lcyBtYXRlbcOhdGljYXMgcGFyYSBwcmVkZWNpciB2YWxvcmVzIGRlc2Nvbm9jaWRvcywgeSB0w6ljbmljYXMgZXN0YWTDrXN0aWNhcywgcXVlIHByb2R1Y2VuIGzDrW1pdGVzIHBhcmEgZGV0ZXJtaW5hciBsYSBwcmVjaXNpw7NuIGRlIHVuYSBwcmVkaWNjacOzbi4gICBTZSBleHBsaWNhcsOhbiB0cmVzIG3DqXRvZG9zIGRpZmVyZW50ZXMgcGFyYSBpbnRlcnBvbGFyIGRhdG9zLCBzaWVuZG8gSURXLCBwcmltZXIgb3JkZW4gcG9saW5vbWlhbCB5IEtyaWdpbmcuIA0KDQojIyMjIEludmVyc2UgRGlzdGFuY2UgV2VpZ2h0aW5nIChJRFcpDQoNCkVsIG3DqXRvZG8gZGUgSURXIChJbnZlcnNlIERpc3RhbmNlIFdlaWdodGluZykgcGVydGVuZWNlIGEgbGEgdMOpY25pY2EgZGV0ZXJtaW5pc3RhLCBlcyBtYXRlbcOhdGljbywgZG9uZGUgbG9zIHZhbG9yZXMgbcOhcyBjZXJjYW5vcyBlc3TDoW4gbcOhcyByZWxhY2lvbmFkb3MgY29uIGxhIHZhcmlhYmxlIHF1ZSBzZSBlc3TDqSBlc3R1ZGlhbmRvLCBlcyBkZWNpciBxdWUgbG9zIHB1bnRvcyBtw6FzIGNlcmNhbm9zIGNvbXBhcnRlbiBjYXJhY3RlcsOtc3RpY2FzIHNpbWlsYXJlcyBhIGRpZmVyZW5jaWEgZGUgbG9zIHB1bnRvcyBsZWphbm9zIChHSVMgR2VvZ3JhcGh5LCBzLmYuKS4gUG9yIGVqZW1wbG8sIGFsIGxsb3ZlciBlbiB1biBwdW50byBkZXRlcm1pbmFkbywgc2UgcHVlZGUgcHJlZGVjaXIgcXVlIGNlcmNhIGRlIGVzdGUgcHVudG8gdGFtYmnDqW4gZXN0w6EgbGxvdmllbmRvLCBhIGRpZmVyZW5jaWEgZGUgdW4gcHVudG8gbGVqYW5vLCBkb25kZSBubyBzZSBwb2Ryw61hIGhhY2VyIGVzdGEgYWZpcm1hY2nDs24gKGF1dG9jb3JyZWxhY2nDs24gZXNwYWNpYWwpLiBTZSBwdWVkZW4gZXN0aW1hciB2YWxvcmVzIGRlc2Nvbm9jaWRvcyBkZSBjZWxkYSByYXN0ZXIgYSBwYXJ0aXIgZGUgdmFsb3JlcyBjb25vY2lkb3MgdG9tYWRvcyBlbiBwdW50b3MgZGUgbXVlc3RyYS4gIA0KDQpBbCB0ZW5lciB1biDDoXJlYSBkZSBlc3R1ZGlvIHkgZGV0ZXJtaW5hZG9zIHB1bnRvcyBkZSBtdWVzdHJhIGNvbiB2YWxvcmVzIGNvbm9jaWRvcywgc2kgc2UgcXVpc2llcmEgbWVkaXIgdW4gcHVudG8gZW4gZXNwZWPDrWZpY28sIGVzIG5lY2VzYXJpbyB0b21hciBsb3MgcHVudG9zIG3DoXMgY2VyY2Fub3MgZGVudHJvIGRlbCByYWRpbyBkZSBsYSB6b25hIGRlIGludGVyw6lzIHBhcmEgcG9kZXIgcmVhbGl6YXIgbGEgaW50ZXJwb2xhY2nDs24sIHB1ZWRlIHNlciB1biBuw7ptZXJvIGZpam8gbyB2YXJpYWJsZSBkZSBwdW50b3MgKEdJUyBHZW9ncmFwaHksIHMuZi4pLiBMb3MgcHVudG9zIGRlc2Nvbm9jaWRvcyBzZSBlc3RpbWFuIHBhcnRpZW5kbyBkZSBsb3MgdmFsb3JlcyBjb25vY2lkb3MgZGUgbG9zIHB1bnRvcyBtdWVzdHJlYWRvcywgZWwgdmFsb3IgZGUgcG90ZW5jaWEgbGUgcGVybWl0ZSBjb250cm9sYXIgbGEgc2lnbmlmaWNhbmNpYSBkZSBsb3MgcHVudG9zIGRlc2Nvbm9jaWRvcyAoQXJjR0lTLCBzLmYuKSwgZG9uZGUgZWwgdmFsb3IgZGUgMiBlcyBlbCBtw6FzIHVzYWRvLiBTdSBmw7NybXVsYSBlczoNCiFbRsOzcm11bGEgZGUgSURXXShEOi9JbWFnZW5lcy9GSURXLnBuZykNCg0KRmlndXJhIDUuIEbDs3JtdWxhIGRlIElEVy4gRXN0YSBmw7NybXVsYSB0aWVuZSBlbCBuw7ptZXJvIHNpZ21hLCBxdWUgZXMgZWwgbsO6bWVybyBkZSBwdW50b3MgcXVlIHNlIGludGVycG9sYXLDoW4sIHo6IFZhcmlhYmxlIGRlIGVzdHVkaW8sIHpwOiBwdW50byBkZXNjb25vY2lkbywgbjogbsO6bWVybyBkZSBwdW50b3MgcXVlIGVzdMOhbiBkZW50cm8gZGVsIHJhZGlvIGRlIGLDunNxdWVkYSwgemk6IHZhbG9yIGNvbm9jaWRvIGRlbCBwdW50byBlbiBlbCByYWRpbyBkZSBiw7pzcXVlZGEsICBkaV5wOiBEaXN0YW5jaWEgZW50cmUgZWwgcHVudG8geSBlbCBwdW50byBkZXNjb25vY2lkbywgcDogUG90ZW5jaWEuIFNlIGNvbnNpZGVyYSBkZXRlcm1pbsOtc3RpY28geWEgcXVlIGVzdMOhIGJhc2FkbyBlbiBsb3MgdmFsb3JlcyBtZWRpZG9zIHkgZW4gZsOzcm11bGEgbWF0ZW3DoXRpY2EsIHF1ZSBkZXRlcm1pbmFuIGxhIHN1YXZpZGFkIGRlIGxhIHN1cGVyZmljaWUgZ2VuZXJhZGEgKEFyY0dJUywgcy5mKS4gICANCg0KIyMjIyBLcmlnaW5nDQpFcyB1biBtw6l0b2RvIGRlIGludGVycG9sYWNpw7NuIGdlb2VzdGFkw61zdGljbyBwYXJhIGNyZWFyIHN1cGVyZmljaWVzIGVzdGltYWRhcyBlbiBiYXNlIGEgdW5vcyBwdW50b3MgY29uIHZhbG9yZXMgY29ub2NpZG9zIGRlIGxhIHZhcmlhYmxlIGRlIGVzdHVkaW8sIHNlIGJhc2EgZW4gbW9kZWxvcyBlc3RhZMOtc3RpY29zLCBlcyBkZWNpciBxdWUgbG9zIHB1bnRvcyBtdWVzdHJlYWRvcyBzZSByZWxhY2lvbmFuIGNvbiBsYSBlc3RhZMOtc3RpY2EuICBMbyBhbnRlcmlvciBwZXJtaXRlIHF1ZSByZXN1bHRlIHVuYSBzdXBlcmZpY2llIGRlIHByZWRpY2Npw7NuIHkgbWVkaWRhcyBkZSBwcmVjaXNpw7NuIGRlIGxhcyBlc3RpbWFjaW9uZXMgKEFyY0dJUywgcy5mKS4gICANCg0KQWwgaWd1YWwgcXVlIElEVywgZWwga3JpZ2luZyB1dGlsaXphIHZhbG9yZXMgZGUgcHVudG9zIG11ZXN0cmVhZG9zIGRlbnRybyBkZSB1biByYWRpbywgYWp1c3TDoW5kb2xvcyBhIHVuYSBmdW5jacOzbiBtYXRlbcOhdGljYS4gRWwga3JpZ2luZyBzZSBiYXNhIGVuIHVuIHZhcmlvZ3JhbWEgcXVlIGRldGVybWluYW4gbGEgYXV0b2NvcnJlbGFjacOzbiwgYWNvcmRlIGNvbiBlbCBnZcOzZ3JhZm8gIFRvYmxlcjog4oCcVG9kbyBlc3TDoSByZWxhY2lvbmFkbyBjb24gdG9kbyBsbyBkZW3DoXMsIHBlcm8gbGFzIGNvc2FzIGNlcmNhbmFzIGVzdMOhbiBtw6FzIHJlbGFjaW9uYWRhcyBxdWUgbGFzIGRpc3RhbnRlc+KAnSwgZXN0byBxdWllcmUgZGVjaXIgbGEgYXV0b2NvcnJlbGFjacOzbiBlcyBlbCBncmFkbyBkZSBzaW1pbGl0dWQgZW50cmUgdW4gb2JqZXRvIHkgbG9zIG9iamV0b3MgY2VyY2Fub3MgYWwgbWlzbW8gKEdJUyBHZW9ncmFwaHksIDIwMjApLCByZXByZXNlbnRhbmRvIGdyw6FmaWNhbWVudGUgbGEgdmFyaWFuemEgZGUgbG9zIGRhdG9zIGFjb3JkZSBjb24gc3UgZGlzdGFuY2lhLiBTaSBsb3MgcHVudG9zIGVzdMOhbiBtw6FzIGNlcmNhbm9zLCB0ZW5kcsOhbiB1bmEgdmFyaWFuemEgcGVxdWXDsWEsIG1pZW50cmFzIHF1ZSBzaSBsb3MgcHVudG9zIGVzdMOhbiBtw6FzIGFsZWphZG9zLCBwcm9iYWJsZW1lbnRlIHNlIHRlbmRyw6EgdW5hIHZhcmlhbnphIGFsdGEuIERlIGxvIGFudGVyaW9yIHNlIHB1ZWRlIGhhY2VyIHVuYSBncsOhZmljYSBxdWUgdGllbmUgdW4gcmFuZ28geSB1biB1bWJyYWwsIGRvbmRlIGVsIMO6bHRpbW8gc2UgYWxjYW56YSBhbCBuaXZlbGFyc2UgbGEgdmFyaWFjacOzbiwgbm8gaGFicsOtYSBhdXRvY29ycmVsYWNpw7NuIGVzcGFjaWFsIGVudHJlIGxvcyBkYXRvcyAoR0lTIEdlb2dyYXBoeSwgMjAyMCkuICANCiFbRsOzcm11bGEgZGUgS3JpZ2luZ10oRDovSW1hZ2VuZXMvRktHLnBuZykgIA0KDQpGaWd1cmEgNi4gRsOzcm11bGEgZGUgS3JpZ2luZy4geihzaSk6IFZhbG9yIG1lZGlkbyBlbiBsYSB1YmljYWNpw7NuIGksIExhbWRhIGk6IHBvbmRlcmFjacOzbiBkZXNjb25vY2lkYSBwYXJhIGVsIHZhbG9yIG1lZGlkbyBlbiBsYSB1YmljYWNpw7NuIGksIHMwOiBVYmljYWNpw7NuIGRlIGxhIHByZWRpY2Npw7NuLCBOOiBjYW50aWRhZCBkZSB2YWxvcmVzIG1lZGlkb3MuIFRvbWFkbyBkZTogIGh0dHBzOi8vZGVza3RvcC5hcmNnaXMuY29tL2VzL2FyY21hcC8xMC4zL3Rvb2xzL3NwYXRpYWwtYW5hbHlzdC10b29sYm94L2hvdy1rcmlnaW5nLXdvcmtzLmh0bQ0KDQpVbiBzZW1pdmFyaW9ncmFtYSBwdWVkZSBzZXIgc3VwZXJmaWNpYWwsIGV4cG9uZW5jaWFsLCBjaXJjdWxhciwgZ2F1c3NpYW5vIG8gbGluZWFsOyBlc3RvIGRlc3B1w6lzIGRlIGhhYmVyIGFqdXN0YWRvIGxhIHN1cGVyZmljaWUgY29tbyB1biBwb2xpbm9taW8uIFBhcmEgdXNhciBlc3RlIG3DqXRvZG8sIGxvcyBkYXRvcyBkZWJlbiB0ZW5lciB1bmEgZGlzdHJpYnVjacOzbiBub3JtYWwsIGRlYmVuIHNlciBlc3RhY2lvbmFyaW9zIHkgbm8gdGVuZXIgbmluZ3VuYSB0ZW5kZW5jaWEgKEFyY0dJUywgcy5mKS4gU2UgZGljZSBxdWUgbG9zIGRhdG9zIHRpZW5lbiB1bmEgZGlzdHJpYnVjacOzbiBub3JtYWwgc2kgbG9zIHB1bnRvcyBlc3TDoW4gc29icmUgdW5hIGzDrW5lYSBkZSA0NcKwLCBsb3MgZGF0b3Mgc29uIGVzdGFjaW9uYXJpb3Mgc2kgbGEgdmFyaWFjacOzbiBsb2NhbCBkZSBlc3RvcyBubyBjYW1iaWEgZW4gZGlmZXJlbnRlcyDDoXJlYXMgZGVsIG1hcGEsIGVzIGRlY2lyIHF1ZSBubyBoYXkgY2FtYmlvcyBhYnJ1cHRvcyBvIGzDrW5lYXMgZGlzY29udGludWFzLCBzZSBwdWVkZSB2ZXJpZmljYXIgbWVkaWFudGUgdW4gbWFwYSBkZSB2b3Jvbm9pLCBxdWUgcmVmbGVqYSBsYSBkZXN2aWFjacOzbiBlc3TDoW5kYXIuICBTZWfDum4gbGFzIHByZWRpY2Npb25lcyBxdWUgbGEgdMOpY25pY2EgZGUgS3JpZ2luZyBoYWdhLCBnZW5lcmFyw6EgdGFtYmnDqW4gdW5hIG1lZGlkYSBkZSBpbmNlcnRpZHVtYnJlIG8gZXJyb3IsIGVzdGltYW5kbyBsYSBjb25maWFuemEgZGUgbGEgc3VwZXJmaWNpZS4gDQoNCkxvcyBncsOhZmljb3MgZGUgbG9zIHNlbWl2YXJpb2dyYW1hcyBwdWVkZW4gc2VyIGNhbGN1bGFkb3MgY29uIGxhIGVjdWFjacOzbjogDQpgYGB7cn0NClNlbWl2YXJpb2dyYW1hKGRpc3RhbmNpYWgpID0gMC41ICogcHJvbWVkaW8oKHZhbG9yaSDigJMgdmFsb3JqKV4yKQ0KYGBgDQpkYW5kbyBjb21vIHJlc3VsdGFkbyB1biBncsOhZmljbyBkZSBsb3MgdmFsb3JlcyBkZSBzZW1pdmFyaW9ncmFtYSBwcm9tZWRpYWRvcyB1YmljYWRvcyBlbiBlbCBlamUgWSwgeSBsYSBkaXN0YW5jaWEgbyBpbnRlcnZhbG8gZW4gZWwgZWplIFguIEVudG9uY2VzLCBsYSB1YmljYWNpw7NuIGRlIGxvcyBwdW50b3MgcHJveWVjdGFkb3MgZW4gZXN0ZSBncsOhZmljbyBwZXJtaXRlIGNvbm9jZXIgc2kgc29uIHZhbG9yZXMgc2ltaWxhcmVzIG8gbm8sIHNpIGxvcyBwdW50b3MgZXN0w6FuIHVubyBjZXJjYSBkZWwgb3Rybywgc2lnbmlmaWNhIHF1ZSBjb21wYXJ0ZW4gY2FyYWN0ZXLDrXN0aWNhcyBzaW1pbGFyZXMsIGEgZGlmZXJlbmNpYSBkZSBzaSBzZSBlbmN1ZW50cmFuIHNlcGFyYWRvcyB1bm8gZGVsIG90cm8sIHNpZ25pZmljYW5kbyBxdWUgc29uIGRpc3RpbnRvcyAoQXJjR0lTLCBzLmYpLiANCg0KIyMjIyBQb2zDrWdvbm9zIGRlIFRoaWVzc2VuIG8gRGlhZ3JhbWFzIGRlIFZvcm9ub2kNCg0KU29uIHVubyBkZSBsb3MgbcOpdG9kb3MgcGFyYSBpbnRlcnBvbGFyIG3DoXMgc2VuY2lsbG9zIHlhIHF1ZSBoYXksIGVzdMOhbiBiYXNhZG9zIGVuIHVuYSBjb25zdHJ1Y2Npw7NuIGdlb23DqXRyaWNhIHF1ZSBwZXJtaXRlbiBoYWNlciBwYXJ0aWNpb25lcyBkZSB1biBwbGFubyBxdWUgcmVwcmVzZW50YXLDoSBlbCDDoXJlYSBkZSBpbnRlcsOpcy4gU3Ugbm9tYnJlIGZ1ZSBwdWVzdG8gZW4gaG9ub3IgYWwgbWV0ZW9yw7Nsb2dvIEFsZnJlZCBUaGllc3NlbiwgYXVucXVlIHRhbWJpw6luIGZ1ZXJvbiBlc3R1ZGlhZG9zIHBvciBlbCBtYXRlbcOhdGljbyBHZW9yZ3kgVm9yb25vaSwgbcOpdG9kbyBkZW5vbWluYWRvIHRhbWJpw6luIERpYWdyYW1hcyBkZSBWb3Jvbm9pIGVuIGhvbm9yIGFsIG1hdGVtw6F0aWNvIChCcmF2bywgcy5mKS4gDQoNCkVzdGUgbcOpdG9kbyB0aWVuZSBtw7psdGlwbGVzIGZ1bmNpb25lcywgZGVudHJvIGRlIGVsbGFzIHNlIGVuY3VlbnRyYSBlbCBhbsOhbGlzaXMgZGUgZGF0b3MgbWV0ZW9yb2zDs2dpY29zIG8gZGV0ZXJtaW5hciDDoXJlYXMgZGUgaW5mbHVlbmNpYSBlbiB1bmEgem9uYSwgcG9yIGVqZW1wbG8gaWdsZXNpYXMgbyBjZW50cm9zIGNvbWVyY2lhbGVzLiBQYXJhIGVsIGNhc28gZGUgcHJlY2lwaXRhY2nDs24sIGVzIG5lY2VzYXJpbyBzYWJlciBkw7NuZGUgc2UgZW5jdWVudHJhbiB1YmljYWRhcyBsYXMgZXN0YWNpb25lcyBwbHV2aW9tw6l0cmljYXMgcGFyYSBpZGVudGlmaWNhciBlbCDDoXJlYSBkZSBpbmZsdWVuY2lhIGRlIGRpY2hhIGVzdGFjacOzbi4gQWwgdW5pcnNlIGxvcyBwdW50b3MgZW50cmUgc8OtLCBzZSB2YW4gdHJhemFuZG8gYSBzdSB2ZXogbWVkaWF0cmljZXMgKGzDrW5lYXMgcGVycGVuZGljdWxhcmVzIGEgdW4gc2VnbWVudG8gcXVlIHBhc2EgcG9yIHN1IHB1bnRvIG1lZGlvKSBkZSBsb3Mgc2VnbWVudG9zIGRlIHVuacOzbiwgY3JlYW5kbyB1bmEgc2VyaWUgZGUgcG9sw61nb25vcyBlbiB1biBlc3BhY2lvIGRlIGRvcyBkaW1lbnNpb25lcyBhbHJlZGVkb3IgZGUgdW4gY29uanVudG8gZmluaXRvIGRlIHB1bnRvcyAoQnJhdm8sIHMuZikuIEZvcm1hbiB0cmnDoW5ndWxvcyBxdWUgdW5lbiBsYXMgZXN0YWNpb25lcywgcG9yIG1lZGlvIGRlIGzDrW5lYXMgcmVjdGFzIHNpbiBxdWUgZXN0YXMgc2UgZW50cmVjb3J0YW4gKEdpbW9uZCwgMjAxOSkuIFVuYSBsaW1pdGFudGUgcXVlIHByZXNlbnRhIGVzdGUgbcOpdG9kbyBlcyBxdWUgbm8gc2UgcHVlZGUgZXN0aW1hciBlbCB2YWxvciBkZSBpbmNlcnRpZHVtYnJlIG8gZXJyb3IgZGViaWRvIGEgcXVlIHVuIHNvbG8gcG9sw61nb25vIHNlIG9idGllbmUgZGUgdW4gc29sbyBwdW50by4gRWwgdGFtYcOxbyB5IGxhIGZvcm1hIGRlIGNhZGEgcG9sw61nb25vIGRlcGVuZGUgZGUgbGEgZGlzdHJpYnVjacOzbiBkZSBsb3MgcHVudG9zLiAgRXN0YXMgZXN0cnVjdHVyYXMgc29uIGRlIHZpdGFsIGltcG9ydGFuY2lhIGVuIGxhIGdlb21ldHLDrWEgY29tcHV0YWNpb25hbCwgc29uIGNhcGFjZXMgZGUgZ3VhcmRhciBpbmZvcm1hY2nDs24gcmVmZXJlbnRlIGEgdW5hIHByb3hpbWlkYWQgZW50cmUgcHVudG9zLg0KDQojIyBQcmVzZW50YWNpw7NuIGRlIHJlc3VsdGFkb3MNCg0KVW5hIHZleiBkZXNjYXJnYWRvcyBsb3MgZGF0b3MgeSBjYXJnYWRhcyBsYXMgbGlicmVyw61hcywgc2UgcHJvY2VkacOzIGEgbGVlcmxvcywgcHJlc2VudGFyb24gdW5hIHJlc29sdWNpw7NuIGRlIGNlbGRhIGRlIDAuMDUgeSBmdWUgdW5hIGNhcGEgcsOhc3Rlci4gU29uIGRhdG9zIGdsb2JhbGVzLCB0aWVuZW4gdW4gc2lzdGVtYSBkZSBjb29yZGVuYWRhcyBnZW9ncsOhZmljYXMgV0dTODQuDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpwcmVjaXAgPC0gcmFzdGVyKCJEOi9Fc2NyaXRvcmlvL2NoaXJwcy12Mi4wLjIwMjAuMDQuNi50aWYiKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpwcmVjaXANCmBgYA0KU2UgaW1wb3J0YXLDoSB1biBhcmNoaXZvIGRlIGZvcm1hdG8gc2hhcGVmaWxlIHBhcmEgZWwgw6FyZWEgcXVlIHNlIGRlc2VhIGVzdHVkaWFyLCBlbiBlc3RlIGNhc28gZWwgZGVwYXJ0YW1lbnRvIGRlIENhcXVldMOhLCBlbCBjdWFsIHNlIGNvbXBvbmUgZGUgMTYgbXVuaWNpcGlvcywgc2lzdGVtYSBkZSBjb29yZGVuYWRhcyBXR1M4NCB5IG51ZXZlIHZhcmlhYmxlcy4gIA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KKGFvaSA8LSBzaGFwZWZpbGUoIkQ6L0RvY3VtZW50b3MvR2VvbcOhdGljYS9BRE1JTklTVFJBVElWTzEvTUdOX01QSU9fUE9MSVRJQ08uc2hwIikpDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnByZWNhIDwtIGFnZ3JlZ2F0ZShwcmVjaXAsIGZhY3Q9NCwgZnVuPW1lYW4pDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnByZWNpcC5jcm9wIDwtIHJhc3Rlcjo6Y3JvcChwcmVjYSwgZXh0ZW50KGFvaSkpDQpgYGANClBhcmEgZGFyIHZhbG9yZXMgbnVsb3MgYSBsYXMgw6FyZWFzIHF1ZSBzZSBlbmN1ZW50cmFuIGZ1ZXJhIGRlIGxvcyBsw61taXRlcyBkZWwgZGVwYXJ0YW1lbnRvIHNlIHVzw7MgbGEgZnVuY2nDs24gbWFzaywgc2llbmRvIHVuYSBjYXBhIHJhc3Rlci4gDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpwcmVjaXAubWFzayA8LSBtYXNrKHggPSBwcmVjaXAuY3JvcCwgbWFzayA9IGFvaSkNCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KcHJlY2lwLm1hc2sgDQpgYGANCmBgYHtyfQ0KcGxvdChwcmVjaXAubWFzaywgbWFpbj0gIkNISVJQUyBkZSBQcmVjaXBpdGFjacOzbiBlbiBDYXF1ZXTDoSBkZXNkZSAxOC8wNS8yMDIwIGhhc3RhIDIzLzA1LzIwMjAgW21tXSIpDQpwbG90KGFvaSwgYWRkPVRSVUUpDQpgYGANCkZpZ3VyYSA3LiBNYXBhIGRlIHZpc3RhIGRlbCBwcmVjaXBpdGFjacOzbiBkZWwgZGVwYXJ0YW1lbnRvIGRlIENhcXVldMOhLiAgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpsaWJyYXJ5KGxlYWZsZXQpDQpsaWJyYXJ5KFJDb2xvckJyZXdlcikNCmBgYA0KYGBge3J9DQpwYWwgPC0gY29sb3JOdW1lcmljKGMoInJlZCIsICJvcmFuZ2UiLCAieWVsbG93IiwgImJsdWUiLCAiZGFya2JsdWUiKSwgdmFsdWVzKHByZWNpcC5tYXNrKSwNCiAgbmEuY29sb3IgPSAidHJhbnNwYXJlbnQiKQ0KDQpsZWFmbGV0KCkgJT4lIGFkZFRpbGVzKCkgJT4lDQogIGFkZFJhc3RlckltYWdlKHByZWNpcC5tYXNrLCBjb2xvcnMgPSBwYWwsIG9wYWNpdHkgPSAwLjYpICU+JQ0KICBhZGRMZWdlbmQocGFsID0gcGFsLCB2YWx1ZXMgPSB2YWx1ZXMocHJlY2lwLm1hc2spLA0KICAgIHRpdGxlID0gIkNISVJQUyBkZSBQcmVjaXBpdGFjacOzbiBlbiBDYXF1ZXTDoVxuIGRlc2RlIDE4LzA1LzIwMjAgaGFzdGEgMjMvMDUvMjAyMCBbbW1dIikNCmBgYA0KRmlndXJhIDguIE1hcGEgaW50ZXJhY3Rpdm8gZGUgcHJlY2lwaXRhY2nDs24gZW4gQ2FxdWV0w6EuIA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KcHJlY2lwLnBvaW50cyA8LSByYXN0ZXJUb1BvaW50cyhwcmVjaXAubWFzaywgc3BhdGlhbCA9IFRSVUUpDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnByZWNpcC5wb2ludHMNCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KbmFtZXMocHJlY2lwLnBvaW50cykgPC0gIkxsdXZpYSINCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KcHJlY2lwLnBvaW50cw0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpzdHIocHJlY2lwLnBvaW50cykNCmBgYA0KUGxvdGVhciBsb3MgcHVudG9zIHBhcmEgbGxldmFyIGEgY2FibyBsYSBpbnRlcnBvbGFjacOzbi4gDQpgYGB7cn0NCnBsb3QocHJlY2lwLm1hc2ssIG1haW49ICJDSElSUFMgZGUgUHJlY2lwaXRhY2nDs24gZGVzZGUgMTgvMDUvMjAyMCBoYXN0YSAyMy8wNS8yMDIwIFttbV0iKQ0KcGxvdChhb2ksIGFkZD1UUlVFKQ0KcG9pbnRzKHByZWNpcC5wb2ludHMkeCwgcHJlY2lwLnBvaW50cyR5LCBjb2wgPSAicHVycGxlIiwgY2V4ID0gLjEpDQpgYGANCkZpZ3VyYSA5LkRlcGFydGFtZW50byBkZSBDYXF1ZXTDoSBjb24gbG9zIHB1bnRvcyBwYXJhIGxhIGludGVycG9sYWNpw7NuLiANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCmxpYnJhcnkoZ2VvanNvbmlvKQ0KZ2VvanNvbmlvOjpnZW9qc29uX3dyaXRlKHByZWNpcC5wb2ludHMsIGZpbGUgPSAiRDovRG9jdW1lbnRvcy9HZW9tw6F0aWNhL3Bwb2ludHMuZ2VvanNvbiIpDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnByZWNpcC5wb2ludHMgPC0gZ2VvanNvbmlvOjpnZW9qc29uX3JlYWQoIkQ6L0RvY3VtZW50b3MvR2VvbcOhdGljYS9wcG9pbnRzLmdlb2pzb24iLCB3aGF0PSJzcCIpDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnByZWNpcC5wb2ludHMNCmBgYA0KRXMgbmVjZXNhcmlvIHBhc2FyIGxvcyBkYXRvcyBhIGNvb3JkZW5hZGFzIHBsYW5hcyBwb3JxdWUgbm8gZXMgcmVjb21lbmRhYmxlIGhhY2VyIGludGVycG9sYWNpw7NuIGNvbiBsb3MgZGF0b3MgZW4gY29vcmRlbmFkYXMgZ2VvZ3LDoWZpY2FzIChkYXR1bVdHUzg0KS4NCmBgYHtyIGVjaG8gPSBGQUxTRX0NCihhb2kgPC0gc2hhcGVmaWxlKCJEOi9Eb2N1bWVudG9zL0dlb23DoXRpY2EvQURNSU5JU1RSQVRJVk8xL01HTl9NUElPX1BPTElUSUNPLnNocCIpKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpjYXF1ZXRhX3NmIDwtICBzZjo6c3RfYXNfc2YoYW9pKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQooYm9yZGVyX3NmIDwtDQogIGNhcXVldGFfc2YgJT4lDQogIHN1bW1hcmlzZShhcmVhID0gc3VtKE1QSU9fTkFSRUEpKSkNCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KIChib3JkZXIgPC0gYXMoYm9yZGVyX3NmLCAnU3BhdGlhbCcpKSANCmBgYA0KUG9sw61nb25vcw0KYGBge3IgZWNobyA9IEZBTFNFfQ0KKGNhcXVldGEuc2YgPC0gc3RfYXNfc2YoYW9pKSAlPiUgbXV0YXRlKE1VTklDID0gTVBJT19DTk1CUiwgQ09ESUdPID0gTVBJT19DQ0RHTykgJT4lIHNlbGVjdChNVU5JQywgQ09ESUdPKSkNCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KcC5zZiA8LSBzdF9hc19zZihwcmVjaXAucG9pbnRzKQ0KYGBgDQpVbmEgaW50ZXJzZWNjacOzbiBkZSBkYXRvcyBlcyB1bmEgb3BlcmFjacOzbiBnZW9tw6l0cmljYSBlbnRyZSBkb3MgZWxlbWVudG9zIGRpc3RpbnRvcywgY3V5byByZXN1bHRhZG8gYnVzY2EgcXVlIHBvciBjYWRhIGVsZW1lbnRvIHF1ZSBzZSBpbnRlcmNlcHRlIHkgYXJyb2plIHVuIGVsZW1lbnRvLCBkb25kZSBxdWVkZW4gbG9zIGF0cmlidXRvcyBkZSBhbWJvcyBvYmpldG9zIGVuIHVubyBzb2xvLiBFbiBlc3RlIGNhc28sIGVuIHVuIGVsZW1lbnRvIHF1ZWRhcm9uIGNvbnNpZ25hZG9zIGxvcyBlbGVtZW50b3MgbXVuaWNpcGlvIChwb2zDrWdvbm9zKSB5IGxhIHByZWNpcGl0YWNpw7NuIChwdW50b3MuKQ0KYGBge3IgZWNobyA9IEZBTFNFfQ0KKHByZWNpcC5zZiA9IHN0X2ludGVyc2VjdGlvbihjYXF1ZXRhLnNmLCBwLnNmKSkNCmBgYA0KRG9zIHRhcmVhcyBkZSByZXByb3RlY2Npw7NuOiBEb3MgbWFuZXJhcyBwYXJhIHJlcHJveWVjY2nDs24sIGNvbnZpcnRpZW5kbyB1biBvYmpldG8gZGUgY2FyYWN0ZXLDrXN0aWNhIHNpbXBsZSAoc2ltcGxlZmVhdHVyZSksIGEgdW4gb2JqZXRvIGVzcGFjaWFsLCBwdWVzIGxhcyBsaWJyZXLDrWFzIHJlcXVpZXJlbiBlc3RvcyBvYmpldG9zLiANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnAuc2YubWFnbmEgPC0gc3RfdHJhbnNmb3JtKHByZWNpcC5zZiwgY3JzPTMxMTYpDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCmNhcXVldGEuc2YubWFnbmEgPC0gc3RfdHJhbnNmb3JtKGNhcXVldGEuc2YsIGNycz0zMTE2KQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQoocHJlY2lwMiA8LSBhcyhwLnNmLm1hZ25hLCAnU3BhdGlhbCcpKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQojIEd1YXJkYXIgdW5hIGNvcGlhIGRlIGxvcyBkYXRvcyBwYXJhIG5vIHBlcmRlciBlbCB0cmFiYWpvIHJlYWxpemFkbyBzaSBvY3VycmllcmEgdW4gZmFsbG8gZW4gZWwgcHJvZ3JhbWEgbyBlbiBsYSBjb25leGnDs24uIA0Kc2hhcGVmaWxlKHByZWNpcDIsIGZpbGVuYW1lPSdEOi9Fc2NyaXRvcmlvL3ByZWNpcDIuc2hwJywgb3ZlcndyaXRlPVRSVUUpDQpgYGANCiBFbGltaW5hciBjaWZyYXMgZGVjaW1hbGVzIGRlIGxhIHZhcmlhYmxlIExsdXZpYSwgcXVlIHJlcHJlc2VudGEgbGEgcHJlY2nDrXRhY2nDs24gZW4gQ2FxdWV0w6EuDQpgYGB7cn0NCiNFc3RhIGluc3RydWNjacOzbiBlcyDDunRpbCBwYXJhIHF1ZSBsb3MgdmFsb3JlcyBkZSBsbHV2aWEgbm8gcmVmbGVqZW4gdGFudGFzIGNpZnJhcyBkZWNpbWFsZXMgZW4gZWwgbWFwYS4NCnByZWNpcDIkTGx1dmlhIDwtIHJvdW5kKHByZWNpcDIkTGx1dmlhLCAxKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpwcmVjaXAyDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCihjYXF1ZXRhMiA8LSBhcyhjYXF1ZXRhLnNmLm1hZ25hLCAnU3BhdGlhbCcpKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpzaGFwZWZpbGUoY2FxdWV0YTIsIGZpbGVuYW1lPSdEOi9Fc2NyaXRvcmlvL2NhcXVldGEyLnNocCcsIG92ZXJ3cml0ZT1UUlVFKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpwcmVjaXAyQGJib3ggPC0gY2FxdWV0YTJAYmJveA0KYGBgDQpUcmF6YXIgbG9zIGRhdG9zIGNvbiB0bWFwOiBMYSBsaWJyZcOtYSB0bWFwIHBlcm1pdGUgaGFjZXIgbWFwYXMsIGVuIGVzdGUgY2FzbyBjb24gbG9zIGRhdG9zIGRlIHByZWNpcGl0YWNpw7NuIHkgbXVuaWNpcGlvIGRlbCBkZXBhcnRhbWVudG8gZGUgQ2FxdWV0w6EuDQpgYGB7cn0NCnRtX3NoYXBlKGNhcXVldGEyKSArIHRtX3BvbHlnb25zKCkgKw0KICB0bV9zaGFwZShwcmVjaXAyKSArDQogIHRtX2RvdHMoY29sPSJMbHV2aWEiLCBwYWxldHRlID0gIlJkQnUiLCBtaWRwb2ludCA9IDMuMCwNCiAgICAgICAgICAgICB0aXRsZT0iUHJlY2lwaXRhY2nDs24gbXVlc3RyZWFkYSBcbihlbiBtbSkiLCBzaXplPTAuMikgKw0KICB0bV90ZXh0KCJMbHV2aWEiLCBqdXN0PSJjZW50ZXIiLCB4bW9kPS4xLCBzaXplID0gMC41KSArDQogIHRtX2xlZ2VuZChsZWdlbmQub3V0c2lkZT1UUlVFKQ0KYGBgDQpGaWd1cmEgMTAuIE1hcGEgY29uIGxvcyBwdW50b3MgeSBzdXMgcmVzcGVjdGl2b3MgdmFsb3JlcyBkZSBwcmVjaXBpdGFjacOzbiwgZW4gZXN0ZSBjYXNvIHZhcmlhbmRvIGVuIGludGVydmFsb3MgZGUgYSAxMCBtbS4NCiMjIyBNw6l0b2RvcyBwYXJhIGludGVycG9sYXIgZGF0b3MgZGUgcHJlY2lwaXRhY2nDs24NCkEgY29udGludWFjacOzbiBzZSByZXByZXNlbnRhcsOhbiBhbGd1bm9zIGRlIGxvcyBtw6l0b2RvcyB0cmFiYWphZG9zIHBhcmEgbGEgaW50ZXJwb2xhY2nDs24gZGUgZGF0b3MgZGUgcHJlY2lwaXRhY2nDs24uDQojIyMjIDEuIFBvbMOtZ29ub3MgZGUgVGhpZXNzZW4NCkVzdG9zIHBvbMOtZ29ub3Mgc29uIChvIHBvbMOtZ25vcyBkZSBwcm94aW1pZGFkKSBzZSBwdWVkZW4gY3JlYXIgdXRpbGl6YW5kbyBsYSBmdW5jacOzbiBkaXJpY2hsZXQgZGUgc3BhdHN0YXQuIEFybWFuIHVub3MgcG9sw61nb25vcyBxdWUgY29udGllbmVuIHRvZGFzIGxhcyB6b25hcyBxdWUgZXN0w6FuIG3DoXMgY2VyY2EgZGUgdW4gcHVudG8gcXVlIGRlIG90cm8gDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpsaWJyYXJ5KHNwYXRzdGF0LmRhdGEpDQpsaWJyYXJ5KG5sbWUpDQpsaWJyYXJ5KHJwYXJ0KQ0KbGlicmFyeShzcGF0c3RhdCkNCmxpYnJhcnkocmdlb3MpDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnRoICA8LSAgYXMoZGlyaWNobGV0KGFzLnBwcChwcmVjaXAyKSksICJTcGF0aWFsUG9seWdvbnMiKQ0KYGBgDQpgYGB7cn0NCmNycyh0aCkgPC0gY3JzKHByZWNpcDIpDQpjcnMoY2FxdWV0YTIpIDwtIGNycyhwcmVjaXAyKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpjcnModGgpIA0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpjcnMocHJlY2lwMikNCmBgYA0KDQpgYGB7ciBlY2hvID0gRkFMU0V9DQp0aC56ICAgICA8LSBvdmVyKHRoLCBwcmVjaXAyLCBmbj1tZWFuKQ0KdGguc3BkZiAgPC0gIFNwYXRpYWxQb2x5Z29uc0RhdGFGcmFtZSh0aCwgdGgueikgICANCmBgYA0KDQpgYGB7ciBlY2hvID0gRkFMU0V9DQp0aC5jbHAgICA8LSByYXN0ZXI6OmludGVyc2VjdChjYXF1ZXRhMix0aC5zcGRmKQ0KYGBgDQpNYXBhDQpgYGB7ciBlY2hvID0gRkFMU0V9DQp0bV9zaGFwZSh0aC5jbHApICsgDQogIHRtX3BvbHlnb25zKGNvbD0iTGx1dmlhIiwgcGFsZXR0ZT0iUmRCdSIsIG1pZHBvaW50PTMuMCwNCiAgICAgICAgICAgICAgdGl0bGU9IlBvbMOtZ29ub3MgZGUgVGhpZXNzZW4gXG4gUHJlY2lwaXRhY2nDs24gcHJldmlzdGEgXG4oaW4gbW0pIikgKw0KICB0bV9sZWdlbmQobGVnZW5kLm91dHNpZGU9VFJVRSkNCmBgYA0KRmlndXJhIDExLiBNYXBhIGRlIHBvbMOtZ29ub3MgZGUgVGhpZXNzZW4uIA0KIyMjIyBJbnRlcnBvbGFjacOzbiBwb25kZXJhZGEgZGUgZGlzdGFuY2lhIGludmVyc2EgKElEVykuDQpMYSBmdW5jacOzbiBJRFcgZXN0w6EgcHJlc2VudGUgZW4gZG9zIHBhcXVldGVzIHNwYXRzdGF0IHkgZ3N0YXQuIFNlIGRlYmUgY3JlYXIgcHJpbWVybyB1bmEgZ3JpbGxhIGNvbiBjZWxkYXMgcXVlIGHDum4gbm8gdGllbmVuIHZhbG9yZXMsIGVzYSBncmlsbGEgdGllbmUgMTAwLjAwMCBjZWxkYXMsIGxhcyBjdWFsZXMgdmFuIGEgY3VicmlyIHVuIHRlcnJpdG9yaW8gZGV0ZXJtaW5hZG8sIGVzdGUgw7psdGltbyBzZXLDoSBlbCByw6FzdGVyIGRlIHNhbGlkYS4gDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpncmQgICAgICAgICAgICAgIDwtIGFzLmRhdGEuZnJhbWUoc3BzYW1wbGUocHJlY2lwMiwgInJlZ3VsYXIiLCBuPTcwMDAwKSkNCm5hbWVzKGdyZCkgICAgICAgPC0gYygiWCIsICJZIikNCmNvb3JkaW5hdGVzKGdyZCkgPC0gYygiWCIsICJZIikNCmdyaWRkZWQoZ3JkKSAgICAgPC0gVFJVRSAgDQpmdWxsZ3JpZChncmQpICAgIDwtIFRSVUUgIA0KDQpwcm9qNHN0cmluZyhncmQpIDwtIHByb2o0c3RyaW5nKHByZWNpcDIpDQoNClAuaWR3IDwtIGdzdGF0OjppZHcoTGx1dmlhIH4gMSwgcHJlY2lwMiwgbmV3ZGF0YT1ncmQsIGlkcD0yLjApDQoNCnIgICAgICAgPC0gcmFzdGVyKFAuaWR3KQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpyDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCmNhcXVldGEyDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnIubSAgIDwtIHJhc3Rlcjo6bWFzayhyLCBjYXF1ZXRhMikNCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0Kci5tIA0KYGBgDQpQbG90ZWFyLg0KYGBge3J9DQp0bV9zaGFwZShyLm0pICsgDQogIHRtX3Jhc3RlcihuPTgscGFsZXR0ZSA9ICJSZEJ1IiwgYXV0by5wYWxldHRlLm1hcHBpbmcgPSBGQUxTRSwNCiAgICAgICAgICAgIHRpdGxlPSJEaXN0YW5jaWEgSW52ZXJzYSBQb2RlcmFkYVxuUHJlY2lwaXRhY2nDs24gcHJldmlzdGFcbihlbiBtbSkiKSArIA0KICB0bV9zaGFwZShwcmVjaXAyKSArIHRtX2RvdHMoc2l6ZT0wLjIpICsNCiAgdG1fbGVnZW5kKGxlZ2VuZC5vdXRzaWRlPVRSVUUpDQpgYGANCkZpZ3VyYSAxMi4gTWFwYSBkZSBJRFcgc2luIGxhIHZpc3RhIGRlIGxvcyB2YWxvcmVzLiANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCmxpYnJhcnkobGVhZmxldCkNCmxpYnJhcnkoUkNvbG9yQnJld2VyKQ0KYGBgDQpgYGB7cn0NCnBhbCA8LSBjb2xvck51bWVyaWMoYygicmVkIiwgIm9yYW5nZSIsICJ5ZWxsb3ciLCAiYmx1ZSIsICJkYXJrYmx1ZSIpLCB2YWx1ZXMocHJlY2lwLm1hc2spLA0KICBuYS5jb2xvciA9ICJ0cmFuc3BhcmVudCIpDQoNCmxlYWZsZXQoKSAlPiUgYWRkVGlsZXMoKSAlPiUNCiAgYWRkUmFzdGVySW1hZ2Uoci5tLCBjb2xvcnMgPSBwYWwsIG9wYWNpdHkgPSAwLjYpICU+JQ0KICBhZGRMZWdlbmQocGFsID0gcGFsLCB2YWx1ZXMgPSB2YWx1ZXMoci5tKSwNCiAgICB0aXRsZSA9ICJQcmVjaXBpdGFjacOzbiBpbnRlcnBvbGFkYSBJRFcgZW4gQ2FxdWV0w6FcbiBkZXNkZSAxOC8wNS8yMDIwIGhhc3RhIDIzLzA1LzIwMjAgZW4gW21tXSIpDQpgYGANCkZpZ3VyYSAxMy4gTWFwYSBkZSBpbnRlcnBvbGFjacOzbiBJRFcgZGUgcHJlY2lwaXRhY2nDs24uIA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KcHJlY2lwMg0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpQIDwtIHByZWNpcDINCmBgYA0KYGBge3IgZWNobyA9IEZBTFNFfQ0KSURXLm91dCA8LSB2ZWN0b3IobGVuZ3RoID0gbGVuZ3RoKFApKQ0KYGBgDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpmb3IgKGkgaW4gMTpsZW5ndGgoUCkpIHsNCiAgSURXLm91dFtpXSA8LSBnc3RhdDo6aWR3KExsdXZpYSB+IDEsIFBbLWksXSwgUFtpLF0sIGlkcD0yLjApJHZhcjEucHJlZH0NCmBgYA0KQ8OhbGN1bGFyIGVsIGVycm9yIGVuIGxvcyBkYXRvcyBpbnRlcnBvbGFkb3MuIA0KYGBge3J9DQpPUCA8LSBwYXIocHR5PSJzIiwgbWFyPWMoNCwzLDAsMCkpDQogIHBsb3QoSURXLm91dCB+IFAkTGx1dmlhLCBhc3A9MiwgeGxhYj0iT2JzZXJ2YWRhIiwgeWxhYj0iUHJldmlzdGEiLCBwY2g9MTYsDQogICAgICAgY29sPXJnYigwLDAsMCwwLjUpKQ0KICBhYmxpbmUobG0oSURXLm91dCB+IFAkTGx1dmlhKSwgY29sPSJyZWQiLCBsdz0yLGx0eT0yKQ0KICBhYmxpbmUoMCwxKQ0KYGBgDQpHcsOhZmljbyAzLiBTZW1pdmFyaW9ncmFtYSANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCnBhcihPUCkNCmBgYA0KRXJyb3IgbWVkaW8gY3VhZHLDoXRpY28uDQpgYGB7cn0NCnNxcnQoIHN1bSgoSURXLm91dCAtIFAkTGx1dmlhKV4yKSAvIGxlbmd0aChQKSkNCmBgYA0KVmFsaWRhY2nDs24gY3J1emFkYS4gDQpgYGB7ciBlY2hvID0gRkFMU0V9DQppbWcgPC0gZ3N0YXQ6OmlkdyhMbHV2aWF+MSwgUCwgbmV3ZGF0YT1ncmQsIGlkcD0yLjApDQpuICAgPC0gbGVuZ3RoKFApDQpaaSAgPC0gbWF0cml4KG5yb3cgPSBsZW5ndGgoaW1nJHZhcjEucHJlZCksIG5jb2wgPSBuKQ0KDQpzdCA8LSBzdGFjaygpDQpmb3IgKGkgaW4gMTpuKXsNCiAgWjEgPC0gZ3N0YXQ6OmlkdyhMbHV2aWF+MSwgUFstaSxdLCBuZXdkYXRhPWdyZCwgaWRwPTEuMCkNCiAgc3QgPC0gYWRkTGF5ZXIoc3QscmFzdGVyKFoxLGxheWVyPTEpKQ0KICAgWmlbLGldIDwtIG4gKiBpbWckdmFyMS5wcmVkIC0gKG4tMSkgKiBaMSR2YXIxLnByZWR9DQoNClpqIDwtIGFzLm1hdHJpeChhcHBseShaaSwgMSwgc3VtLCBuYS5ybT1UKSAvIG4gKQ0KYzEgPC0gYXBwbHkoWmksMiwnLScsWmopICAgICAgICAgIA0KYzEgPC0gYXBwbHkoYzFeMiwgMSwgc3VtLCBuYS5ybT1UICkNCg0KQ0kgPC0gc3FydCggMS8obioobi0xKSkgKiBjMSkNCg0KaW1nLnNpZyAgIDwtIGltZw0KaW1nLnNpZyR2IDwtIENJIC9pbWckdmFyMS5wcmVkIA0KYGBgDQoNCmBgYHtyfQ0KciA8LSByYXN0ZXIoaW1nLnNpZywgbGF5ZXI9InYiKQ0Kci5tIDwtIHJhc3Rlcjo6bWFzayhyLCBjYXF1ZXRhMikNCg0KdG1fc2hhcGUoci5tKSArIHRtX3Jhc3RlcihuPTgsdGl0bGU9IklEV1xuOTUlIGludGVydmFsbyBkZSBjb25maWFuemEgXG4oZW4gbW0pIikgKw0KICB0bV9zaGFwZShQKSArIHRtX2RvdHMoc2l6ZT0wLjIpICsNCiAgDQogIHRtX2xlZ2VuZChsZWdlbmQub3V0c2lkZT1UUlVFKQ0KYGBgDQpGaWd1cmEgMTQuIE1hcGEgZGUgaW50ZXJ2YWxvIGRlIGNvbmZpYW56YSBkZSA5NSUgZGVsIG1vZGVsbyBkZSBpbnRlcnBvbGFjacOzbi4gDQpgYGB7ciBlY2hvID0gRkFMU0V9DQojIERlZmluZSB0aGUgMXN0IG9yZGVyIHBvbHlub21pYWwgZXF1YXRpb24NCmYuMSA8LSBhcy5mb3JtdWxhKExsdXZpYSB+IFggKyBZKSANCiANCiMgQWRkIFggYW5kIFkgdG8gUA0KUCRYIDwtIGNvb3JkaW5hdGVzKFApWywxXQ0KUCRZIDwtIGNvb3JkaW5hdGVzKFApWywyXQ0KDQojIFJ1biB0aGUgcmVncmVzc2lvbiBtb2RlbA0KbG0uMSA8LSBsbSggZi4xLCBkYXRhPVApDQoNCiMgVXNlIHRoZSByZWdyZXNzaW9uIG1vZGVsIG91dHB1dCB0byBpbnRlcnBvbGF0ZSB0aGUgc3VyZmFjZQ0KZGF0LjFzdCA8LSBTcGF0aWFsR3JpZERhdGFGcmFtZShncmQsIGRhdGEuZnJhbWUodmFyMS5wcmVkID0gcHJlZGljdChsbS4xLCBuZXdkYXRhPWdyZCkpKSANCmBgYA0KDQpgYGB7ciBlY2hvID0gRkFMU0V9DQojIENsaXAgdGhlIGludGVycG9sYXRlZCByYXN0ZXIgdG8gVGV4YXMNCnIgICA8LSByYXN0ZXIoZGF0LjFzdCkNCnIubSA8LSByYXN0ZXI6Om1hc2sociwgY2FxdWV0YTIpDQoNCiMgUGxvdCB0aGUgbWFwDQp0bV9zaGFwZShyLm0pICsgDQogIHRtX3Jhc3RlcihuPTEwLCBwYWxldHRlPSJSZEJ1IiwgYXV0by5wYWxldHRlLm1hcHBpbmc9RkFMU0UsIA0KICAgICAgICAgICAgdGl0bGU9IjFzdCBvcmRlciBwb2xpbm9taWFsIGZpciBcblByZWRpY3RlZCBwcmVjaXBpdGF0aW9uIFxuKGluIG1tKSIpICsNCiAgdG1fc2hhcGUoUCkgKyB0bV9kb3RzKHNpemU9MC4yKSArDQogIHRtX2xlZ2VuZChsZWdlbmQub3V0c2lkZT1UUlVFKQ0KYGBgDQojIyMgS3JpZ2luZw0KYGBge3IgZWNobyA9IEZBTFNFfQ0KIyBEZWZpbmUgdGhlIDFzdCBvcmRlciBwb2x5bm9taWFsIGVxdWF0aW9uDQpmLjEgPC0gYXMuZm9ybXVsYShMbHV2aWEgfiBYICsgWSkgDQoNCiMgQ29tcHV0ZSB0aGUgc2FtcGxlIHZhcmlvZ3JhbTsgbm90ZSB0aGF0IHRoZSBmLjEgdHJlbmQgbW9kZWwgaXMgb25lIG9mIHRoZQ0KIyBwYXJhbWV0ZXJzIHBhc3NlZCB0byB2YXJpb2dyYW0oKS4gVGhpcyB0ZWxscyB0aGUgZnVuY3Rpb24gdG8gY3JlYXRlIHRoZSANCiMgdmFyaW9ncmFtIG9uIHRoZSBkZS10cmVuZGVkIGRhdGEuDQp2YXIuc21wbCA8LSB2YXJpb2dyYW0oZi4xLCBQLCBjbG91ZCA9IEZBTFNFLCBjdXRvZmY9MTAwMDAwLCB3aWR0aD04OTkwKQ0KDQojIENvbXB1dGUgdGhlIHZhcmlvZ3JhbSBtb2RlbCBieSBwYXNzaW5nIHRoZSBudWdnZXQsIHNpbGwgYW5kIHJhbmdlIHZhbHVlcw0KIyB0byBmaXQudmFyaW9ncmFtKCkgdmlhIHRoZSB2Z20oKSBmdW5jdGlvbi4NCmRhdC5maXQgIDwtIGZpdC52YXJpb2dyYW0odmFyLnNtcGwsIGZpdC5yYW5nZXMgPSBUUlVFLCBmaXQuc2lsbHMgPSBUUlVFLA0KICAgICAgICAgICAgICAgICAgICAgICAgICB2Z20ocHNpbGw9MywgbW9kZWw9Ik1hdCIsIHJhbmdlPTE1MDAwMCwgbnVnZ2V0PTAuMCkpDQoNCiMjIG1vZGVsIGNhbiBiZSBFeHAsIEdhdSwgU3BoLCBNYXQNCiMjIFNlZSBnc3RhdCBwYWNrYWdlIC0gdmdtIGZ1bmN0aW9uIC0gdG8gZ2V0IHRoZSBuYW1lcyBvZiB0aGVzZSBtb2RlbHMNCiMjIFJldmlldyBrcmlnaW5nIHRoZW9yeSB0byB1bmRlcnN0YW5kIHRoZWlyIG1lYW5pbmcNCmBgYA0KDQpgYGB7ciBlY2hvID0gRkFMU0V9DQpkYXQuZml0DQpgYGANCg0KYGBge3J9DQojIFRoZSBmb2xsb3dpbmcgcGxvdCBhbGxvd3MgdXMgdG8gYXNzZXNzIHRoZSBmaXQNCnBsb3QodmFyLnNtcGwsIGRhdC5maXQsIHhsaW09YygwLDEzMDAwMCkpDQpgYGANCkdyw6FmaWNvIDQuIFNlbWl2YXJpb2dyYW1hLg0KYGBge3IgZWNobyA9IEZBTFNFfQ0KIyBEZWZpbmUgdGhlIHRyZW5kIG1vZGVsDQpmLjEgPC0gYXMuZm9ybXVsYShMbHV2aWEgfiBYICsgWSkgDQoNCiMgUGVyZm9ybSB0aGUga3JpZ2UgaW50ZXJwb2xhdGlvbiAobm90ZSB0aGUgdXNlIG9mIHRoZSB2YXJpb2dyYW0gbW9kZWwNCiMgY3JlYXRlZCBpbiB0aGUgZWFybGllciBzdGVwKQ0KZGF0LmtyZyA8LSBrcmlnZSggZi4xLCBQLCBncmQsIGRhdC5maXQpDQpgYGANCmBgYHtyIGVjaG8gPSBGQUxTRX0NCiMgQ29udmVydCBrcmlnZWQgc3VyZmFjZSB0byBhIHJhc3RlciBvYmplY3QgZm9yIGNsaXBwaW5nDQpyIDwtIHJhc3RlcihkYXQua3JnKQ0Kci5tIDwtIHJhc3Rlcjo6bWFzayhyLCBjYXF1ZXRhMikNCmBgYA0KYGBge3J9DQpyLm0NCmBgYA0KTWFwYS4NCmBgYHtyfQ0KIyBQbG90IHRoZSBtYXANCnRtX3NoYXBlKHIubSkgKyANCiAgdG1fcmFzdGVyKG49MTAsIHBhbGV0dGU9IlJkQnUiLCBhdXRvLnBhbGV0dGUubWFwcGluZz1GQUxTRSwgDQogICAgICAgICAgICB0aXRsZT0iS3JpZ2luZyBVbml2ZXJzYWxcblByZWNpcGl0YWNpw7NuIHByZXZpc3RhIFxuKGVuIG1tKSIpICsNCiAgdG1fc2hhcGUoUCkgKyB0bV9kb3RzKHNpemU9MC4yKSArDQogIHRtX2xlZ2VuZChsZWdlbmQub3V0c2lkZT1UUlVFKQ0KYGBgDQpGaWd1cmEgMTUuIE1hcGEgZGUga3JpZ2luZyBkZSBwcmVjaXBpdGFjacOzbi4gDQpgYGB7cn0NCmxpYnJhcnkobGVhZmxldCkNCmxpYnJhcnkoUkNvbG9yQnJld2VyKQ0KcGFsIDwtIGNvbG9yTnVtZXJpYyhjKCJyZWQiLCAib3JhbmdlIiwgInllbGxvdyIsICJibHVlIiwgImRhcmtibHVlIiksIHZhbHVlcyhwcmVjaXAubWFzayksDQogIG5hLmNvbG9yID0gInRyYW5zcGFyZW50IikNCg0KbGVhZmxldCgpICU+JSBhZGRUaWxlcygpICU+JQ0KICBhZGRSYXN0ZXJJbWFnZShyLm0sIGNvbG9ycyA9IHBhbCwgb3BhY2l0eSA9IDAuNikgJT4lDQogIGFkZExlZ2VuZChwYWwgPSBwYWwsIHZhbHVlcyA9IHZhbHVlcyhyLm0pLA0KICAgIHRpdGxlID0gIktyaWdpbmcgUHJlY2lwaXRhY2nDs24gSW50ZXJwb2xhZGEgZW4gQ2FxdWV0w6FcbiBkZXNkZSAxOC8wNS8yMDIwIGhhc3RhIDIzLzA1LzIwMjAgW21tXSIpDQpgYGANCkZpZ3VyYSAxNi4gTWFwYSBpbnRlcmFjdGl2byBLcmlnaW5nIGRlIGxhIHByZWNpcGl0YWNpw7NuIGludGVycG9sYWRhLiANCkdlbmVyYXIgbG9zIG1hcGFzIGRlIHZhcmlhbnphIGUgaW50ZXJ2YWxvIGRlIGNvbmZpYW56YS4NCmBgYHtyfQ0KciAgIDwtIHJhc3RlcihkYXQua3JnLCBsYXllcj0idmFyMS52YXIiKQ0Kci5tIDwtIHJhc3Rlcjo6bWFzayhyLCBjYXF1ZXRhMikNCg0KdG1fc2hhcGUoci5tKSArIA0KICB0bV9yYXN0ZXIobj01LCBwYWxldHRlID0iUmVkcyIsDQogICAgICAgICAgICB0aXRsZT0iSW50ZXJwb2xhY2nDs24gZGUgS3JpZ2luZ1xuTWFwYSBkZSB2YXJpYWNpw7NuIFxuKGVuIHNxdWFyZWQgbW0pIikgK3RtX3NoYXBlKFApICsgdG1fZG90cyhzaXplPTAuMikgKw0KICB0bV9sZWdlbmQobGVnZW5kLm91dHNpZGU9VFJVRSkNCmBgYA0KRmlndXJhIDE3LiBNYXBhIGRlIHZhcmlhY2nDs24gZW4gS3JpZ2luZy4gDQpgYGB7cn0NCnIgICA8LSBzcXJ0KHJhc3RlcihkYXQua3JnLCBsYXllcj0idmFyMS52YXIiKSkgKiAxLjk2DQpyLm0gPC0gcmFzdGVyOjptYXNrKHIsIGNhcXVldGEyKQ0KDQp0bV9zaGFwZShyLm0pICsgDQogIHRtX3Jhc3RlcihuPTUsIHBhbGV0dGUgPSJSZWRzIiwNCiAgICAgICAgICAgIHRpdGxlPSJJbnRlcnBvbGFjacOzbiBLcmlnaW5nXG4gTWFwYSBkZSBpbnRlcnZhbG8gZGUgY29uZmlhbnphIGFsIDk1JSBcbihlbiBtbSkiKSArdG1fc2hhcGUoUCkgKyB0bV9kb3RzKHNpemU9MC4yKSArDQogIHRtX2xlZ2VuZChsZWdlbmQub3V0c2lkZT1UUlVFKQ0KYGBgDQpGaWd1cmEgMTguIE1hcGEgZGUgaW50ZXJ2YWxvIGRlIGNvbmZpYW56YSBkZSBrcmlnaW5nLiANCmBgYHtyID0gRkFMU0V9DQpzZXNzaW9uSW5mbygpDQpgYGANCiMjIEFuw6FsaXNpcyBkZSByZXN1bHRhZG9zDQpFbiBiYXNlIGEgbG9zIHJlc3VsdGFkb3MgYW50ZXJpb3Jlcywgc2UgcHVlZGUgdmVyIHF1ZSBsb3MgbcOpdG9kb3MgcGFyYSBsYSBpbnRlcnBvbGFjacOzbiBkZSBkYXRvcyBwcmVzZW50YW4gZGlmZXJlbmNpYXMgeSB1bm9zIHNvbiBtZWpvcmVzIHF1ZSBvdHJvcyBkZXBlbmRpZW5kbyBkZWwgdGlwbyBkZSB2YXJpYWJsZSBxdWUgc2UgcXVpZXJhIGVzdHVkaWFyLiBUYW1iacOpbiBwcmVzZW50YW4gZGlmZXJlbmNpYXMgZW4gY3VhbnRvIGEgbGEgbWFuZXJhIGRlIGNhbGN1bGFybG9zLCBkZSB0b21hciBsYXMgbWVkaWRhcywgY3JlYWNpw7NuIGRlIGxhcyBlc3RydWN0dXJhcyB5IHJlc29sdWNpw7NuIGRlIGxvcyBtYXBhcy4gDQoNCkVuIGxhcyBmaWd1cmFzIDcgeSA4IHNlIHB1ZWRlIGFwcmVjaWFyIHVuYSB2aXN0YSBkZWwgZGVwYXJ0YW1lbnRvIGRlIGNhcXVldMOhLCBzZSBwdWVkZSB2ZXIgdW5hIGNhcGEgcsOhc3RlciBjb21wdWVzdGEgZGUgdmFyaWFzIGNlbGRhcyBkZSBkaWZlcmVudGVzIGNvbG9yZXMsIGRvbmRlIGNhZGEgY29sb3IgcmVwcmVzZW50YSBsYSBjYW50aWRhZCBkZSBwcmVjaXBpdGFjacOzbiBlbiBtaWzDrW1ldHJvcyAobW0pIHF1ZSB0dXZvIGVsIGRlcGFydGFtZW50bywgZG9uZGUgbG9zIG11bmljaXBpb3MgZGUgQ2FydGFnZW5hIGRlbCBDaGFpcmEsIFNhbiBKb3PDqSBkZWwgRnJhZ3VhLCBWYWxwYXJhw61zbyB5IE1pbGFuIGZ1ZXJvbiBsb3MgcXVlIHByZXNlbnRhcm9uIG1heW9yIHByZWNpcGl0YWNpw7NuLCBhIGNvbXBhcmFjacOzbiBkZSBsb3MgbXVuaWNpcGlvcyBkZSBFbCBQYXVqaWwsIEZsb3JlbmNpYSB5IFNhbiBWaWNlbnRlIGRlbCBDYWd1w6FuLCBkb25kZSBzdXMgbml2ZWxlcyBkZSBwcmVjaXBpdGFjacOzbiBmdWVyb24gbWVub3Jlcy4gRW4gYW1ib3MgbWFwYXMgc2UgcHVlZGVuIHZlciB1bmEgc2VyaWUgZGUgY2VsZGFzIGRlIGZvcm1hIGN1YWRyYWRhIGN1eWEgcmVzb2x1Y2nDs24gZXMgZGUgMC4yICogMC4yLiAgQWxndW5hcyBkaWZlcmVuY2lhcyBlbnRyZSBhbWJvcyBtYXBhcyBlcyBxdWUgZWwgZGUgbGEgZmlndXJhIDcgdGllbmUgdW5hIHZpc3RhIGRlbCBkZXBhcnRhbWVudG8gc29uIGxvcyBsw61taXRlcyBkZSBjYWRhIHVubyBkZSBzdXMgbXVuaWNpcGlvcywgbm8gZXMgaW50ZXJhY3Rpdm8geSBzdSBjb2xvciBkZSBjZWxkYXMgdmFyw61hIGRlIHJvam8gYSB2ZXJkZTsgbWllbnRyYXMgcXVlIGVsIG1hcGEgZGUgbGEgZmlndXJhIDggZXMgaW50ZXJhY3Rpdm8gKE9wZW5TdHJlZXRNYXApIHkgIG3DoXMgZGV0YWxsYWRvLCBwZXJtaXRlIGlkZW50aWZpY2FyIGVsIGRlcGFydGFtZW50byBkZXNkZSB1bmEgdmlzdGEgZGVsIG1hcGEgZGUgQ29sb21iaWEsIGVuIGVsIHF1ZSBzZSBwdWVkZW4gYXByZWNpYXIgY29uIGN1w6FsZXMgZGVwYXJ0YW1lbnRvcyBsaW1pdGEsIHVuYSB2aXN0YSBzaW1wbGUgZGUgbGFzIHpvbmFzIGVuIGxhcyBxdWUgaGF5IHByZXNlbmNpYSBkZSB2ZWdldGFjacOzbiwgbWFuZWphIHVuYSBwYWxldGEgZGUgY29sb3IgcXVlIHZhIGRlbCByb2pvIGFsIGF6dWwgeSBubyBtdWVzdHJhIGxvcyBsw61taXRlcyBlbnRyZSBzdXMgbXVuaWNpcGlvcy4gTGEgcmVzb2x1Y2nDs24gZGUgbGFzIGNlbGRhcyBxdWUgcHJlc2VudGFuLCBubyBlcyBtdXkgcHJlY2lzYSwgc2luIGVtYmFyZ28gc2UgdHJhYmFqw7MgY29uIGVzdGEgcmVzb2x1Y2nDs24gZGViaWRvIGEgcXVlIG3DoXMgYWRlbGFudGUgc2UgcmVxdWVyaXLDoSwgcGFyYSBsYSB2aXN0YSBkZSBsb3MgbWFwYXMsIHB1bnRvcyBubyB0YW4gY29uY2VudHJhZG9zLiBSZXF1aXJpw7MgaGFjZXIgdmFyaWFzIG9wZXJhY2lvbmVzIHBhcmEgdm9sdmVyIGxvcyBkYXRvcyBlc3BhY2lhbGVzLiBFbiBsYSBmaWd1cmEgOSBzZSBwdWVkZW4gYXByZWNpYXIgbGFzIGNlbGRhcyBkZSBsYSBjYXBhIHJhc3RlciBjb24gdW4gcHVudG8gY29sb3IgbW9yYWRvIGVuIGVsIGNlbnRybyBkZSBjYWRhIHVuYSwgZXN0b3Mgc2Vyw6FuIGxvcyBwdW50b3MgcGFyYSBoYWNlciBsYSBpbnRlcnBvbGFjacOzbi4gDQoNCkxvcyBkYXRvcyB0YW1iacOpbiBzZSB0cmFiYWphcm9uIHBvciBtZWRpbyBkZWwgZm9ybWF0byBHZW9qc29uLCBlbCBjdWFsIGVzdMOhIGRpc2XDsWFkbyBwYXJhIGdlbmVyYXIsIHZpc3VhbGl6YXIgeSBlZGl0YXIgZGF0b3MgZ2VvZ3LDoWZpY29zIChnZW9kYXRvcylHZW9Kc29uLmlvIGVzIHVuYSBoZXJyYW1pZW50YSBww7pibGljYSB5IHZpcnR1YWwgcXVlIHBlcm1pdGUgaW1wb3J0YXIgeSBleHBvcnRhciBnZW9kYXRvcywgeSB1bmEgZGUgc3VzIGZ1bmNpb25lcyBlcyByZXByb3llY3RhciBjYXBhcyBkZSBnZW9kYXRvcyAoVmlsb3JpYSwgcy5mKS4gIExvcyBwdW50b3MgZnVlcm9uIHBhc2Fkb3MgYSBwb2zDrWdvbm9zIGNvbiBlbCBmaW4gZGUgY29udmVydGlyIGxhIGNhcmFjdGVyw61zdGljYSBwcmVjaXBpdGFjacOzbiBlbiB1biBtYXJjbyBkZSBkYXRvcyBlc3BhY2lhbC4gVmFsZSBhY2xhcmFyIHF1ZSBsb3MgdmFsb3JlcyBkZSBsb3MgZGF0b3MgZGUgcHJlY2lwaXRhY2nDs24gcHJlc2VudGFyb24gbXVjaGFzIGNpZnJhcyBkZWNpbWFsZXMsIGxvIHF1ZSBkaWZpY3VsdGEgbGEgdmlzdWFsaXphY2nDs24gZGUgbG9zIHB1bnRvcyBlbiBlbCBtYXBhLCAgcGFyYSBlbGxvIGZ1ZSBuZWNlc2FyaW8gcmVkb25kZWFyIGxhcyBjaWZyYXMgcGFyYSBxdWUgYXBhcmVjaWVyYSBzb2xvIHVuIGRlY2ltYWwuIA0KDQpMYSBmaWd1cmEgOSByZXByZXNlbnRhIGVsIG1hcGEgZGUgQ2FxdWV0w6EgY29uIGludGVydmFsb3MgZGUgcHJlY2lwaXRhY2nDs24gZGUgMTAgbW0uIENhZGEgcHVudG8gcmVwcmVzZW50YSBlbCBuaXZlbCBkZSBwcmVjaXBpdGFjacOzbiBtdWVzdHJlYWRhIGVuIGNhZGEgdW5vIGRlIGxvcyBwdW50b3MsIHZhcmlhbmRvIGRlIGJsYW5jbyBjbGFybyBhIG9zY3VybywgZG9uZGUgYSBtYXlvciBuaXZlbCBkZSBwcmVjaXBpdGFjacOzbiwgbGEgdG9uYWxpZGFkIGF6dWwgZGUgY2FkYSBwdW50byBzZSB2YSB0b3JuYW5kbyBtw6FzIG9zY3VyYS4gIExvcyBwb2zDrWdvbm9zIGRlIFRoaWVzc2VuIHNlIHB1ZWRlbiBhcHJlY2lhciBlbiBsYSBmaWd1cmEgMTEgcG9sw61nb25vcyBjdWFkcmFkb3MsIGVzdG8gZGViaWRvIGEgcXVlIGxhIHBvc2ljacOzbiBkZSBzdXMgcHVudG9zIHRpZW5lIGxhIG1pc21hIGRpc3RhbmNpYSBlbiBlbCBlamUgWCB5IFkuIExvcyBwb2zDrWdvbm9zIGZvcm1hZG9zIGVuIGVzdGUgbWFwYSBubyBjdW1wbGVuIGVsIHByb3DDs3NpdG8gZGUgZXN0ZSBlc3RlIG3DqXRvZG8geWEgcXVlIGxvcyBwb2zDrWdvbm9zIGVzdMOhbiBkaXN0cmlidWlkb3MgZGUgZm9ybWEgcmVndWxhciwgZW50b25jZXMgbm8gcHJvcG9yY2lvbmEgdW5hIGluZm9ybWFjacOzbiBjbGFyYSByZXNwZWN0byBkZSBsYSBsbHV2aWEgZW4gZWwgZGVwYXJ0YW1lbnRvLiBBbGdvIHF1ZSBzZSBwdWVkZSBkZWR1Y2lyIGRlbCBtYXBhIGVzIHF1ZSBlc3RlIGRlcGFydGFtZW50byBwcmVzZW50YSBwcmVjaXBpdGFjaW9uZXMgcXVlIGN1YnJlbiB0b2RhIGxhIHpvbmEsIGVzdG8gZW4gY29uY29yZGFuY2lhIGNvbiBsb3MgbWFwYXMgYW50ZXJpb3Jlcy4gDQoNCkxhIGludGVycG9sYWNpw7NuIGRlIGRpc3RhbmNpYSBpbnZlcnNhIChJRFcpIHNlIHB1ZWRlIGFwcmVjaWFyIGVuIGxhIGZpZ3VyYSAxMiwgZG9uZGUgc2UgdmVuIGNlbGRhcyByw6FzdGVyIHF1ZSBlc3TDoW4gc29icmVwdWVzdGFzIGVuIGxvcyBwdW50b3MgZGUgbXVlc3RyZW8sIHNpbiBlbWJhcmdvIG5vIHNlIHZlIGxhIHByZXNlbmNpYSBkZSBsb3MgdmFsb3JlcyAoZXhwcmVzYWRvcyBlbiBuw7ptZXJvcykgc29icmUgbG9zIHB1bnRvcy4gUHJlc2VudGEgdW5hIHBhbGV0YSBkZSBjb2xvcmVzIHF1ZSB2YXLDrWEgZW50cmUgZWwgcm9qbyB5IGVsIGF6dWwsIGRvbmRlIGxvcyB2YWxvcmVzIG3DoXMgY2VyY2Fub3MsIGVzdMOhbiBtw6FzIHJlbGFjaW9uYWRvcyBjb24gbGEgdmFyaWFibGUsIHF1ZSBlcyBsYSBwcmVjaXBpdGFjacOzbiwgZXMgZGVjaXIgcXVlIGxvcyBwdW50b3MgbcOhcyBjZXJjYW5vcyBjb21wYXJ0ZW4gY2FyYWN0ZXLDrXN0aWNhcyBzaW1pbGFyZXMgYSBkaWZlcmVuY2lhIGRlIGxvcyBwdW50b3MgbGVqYW5vcy4gTG8gYW50ZXJpb3Igc2UgcHVlZGUgdmVyIHJlZmxlamFkbyBlbiBlbCBhZ3J1cGFtaWVudG8gZGUgcHVudG9zIHBvciBjb2xvcmVzIHF1ZSB2YXLDrWFuIGVudHJlIHRvbmFsaWRhZGVzIGF6dWxlcyB5IHJvamFzLCB1bmFzIG3DoXMgY2xhcmFzIGNsYXJhcyB5IG90cmFzIG9zY3VyYXMsIGNhZGEgYWdydXBhbWllbnRvIHNpZ25pZmljYSBxdWUgbG9zIHB1bnRvcyBxdWUgc2UgZW5jdWVudHJhbiBkZW50cm8gZGVsIG1pc21vIGNvbXBhcnRlbiBjYXJhY3RlcsOtc3RpY2FzIHNpbWlsYXJlcy4gUG9yIGVqZW1wbG8gIHNlIHB1ZWRlbiB2ZXIgdG9uYWxpZGFkZXMgYXp1bGVzIG9zY3VyYXMgZW4gbGEgem9uYSBhIGxhIHF1ZSBwZXJ0ZW5lY2VuIGxvcyBtdW5pY2lwaW9zIGRlIENhcnRhZ2VuYSBkZWwgQ2hhaXJhLCBTb2xhbm8geSBNaWzDoW4sIHByZXNlbnRhbmRvIG1heW9yZXMgcHJlY2lwaXRhY2lvbmVzIGVuIGVzdGEgem9uYSwgZWwgbG9zIHB1bnRvcyBxdWUgc2UgZW5jdWVudHJhbiBhZ3J1cGFkb3MgZW4gZWwgY29sb3IgYXp1bCBvc2N1cm8sIHRpZW5lbiBlbiBjb23Dum4gcXVlIGhheSBwcmVjaXBpdGFjaW9uZXMgZnVlcnRlIGFsbMOtLCB5IGEgbWVkaWRhIHF1ZSBzZSB2YW4gYWxlamFuZG8sIGxvcyBwdW50b3Mgc2UgdmFuIGFncnVwYW5kbyBlbiBjb2xvcmFjaW9uZXMgbcOhcyBjbGFyYXMsIGxvIHF1ZSBzaWduaWZpY2EgcXVlIGNvbXBhcnRlbiBsYSBjYXJhY3RlcsOtc3RpY2EgZGUgcXVlIGhheSBwcmVjaXBpdGFjaW9uZXMsIHBlcm8gbcOhcyBsZXZlcy4gIExvcyBhZ3J1cGFtaWVudG9zIGRlIGNvbG9yIHJvaml6bywgc2lnbmlmaWNhbiBxdWUgbG9zIHB1bnRvcyBjb250ZW5pZG9zIGFow60sIGNvbXBhcnRlbiBsYSBjYXJhY3RlcsOtc3RpY2EgZGUgdW5hIGJhamEgcHJlY2lwaXRhY2nDs24sIHBlcnRlbmVjaWVuZG8gYSBsb3MgbXVuaWNpcGlvcyBkZSBGbG9yZW5jaWEsIEJlbMOpbiBkZSBsb3MgQW5kYXF1w61lcywgdW5hIHBhcnRlIGRlIFNhbiBWaWNlbnRlIGRlbCBDYWd1w6FuIHkgZWwgc3VyIGRlbCBtdW5pY2lwaW8gZGUgU29sYW5vLiBMYSBmaWd1cmEgMTMgcHJlc2VudGEgdW5hIHZpc2nDs24gbcOhcyBkZXRhbGxhZGEgZGVsIG1hcGEsIGNvbiBsYXMgY2FyYWN0ZXLDrXN0aWNhcyBkZSBsYSBmaWd1cmEgOCwgcGVybyBlc3RhIHZleiByZXByZXNlbnRhbmRvIGVsIG3DqXRvZG8gSURXLg0KDQpFbCBtw6l0b2RvIElEVyBwZXJtaXRlIGNhbGN1bGFyIGVsIHZhbG9yIGRlIGVycm9yIGN1YWRyw6F0aWNvIG1lZGlvIChSTVNFKSBkZSBsb3MgZGF0b3MgaW50ZXJwb2xhZG9zLiBFbCBncsOhZmljbyAzLCBtdWVzdHJhIGN1w6FsIGVzIGVsIHZhbG9yIGRlIHByZWNpcGl0YWNpw7NuIG9ic2VydmFkYSBlbiBlbCBlamUgWCB5IGN1w6FsIGZ1ZSBsYSBwcmV2aXN0YSBlbiBlbCBlamUgWS4gU2kgbG9zIGRhdG9zIGNvaW5jaWRpZXJhbiBwZXJmZWN0YW1lbnRlLCBlc3RhcsOtYW4gYWxpbmVhZG9zIGNvbiBsYSBsw61uZWEgZGUgY29sb3IgbmVncm8sIHF1ZSBlcyBkZSA0NcKwOyBzaW4gZW1iYXJnbyBsb3MgcmVzdWx0YWRvcyBtdWVzdHJhbiBxdWUgbG9zIHB1bnRvcyBlc3TDoW4gc29icmUgbGEgbMOtbmVhIHJvamEsIGxhIGN1YWwgcHVlZGUgdmFyaWFyIHNpIGVsIGV4cG9uZW50ZSBmdWVyYSBkaXN0aW50byBhIGRvcyAoMi4yLCAyLDQpLCBwZXJvIG5vIG11eSBsZWphbm8gYSBkb3MuIFNlIHRyYWJhasOzIGNvbiB1bmEgcG90ZW5jaWEgSURXIGRlIDIsIHF1ZSBlcyBsYSBxdWUgZ2VuZXJhbG1lbnRlIHNlIHVzYS4NCg0KQWwgY2FsY3VsYXIgZWwgZXJyb3IgbWVkaW8gY3VhZHLDoXRpY28gZGUgbG9zIGRhdG9zLCBhcnJvasOzIHVuIHJlc3VsdGFkbyBkZSA2LjY1MCwgeSBwcm92aWVuZSBkZSBsYSBmw7NybXVsYToNCmBgYHtyfQ0KKHN1bSgoSURXLm91dCAtIFAkTGx1dmlhKV4yKSAvIGxlbmd0aChQKSkNCmBgYA0KU3VtOiBTdW1hdG9yaWEsICBJRFcub3V0OiBMb25naXR1ZCBkZWwgdmVjdG9yLCBQJExsdXZpYTogdmFsb3IgZGUgcHJlY2lwaXRhY2nDs24gZW4gZWwgcHVudG8gIGxlbmd0aChQKTogTG9uZ2l0dWQuDQoNCkxhIHZhbGlkYWNpw7NuIGNydXphZGEgcHVlZGUgZGV0ZXJtaW5hciBjdcOhbCBlcyBsYSBpbmNlcnRpZHVtYnJlIGRlIGxvcyByZXN1bHRhZG9zLCBkb25kZSBzZSBjcmXDsyB1biBtYXBhIGRlIGludGVydmFsbyBkZSBjb25maWFuemEgZGUgOTUlIGRlbCBtb2RlbG8gZGUgaW50ZXJwb2xhY2nDs24sIHF1ZSBjb3JyZXNwb25kZSBhIGxhIGZpZ3VyYSAxNC4gRXN0YSBmaWd1cmEgcGVybWl0ZSBhcHJlY2lhciBxdWUgZW4gbGEgbWF5b3LDrWEgZGUgbG9zIHB1bnRvcyBpbnRlcnBvbGFkb3MgZGVsIGRlcGFydGFtZW50byBkZSBDYXF1ZXTDoSwgZWwgcmFuZ28gZGUgaW5jZXJ0aWR1bWJyZSBlcyBtdXkgYmFqbywgdGFsIGNvbW8gbG8gaW5kaWNhIGVsIGNvbG9yLiBFbnRvbmNlcywgc2UgcHVlZGUgZGVjaXIgZW4gYmFzZSBhbCBtYXBhLCBxdWUgbG9zIGludGVydmFsb3MgZGUgZXJyb3IgbcOhcyBhbHRvIHNlIHByZXNlbnRhbiBlbiB1bmEgcGVxdWXDsWEgw6FyZWEgZGVsIG11bmljaXBpbyBkZSBTb2xhbm8uIA0KDQpFbiBlbCBtw6l0b2RvIGRlIEtyaWdpbmcsIHNlIGNhbGN1bMOzIHVuIHNlbWl2YXJpb2dyYW1hIGxpbmVhbCBwb3JxdWUgc2UgdXNhIGxhIGbDs3JtdWxhIGRlIHByaW1lciBvcmRlbiBwb2xpbm9taWFsLCBzaWVuZG8gcHJlY2lwPWzDrW5lYSthWCtiWS4gUGFyYSBhanVzdGFyIGxvcyB2YWxvcmVzIHNlIHJlYWxpemEgZWwgc2VtaXZhcmlvZ3JhbWEsIGRhbmRvIGNvbW8gcmVzdWx0YWRvIHVuIGdyw6FmaWNvIGRvbmRlIGxvcyB2YWxvcmVzIGRlIHNlbWl2YXJpYW56YSBwcm9tZWRpYWRvcywgbG9zIGN1YWxlcyBlc3TDoW4gdWJpY2Fkb3MgZW4gZWwgZWplIFksIHkgbGEgZGlzdGFuY2lhIG8gaW50ZXJ2YWxvIGVzdMOhIHViaWNhZGEgZW4gZWwgZWplIFgsIGFkZW3DoXMgdGllbmUgdW4gbnVnZ2V0IGlndWFsIGEgY2Vyby4gU2UgcHVlZGVuIHZlciBhbGd1bm9zIHB1bnRvcyBzb2JyZSB1bmEgcmVjdGEsIGhhYmllbmRvIHVuYSBjb3JyZWxhY2nDs24gZXNwYWNpYWwgZW50cmUgZGljaG9zIHB1bnRvcywgZG9uZGUgZXN0w6FuIG3DoXMgcmVsYWNpb25hZG9zIGVudHJlIHPDrSBsb3MgcHVudG9zIHF1ZSBzZSBlbmN1ZW50cmFuIHVubyBtw6FzIGNlcmNhIGRlIG90cm8uIExhcyBkaWZlcmVuY2lhcyBubyBwcmVzZW50YSB2YXJpYWNpb25lcyBhbHRhcywgZW50b25jZXMgZXNlIG1vZGVsbyBkZSB2YXJpb2dyYW1hIHNlIGFqdXN0YSBjb24gbG9zIHB1bnRvcyBkZSBtdWVzdHJlby4gIA0KDQpMYSBmaWd1cmEgMTUgcHJlc2VudGEgdW4gbWFwYSBjb24gbWVqb3IgcmVzb2x1Y2nDs24sIHVuYSBwYWxldGEgZGUgY29sb3IgcXVlIHZhcsOtYSBlbnRyZSBlbCByb2pvIHkgZWwgYXp1bCwgcmVmbGVqYW5kbyB6b25hcyBjb24gbWVub3IgcHJlY2lwaXRhY2nDs24sIHkgem9uYXMgY29uIG1heW9yIHByZWNpcGl0YWNpw7NuIHJlc3BlY3RpdmFtZW50ZS4gTG9zIGRhdG9zIGVzdMOhbiBhZ3J1cGFkb3MgcG9yIGNvbG9yZXMgc2Vnw7puIGxhIHNpbWlsaXR1ZCBkZSBwcmVjaXBpdGFjacOzbiBxdWUgZXN0b3MgcHJlc2VudGVuLCBjb21vIHNlIGhhYsOtYSBtZW5jaW9uYWRvIGVuIGFudGVyaW9ybWVudGUsIGxhcyBhZ3J1cGFjaW9uZXMgZW4gdG9uYWxpZGFkZXMgZGUgY29sb3IgYXp1bCBzb24gc2ltaWxhcmVzIGVuIGN1YW50byBhbCBuaXZlbCBkZSBwcmVjaXBpdGFjacOzbiBlbiBlbCBkZXBhcnRhbWVudG8sIHkgbGFzIHpvbmFzIGNvbiBjb2xvcmFjaW9uZXMgcm9qaXphcyBzb24gYXF1ZWxsYXMgZW4gbGFzIHF1ZSBsb3MgcHVudG9zIHNvbiBwYXJlY2lkb3MgZW4gY3VhbnRvIGEgc3Ugbml2ZWwgZGUgcHJlY2lwaXRhY2nDs24sIHByZXNlbnRhbmRvIGludGVydmFsb3MgbWVub3JlcyBxdWUgbG9zIGRlIGxhIHpvbmEgYXp1bC4gDQoNCkxhIGZpZ3VyYSAxNiBtdWVzdHJhIHVuIG1hcGEgaW50ZXJhY3Rpdm8gZGUgbGEgcHJlY2lwaXRhY2nDs24gaW50ZXJwb2xhZGEgcG9yIGVsIG3DqXRvZG8gZGUgS3JpZ2luZywgcHJlc2VudGFuZG8gcmVwcmVzZW50YW5kbyBsYSBpbmZvcm1hY2nDs24gZGUgbGEgZmlndXJhIDE1LCBwZXJvIGVuIGVzdGEgb2Nhc2nDs24gZXMgZWwgbWFwYSBjb24gbWVqb3IgcmVzb2x1Y2nDs24gZW4gY29tcGFyYWNpw7NuIGRlIHRvZG9zIGxvcyBhbnRlcmlvcmVzLCBlc3RvIHNlIGRpY2UgcG9ycXVlIG5vIHNlIHZlbiBsYXMgY2VsZGFzIHRhbiBtYXJjYWRhcywgcHJlc2VudGEgdW5hIGNvbG9yYWNpw7NuIHF1ZSB2YXLDrWEgZGUgdW5hIGZvcm1hIGFkZWN1YWRhIHkgY29oZXJlbnRlLg0KDQpMYSBmaWd1cmEgMTcgcGVybWl0ZSBvYnNlcnZhciBlbCBpbnRlcnZhbG8gZGUgdmFyaWFjacOzbiByZXNwZWN0byBhIGxvcyBkYXRvcyBvYnRlbmlkb3MsIGRvbmRlIHNlIHB1ZWRlIHZlciBxdWUgZXN0ZSBpbnRlcnZhbG8gcHJlc2VudGEgdmFsb3JlcyBtYXlvcmVzIGVuIGxvcyBib3JkZXMgZGVsIGRlcGFydGFtZW50bywgcGVybWl0aWVuZG8gZGVkdWNpciBxdWUgc3VzIHZhbG9yZXMgdGllbmVuIGNpZXJ0byBncmFkbyBkZSBpbmNlcnRpZHVtYnJlLCBtaWVudHJhcyBxdWUgbG9zIGRhdG9zIGN1YnJlbiBlbCBpbnRlcmlvciBkZWwgZGVwYXJ0YW1lbnRvIHByZXNlbnRhbiB1biBpbnRlcnZhbG8gZGUgdmFyaWFjacOzbiBlbnRyZSAxMCB5IDIwIG1tLCBwZXJvIG1lbm9yIGEgY29tcGFyYWNpw7NuIGRlIGxvcyBsw61taXRlcy4gDQoNCkxhIGZpZ3VyYSAxOCByZXByZXNlbnRhIGVsIGludGVydmFsbyBkZSBjb25maWFuemEgZGUgbG9zIGRhdG9zIGRlIHByZWNpcGl0YWNpw7NuIGEgdHJhdsOpcyBkZSBsYSBpbnRlcnBvbGFjacOzbiBwb3IgZWwgbcOpdG9kbyBkZSBrcmlnaW5nLiBTZSBwdWVkZSBhcHJlY2lhciBxdWUgbGEgbWF5b3LDrWEgZGUgc3VzIHJlc3VsdGFkb3MgcHJlc2VudGFuIGNvbG9yYWNpb25lcyBjb3JyZXNwb25kaWVudGVzIGEgaW50ZXJ2YWxvcyBlbnRyZSA2IHkgMTIgbW0sIGRvbmRlIGVsIG5pdmVsIGRlIGNvbmZpYW56YSBlcyBmYXZvcmFibGUuIA0KDQojIyBDb25jbHVzaW9uZXMgDQoNCkxhIGludGVycG9sYWNpw7NuIGVzIHVuYSBoZXJyYW1pZW50YSBkZSB2aXRhbCBpbXBvcnRhbmNpYSBwYXJhIA0KbXVjaGFzIGNhcnJlcmFzIGRlYmlkbyBhIHF1ZSBwZXJtaXRlIHJlYWxpemFyIGVzdHVkaW9zIGRlIGRpZmVyZW50ZXMgdmFyaWFsZXMgY29tbyBsYSBwcmVjaXBpdGFjacOzbiwgcXVlIGZ1ZSBsYSBxdWUgc2UgdHJhYmFqw7MgZW4gZWwgaW5mb3JtZSwgc2luIHRlbmVyIHF1ZSBpciBkaXJlY3RhbWVudGUgYSBsYSB6b25hIHF1ZSBzZSBxdWllcmUgZXN0dWRpYXIsIHJlcHJlc2VudGEgdGFtYmnDqW4gaW1wb3J0YW5jaWEgZW4gY3VhbnRvIGEgY29zdG9zIHlhIHF1ZSBzZSBwdWVkZW4gb2J0ZW5lciB5IHJlcHJlc2VudGFyIGRhdG9zIGRlIGRpZmVyZW50ZXMgdmFyaWFibGVzIHBhcnRpZW5kbyBkZSB1biBuw7ptZXJvIGxpbWl0YWRvIGRlIHB1bnRvcyBxdWUgdGVybWl0ZW4gY3JlYXIgZXN0cnVjdHVyYXMgcsOhc3Rlci4gDQoNCkV4aXN0ZW4gdmFyaW9zIG3DqXRvZG9zIHBhcmEgcG9kZXIgcmVhbGl6YXIgaW50ZXJwb2xhY2nDs24sIHByZXNlbnRhbmRvIGRpZmVyZW5jaWFzIGNvbW8gbGEgbWFuZXJhIGRlIGNhbGN1bGFybG9zLCBsYXMgZXN0cnVjdHVyYXMgcXVlIGZvcm1hbiwgbGFzIHZhcmlhYmxlcyBhIGxhcyBxdWUgY2FkYSB1bm8gc2UgYWNvbW9kYSBtZWpvciBwYXJhIGVzdHVkaWFyLCBsYSBtYW5lcmEgZGUgaW50ZXJwcmV0YXIgeSBsZWVyIGxvcyBkYXRvcywgYWxndW5vcyBwcm9wb3JjaW9uYW4gaW5mb3JtYWNpw7NuIGFkaWNpb25hbCBjb21vIGxhIGluY2VydGlkdW1icmUgZGUgbG9zIGRhdG9zLiANCg0KTGEgaGVycmFtaWVudGEgUlN0dWRpbyBvZnJlY2UgYSBzdXMgdXN1YXJpb3MgdW5hIGFtcGxpYSBnYW1hIGRlIGxpYnJlcsOtYXMgY29uIGRpZmVyZW50ZXMgZnVuY2lvbmVzLCBicmluZGFuZG8gZGlmZXJlbnRlcyBhbHRlcm5hdGl2YXMgcGFyYSByZXByZXNlbnRhciwgZW4gYmFzZSBhIGRhdG9zIGRlc2NhcmdhZG9zIGRlIHBsYXRhZm9ybWFzIGNvbmZpYWJsZXMsIHRhYmxhcywgZ3LDoWZpY29zLCByZWFsaXphciBtYXBhcyBxdWUgcmVwcmVzZW50ZW4gZ3LDoWZpY2FtZW50ZSB2YWxvcmVzIGRlIGxvcyBncsOhZmljb3MsIHRhbGVzIGNvbW8gbWFwYXMgdGVtw6F0aWNvcywgaW50ZXJhY3Rpdm9zLCBlbnRyZSBvdHJvcywgcGVybWl0aWVuZG8gaGFjZXIgYW7DoWxpc2lzIGRlIHRvZG8gdGlwbywgcG9yIGVqZW1wbG8gYW7DoWxpc2lzIGRlIGxhcyBuZWNlc2lkYWRlcyBiw6FzaWNhcyBpbnNhdGlzZmVjaGFzIGRlIHVuYSByZWdpw7NuLCBuaXZlbCBkZSBlc2NvbGFyaWRhZCwgbml2ZWwgZGUgbmF0YWxpZGFkLCBuaXZlbGVzIGRlIHByb2R1Y2Npw7NuIHkgcmVuZGltaWVudG8gZGUgZGV0ZXJtaW5hZG9zIGN1bHRpdm9zLCBlbnRyZSBvdHJvcy4gDQoNCkRlbnRybyBkZSBsYXMgaGVycmFtaWVudGFzIGRlIFIgc2UgZW5jdWVudHJhIGxhIGludGVycG9sYWNpw7NuIGRlIGRhdG9zLCBwZXJtaXRpZW5kbyByZWFsaXphciBhbsOhbGlzaXMgZGUgcHJlY2lwaXRhY2nDs24geSBhc8OtIHBvZGVyIHJlYWxpemFyLCBlbiBiYXNlIGEgbGl0ZXJhdHVyYSB5IGVzdGFkw61zdGljYXMsIGVzdGltYWNpb25lcyBzb2JyZSBpbXBhY3RvcyBkZSBzZXF1w61hcyBvIGludW5kYWNpb25lcy4NCg0KIyMgQmlibGlvZ3JhZsOtYSANCg0KQnJhdm8sIEwuIHMuZi4gRGlhZ3JhbWEgZGUgVm9yb25vaS4gUmVjdXBlcmFkbyBkZTogaHR0cDovL21hdGVtYXRpY2FzLnVuZXguZXMvfnRyaW5pZGFkL211aS92b3Jvbm9pLnBkZjtjb25zdWx0YTogSnVuaW8gZGUgMjAyMC4NCg0KRnVuaywgQy4gIFAsIFBldGVyc29uLiBNLCBMYW5kc2ZlbGQuIEQsIFBlZHJlcm9zLiBKLCBWZXJkaW4uIFMsIFNodWtsYS4gRywgSHVzYWsuSiwgUm93bGFuZC4gTCwgSGFycmlzb24uIEEsIEhvZWxsIHkgSiBNaWNoYWVsc2VuLiAyMDE1LiBUaGUgY2xpbWF0ZSBoYXphcmRzIGluZnJhcmVkIHByZWNpcGl0YXRpb24gd2l0aCBzdGF0aW9uc+KAlGEgbmV3IGVudmlyb25tZW50YWwgcmVjb3JkIGZvciBtb25pdG9yaW5nIGV4dHJlbWVzLiBSZWN1cGVyYWRvIGRlOiAgaHR0cHM6Ly93d3cubmF0dXJlLmNvbS9hcnRpY2xlcy9zZGF0YTIwMTU2NjsgY29uc3VsdGE6IEp1bmlvIGRlIDIwMjAuIA0KDQpHaW1vbmQsIE0uIDIwMTkuIEludHJvIHRvIEdJUyBhbmQgU3BhdGlhbCBBbmFseXNpcy4gUmVjdXBlcmFkbyBkZTogaHR0cHM6Ly9tZ2ltb25kLmdpdGh1Yi5pby9TcGF0aWFsL2ludGVycG9sYXRpb24taW4tci5odG07IGNvbnN1bHRhOiBKdW5pbyBkZSAyMDIwLg0KDQpHSVNHZW9ncmFwaHkuIHMuZi5JbnZlcnNlIERpc3RhbmNlIFdlaWdodGluZyAoSURXKSBJbnRlcnBvbGF0aW9uLiBSZWN1cGVyYWRvIGRlOiBodHRwczovL2dpc2dlb2dyYXBoeS5jb20vaW52ZXJzZS1kaXN0YW5jZS13ZWlnaHRpbmctaWR3LWludGVycG9sYXRpb24vOyBjb25zdWx0YTogSnVuaW8gZGUgMjAyMC4NCg0KR3J1cG8gS3Jha2VuIElERS4gMjAxOS4gR2xvYmFsIFByZWNpcGl0YXRpb24gRGF0YSAoQ0hJUlBTKS4gUmVjdXBlcmFkbyBkZTogaHR0cDovL2lkZS51bmV4LmVzL2Nvbm9jaW1pZW50by9pbmRleC5waHA/L2FydGljbGUvQUEtMzE3NDUvMC9EYXRvcy1nbG9iYWxlcy1kZS1wcmVjaXBpdGFjaW4tQ0hJUlBTLmh0bTsgQ29uc3VsdGE6IEp1bmlvIGRlIDIwMjANCg0KTWluaXN0ZXJpbyBkZSBBZ3JpY3VsdHVyYS4gMjAxNC4gUHJpbmNpcGFsZXMgQ3VsdGl2b3MgcG9yIMOBcmVhIHNlbWJyYWRhIGVuIGVsIGHDsW8gMjAxNC4gUmVjdXBlcmFkbyBkZTogaHR0cDovL3d3dy5hZ3JvbmV0Lmdvdi5jby9Eb2N1bWVudHMvQ2FxdWV0JUMzJUExLnBkZjsgY29uc3VsdGEgSnVuaW8gZGUgMjAyMC4gDQoNClZpbG9yaWEsIEouIHMuZi5HZW9Kc29uLmlvLCBoZXJyYW1pZW50YSBwYXJhIGdlbmVyYXIgZ2VvZGF0b3MuUmVjdXBlcmFkbyBkZTogIGh0dHBzOi8vZ2VvaW5ub3ZhLm9yZy9ibG9nLXRlcnJpdG9yaW8vZ2VvanNvbi1pby1oZXJyYW1pZW50YS1wYXJhLWdlbmVyYXItZ2VvZGF0b3MvOyBjb25zdWx0YTogSnVuaW8gZGUgMjAyMC4NCg0KDQo=