Introduction
For this project, we will be creating a Time Series. We will be
working on decomposing this time series and forecasting with
decomposing. The data set I found for this project looks at the sale
prices for homes that have been sold from 2007 to 2019 in the United
States. This data set includes the sale prices of these various homes
over this course of 12 years.
We will use this data set to create a monthly time series to analyze
these home sale prices along with any sort of trends that there may be.
Using this monthly time series, we will look at the trends in home sale
prices by month, meaning we will find the average home sale price for
each month over the course of 2007 to 2019. This will allow us to
analyze the time series and look for trends occurring across the many
months which the data was collected over the course of. We will work on
decomposing this monthly time series of the average home sale prices and
will use forecasting with decomposing for this analysis of the time
series data.
Data Description
I found this data set on kaggle.com on the following webpage: https://www.kaggle.com/datasets/htagholdings/property-sales?select=raw_sales.csv
This data set looks at the sale prices for homes that have been
recorded from 2007 to 2019. The first observation was collected on
February 6, 2007, and the final observation in the data set was
collected on July 26, 2019. The sale prices are given in US dollars, and
were collected to look at the trends amongst the sale prices of homes in
this particular region.
We will read in the data set from Github and we will call it
“home”.
home <- read.csv("https://raw.githubusercontent.com/JosieGallop/STA321/refs/heads/main/dataset/raw_sales.csv")
The original data set contains multiple variables looking at things
such as the postcode of the house, the type of property it is, and the
number of bedrooms in the house. However, for this project, we are just
looking at creating a time series with the variable of house sale
prices. So, we will only be interested in the home sale price and the
date of which the house was sold. For this time series project, we will
look at the monthly averages of the home sale prices in order to create
a monthly time series which we will use for analysis to see if there are
any notable patterns we can see from the monthly time series.
Variables
The two variables which we are interested in looking at for this time
series project include:
datesold: The date on which the house was sold. This is given in
the format of year-month-day time”, for example, “2007-02-07 00:00:00”.
This is a variable used for identifying each observation of house sales.
We will adjust this variable to represent the year and the month of
which the home sales were collected in order to create a monthly time
series report.
price: The price for which a house was sold for, given in US
dollars. This is a quantitative, numerical variable which we are
interested in observing the trends of over time. We will adjust this
variable to represent the average home sale price for a specific month
of a specific year in order to create a monthly time series
report.
We will create a monthly time series which observed and analyzes the
trends and patterns seen in the average home sale prices by month over
the course of 2007 to 2019.
Exploratory Data
Analysis
Before we create our time series object, let’s ensure that there are
no missing values in the original data set, “home”.
colSums(is.na(home))
datesold postcode price propertyType bedrooms
0 0 0 0 0
As we can see, there are zero missing values in our data set, so that
means we do not have to worry about filling in any missing observations.
We can proceed with creating our time series object.
Time Series Data
Prepartion
We will adjust the data to create our monthly time series. This will
allow us to analyze the monthly trends in home sale prices over the
years of which this data was collected.
We will start by creating a new data set called “home1” with just the
variables of datesold and price.
home1 <- data.frame(home$datesold, home$price)
home1$datesold <- home1$home.datesold
home1$price <- home1$home.price
home1 <- select(home1, -1,-2)
For this time series project, we will create a monthly time series.
This will take a look at the average home sale price from each month of
which the data set was collected from. This will allow us to look for
trends and patterns across the monthly average sale prices that have
been observed from the span of 2007 to 2019.
The datesold variable includes dates that are given in the format of
“Year-Month-Day hour:minute:second”. While scrolling through the data
set entries, I noticed that the time portion of every data entry was
given as 00:00:00. This means that all of the observations were recorded
exactly at midnight. All of the observations have this exact same time
as their recorded date, so we will drop the time portion from the
datesold variable to make it easier to interpret, as well as to make it
easier to create our monthly average time series.
We will start by dropping the time component from the observations
and the date of which the home sale occurred. This will leave us with
just a “Year-Month-Day” format for the entries of the datesold
variable.
home1$datesold <- as.Date(ymd_hms(home1$datesold))
Next, we will calculate the average home sale price per month in
order to create a data set which we can use to create a montly time
series. The variable datesold will now be given in the format
“Year-Month” and the price variable will represent the average home sale
price for that specific month. We will create a new data set called
“home2” to store this updated version of the data which we will use for
our monthly time series.
home2 <- home1 %>%
mutate(datesold = format(datesold, "%Y-%m")) %>%
group_by(datesold) %>%
summarise(price = mean(price, na.rm = TRUE))
There are exactly 150 observations in this revised data set which
looks at the average home sale prices by month, so we do not need to
drop any observations from the data set since this is an ideal amount to
use for a time series.
Time Series Plot
Now, let’s create a time series object from our data and plot it to
help visualize any potential trends that may be occurring within this
time series object. We will call this time series object “home.ts”.
Since we are creating a monthly time series looking at the average home
sale prices by month, our frequency will be 12.
home.ts <- ts(home2$price, start = c(2007, 1), frequency = 12)
plot(home.ts, main="Monthly Average Home Sale Prices from 2007 to 2019", xlab = "Year", ylab = "Price")

Looking at the time series plot, it appears that there are several
patterns and trends going on within this monthly time series of the home
sale prices from 2007 to 2019. There appears to be some sort of
seasonality which can be seen by the various peaks and drops which
appears to be repeating after some period of time. We will look further
into any potential seasonality in this time series with the
decomposition methods.
Additionally, there appears to be a major peak and drop around the
start of the time series at around 2007 to 2008. This reaches much
higher than any other portion of the time series and is evidence of
something unusual which could be going on at this point. It is possible
that there was some major event occurring within the housing market at
this point which could have led to a massive rise and then a sudden fall
in the average sale prices of homes at the time.
Also, it appears that home sale prices have gradually increased from
the start of the time series in 2007 to the end of the time series in
2019. We can see that the average home sale price has continuously risen
over the course of this time series. This could suggest an additive or
multiplicative trend. In this case, it appears to be more of a
multiplicative trend as the seasonal variation does appear to have grown
and gotten more dramatic over time rather than staying identical
regardless of the year.
Forecasting with
Classical Decomposing
First, let’s begin with looking at a classical decomposition of our
time series data.
# Classical Decomposition
cls.decomp = decompose(home.ts)
par(mar = c(2,2,2,2))
plot(cls.decomp, xlab = "Year")

As we can see in our plot, most of the house prices range between
$300,000 and $800,000.
There appears to be something interesting going on at the beginning
of the time series plot. There is a very sharp peak around 2007 to 2008,
with a major spike much higher than anything around it. This is in fact
the observation with the highest price in the entire time series plot,
reaching up to $800,000, so this is something of interest from the data.
After doing some research, there was a major financial crisis which
occurred from 2007 to 2008 which marked a huge economic recession. It
would make sense that a big financial crisis like this would also have a
significant effect on the housing market, so this is likely why there is
such a sharp and sudden peak in home sale prices around 2007 to
2008.
There does appear to be some sort of seasonal trend going on within
the data as seen by the various peaks and drops that can be seen within
the plot. This shows evidence of some sort of seasonality occurring.
This seasonal pattern appears to repeat over each year, with the highest
and lowest peaks occurring within the span of each year period.
A seasonal trend would make sense for a data set relating to house
sale prices as the time of year could affect the number of individuals
buying a new home, and thus sale prices rising to meet this larger
demand. For instance, times of year such as the summer may see an
increase of buyers looking for a new house due to the ideal weather and
the timing of summer break making it ideal to buy a house before the
next school year begins if the buyers have children. This greater demand
could lead to a rise in the sales prices of the homes, and could be a
potential explanation for this seasonal trend we see in the time series
plot.
Additionally, there appears to be an overall increase in home sale
prices from 2007 to 2019. Looking at the trend curve, we can see that
there has been an overall, gradual increase in the home sale prices from
the start of this data set’s collection to the end of its collection.
So, we can conclude that the home sale prices have gradually increased
from what they were in 2007 to what they became in 2019.
Forecasting with STL
Decomposing
Next, let’s use STL decomposition on our time series data.
# STL Decomposition
stl.decomp = stl(home.ts, s.window = "periodic")
par(mar = c(2,2,2,2))
plot(stl.decomp)

Using this STL decomposition method provides several advantages to
the classical decomposition method we used previously. The STL
decomposition method uses locally estimated scatterplot smoothing, also
known as LOESS, to estimate non-linear trends with greater accuracy in
its forecasting than using the classical decomposition would
provide.
These plots created with the STL decomposition method allow us to
observe some of the trends and patterns of our time series data.
Overall, these plots generated by the STL decomposition provide similar
findings to those created in the previous classical decomposition
method. We see a similar overall trend, with various peaks and falls
over the course of the data being collected from 2007 to 2019 by monthly
averages of the home sale prices.
We also see a similar seasonal pattern that repeats multiple times
over the course of the time which the data was collected. This once
again matches with the idea of an annual seasonality, as it appears like
this seasonal pattern appears to repeat for each year that occurs over
the course of the time series data collection. Additionally, similar to
what was found in the classical decomposition method, is that there is a
significant, notable peak around the start of the time series in 2007 to
2008 which shows the highest home sales prices out of the entire data
set. This major peak around 2007 to 2008 is the highest average home
sales prices which was observed throughout the time series data
collection. Furthermore, we can see the overall trend of a gradual
increase in the home sale prices from 2007 to 2019. This can be seen in
the trend curve by how the average home sale prices have gradually risen
and increased from the start of the time series data collection in 2007
to the end of the time series in 2019. These patterns found by the STL
decomposition method match up with what was observed previously, and
this STL decomposition method provides greater accuracy in its
forecasting.
Training and Testing
Data Sets
Next, let’s look into creating a training and a testing data set to
forecast the time series model.
We will use the last seven observations to make up our testing data
set, and we will try out four different potential sizes for the training
data set. The four different sizes I will try out for the training data
set are n = 100, n = 70, n= 50, and n = 35. This will be the number of
observations which are used in the training data set.
data = home.ts
n0 = length(data)
train.data1 = home.ts[43:(n0-7)]
train.data2 = home.ts[73:(n0-7)]
train.data3 = home.ts[93:(n0-7)]
train.data4 = home.ts[108:(n0-7)]
# The testing data set will be the last 7 observations.
test.data = home.ts[(n0-6):n0]
# Creating the four potential training data set sizes.
train1.ts = ts(train.data1, frequency = 12, start = c(2007-02, 1))
train2.ts = ts(train.data2, frequency = 12, start = c(2010-01, 1))
train3.ts = ts(train.data3, frequency = 12, start = c(2013-01, 1))
train4.ts = ts(train.data4, frequency = 12, start = c(2015-01, 1))
stl1 = stl(train1.ts, s.window = 12)
stl2 = stl(train2.ts, s.window = 12)
stl3 = stl(train3.ts, s.window = 12)
stl4 = stl(train4.ts, s.window = 12)
Next, let’s create the objects for forecasting.
# Forecasting
fcst1 = forecast(stl1,h = 7, method = "naive")
fcst2 = forecast(stl2,h = 7, method = "naive")
fcst3 = forecast(stl3,h = 7, method = "naive")
fcst4 = forecast(stl4,h = 7, method = "naive")
We will perform error analysis to help us determine which size is
best for the training data set out of the four potential sizes we are
going to be choosing between. We will look at both the mean absolute
prediction error (MAPE) and the mean squared error (MSE) of the
potential training data sets.
PE1 = (test.data-fcst1$mean)/fcst1$mean
PE2 = (test.data-fcst2$mean)/fcst2$mean
PE3 = (test.data-fcst3$mean)/fcst3$mean
PE4 = (test.data-fcst4$mean)/fcst4$mean
# Mean Absolute Prediction Errors.
MAPE1 = mean(abs(PE1))
MAPE2 = mean(abs(PE2))
MAPE3 = mean(abs(PE3))
MAPE4 = mean(abs(PE4))
E1 = test.data-fcst1$mean
E2 = test.data-fcst2$mean
E3 = test.data-fcst3$mean
E4 = test.data-fcst4$mean
# Mean Squared Errors.
MSE1 = mean(E1^2)
MSE2 = mean(E2^2)
MSE3 = mean(E3^2)
MSE4 = mean(E4^2)
MSE = c(MSE1, MSE2, MSE3, MSE4)
MAPE = c(MAPE1, MAPE2, MAPE3, MAPE4)
accuracy = cbind(MSE = MSE, MAPE = MAPE)
row.names(accuracy) = c("n = 100", "n = 70", "n = 50", "n = 35")
kable(accuracy, caption = "Error Comparison of the Forecast Results with Different Training Data Set Sizes")
Error Comparison of the Forecast Results with Different
Training Data Set Sizes
n = 100 |
1206113411 |
0.0421218 |
n = 70 |
1246521262 |
0.0443203 |
n = 50 |
1365242537 |
0.0486566 |
n = 35 |
1292631907 |
0.0484141 |
As we can see, the training data set with a size of n = 100 has the
lowest of both the MSE and the MAPE out of the four potential training
data set sizes that were looked at. This suggests that this size is the
most ideal out of the potential options as it reduces the errors the
most out of the four options that were considered.
We will create a visualization to compare these forecast errors and
confirm the finding that a sample size of 100 observations reduces the
errors most out of the potential sample sizes that were considered for
the training data set of the time series.
First, let’s look at a plot of the mean squared errors (MSE) for each
of the four potential sample sizes.
# Plot of the MSE.
plot(1:4, MSE, type = "b", col="darkorchid", ylab = "Errors", xlab = "Sample Size",
main = "MSE", axes = FALSE)
labs = c("n = 100", "n = 70", "n = 50", "n = 35")
axis(1, at = 1:4, label = labs)
axis(2)

