Using Linear Regression Models to Predict Capital Gain/Loss (Income)

Jacqueline Nosrati

Overview

In this week’s assignment I will use linear regression models to predict whether an individual has capital gains or loss (income) using extracted data from the 1994 US Census Data set. To make predictions about capital gains/loss (income) I will look at gender, race, number of years of education,and age and using an interaction I will look at differences within the categories.

Load packages

library(Zelig)
library(readr)
library(pander)
library(radiant.data)
library(texreg)
library(lmtest)
library(visreg)
library(tidyverse)

In this step I loaded the required packages to analyze and visualize the data.

Load data set

Income<- read_csv("C:/Users/Papa/Desktop/Soc 712 -R/adult.csv", col_names = TRUE)
head(Income)

In this step, I loaded my data set and saved it as “Income”. Currently, we only see the first 6 observations.

Recode outcome and independent variables

Income2 <- Income %>%  mutate(newincome = capital.gain - capital.loss)
head(Income2)

In this step, I first created a new data set called Income2. Next, I created a continuous outcome variable called “newincome” using the mutate command by taking the difference of capital gains and capital loss variables.

Income2 <- Income2 %>% mutate(newsex = ifelse(sex == "Female",1,0))
head(Income2)

Here I generated a new variable called “newsex” using the mutate command in which “Female” is 1 and “Male” is 0.

A Simple Model

lm0 <- lm(newincome ~ newsex, data = Income2)
summary(lm0)

Call:
lm(formula = newincome ~ newsex, data = Income2)

Residuals:
   Min     1Q Median     3Q    Max 
 -4999  -1229  -1229   -507  99492 

Coefficients:
            Estimate Std. Error t value            Pr(>|t|)    
(Intercept)  1229.16      50.14  24.515 <0.0000000000000002 ***
newsex       -721.93      87.18  -8.281 <0.0000000000000002 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 7401 on 32559 degrees of freedom
Multiple R-squared:  0.002102,  Adjusted R-squared:  0.002071 
F-statistic: 68.58 on 1 and 32559 DF,  p-value: < 0.00000000000000022

For the first model, I looked at the relationship between income and sex. When looking at the result we see that women on average make 721.93 dollars less than men in capital gains. We see that the results are statistically significant at a 99% confidence level. I chose this variable because there is generally a gender pay gap.

Model 2 - Adding of 2 more variables

lm1 <- lm(newincome ~ newsex + race + age, data = Income2)
summary(lm1)

Call:
lm(formula = newincome ~ newsex + race + age, data = Income2)

Residuals:
   Min     1Q Median     3Q    Max 
 -6943  -1418   -896   -396 100395 

Coefficients:
                       Estimate Std. Error t value             Pr(>|t|)    
(Intercept)            -608.486    435.394  -1.398                0.162    
newsex                 -598.674     87.895  -6.811     0.00000000000984 ***
raceAsian-Pac-Islander  738.306    477.191   1.547                0.122    
raceBlack                 4.547    439.080   0.010                0.992    
raceOther               437.036    613.567   0.712                0.476    
raceWhite               335.342    421.016   0.797                0.426    
age                      38.432      3.013  12.753 < 0.0000000000000002 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 7382 on 32554 degrees of freedom
Multiple R-squared:  0.007367,  Adjusted R-squared:  0.007184 
F-statistic: 40.27 on 6 and 32554 DF,  p-value: < 0.00000000000000022

For the second model I added the variables race and age to the previous model. In this case the intercept represents an individual of American Indian/Eskimo race. Now we see that women make on average 598.67 dollars less than men in capital gains and that this is still statistically significant a 99% confidence level. Next, we see that Asian/Pacific Islander make on average 738.31 dollars more in capital gains than their American-Indian/Eskimo counterparts. Next, we see that Black individuals make on average 4.547 dollars more in capital gains than their American-Indian/Eskimo counterparts and individuals in the Other races category make on average 437.04 dollars more in capital gains than their American-Indian/Eskimo counterparts. White individuals make on average 335.34 dollars more in capital gains than their American-Indian/Eskimo counterparts. It should be noted that across all races the values were not statistically significant at all. Finally, for the age variable we see that with every additional year, on average capital gains increase by 38.43 dollars, which is statistically significant at a 99% confidence level.

Adding Years of Education Variable To the Model

lm2 <- lm(newincome ~ newsex + race + age + education.num, data = Income2)
summary(lm2)

Call:
lm(formula = newincome ~ newsex + race + age + education.num, 
    data = Income2)

Residuals:
   Min     1Q Median     3Q    Max 
 -7518  -1627   -804    -70 100488 

Coefficients:
                        Estimate Std. Error t value             Pr(>|t|)    
(Intercept)            -3605.559    455.981  -7.907  0.00000000000000271 ***
newsex                  -598.927     87.319  -6.859  0.00000000000705673 ***
raceAsian-Pac-Islander   194.967    474.789   0.411                0.681    
raceBlack                -51.752    436.214  -0.119                0.906    
raceOther                584.620    609.593   0.959                0.338    
raceWhite                 66.746    418.460   0.160                0.873    
age                       36.320      2.995  12.125 < 0.0000000000000002 ***
education.num            330.295     15.903  20.769 < 0.0000000000000002 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 7334 on 32553 degrees of freedom
Multiple R-squared:  0.02035,   Adjusted R-squared:  0.02014 
F-statistic: 96.59 on 7 and 32553 DF,  p-value: < 0.00000000000000022

In this model, I added the numbers of years of education variable. This time we see that on average women make 598.27 dollars less than men in capital gains and that this is still statistically significant a 99% confidence level. Next, we see that Asian/Pacific Islander individuals make on average 194.97 dollars more in capital gains than their American-Indian/Eskimo counterparts. Next, we see that Black individuals make on average 51.75 dollars less in capital gains than their American-Indian/Eskimo counterparts and individuals in the Other races category make on average 584.62 dollars more in capital gains than their American-Indian/Eskimo counterparts. White individuals make on average 66.75 dollars more in capital gains than their American-Indian/Eskimo counterparts. Again, across all races the values were not statistically significant at all. Finally, for the age variable we see that with every additional year, on average capital gains increase by 36.32 dollars and with every additional year of education capital gains increase on average by 330.30 dollars. Both numbers are statistically significant at a 99% confidence level.

Looking at the interaction between race and sex

lm3 <- lm(newincome ~ newsex*race + age + education.num, data = Income2)
summary(lm3)

Call:
lm(formula = newincome ~ newsex * race + age + education.num, 
    data = Income2)

Residuals:
   Min     1Q Median     3Q    Max 
 -7474  -1631   -798    -64 100526 

Coefficients:
                               Estimate Std. Error t value             Pr(>|t|)    
(Intercept)                   -3711.615    558.888  -6.641      0.0000000000316 ***
newsex                         -301.621    855.725  -0.352                0.724    
raceAsian-Pac-Islander          293.991    599.153   0.491                0.624    
raceBlack                      -134.379    560.775  -0.240                0.811    
raceOther                       867.200    782.472   1.108                0.268    
raceWhite                       197.400    532.252   0.371                0.711    
age                              36.158      2.997  12.064 < 0.0000000000000002 ***
education.num                   330.116     15.911  20.748 < 0.0000000000000002 ***
newsex:raceAsian-Pac-Islander  -251.889    982.811  -0.256                0.798    
newsex:raceBlack                 97.491    895.044   0.109                0.913    
newsex:raceOther               -718.742   1248.127  -0.576                0.565    
newsex:raceWhite               -350.373    861.023  -0.407                0.684    
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 7334 on 32549 degrees of freedom
Multiple R-squared:  0.02044,   Adjusted R-squared:  0.0201 
F-statistic: 61.73 on 11 and 32549 DF,  p-value: < 0.00000000000000022