As we can see, n = 100 observations has the lowest MSE out of the
four potential sample sizes, indicating that it is the ideal choice,
because it reduces the errors.
We will also look at the plot of the mean absolute prediction errors
(MAPE) for each of the four potential training data set sizes.
# Plot of the MAPE.
plot(1:4, MAPE, type = "b", col="darkorchid", ylab = "Errors", xlab = "Sample Size",
main = "MAPE", axes = FALSE)
labs = c("n = 100", "n = 70", "n = 50", "n = 35")
axis(1, at = 1:4, label = labs)
axis(2)

Once again, the sample size of n = 100 observations shows the lowest
value of the MAPE, showing that is the ideal choice out of the four
sample sizes, because it reduces the errors.
As we can see in the plots for both the MSE and the MAPE, n = 100
observations shows the lowest errors, and as the sample size decreases
in the number of observations, the errors for both the MSE and the MAPE
increase, resulting in errors much greater than those of the sample size
with 100 observations. This strengthens that the ideal training data set
size out of the four options that were considered is a size of 100
observations. A training data set with 100 observations yields the best
performance, because it reduces the errors.
So, we can conclude that from the choices of a training data set with
100, 70, 50, or 35 observations, the best choice is the training data
set with 100 observations. This choice of 100 observations results in
the lowest errors, and therefore, provides the best performance for
forecasting our time series.
Forecasting the
Upcoming Months
We will use forecasting to provide an estimate for the upcoming
months after the end of the time series data collection. This time
series collected data up until July 2019, so we will forecast the
estimated home sale prices for the months which follow the end of this
data collection.
We will use an exponential smoothing method for this forecasting.
This will allow us to forecast the next twelve months of average home
sale prices by the month. Since our time series stopped at July 2019,
this forecasting will provide estimates of monthly average home sale
prices up through June 2020.
We stated previosuly that there appeared to be a multiplicative trend
occurring within this time series. This was seen by how the seasonal
variation appeared to increase over time along with the overall gradual
increase in monthly average home sales. We will reflect this
multiplicative trend with the exponential smoothing forecast.
ets <- ets(home.ts, model = "MAM")
forecast <- forecast(ets, h = 12)
plot(forecast, main = "Forecast of the Average Home Sale Prices \n for the Next 12 Months")

As we can see, this plot illustrates the forecast for the next twelve
months after the end of the time series. This forecast provides an
estimate for what the average home sale prices will look like for the
next twelve months.
We can see what the specific estimated home sale prices are for each
of the next twelve months after July 2019.
forecast$mean
Jan Feb Mar Apr May Jun Jul Aug
2019 633256.4 669327.5
2020 648920.1 671477.6 728994.7 658684.8 665938.5 660994.9
Sep Oct Nov Dec
2019 658924.8 691939.7 671194.7 624725.1
2020
We can see that the month with the highest forecasted price is March
2020 with a forecasted average home sale price of $728,994.70. The month
with the lowest forecasted price is December 2019 with a forecasted
average home sale price of $624,725.10.
Conclusion
In this project, we created a time series of the monthly average home
sales prices that were collected from the span of 2007 to 2019. We
analyzed the trends and patterns of this time series to make note of any
findings which stood out. One notable aspect of this time series was
that it showed a seasonal pattern, with what looked like an annual
seasonality. It was evident that there was some sort of a seasonal
pattern within the home sales prices which repeated after a certain
period of time, which appeared to be annually. The time series plot
showed that this pattern appeared to repeat on approximately an annual
basis, with the home sales prices going through different phases of
highs and lows over the course of each year. Both the classical
decomposition method and the STL decomposition method confirmed the
presence of this seasonal trend within the data for this time series of
the home sales prices.
Another notable finding in this time series project was that there
appeared to be an overall increase in the average home sale prices from
the beginning of the time series data collection in 2007 to the end of
the data collection in 2019. It appeared that home sale prices gradually
increased over the course of this 12 year period of the data collection.
The time series plots as well as the decomposition plots for the time
series showed evidence of this increase in the average home sale prices
from 2007 to 2019.
Additionally, we looked at four potential sample sizes to use for a
training data set in order to determine which number of observations
would be ideal to use. The four potential sizes for the training data
set which we looked at were n = 100, 70, 50, and 35 observations. It
turned out that the sample size of n = 100 observations was the ideal
choice out of these four options, because it resulted in the lowest
errors, as seen by how it had the lowest values for both its MSE and its
MAPE. This indicates that the sample size of 100 observations provides
the best utility for the training set, because it reduces the
errors.
We also used exponential smoothing methods to forecast the following
twelve months after the end of the time series data collection. This
provided forecasted predictions for the average home sale prices up
through June of 2020.
Recommendations
Some recommendations I would make for future projects include:
Overall, it appeared like there was an annual seasonality in this
particular time series done on the observed values of the sales prices
of houses over the span of 2007 to 2019. Some potential reasons were
given to provide an explanation for this seasonal trend, such as more
individuals buying houses in the summer leading the an increase in sales
prices. To further strengthen the evidence of this seasonal trend,
future projects could look further into this to see if this is indeed a
common pattern with records of house sales prices.
Future projects could look into trying out even more different
training data set sizes to see if there is another one which would work
even better than the ones that we tried out in this project. We looked
at four potential sizes for the training data set to see which one
provided the best accuracy, and found that n = 100 observations provided
the best utility by reducing the errors. However, perhaps future
projects could try out even more different sizes to see if there is one
which provides even better accuracy by reducing the errors.
Overall, this time series projects provided insight into some of the
patterns and trends surrounding the monthly average home sale prices
from the span of time from 2007 to 2019. The seasonality and trends
which were observed show that the sales prices of homes is something
which goes through cycles of changes, and various highs and lows
throughout the span of time.
LS0tDQp0aXRsZTogIkhvdXNlIFNhbGUgUHJpY2VzIGZyb20gMjAwNyB0byAyMDE5OiBUaW1lIFNlcmllcyBGb3JlY2FzdGluZyB3aXRoIERlY29tcG9zaXRpb24iDQphdXRob3I6ICJKb3NpZSBHYWxsb3AiDQpkYXRlOiAiMjAyNC0xMS0xOCINCm91dHB1dDoNCiAgaHRtbF9kb2N1bWVudDogDQogICAgdG9jOiB5ZXMNCiAgICB0b2NfZGVwdGg6IDQNCiAgICB0b2NfZmxvYXQ6IHllcw0KICAgIGZpZ193aWR0aDogNg0KICAgIGZpZ19jYXB0aW9uOiB5ZXMNCiAgICBudW1iZXJfc2VjdGlvbnM6IHllcw0KICAgIHRvY19jb2xsYXBzZWQ6IHllcw0KICAgIGNvZGVfZm9sZGluZzogaGlkZQ0KICAgIGNvZGVfZG93bmxvYWQ6IHllcw0KICAgIHNtb290aF9zY3JvbGw6IHllcw0KICAgIHRoZW1lOiBsdW1lbg0KICB3b3JkX2RvY3VtZW50OiANCiAgICB0b2M6IHllcw0KICAgIHRvY19kZXB0aDogNA0KICAgIGZpZ19jYXB0aW9uOiB5ZXMNCiAgICBrZWVwX21kOiB5ZXMNCiAgcGRmX2RvY3VtZW50OiANCiAgICB0b2M6IHllcw0KICAgIHRvY19kZXB0aDogNA0KICAgIGZpZ19jYXB0aW9uOiB5ZXMNCiAgICBudW1iZXJfc2VjdGlvbnM6IHllcw0KZWRpdG9yX29wdGlvbnM6IA0KICBjaHVua19vdXRwdXRfdHlwZTogY29uc29sZQ0KLS0tDQoNCmBgYHs9aHRtbH0NCg0KPHN0eWxlIHR5cGU9InRleHQvY3NzIj4NCg0KLyogQ2FzY2FkaW5nIFN0eWxlIFNoZWV0cyAoQ1NTKSBpcyBhIHN0eWxlc2hlZXQgbGFuZ3VhZ2UgdXNlZCB0byBkZXNjcmliZSB0aGUgcHJlc2VudGF0aW9uIG9mIGEgZG9jdW1lbnQgd3JpdHRlbiBpbiBIVE1MIG9yIFhNTC4gaXQgaXMgYSBzaW1wbGUgbWVjaGFuaXNtIGZvciBhZGRpbmcgc3R5bGUgKGUuZy4sIGZvbnRzLCBjb2xvcnMsIHNwYWNpbmcpIHRvIFdlYiBkb2N1bWVudHMuICovDQoNCmgxLnRpdGxlIHsgIC8qIFRpdGxlIC0gZm9udCBzcGVjaWZpY2F0aW9ucyBvZiB0aGUgcmVwb3J0IHRpdGxlICovDQogIGZvbnQtc2l6ZTogMjRweDsNCiAgY29sb3I6IERhcmtSZWQ7DQogIHRleHQtYWxpZ246IGNlbnRlcjsNCiAgZm9udC1mYW1pbHk6ICJHaWxsIFNhbnMiLCBzYW5zLXNlcmlmOw0KfQ0KaDQuYXV0aG9yIHsgLyogSGVhZGVyIDQgLSBmb250IHNwZWNpZmljYXRpb25zIGZvciBhdXRob3JzICAqLw0KICBmb250LXNpemU6IDIwcHg7DQogIGZvbnQtZmFtaWx5OiBzeXN0ZW0tdWk7DQogIGNvbG9yOiBEYXJrUmVkOw0KICB0ZXh0LWFsaWduOiBjZW50ZXI7DQp9DQpoNC5kYXRlIHsgLyogSGVhZGVyIDQgLSBmb250IHNwZWNpZmljYXRpb25zIGZvciB0aGUgZGF0ZSAgKi8NCiAgZm9udC1zaXplOiAxOHB4Ow0KICBmb250LWZhbWlseTogc3lzdGVtLXVpOw0KICBjb2xvcjogRGFya0JsdWU7DQogIHRleHQtYWxpZ246IGNlbnRlcjsNCn0NCmgxIHsgLyogSGVhZGVyIDEgLSBmb250IHNwZWNpZmljYXRpb25zIGZvciBsZXZlbCAxIHNlY3Rpb24gdGl0bGUgICovDQogICAgZm9udC1zaXplOiAyMnB4Ow0KICAgIGZvbnQtZmFtaWx5OiAiVGltZXMgTmV3IFJvbWFuIiwgVGltZXMsIHNlcmlmOw0KICAgIGNvbG9yOiBuYXZ5Ow0KICAgIHRleHQtYWxpZ246IGNlbnRlcjsNCn0NCmgyIHsgLyogSGVhZGVyIDIgLSBmb250IHNwZWNpZmljYXRpb25zIGZvciBsZXZlbCAyIHNlY3Rpb24gdGl0bGUgKi8NCiAgICBmb250LXNpemU6IDIwcHg7DQogICAgZm9udC1mYW1pbHk6ICJUaW1lcyBOZXcgUm9tYW4iLCBUaW1lcywgc2VyaWY7DQogICAgY29sb3I6IG5hdnk7DQogICAgdGV4dC1hbGlnbjogbGVmdDsNCn0NCg0KaDMgeyAvKiBIZWFkZXIgMyAtIGZvbnQgc3BlY2lmaWNhdGlvbnMgb2YgbGV2ZWwgMyBzZWN0aW9uIHRpdGxlICAqLw0KICAgIGZvbnQtc2l6ZTogMThweDsNCiAgICBmb250LWZhbWlseTogIlRpbWVzIE5ldyBSb21hbiIsIFRpbWVzLCBzZXJpZjsNCiAgICBjb2xvcjogbmF2eTsNCiAgICB0ZXh0LWFsaWduOiBsZWZ0Ow0KfQ0KDQpoNCB7IC8qIEhlYWRlciA0IC0gZm9udCBzcGVjaWZpY2F0aW9ucyBvZiBsZXZlbCA0IHNlY3Rpb24gdGl0bGUgICovDQogICAgZm9udC1zaXplOiAxOHB4Ow0KICAgIGZvbnQtZmFtaWx5OiAiVGltZXMgTmV3IFJvbWFuIiwgVGltZXMsIHNlcmlmOw0KICAgIGNvbG9yOiBkYXJrcmVkOw0KICAgIHRleHQtYWxpZ246IGxlZnQ7DQp9DQoNCmJvZHkgeyBiYWNrZ3JvdW5kLWNvbG9yOndoaXRlOyB9DQoNCi5oaWdobGlnaHRtZSB7IGJhY2tncm91bmQtY29sb3I6eWVsbG93OyB9DQoNCnAgeyBiYWNrZ3JvdW5kLWNvbG9yOndoaXRlOyB9DQoNCjwvc3R5bGU+DQpgYGANCmBgYHtyIHNldHVwLCBpbmNsdWRlPUZBTFNFfQ0KIyBEZXRlY3QsIGluc3RhbGwsIGFuZCBsb2FkIHBhY2thZ2VzIGlmIG5lZWRlZC4NCmlmICghcmVxdWlyZSgia25pdHIiKSkgew0KICAgaW5zdGFsbC5wYWNrYWdlcygia25pdHIiKQ0KICAgbGlicmFyeShrbml0cikNCn0NCmlmICghcmVxdWlyZSgibGVhZmxldCIpKSB7DQogICBpbnN0YWxsLnBhY2thZ2VzKCJsZWFmbGV0IikNCiAgIGxpYnJhcnkobGVhZmxldCkNCn0NCmlmICghcmVxdWlyZSgiRW52U3RhdHMiKSkgew0KICAgaW5zdGFsbC5wYWNrYWdlcygiRW52U3RhdHMiKQ0KICAgbGlicmFyeShFbnZTdGF0cykNCn0NCmlmICghcmVxdWlyZSgiTUFTUyIpKSB7DQogICBpbnN0YWxsLnBhY2thZ2VzKCJNQVNTIikNCiAgIGxpYnJhcnkoTUFTUykNCn0NCmlmICghcmVxdWlyZSgicGh5dG9vbHMiKSkgew0KICAgaW5zdGFsbC5wYWNrYWdlcygicGh5dG9vbHMiKQ0KICAgbGlicmFyeShwaHl0b29scykNCn0NCmlmKCFyZXF1aXJlKCJkcGx5ciIpKSB7DQogICBpbnN0YWxsLnBhY2thZ2VzKCJkcGx5ciIpDQogICBsaWJyYXJ5KGRwbHlyKQ0KfQ0KaWYoIXJlcXVpcmUoInRpZHl2ZXJzZSIpKSB7DQogICBpbnN0YWxsLnBhY2thZ2VzKCJ0aWR5dmVyc2UiKQ0KICAgbGlicmFyeSh0aWR5dmVyc2UpDQp9DQppZighcmVxdWlyZSgiR0dhbGx5IikpIHsNCiAgIGluc3RhbGwucGFja2FnZXMoIkdHYWxseSIpDQogICBsaWJyYXJ5KEdHYWxseSkNCn0NCmlmICghcmVxdWlyZSgiYm9vdCIpKSB7DQogICBpbnN0YWxsLnBhY2thZ2VzKCJib290IikNCiAgIGxpYnJhcnkoYm9vdCkNCn0NCmlmKCFyZXF1aXJlKCJwYW5kZXIiKSkgew0KICAgaW5zdGFsbC5wYWNrYWdlcygicGFuZGVyIikNCiAgIGxpYnJhcnkocGFuZGVyKQ0KfQ0KaWYoIXJlcXVpcmUoIm1sYmVuY2giKSkgew0KICAgaW5zdGFsbC5wYWNrYWdlcygibWxiZW5jaCIpDQogICBsaWJyYXJ5KG1sYmVuY2gpDQp9DQppZighcmVxdWlyZSgicHN5Y2giKSkgew0KICAgaW5zdGFsbC5wYWNrYWdlcygicHN5Y2giKQ0KICAgbGlicmFyeShwc3ljaCkNCn0NCmlmKCFyZXF1aXJlKCJsdWJyaWRhdGUiKSkgew0KICAgaW5zdGFsbC5wYWNrYWdlcygibHVicmlkYXRlIikNCiAgIGxpYnJhcnkobHVicmlkYXRlKQ0KfQ0KaWYoIXJlcXVpcmUoIkdHYWxseSIpKSB7DQogICBpbnN0YWxsLnBhY2thZ2VzKCJHR2FsbHkiKQ0KICAgbGlicmFyeShHR2FsbHkpDQp9DQppZiAoIXJlcXVpcmUoInBST0MiKSkgew0KICAgaW5zdGFsbC5wYWNrYWdlcygicFJPQyIpDQogICBsaWJyYXJ5KHBST0MpDQp9DQppZiAoIXJlcXVpcmUoImZvcmVjYXN0IikpIHsNCiAgIGluc3RhbGwucGFja2FnZXMoImZvcmVjYXN0IikNCiAgIGxpYnJhcnkoZm9yZWNhc3QpDQp9DQprbml0cjo6b3B0c19jaHVuayRzZXQoZWNobyA9IFRSVUUsICANCiAgICAgICAgICAgICAgICAgICB3YXJuaW5nID0gRkFMU0UsICAgDQogICAgICAgICAgICAgICAgICAgbWVzc2FnZSA9IEZBTFNFLCAgDQogICAgICAgICAgICAgICAgICAgcmVzdWx0cyA9IFRSVUUsICANCiAgICAgICAgICAgICAgICAgICBjb21tZW50ID0gTkEgICANCiAgICAgICAgICAgICAgICAgICAgICApICAgDQpgYGANCg0KDQojIEludHJvZHVjdGlvbg0KDQpGb3IgdGhpcyBwcm9qZWN0LCB3ZSB3aWxsIGJlIGNyZWF0aW5nIGEgVGltZSBTZXJpZXMuIFdlIHdpbGwgYmUgd29ya2luZyBvbiBkZWNvbXBvc2luZyB0aGlzIHRpbWUgc2VyaWVzIGFuZCBmb3JlY2FzdGluZyB3aXRoIGRlY29tcG9zaW5nLiBUaGUgZGF0YSBzZXQgSSBmb3VuZCBmb3IgdGhpcyBwcm9qZWN0IGxvb2tzIGF0IHRoZSBzYWxlIHByaWNlcyBmb3IgaG9tZXMgdGhhdCBoYXZlIGJlZW4gc29sZCBmcm9tIDIwMDcgdG8gMjAxOSBpbiB0aGUgVW5pdGVkIFN0YXRlcy4gVGhpcyBkYXRhIHNldCBpbmNsdWRlcyB0aGUgc2FsZSBwcmljZXMgb2YgdGhlc2UgdmFyaW91cyBob21lcyBvdmVyIHRoaXMgY291cnNlIG9mIDEyIHllYXJzLiANCg0KV2Ugd2lsbCB1c2UgdGhpcyBkYXRhIHNldCB0byBjcmVhdGUgYSBtb250aGx5IHRpbWUgc2VyaWVzIHRvIGFuYWx5emUgdGhlc2UgaG9tZSBzYWxlIHByaWNlcyBhbG9uZyB3aXRoIGFueSBzb3J0IG9mIHRyZW5kcyB0aGF0IHRoZXJlIG1heSBiZS4gVXNpbmcgdGhpcyBtb250aGx5IHRpbWUgc2VyaWVzLCB3ZSB3aWxsIGxvb2sgYXQgdGhlIHRyZW5kcyBpbiBob21lIHNhbGUgcHJpY2VzIGJ5IG1vbnRoLCBtZWFuaW5nIHdlIHdpbGwgZmluZCB0aGUgYXZlcmFnZSBob21lIHNhbGUgcHJpY2UgZm9yIGVhY2ggbW9udGggb3ZlciB0aGUgY291cnNlIG9mIDIwMDcgdG8gMjAxOS4gVGhpcyB3aWxsIGFsbG93IHVzIHRvIGFuYWx5emUgdGhlIHRpbWUgc2VyaWVzIGFuZCBsb29rIGZvciB0cmVuZHMgb2NjdXJyaW5nIGFjcm9zcyB0aGUgbWFueSBtb250aHMgd2hpY2ggdGhlIGRhdGEgd2FzIGNvbGxlY3RlZCBvdmVyIHRoZSBjb3Vyc2Ugb2YuIFdlIHdpbGwgd29yayBvbiBkZWNvbXBvc2luZyB0aGlzIG1vbnRobHkgdGltZSBzZXJpZXMgb2YgdGhlIGF2ZXJhZ2UgaG9tZSBzYWxlIHByaWNlcyBhbmQgd2lsbCB1c2UgZm9yZWNhc3Rpbmcgd2l0aCBkZWNvbXBvc2luZyBmb3IgdGhpcyBhbmFseXNpcyBvZiB0aGUgdGltZSBzZXJpZXMgZGF0YS4NCg0KDQoNCiMjIERhdGEgRGVzY3JpcHRpb24NCg0KSSBmb3VuZCB0aGlzIGRhdGEgc2V0IG9uIGthZ2dsZS5jb20gb24gdGhlIGZvbGxvd2luZyB3ZWJwYWdlOg0KaHR0cHM6Ly93d3cua2FnZ2xlLmNvbS9kYXRhc2V0cy9odGFnaG9sZGluZ3MvcHJvcGVydHktc2FsZXM/c2VsZWN0PXJhd19zYWxlcy5jc3YNCg0KVGhpcyBkYXRhIHNldCBsb29rcyBhdCB0aGUgc2FsZSBwcmljZXMgZm9yIGhvbWVzIHRoYXQgaGF2ZSBiZWVuIHJlY29yZGVkIGZyb20gMjAwNyB0byAyMDE5LiBUaGUgZmlyc3Qgb2JzZXJ2YXRpb24gd2FzIGNvbGxlY3RlZCBvbiBGZWJydWFyeSA2LCAyMDA3LCBhbmQgdGhlIGZpbmFsIG9ic2VydmF0aW9uIGluIHRoZSBkYXRhIHNldCB3YXMgY29sbGVjdGVkIG9uIEp1bHkgMjYsIDIwMTkuIFRoZSBzYWxlIHByaWNlcyBhcmUgZ2l2ZW4gaW4gVVMgZG9sbGFycywgYW5kIHdlcmUgY29sbGVjdGVkIHRvIGxvb2sgYXQgdGhlIHRyZW5kcyBhbW9uZ3N0IHRoZSBzYWxlIHByaWNlcyBvZiBob21lcyBpbiB0aGlzIHBhcnRpY3VsYXIgcmVnaW9uLiANCg0KV2Ugd2lsbCByZWFkIGluIHRoZSBkYXRhIHNldCBmcm9tIEdpdGh1YiBhbmQgd2Ugd2lsbCBjYWxsIGl0ICJob21lIi4gDQoNCmBgYHtyfQ0KaG9tZSA8LSByZWFkLmNzdigiaHR0cHM6Ly9yYXcuZ2l0aHVidXNlcmNvbnRlbnQuY29tL0pvc2llR2FsbG9wL1NUQTMyMS9yZWZzL2hlYWRzL21haW4vZGF0YXNldC9yYXdfc2FsZXMuY3N2IikNCmBgYA0KDQpUaGUgb3JpZ2luYWwgZGF0YSBzZXQgY29udGFpbnMgbXVsdGlwbGUgdmFyaWFibGVzIGxvb2tpbmcgYXQgdGhpbmdzIHN1Y2ggYXMgdGhlIHBvc3Rjb2RlIG9mIHRoZSBob3VzZSwgdGhlIHR5cGUgb2YgcHJvcGVydHkgaXQgaXMsIGFuZCB0aGUgbnVtYmVyIG9mIGJlZHJvb21zIGluIHRoZSBob3VzZS4gSG93ZXZlciwgZm9yIHRoaXMgcHJvamVjdCwgd2UgYXJlIGp1c3QgbG9va2luZyBhdCBjcmVhdGluZyBhIHRpbWUgc2VyaWVzIHdpdGggdGhlIHZhcmlhYmxlIG9mIGhvdXNlIHNhbGUgcHJpY2VzLiBTbywgd2Ugd2lsbCBvbmx5IGJlIGludGVyZXN0ZWQgaW4gdGhlIGhvbWUgc2FsZSBwcmljZSBhbmQgdGhlIGRhdGUgb2Ygd2hpY2ggdGhlIGhvdXNlIHdhcyBzb2xkLiBGb3IgdGhpcyB0aW1lIHNlcmllcyBwcm9qZWN0LCB3ZSB3aWxsIGxvb2sgYXQgdGhlIG1vbnRobHkgYXZlcmFnZXMgb2YgdGhlIGhvbWUgc2FsZSBwcmljZXMgaW4gb3JkZXIgdG8gY3JlYXRlIGEgbW9udGhseSB0aW1lIHNlcmllcyB3aGljaCB3ZSB3aWxsIHVzZSBmb3IgYW5hbHlzaXMgdG8gc2VlIGlmIHRoZXJlIGFyZSBhbnkgbm90YWJsZSBwYXR0ZXJucyB3ZSBjYW4gc2VlIGZyb20gdGhlIG1vbnRobHkgdGltZSBzZXJpZXMuDQoNCg0KIyMgVmFyaWFibGVzDQoNClRoZSB0d28gdmFyaWFibGVzIHdoaWNoIHdlIGFyZSBpbnRlcmVzdGVkIGluIGxvb2tpbmcgYXQgZm9yIHRoaXMgdGltZSBzZXJpZXMgcHJvamVjdCBpbmNsdWRlOg0KDQoqIGRhdGVzb2xkOiBUaGUgZGF0ZSBvbiB3aGljaCB0aGUgaG91c2Ugd2FzIHNvbGQuIFRoaXMgaXMgZ2l2ZW4gaW4gdGhlIGZvcm1hdCBvZiB5ZWFyLW1vbnRoLWRheSB0aW1lIiwgZm9yIGV4YW1wbGUsICIyMDA3LTAyLTA3IDAwOjAwOjAwIi4gVGhpcyBpcyBhIHZhcmlhYmxlIHVzZWQgZm9yIGlkZW50aWZ5aW5nIGVhY2ggb2JzZXJ2YXRpb24gb2YgaG91c2Ugc2FsZXMuIFdlIHdpbGwgYWRqdXN0IHRoaXMgdmFyaWFibGUgdG8gcmVwcmVzZW50IHRoZSB5ZWFyIGFuZCB0aGUgbW9udGggb2Ygd2hpY2ggdGhlIGhvbWUgc2FsZXMgd2VyZSBjb2xsZWN0ZWQgaW4gb3JkZXIgdG8gY3JlYXRlIGEgbW9udGhseSB0aW1lIHNlcmllcyByZXBvcnQuDQoNCiogcHJpY2U6IFRoZSBwcmljZSBmb3Igd2hpY2ggYSBob3VzZSB3YXMgc29sZCBmb3IsIGdpdmVuIGluIFVTIGRvbGxhcnMuIFRoaXMgaXMgYSBxdWFudGl0YXRpdmUsIG51bWVyaWNhbCB2YXJpYWJsZSB3aGljaCB3ZSBhcmUgaW50ZXJlc3RlZCBpbiBvYnNlcnZpbmcgdGhlIHRyZW5kcyBvZiBvdmVyIHRpbWUuIFdlIHdpbGwgYWRqdXN0IHRoaXMgdmFyaWFibGUgdG8gcmVwcmVzZW50IHRoZSBhdmVyYWdlIGhvbWUgc2FsZSBwcmljZSBmb3IgYSBzcGVjaWZpYyBtb250aCBvZiBhIHNwZWNpZmljIHllYXIgaW4gb3JkZXIgdG8gY3JlYXRlIGEgbW9udGhseSB0aW1lIHNlcmllcyByZXBvcnQuDQoNCldlIHdpbGwgY3JlYXRlIGEgbW9udGhseSB0aW1lIHNlcmllcyB3aGljaCBvYnNlcnZlZCBhbmQgYW5hbHl6ZXMgdGhlIHRyZW5kcyBhbmQgcGF0dGVybnMgc2VlbiBpbiB0aGUgYXZlcmFnZSBob21lIHNhbGUgcHJpY2VzIGJ5IG1vbnRoIG92ZXIgdGhlIGNvdXJzZSBvZiAyMDA3IHRvIDIwMTkuIA0KDQoNCg0KDQojIEV4cGxvcmF0b3J5IERhdGEgQW5hbHlzaXMNCg0KQmVmb3JlIHdlIGNyZWF0ZSBvdXIgdGltZSBzZXJpZXMgb2JqZWN0LCBsZXQncyBlbnN1cmUgdGhhdCB0aGVyZSBhcmUgbm8gbWlzc2luZyB2YWx1ZXMgaW4gdGhlIG9yaWdpbmFsIGRhdGEgc2V0LCAiaG9tZSIuIA0KDQpgYGB7cn0NCmNvbFN1bXMoaXMubmEoaG9tZSkpDQpgYGANCg0KQXMgd2UgY2FuIHNlZSwgdGhlcmUgYXJlIHplcm8gbWlzc2luZyB2YWx1ZXMgaW4gb3VyIGRhdGEgc2V0LCBzbyB0aGF0IG1lYW5zIHdlIGRvIG5vdCBoYXZlIHRvIHdvcnJ5IGFib3V0IGZpbGxpbmcgaW4gYW55IG1pc3Npbmcgb2JzZXJ2YXRpb25zLiBXZSBjYW4gcHJvY2VlZCB3aXRoIGNyZWF0aW5nIG91ciB0aW1lIHNlcmllcyBvYmplY3QuIA0KDQoNCg0KIyMgVGltZSBTZXJpZXMgRGF0YSBQcmVwYXJ0aW9uDQoNCldlIHdpbGwgYWRqdXN0IHRoZSBkYXRhIHRvIGNyZWF0ZSBvdXIgbW9udGhseSB0aW1lIHNlcmllcy4gVGhpcyB3aWxsIGFsbG93IHVzIHRvIGFuYWx5emUgdGhlIG1vbnRobHkgdHJlbmRzIGluIGhvbWUgc2FsZSBwcmljZXMgb3ZlciB0aGUgeWVhcnMgb2Ygd2hpY2ggdGhpcyBkYXRhIHdhcyBjb2xsZWN0ZWQuIA0KDQpXZSB3aWxsIHN0YXJ0IGJ5IGNyZWF0aW5nIGEgbmV3IGRhdGEgc2V0IGNhbGxlZCAiaG9tZTEiIHdpdGgganVzdCB0aGUgdmFyaWFibGVzIG9mIGRhdGVzb2xkIGFuZCBwcmljZS4gDQoNCmBgYHtyfQ0KaG9tZTEgPC0gZGF0YS5mcmFtZShob21lJGRhdGVzb2xkLCBob21lJHByaWNlKQ0KaG9tZTEkZGF0ZXNvbGQgPC0gaG9tZTEkaG9tZS5kYXRlc29sZA0KaG9tZTEkcHJpY2UgPC0gaG9tZTEkaG9tZS5wcmljZQ0KaG9tZTEgPC0gc2VsZWN0KGhvbWUxLCAtMSwtMikNCmBgYA0KDQpGb3IgdGhpcyB0aW1lIHNlcmllcyBwcm9qZWN0LCB3ZSB3aWxsIGNyZWF0ZSBhIG1vbnRobHkgdGltZSBzZXJpZXMuIFRoaXMgd2lsbCB0YWtlIGEgbG9vayBhdCB0aGUgYXZlcmFnZSBob21lIHNhbGUgcHJpY2UgZnJvbSBlYWNoIG1vbnRoIG9mIHdoaWNoIHRoZSBkYXRhIHNldCB3YXMgY29sbGVjdGVkIGZyb20uIFRoaXMgd2lsbCBhbGxvdyB1cyB0byBsb29rIGZvciB0cmVuZHMgYW5kIHBhdHRlcm5zIGFjcm9zcyB0aGUgbW9udGhseSBhdmVyYWdlIHNhbGUgcHJpY2VzIHRoYXQgaGF2ZSBiZWVuIG9ic2VydmVkIGZyb20gdGhlIHNwYW4gb2YgMjAwNyB0byAyMDE5LiANCg0KVGhlIGRhdGVzb2xkIHZhcmlhYmxlIGluY2x1ZGVzIGRhdGVzIHRoYXQgYXJlIGdpdmVuIGluIHRoZSBmb3JtYXQgb2YgIlllYXItTW9udGgtRGF5IGhvdXI6bWludXRlOnNlY29uZCIuIFdoaWxlIHNjcm9sbGluZyB0aHJvdWdoIHRoZSBkYXRhIHNldCBlbnRyaWVzLCBJIG5vdGljZWQgdGhhdCB0aGUgdGltZSBwb3J0aW9uIG9mIGV2ZXJ5IGRhdGEgZW50cnkgd2FzIGdpdmVuIGFzIDAwOjAwOjAwLiBUaGlzIG1lYW5zIHRoYXQgYWxsIG9mIHRoZSBvYnNlcnZhdGlvbnMgd2VyZSByZWNvcmRlZCBleGFjdGx5IGF0IG1pZG5pZ2h0LiBBbGwgb2YgdGhlIG9ic2VydmF0aW9ucyBoYXZlIHRoaXMgZXhhY3Qgc2FtZSB0aW1lIGFzIHRoZWlyIHJlY29yZGVkIGRhdGUsIHNvIHdlIHdpbGwgZHJvcCB0aGUgdGltZSBwb3J0aW9uIGZyb20gdGhlIGRhdGVzb2xkIHZhcmlhYmxlIHRvIG1ha2UgaXQgZWFzaWVyIHRvIGludGVycHJldCwgYXMgd2VsbCBhcyB0byBtYWtlIGl0IGVhc2llciB0byBjcmVhdGUgb3VyIG1vbnRobHkgYXZlcmFnZSB0aW1lIHNlcmllcy4gDQoNCldlIHdpbGwgc3RhcnQgYnkgZHJvcHBpbmcgdGhlIHRpbWUgY29tcG9uZW50IGZyb20gdGhlIG9ic2VydmF0aW9ucyBhbmQgdGhlIGRhdGUgb2Ygd2hpY2ggdGhlIGhvbWUgc2FsZSBvY2N1cnJlZC4gVGhpcyB3aWxsIGxlYXZlIHVzIHdpdGgganVzdCBhICJZZWFyLU1vbnRoLURheSIgZm9ybWF0IGZvciB0aGUgZW50cmllcyBvZiB0aGUgZGF0ZXNvbGQgdmFyaWFibGUuIA0KDQpgYGB7cn0NCmhvbWUxJGRhdGVzb2xkIDwtIGFzLkRhdGUoeW1kX2htcyhob21lMSRkYXRlc29sZCkpDQpgYGANCg0KTmV4dCwgd2Ugd2lsbCBjYWxjdWxhdGUgdGhlIGF2ZXJhZ2UgaG9tZSBzYWxlIHByaWNlIHBlciBtb250aCBpbiBvcmRlciB0byBjcmVhdGUgYSBkYXRhIHNldCB3aGljaCB3ZSBjYW4gdXNlIHRvIGNyZWF0ZSBhIG1vbnRseSB0aW1lIHNlcmllcy4gVGhlIHZhcmlhYmxlIGRhdGVzb2xkIHdpbGwgbm93IGJlIGdpdmVuIGluIHRoZSBmb3JtYXQgIlllYXItTW9udGgiIGFuZCB0aGUgcHJpY2UgdmFyaWFibGUgd2lsbCByZXByZXNlbnQgdGhlIGF2ZXJhZ2UgaG9tZSBzYWxlIHByaWNlIGZvciB0aGF0IHNwZWNpZmljIG1vbnRoLiBXZSB3aWxsIGNyZWF0ZSBhIG5ldyBkYXRhIHNldCBjYWxsZWQgImhvbWUyIiB0byBzdG9yZSB0aGlzIHVwZGF0ZWQgdmVyc2lvbiBvZiB0aGUgZGF0YSB3aGljaCB3ZSB3aWxsIHVzZSBmb3Igb3VyIG1vbnRobHkgdGltZSBzZXJpZXMuIA0KDQpgYGB7cn0NCmhvbWUyIDwtIGhvbWUxICU+JQ0KICBtdXRhdGUoZGF0ZXNvbGQgPSBmb3JtYXQoZGF0ZXNvbGQsICIlWS0lbSIpKSAlPiUNCiAgZ3JvdXBfYnkoZGF0ZXNvbGQpICU+JQ0KICBzdW1tYXJpc2UocHJpY2UgPSBtZWFuKHByaWNlLCBuYS5ybSA9IFRSVUUpKQ0KYGBgDQoNClRoZXJlIGFyZSBleGFjdGx5IDE1MCBvYnNlcnZhdGlvbnMgaW4gdGhpcyByZXZpc2VkIGRhdGEgc2V0IHdoaWNoIGxvb2tzIGF0IHRoZSBhdmVyYWdlIGhvbWUgc2FsZSBwcmljZXMgYnkgbW9udGgsIHNvIHdlIGRvIG5vdCBuZWVkIHRvIGRyb3AgYW55IG9ic2VydmF0aW9ucyBmcm9tIHRoZSBkYXRhIHNldCBzaW5jZSB0aGlzIGlzIGFuIGlkZWFsIGFtb3VudCB0byB1c2UgZm9yIGEgdGltZSBzZXJpZXMuIA0KDQoNCg0KIyMgVGltZSBTZXJpZXMgUGxvdA0KDQpOb3csIGxldCdzIGNyZWF0ZSBhIHRpbWUgc2VyaWVzIG9iamVjdCBmcm9tIG91ciBkYXRhIGFuZCBwbG90IGl0IHRvIGhlbHAgdmlzdWFsaXplIGFueSBwb3RlbnRpYWwgdHJlbmRzIHRoYXQgbWF5IGJlIG9jY3VycmluZyB3aXRoaW4gdGhpcyB0aW1lIHNlcmllcyBvYmplY3QuIFdlIHdpbGwgY2FsbCB0aGlzIHRpbWUgc2VyaWVzIG9iamVjdCAiaG9tZS50cyIuIFNpbmNlIHdlIGFyZSBjcmVhdGluZyBhIG1vbnRobHkgdGltZSBzZXJpZXMgbG9va2luZyBhdCB0aGUgYXZlcmFnZSBob21lIHNhbGUgcHJpY2VzIGJ5IG1vbnRoLCBvdXIgZnJlcXVlbmN5IHdpbGwgYmUgMTIuIA0KDQpgYGB7cn0NCmhvbWUudHMgPC0gdHMoaG9tZTIkcHJpY2UsIHN0YXJ0ID0gYygyMDA3LCAxKSwgZnJlcXVlbmN5ID0gMTIpDQpwbG90KGhvbWUudHMsIG1haW49Ik1vbnRobHkgQXZlcmFnZSBIb21lIFNhbGUgUHJpY2VzIGZyb20gMjAwNyB0byAyMDE5IiwgeGxhYiA9ICJZZWFyIiwgeWxhYiA9ICJQcmljZSIpDQpgYGANCg0KTG9va2luZyBhdCB0aGUgdGltZSBzZXJpZXMgcGxvdCwgaXQgYXBwZWFycyB0aGF0IHRoZXJlIGFyZSBzZXZlcmFsIHBhdHRlcm5zIGFuZCB0cmVuZHMgZ29pbmcgb24gd2l0aGluIHRoaXMgbW9udGhseSB0aW1lIHNlcmllcyBvZiB0aGUgaG9tZSBzYWxlIHByaWNlcyBmcm9tIDIwMDcgdG8gMjAxOS4gVGhlcmUgYXBwZWFycyB0byBiZSBzb21lIHNvcnQgb2Ygc2Vhc29uYWxpdHkgd2hpY2ggY2FuIGJlIHNlZW4gYnkgdGhlIHZhcmlvdXMgcGVha3MgYW5kIGRyb3BzIHdoaWNoIGFwcGVhcnMgdG8gYmUgcmVwZWF0aW5nIGFmdGVyIHNvbWUgcGVyaW9kIG9mIHRpbWUuIFdlIHdpbGwgbG9vayBmdXJ0aGVyIGludG8gYW55IHBvdGVudGlhbCBzZWFzb25hbGl0eSBpbiB0aGlzIHRpbWUgc2VyaWVzIHdpdGggdGhlIGRlY29tcG9zaXRpb24gbWV0aG9kcy4gDQoNCkFkZGl0aW9uYWxseSwgdGhlcmUgYXBwZWFycyB0byBiZSBhIG1ham9yIHBlYWsgYW5kIGRyb3AgYXJvdW5kIHRoZSBzdGFydCBvZiB0aGUgdGltZSBzZXJpZXMgYXQgYXJvdW5kIDIwMDcgdG8gMjAwOC4gVGhpcyByZWFjaGVzIG11Y2ggaGlnaGVyIHRoYW4gYW55IG90aGVyIHBvcnRpb24gb2YgdGhlIHRpbWUgc2VyaWVzIGFuZCBpcyBldmlkZW5jZSBvZiBzb21ldGhpbmcgdW51c3VhbCB3aGljaCBjb3VsZCBiZSBnb2luZyBvbiBhdCB0aGlzIHBvaW50LiBJdCBpcyBwb3NzaWJsZSB0aGF0IHRoZXJlIHdhcyBzb21lIG1ham9yIGV2ZW50IG9jY3VycmluZyB3aXRoaW4gdGhlIGhvdXNpbmcgbWFya2V0IGF0IHRoaXMgcG9pbnQgd2hpY2ggY291bGQgaGF2ZSBsZWQgdG8gYSBtYXNzaXZlIHJpc2UgYW5kIHRoZW4gYSBzdWRkZW4gZmFsbCBpbiB0aGUgYXZlcmFnZSBzYWxlIHByaWNlcyBvZiBob21lcyBhdCB0aGUgdGltZS4NCg0KQWxzbywgaXQgYXBwZWFycyB0aGF0IGhvbWUgc2FsZSBwcmljZXMgaGF2ZSBncmFkdWFsbHkgaW5jcmVhc2VkIGZyb20gdGhlIHN0YXJ0IG9mIHRoZSB0aW1lIHNlcmllcyBpbiAyMDA3IHRvIHRoZSBlbmQgb2YgdGhlIHRpbWUgc2VyaWVzIGluIDIwMTkuIFdlIGNhbiBzZWUgdGhhdCB0aGUgYXZlcmFnZSBob21lIHNhbGUgcHJpY2UgaGFzIGNvbnRpbnVvdXNseSByaXNlbiBvdmVyIHRoZSBjb3Vyc2Ugb2YgdGhpcyB0aW1lIHNlcmllcy4gVGhpcyBjb3VsZCBzdWdnZXN0IGFuIGFkZGl0aXZlIG9yIG11bHRpcGxpY2F0aXZlIHRyZW5kLiBJbiB0aGlzIGNhc2UsIGl0IGFwcGVhcnMgdG8gYmUgbW9yZSBvZiBhIG11bHRpcGxpY2F0aXZlIHRyZW5kIGFzIHRoZSBzZWFzb25hbCB2YXJpYXRpb24gZG9lcyBhcHBlYXIgdG8gaGF2ZSBncm93biBhbmQgZ290dGVuIG1vcmUgZHJhbWF0aWMgb3ZlciB0aW1lIHJhdGhlciB0aGFuIHN0YXlpbmcgaWRlbnRpY2FsIHJlZ2FyZGxlc3Mgb2YgdGhlIHllYXIuIA0KDQoNCg0KIyBGb3JlY2FzdGluZyB3aXRoIENsYXNzaWNhbCBEZWNvbXBvc2luZw0KDQpGaXJzdCwgbGV0J3MgYmVnaW4gd2l0aCBsb29raW5nIGF0IGEgY2xhc3NpY2FsIGRlY29tcG9zaXRpb24gb2Ygb3VyIHRpbWUgc2VyaWVzIGRhdGEuIA0KDQpgYGB7cn0NCiMgQ2xhc3NpY2FsIERlY29tcG9zaXRpb24NCmNscy5kZWNvbXAgPSBkZWNvbXBvc2UoaG9tZS50cykNCnBhcihtYXIgPSBjKDIsMiwyLDIpKQ0KcGxvdChjbHMuZGVjb21wLCB4bGFiID0gIlllYXIiKQ0KYGBgDQoNCkFzIHdlIGNhbiBzZWUgaW4gb3VyIHBsb3QsIG1vc3Qgb2YgdGhlIGhvdXNlIHByaWNlcyByYW5nZSBiZXR3ZWVuICQzMDAsMDAwIGFuZCAkODAwLDAwMC4gDQoNClRoZXJlIGFwcGVhcnMgdG8gYmUgc29tZXRoaW5nIGludGVyZXN0aW5nIGdvaW5nIG9uIGF0IHRoZSBiZWdpbm5pbmcgb2YgdGhlIHRpbWUgc2VyaWVzIHBsb3QuIFRoZXJlIGlzIGEgdmVyeSBzaGFycCBwZWFrIGFyb3VuZCAyMDA3IHRvIDIwMDgsIHdpdGggYSBtYWpvciBzcGlrZSBtdWNoIGhpZ2hlciB0aGFuIGFueXRoaW5nIGFyb3VuZCBpdC4gVGhpcyBpcyBpbiBmYWN0IHRoZSBvYnNlcnZhdGlvbiB3aXRoIHRoZSBoaWdoZXN0IHByaWNlIGluIHRoZSBlbnRpcmUgdGltZSBzZXJpZXMgcGxvdCwgcmVhY2hpbmcgdXAgdG8gJDgwMCwwMDAsIHNvIHRoaXMgaXMgc29tZXRoaW5nIG9mIGludGVyZXN0IGZyb20gdGhlIGRhdGEuIEFmdGVyIGRvaW5nIHNvbWUgcmVzZWFyY2gsIHRoZXJlIHdhcyBhIG1ham9yIGZpbmFuY2lhbCBjcmlzaXMgd2hpY2ggb2NjdXJyZWQgZnJvbSAyMDA3IHRvIDIwMDggd2hpY2ggbWFya2VkIGEgaHVnZSBlY29ub21pYyByZWNlc3Npb24uIEl0IHdvdWxkIG1ha2Ugc2Vuc2UgdGhhdCBhIGJpZyBmaW5hbmNpYWwgY3Jpc2lzIGxpa2UgdGhpcyB3b3VsZCBhbHNvIGhhdmUgYSBzaWduaWZpY2FudCBlZmZlY3Qgb24gdGhlIGhvdXNpbmcgbWFya2V0LCBzbyB0aGlzIGlzIGxpa2VseSB3aHkgdGhlcmUgaXMgc3VjaCBhIHNoYXJwIGFuZCBzdWRkZW4gcGVhayBpbiBob21lIHNhbGUgcHJpY2VzIGFyb3VuZCAyMDA3IHRvIDIwMDguIA0KDQpUaGVyZSBkb2VzIGFwcGVhciB0byBiZSBzb21lIHNvcnQgb2Ygc2Vhc29uYWwgdHJlbmQgZ29pbmcgb24gd2l0aGluIHRoZSBkYXRhIGFzIHNlZW4gYnkgdGhlIHZhcmlvdXMgcGVha3MgYW5kIGRyb3BzIHRoYXQgY2FuIGJlIHNlZW4gd2l0aGluIHRoZSBwbG90LiBUaGlzIHNob3dzIGV2aWRlbmNlIG9mIHNvbWUgc29ydCBvZiBzZWFzb25hbGl0eSBvY2N1cnJpbmcuIFRoaXMgc2Vhc29uYWwgcGF0dGVybiBhcHBlYXJzIHRvIHJlcGVhdCBvdmVyIGVhY2ggeWVhciwgd2l0aCB0aGUgaGlnaGVzdCBhbmQgbG93ZXN0IHBlYWtzIG9jY3VycmluZyB3aXRoaW4gdGhlIHNwYW4gb2YgZWFjaCB5ZWFyIHBlcmlvZC4gDQoNCkEgc2Vhc29uYWwgdHJlbmQgd291bGQgbWFrZSBzZW5zZSBmb3IgYSBkYXRhIHNldCByZWxhdGluZyB0byBob3VzZSBzYWxlIHByaWNlcyBhcyB0aGUgdGltZSBvZiB5ZWFyIGNvdWxkIGFmZmVjdCB0aGUgbnVtYmVyIG9mIGluZGl2aWR1YWxzIGJ1eWluZyBhIG5ldyBob21lLCBhbmQgdGh1cyBzYWxlIHByaWNlcyByaXNpbmcgdG8gbWVldCB0aGlzIGxhcmdlciBkZW1hbmQuIEZvciBpbnN0YW5jZSwgdGltZXMgb2YgeWVhciBzdWNoIGFzIHRoZSBzdW1tZXIgbWF5IHNlZSBhbiBpbmNyZWFzZSBvZiBidXllcnMgbG9va2luZyBmb3IgYSBuZXcgaG91c2UgZHVlIHRvIHRoZSBpZGVhbCB3ZWF0aGVyIGFuZCB0aGUgdGltaW5nIG9mIHN1bW1lciBicmVhayBtYWtpbmcgaXQgaWRlYWwgdG8gYnV5IGEgaG91c2UgYmVmb3JlIHRoZSBuZXh0IHNjaG9vbCB5ZWFyIGJlZ2lucyBpZiB0aGUgYnV5ZXJzIGhhdmUgY2hpbGRyZW4uIFRoaXMgZ3JlYXRlciBkZW1hbmQgY291bGQgbGVhZCB0byBhIHJpc2UgaW4gdGhlIHNhbGVzIHByaWNlcyBvZiB0aGUgaG9tZXMsIGFuZCBjb3VsZCBiZSBhIHBvdGVudGlhbCBleHBsYW5hdGlvbiBmb3IgdGhpcyBzZWFzb25hbCB0cmVuZCB3ZSBzZWUgaW4gdGhlIHRpbWUgc2VyaWVzIHBsb3QuIA0KDQpBZGRpdGlvbmFsbHksIHRoZXJlIGFwcGVhcnMgdG8gYmUgYW4gb3ZlcmFsbCBpbmNyZWFzZSBpbiBob21lIHNhbGUgcHJpY2VzIGZyb20gMjAwNyB0byAyMDE5LiBMb29raW5nIGF0IHRoZSB0cmVuZCBjdXJ2ZSwgd2UgY2FuIHNlZSB0aGF0IHRoZXJlIGhhcyBiZWVuIGFuIG92ZXJhbGwsIGdyYWR1YWwgaW5jcmVhc2UgaW4gdGhlIGhvbWUgc2FsZSBwcmljZXMgZnJvbSB0aGUgc3RhcnQgb2YgdGhpcyBkYXRhIHNldCdzIGNvbGxlY3Rpb24gdG8gdGhlIGVuZCBvZiBpdHMgY29sbGVjdGlvbi4gU28sIHdlIGNhbiBjb25jbHVkZSB0aGF0IHRoZSBob21lIHNhbGUgcHJpY2VzIGhhdmUgZ3JhZHVhbGx5IGluY3JlYXNlZCBmcm9tIHdoYXQgdGhleSB3ZXJlIGluIDIwMDcgdG8gd2hhdCB0aGV5IGJlY2FtZSBpbiAyMDE5LiANCg0KDQoNCg0KIyBGb3JlY2FzdGluZyB3aXRoIFNUTCBEZWNvbXBvc2luZyANCg0KTmV4dCwgbGV0J3MgdXNlIFNUTCBkZWNvbXBvc2l0aW9uIG9uIG91ciB0aW1lIHNlcmllcyBkYXRhLg0KDQpgYGB7cn0NCiMgU1RMIERlY29tcG9zaXRpb24NCnN0bC5kZWNvbXAgPSBzdGwoaG9tZS50cywgIHMud2luZG93ID0gInBlcmlvZGljIikNCnBhcihtYXIgPSBjKDIsMiwyLDIpKQ0KcGxvdChzdGwuZGVjb21wKQ0KYGBgDQoNClVzaW5nIHRoaXMgU1RMIGRlY29tcG9zaXRpb24gbWV0aG9kIHByb3ZpZGVzIHNldmVyYWwgYWR2YW50YWdlcyB0byB0aGUgY2xhc3NpY2FsIGRlY29tcG9zaXRpb24gbWV0aG9kIHdlIHVzZWQgcHJldmlvdXNseS4gVGhlIFNUTCBkZWNvbXBvc2l0aW9uIG1ldGhvZCB1c2VzIGxvY2FsbHkgZXN0aW1hdGVkIHNjYXR0ZXJwbG90IHNtb290aGluZywgYWxzbyBrbm93biBhcyBMT0VTUywgdG8gZXN0aW1hdGUgbm9uLWxpbmVhciB0cmVuZHMgd2l0aCBncmVhdGVyIGFjY3VyYWN5IGluIGl0cyBmb3JlY2FzdGluZyB0aGFuIHVzaW5nIHRoZSBjbGFzc2ljYWwgZGVjb21wb3NpdGlvbiB3b3VsZCBwcm92aWRlLiANCg0KVGhlc2UgcGxvdHMgY3JlYXRlZCB3aXRoIHRoZSBTVEwgZGVjb21wb3NpdGlvbiBtZXRob2QgYWxsb3cgdXMgdG8gb2JzZXJ2ZSBzb21lIG9mIHRoZSB0cmVuZHMgYW5kIHBhdHRlcm5zIG9mIG91ciB0aW1lIHNlcmllcyBkYXRhLiBPdmVyYWxsLCB0aGVzZSBwbG90cyBnZW5lcmF0ZWQgYnkgdGhlIFNUTCBkZWNvbXBvc2l0aW9uIHByb3ZpZGUgc2ltaWxhciBmaW5kaW5ncyB0byB0aG9zZSBjcmVhdGVkIGluIHRoZSBwcmV2aW91cyBjbGFzc2ljYWwgZGVjb21wb3NpdGlvbiBtZXRob2QuIFdlIHNlZSBhIHNpbWlsYXIgb3ZlcmFsbCB0cmVuZCwgd2l0aCB2YXJpb3VzIHBlYWtzIGFuZCBmYWxscyBvdmVyIHRoZSBjb3Vyc2Ugb2YgdGhlIGRhdGEgYmVpbmcgY29sbGVjdGVkIGZyb20gMjAwNyB0byAyMDE5IGJ5IG1vbnRobHkgYXZlcmFnZXMgb2YgdGhlIGhvbWUgc2FsZSBwcmljZXMuIA0KDQpXZSBhbHNvIHNlZSBhIHNpbWlsYXIgc2Vhc29uYWwgcGF0dGVybiB0aGF0IHJlcGVhdHMgbXVsdGlwbGUgdGltZXMgb3ZlciB0aGUgY291cnNlIG9mIHRoZSB0aW1lIHdoaWNoIHRoZSBkYXRhIHdhcyBjb2xsZWN0ZWQuIFRoaXMgb25jZSBhZ2FpbiBtYXRjaGVzIHdpdGggdGhlIGlkZWEgb2YgYW4gYW5udWFsIHNlYXNvbmFsaXR5LCBhcyBpdCBhcHBlYXJzIGxpa2UgdGhpcyBzZWFzb25hbCBwYXR0ZXJuIGFwcGVhcnMgdG8gcmVwZWF0IGZvciBlYWNoIHllYXIgdGhhdCBvY2N1cnMgb3ZlciB0aGUgY291cnNlIG9mIHRoZSB0aW1lIHNlcmllcyBkYXRhIGNvbGxlY3Rpb24uIEFkZGl0aW9uYWxseSwgc2ltaWxhciB0byB3aGF0IHdhcyBmb3VuZCBpbiB0aGUgY2xhc3NpY2FsIGRlY29tcG9zaXRpb24gbWV0aG9kLCBpcyB0aGF0IHRoZXJlIGlzIGEgc2lnbmlmaWNhbnQsIG5vdGFibGUgcGVhayBhcm91bmQgdGhlIHN0YXJ0IG9mIHRoZSB0aW1lIHNlcmllcyBpbiAyMDA3IHRvIDIwMDggd2hpY2ggc2hvd3MgdGhlIGhpZ2hlc3QgaG9tZSBzYWxlcyBwcmljZXMgb3V0IG9mIHRoZSBlbnRpcmUgZGF0YSBzZXQuIFRoaXMgbWFqb3IgcGVhayBhcm91bmQgMjAwNyB0byAyMDA4IGlzIHRoZSBoaWdoZXN0IGF2ZXJhZ2UgaG9tZSBzYWxlcyBwcmljZXMgd2hpY2ggd2FzIG9ic2VydmVkIHRocm91Z2hvdXQgdGhlIHRpbWUgc2VyaWVzIGRhdGEgY29sbGVjdGlvbi4gRnVydGhlcm1vcmUsIHdlIGNhbiBzZWUgdGhlIG92ZXJhbGwgdHJlbmQgb2YgYSBncmFkdWFsIGluY3JlYXNlIGluIHRoZSBob21lIHNhbGUgcHJpY2VzIGZyb20gMjAwNyB0byAyMDE5LiBUaGlzIGNhbiBiZSBzZWVuIGluIHRoZSB0cmVuZCBjdXJ2ZSBieSBob3cgdGhlIGF2ZXJhZ2UgaG9tZSBzYWxlIHByaWNlcyBoYXZlIGdyYWR1YWxseSByaXNlbiBhbmQgaW5jcmVhc2VkIGZyb20gdGhlIHN0YXJ0IG9mIHRoZSB0aW1lIHNlcmllcyBkYXRhIGNvbGxlY3Rpb24gaW4gMjAwNyB0byB0aGUgZW5kIG9mIHRoZSB0aW1lIHNlcmllcyBpbiAyMDE5LiBUaGVzZSBwYXR0ZXJucyBmb3VuZCBieSB0aGUgU1RMIGRlY29tcG9zaXRpb24gbWV0aG9kIG1hdGNoIHVwIHdpdGggd2hhdCB3YXMgb2JzZXJ2ZWQgcHJldmlvdXNseSwgYW5kIHRoaXMgU1RMIGRlY29tcG9zaXRpb24gbWV0aG9kIHByb3ZpZGVzIGdyZWF0ZXIgYWNjdXJhY3kgaW4gaXRzIGZvcmVjYXN0aW5nLiANCg0KDQoNCg0KIyBUcmFpbmluZyBhbmQgVGVzdGluZyBEYXRhIFNldHMNCg0KTmV4dCwgbGV0J3MgbG9vayBpbnRvIGNyZWF0aW5nIGEgdHJhaW5pbmcgYW5kIGEgdGVzdGluZyBkYXRhIHNldCB0byBmb3JlY2FzdCB0aGUgdGltZSBzZXJpZXMgbW9kZWwuIA0KDQpXZSB3aWxsIHVzZSB0aGUgbGFzdCBzZXZlbiBvYnNlcnZhdGlvbnMgdG8gbWFrZSB1cCBvdXIgdGVzdGluZyBkYXRhIHNldCwgYW5kIHdlIHdpbGwgdHJ5IG91dCBmb3VyIGRpZmZlcmVudCBwb3RlbnRpYWwgc2l6ZXMgZm9yIHRoZSB0cmFpbmluZyBkYXRhIHNldC4gVGhlIGZvdXIgZGlmZmVyZW50IHNpemVzIEkgd2lsbCB0cnkgb3V0IGZvciB0aGUgdHJhaW5pbmcgZGF0YSBzZXQgYXJlIG4gPSAxMDAsIG4gPSA3MCwgbj0gNTAsIGFuZCBuID0gMzUuIFRoaXMgd2lsbCBiZSB0aGUgbnVtYmVyIG9mIG9ic2VydmF0aW9ucyB3aGljaCBhcmUgdXNlZCBpbiB0aGUgdHJhaW5pbmcgZGF0YSBzZXQuIA0KDQoNCmBgYHtyfQ0KZGF0YSA9IGhvbWUudHMNCm4wID0gbGVuZ3RoKGRhdGEpDQp0cmFpbi5kYXRhMSA9IGhvbWUudHNbNDM6KG4wLTcpXQ0KdHJhaW4uZGF0YTIgPSBob21lLnRzWzczOihuMC03KV0NCnRyYWluLmRhdGEzID0gaG9tZS50c1s5MzoobjAtNyldDQp0cmFpbi5kYXRhNCA9IGhvbWUudHNbMTA4OihuMC03KV0NCg0KIyBUaGUgdGVzdGluZyBkYXRhIHNldCB3aWxsIGJlIHRoZSBsYXN0IDcgb2JzZXJ2YXRpb25zLg0KdGVzdC5kYXRhID0gaG9tZS50c1sobjAtNik6bjBdDQoNCiMgQ3JlYXRpbmcgdGhlIGZvdXIgcG90ZW50aWFsIHRyYWluaW5nIGRhdGEgc2V0IHNpemVzLg0KdHJhaW4xLnRzID0gdHModHJhaW4uZGF0YTEsIGZyZXF1ZW5jeSA9IDEyLCBzdGFydCA9IGMoMjAwNy0wMiwgMSkpDQp0cmFpbjIudHMgPSB0cyh0cmFpbi5kYXRhMiwgZnJlcXVlbmN5ID0gMTIsIHN0YXJ0ID0gYygyMDEwLTAxLCAxKSkNCnRyYWluMy50cyA9IHRzKHRyYWluLmRhdGEzLCBmcmVxdWVuY3kgPSAxMiwgc3RhcnQgPSBjKDIwMTMtMDEsIDEpKQ0KdHJhaW40LnRzID0gdHModHJhaW4uZGF0YTQsIGZyZXF1ZW5jeSA9IDEyLCBzdGFydCA9IGMoMjAxNS0wMSwgMSkpDQoNCnN0bDEgPSBzdGwodHJhaW4xLnRzLCBzLndpbmRvdyA9IDEyKQ0Kc3RsMiA9IHN0bCh0cmFpbjIudHMsIHMud2luZG93ID0gMTIpDQpzdGwzID0gc3RsKHRyYWluMy50cywgcy53aW5kb3cgPSAxMikNCnN0bDQgPSBzdGwodHJhaW40LnRzLCBzLndpbmRvdyA9IDEyKQ0KYGBgDQoNCk5leHQsIGxldCdzIGNyZWF0ZSB0aGUgb2JqZWN0cyBmb3IgZm9yZWNhc3RpbmcuDQoNCmBgYHtyfQ0KIyBGb3JlY2FzdGluZw0KZmNzdDEgPSBmb3JlY2FzdChzdGwxLGggPSA3LCBtZXRob2QgPSAibmFpdmUiKQ0KZmNzdDIgPSBmb3JlY2FzdChzdGwyLGggPSA3LCBtZXRob2QgPSAibmFpdmUiKQ0KZmNzdDMgPSBmb3JlY2FzdChzdGwzLGggPSA3LCBtZXRob2QgPSAibmFpdmUiKQ0KZmNzdDQgPSBmb3JlY2FzdChzdGw0LGggPSA3LCBtZXRob2QgPSAibmFpdmUiKQ0KYGBgDQoNCldlIHdpbGwgcGVyZm9ybSBlcnJvciBhbmFseXNpcyB0byBoZWxwIHVzIGRldGVybWluZSB3aGljaCBzaXplIGlzIGJlc3QgZm9yIHRoZSB0cmFpbmluZyBkYXRhIHNldCBvdXQgb2YgdGhlIGZvdXIgcG90ZW50aWFsIHNpemVzIHdlIGFyZSBnb2luZyB0byBiZSBjaG9vc2luZyBiZXR3ZWVuLiBXZSB3aWxsIGxvb2sgYXQgYm90aCB0aGUgbWVhbiBhYnNvbHV0ZSBwcmVkaWN0aW9uIGVycm9yIChNQVBFKSBhbmQgdGhlIG1lYW4gc3F1YXJlZCBlcnJvciAoTVNFKSBvZiB0aGUgcG90ZW50aWFsIHRyYWluaW5nIGRhdGEgc2V0cy4gDQoNCmBgYHtyfQ0KUEUxID0gKHRlc3QuZGF0YS1mY3N0MSRtZWFuKS9mY3N0MSRtZWFuDQpQRTIgPSAodGVzdC5kYXRhLWZjc3QyJG1lYW4pL2Zjc3QyJG1lYW4NClBFMyA9ICh0ZXN0LmRhdGEtZmNzdDMkbWVhbikvZmNzdDMkbWVhbg0KUEU0ID0gKHRlc3QuZGF0YS1mY3N0NCRtZWFuKS9mY3N0NCRtZWFuDQoNCiMgTWVhbiBBYnNvbHV0ZSBQcmVkaWN0aW9uIEVycm9ycy4NCk1BUEUxID0gbWVhbihhYnMoUEUxKSkNCk1BUEUyID0gbWVhbihhYnMoUEUyKSkNCk1BUEUzID0gbWVhbihhYnMoUEUzKSkNCk1BUEU0ID0gbWVhbihhYnMoUEU0KSkNCg0KRTEgPSB0ZXN0LmRhdGEtZmNzdDEkbWVhbg0KRTIgPSB0ZXN0LmRhdGEtZmNzdDIkbWVhbg0KRTMgPSB0ZXN0LmRhdGEtZmNzdDMkbWVhbg0KRTQgPSB0ZXN0LmRhdGEtZmNzdDQkbWVhbg0KDQojIE1lYW4gU3F1YXJlZCBFcnJvcnMuDQpNU0UxID0gbWVhbihFMV4yKQ0KTVNFMiA9IG1lYW4oRTJeMikNCk1TRTMgPSBtZWFuKEUzXjIpDQpNU0U0ID0gbWVhbihFNF4yKQ0KDQpNU0UgPSBjKE1TRTEsIE1TRTIsIE1TRTMsIE1TRTQpDQpNQVBFID0gYyhNQVBFMSwgTUFQRTIsIE1BUEUzLCBNQVBFNCkNCmFjY3VyYWN5ID0gY2JpbmQoTVNFID0gTVNFLCBNQVBFID0gTUFQRSkNCnJvdy5uYW1lcyhhY2N1cmFjeSkgPSBjKCJuID0gMTAwIiwgIm4gPSA3MCIsICJuID0gNTAiLCAibiA9IDM1IikNCmthYmxlKGFjY3VyYWN5LCBjYXB0aW9uID0gIkVycm9yIENvbXBhcmlzb24gb2YgdGhlIEZvcmVjYXN0IFJlc3VsdHMgd2l0aCBEaWZmZXJlbnQgVHJhaW5pbmcgRGF0YSBTZXQgU2l6ZXMiKQ0KYGBgDQoNCkFzIHdlIGNhbiBzZWUsIHRoZSB0cmFpbmluZyBkYXRhIHNldCB3aXRoIGEgc2l6ZSBvZiBuID0gMTAwIGhhcyB0aGUgbG93ZXN0IG9mIGJvdGggdGhlIE1TRSBhbmQgdGhlIE1BUEUgb3V0IG9mIHRoZSBmb3VyIHBvdGVudGlhbCB0cmFpbmluZyBkYXRhIHNldCBzaXplcyB0aGF0IHdlcmUgbG9va2VkIGF0LiBUaGlzIHN1Z2dlc3RzIHRoYXQgdGhpcyBzaXplIGlzIHRoZSBtb3N0IGlkZWFsIG91dCBvZiB0aGUgcG90ZW50aWFsIG9wdGlvbnMgYXMgaXQgcmVkdWNlcyB0aGUgZXJyb3JzIHRoZSBtb3N0IG91dCBvZiB0aGUgZm91ciBvcHRpb25zIHRoYXQgd2VyZSBjb25zaWRlcmVkLiANCg0KV2Ugd2lsbCBjcmVhdGUgYSB2aXN1YWxpemF0aW9uIHRvIGNvbXBhcmUgdGhlc2UgZm9yZWNhc3QgZXJyb3JzIGFuZCBjb25maXJtIHRoZSBmaW5kaW5nIHRoYXQgYSBzYW1wbGUgc2l6ZSBvZiAxMDAgb2JzZXJ2YXRpb25zIHJlZHVjZXMgdGhlIGVycm9ycyBtb3N0IG91dCBvZiB0aGUgcG90ZW50aWFsIHNhbXBsZSBzaXplcyB0aGF0IHdlcmUgY29uc2lkZXJlZCBmb3IgdGhlIHRyYWluaW5nIGRhdGEgc2V0IG9mIHRoZSB0aW1lIHNlcmllcy4NCg0KRmlyc3QsIGxldCdzIGxvb2sgYXQgYSBwbG90IG9mIHRoZSBtZWFuIHNxdWFyZWQgZXJyb3JzIChNU0UpIGZvciBlYWNoIG9mIHRoZSBmb3VyIHBvdGVudGlhbCBzYW1wbGUgc2l6ZXMuIA0KDQpgYGB7cn0NCiMgUGxvdCBvZiB0aGUgTVNFLg0KcGxvdCgxOjQsIE1TRSwgdHlwZSA9ICJiIiwgY29sPSJkYXJrb3JjaGlkIiwgeWxhYiA9ICJFcnJvcnMiLCB4bGFiID0gIlNhbXBsZSBTaXplIiwNCiAgICAgbWFpbiA9ICJNU0UiLCBheGVzID0gRkFMU0UpDQogICAgIGxhYnMgPSBjKCJuID0gMTAwIiwgIm4gPSA3MCIsICJuID0gNTAiLCAibiA9IDM1IikNCiAgICAgYXhpcygxLCBhdCA9IDE6NCwgbGFiZWwgPSBsYWJzKQ0KICAgICBheGlzKDIpDQpgYGANCg0KQXMgd2UgY2FuIHNlZSwgbiA9IDEwMCBvYnNlcnZhdGlvbnMgaGFzIHRoZSBsb3dlc3QgTVNFIG91dCBvZiB0aGUgZm91ciBwb3RlbnRpYWwgc2FtcGxlIHNpemVzLCBpbmRpY2F0aW5nIHRoYXQgaXQgaXMgdGhlIGlkZWFsIGNob2ljZSwgYmVjYXVzZSBpdCByZWR1Y2VzIHRoZSBlcnJvcnMuIA0KDQpXZSB3aWxsIGFsc28gbG9vayBhdCB0aGUgcGxvdCBvZiB0aGUgbWVhbiBhYnNvbHV0ZSBwcmVkaWN0aW9uIGVycm9ycyAoTUFQRSkgZm9yIGVhY2ggb2YgdGhlIGZvdXIgcG90ZW50aWFsIHRyYWluaW5nIGRhdGEgc2V0IHNpemVzLiANCg0KYGBge3J9DQojIFBsb3Qgb2YgdGhlIE1BUEUuDQpwbG90KDE6NCwgTUFQRSwgdHlwZSA9ICJiIiwgY29sPSJkYXJrb3JjaGlkIiwgeWxhYiA9ICJFcnJvcnMiLCB4bGFiID0gIlNhbXBsZSBTaXplIiwNCiAgICAgbWFpbiA9ICJNQVBFIiwgYXhlcyA9IEZBTFNFKQ0KICAgICBsYWJzID0gYygibiA9IDEwMCIsICJuID0gNzAiLCAibiA9IDUwIiwgIm4gPSAzNSIpDQogICAgIGF4aXMoMSwgYXQgPSAxOjQsIGxhYmVsID0gbGFicykNCiAgICAgYXhpcygyKQ0KYGBgDQoNCk9uY2UgYWdhaW4sIHRoZSBzYW1wbGUgc2l6ZSBvZiBuID0gMTAwIG9ic2VydmF0aW9ucyBzaG93cyB0aGUgbG93ZXN0IHZhbHVlIG9mIHRoZSBNQVBFLCBzaG93aW5nIHRoYXQgaXMgdGhlIGlkZWFsIGNob2ljZSBvdXQgb2YgdGhlIGZvdXIgc2FtcGxlIHNpemVzLCBiZWNhdXNlIGl0IHJlZHVjZXMgdGhlIGVycm9ycy4gDQoNCkFzIHdlIGNhbiBzZWUgaW4gdGhlIHBsb3RzIGZvciBib3RoIHRoZSBNU0UgYW5kIHRoZSBNQVBFLCBuID0gMTAwIG9ic2VydmF0aW9ucyBzaG93cyB0aGUgbG93ZXN0IGVycm9ycywgYW5kICBhcyB0aGUgc2FtcGxlIHNpemUgZGVjcmVhc2VzIGluIHRoZSBudW1iZXIgb2Ygb2JzZXJ2YXRpb25zLCB0aGUgZXJyb3JzIGZvciBib3RoIHRoZSBNU0UgYW5kIHRoZSBNQVBFIGluY3JlYXNlLCByZXN1bHRpbmcgaW4gZXJyb3JzIG11Y2ggZ3JlYXRlciB0aGFuIHRob3NlIG9mIHRoZSBzYW1wbGUgc2l6ZSB3aXRoIDEwMCBvYnNlcnZhdGlvbnMuIFRoaXMgc3RyZW5ndGhlbnMgdGhhdCB0aGUgaWRlYWwgdHJhaW5pbmcgZGF0YSBzZXQgc2l6ZSBvdXQgb2YgdGhlIGZvdXIgb3B0aW9ucyB0aGF0IHdlcmUgY29uc2lkZXJlZCBpcyBhIHNpemUgb2YgMTAwIG9ic2VydmF0aW9ucy4gQSB0cmFpbmluZyBkYXRhIHNldCB3aXRoIDEwMCBvYnNlcnZhdGlvbnMgeWllbGRzIHRoZSBiZXN0IHBlcmZvcm1hbmNlLCBiZWNhdXNlIGl0IHJlZHVjZXMgdGhlIGVycm9ycy4gDQoNClNvLCB3ZSBjYW4gY29uY2x1ZGUgdGhhdCBmcm9tIHRoZSBjaG9pY2VzIG9mIGEgdHJhaW5pbmcgZGF0YSBzZXQgd2l0aCAxMDAsIDcwLCA1MCwgb3IgMzUgb2JzZXJ2YXRpb25zLCB0aGUgYmVzdCBjaG9pY2UgaXMgdGhlIHRyYWluaW5nIGRhdGEgc2V0IHdpdGggMTAwIG9ic2VydmF0aW9ucy4gVGhpcyBjaG9pY2Ugb2YgMTAwIG9ic2VydmF0aW9ucyByZXN1bHRzIGluIHRoZSBsb3dlc3QgZXJyb3JzLCBhbmQgdGhlcmVmb3JlLCBwcm92aWRlcyB0aGUgYmVzdCBwZXJmb3JtYW5jZSBmb3IgZm9yZWNhc3Rpbmcgb3VyIHRpbWUgc2VyaWVzLiANCg0KDQoNCiMgRm9yZWNhc3RpbmcgdGhlIFVwY29taW5nIE1vbnRocw0KDQpXZSB3aWxsIHVzZSBmb3JlY2FzdGluZyB0byBwcm92aWRlIGFuIGVzdGltYXRlIGZvciB0aGUgdXBjb21pbmcgbW9udGhzIGFmdGVyIHRoZSBlbmQgb2YgdGhlIHRpbWUgc2VyaWVzIGRhdGEgY29sbGVjdGlvbi4gVGhpcyB0aW1lIHNlcmllcyBjb2xsZWN0ZWQgZGF0YSB1cCB1bnRpbCBKdWx5IDIwMTksIHNvIHdlIHdpbGwgZm9yZWNhc3QgdGhlIGVzdGltYXRlZCBob21lIHNhbGUgcHJpY2VzIGZvciB0aGUgbW9udGhzIHdoaWNoIGZvbGxvdyB0aGUgZW5kIG9mIHRoaXMgZGF0YSBjb2xsZWN0aW9uLg0KDQpXZSB3aWxsIHVzZSBhbiBleHBvbmVudGlhbCBzbW9vdGhpbmcgbWV0aG9kIGZvciB0aGlzIGZvcmVjYXN0aW5nLiBUaGlzIHdpbGwgYWxsb3cgdXMgdG8gZm9yZWNhc3QgdGhlIG5leHQgdHdlbHZlIG1vbnRocyBvZiBhdmVyYWdlIGhvbWUgc2FsZSBwcmljZXMgYnkgdGhlIG1vbnRoLiBTaW5jZSBvdXIgdGltZSBzZXJpZXMgc3RvcHBlZCBhdCBKdWx5IDIwMTksIHRoaXMgZm9yZWNhc3Rpbmcgd2lsbCBwcm92aWRlIGVzdGltYXRlcyBvZiBtb250aGx5IGF2ZXJhZ2UgaG9tZSBzYWxlIHByaWNlcyB1cCB0aHJvdWdoIEp1bmUgMjAyMC4NCg0KV2Ugc3RhdGVkIHByZXZpb3N1bHkgdGhhdCB0aGVyZSBhcHBlYXJlZCB0byBiZSBhIG11bHRpcGxpY2F0aXZlIHRyZW5kIG9jY3VycmluZyB3aXRoaW4gdGhpcyB0aW1lIHNlcmllcy4gVGhpcyB3YXMgc2VlbiBieSBob3cgdGhlIHNlYXNvbmFsIHZhcmlhdGlvbiBhcHBlYXJlZCB0byBpbmNyZWFzZSBvdmVyIHRpbWUgYWxvbmcgd2l0aCB0aGUgb3ZlcmFsbCBncmFkdWFsIGluY3JlYXNlIGluIG1vbnRobHkgYXZlcmFnZSBob21lIHNhbGVzLiBXZSB3aWxsIHJlZmxlY3QgdGhpcyBtdWx0aXBsaWNhdGl2ZSB0cmVuZCB3aXRoIHRoZSBleHBvbmVudGlhbCBzbW9vdGhpbmcgZm9yZWNhc3QuIA0KDQpgYGB7cn0NCmV0cyA8LSBldHMoaG9tZS50cywgbW9kZWwgPSAiTUFNIikNCmZvcmVjYXN0IDwtIGZvcmVjYXN0KGV0cywgaCA9IDEyKQ0KcGxvdChmb3JlY2FzdCwgbWFpbiA9ICJGb3JlY2FzdCBvZiB0aGUgQXZlcmFnZSBIb21lIFNhbGUgUHJpY2VzIFxuIGZvciB0aGUgTmV4dCAxMiBNb250aHMiKQ0KYGBgDQoNCkFzIHdlIGNhbiBzZWUsIHRoaXMgcGxvdCBpbGx1c3RyYXRlcyB0aGUgZm9yZWNhc3QgZm9yIHRoZSBuZXh0IHR3ZWx2ZSBtb250aHMgYWZ0ZXIgdGhlIGVuZCBvZiB0aGUgdGltZSBzZXJpZXMuIFRoaXMgZm9yZWNhc3QgcHJvdmlkZXMgYW4gZXN0aW1hdGUgZm9yIHdoYXQgdGhlIGF2ZXJhZ2UgaG9tZSBzYWxlIHByaWNlcyB3aWxsIGxvb2sgbGlrZSBmb3IgdGhlIG5leHQgdHdlbHZlIG1vbnRocy4gDQoNCldlIGNhbiBzZWUgd2hhdCB0aGUgc3BlY2lmaWMgZXN0aW1hdGVkIGhvbWUgc2FsZSBwcmljZXMgYXJlIGZvciBlYWNoIG9mIHRoZSBuZXh0IHR3ZWx2ZSBtb250aHMgYWZ0ZXIgSnVseSAyMDE5LiANCg0KYGBge3J9DQpmb3JlY2FzdCRtZWFuIA0KYGBgDQoNCldlIGNhbiBzZWUgdGhhdCB0aGUgbW9udGggd2l0aCB0aGUgaGlnaGVzdCBmb3JlY2FzdGVkIHByaWNlIGlzIE1hcmNoIDIwMjAgd2l0aCBhIGZvcmVjYXN0ZWQgYXZlcmFnZSBob21lIHNhbGUgcHJpY2Ugb2YgJDcyOCw5OTQuNzAuIFRoZSBtb250aCB3aXRoIHRoZSBsb3dlc3QgZm9yZWNhc3RlZCBwcmljZSBpcyBEZWNlbWJlciAyMDE5IHdpdGggYSBmb3JlY2FzdGVkIGF2ZXJhZ2UgaG9tZSBzYWxlIHByaWNlIG9mICQ2MjQsNzI1LjEwLiANCg0KDQoNCiMgQ29uY2x1c2lvbg0KDQpJbiB0aGlzIHByb2plY3QsIHdlIGNyZWF0ZWQgYSB0aW1lIHNlcmllcyBvZiB0aGUgbW9udGhseSBhdmVyYWdlIGhvbWUgc2FsZXMgcHJpY2VzIHRoYXQgd2VyZSBjb2xsZWN0ZWQgZnJvbSB0aGUgc3BhbiBvZiAyMDA3IHRvIDIwMTkuIFdlIGFuYWx5emVkIHRoZSB0cmVuZHMgYW5kIHBhdHRlcm5zIG9mIHRoaXMgdGltZSBzZXJpZXMgdG8gbWFrZSBub3RlIG9mIGFueSBmaW5kaW5ncyB3aGljaCBzdG9vZCBvdXQuIE9uZSBub3RhYmxlIGFzcGVjdCBvZiB0aGlzIHRpbWUgc2VyaWVzIHdhcyB0aGF0IGl0IHNob3dlZCBhIHNlYXNvbmFsIHBhdHRlcm4sIHdpdGggd2hhdCBsb29rZWQgbGlrZSBhbiBhbm51YWwgc2Vhc29uYWxpdHkuIEl0IHdhcyBldmlkZW50IHRoYXQgdGhlcmUgd2FzIHNvbWUgc29ydCBvZiBhIHNlYXNvbmFsIHBhdHRlcm4gd2l0aGluIHRoZSBob21lIHNhbGVzIHByaWNlcyB3aGljaCByZXBlYXRlZCBhZnRlciBhIGNlcnRhaW4gcGVyaW9kIG9mIHRpbWUsIHdoaWNoIGFwcGVhcmVkIHRvIGJlIGFubnVhbGx5LiBUaGUgdGltZSBzZXJpZXMgcGxvdCBzaG93ZWQgdGhhdCB0aGlzIHBhdHRlcm4gYXBwZWFyZWQgdG8gcmVwZWF0IG9uIGFwcHJveGltYXRlbHkgYW4gYW5udWFsIGJhc2lzLCB3aXRoIHRoZSBob21lIHNhbGVzIHByaWNlcyBnb2luZyB0aHJvdWdoIGRpZmZlcmVudCBwaGFzZXMgb2YgaGlnaHMgYW5kIGxvd3Mgb3ZlciB0aGUgY291cnNlIG9mIGVhY2ggeWVhci4gQm90aCB0aGUgY2xhc3NpY2FsIGRlY29tcG9zaXRpb24gbWV0aG9kIGFuZCB0aGUgU1RMIGRlY29tcG9zaXRpb24gbWV0aG9kIGNvbmZpcm1lZCB0aGUgcHJlc2VuY2Ugb2YgdGhpcyBzZWFzb25hbCB0cmVuZCB3aXRoaW4gdGhlIGRhdGEgZm9yIHRoaXMgdGltZSBzZXJpZXMgb2YgdGhlIGhvbWUgc2FsZXMgcHJpY2VzLiANCg0KQW5vdGhlciBub3RhYmxlIGZpbmRpbmcgaW4gdGhpcyB0aW1lIHNlcmllcyBwcm9qZWN0IHdhcyB0aGF0IHRoZXJlIGFwcGVhcmVkIHRvIGJlIGFuIG92ZXJhbGwgaW5jcmVhc2UgaW4gdGhlIGF2ZXJhZ2UgaG9tZSBzYWxlIHByaWNlcyBmcm9tIHRoZSBiZWdpbm5pbmcgb2YgdGhlIHRpbWUgc2VyaWVzIGRhdGEgY29sbGVjdGlvbiBpbiAyMDA3IHRvIHRoZSBlbmQgb2YgdGhlIGRhdGEgY29sbGVjdGlvbiBpbiAyMDE5LiBJdCBhcHBlYXJlZCB0aGF0IGhvbWUgc2FsZSBwcmljZXMgZ3JhZHVhbGx5IGluY3JlYXNlZCBvdmVyIHRoZSBjb3Vyc2Ugb2YgdGhpcyAxMiB5ZWFyIHBlcmlvZCBvZiB0aGUgZGF0YSBjb2xsZWN0aW9uLiBUaGUgdGltZSBzZXJpZXMgcGxvdHMgYXMgd2VsbCBhcyB0aGUgZGVjb21wb3NpdGlvbiBwbG90cyBmb3IgdGhlIHRpbWUgc2VyaWVzIHNob3dlZCBldmlkZW5jZSBvZiB0aGlzIGluY3JlYXNlIGluIHRoZSBhdmVyYWdlIGhvbWUgc2FsZSBwcmljZXMgZnJvbSAyMDA3IHRvIDIwMTkuDQoNCkFkZGl0aW9uYWxseSwgd2UgbG9va2VkIGF0IGZvdXIgcG90ZW50aWFsIHNhbXBsZSBzaXplcyB0byB1c2UgZm9yIGEgdHJhaW5pbmcgZGF0YSBzZXQgaW4gb3JkZXIgdG8gZGV0ZXJtaW5lIHdoaWNoIG51bWJlciBvZiBvYnNlcnZhdGlvbnMgd291bGQgYmUgaWRlYWwgdG8gdXNlLiBUaGUgZm91ciBwb3RlbnRpYWwgc2l6ZXMgZm9yIHRoZSB0cmFpbmluZyBkYXRhIHNldCB3aGljaCB3ZSBsb29rZWQgYXQgd2VyZSBuID0gMTAwLCA3MCwgNTAsIGFuZCAzNSBvYnNlcnZhdGlvbnMuIEl0IHR1cm5lZCBvdXQgdGhhdCB0aGUgc2FtcGxlIHNpemUgb2YgbiA9IDEwMCBvYnNlcnZhdGlvbnMgd2FzIHRoZSBpZGVhbCBjaG9pY2Ugb3V0IG9mIHRoZXNlIGZvdXIgb3B0aW9ucywgYmVjYXVzZSBpdCByZXN1bHRlZCBpbiB0aGUgbG93ZXN0IGVycm9ycywgYXMgc2VlbiBieSBob3cgaXQgaGFkIHRoZSBsb3dlc3QgdmFsdWVzIGZvciBib3RoIGl0cyBNU0UgYW5kIGl0cyBNQVBFLiBUaGlzIGluZGljYXRlcyB0aGF0IHRoZSBzYW1wbGUgc2l6ZSBvZiAxMDAgb2JzZXJ2YXRpb25zIHByb3ZpZGVzIHRoZSBiZXN0IHV0aWxpdHkgZm9yIHRoZSB0cmFpbmluZyBzZXQsIGJlY2F1c2UgaXQgcmVkdWNlcyB0aGUgZXJyb3JzLiANCg0KV2UgYWxzbyB1c2VkIGV4cG9uZW50aWFsIHNtb290aGluZyBtZXRob2RzIHRvIGZvcmVjYXN0IHRoZSBmb2xsb3dpbmcgdHdlbHZlIG1vbnRocyBhZnRlciB0aGUgZW5kIG9mIHRoZSB0aW1lIHNlcmllcyBkYXRhIGNvbGxlY3Rpb24uIFRoaXMgcHJvdmlkZWQgZm9yZWNhc3RlZCBwcmVkaWN0aW9ucyBmb3IgdGhlIGF2ZXJhZ2UgaG9tZSBzYWxlIHByaWNlcyB1cCB0aHJvdWdoIEp1bmUgb2YgMjAyMC4gDQoNCg0KIyMgUmVjb21tZW5kYXRpb25zDQoNClNvbWUgcmVjb21tZW5kYXRpb25zIEkgd291bGQgbWFrZSBmb3IgZnV0dXJlIHByb2plY3RzIGluY2x1ZGU6DQoNCiogT3ZlcmFsbCwgaXQgYXBwZWFyZWQgbGlrZSB0aGVyZSB3YXMgYW4gYW5udWFsIHNlYXNvbmFsaXR5IGluIHRoaXMgcGFydGljdWxhciB0aW1lIHNlcmllcyBkb25lIG9uIHRoZSBvYnNlcnZlZCB2YWx1ZXMgb2YgdGhlIHNhbGVzIHByaWNlcyBvZiBob3VzZXMgb3ZlciB0aGUgc3BhbiBvZiAyMDA3IHRvIDIwMTkuIFNvbWUgcG90ZW50aWFsIHJlYXNvbnMgd2VyZSBnaXZlbiB0byBwcm92aWRlIGFuIGV4cGxhbmF0aW9uIGZvciB0aGlzIHNlYXNvbmFsIHRyZW5kLCBzdWNoIGFzIG1vcmUgaW5kaXZpZHVhbHMgYnV5aW5nIGhvdXNlcyBpbiB0aGUgc3VtbWVyIGxlYWRpbmcgdGhlIGFuIGluY3JlYXNlIGluIHNhbGVzIHByaWNlcy4gVG8gZnVydGhlciBzdHJlbmd0aGVuIHRoZSBldmlkZW5jZSBvZiB0aGlzIHNlYXNvbmFsIHRyZW5kLCBmdXR1cmUgcHJvamVjdHMgY291bGQgbG9vayBmdXJ0aGVyIGludG8gdGhpcyB0byBzZWUgaWYgdGhpcyBpcyBpbmRlZWQgYSBjb21tb24gcGF0dGVybiB3aXRoIHJlY29yZHMgb2YgaG91c2Ugc2FsZXMgcHJpY2VzLiANCg0KKiBGdXR1cmUgcHJvamVjdHMgY291bGQgbG9vayBpbnRvIHRyeWluZyBvdXQgZXZlbiBtb3JlIGRpZmZlcmVudCB0cmFpbmluZyBkYXRhIHNldCBzaXplcyB0byBzZWUgaWYgdGhlcmUgaXMgYW5vdGhlciBvbmUgd2hpY2ggd291bGQgd29yayBldmVuIGJldHRlciB0aGFuIHRoZSBvbmVzIHRoYXQgd2UgdHJpZWQgb3V0IGluIHRoaXMgcHJvamVjdC4gV2UgbG9va2VkIGF0IGZvdXIgcG90ZW50aWFsIHNpemVzIGZvciB0aGUgdHJhaW5pbmcgZGF0YSBzZXQgdG8gc2VlIHdoaWNoIG9uZSBwcm92aWRlZCB0aGUgYmVzdCBhY2N1cmFjeSwgYW5kIGZvdW5kIHRoYXQgbiA9IDEwMCBvYnNlcnZhdGlvbnMgcHJvdmlkZWQgdGhlIGJlc3QgdXRpbGl0eSBieSByZWR1Y2luZyB0aGUgZXJyb3JzLiBIb3dldmVyLCBwZXJoYXBzIGZ1dHVyZSBwcm9qZWN0cyBjb3VsZCB0cnkgb3V0IGV2ZW4gbW9yZSBkaWZmZXJlbnQgc2l6ZXMgdG8gc2VlIGlmIHRoZXJlIGlzIG9uZSB3aGljaCBwcm92aWRlcyBldmVuIGJldHRlciBhY2N1cmFjeSBieSByZWR1Y2luZyB0aGUgZXJyb3JzLiAgDQoNCg0KT3ZlcmFsbCwgdGhpcyB0aW1lIHNlcmllcyBwcm9qZWN0cyBwcm92aWRlZCBpbnNpZ2h0IGludG8gc29tZSBvZiB0aGUgcGF0dGVybnMgYW5kIHRyZW5kcyBzdXJyb3VuZGluZyB0aGUgbW9udGhseSBhdmVyYWdlIGhvbWUgc2FsZSBwcmljZXMgZnJvbSB0aGUgc3BhbiBvZiB0aW1lIGZyb20gMjAwNyB0byAyMDE5LiBUaGUgc2Vhc29uYWxpdHkgYW5kIHRyZW5kcyB3aGljaCB3ZXJlIG9ic2VydmVkIHNob3cgdGhhdCB0aGUgc2FsZXMgcHJpY2VzIG9mIGhvbWVzIGlzIHNvbWV0aGluZyB3aGljaCBnb2VzIHRocm91Z2ggY3ljbGVzIG9mIGNoYW5nZXMsIGFuZCB2YXJpb3VzIGhpZ2hzIGFuZCBsb3dzIHRocm91Z2hvdXQgdGhlIHNwYW4gb2YgdGltZS4gDQoNCg0KDQojIFJlZmVyZW5jZXMNCg0KVGhlIGRhdGEgc2V0IEkgdXNlZCBmb3IgbXkgdGltZSBzZXJpZXMgd2FzIGZvdW5kIG9uIGthZ2dsZS5jb20uIEluY2x1ZGVkIGJlbG93IGlzIHRoZSBjaXRhdGlvbiBvZiB0aGUgd2ViIHBhZ2Ugd2hlcmUgSSBmb3VuZCB0aGlzIGRhdGEgc2V0LiANCg0KSG9sZGluZ3MsIEguLCAmIEphbWVzLCBULiAoMjAxOSwgQXVndXN0IDEyKS4gSG91c2UgUHJvcGVydHkgU2FsZXMgVGltZSBTZXJpZXMuIEthZ2dsZS4gaHR0cHM6Ly93d3cua2FnZ2xlLmNvbS9kYXRhc2V0cy9odGFnaG9sZGluZ3MvcHJvcGVydHktc2FsZXMvZGF0YSANCg==