For this model I looked at the interaction between sex and race with respect to whether an individual has a capital gain or loss to see whether there are differences across both genders and different races. I chose the interaction between race and gender to get a closer look at income discrepancies.

In this interaction, the intercept (-3711.615) represents male individuals of American-Indian/Eskimo race. Now we see that on average females make 301.621 dollars less than men in capital gains. Next we see that Asian-Pac-Islander males make on average 293.991 dollars more than their American-Indian/Eskimo counterparts. Next we see that Black males make on average 134.379 dollars less than their American-Indian/Eskimo counterparts, males of other races make on average 867.200 dollars more than their American-Indian/Eskimo counterparts and White males make on average 197.400 dollars more than their American-Indian/Eskimo counterparts. For each additional year in age on average capital gains increase by 36.158 dollars and for each additional in year in education capital gains increase on average by 330.116 dollars. Next, Asian/Pac Islander females make on average 251.889 dollars less in capital gains than their American-Indian/Eskimo counterparts and Black females make on average 97.491 dollars more than their American-Indian/Eskimo counterparts in capital gains. Finally, females from other races make on average 718.742 dollars less than their American-Indian/Eskimo counterparts in capital gains and White females make on average 350.373 dollars less than their American-Indian/Eskimo counterparts. We see that in this model that only the values for age and years of education are statistically significant at a 99% confidence level.

Income3 <- Income2 %>%
  select(newincome, newsex, race ) %>% 
  group_by(newsex, race) %>%
  summarise(mean = mean(newincome))
Income3

In this step, I created another data set called “Income3” which has a group-wise summary statistics of the dependent variable and where we have the means for each race and sex group, showing the average capital gains for each grouping. For accuracy of the interpretation of the results I will verify the results of the regression with the interaction terms with the results of the summary statistics. I will compare the differences among genders for each race group by subtracting the male and female values for each race group for both the regression results and the summary. Next, I will look if the differences between the regression and the summary and significant or not.

Gender differences among Asian males & females:

  • For the regression we simply look at the difference between the capital gains values for Asian Males (293.991) and Asian Females (-251.889), which is 42.102 dollars.
  • For the summary statistics we look at the difference in capital gains averages for Asian Males (1707.4401) and Asian Females (727.5838) which is 979.8563 dollars.

This shows a large difference between the two results.

Gender differences among Black males and females:

  • For the regression we simply look at the difference between the capital gains values for Black Males (134.379) and Black Females (97.491), which is 36.888 dollars.
  • For the summary statistics we look at the difference in capital gains averages for Black Males (627.2683) and Black Females (471.1428) which is 156.1255 dollars.

We see again large differences from both results.

Gender differences among Other races males and females:

  • For the regression we simply look at the difference between the capital gains values for Other Males (867.200) and Other Females (-718.472), which is 148.458 dollars.
  • For the summary statistics we look at the difference in capital gains averages for Other Males (1314.4383) and Other Females (218.3853) which is 1096.053 dollars.

For this group we also see large differences from both results.

Gender differences among White males and females:

  • For the regression we simply look at the difference between the capital gains values for White Males (197.4) and White Females (-350.373), which is 152.973 dollars.
  • For the summary statistics we look at the difference in capital gains averages for White Males (1266.4131) and White Females (508.2199) which is 758.1932 dollars.

Checking the regression esimates against the summary results suggest that the findings of the regression with the interaction term are accurate and make sense. This is because as the regression model showed us that, even with the interaction term, race and sex are not statistically significant, which is confirmed by the large deviations in the results and make those two variables unreliable for estimation.

Based on this conclusion, we will go back to the last model and look at the two variables that were statistically significant, age and years of education.

Summary Statistics for Years of education and Age

Income4 <- Income2 %>%
  select(newincome, education.num) %>% 
  group_by(education.num) %>%
  summarise(mean = mean(newincome))
Income4

In this step, I created another data set called “Income4” which has a group-wise summary statistics of the dependent variable and where we have the means for each year of education group, showing the average capital gains for each grouping. Looking at both results, we see that as years of education increase we also see an increase in capital gains, confirming the regression results that years of education is statistically significant.

Comparing Models

library(texreg)
htmlreg(list(lm0, lm1, lm2, lm3))
Statistical models
Model 1 Model 2 Model 3 Model 4
(Intercept) 1229.16*** -608.49 -3605.56*** -3711.62***
(50.14) (435.39) (455.98) (558.89)
newsex -721.93*** -598.67*** -598.93*** -301.62
(87.18) (87.89) (87.32) (855.72)
raceAsian-Pac-Islander 738.31 194.97 293.99
(477.19) (474.79) (599.15)
raceBlack 4.55 -51.75 -134.38
(439.08) (436.21) (560.78)
raceOther 437.04 584.62 867.20
(613.57) (609.59) (782.47)
raceWhite 335.34 66.75 197.40
(421.02) (418.46) (532.25)
age 38.43*** 36.32*** 36.16***
(3.01) (3.00) (3.00)
education.num 330.29*** 330.12***
(15.90) (15.91)
newsex:raceAsian-Pac-Islander -251.89
(982.81)
newsex:raceBlack 97.49
(895.04)
newsex:raceOther -718.74
(1248.13)
newsex:raceWhite -350.37
(861.02)
R2 0.00 0.01 0.02 0.02
Adj. R2 0.00 0.01 0.02 0.02
Num. obs. 32561 32561 32561 32561
RMSE 7401.31 7382.33 7334.01 7334.13
p < 0.001, p < 0.01, p < 0.05

Using the texreg package we put the results of the 4 models into a table to compare the results. Even though the model was not very successful in explaining some of the factors that influence capital gains, we were able to slightly improve it from an R^2 of 0.00 in the first model to an R^2 of 0.02 in the last model. In this case R^2 means that our model explains only 2% of the variations in the data. This means that in the future, we need to select better independent variables and choose our interaction terms more carefully.

Graphs

The first graph shows the relationship between age and capital gains.

library(visreg)
visreg(lm2, "age", scale = "response")

As confirmed by our results, age positively influences capital gains as the variable is statistically significant.

The second graph shows the relationship between years of education and capital gains.

visreg(lm2, "education.num", scale = "response")

Again, this graph confirms our results that years of education positively influences capital gains as the variable is statistically significant.

For the third graph we first need to recode race into a numerical variable, create a new data set (Income5) and re-run the lm2 model as lmodel5 .

Income5 <- Income2%>%
  mutate(newrace = factor(ifelse(race == "White", 1,
                ifelse(race == "Asian-Pac-Islander", 2,
                ifelse(race == "Black", 3,
                ifelse(race == "Other", 4,
                ifelse(race == "Amer-Indian-Eskimo", 5, "error")))))))                    
Income5
lmodel2 <- lm(newincome ~ newsex + newrace + age + education.num, data = Income5)
summary(lmodel2)

Call:
lm(formula = newincome ~ newsex + newrace + age + education.num, 
    data = Income5)

Residuals:
   Min     1Q Median     3Q    Max 
 -7518  -1627   -804    -70 100488 

Coefficients:
               Estimate Std. Error t value             Pr(>|t|)    
(Intercept)   -3538.813    203.491 -17.391 < 0.0000000000000002 ***
newsex         -598.927     87.319  -6.859     0.00000000000706 ***
newrace2        128.220    232.141   0.552                0.581    
newrace3       -118.499    139.725  -0.848                0.396    
newrace4        517.874    448.451   1.155                0.248    
newrace5        -66.746    418.460  -0.160                0.873    
age              36.320      2.995  12.125 < 0.0000000000000002 ***
education.num   330.295     15.903  20.769 < 0.0000000000000002 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 7334 on 32553 degrees of freedom
Multiple R-squared:  0.02035,   Adjusted R-squared:  0.02014 
F-statistic: 96.59 on 7 and 32553 DF,  p-value: < 0.00000000000000022
visreg(lmodel2, "newrace", by = "newsex", scale = "response")

Looking at this graph, we see the differences in capital by gender, clustered by race. This graph further confirms that there is not a statistically significant relationship between sex, race and capital gains.

visreg(lmodel2, "newsex", by = "newrace", scale = "response")

Now we switched gender and race and the graph shows us capital gains by race and clustered by gender. Again, we don’t see a statistically significant relationship between the variables.

Next, we will re-run the lm3 model with the interaction term and label it lmodel3. Finally, we will generate the last graph.

lmodel3 <- lm(newincome ~ newsex*newrace + age + education.num, data = Income5)
summary(lmodel3)

Call:
lm(formula = newincome ~ newsex * newrace + age + education.num, 
    data = Income5)

Residuals:
   Min     1Q Median     3Q    Max 
 -7474  -1631   -798    -64 100526 

Coefficients:
                 Estimate Std. Error t value             Pr(>|t|)    
(Intercept)     -3514.215    204.139 -17.215 < 0.0000000000000002 ***
newsex           -651.994     95.404  -6.834      0.0000000000084 ***
newrace2           96.590    284.146   0.340               0.7339    
newrace3         -331.779    192.997  -1.719               0.0856 .  
newrace4          669.799    579.219   1.156               0.2475    
newrace5         -197.400    532.252  -0.371               0.7107    
age                36.158      2.997  12.064 < 0.0000000000000002 ***
education.num     330.116     15.911  20.748 < 0.0000000000000002 ***
newsex:newrace2    98.484    492.238   0.200               0.8414    
newsex:newrace3   447.864    279.264   1.604               0.1088    
newsex:newrace4  -368.368    913.536  -0.403               0.6868    
newsex:newrace5   350.373    861.023   0.407               0.6841    
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 7334 on 32549 degrees of freedom
Multiple R-squared:  0.02044,   Adjusted R-squared:  0.0201 
F-statistic: 61.73 on 11 and 32549 DF,  p-value: < 0.00000000000000022
visreg(lmodel3, "newrace", by = "newsex", scale = "response")

Again, we can confirm no statistically significant differences among different races by gender when it comes to capital gains.

Conclusion

Using the regression models, the summary statistics and the graphs we can see that the relationship between gender, race and capital gains is not statistically significant and that there are no significant differences in capital gains; however, in our models the variables that proved to be statistically significant are age and years of education, as both variables tend to increase capital gains.

LS0tDQp0aXRsZTogIldlZWsgNSINCm91dHB1dDogaHRtbF9ub3RlYm9vaw0KLS0tDQoNCiMjVXNpbmcgTGluZWFyIFJlZ3Jlc3Npb24gTW9kZWxzIHRvIFByZWRpY3QgQ2FwaXRhbCBHYWluL0xvc3MgKEluY29tZSkNCg0KIyMjI0phY3F1ZWxpbmUgTm9zcmF0aQ0KDQojIyNPdmVydmlldw0KSW4gdGhpcyB3ZWVrJ3MgYXNzaWdubWVudCBJIHdpbGwgdXNlIGxpbmVhciByZWdyZXNzaW9uIG1vZGVscyB0byBwcmVkaWN0IHdoZXRoZXIgYW4gaW5kaXZpZHVhbCBoYXMgY2FwaXRhbCBnYWlucyBvciBsb3NzIChpbmNvbWUpIHVzaW5nIGV4dHJhY3RlZCBkYXRhIGZyb20gdGhlIDE5OTQgVVMgQ2Vuc3VzIERhdGEgc2V0LiBUbyBtYWtlIHByZWRpY3Rpb25zIGFib3V0IGNhcGl0YWwgZ2FpbnMvbG9zcyAoaW5jb21lKSBJIHdpbGwgbG9vayBhdCBnZW5kZXIsIHJhY2UsIG51bWJlciBvZiB5ZWFycyBvZiBlZHVjYXRpb24sYW5kIGFnZSBhbmQgdXNpbmcgYW4gaW50ZXJhY3Rpb24gSSB3aWxsIGxvb2sgYXQgZGlmZmVyZW5jZXMgd2l0aGluIHRoZSBjYXRlZ29yaWVzLiANCg0KIyMjTG9hZCBwYWNrYWdlcw0KYGBge3IsbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCmxpYnJhcnkoWmVsaWcpDQpsaWJyYXJ5KHJlYWRyKQ0KbGlicmFyeShwYW5kZXIpDQpsaWJyYXJ5KHJhZGlhbnQuZGF0YSkNCmxpYnJhcnkodGV4cmVnKQ0KbGlicmFyeShsbXRlc3QpDQpsaWJyYXJ5KHZpc3JlZykNCmxpYnJhcnkodGlkeXZlcnNlKQ0KYGBgDQoNCkluIHRoaXMgc3RlcCBJIGxvYWRlZCB0aGUgcmVxdWlyZWQgcGFja2FnZXMgdG8gYW5hbHl6ZSBhbmQgdmlzdWFsaXplIHRoZSBkYXRhLg0KDQojIyNMb2FkIGRhdGEgc2V0DQpgYGB7ciAsbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCkluY29tZTwtIHJlYWRfY3N2KCJDOi9Vc2Vycy9QYXBhL0Rlc2t0b3AvU29jIDcxMiAtUi9hZHVsdC5jc3YiLCBjb2xfbmFtZXMgPSBUUlVFKQ0KaGVhZChJbmNvbWUpDQpgYGANCg0KSW4gdGhpcyBzdGVwLCBJIGxvYWRlZCBteSBkYXRhIHNldCBhbmQgc2F2ZWQgaXQgYXMgIkluY29tZSIuIEN1cnJlbnRseSwgd2Ugb25seSBzZWUgdGhlIGZpcnN0IDYgb2JzZXJ2YXRpb25zLg0KDQojIyNSZWNvZGUgb3V0Y29tZSBhbmQgaW5kZXBlbmRlbnQgdmFyaWFibGVzDQpgYGB7ciAsbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCkluY29tZTIgPC0gSW5jb21lICU+JSAgbXV0YXRlKG5ld2luY29tZSA9IGNhcGl0YWwuZ2FpbiAtIGNhcGl0YWwubG9zcykNCmhlYWQoSW5jb21lMikNCmBgYA0KDQpJbiB0aGlzIHN0ZXAsIEkgZmlyc3QgY3JlYXRlZCBhIG5ldyBkYXRhIHNldCBjYWxsZWQgSW5jb21lMi4gTmV4dCwgSSBjcmVhdGVkIGEgY29udGludW91cyBvdXRjb21lIHZhcmlhYmxlIGNhbGxlZCAibmV3aW5jb21lIiB1c2luZyB0aGUgbXV0YXRlIGNvbW1hbmQgYnkgdGFraW5nIHRoZSBkaWZmZXJlbmNlIG9mIGNhcGl0YWwgZ2FpbnMgYW5kIGNhcGl0YWwgbG9zcyB2YXJpYWJsZXMuICANCg0KYGBge3IsIG1lc3NhZ2U9RkFMU0UsIHdhcm5pbmc9RkFMU0V9DQpJbmNvbWUyIDwtIEluY29tZTIgJT4lIG11dGF0ZShuZXdzZXggPSBpZmVsc2Uoc2V4ID09ICJGZW1hbGUiLDEsMCkpDQpoZWFkKEluY29tZTIpDQpgYGANCg0KSGVyZSBJIGdlbmVyYXRlZCBhIG5ldyB2YXJpYWJsZSBjYWxsZWQgIm5ld3NleCIgdXNpbmcgdGhlIG11dGF0ZSBjb21tYW5kIGluIHdoaWNoICJGZW1hbGUiIGlzIDEgYW5kICJNYWxlIiBpcyAwLg0KDQojIyNBIFNpbXBsZSBNb2RlbA0KYGBge3IsbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCmxtMCA8LSBsbShuZXdpbmNvbWUgfiBuZXdzZXgsIGRhdGEgPSBJbmNvbWUyKQ0Kc3VtbWFyeShsbTApDQpgYGANCg0KRm9yIHRoZSBmaXJzdCBtb2RlbCwgSSBsb29rZWQgYXQgdGhlIHJlbGF0aW9uc2hpcCBiZXR3ZWVuIGluY29tZSBhbmQgc2V4LiBXaGVuIGxvb2tpbmcgYXQgdGhlIHJlc3VsdCB3ZSBzZWUgdGhhdCB3b21lbiBvbiBhdmVyYWdlIG1ha2UgNzIxLjkzIGRvbGxhcnMgbGVzcyB0aGFuIG1lbiBpbiBjYXBpdGFsIGdhaW5zLiBXZSBzZWUgdGhhdCB0aGUgcmVzdWx0cyBhcmUgc3RhdGlzdGljYWxseSBzaWduaWZpY2FudCBhdCBhIDk5JSBjb25maWRlbmNlIGxldmVsLiBJIGNob3NlIHRoaXMgdmFyaWFibGUgYmVjYXVzZSB0aGVyZSBpcyBnZW5lcmFsbHkgYSBnZW5kZXIgcGF5IGdhcC4NCg0KIyMjIE1vZGVsIDIgLSBBZGRpbmcgb2YgMiBtb3JlIHZhcmlhYmxlcw0KYGBge3IsbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCmxtMSA8LSBsbShuZXdpbmNvbWUgfiBuZXdzZXggKyByYWNlICsgYWdlLCBkYXRhID0gSW5jb21lMikNCnN1bW1hcnkobG0xKQ0KYGBgDQoNCkZvciB0aGUgc2Vjb25kIG1vZGVsIEkgYWRkZWQgdGhlIHZhcmlhYmxlcyByYWNlIGFuZCBhZ2UgdG8gdGhlIHByZXZpb3VzIG1vZGVsLiBJbiB0aGlzIGNhc2UgdGhlIGludGVyY2VwdCByZXByZXNlbnRzIGFuIGluZGl2aWR1YWwgb2YgQW1lcmljYW4gSW5kaWFuL0Vza2ltbyByYWNlLiBOb3cgd2Ugc2VlIHRoYXQgd29tZW4gbWFrZSBvbiBhdmVyYWdlIDU5OC42NyBkb2xsYXJzIGxlc3MgdGhhbiBtZW4gaW4gY2FwaXRhbCBnYWlucyBhbmQgdGhhdCB0aGlzIGlzIHN0aWxsIHN0YXRpc3RpY2FsbHkgc2lnbmlmaWNhbnQgYSA5OSUgY29uZmlkZW5jZSBsZXZlbC4gTmV4dCwgd2Ugc2VlIHRoYXQgQXNpYW4vUGFjaWZpYyBJc2xhbmRlciBtYWtlIG9uIGF2ZXJhZ2UgNzM4LjMxIGRvbGxhcnMgbW9yZSBpbiBjYXBpdGFsIGdhaW5zIHRoYW4gdGhlaXIgQW1lcmljYW4tSW5kaWFuL0Vza2ltbyBjb3VudGVycGFydHMuIE5leHQsIHdlIHNlZSB0aGF0IEJsYWNrIGluZGl2aWR1YWxzIG1ha2Ugb24gYXZlcmFnZSA0LjU0NyBkb2xsYXJzIG1vcmUgaW4gY2FwaXRhbCBnYWlucyB0aGFuIHRoZWlyIEFtZXJpY2FuLUluZGlhbi9Fc2tpbW8gY291bnRlcnBhcnRzIGFuZCBpbmRpdmlkdWFscyBpbiB0aGUgT3RoZXIgcmFjZXMgY2F0ZWdvcnkgbWFrZSBvbiBhdmVyYWdlIDQzNy4wNCBkb2xsYXJzIG1vcmUgaW4gY2FwaXRhbCBnYWlucyB0aGFuIHRoZWlyIEFtZXJpY2FuLUluZGlhbi9Fc2tpbW8gY291bnRlcnBhcnRzLiBXaGl0ZSBpbmRpdmlkdWFscyBtYWtlIG9uIGF2ZXJhZ2UgMzM1LjM0IGRvbGxhcnMgbW9yZSBpbiBjYXBpdGFsIGdhaW5zIHRoYW4gdGhlaXIgQW1lcmljYW4tSW5kaWFuL0Vza2ltbyBjb3VudGVycGFydHMuIEl0IHNob3VsZCBiZSBub3RlZCB0aGF0IGFjcm9zcyBhbGwgcmFjZXMgdGhlIHZhbHVlcyB3ZXJlIG5vdCBzdGF0aXN0aWNhbGx5IHNpZ25pZmljYW50IGF0IGFsbC4gRmluYWxseSwgZm9yIHRoZSBhZ2UgdmFyaWFibGUgd2Ugc2VlIHRoYXQgd2l0aCBldmVyeSBhZGRpdGlvbmFsIHllYXIsIG9uIGF2ZXJhZ2UgY2FwaXRhbCBnYWlucyBpbmNyZWFzZSBieSAzOC40MyBkb2xsYXJzLCB3aGljaCBpcyBzdGF0aXN0aWNhbGx5IHNpZ25pZmljYW50IGF0IGEgOTklIGNvbmZpZGVuY2UgbGV2ZWwuDQoNCiMjI0FkZGluZyBZZWFycyBvZiBFZHVjYXRpb24gVmFyaWFibGUgVG8gdGhlIE1vZGVsDQpgYGB7cixtZXNzYWdlPUZBTFNFLCB3YXJuaW5nPUZBTFNFfQ0KbG0yIDwtIGxtKG5ld2luY29tZSB+IG5ld3NleCArIHJhY2UgKyBhZ2UgKyBlZHVjYXRpb24ubnVtLCBkYXRhID0gSW5jb21lMikNCnN1bW1hcnkobG0yKQ0KYGBgDQoNCkluIHRoaXMgbW9kZWwsIEkgYWRkZWQgdGhlIG51bWJlcnMgb2YgeWVhcnMgb2YgZWR1Y2F0aW9uIHZhcmlhYmxlLiBUaGlzIHRpbWUgd2Ugc2VlIHRoYXQgb24gYXZlcmFnZSB3b21lbiBtYWtlIDU5OC4yNyBkb2xsYXJzIGxlc3MgdGhhbiBtZW4gaW4gY2FwaXRhbCBnYWlucyBhbmQgdGhhdCB0aGlzIGlzIHN0aWxsIHN0YXRpc3RpY2FsbHkgc2lnbmlmaWNhbnQgYSA5OSUgY29uZmlkZW5jZSBsZXZlbC4gTmV4dCwgd2Ugc2VlIHRoYXQgQXNpYW4vUGFjaWZpYyBJc2xhbmRlciBpbmRpdmlkdWFscyBtYWtlIG9uIGF2ZXJhZ2UgMTk0Ljk3IGRvbGxhcnMgbW9yZSBpbiBjYXBpdGFsIGdhaW5zIHRoYW4gdGhlaXIgQW1lcmljYW4tSW5kaWFuL0Vza2ltbyBjb3VudGVycGFydHMuIE5leHQsIHdlIHNlZSB0aGF0IEJsYWNrIGluZGl2aWR1YWxzIG1ha2Ugb24gYXZlcmFnZSA1MS43NSBkb2xsYXJzIGxlc3MgaW4gY2FwaXRhbCBnYWlucyB0aGFuIHRoZWlyIEFtZXJpY2FuLUluZGlhbi9Fc2tpbW8gY291bnRlcnBhcnRzIGFuZCBpbmRpdmlkdWFscyBpbiB0aGUgT3RoZXIgcmFjZXMgY2F0ZWdvcnkgbWFrZSBvbiBhdmVyYWdlIDU4NC42MiBkb2xsYXJzIG1vcmUgaW4gY2FwaXRhbCBnYWlucyB0aGFuIHRoZWlyIEFtZXJpY2FuLUluZGlhbi9Fc2tpbW8gY291bnRlcnBhcnRzLiBXaGl0ZSBpbmRpdmlkdWFscyBtYWtlIG9uIGF2ZXJhZ2UgNjYuNzUgZG9sbGFycyBtb3JlIGluIGNhcGl0YWwgZ2FpbnMgdGhhbiB0aGVpciBBbWVyaWNhbi1JbmRpYW4vRXNraW1vIGNvdW50ZXJwYXJ0cy4gQWdhaW4sIGFjcm9zcyBhbGwgcmFjZXMgdGhlIHZhbHVlcyB3ZXJlIG5vdCBzdGF0aXN0aWNhbGx5IHNpZ25pZmljYW50IGF0IGFsbC4gRmluYWxseSwgZm9yIHRoZSBhZ2UgdmFyaWFibGUgd2Ugc2VlIHRoYXQgd2l0aCBldmVyeSBhZGRpdGlvbmFsIHllYXIsIG9uIGF2ZXJhZ2UgY2FwaXRhbCBnYWlucyBpbmNyZWFzZSBieSAzNi4zMiBkb2xsYXJzIGFuZCB3aXRoIGV2ZXJ5IGFkZGl0aW9uYWwgeWVhciBvZiBlZHVjYXRpb24gY2FwaXRhbCBnYWlucyBpbmNyZWFzZSBvbiBhdmVyYWdlIGJ5IDMzMC4zMCBkb2xsYXJzLiBCb3RoIG51bWJlcnMgYXJlIHN0YXRpc3RpY2FsbHkgc2lnbmlmaWNhbnQgYXQgYSA5OSUgY29uZmlkZW5jZSBsZXZlbC4NCg0KIyMjTG9va2luZyBhdCB0aGUgaW50ZXJhY3Rpb24gYmV0d2VlbiByYWNlIGFuZCBzZXgNCmBgYHtyLG1lc3NhZ2U9RkFMU0UsIHdhcm5pbmc9RkFMU0V9DQpsbTMgPC0gbG0obmV3aW5jb21lIH4gbmV3c2V4KnJhY2UgKyBhZ2UgKyBlZHVjYXRpb24ubnVtLCBkYXRhID0gSW5jb21lMikNCnN1bW1hcnkobG0zKQ0KYGBgDQoNCkZvciB0aGlzIG1vZGVsIEkgbG9va2VkIGF0IHRoZSBpbnRlcmFjdGlvbiBiZXR3ZWVuIHNleCBhbmQgcmFjZSB3aXRoIHJlc3BlY3QgdG8gIHdoZXRoZXIgYW4gaW5kaXZpZHVhbCBoYXMgYSBjYXBpdGFsIGdhaW4gb3IgbG9zcyB0byBzZWUgd2hldGhlciB0aGVyZSBhcmUgZGlmZmVyZW5jZXMgYWNyb3NzIGJvdGggZ2VuZGVycyBhbmQgZGlmZmVyZW50IHJhY2VzLiBJIGNob3NlIHRoZSBpbnRlcmFjdGlvbiBiZXR3ZWVuIHJhY2UgYW5kIGdlbmRlciB0byBnZXQgYSBjbG9zZXIgbG9vayBhdCBpbmNvbWUgZGlzY3JlcGFuY2llcy4NCg0KSW4gdGhpcyBpbnRlcmFjdGlvbiwgdGhlIGludGVyY2VwdCAoLTM3MTEuNjE1KSByZXByZXNlbnRzIG1hbGUgaW5kaXZpZHVhbHMgb2YgQW1lcmljYW4tSW5kaWFuL0Vza2ltbyByYWNlLiBOb3cgd2Ugc2VlIHRoYXQgb24gYXZlcmFnZSBmZW1hbGVzIG1ha2UgMzAxLjYyMSBkb2xsYXJzIGxlc3MgdGhhbiBtZW4gaW4gY2FwaXRhbCBnYWlucy4gTmV4dCB3ZSBzZWUgdGhhdCBBc2lhbi1QYWMtSXNsYW5kZXIgbWFsZXMgbWFrZSBvbiBhdmVyYWdlIDI5My45OTEgZG9sbGFycyBtb3JlIHRoYW4gdGhlaXIgQW1lcmljYW4tSW5kaWFuL0Vza2ltbyBjb3VudGVycGFydHMuIE5leHQgd2Ugc2VlIHRoYXQgQmxhY2sgbWFsZXMgbWFrZSBvbiBhdmVyYWdlIDEzNC4zNzkgZG9sbGFycyBsZXNzIHRoYW4gdGhlaXIgQW1lcmljYW4tSW5kaWFuL0Vza2ltbyBjb3VudGVycGFydHMsIG1hbGVzIG9mIG90aGVyIHJhY2VzIG1ha2Ugb24gYXZlcmFnZSA4NjcuMjAwIGRvbGxhcnMgbW9yZSB0aGFuIHRoZWlyIEFtZXJpY2FuLUluZGlhbi9Fc2tpbW8gY291bnRlcnBhcnRzIGFuZCBXaGl0ZSBtYWxlcyBtYWtlIG9uIGF2ZXJhZ2UgMTk3LjQwMCBkb2xsYXJzIG1vcmUgdGhhbiB0aGVpciBBbWVyaWNhbi1JbmRpYW4vRXNraW1vIGNvdW50ZXJwYXJ0cy4gDQpGb3IgZWFjaCBhZGRpdGlvbmFsIHllYXIgaW4gYWdlIG9uIGF2ZXJhZ2UgY2FwaXRhbCBnYWlucyBpbmNyZWFzZSBieSAzNi4xNTggZG9sbGFycyBhbmQgZm9yIGVhY2ggYWRkaXRpb25hbCBpbiB5ZWFyIGluIGVkdWNhdGlvbiBjYXBpdGFsIGdhaW5zIGluY3JlYXNlIG9uIGF2ZXJhZ2UgYnkgMzMwLjExNiBkb2xsYXJzLiBOZXh0LCBBc2lhbi9QYWMgSXNsYW5kZXIgZmVtYWxlcyBtYWtlIG9uIGF2ZXJhZ2UgMjUxLjg4OSBkb2xsYXJzIGxlc3MgaW4gY2FwaXRhbCBnYWlucyB0aGFuIHRoZWlyIEFtZXJpY2FuLUluZGlhbi9Fc2tpbW8gY291bnRlcnBhcnRzIGFuZCBCbGFjayBmZW1hbGVzIG1ha2Ugb24gYXZlcmFnZSA5Ny40OTEgZG9sbGFycyBtb3JlIHRoYW4gdGhlaXIgQW1lcmljYW4tSW5kaWFuL0Vza2ltbyBjb3VudGVycGFydHMgaW4gY2FwaXRhbCBnYWlucy4gRmluYWxseSwgZmVtYWxlcyBmcm9tIG90aGVyIHJhY2VzIG1ha2Ugb24gYXZlcmFnZSA3MTguNzQyIGRvbGxhcnMgbGVzcyB0aGFuIHRoZWlyIEFtZXJpY2FuLUluZGlhbi9Fc2tpbW8gY291bnRlcnBhcnRzIGluIGNhcGl0YWwgZ2FpbnMgYW5kIFdoaXRlIGZlbWFsZXMgbWFrZSBvbiBhdmVyYWdlIDM1MC4zNzMgZG9sbGFycyBsZXNzIHRoYW4gdGhlaXIgQW1lcmljYW4tSW5kaWFuL0Vza2ltbyBjb3VudGVycGFydHMuIFdlIHNlZSB0aGF0IGluIHRoaXMgbW9kZWwgdGhhdCBvbmx5IHRoZSB2YWx1ZXMgZm9yIGFnZSBhbmQgeWVhcnMgb2YgZWR1Y2F0aW9uIGFyZSBzdGF0aXN0aWNhbGx5IHNpZ25pZmljYW50IGF0IGEgOTklIGNvbmZpZGVuY2UgbGV2ZWwuDQoNCg0KYGBge3IsbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCkluY29tZTMgPC0gSW5jb21lMiAlPiUNCiAgc2VsZWN0KG5ld2luY29tZSwgbmV3c2V4LCByYWNlICkgJT4lIA0KICBncm91cF9ieShuZXdzZXgsIHJhY2UpICU+JQ0KICBzdW1tYXJpc2UobWVhbiA9IG1lYW4obmV3aW5jb21lKSkNCkluY29tZTMNCmBgYA0KDQpJbiB0aGlzIHN0ZXAsIEkgY3JlYXRlZCBhbm90aGVyIGRhdGEgc2V0IGNhbGxlZCAiSW5jb21lMyIgd2hpY2ggaGFzIGEgZ3JvdXAtd2lzZSBzdW1tYXJ5IHN0YXRpc3RpY3Mgb2YgdGhlIGRlcGVuZGVudCB2YXJpYWJsZSBhbmQgd2hlcmUgd2UgaGF2ZSB0aGUgbWVhbnMgZm9yIGVhY2ggcmFjZSBhbmQgc2V4IGdyb3VwLCBzaG93aW5nIHRoZSBhdmVyYWdlIGNhcGl0YWwgZ2FpbnMgZm9yIGVhY2ggZ3JvdXBpbmcuIEZvciBhY2N1cmFjeSBvZiB0aGUgaW50ZXJwcmV0YXRpb24gb2YgdGhlIHJlc3VsdHMgSSB3aWxsIHZlcmlmeSB0aGUgcmVzdWx0cyBvZiB0aGUgcmVncmVzc2lvbiB3aXRoIHRoZSBpbnRlcmFjdGlvbiB0ZXJtcyB3aXRoIHRoZSByZXN1bHRzIG9mIHRoZSBzdW1tYXJ5IHN0YXRpc3RpY3MuIEkgd2lsbCBjb21wYXJlIHRoZSBkaWZmZXJlbmNlcyBhbW9uZyBnZW5kZXJzIGZvciBlYWNoIHJhY2UgZ3JvdXAgYnkgc3VidHJhY3RpbmcgdGhlIG1hbGUgYW5kIGZlbWFsZSB2YWx1ZXMgZm9yIGVhY2ggcmFjZSBncm91cCBmb3IgYm90aCB0aGUgcmVncmVzc2lvbiByZXN1bHRzIGFuZCB0aGUgc3VtbWFyeS4gTmV4dCwgSSB3aWxsIGxvb2sgaWYgdGhlIGRpZmZlcmVuY2VzIGJldHdlZW4gdGhlIHJlZ3Jlc3Npb24gYW5kIHRoZSBzdW1tYXJ5IGFuZCBzaWduaWZpY2FudCBvciBub3QuIA0KICAgICAgIA0KKipHZW5kZXIgZGlmZmVyZW5jZXMgYW1vbmcgQXNpYW4gbWFsZXMgJiBmZW1hbGVzOioqDQoNCiogRm9yIHRoZSByZWdyZXNzaW9uIHdlIHNpbXBseSBsb29rIGF0IHRoZSBkaWZmZXJlbmNlIGJldHdlZW4gdGhlIGNhcGl0YWwgZ2FpbnMgdmFsdWVzIGZvciBBc2lhbiBNYWxlcyAoMjkzLjk5MSkgYW5kIEFzaWFuIEZlbWFsZXMgKC0yNTEuODg5KSwgd2hpY2ggaXMgNDIuMTAyIGRvbGxhcnMuDQoqIEZvciB0aGUgc3VtbWFyeSBzdGF0aXN0aWNzIHdlIGxvb2sgYXQgdGhlIGRpZmZlcmVuY2UgaW4gY2FwaXRhbCBnYWlucyBhdmVyYWdlcyBmb3IgQXNpYW4gTWFsZXMgKDE3MDcuNDQwMSkgYW5kIEFzaWFuIEZlbWFsZXMgKDcyNy41ODM4KSB3aGljaCBpcyA5NzkuODU2MyBkb2xsYXJzLg0KDQpUaGlzIHNob3dzIGEgbGFyZ2UgZGlmZmVyZW5jZSBiZXR3ZWVuIHRoZSB0d28gcmVzdWx0cy4NCiANCioqR2VuZGVyIGRpZmZlcmVuY2VzIGFtb25nIEJsYWNrIG1hbGVzIGFuZCBmZW1hbGVzOioqDQoNCiogRm9yIHRoZSByZWdyZXNzaW9uIHdlIHNpbXBseSBsb29rIGF0IHRoZSBkaWZmZXJlbmNlIGJldHdlZW4gdGhlIGNhcGl0YWwgZ2FpbnMgdmFsdWVzIGZvciBCbGFjayBNYWxlcyAoMTM0LjM3OSkgYW5kIEJsYWNrIEZlbWFsZXMgKDk3LjQ5MSksIHdoaWNoIGlzIDM2Ljg4OCBkb2xsYXJzLg0KKiBGb3IgdGhlIHN1bW1hcnkgc3RhdGlzdGljcyB3ZSBsb29rIGF0IHRoZSBkaWZmZXJlbmNlIGluIGNhcGl0YWwgZ2FpbnMgYXZlcmFnZXMgZm9yIEJsYWNrIE1hbGVzICg2MjcuMjY4MykgYW5kIEJsYWNrIEZlbWFsZXMgKDQ3MS4xNDI4KSB3aGljaCBpcyAxNTYuMTI1NSBkb2xsYXJzLg0KDQpXZSBzZWUgYWdhaW4gbGFyZ2UgZGlmZmVyZW5jZXMgZnJvbSBib3RoIHJlc3VsdHMuDQoNCioqR2VuZGVyIGRpZmZlcmVuY2VzIGFtb25nIE90aGVyIHJhY2VzIG1hbGVzIGFuZCBmZW1hbGVzOioqDQoNCiogRm9yIHRoZSByZWdyZXNzaW9uIHdlIHNpbXBseSBsb29rIGF0IHRoZSBkaWZmZXJlbmNlIGJldHdlZW4gdGhlIGNhcGl0YWwgZ2FpbnMgdmFsdWVzIGZvciBPdGhlciBNYWxlcyAoODY3LjIwMCkgYW5kIE90aGVyIEZlbWFsZXMgKC03MTguNDcyKSwgd2hpY2ggaXMgMTQ4LjQ1OCBkb2xsYXJzLg0KKiBGb3IgdGhlIHN1bW1hcnkgc3RhdGlzdGljcyB3ZSBsb29rIGF0IHRoZSBkaWZmZXJlbmNlIGluIGNhcGl0YWwgZ2FpbnMgYXZlcmFnZXMgZm9yIE90aGVyIE1hbGVzICgxMzE0LjQzODMpIGFuZCBPdGhlciBGZW1hbGVzICgyMTguMzg1Mykgd2hpY2ggaXMgMTA5Ni4wNTMgZG9sbGFycy4NCg0KRm9yIHRoaXMgZ3JvdXAgd2UgYWxzbyBzZWUgbGFyZ2UgZGlmZmVyZW5jZXMgZnJvbSBib3RoIHJlc3VsdHMuDQoNCioqR2VuZGVyIGRpZmZlcmVuY2VzIGFtb25nIFdoaXRlIG1hbGVzIGFuZCBmZW1hbGVzOioqDQoNCiogRm9yIHRoZSByZWdyZXNzaW9uIHdlIHNpbXBseSBsb29rIGF0IHRoZSBkaWZmZXJlbmNlIGJldHdlZW4gdGhlIGNhcGl0YWwgZ2FpbnMgdmFsdWVzIGZvciBXaGl0ZSBNYWxlcyAoMTk3LjQpIGFuZCBXaGl0ZSBGZW1hbGVzICgtMzUwLjM3MyksIHdoaWNoIGlzIDE1Mi45NzMgZG9sbGFycy4NCiogRm9yIHRoZSBzdW1tYXJ5IHN0YXRpc3RpY3Mgd2UgbG9vayBhdCB0aGUgZGlmZmVyZW5jZSBpbiBjYXBpdGFsIGdhaW5zIGF2ZXJhZ2VzIGZvciBXaGl0ZSBNYWxlcyAoMTI2Ni40MTMxKSBhbmQgV2hpdGUgRmVtYWxlcyAoNTA4LjIxOTkpIHdoaWNoIGlzIDc1OC4xOTMyIGRvbGxhcnMuDQoNCkNoZWNraW5nIHRoZSByZWdyZXNzaW9uIGVzaW1hdGVzIGFnYWluc3QgdGhlIHN1bW1hcnkgcmVzdWx0cyBzdWdnZXN0IHRoYXQgdGhlIGZpbmRpbmdzIG9mIHRoZSByZWdyZXNzaW9uIHdpdGggdGhlIGludGVyYWN0aW9uIHRlcm0gYXJlIGFjY3VyYXRlIGFuZCBtYWtlIHNlbnNlLiBUaGlzIGlzIGJlY2F1c2UgYXMgdGhlIHJlZ3Jlc3Npb24gbW9kZWwgc2hvd2VkIHVzIHRoYXQsIGV2ZW4gd2l0aCB0aGUgaW50ZXJhY3Rpb24gdGVybSwgcmFjZSBhbmQgc2V4IGFyZSBub3Qgc3RhdGlzdGljYWxseSBzaWduaWZpY2FudCwgd2hpY2ggaXMgY29uZmlybWVkIGJ5IHRoZSBsYXJnZSBkZXZpYXRpb25zIGluIHRoZSByZXN1bHRzIGFuZCBtYWtlIHRob3NlIHR3byB2YXJpYWJsZXMgdW5yZWxpYWJsZSBmb3IgZXN0aW1hdGlvbi4NCg0KQmFzZWQgb24gdGhpcyBjb25jbHVzaW9uLCB3ZSB3aWxsIGdvIGJhY2sgdG8gdGhlIGxhc3QgbW9kZWwgYW5kIGxvb2sgYXQgdGhlIHR3byB2YXJpYWJsZXMgdGhhdCB3ZXJlIHN0YXRpc3RpY2FsbHkgc2lnbmlmaWNhbnQsIGFnZSBhbmQgeWVhcnMgb2YgZWR1Y2F0aW9uLg0KDQojI1N1bW1hcnkgU3RhdGlzdGljcyBmb3IgWWVhcnMgb2YgZWR1Y2F0aW9uIGFuZCBBZ2UNCmBgYHtyLG1lc3NhZ2U9RkFMU0UsIHdhcm5pbmc9RkFMU0V9DQpJbmNvbWU0IDwtIEluY29tZTIgJT4lDQogIHNlbGVjdChuZXdpbmNvbWUsIGVkdWNhdGlvbi5udW0pICU+JSANCiAgZ3JvdXBfYnkoZWR1Y2F0aW9uLm51bSkgJT4lDQogIHN1bW1hcmlzZShtZWFuID0gbWVhbihuZXdpbmNvbWUpKQ0KSW5jb21lNA0KYGBgDQogDQpJbiB0aGlzIHN0ZXAsIEkgY3JlYXRlZCBhbm90aGVyIGRhdGEgc2V0IGNhbGxlZCAiSW5jb21lNCIgd2hpY2ggaGFzIGEgZ3JvdXAtd2lzZSBzdW1tYXJ5IHN0YXRpc3RpY3Mgb2YgdGhlIGRlcGVuZGVudCB2YXJpYWJsZSBhbmQgd2hlcmUgd2UgaGF2ZSB0aGUgbWVhbnMgZm9yIGVhY2ggeWVhciBvZiBlZHVjYXRpb24gZ3JvdXAsIHNob3dpbmcgdGhlIGF2ZXJhZ2UgY2FwaXRhbCBnYWlucyBmb3IgZWFjaCBncm91cGluZy4gTG9va2luZyBhdCBib3RoIHJlc3VsdHMsIHdlIHNlZSB0aGF0IGFzIHllYXJzIG9mIGVkdWNhdGlvbiBpbmNyZWFzZSB3ZSBhbHNvIHNlZSBhbiBpbmNyZWFzZSBpbiBjYXBpdGFsIGdhaW5zLCBjb25maXJtaW5nIHRoZSByZWdyZXNzaW9uIHJlc3VsdHMgdGhhdCB5ZWFycyBvZiBlZHVjYXRpb24gaXMgc3RhdGlzdGljYWxseSBzaWduaWZpY2FudC4NCg0KIyNDb21wYXJpbmcgTW9kZWxzDQpgYGB7cixtZXNzYWdlPUZBTFNFLCB3YXJuaW5nPUZBTFNFLHJlc3VsdHM9J2FzaXMnfQ0KbGlicmFyeSh0ZXhyZWcpDQpodG1scmVnKGxpc3QobG0wLCBsbTEsIGxtMiwgbG0zKSkNCmBgYA0KDQpVc2luZyB0aGUgdGV4cmVnIHBhY2thZ2Ugd2UgcHV0IHRoZSByZXN1bHRzIG9mIHRoZSA0IG1vZGVscyBpbnRvIGEgdGFibGUgdG8gY29tcGFyZSB0aGUgcmVzdWx0cy4gRXZlbiB0aG91Z2ggdGhlIG1vZGVsIHdhcyBub3QgdmVyeSBzdWNjZXNzZnVsIGluIGV4cGxhaW5pbmcgc29tZSBvZiB0aGUgZmFjdG9ycyB0aGF0IGluZmx1ZW5jZSBjYXBpdGFsIGdhaW5zLCB3ZSB3ZXJlIGFibGUgdG8gc2xpZ2h0bHkgaW1wcm92ZSBpdCBmcm9tIGFuIFJeMiBvZiAwLjAwIGluIHRoZSBmaXJzdCBtb2RlbCB0byBhbiBSXjIgb2YgMC4wMiBpbiB0aGUgbGFzdCBtb2RlbC4gSW4gdGhpcyBjYXNlIFJeMiBtZWFucyB0aGF0IG91ciBtb2RlbCBleHBsYWlucyBvbmx5IDIlIG9mIHRoZSB2YXJpYXRpb25zIGluIHRoZSBkYXRhLiBUaGlzIG1lYW5zIHRoYXQgaW4gdGhlIGZ1dHVyZSwgd2UgbmVlZCB0byBzZWxlY3QgYmV0dGVyIGluZGVwZW5kZW50IHZhcmlhYmxlcyBhbmQgY2hvb3NlIG91ciBpbnRlcmFjdGlvbiB0ZXJtcyBtb3JlIGNhcmVmdWxseS4NCg0KIyNHcmFwaHMNClRoZSBmaXJzdCBncmFwaCBzaG93cyB0aGUgcmVsYXRpb25zaGlwIGJldHdlZW4gYWdlIGFuZCBjYXBpdGFsIGdhaW5zLg0KDQpgYGB7cixtZXNzYWdlPUZBTFNFLCB3YXJuaW5nPUZBTFNFfQ0KbGlicmFyeSh2aXNyZWcpDQp2aXNyZWcobG0yLCAiYWdlIiwgc2NhbGUgPSAicmVzcG9uc2UiKQ0KYGBgDQoNCkFzIGNvbmZpcm1lZCBieSBvdXIgcmVzdWx0cywgYWdlIHBvc2l0aXZlbHkgaW5mbHVlbmNlcyBjYXBpdGFsIGdhaW5zIGFzIHRoZSB2YXJpYWJsZSBpcyBzdGF0aXN0aWNhbGx5IHNpZ25pZmljYW50Lg0KDQpUaGUgc2Vjb25kIGdyYXBoIHNob3dzIHRoZSByZWxhdGlvbnNoaXAgYmV0d2VlbiB5ZWFycyBvZiBlZHVjYXRpb24gYW5kIGNhcGl0YWwgZ2FpbnMuDQoNCmBgYHtyLG1lc3NhZ2U9RkFMU0UsIHdhcm5pbmc9RkFMU0V9DQp2aXNyZWcobG0yLCAiZWR1Y2F0aW9uLm51bSIsIHNjYWxlID0gInJlc3BvbnNlIikNCmBgYA0KIA0KQWdhaW4sIHRoaXMgZ3JhcGggY29uZmlybXMgb3VyIHJlc3VsdHMgdGhhdCB5ZWFycyBvZiBlZHVjYXRpb24gcG9zaXRpdmVseSBpbmZsdWVuY2VzIGNhcGl0YWwgZ2FpbnMgYXMgdGhlIHZhcmlhYmxlIGlzIHN0YXRpc3RpY2FsbHkgc2lnbmlmaWNhbnQuDQoNCg0KRm9yIHRoZSB0aGlyZCBncmFwaCB3ZSBmaXJzdCBuZWVkIHRvIHJlY29kZSByYWNlIGludG8gYSBudW1lcmljYWwgdmFyaWFibGUsIGNyZWF0ZSBhIG5ldyBkYXRhIHNldCAoSW5jb21lNSkgYW5kIHJlLXJ1biB0aGUgbG0yIG1vZGVsIGFzIGxtb2RlbDUgLg0KYGBge3IsIG1lc3NhZ2U9RkFMU0UsIHdhcm5pbmc9RkFMU0V9DQpJbmNvbWU1IDwtIEluY29tZTIlPiUNCiAgbXV0YXRlKG5ld3JhY2UgPSBmYWN0b3IoaWZlbHNlKHJhY2UgPT0gIldoaXRlIiwgMSwNCiAgICAgICAgICAgICAgICBpZmVsc2UocmFjZSA9PSAiQXNpYW4tUGFjLUlzbGFuZGVyIiwgMiwNCiAgICAgICAgICAgICAgICBpZmVsc2UocmFjZSA9PSAiQmxhY2siLCAzLA0KICAgICAgICAgICAgICAgIGlmZWxzZShyYWNlID09ICJPdGhlciIsIDQsDQogICAgICAgICAgICAgICAgaWZlbHNlKHJhY2UgPT0gIkFtZXItSW5kaWFuLUVza2ltbyIsIDUsICJlcnJvciIpKSkpKSkpICAgICAgICAgICAgICAgICAgICANCkluY29tZTUNCmBgYA0KDQpgYGB7ciwgbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCmxtb2RlbDIgPC0gbG0obmV3aW5jb21lIH4gbmV3c2V4ICsgbmV3cmFjZSArIGFnZSArIGVkdWNhdGlvbi5udW0sIGRhdGEgPSBJbmNvbWU1KQ0Kc3VtbWFyeShsbW9kZWwyKQ0KYGBgDQoNCg0KYGBge3IsbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCnZpc3JlZyhsbW9kZWwyLCAibmV3cmFjZSIsIGJ5ID0gIm5ld3NleCIsIHNjYWxlID0gInJlc3BvbnNlIikNCmBgYCAgIA0KDQpMb29raW5nIGF0IHRoaXMgZ3JhcGgsIHdlIHNlZSB0aGUgZGlmZmVyZW5jZXMgaW4gY2FwaXRhbCBieSBnZW5kZXIsIGNsdXN0ZXJlZCBieSByYWNlLiBUaGlzIGdyYXBoIGZ1cnRoZXIgY29uZmlybXMgdGhhdCB0aGVyZSBpcyBub3QgYSBzdGF0aXN0aWNhbGx5IHNpZ25pZmljYW50IHJlbGF0aW9uc2hpcCBiZXR3ZWVuIHNleCwgcmFjZSBhbmQgY2FwaXRhbCBnYWlucy4NCg0KYGBge3IsbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCnZpc3JlZyhsbW9kZWwyLCAibmV3c2V4IiwgYnkgPSAibmV3cmFjZSIsIHNjYWxlID0gInJlc3BvbnNlIikNCmBgYCAgIA0KDQpOb3cgd2Ugc3dpdGNoZWQgZ2VuZGVyIGFuZCByYWNlIGFuZCB0aGUgZ3JhcGggc2hvd3MgdXMgY2FwaXRhbCBnYWlucyBieSByYWNlIGFuZCBjbHVzdGVyZWQgYnkgZ2VuZGVyLiBBZ2Fpbiwgd2UgZG9uJ3Qgc2VlIGEgc3RhdGlzdGljYWxseSBzaWduaWZpY2FudCByZWxhdGlvbnNoaXAgYmV0d2VlbiB0aGUgdmFyaWFibGVzLg0KDQoNCk5leHQsIHdlIHdpbGwgcmUtcnVuIHRoZSBsbTMgbW9kZWwgd2l0aCB0aGUgaW50ZXJhY3Rpb24gdGVybSBhbmQgbGFiZWwgaXQgbG1vZGVsMy4gRmluYWxseSwgd2Ugd2lsbCBnZW5lcmF0ZSB0aGUgbGFzdCBncmFwaC4NCg0KYGBge3IsbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCmxtb2RlbDMgPC0gbG0obmV3aW5jb21lIH4gbmV3c2V4Km5ld3JhY2UgKyBhZ2UgKyBlZHVjYXRpb24ubnVtLCBkYXRhID0gSW5jb21lNSkNCnN1bW1hcnkobG1vZGVsMykNCmBgYA0KDQpgYGB7ciwgbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRX0NCnZpc3JlZyhsbW9kZWwzLCAibmV3cmFjZSIsIGJ5ID0gIm5ld3NleCIsIHNjYWxlID0gInJlc3BvbnNlIikNCmBgYA0KDQpBZ2Fpbiwgd2UgY2FuIGNvbmZpcm0gbm8gc3RhdGlzdGljYWxseSBzaWduaWZpY2FudCBkaWZmZXJlbmNlcyBhbW9uZyBkaWZmZXJlbnQgcmFjZXMgYnkgZ2VuZGVyIHdoZW4gaXQgY29tZXMgdG8gY2FwaXRhbCBnYWlucy4gDQoNCiMjQ29uY2x1c2lvbg0KVXNpbmcgdGhlIHJlZ3Jlc3Npb24gbW9kZWxzLCB0aGUgc3VtbWFyeSBzdGF0aXN0aWNzIGFuZCB0aGUgZ3JhcGhzIHdlIGNhbiBzZWUgdGhhdCB0aGUgcmVsYXRpb25zaGlwIGJldHdlZW4gZ2VuZGVyLCByYWNlIGFuZCBjYXBpdGFsIGdhaW5zIGlzIG5vdCBzdGF0aXN0aWNhbGx5IHNpZ25pZmljYW50IGFuZCB0aGF0IHRoZXJlIGFyZSBubyBzaWduaWZpY2FudCBkaWZmZXJlbmNlcyBpbiBjYXBpdGFsIGdhaW5zOyBob3dldmVyLCBpbiBvdXIgbW9kZWxzIHRoZSB2YXJpYWJsZXMgdGhhdCBwcm92ZWQgdG8gYmUgc3RhdGlzdGljYWxseSBzaWduaWZpY2FudCBhcmUgYWdlIGFuZCB5ZWFycyBvZiBlZHVjYXRpb24sIGFzIGJvdGggdmFyaWFibGVzIHRlbmQgdG8gaW5jcmVhc2UgY2FwaXRhbCBnYWlucy4gDQo=