Midterm Exam Objectives
Understand the definition and relationship between PDFs and CDFs,
including their non-parametric estimators: the empirical distribution
function and kernel density estimation (KDE).
Estimate sampling distributions using simulation-based methods,
specifically the bootstrap.
Derive point estimates of parameters using the method of moments
and maximum likelihood estimation (MLE).
Describe the asymptotic (normal) and bootstrap sampling
distributions of maximum likelihood estimators.
Apply all the above inferential procedures in a programming
environment (such as Python) to perform numerical data analysis.
Lognormal Distrubution
5.1 Log-normal Distribution The log-normal distributions have been
widely used in many different fields such as finance and economics,
engineering and reliability, environmental science, medical and biology
etc. If X follows a lognormal distribution: f(x;µ,σ2) = √ 1 x 2πσ2 exp
−(lnx−µ)2 2σ2 where µ ∈ R is the mean of lnX and σ2 > 0 is the
variance of lnX.
Working Dataset: A reservoir engineer at an oil exploration company
has recently drilled 50 new wells in a shale formation. According to
geological theory, the size of oil reserves in this type of formation is
often modeled using a log-normal distribution. The engineer is
responsible for estimating the typical reserve size and quantifying the
uncertainty of these estimates for a presentation to senior management.
The estimated ultimate recovery (EUR) for the 50 wells, measured in
thousands of barrels (Mbbl), is as follows:
17.3, 24.8, 8.2, 31.5, 14.1, 42.7, 11.9, 55.3, 21.4, 9.7, 36.2, 18.6, 63.1, 13.2, 28.9, 47.5, 19.8, 7.5, 33.4, 52.1, 16.0, 25.9, 38.7, 10.3, 44.2, 22.5, 58.6, 12.8, 30.3, 48.9, 20.1, 35.4, 15.7, 60.2, 26.7, 41.3, 18.1, 53.8, 23.9, 46.2, 29.4, 37.6, 14.9, 50.5, 32.8, 19.3, 56.7, 11.2, 39.5, 27.1
This assignment focuses on finding the asymptotic sampling
distributions of the MLE ˆµ and ˆ to µ and σ2 based on an environmental
study data.
Question 1: Method of Moments Estimation (MME) of µ and σ2
Estimate the parameters µ and σ2 (caution: not σ!) from the raw oil
reserve data using the given k-th moment function. Organize your work
into three parts:
- Derive the system of two equations for the method of moments
estimators (MMEs) of µ and σ2.
#1a. Deriving the system of two equations for the methods of moment estimators (MME) of mu and sigma_sq
wellsize= sort(c(17.3, 24.8, 8.2, 31.5, 14.1, 42.7, 11.9, 55.3, 21.4, 9.7, 36.2, 18.6, 63.1, 13.2, 28.9, 47.5, 19.8, 7.5, 33.4, 52.1, 16.0, 25.9, 38.7, 10.3, 44.2, 22.5, 58.6, 12.8, 30.3, 48.9, 20.1, 35.4, 15.7, 60.2, 26.7, 41.3, 18.1, 53.8, 23.9, 46.2, 29.4, 37.6, 14.9, 50.5, 32.8, 19.3, 56.7, 11.2, 39.5, 27.1 ))
#m moments for parameters
m1 = mean(wellsize) #xbar
m2= mean(wellsize^2) #x squared bar
#algebric application for closed form population parameters sigma^2 and mu
mom_sigma_sq = log(m2) - 2*log(m1)
mom_mu = log(m1) -0.5 * mom_sigma_sq
cat("MME for mu:", mom_mu, "\nMME for sigma_sq:", mom_sigma_sq)
MME for mu: 3.301269
MME for sigma_sq: 0.2339652
cat("Sample mean:", m1, "sample standard deviation:", m2)
Sample mean: 30.516 sample standard deviation: 1176.698
- Derive the closed-form expressions for the MMEs of µ, σ2, and µLN,
denoted by µ~, σ2~, and µLN~, respectively.
System of equations: \[
\ln(\bar{x}) = \mu + \frac{1}{2}\sigma^2
\ln(\bar{x^2}) = 2\mu + 2\sigma^2
\]
Solve Equation 1 for \(\mu\) in
terms of \(\sigma^2\): \[
[
mu = \ln(\bar{x}) - \frac{1}{2}\sigma^2
]
\]
Substitute this expression for \(\mu\):
\[
[ln({x^2}) = 2[ \ln(\bar{x}) - \frac{1}{2}\sigma^2] + 2\sigma^2]
\]
Distribute and simplify to find \(\tilde{\sigma}^2\):}
\[
[ln({x^2}) = 2ln(\bar{x}) - \sigma^2 + 2\sigma^2]
\] \[
[ln({x^2}) = 2ln(\bar{x}) + \sigma^2]
\]
\[
[ \tilde{\sigma}^2 = ln({x^2}) - 2ln(\bar{x})]
\]
Substitute \(\tilde{\sigma}^2\) back
into the expression for \(\mu\):
\[
[\tilde{\mu} = ln(\bar{x}) - \frac{1}{2} [ln({x^2}) - 2ln(\bar{x})]]
\] \[
[\tilde{\mu} = ln(\bar{x}) - \frac{1}{2} ln({x^2}) + ln(\bar{x})]
\] \[
[\tilde{\mu} = 2ln(\bar{x}) - \frac{1}{2}ln({x^2})]
\]
Observing both equations
\[
[\tilde{\mu} = 2ln(\bar{x}) - \frac{1}{2}\ln(x^2)]
\]
\[
[\tilde{\sigma}^2 = ln({x^2}) - 2ln(\bar{x})]
\]
- Write an R function that outputs the MMEs µ, σ2, and µLN based on
the given data set.
sigma_squ_tilda = log(m2)-2* log(m1)
mu_tilda = 2*log(m1) - ((1/2)*log(m2))
cat("Mu tilda:", mu_tilda, "Population standard deviation:", sigma_squ_tilda)
Mu tilda: 3.301269 Population standard deviation: 0.2339652
#Writing a function for Methods of Moment Estimation
MMElognorm= function(wellsize)
{
#m moments for parameters
m1 = mean(wellsize) #xbar
m2= mean(wellsize^2) #x squared bar
#algebric application for closed form population parameters sigma^2 and mu
#mom_sigma_sq = log(m2) - 2*log(m1) #remove its the same below
#mom_mu = log(m1) -0.5 * mom_sigma_sq
sigma_squ_tilda = log(m2)-2* log(m1) #calculate the MOM for standard deivation
mu_tilda = 2*log(m1) - ((1/2)*log(m2)) # calculate the MOM for mean
return(c(mu_tilda, sigma_squ_tilda, m1) )
}
results = MMElognorm(wellsize)
cat("Mu tilda:", mu_tilda, "Population standard deviation:", sigma_squ_tilda, "mu_LN", m1)
Mu tilda: 3.301269 Population standard deviation: 0.2339652 mu_LN 30.516
The outputs for the method of moment estimators are \(\tilde\mu\) = 3.3012685, \(\tilde\sigma^2\) = 0.2339652, and \(\tilde\mu_{LN}\) = 30.516.
Question 2: Finding the MLE of \(\mu\) and \(\sigma^2\)
Question 2.1
(1). Derive the score functions (i.e., the gradient of the
log-likelihood) for the parameters of the log-normal distribution,
and
set them to zero to obtain the system of score equations.
Begin with the full log-likelihood and compute its partial
derivatives with respect to µ and σ2. [Hint: letting β = σ2 may simplify
differentiation.]
The log-likelihood for the log-normal distribution is given by:
\[
\ell(\mu, \beta) = -\frac{n}{2} \ln(2\pi) - \frac{n}{2} \ln \beta -
\sum_{i=1}^n \ln x_i - \frac{1}{2\beta} \sum_{i=1}^n (\ln x_i - \mu)^2
\] Partial derivative with respect to \(\mu\):
\[
\frac{\partial \ell}{\partial \mu} = \frac{\partial}{\partial \mu}
\left[ -\frac{1}{2\beta} \sum_{i=1}^n (\ln x_i - \mu)^2 \right] \\
= -\frac{1}{2\beta} \sum_{i=1}^n 2(\ln x_i - \mu) \cdot
\frac{\partial}{\partial \mu}(\ln x_i - \mu) \\
= -\frac{1}{2\beta} \sum_{i=1}^n 2(\ln x_i - \mu) \cdot (-1) \\
U(\mu) = \frac{1}{\beta} \sum_{i=1}^n (\ln x_i - \mu)
\]
Reach the score function of the equations Partial derivative with
respect to \(\beta\), we treat \(\beta\) in substitution of \(\sigma^2\) for simplicity: \[
\frac{\partial \ell}{\partial \beta} = \frac{\partial}{\partial \beta}
\left[ -\frac{n}{2} \ln \beta \right] - \frac{\partial}{\partial \beta}
\left[ \frac{1}{2\beta} \sum_{i=1}^n (\ln x_i - \mu)^2 \right] \\
= -\frac{n}{2\beta} - \frac{1}{2} \sum_{i=1}^n (\ln x_i - \mu)^2
\cdot \frac{d}{d\beta}(\beta^{-1}) \\
= -\frac{n}{2\beta} - \frac{1}{2} \sum_{i=1}^n (\ln x_i - \mu)^2
\cdot (-\beta^{-2}) \\
U(\beta) = -\frac{n}{2\beta} + \frac{1}{2\beta^2} \sum_{i=1}^n (\ln
x_i - \mu)^2
\]
Replacing \(\beta\) with \(\sigma^2\)
\[
-\frac{n}{2\sigma^2} + \frac{1}{2\sigma^4} \sum_{i=1}^n (\ln x_i -
\mu)^2 = 0
\]
Question 2.2
(2). Perform some algebra to find the closed form of the MLE of µ and
σ2, denoted by µ and σ2
Solving for \(\hat\mu\)
\[
\sum_{i=1}^n (\ln x_i - \mu) = 0 \\
\sum_{i=1}^n \ln x_i - n\mu = 0 \\
\hat{\mu} = \frac{1}{n} \sum_{i=1}^n \ln x_i
\]
Solving for \(\hat\sigma^2\)
\[
\frac{n}{2\sigma^2} = \frac{1}{2\sigma^4} \sum_{i=1}^n (\ln x_i -
\hat{\mu})^2 \\
n\sigma^2 = \sum_{i=1}^n (\ln x_i - \hat{\mu})^2 \\
\hat{\sigma}^2 = \frac{1}{n} \sum_{i=1}^n (\ln x_i - \hat{\mu})^2
\]
Question 2.3
(3). Recall that lognormal population mean (i.e., the first moment)
is μLN = E[X] = exp(μ + 1/2σ2). Using the relationship between variance
and the first and second moments,
Var(X) = E[X2] − (E[X])2,
we derive the population variance of the lognormal distribution,
denoted as σ2 LN. This result will be used in applying the Central Limit
Theorem in subsequent questions
\[
{Var}(X) = E[X^2] -(E[X])^2 \\
\]
\[
\sigma^2_{LN} = E[X^2] - (E[X])^2
\]
$$ E[X] = exp(+ ^2) \
E[X^k] = exp(k+ k22), \
E[X^2] = exp(2+ (22)2) \ E[X^2] = exp(2+ 2^2)
$$
\[
\sigma^2_{LN} = E[X^2] - (E[X])^2
\]
\[
\sigma^2_{LN} = exp(2\mu + 2\sigma^2) - [ exp(\mu +
\frac{1}{2}\sigma^2)]^2
\] \[
\sigma^2_{LN} = exp(2\mu + 2\sigma^2) - exp(2\mu + \sigma^2)
\]
Question 3: Sampling Distribution of Lognormal Sample Mean \(\hat\mu_{LN}\)
We have derived two different estimators of lognormal population mean
μLN. This Question focuses on the sampling distribution of lognormal
sample sample means based on MLE. The following are detailed
instructions.
Question 3.1
(1). Write an R function to estimate the MLE of μ and σ2, denoted by
bμ and cσ2 and return the MLE of μLN, denoted by \(\hat\mu_{LN}\).
The log-likelihood for the log-normal distribution is given by:
\[
\ell(\mu, \beta) = -\frac{n}{2} \ln(2\pi) - \frac{n}{2} \ln \beta -
\sum_{i=1}^n \ln x_i - \frac{1}{2\beta} \sum_{i=1}^n (\ln x_i - \mu)^2
\]
#Write the R function that estimations the MLE of the mu and sigma^2 denoted by mu_hat and sigma square hat to then return
#The Maximum Limitation Estimator of the mu_LN, denoted mu_LN_hat
data = wellsize #inserting the data of interest to be wellsize
normlog_mle= function(data)
{
#LOG LIKLEIHOOD--> its a normallog so fine
log_data = log(data)
#Find the length of the data for gradient equations
n = length(data)
#closed form for mu_hat and sigma_sq_hat
mu_hat = mean(log_data)
sigma_sq_hat = mean((log_data-mu_hat)^2)
#Calculating the population paraters for MLE: mu_ln_hat
mu_ln_hat = exp(mu_hat + (0.5* sigma_sq_hat))
cat("Mu hat:", mu_hat, "Sigma Squared hat - Predicted standard deviation:", sigma_sq_hat, "MLE mu_ln", mu_ln_hat)
return(c(mu_hat = mu_hat, sigma_sq_hat = sigma_sq_hat, mu_ln_hat = mu_ln_hat))
}
mle_results = normlog_mle(wellsize)
Mu hat: 3.268536 Sigma Squared hat - Predicted standard deviation: 0.3271989 MLE mu_ln 30.94264
#no gradient function (closed form no optim) --> partial differentiation and set to 0
# Solve system for MLE (mu_LN_hat)
Question 3.2
(2). Take 1000 Bootstrap samples from the raw oil data set. For each
bootstrap sample, call the above R function to find the bootstrap MLE of
μLN, denoted by dμ∗ LN (1) , dμ∗ LN (2) , · · · , dμ∗ LN (1000).
Note: \[\mu_{LN} = \exp\left(\mu +
\frac{1}{2}\sigma^2\right)\]
set.seed(143)
length(wellsize) #n =50
[1] 50
boot_mu_ln_mle = NULL
log_well= wellsize
for (i in 1:1000)
{
#bootstrap sample
# make sure sample is in its log form
# take raw not log of mean #log(wellsize) --> log the bootstrapped sample
bootstrap_well= sample(x=log_well, 50, replace= TRUE) #bootstrapping from the well sample
log_boot_well=log(bootstrap_well) #take the log of the bootstrapped sample to run the log likelihood
#take the mean of the log likelihood bootstrap to input in MLE mu equation
mu_hat = mean(log_boot_well) #MLE estimator for mu
sigma_sq_hat = mean((log_boot_well-mu_hat)^2) #MLE estimator for simga^2
#Now calculate the mu ln
boot_mu_ln_mle[i] = exp(mu_hat +(0.5* sigma_sq_hat)) #gives distrubution of the bootstrap for the mu ln mle
final_mu_ln_MLE = mean(boot_mu_ln_mle) #gives single value for bootstrapped mle mu ln
#return(c(final_mu_ln_MLE)) #only keeping last thing ran --> VERRY VERYY BAD FOR bootstrapping --> not keeping the distribution for the model
}
cat("Bootstrap MLE of μLN:", final_mu_ln_MLE)
Bootstrap MLE of μLN: 30.93064
The bootstrap MLE of \(\mu_{ln}\) is
30.9306417.
Question 3.3
(3). Using kernel density estimation approach to estimate the
bootstrap density curves based on the bootstrap MLEs: dμ∗ LN (1) , dμ∗
LN (2) , · · · , dμ∗ LN (1000).
#sd_ml_MLE=sd(boot_mu_ln_mle) #you would need to calculate standard error of the distribution to make a bandwidth for the kernel
kde = density(boot_mu_ln_mle, kernel = "gaussian") #density(boot_mu_ln_mle, bw = sd_ml_MLE)
hist(boot_mu_ln_mle, # data used for histogram
breaks = 14, # specify number of vertical bars
probability = TRUE,
xlab = "Bootstrap sample means", # change the label of x-axis
# add a title to the histogram
main="Bootstrap Sampling Distribution and Kernel Comparison \n of Sample Means",
cex.main = 0.9,
col.main = "navy")
lines(density(boot_mu_ln_mle, kernel = "gaussian"), col= "skyblue", lwd=2)
x_values <- seq(min(boot_mu_ln_mle), max(boot_mu_ln_mle), length = 100)
y_values <- dnorm(x_values, mean = mean(boot_mu_ln_mle), sd = sd(boot_mu_ln_mle))
lines(x_values, y_values, col = "red", lty = 2, lwd = 2) # Theoretical Normal
legend("topright", legend = c("KDE (Actual)", "Bootstrapped Normal (Theory)"),
col = c("skyblue", "red"), lty = c(1, 2), lwd = 2)

##Add asymptotic density curve
Question 3.4
(4). In order to find the asymptotic sampling distribution using the
central limit theorem (CLT). That is, when sample size is large, ¯X → N
μLN, σLN √ n where μLN and σLN can be estimated by using the plug-in
principle of MLE. Based on the asymptotic sampling distribution of
lognormal sample mean ¯X , add the asymptotic density curve to the above
Bootstrap kernel density curve.
n = length(wellsize) #
#sigma / (sqrt(n))
########################Background info for log specific estimators
#a normal distribution function dnorm() requires a mean and standard deviation
mu_hat= mean(log(wellsize)) # mean of natural log of sample
sigma_sq_hat = mean((log(wellsize)-mu_hat)^2) #needed to calculate standard error #no use ln value
#dnorm(wellsize, mean = mu_hat, sd= )
##############################################
#######LN values needed to calculate dnorm() asymptotic distribution
mu_ln_hat = exp(mu_hat + (0.5* sigma_sq_hat))
sigma_sq_hat_ln= exp(2*mu_hat + sigma_sq_hat) * (exp(sigma_sq_hat) - 1) #sigma^2 ln hat value --> predicted MLE value for variation
asympt_dis_se=sqrt(sigma_sq_hat_ln)/sqrt(n) #standard error for asymptotic sampling distribution
x_axis = seq(min(boot_mu_ln_mle), max(boot_mu_ln_mle), length = 200) #defining range for distribution most valuable when being graphed
#Make theoretical density of asymptotic distribution
asymptotic_dis_theory = dnorm(x_axis, mean = mu_ln_hat, sd = asympt_dis_se)
#asymptotic_dis_theory = dnorm(wellsize, mean= mu_ln_hat, sd=asympt_dis_se ) #sd --> enter standard error asympt_dis_se
kde = density(boot_mu_ln_mle, kernel = "gaussian") #density(boot_mu_ln_mle, bw = sd_ml_MLE)
hist(boot_mu_ln_mle, # data used for histogram
breaks = 14, # specify number of vertical bars
probability = TRUE,
xlab = "Bootstrap sample means", # change the label of x-axis
# add a title to the histogram
main="Bootstrap Sampling Distribution, Kernel and Asymptotic Density \n of Sample Means",
cex.main = 0.9,
col.main = "navy")
lines(density(boot_mu_ln_mle, kernel = "gaussian"), col= "skyblue", lwd=2)
lines(x_axis, asymptotic_dis_theory, col = "blue", lwd = 2, lty = 4)
x_values <- seq(min(boot_mu_ln_mle), max(boot_mu_ln_mle), length = 100) #defining graph range bootstrap
y_values <- dnorm(x_values, mean = mean(boot_mu_ln_mle), sd = sd(boot_mu_ln_mle))
lines(x_values, y_values, col = "red", lty = 2, lwd = 2) # Theoretical Normal
legend("topright", legend = c("Bootstrap Normal KDE (Actual)", "Bootstrap Normal (Theory)", "Asymptotic CLT"),
col = c("skyblue", "red", "blue"), lty = c(1, 2), lwd = 2) #col = c("skyblue", "blue"), lty = c(1, 2), lwd = 2)

Question 3.5
(5). Write a short summary to compare the two sampling distributions
of the sample mean of the lognormal distribution.
The description below refers to the behavior of the kernel density
estimator (KDE) bootstrap exclusively when referring to the bootstrap
distrbution.
The two major sampling distributions used above for the sample mean
included bootstrap sampling distribution for \(\mu_{ln}\) and asymptotic distribution.
Both distributions are used to estimate the behavior of a distribution
and estimations for population parameters.
The bootstrapping distribution is an empirical estimation of the
\(\mu_{LN}\) parameter by taking
repeated random samples from the original well sample and repeatedly
calculating a mean from each sample. All of the bootstrapped samples are
then meaned to reach an \(\mu\)
estimator. This is a simulated approach to the MLE \(\hat\mu_{LN}\). As the bootstrap resampling
method is an indirect way to calculate and estimator, as in the
collected distribution is not assessed soley within the single collected
distribution but the estimator is calculated over the estimator over of
collection of resamples from the originally collected distribution.
Repeatably resampling and calculating random bootstrap variables to
ultimately calculate the random variable estimator of interest, \(\hat\mu_{LN}\).
We see the relationship in the Figure above (last figure in question
3.4) the bootstrap gaussian kernel density has a better fit to the
maxima and minimums of the distribution, while the asymptotic
distribution under performs in assuming the shape for the most occurring
density at \(\hat\mu_{LN}\) and has
fatter tails than the bootstrap KDE, suggesting a weaker fit than the
KDE bootstrap.
The more the bootstrap is sampled, it can be assumed the bootstrap
estimator reaches closer to the true estimator. In examining the
differences between a kernel and asymptotic distribution, the bootstrap
kernel density best suits the empirical data rather than assuming
normality with a large sample size to met an approximation for the
asymptotic distribution. As the best suited normal distribution is
assigned to the asymptotic distribution in its parametric approach in
approximation rather than fitting for the data empirically.
In reflection for this lognormal distribution specifically, Both
distributions are similar in shape showing a natural order pattern in
the data set, in which the distributions meets their respective
conditions. Additionally, both distributions show a similar value
towards the \(\hat\mu_{LN}\), the
bootstrap being 30.9306417 and the asymptotic distribution being
30.9426444.
The bootstrapped value for \(\hat\mu_{LN}\) is 30.9306417 which is very
close to the asymptotic mean at30.9426444. Our two distributions capture
the predicted \(\hat\mu_{LN}\)
similarly suggesting some rigor in both tests. If a decision needs to be
made about which distribution best suits the model, the bootstrap KDE
resamping offers a stronger fit to the histogram’s raw or natural
distribution suggesting the MLE parameters derived from this
distribution may have more rigor than their asymptotic distribution
counterparts, although again, both distributions follow very similar
patterns and information. Any selection made between the two
distributions, should not vary between each other very much by eye and
graph analysis.
4 Bonus Question
Derive the Hessian matrix by computing the second-order partial
derivatives of the log-likelihood function (with respect to μ and σ2).
Then, translate the derived Hessian into an R function that takes the
MLEs of the parameters and the data as inputs and returns the Hessian
matrix. Finally, compare your analytically derived Hessian with the
numerical Hessian returned by optim().
data= wellsize #log(wellsize)
log_like_wells_hess <- function(params, data)
{
mu = params[1] # shape parameter
sigma_sq = params[2] # scale parameter
n <- length(data)
log_lik = (-n/2 * log(2*pi) - n/2 * log(sigma_sq) - sum(log(data)) - (1/(2*sigma_sq)) * sum((log(data) - mu)^2)) #we flip signs in the matrix process
return(log_lik)
}
log_likelihood_gradient = function(params, data)
{
mu = params[1]
sigma_sq = params[2]
n = length(data)
#Gradient functions
# Taking the partial derivative with respect to mu
d_mu <- (1/sigma_sq) * sum(log(data) - mu)
# Partial derivative with respect to sigma_sq
d_sigma_sq <- -n/(2 * sigma_sq) + (1/(2 * sigma_sq^2)) * sum((log(data) - mu)^2)
return(c(d_mu, d_sigma_sq))
}
analytical_hessian_func = function(params, data)
{
mu = params[1]
sigma_sq = params[2]
n = length(data)
#Computing the second derivatives for mu and sigma^2
d2_mu <- -n / sigma_sq
d2_sigma_sq <- n/(2 * sigma_sq^2) - (1/sigma_sq^3) * sum((log(data) - mu)^2)
d_mu_d_sigma_sq <- -(1/sigma_sq^2) * sum(log(data) - mu)
# This analytically derived matrix
hess_mat <- matrix(c(d2_mu, d_mu_d_sigma_sq, d_mu_d_sigma_sq, d2_sigma_sq),nrow = 2, byrow = TRUE)
#return(c(d_mu, d_sigma_sq, d2_mu, d2_sigma_sq, d_mu_d_sigma_sq)) # Return log-likelihood NOT the negative log-likelihood and gradients
return(hess_mat)
}
# Finding Initial Values
## It is critical to select appropriate initial values to
## ensure fast convergence. In general, we can use whatever
## methods (such as MME) that are available to get appropriate
## initial values
# Using the MLE as the initial parameter estimates
initial_mu = mu_hat
initial_sigma_sq = sigma_sq_hat
#mle_optimization <- optim(par = c(initial_mu,initial_sigma_sq), fn = log_like_wells_hess, x = wellsize, hessian = TRUE)
# MLE using optim() with gradient
mle_result <- optim(
par = c(mu_hat, sigma_sq_hat), #starting point of the predicted mu and sigma for the MLE
fn = log_like_wells_hess,
gr = log_likelihood_gradient,
data = wellsize,
method = "L-BFGS-B",
lower = c(-Inf, 1e-6),
hessian = TRUE,
control = list(fnscale = -1)
)
##
mle_result
$par
[1] 3.2685359 0.3271989
$value
[1] -206.444
$counts
function gradient
8 8
$convergence
[1] 0
$message
[1] "CONVERGENCE: REL_REDUCTION_OF_F <= FACTR*EPSMCH"
$hessian
[,1] [,2]
[1,] -1.528123e+02 5.185142e-14
[2,] 5.185142e-14 -2.335224e+02
#Comparing the hessian matrices derived analytically and optim()
numerical_hessian <- mle_result$hessian
analytical_hessian <- analytical_hessian_func(mle_result$par, wellsize)
# Print for your midterm report
cat("--- Numerical Hessian from optim() ---\n")
--- Numerical Hessian from optim() ---
print(numerical_hessian)
[,1] [,2]
[1,] -1.528123e+02 5.185142e-14
[2,] 5.185142e-14 -2.335224e+02
cat("\n--- Analytically Derived Hessian ---\n")
--- Analytically Derived Hessian ---
print(analytical_hessian)
[,1] [,2]
[1,] -1.528123e+02 1.037019e-13
[2,] 1.037019e-13 -2.335158e+02
Both show negative correlation among \(\mu\) and \(\sigma^2\) and present similar values. Both
show similarity in their sampling distribution.
LS0tDQp0aXRsZTogIjA3LSBNaWR0ZXJtIEV4YW06IFNUQSA1MDYiDQphdXRob3I6ICJFemFuYSBSaXZlcnMiDQpkYXRlOiAiIER1ZTogMDMtMDgtMjAyNiINCm91dHB1dDoNCiAgaHRtbF9kb2N1bWVudDogDQogICAgdG9jOiB5ZXMNCiAgICB0b2NfZGVwdGg6IDQNCiAgICB0b2NfZmxvYXQ6IHllcw0KICAgIG51bWJlcl9zZWN0aW9uczogbm8NCiAgICB0b2NfY29sbGFwc2VkOiB5ZXMNCiAgICBjb2RlX2ZvbGRpbmc6IGhpZGUNCiAgICBjb2RlX2Rvd25sb2FkOiB5ZXMNCiAgICBzbW9vdGhfc2Nyb2xsOiB5ZXMNCiAgICB0aGVtZTogbHVtZW4NCiAgcGRmX2RvY3VtZW50OiANCiAgICB0b2M6IHllcw0KICAgIHRvY19kZXB0aDogNA0KICAgIGZpZ19jYXB0aW9uOiB5ZXMNCiAgICBudW1iZXJfc2VjdGlvbnM6IHllcw0KICAgIGZpZ193aWR0aDogMw0KICAgIGZpZ19oZWlnaHQ6IDMNCiAgd29yZF9kb2N1bWVudDogDQogICAgdG9jOiB5ZXMNCiAgICB0b2NfZGVwdGg6IDQNCiAgICBmaWdfY2FwdGlvbjogeWVzDQogICAga2VlcF9tZDogeWVzDQplZGl0b3Jfb3B0aW9uczogDQogIGNodW5rX291dHB1dF90eXBlOiBpbmxpbmUNCi0tLQ0KDQpgYGB7Y3NzLCBlY2hvID0gRkFMU0V9DQojVE9DOjpiZWZvcmUgew0KICBjb250ZW50OiAiVGFibGUgb2YgQ29udGVudHMiOw0KICBmb250LXdlaWdodDogYm9sZDsNCiAgZm9udC1zaXplOiAxLjJlbTsNCiAgZGlzcGxheTogYmxvY2s7DQogIGNvbG9yOiBuYXZ5Ow0KICBtYXJnaW4tYm90dG9tOiAxMHB4Ow0KfQ0KDQoNCmRpdiNUT0MgbGkgeyAgICAgLyogdGFibGUgb2YgY29udGVudCAgKi8NCiAgICBsaXN0LXN0eWxlOnVwcGVyLXJvbWFuOw0KICAgIGJhY2tncm91bmQtaW1hZ2U6bm9uZTsNCiAgICBiYWNrZ3JvdW5kLXJlcGVhdDpub25lOw0KICAgIGJhY2tncm91bmQtcG9zaXRpb246MDsNCn0NCg0KaDEudGl0bGUgeyAgICAvKiBsZXZlbCAxIGhlYWRlciBvZiB0aXRsZSAgKi8NCiAgZm9udC1zaXplOiAyMnB4Ow0KICBmb250LXdlaWdodDogYm9sZDsNCiAgY29sb3I6IERhcmtSZWQ7DQogIHRleHQtYWxpZ246IGNlbnRlcjsNCiAgZm9udC1mYW1pbHk6ICJHaWxsIFNhbnMiLCBzYW5zLXNlcmlmOw0KfQ0KDQpoNC5hdXRob3IgeyAvKiBIZWFkZXIgNCAtIGFuZCB0aGUgYXV0aG9yIGFuZCBkYXRhIGhlYWRlcnMgdXNlIHRoaXMgdG9vICAqLw0KICBmb250LXNpemU6IDE1cHg7DQogIGZvbnQtd2VpZ2h0OiBib2xkOw0KICBmb250LWZhbWlseTogc3lzdGVtLXVpOw0KICBjb2xvcjogbmF2eTsNCiAgdGV4dC1hbGlnbjogY2VudGVyOw0KfQ0KDQpoNC5kYXRlIHsgLyogSGVhZGVyIDQgLSBhbmQgdGhlIGF1dGhvciBhbmQgZGF0YSBoZWFkZXJzIHVzZSB0aGlzIHRvbyAgKi8NCiAgZm9udC1zaXplOiAxOHB4Ow0KICBmb250LXdlaWdodDogYm9sZDsNCiAgZm9udC1mYW1pbHk6ICJHaWxsIFNhbnMiLCBzYW5zLXNlcmlmOw0KICBjb2xvcjogRGFya0JsdWU7DQogIHRleHQtYWxpZ246IGNlbnRlcjsNCn0NCg0KaDEgeyAvKiBIZWFkZXIgMSAtIGFuZCB0aGUgYXV0aG9yIGFuZCBkYXRhIGhlYWRlcnMgdXNlIHRoaXMgdG9vICAqLw0KICAgIGZvbnQtc2l6ZTogMjBweDsNCiAgICBmb250LXdlaWdodDogYm9sZDsNCiAgICBmb250LWZhbWlseTogIlRpbWVzIE5ldyBSb21hbiIsIFRpbWVzLCBzZXJpZjsNCiAgICBjb2xvcjogZGFya3JlZDsNCiAgICB0ZXh0LWFsaWduOiBjZW50ZXI7DQp9DQoNCmgyIHsgLyogSGVhZGVyIDIgLSBhbmQgdGhlIGF1dGhvciBhbmQgZGF0YSBoZWFkZXJzIHVzZSB0aGlzIHRvbyAgKi8NCiAgICBmb250LXNpemU6IDE4cHg7DQogICAgZm9udC13ZWlnaHQ6IGJvbGQ7DQogICAgZm9udC1mYW1pbHk6ICJUaW1lcyBOZXcgUm9tYW4iLCBUaW1lcywgc2VyaWY7DQogICAgY29sb3I6IG5hdnk7DQogICAgdGV4dC1hbGlnbjogbGVmdDsNCn0NCg0KaDMgeyAvKiBIZWFkZXIgMyAtIGFuZCB0aGUgYXV0aG9yIGFuZCBkYXRhIGhlYWRlcnMgdXNlIHRoaXMgdG9vICAqLw0KICAgIGZvbnQtc2l6ZTogMTZweDsNCiAgICBmb250LXdlaWdodDogYm9sZDsNCiAgICBmb250LWZhbWlseTogIlRpbWVzIE5ldyBSb21hbiIsIFRpbWVzLCBzZXJpZjsNCiAgICBjb2xvcjogbmF2eTsNCiAgICB0ZXh0LWFsaWduOiBsZWZ0Ow0KfQ0KDQpoNCB7IC8qIEhlYWRlciA0IC0gYW5kIHRoZSBhdXRob3IgYW5kIGRhdGEgaGVhZGVycyB1c2UgdGhpcyB0b28gICovDQogICAgZm9udC1zaXplOiAxNHB4Ow0KICBmb250LXdlaWdodDogYm9sZDsNCiAgICBmb250LWZhbWlseTogIlRpbWVzIE5ldyBSb21hbiIsIFRpbWVzLCBzZXJpZjsNCiAgICBjb2xvcjogZGFya3JlZDsNCiAgICB0ZXh0LWFsaWduOiBsZWZ0Ow0KfQ0KDQovKiBBZGQgZG90cyBhZnRlciBudW1iZXJlZCBoZWFkZXJzICovDQouaGVhZGVyLXNlY3Rpb24tbnVtYmVyOjphZnRlciB7DQogIGNvbnRlbnQ6ICIuIjsNCg0KYm9keSB7IGJhY2tncm91bmQtY29sb3I6d2hpdGU7IH0NCg0KLmhpZ2hsaWdodG1lIHsgYmFja2dyb3VuZC1jb2xvcjp5ZWxsb3c7IH0NCg0KcCB7IGJhY2tncm91bmQtY29sb3I6d2hpdGU7IH0NCg0KfQ0KYGBgDQoNCmBgYHtyIHNldHVwLCBpbmNsdWRlPUZBTFNFfQ0KIyBjb2RlIGNodW5rIHNwZWNpZmllcyB3aGV0aGVyIHRoZSBSIGNvZGUsIHdhcm5pbmdzLCBhbmQgb3V0cHV0IA0KIyB3aWxsIGJlIGluY2x1ZGVkIGluIHRoZSBvdXRwdXQgZmlsZXMuDQppZiAoIXJlcXVpcmUoImtuaXRyIikpIHsNCiAgIGluc3RhbGwucGFja2FnZXMoImtuaXRyIikNCiAgIGxpYnJhcnkoa25pdHIpDQp9DQppZiAoIXJlcXVpcmUoInBhbmRlciIpKSB7DQogICBpbnN0YWxsLnBhY2thZ2VzKCJwYW5kZXIiKQ0KICAgbGlicmFyeShwYW5kZXIpDQp9DQppZiAoIXJlcXVpcmUoImdncGxvdDIiKSkgew0KICBpbnN0YWxsLnBhY2thZ2VzKCJnZ3Bsb3QyIikNCiAgbGlicmFyeShnZ3Bsb3QyKQ0KfQ0KaWYgKCFyZXF1aXJlKCJ0aWR5dmVyc2UiKSkgew0KICBpbnN0YWxsLnBhY2thZ2VzKCJ0aWR5dmVyc2UiKQ0KICBsaWJyYXJ5KHRpZHl2ZXJzZSkNCn0NCg0KaWYgKCFyZXF1aXJlKCJwbG90bHkiKSkgew0KICBpbnN0YWxsLnBhY2thZ2VzKCJwbG90bHkiKQ0KICBsaWJyYXJ5KHBsb3RseSkNCn0NCiMjIyMNCmtuaXRyOjpvcHRzX2NodW5rJHNldChlY2hvID0gVFJVRSwgICAgICAgIyBpbmNsdWRlIGNvZGUgY2h1bmsgaW4gdGhlIG91dHB1dCBmaWxlDQogICAgICAgICAgICAgICAgICAgICAgd2FybmluZyA9IEZBTFNFLCAgICMgc29tZXRpbWVzLCB5b3UgY29kZSBtYXkgcHJvZHVjZSB3YXJuaW5nIG1lc3NhZ2VzLA0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAjIHlvdSBjYW4gY2hvb3NlIHRvIGluY2x1ZGUgdGhlIHdhcm5pbmcgbWVzc2FnZXMgaW4NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIyB0aGUgb3V0cHV0IGZpbGUuIA0KICAgICAgICAgICAgICAgICAgICAgIHJlc3VsdHMgPSBUUlVFLCAgICAjIHlvdSBjYW4gYWxzbyBkZWNpZGUgd2hldGhlciB0byBpbmNsdWRlIHRoZSBvdXRwdXQNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIyBpbiB0aGUgb3V0cHV0IGZpbGUuDQogICAgICAgICAgICAgICAgICAgICAgbWVzc2FnZSA9IEZBTFNFLA0KICAgICAgICAgICAgICAgICAgICAgIGNvbW1lbnQgPSBOQQ0KICAgICAgICAgICAgICAgICAgICAgICkgIA0KYGBgDQogDQpcDQoNCiMgTWlkdGVybSBFeGFtIE9iamVjdGl2ZXMgDQoNCg0KKiBVbmRlcnN0YW5kIHRoZSBkZWZpbml0aW9uIGFuZCByZWxhdGlvbnNoaXAgYmV0d2VlbiBQREZzIGFuZCBDREZzLCBpbmNsdWRpbmcgdGhlaXIgbm9uLXBhcmFtZXRyaWMgZXN0aW1hdG9yczogdGhlIGVtcGlyaWNhbCBkaXN0cmlidXRpb24gZnVuY3Rpb24gYW5kIGtlcm5lbCBkZW5zaXR5IGVzdGltYXRpb24gKEtERSkuIFwNCg0KKiBFc3RpbWF0ZSBzYW1wbGluZyBkaXN0cmlidXRpb25zIHVzaW5nIHNpbXVsYXRpb24tYmFzZWQgbWV0aG9kcywgc3BlY2lmaWNhbGx5IHRoZSBib290c3RyYXAuIFwNCg0KKiBEZXJpdmUgcG9pbnQgZXN0aW1hdGVzIG9mIHBhcmFtZXRlcnMgdXNpbmcgdGhlIG1ldGhvZCBvZiBtb21lbnRzIGFuZCBtYXhpbXVtIGxpa2VsaWhvb2QgZXN0aW1hdGlvbiAoTUxFKS4gXA0KKiBEZXNjcmliZSB0aGUgYXN5bXB0b3RpYyAobm9ybWFsKSBhbmQgYm9vdHN0cmFwIHNhbXBsaW5nIGRpc3RyaWJ1dGlvbnMgb2YgbWF4aW11bSBsaWtlbGlob29kIGVzdGltYXRvcnMuIFwNCiogQXBwbHkgYWxsIHRoZSBhYm92ZSBpbmZlcmVudGlhbCBwcm9jZWR1cmVzIGluIGEgcHJvZ3JhbW1pbmcgZW52aXJvbm1lbnQgKHN1Y2ggYXMgUHl0aG9uKSB0byBwZXJmb3JtIG51bWVyaWNhbCBkYXRhIGFuYWx5c2lzLiBcDQoNCg0KDQojIyBMb2dub3JtYWwgRGlzdHJ1YnV0aW9uDQoNCjUuMSBMb2ctbm9ybWFsIERpc3RyaWJ1dGlvbiBUaGUgbG9nLW5vcm1hbCBkaXN0cmlidXRpb25zIGhhdmUgYmVlbiB3aWRlbHkgdXNlZCBpbiBtYW55IGRpZmZlcmVudCBmaWVsZHMgc3VjaCBhcyBmaW5hbmNlIGFuZCBlY29ub21pY3MsIGVuZ2luZWVyaW5nIGFuZCByZWxpYWJpbGl0eSwgZW52aXJvbm1lbnRhbCBzY2llbmNlLCBtZWRpY2FsIGFuZCBiaW9sb2d5IGV0Yy4gSWYgWCBmb2xsb3dzIGEgbG9nbm9ybWFsIGRpc3RyaWJ1dGlvbjogZih4O8K1LM+DMikgPSDiiJogMSB4IDLPgM+DMiBleHAg4oiSKGxueOKIksK1KTIgMs+DMiB3aGVyZSDCtSDiiIggUiBpcyB0aGUgbWVhbiBvZiBsblggYW5kIM+DMiA+IDAgaXMgdGhlIHZhcmlhbmNlIG9mIGxuWC4NCg0KDQoNCldvcmtpbmcgRGF0YXNldDogQSByZXNlcnZvaXIgZW5naW5lZXIgYXQgYW4gb2lsIGV4cGxvcmF0aW9uIGNvbXBhbnkgaGFzIHJlY2VudGx5IGRyaWxsZWQgNTAgbmV3IHdlbGxzIGluIGEgc2hhbGUgZm9ybWF0aW9uLiBBY2NvcmRpbmcgdG8gZ2VvbG9naWNhbCB0aGVvcnksIHRoZSBzaXplIG9mIG9pbCByZXNlcnZlcyBpbiB0aGlzIHR5cGUgb2YgZm9ybWF0aW9uIGlzIG9mdGVuIG1vZGVsZWQgdXNpbmcgYSBsb2ctbm9ybWFsIGRpc3RyaWJ1dGlvbi4gVGhlIGVuZ2luZWVyIGlzIHJlc3BvbnNpYmxlIGZvciBlc3RpbWF0aW5nIHRoZSB0eXBpY2FsIHJlc2VydmUgc2l6ZSBhbmQgcXVhbnRpZnlpbmcgdGhlIHVuY2VydGFpbnR5IG9mIHRoZXNlIGVzdGltYXRlcyBmb3IgYSBwcmVzZW50YXRpb24gdG8gc2VuaW9yIG1hbmFnZW1lbnQuIFRoZSBlc3RpbWF0ZWQgdWx0aW1hdGUgcmVjb3ZlcnkgKEVVUikgZm9yIHRoZSA1MCB3ZWxscywgbWVhc3VyZWQgaW4gdGhvdXNhbmRzIG9mIGJhcnJlbHMgKE1iYmwpLCBpcyBhcyBmb2xsb3dzOiANCg0KYGBgDQoxNy4zLCAyNC44LCA4LjIsIDMxLjUsIDE0LjEsIDQyLjcsIDExLjksIDU1LjMsIDIxLjQsIDkuNywgMzYuMiwgMTguNiwgNjMuMSwgMTMuMiwgMjguOSwgNDcuNSwgMTkuOCwgNy41LCAzMy40LCA1Mi4xLCAxNi4wLCAyNS45LCAzOC43LCAxMC4zLCA0NC4yLCAyMi41LCA1OC42LCAxMi44LCAzMC4zLCA0OC45LCAyMC4xLCAzNS40LCAxNS43LCA2MC4yLCAyNi43LCA0MS4zLCAxOC4xLCA1My44LCAyMy45LCA0Ni4yLCAyOS40LCAzNy42LCAxNC45LCA1MC41LCAzMi44LCAxOS4zLCA1Ni43LCAxMS4yLCAzOS41LCAyNy4xIA0KYGBgDQoNClRoaXMgYXNzaWdubWVudCBmb2N1c2VzIG9uIGZpbmRpbmcgdGhlIGFzeW1wdG90aWMgc2FtcGxpbmcgZGlzdHJpYnV0aW9ucyBvZiB0aGUgTUxFIMuGwrUgYW5kIMuGIHRvIMK1IGFuZCDPgzIgYmFzZWQgb24gYW4gZW52aXJvbm1lbnRhbCBzdHVkeSBkYXRhLg0KDQoNCiMgUXVlc3Rpb24gMTogTWV0aG9kIG9mIE1vbWVudHMgRXN0aW1hdGlvbiAoTU1FKSBvZiDCtSBhbmQgz4MyDQoNCkVzdGltYXRlIHRoZSBwYXJhbWV0ZXJzIMK1IGFuZCDPgzIgKGNhdXRpb246IG5vdCDPgyEpICBmcm9tIHRoZSByYXcgb2lsIHJlc2VydmUgZGF0YSB1c2luZyB0aGUgZ2l2ZW4gay10aCBtb21lbnQgZnVuY3Rpb24uIA0KT3JnYW5pemUgeW91ciB3b3JrIGludG8gdGhyZWUgcGFydHM6DQoNCihhKSBEZXJpdmUgdGhlIHN5c3RlbSBvZiB0d28gZXF1YXRpb25zIGZvciB0aGUgbWV0aG9kIG9mIG1vbWVudHMgZXN0aW1hdG9ycyAoTU1Fcykgb2YgwrUgYW5kIM+DMi4NCg0KDQpgYGB7cn0NCiMxYS4gRGVyaXZpbmcgdGhlIHN5c3RlbSBvZiB0d28gZXF1YXRpb25zIGZvciB0aGUgbWV0aG9kcyBvZiBtb21lbnQgZXN0aW1hdG9ycyAoTU1FKSBvZiBtdSBhbmQgc2lnbWFfc3ENCg0Kd2VsbHNpemU9IHNvcnQoYygxNy4zLCAyNC44LCA4LjIsIDMxLjUsIDE0LjEsIDQyLjcsIDExLjksIDU1LjMsIDIxLjQsIDkuNywgMzYuMiwgMTguNiwgNjMuMSwgMTMuMiwgMjguOSwgNDcuNSwgMTkuOCwgNy41LCAzMy40LCA1Mi4xLCAxNi4wLCAyNS45LCAzOC43LCAxMC4zLCA0NC4yLCAyMi41LCA1OC42LCAxMi44LCAzMC4zLCA0OC45LCAyMC4xLCAzNS40LCAxNS43LCA2MC4yLCAyNi43LCA0MS4zLCAxOC4xLCA1My44LCAyMy45LCA0Ni4yLCAyOS40LCAzNy42LCAxNC45LCA1MC41LCAzMi44LCAxOS4zLCA1Ni43LCAxMS4yLCAzOS41LCAyNy4xICkpDQoNCg0KI20gbW9tZW50cyBmb3IgcGFyYW1ldGVycw0KbTEgPSBtZWFuKHdlbGxzaXplKSAjeGJhcg0KbTI9IG1lYW4od2VsbHNpemVeMikgI3ggc3F1YXJlZCBiYXINCiNhbGdlYnJpYyBhcHBsaWNhdGlvbiBmb3IgY2xvc2VkIGZvcm0gcG9wdWxhdGlvbiBwYXJhbWV0ZXJzIHNpZ21hXjIgYW5kIG11DQoNCm1vbV9zaWdtYV9zcSA9IGxvZyhtMikgLSAyKmxvZyhtMSkNCm1vbV9tdSA9IGxvZyhtMSkgLTAuNSAqIG1vbV9zaWdtYV9zcQ0KDQpjYXQoIk1NRSBmb3IgbXU6IiwgbW9tX211LCAiXG5NTUUgZm9yIHNpZ21hX3NxOiIsIG1vbV9zaWdtYV9zcSkNCg0KY2F0KCJTYW1wbGUgbWVhbjoiLCBtMSwgInNhbXBsZSBzdGFuZGFyZCBkZXZpYXRpb246IiwgbTIpDQpgYGANCg0KDQooYikgRGVyaXZlIHRoZSBjbG9zZWQtZm9ybSBleHByZXNzaW9ucyBmb3IgdGhlIE1NRXMgb2YgwrUsIM+DMiwgYW5kIMK1TE4sIGRlbm90ZWQgYnkgwrV+LCDPgzJ+LCBhbmQgwrVMTn4sIHJlc3BlY3RpdmVseS4NCg0KDQpTeXN0ZW0gb2YgZXF1YXRpb25zOg0KJCQNCiAgICBcbG4oXGJhcnt4fSkgPSBcbXUgKyBcZnJhY3sxfXsyfVxzaWdtYV4yDQogICAgIFxsbihcYmFye3heMn0pID0gMlxtdSArIDJcc2lnbWFeMg0KJCQNCg0KDQoNCg0KU29sdmUgRXF1YXRpb24gMSBmb3IgJFxtdSQgaW4gdGVybXMgb2YgJFxzaWdtYV4yJDoNCiQkDQpbDQptdSA9IFxsbihcYmFye3h9KSAtIFxmcmFjezF9ezJ9XHNpZ21hXjINCl0NCiQkDQoNClN1YnN0aXR1dGUgdGhpcyBleHByZXNzaW9uIGZvciAkXG11JDoNCiANCiQkIA0KW2xuKHt4XjJ9KSA9IDJbIFxsbihcYmFye3h9KSAtIFxmcmFjezF9ezJ9XHNpZ21hXjJdICsgMlxzaWdtYV4yXQ0KJCQNCg0KRGlzdHJpYnV0ZSBhbmQgc2ltcGxpZnkgdG8gZmluZCAkXHRpbGRle1xzaWdtYX1eMiQ6fQ0KDQokJA0KW2xuKHt4XjJ9KSA9IDJsbihcYmFye3h9KSAtIFxzaWdtYV4yICsgMlxzaWdtYV4yXQ0KJCQNCiQkDQpbbG4oe3heMn0pID0gMmxuKFxiYXJ7eH0pICsgXHNpZ21hXjJdDQokJA0KDQokJA0KWyBcdGlsZGV7XHNpZ21hfV4yID0gbG4oe3heMn0pIC0gMmxuKFxiYXJ7eH0pXQ0KJCQNCiANCg0KDQogU3Vic3RpdHV0ZSAkXHRpbGRle1xzaWdtYX1eMiQgYmFjayBpbnRvIHRoZSBleHByZXNzaW9uIGZvciAkXG11JDoNCg0KJCQNCltcdGlsZGV7XG11fSA9IGxuKFxiYXJ7eH0pIC0gXGZyYWN7MX17Mn0gW2xuKHt4XjJ9KSAtIDJsbihcYmFye3h9KV1dDQokJA0KJCQNCltcdGlsZGV7XG11fSA9IGxuKFxiYXJ7eH0pIC0gXGZyYWN7MX17Mn0gbG4oe3heMn0pICsgbG4oXGJhcnt4fSldDQokJA0KJCQNCltcdGlsZGV7XG11fSA9IDJsbihcYmFye3h9KSAtIFxmcmFjezF9ezJ9bG4oe3heMn0pXQ0KJCQNCg0KDQpPYnNlcnZpbmcgYm90aCBlcXVhdGlvbnMNCg0KJCQNCltcdGlsZGV7XG11fSA9IDJsbihcYmFye3h9KSAtIFxmcmFjezF9ezJ9XGxuKHheMildDQokJA0KDQokJA0KW1x0aWxkZXtcc2lnbWF9XjIgPSBsbih7eF4yfSkgLSAybG4oXGJhcnt4fSldDQokJA0KDQoNCg0KKGMpIFdyaXRlIGFuIFIgZnVuY3Rpb24gdGhhdCBvdXRwdXRzIHRoZSBNTUVzIMK1LCDPgzIsIGFuZCDCtUxOIGJhc2VkIG9uIHRoZSBnaXZlbiBkYXRhIHNldC4NCg0KDQpgYGB7cn0NCg0KDQpzaWdtYV9zcXVfdGlsZGEgPSBsb2cobTIpLTIqIGxvZyhtMSkNCm11X3RpbGRhID0gMipsb2cobTEpIC0gKCgxLzIpKmxvZyhtMikpDQoNCg0KY2F0KCJNdSB0aWxkYToiLCBtdV90aWxkYSwgIlBvcHVsYXRpb24gc3RhbmRhcmQgZGV2aWF0aW9uOiIsIHNpZ21hX3NxdV90aWxkYSkNCg0KDQpgYGANCmBgYHtyfQ0KI1dyaXRpbmcgYSBmdW5jdGlvbiBmb3IgTWV0aG9kcyBvZiBNb21lbnQgRXN0aW1hdGlvbg0KDQpNTUVsb2dub3JtPSBmdW5jdGlvbih3ZWxsc2l6ZSkNCnsNCiAgDQojbSBtb21lbnRzIGZvciBwYXJhbWV0ZXJzDQptMSA9IG1lYW4od2VsbHNpemUpICN4YmFyDQptMj0gbWVhbih3ZWxsc2l6ZV4yKSAjeCBzcXVhcmVkIGJhcg0KI2FsZ2VicmljIGFwcGxpY2F0aW9uIGZvciBjbG9zZWQgZm9ybSBwb3B1bGF0aW9uIHBhcmFtZXRlcnMgc2lnbWFeMiBhbmQgbXUNCg0KI21vbV9zaWdtYV9zcSA9IGxvZyhtMikgLSAyKmxvZyhtMSkgICNyZW1vdmUgaXRzIHRoZSBzYW1lIGJlbG93DQojbW9tX211ID0gbG9nKG0xKSAtMC41ICogbW9tX3NpZ21hX3NxDQogIA0Kc2lnbWFfc3F1X3RpbGRhID0gbG9nKG0yKS0yKiBsb2cobTEpICNjYWxjdWxhdGUgdGhlIE1PTSBmb3Igc3RhbmRhcmQgZGVpdmF0aW9uDQptdV90aWxkYSA9IDIqbG9nKG0xKSAtICgoMS8yKSpsb2cobTIpKSAjIGNhbGN1bGF0ZSB0aGUgTU9NIGZvciBtZWFuDQoNCnJldHVybihjKG11X3RpbGRhLCBzaWdtYV9zcXVfdGlsZGEsIG0xKSApDQoNCn0NCnJlc3VsdHMgPSBNTUVsb2dub3JtKHdlbGxzaXplKQ0KDQpjYXQoIk11IHRpbGRhOiIsIG11X3RpbGRhLCAiUG9wdWxhdGlvbiBzdGFuZGFyZCBkZXZpYXRpb246Iiwgc2lnbWFfc3F1X3RpbGRhLCAibXVfTE4iLCBtMSkNCg0KYGBgDQoNClRoZSBvdXRwdXRzIGZvciB0aGUgbWV0aG9kIG9mIG1vbWVudCBlc3RpbWF0b3JzIGFyZSAkXHRpbGRlXG11JCA9IGByIG11X3RpbGRhYCwgJFx0aWxkZVxzaWdtYV4yJCA9IGByIHNpZ21hX3NxdV90aWxkYWAsIGFuZCAkXHRpbGRlXG11X3tMTn0kID0gYHIgbTFgLg0KDQoNCiMgUXVlc3Rpb24gMjogRmluZGluZyB0aGUgTUxFIG9mICRcbXUkIGFuZCAkXHNpZ21hXjIkIA0KDQojIyBRdWVzdGlvbiAyLjEgDQoNCigxKS4gRGVyaXZlIHRoZSBzY29yZSBmdW5jdGlvbnMgKGkuZS4sIHRoZSBncmFkaWVudCBvZiB0aGUgbG9nLWxpa2VsaWhvb2QpIGZvciB0aGUgcGFyYW1ldGVycyBvZiB0aGUgbG9nLW5vcm1hbCBkaXN0cmlidXRpb24sIGFuZCANCg0Kc2V0IHRoZW0gdG8gemVybyB0byBvYnRhaW4gdGhlIHN5c3RlbSBvZiBzY29yZSBlcXVhdGlvbnMuIA0KDQpCZWdpbiB3aXRoIHRoZSBmdWxsIGxvZy1saWtlbGlob29kIGFuZCBjb21wdXRlIGl0cyBwYXJ0aWFsIGRlcml2YXRpdmVzIHdpdGggcmVzcGVjdCB0byDCtSBhbmQgz4MyLiBbSGludDogbGV0dGluZyDOsiA9IM+DMiBtYXkgc2ltcGxpZnkgZGlmZmVyZW50aWF0aW9uLl0NCg0KDQoNClRoZSBsb2ctbGlrZWxpaG9vZCBmb3IgdGhlIGxvZy1ub3JtYWwgZGlzdHJpYnV0aW9uIGlzIGdpdmVuIGJ5Og0KDQokJA0KXGVsbChcbXUsIFxiZXRhKSA9IC1cZnJhY3tufXsyfSBcbG4oMlxwaSkgLSBcZnJhY3tufXsyfSBcbG4gXGJldGEgLSBcc3VtX3tpPTF9Xm4gXGxuIHhfaSAtIFxmcmFjezF9ezJcYmV0YX0gXHN1bV97aT0xfV5uIChcbG4geF9pIC0gXG11KV4yDQokJA0KIFBhcnRpYWwgZGVyaXZhdGl2ZSB3aXRoIHJlc3BlY3QgdG8gJFxtdSQ6DQogDQogDQokJA0KXGZyYWN7XHBhcnRpYWwgXGVsbH17XHBhcnRpYWwgXG11fSA9IFxmcmFje1xwYXJ0aWFsfXtccGFydGlhbCBcbXV9IFxsZWZ0WyAtXGZyYWN7MX17MlxiZXRhfSBcc3VtX3tpPTF9Xm4gKFxsbiB4X2kgLSBcbXUpXjIgXHJpZ2h0XSBcXA0KICAgID0gLVxmcmFjezF9ezJcYmV0YX0gXHN1bV97aT0xfV5uIDIoXGxuIHhfaSAtIFxtdSkgXGNkb3QgXGZyYWN7XHBhcnRpYWx9e1xwYXJ0aWFsIFxtdX0oXGxuIHhfaSAtIFxtdSkgXFwNCiAgICA9IC1cZnJhY3sxfXsyXGJldGF9IFxzdW1fe2k9MX1ebiAyKFxsbiB4X2kgLSBcbXUpIFxjZG90ICgtMSkgXFwNCiAgICBVKFxtdSkgPSBcZnJhY3sxfXtcYmV0YX0gXHN1bV97aT0xfV5uIChcbG4geF9pIC0gXG11KQ0KJCQNCg0KDQoNClJlYWNoIHRoZSBzY29yZSBmdW5jdGlvbiBvZiB0aGUgZXF1YXRpb25zDQpQYXJ0aWFsIGRlcml2YXRpdmUgd2l0aCByZXNwZWN0IHRvICRcYmV0YSQsIHdlIHRyZWF0ICRcYmV0YSQgaW4gc3Vic3RpdHV0aW9uIG9mICRcc2lnbWFeMiQgZm9yIHNpbXBsaWNpdHk6DQokJA0KXGZyYWN7XHBhcnRpYWwgXGVsbH17XHBhcnRpYWwgXGJldGF9ID0gXGZyYWN7XHBhcnRpYWx9e1xwYXJ0aWFsIFxiZXRhfSBcbGVmdFsgLVxmcmFje259ezJ9IFxsbiBcYmV0YSBccmlnaHRdIC0gXGZyYWN7XHBhcnRpYWx9e1xwYXJ0aWFsIFxiZXRhfSBcbGVmdFsgXGZyYWN7MX17MlxiZXRhfSBcc3VtX3tpPTF9Xm4gKFxsbiB4X2kgLSBcbXUpXjIgXHJpZ2h0XSBcXA0KICAgID0gLVxmcmFje259ezJcYmV0YX0gLSBcZnJhY3sxfXsyfSBcc3VtX3tpPTF9Xm4gKFxsbiB4X2kgLSBcbXUpXjIgXGNkb3QgXGZyYWN7ZH17ZFxiZXRhfShcYmV0YV57LTF9KSBcXA0KICAgID0gLVxmcmFje259ezJcYmV0YX0gLSBcZnJhY3sxfXsyfSBcc3VtX3tpPTF9Xm4gKFxsbiB4X2kgLSBcbXUpXjIgXGNkb3QgKC1cYmV0YV57LTJ9KSBcXA0KICAgIFUoXGJldGEpID0gLVxmcmFje259ezJcYmV0YX0gKyBcZnJhY3sxfXsyXGJldGFeMn0gXHN1bV97aT0xfV5uIChcbG4geF9pIC0gXG11KV4yDQokJA0KDQpSZXBsYWNpbmcgJFxiZXRhJCB3aXRoICRcc2lnbWFeMiQgIA0KDQokJA0KLVxmcmFje259ezJcc2lnbWFeMn0gKyBcZnJhY3sxfXsyXHNpZ21hXjR9IFxzdW1fe2k9MX1ebiAoXGxuIHhfaSAtIFxtdSleMiA9IDAgDQokJA0KDQoNCiMjIFF1ZXN0aW9uIDIuMg0KDQooMikuIFBlcmZvcm0gc29tZSBhbGdlYnJhIHRvIGZpbmQgdGhlIGNsb3NlZCBmb3JtIG9mIHRoZSBNTEUgb2YgwrUgYW5kIM+DMiwgZGVub3RlZCBieSDCtSBhbmQgz4MyDQoNCg0KU29sdmluZyBmb3IgJFxoYXRcbXUkDQoNCiQkDQpcc3VtX3tpPTF9Xm4gKFxsbiB4X2kgLSBcbXUpID0gMCBcXA0KXHN1bV97aT0xfV5uIFxsbiB4X2kgLSBuXG11ID0gMCBcXA0KXGhhdHtcbXV9ID0gXGZyYWN7MX17bn0gXHN1bV97aT0xfV5uIFxsbiB4X2kNCiQkDQoNCg0KU29sdmluZyBmb3IgJFxoYXRcc2lnbWFeMiQNCg0KJCQNClxmcmFje259ezJcc2lnbWFeMn0gPSBcZnJhY3sxfXsyXHNpZ21hXjR9IFxzdW1fe2k9MX1ebiAoXGxuIHhfaSAtIFxoYXR7XG11fSleMiBcXA0KblxzaWdtYV4yID0gXHN1bV97aT0xfV5uIChcbG4geF9pIC0gXGhhdHtcbXV9KV4yIFxcDQpcaGF0e1xzaWdtYX1eMiA9IFxmcmFjezF9e259IFxzdW1fe2k9MX1ebiAoXGxuIHhfaSAtIFxoYXR7XG11fSleMg0KJCQNCg0KDQoNCiMjIFF1ZXN0aW9uIDIuMyANCg0KKDMpLiBSZWNhbGwgdGhhdCBsb2dub3JtYWwgcG9wdWxhdGlvbiBtZWFuIChpLmUuLCB0aGUgZmlyc3QgbW9tZW50KSBpcw0KzrxMTiA9IEVbWF0gPSBleHAozrwgKyAxLzLPgzIpLg0KVXNpbmcgdGhlIHJlbGF0aW9uc2hpcCBiZXR3ZWVuIHZhcmlhbmNlIGFuZCB0aGUgZmlyc3QgYW5kIHNlY29uZCBtb21lbnRzLCANCg0KVmFyKFgpID0gRVtYMl0g4oiSIChFW1hdKTIsIA0KDQp3ZSBkZXJpdmUgdGhlIHBvcHVsYXRpb24gdmFyaWFuY2Ugb2YgdGhlIGxvZ25vcm1hbCBkaXN0cmlidXRpb24sIGRlbm90ZWQgYXMgz4MyDQpMTi4gVGhpcyByZXN1bHQgd2lsbCBiZSB1c2VkIGluDQphcHBseWluZyB0aGUgQ2VudHJhbCBMaW1pdCBUaGVvcmVtIGluIHN1YnNlcXVlbnQgcXVlc3Rpb25zDQoNCg0KJCQNCntWYXJ9KFgpID0gRVtYXjJdIC0oRVtYXSleMiBcXA0KJCQNCg0KJCQNClxzaWdtYV4yX3tMTn0gPSBFW1heMl0gLSAoRVtYXSleMiANCiQkDQoNCiQkDQpFW1hdID0gZXhwKFxtdSArIFxmcmFjezF9ezJ9XHNpZ21hXjIpIFxcDQoNCkVbWF5rXSA9IGV4cChrXG11ICsgXGZyYWN7MX17a31rXjJcc2lnbWFeMiksIFxcDQoNCkVbWF4yXSA9IGV4cCgyXG11ICsgXGZyYWN7MX17Mn0oMl4yKVxzaWdtYV4yKSBcXA0KRVtYXjJdID0gZXhwKDJcbXUgKyAyXHNpZ21hXjIpDQoNCiQkDQoNCiQkDQpcc2lnbWFeMl97TE59ID0gRVtYXjJdIC0gKEVbWF0pXjIgDQokJA0KDQoNCiQkDQpcc2lnbWFeMl97TE59ID0gZXhwKDJcbXUgKyAyXHNpZ21hXjIpIC0gWyBleHAoXG11ICsgXGZyYWN7MX17Mn1cc2lnbWFeMildXjIgDQokJA0KJCQNClxzaWdtYV4yX3tMTn0gPSBleHAoMlxtdSArIDJcc2lnbWFeMikgLSBleHAoMlxtdSArIFxzaWdtYV4yKQ0KJCQNCg0KDQoNCg0KDQoNCiMgUXVlc3Rpb24gMzogU2FtcGxpbmcgRGlzdHJpYnV0aW9uIG9mIExvZ25vcm1hbCBTYW1wbGUgTWVhbiAkXGhhdFxtdV97TE59JA0KDQpXZSBoYXZlIGRlcml2ZWQgdHdvIGRpZmZlcmVudCBlc3RpbWF0b3JzIG9mIGxvZ25vcm1hbCBwb3B1bGF0aW9uIG1lYW4gzrxMTi4gVGhpcyBRdWVzdGlvbiBmb2N1c2VzIG9uDQp0aGUgc2FtcGxpbmcgZGlzdHJpYnV0aW9uIG9mIGxvZ25vcm1hbCBzYW1wbGUgc2FtcGxlIG1lYW5zIGJhc2VkIG9uIE1MRS4gVGhlIGZvbGxvd2luZyBhcmUgZGV0YWlsZWQNCmluc3RydWN0aW9ucy4NCg0KIyBRdWVzdGlvbiAzLjEgDQoNCigxKS4gV3JpdGUgYW4gUiBmdW5jdGlvbiB0byBlc3RpbWF0ZSB0aGUgTUxFIG9mIM68IGFuZCDPgzIsIGRlbm90ZWQgYnkgYs68IGFuZCBjz4MyIGFuZCByZXR1cm4gdGhlIE1MRSBvZg0KzrxMTiwgZGVub3RlZCBieSAgJFxoYXRcbXVfe0xOfSQuDQoNClRoZSBsb2ctbGlrZWxpaG9vZCBmb3IgdGhlIGxvZy1ub3JtYWwgZGlzdHJpYnV0aW9uIGlzIGdpdmVuIGJ5Og0KDQokJA0KXGVsbChcbXUsIFxiZXRhKSA9IC1cZnJhY3tufXsyfSBcbG4oMlxwaSkgLSBcZnJhY3tufXsyfSBcbG4gXGJldGEgLSBcc3VtX3tpPTF9Xm4gXGxuIHhfaSAtIFxmcmFjezF9ezJcYmV0YX0gXHN1bV97aT0xfV5uIChcbG4geF9pIC0gXG11KV4yDQokJA0KDQoNCmBgYHtyfQ0KDQojV3JpdGUgdGhlIFIgZnVuY3Rpb24gdGhhdCBlc3RpbWF0aW9ucyB0aGUgTUxFIG9mIHRoZSBtdSBhbmQgc2lnbWFeMiBkZW5vdGVkIGJ5IG11X2hhdCBhbmQgc2lnbWEgc3F1YXJlIGhhdCB0byB0aGVuIHJldHVybg0KI1RoZSBNYXhpbXVtIExpbWl0YXRpb24gRXN0aW1hdG9yIG9mIHRoZSBtdV9MTiwgZGVub3RlZCBtdV9MTl9oYXQNCg0KDQpkYXRhID0gd2VsbHNpemUgI2luc2VydGluZyB0aGUgZGF0YSBvZiBpbnRlcmVzdCB0byBiZSB3ZWxsc2l6ZQ0KDQoNCg0Kbm9ybWxvZ19tbGU9IGZ1bmN0aW9uKGRhdGEpDQogIHsNCiAgICAjTE9HIExJS0xFSUhPT0QtLT4gaXRzIGEgbm9ybWFsbG9nIHNvIGZpbmUNCiAgICBsb2dfZGF0YSA9IGxvZyhkYXRhKQ0KICAgICNGaW5kIHRoZSBsZW5ndGggb2YgdGhlIGRhdGEgZm9yIGdyYWRpZW50IGVxdWF0aW9ucw0KICAgIA0KICAgIG4gPSBsZW5ndGgoZGF0YSkNCiAgICANCiAgICAjY2xvc2VkIGZvcm0gZm9yIG11X2hhdCBhbmQgc2lnbWFfc3FfaGF0DQogICAgbXVfaGF0ID0gbWVhbihsb2dfZGF0YSkNCiAgICBzaWdtYV9zcV9oYXQgPSBtZWFuKChsb2dfZGF0YS1tdV9oYXQpXjIpIA0KICAgIA0KICAgICNDYWxjdWxhdGluZyB0aGUgcG9wdWxhdGlvbiBwYXJhdGVycyBmb3IgTUxFOiBtdV9sbl9oYXQNCiAgICANCiAgICBtdV9sbl9oYXQgPSBleHAobXVfaGF0ICsgKDAuNSogc2lnbWFfc3FfaGF0KSkNCiAgICANCmNhdCgiTXUgaGF0OiIsIG11X2hhdCwgIlNpZ21hIFNxdWFyZWQgaGF0IC0gUHJlZGljdGVkIHN0YW5kYXJkIGRldmlhdGlvbjoiLCBzaWdtYV9zcV9oYXQsICJNTEUgbXVfbG4iLCBtdV9sbl9oYXQpICAgDQoNCg0KcmV0dXJuKGMobXVfaGF0ID0gbXVfaGF0LCBzaWdtYV9zcV9oYXQgPSBzaWdtYV9zcV9oYXQsIG11X2xuX2hhdCA9IG11X2xuX2hhdCkpDQp9DQoNCg0KbWxlX3Jlc3VsdHMgPSBub3JtbG9nX21sZSh3ZWxsc2l6ZSkNCg0KDQojbm8gZ3JhZGllbnQgZnVuY3Rpb24gKGNsb3NlZCBmb3JtIG5vIG9wdGltKSAtLT4gcGFydGlhbCBkaWZmZXJlbnRpYXRpb24gYW5kIHNldCB0byAwDQoNCg0KDQoNCiMgU29sdmUgc3lzdGVtIGZvciBNTEUgKG11X0xOX2hhdCkNCg0KDQpgYGANCiMjIFF1ZXN0aW9uIDMuMiANCg0KKDIpLiBUYWtlIDEwMDAgQm9vdHN0cmFwIHNhbXBsZXMgZnJvbSB0aGUgcmF3IG9pbCBkYXRhIHNldC4gRm9yIGVhY2ggYm9vdHN0cmFwIHNhbXBsZSwgY2FsbCB0aGUgYWJvdmUgUg0KZnVuY3Rpb24gdG8gZmluZCB0aGUgYm9vdHN0cmFwIE1MRSBvZiDOvExOLCBkZW5vdGVkIGJ5IGTOvOKIlw0KTE4NCigxKQ0KLCBkzrziiJcNCkxODQooMikNCiwgwrcgwrcgwrcgLCBkzrziiJcNCkxODQooMTAwMCkuDQoNCk5vdGU6IA0KJCRcbXVfe0xOfSA9IFxleHBcbGVmdChcbXUgKyBcZnJhY3sxfXsyfVxzaWdtYV4yXHJpZ2h0KSQkDQoNCmBgYHtyfQ0KDQpzZXQuc2VlZCgxNDMpDQoNCmxlbmd0aCh3ZWxsc2l6ZSkgI24gPTUwDQoNCmJvb3RfbXVfbG5fbWxlID0gTlVMTA0KbG9nX3dlbGw9IHdlbGxzaXplDQoNCg0KZm9yIChpIGluIDE6MTAwMCkNCnsNCg0KI2Jvb3RzdHJhcCBzYW1wbGUNCiMgbWFrZSBzdXJlIHNhbXBsZSBpcyBpbiBpdHMgbG9nIGZvcm0NCiAgDQogIyB0YWtlIHJhdyBub3QgbG9nIG9mIG1lYW4gI2xvZyh3ZWxsc2l6ZSkgLS0+IGxvZyB0aGUgYm9vdHN0cmFwcGVkIHNhbXBsZQ0KICANCmJvb3RzdHJhcF93ZWxsPSBzYW1wbGUoeD1sb2dfd2VsbCwgNTAsIHJlcGxhY2U9IFRSVUUpICNib290c3RyYXBwaW5nIGZyb20gdGhlIHdlbGwgc2FtcGxlDQoNCmxvZ19ib290X3dlbGw9bG9nKGJvb3RzdHJhcF93ZWxsKSAjdGFrZSB0aGUgbG9nIG9mIHRoZSBib290c3RyYXBwZWQgc2FtcGxlIHRvIHJ1biB0aGUgbG9nIGxpa2VsaWhvb2QNCg0KDQojdGFrZSB0aGUgbWVhbiBvZiB0aGUgbG9nIGxpa2VsaWhvb2QgYm9vdHN0cmFwIHRvIGlucHV0IGluIE1MRSBtdSBlcXVhdGlvbg0KbXVfaGF0ID0gbWVhbihsb2dfYm9vdF93ZWxsKSAgI01MRSBlc3RpbWF0b3IgZm9yIG11DQpzaWdtYV9zcV9oYXQgPSBtZWFuKChsb2dfYm9vdF93ZWxsLW11X2hhdCleMikgI01MRSBlc3RpbWF0b3IgZm9yIHNpbWdhXjINCg0KDQojTm93IGNhbGN1bGF0ZSB0aGUgbXUgbG4NCg0KYm9vdF9tdV9sbl9tbGVbaV0gPSBleHAobXVfaGF0ICsoMC41KiBzaWdtYV9zcV9oYXQpKSAjZ2l2ZXMgZGlzdHJ1YnV0aW9uIG9mIHRoZSBib290c3RyYXAgZm9yIHRoZSBtdSBsbiBtbGUNCg0KZmluYWxfbXVfbG5fTUxFID0gbWVhbihib290X211X2xuX21sZSkgI2dpdmVzIHNpbmdsZSB2YWx1ZSBmb3IgYm9vdHN0cmFwcGVkIG1sZSBtdSBsbg0KDQojcmV0dXJuKGMoZmluYWxfbXVfbG5fTUxFKSkgI29ubHkga2VlcGluZyBsYXN0IHRoaW5nIHJhbiAtLT4gVkVSUlkgVkVSWVkgQkFEIEZPUiBib290c3RyYXBwaW5nIC0tPiBub3Qga2VlcGluZyB0aGUgZGlzdHJpYnV0aW9uIGZvciB0aGUgbW9kZWwNCn0NCg0KY2F0KCJCb290c3RyYXAgTUxFIG9mIM68TE46IiwgZmluYWxfbXVfbG5fTUxFKQ0KDQpgYGANClRoZSBib290c3RyYXAgTUxFIG9mICRcbXVfe2xufSQgaXMgYHIgZmluYWxfbXVfbG5fTUxFYC4gDQoNCmBgYHtyIGluY2x1ZGU9RkFMU0V9IA0KI0NhbiByZW1vdmUgYmMgcXVlc3Rpb24gMy4zIGNyZWF0ZXMgZ3JhcGgNCmhpc3QoYm9vdF9tdV9sbl9tbGUsICAgICAgICAgICAgICAgICAgICAgIyBkYXRhIHVzZWQgZm9yIGhpc3RvZ3JhbQ0KICAgICBicmVha3MgPSAxNCwgICAgICAgICAgICAgICAgICAgICAgICAgICAgIyBzcGVjaWZ5IG51bWJlciBvZiB2ZXJ0aWNhbCBiYXJzDQogICAgIHByb2JhYmlsaXR5ID0gVFJVRSwNCiAgICAgICB4bGFiID0gIkJvb3RzdHJhcCBzYW1wbGUgbWVhbnMiLCAgICAgICMgY2hhbmdlIHRoZSBsYWJlbCBvZiB4LWF4aXMNCiAgICAgICMgYWRkIGEgdGl0bGUgdG8gdGhlIGhpc3RvZ3JhbQ0KICAgICAgICBtYWluPSJCb290c3RyYXAgU2FtcGxpbmcgRGlzdHJpYnV0aW9uIFxuIG9mIFNhbXBsZSBNZWFucyIsDQogICAgICAgICAgY2V4Lm1haW4gPSAwLjksDQogICAgICAgY29sLm1haW4gPSAibmF2eSIpICAgDQpsaW5lcyhkZW5zaXR5KGJvb3RfbXVfbG5fbWxlKSwgY29sID0gInNreWJsdWUiLCBsd2QgPSAyKQ0KDQoNCmBgYA0KIyBRdWVzdGlvbiAzLjMgDQoNCigzKS4gVXNpbmcga2VybmVsIGRlbnNpdHkgZXN0aW1hdGlvbiBhcHByb2FjaCB0byBlc3RpbWF0ZSB0aGUgYm9vdHN0cmFwIGRlbnNpdHkgY3VydmVzIGJhc2VkIG9uIHRoZSBib290c3RyYXAgTUxFczogDQpkzrziiJcNCkxODQooMSkNCiwgZM684oiXDQpMTg0KKDIpDQosIMK3IMK3IMK3ICwgZM684oiXDQpMTg0KKDEwMDApLg0KDQoNCmBgYHtyfQ0KDQojc2RfbWxfTUxFPXNkKGJvb3RfbXVfbG5fbWxlKSAjeW91IHdvdWxkIG5lZWQgdG8gY2FsY3VsYXRlIHN0YW5kYXJkIGVycm9yIG9mIHRoZSBkaXN0cmlidXRpb24gdG8gbWFrZSBhIGJhbmR3aWR0aCBmb3IgdGhlIGtlcm5lbCANCg0Ka2RlID0gZGVuc2l0eShib290X211X2xuX21sZSwga2VybmVsID0gImdhdXNzaWFuIikgICNkZW5zaXR5KGJvb3RfbXVfbG5fbWxlLCBidyA9IHNkX21sX01MRSkNCg0KaGlzdChib290X211X2xuX21sZSwgICAgICAgICAgICAgICAgICAgICAjIGRhdGEgdXNlZCBmb3IgaGlzdG9ncmFtDQogICAgIGJyZWFrcyA9IDE0LCAgICAgICAgICAgICAgICAgICAgICAgICAgICAjIHNwZWNpZnkgbnVtYmVyIG9mIHZlcnRpY2FsIGJhcnMNCiAgICAgcHJvYmFiaWxpdHkgPSBUUlVFLA0KICAgICAgIHhsYWIgPSAiQm9vdHN0cmFwIHNhbXBsZSBtZWFucyIsICAgICAgIyBjaGFuZ2UgdGhlIGxhYmVsIG9mIHgtYXhpcw0KICAgICAgIyBhZGQgYSB0aXRsZSB0byB0aGUgaGlzdG9ncmFtDQogICAgICAgIG1haW49IkJvb3RzdHJhcCBTYW1wbGluZyBEaXN0cmlidXRpb24gYW5kIEtlcm5lbCBDb21wYXJpc29uIFxuIG9mIFNhbXBsZSBNZWFucyIsDQogICAgICAgICAgY2V4Lm1haW4gPSAwLjksDQogICAgICAgY29sLm1haW4gPSAibmF2eSIpICANCmxpbmVzKGRlbnNpdHkoYm9vdF9tdV9sbl9tbGUsIGtlcm5lbCA9ICJnYXVzc2lhbiIpLCBjb2w9ICJza3libHVlIiwgbHdkPTIpDQoNCnhfdmFsdWVzIDwtIHNlcShtaW4oYm9vdF9tdV9sbl9tbGUpLCBtYXgoYm9vdF9tdV9sbl9tbGUpLCBsZW5ndGggPSAxMDApDQp5X3ZhbHVlcyA8LSBkbm9ybSh4X3ZhbHVlcywgbWVhbiA9IG1lYW4oYm9vdF9tdV9sbl9tbGUpLCBzZCA9IHNkKGJvb3RfbXVfbG5fbWxlKSkNCmxpbmVzKHhfdmFsdWVzLCB5X3ZhbHVlcywgY29sID0gInJlZCIsIGx0eSA9IDIsIGx3ZCA9IDIpICMgVGhlb3JldGljYWwgTm9ybWFsDQpsZWdlbmQoInRvcHJpZ2h0IiwgbGVnZW5kID0gYygiS0RFIChBY3R1YWwpIiwgIkJvb3RzdHJhcHBlZCBOb3JtYWwgKFRoZW9yeSkiKSwgDQogICAgICAgY29sID0gYygic2t5Ymx1ZSIsICJyZWQiKSwgbHR5ID0gYygxLCAyKSwgbHdkID0gMikNCg0KDQojI0FkZCBhc3ltcHRvdGljIGRlbnNpdHkgY3VydmUNCg0KYGBgDQoNCg0KIyMgUXVlc3Rpb24gMy40DQoNCig0KS4gSW4gb3JkZXIgdG8gZmluZCB0aGUgYXN5bXB0b3RpYyBzYW1wbGluZyBkaXN0cmlidXRpb24gdXNpbmcgdGhlIGNlbnRyYWwgbGltaXQgdGhlb3JlbSAoQ0xUKS4gVGhhdCBpcywNCndoZW4gc2FtcGxlIHNpemUgaXMgbGFyZ2UsDQrCr1gNCuKGkiBODQoSDQrOvExOLA0Kz4NMTiDiiJoNCm4NChMNCndoZXJlIM68TE4gYW5kIM+DTE4gY2FuIGJlIGVzdGltYXRlZCBieSB1c2luZyB0aGUgcGx1Zy1pbiBwcmluY2lwbGUgb2YgTUxFLiBCYXNlZCBvbiB0aGUgYXN5bXB0b3RpYw0Kc2FtcGxpbmcgZGlzdHJpYnV0aW9uIG9mIGxvZ25vcm1hbCBzYW1wbGUgbWVhbiDCr1ggLCBhZGQgdGhlIGFzeW1wdG90aWMgZGVuc2l0eSBjdXJ2ZSB0byB0aGUgYWJvdmUNCkJvb3RzdHJhcCBrZXJuZWwgZGVuc2l0eSBjdXJ2ZS4NCg0KDQoNCmBgYHtyfQ0KDQpuID0gbGVuZ3RoKHdlbGxzaXplKSAjDQoNCiNzaWdtYSAvIChzcXJ0KG4pKQ0KDQojIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyNCYWNrZ3JvdW5kIGluZm8gZm9yIGxvZyBzcGVjaWZpYyBlc3RpbWF0b3JzDQojYSBub3JtYWwgZGlzdHJpYnV0aW9uICBmdW5jdGlvbiBkbm9ybSgpIHJlcXVpcmVzIGEgbWVhbiBhbmQgc3RhbmRhcmQgZGV2aWF0aW9uIA0KbXVfaGF0PSAgbWVhbihsb2cod2VsbHNpemUpKSAjIG1lYW4gb2YgbmF0dXJhbCBsb2cgb2Ygc2FtcGxlDQoNCg0Kc2lnbWFfc3FfaGF0ID0gbWVhbigobG9nKHdlbGxzaXplKS1tdV9oYXQpXjIpICNuZWVkZWQgdG8gY2FsY3VsYXRlIHN0YW5kYXJkIGVycm9yICNubyB1c2UgbG4gdmFsdWUNCg0KI2Rub3JtKHdlbGxzaXplLCBtZWFuID0gbXVfaGF0LCBzZD0gKQ0KIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIw0KDQoNCg0KIyMjIyMjI0xOIHZhbHVlcyBuZWVkZWQgdG8gY2FsY3VsYXRlIGRub3JtKCkgYXN5bXB0b3RpYyBkaXN0cmlidXRpb24gDQoNCm11X2xuX2hhdCA9IGV4cChtdV9oYXQgKyAoMC41KiBzaWdtYV9zcV9oYXQpKQ0Kc2lnbWFfc3FfaGF0X2xuPSBleHAoMiptdV9oYXQgKyBzaWdtYV9zcV9oYXQpICogKGV4cChzaWdtYV9zcV9oYXQpIC0gMSkgI3NpZ21hXjIgbG4gaGF0IHZhbHVlIC0tPiBwcmVkaWN0ZWQgTUxFIHZhbHVlIGZvciB2YXJpYXRpb24gDQoNCg0KYXN5bXB0X2Rpc19zZT1zcXJ0KHNpZ21hX3NxX2hhdF9sbikvc3FydChuKSAjc3RhbmRhcmQgZXJyb3IgZm9yIGFzeW1wdG90aWMgc2FtcGxpbmcgZGlzdHJpYnV0aW9uIA0KDQoNCnhfYXhpcyA9IHNlcShtaW4oYm9vdF9tdV9sbl9tbGUpLCBtYXgoYm9vdF9tdV9sbl9tbGUpLCBsZW5ndGggPSAyMDApICNkZWZpbmluZyByYW5nZSBmb3IgZGlzdHJpYnV0aW9uIG1vc3QgdmFsdWFibGUgd2hlbiBiZWluZyBncmFwaGVkDQoNCiNNYWtlIHRoZW9yZXRpY2FsIGRlbnNpdHkgb2YgYXN5bXB0b3RpYyBkaXN0cmlidXRpb24gDQoNCmFzeW1wdG90aWNfZGlzX3RoZW9yeSA9IGRub3JtKHhfYXhpcywgbWVhbiA9IG11X2xuX2hhdCwgc2QgPSBhc3ltcHRfZGlzX3NlKQ0KDQojYXN5bXB0b3RpY19kaXNfdGhlb3J5ID0gZG5vcm0od2VsbHNpemUsIG1lYW49IG11X2xuX2hhdCwgc2Q9YXN5bXB0X2Rpc19zZSApICNzZCAtLT4gZW50ZXIgc3RhbmRhcmQgZXJyb3IgYXN5bXB0X2Rpc19zZQ0KDQpgYGANCg0KDQoNCmBgYHtyfQ0KDQoNCmtkZSA9IGRlbnNpdHkoYm9vdF9tdV9sbl9tbGUsIGtlcm5lbCA9ICJnYXVzc2lhbiIpICAjZGVuc2l0eShib290X211X2xuX21sZSwgYncgPSBzZF9tbF9NTEUpDQoNCmhpc3QoYm9vdF9tdV9sbl9tbGUsICAgICAgICAgICAgICAgICAgICAgIyBkYXRhIHVzZWQgZm9yIGhpc3RvZ3JhbQ0KICAgICBicmVha3MgPSAxNCwgICAgICAgICAgICAgICAgICAgICAgICAgICAgIyBzcGVjaWZ5IG51bWJlciBvZiB2ZXJ0aWNhbCBiYXJzDQogICAgIHByb2JhYmlsaXR5ID0gVFJVRSwNCiAgICAgICB4bGFiID0gIkJvb3RzdHJhcCBzYW1wbGUgbWVhbnMiLCAgICAgICMgY2hhbmdlIHRoZSBsYWJlbCBvZiB4LWF4aXMNCiAgICAgICMgYWRkIGEgdGl0bGUgdG8gdGhlIGhpc3RvZ3JhbQ0KICAgICAgICBtYWluPSJCb290c3RyYXAgU2FtcGxpbmcgRGlzdHJpYnV0aW9uLCBLZXJuZWwgYW5kIEFzeW1wdG90aWMgRGVuc2l0eSBcbiBvZiBTYW1wbGUgTWVhbnMiLA0KICAgICAgICAgIGNleC5tYWluID0gMC45LA0KICAgICAgIGNvbC5tYWluID0gIm5hdnkiKSAgDQpsaW5lcyhkZW5zaXR5KGJvb3RfbXVfbG5fbWxlLCBrZXJuZWwgPSAiZ2F1c3NpYW4iKSwgY29sPSAic2t5Ymx1ZSIsIGx3ZD0yKQ0KDQpsaW5lcyh4X2F4aXMsIGFzeW1wdG90aWNfZGlzX3RoZW9yeSwgY29sID0gImJsdWUiLCBsd2QgPSAyLCBsdHkgPSA0KQ0KDQp4X3ZhbHVlcyA8LSBzZXEobWluKGJvb3RfbXVfbG5fbWxlKSwgbWF4KGJvb3RfbXVfbG5fbWxlKSwgbGVuZ3RoID0gMTAwKSAjZGVmaW5pbmcgZ3JhcGggcmFuZ2UgYm9vdHN0cmFwDQp5X3ZhbHVlcyA8LSBkbm9ybSh4X3ZhbHVlcywgbWVhbiA9IG1lYW4oYm9vdF9tdV9sbl9tbGUpLCBzZCA9IHNkKGJvb3RfbXVfbG5fbWxlKSkNCmxpbmVzKHhfdmFsdWVzLCB5X3ZhbHVlcywgY29sID0gInJlZCIsIGx0eSA9IDIsIGx3ZCA9IDIpICMgVGhlb3JldGljYWwgTm9ybWFsDQpsZWdlbmQoInRvcHJpZ2h0IiwgbGVnZW5kID0gYygiQm9vdHN0cmFwIE5vcm1hbCBLREUgKEFjdHVhbCkiLCAiQm9vdHN0cmFwIE5vcm1hbCAoVGhlb3J5KSIsICJBc3ltcHRvdGljIENMVCIpLCANCiAgICAgICBjb2wgPSBjKCJza3libHVlIiwgInJlZCIsICJibHVlIiksIGx0eSA9IGMoMSwgMiksIGx3ZCA9IDIpICAjY29sID0gYygic2t5Ymx1ZSIsICJibHVlIiksIGx0eSA9IGMoMSwgMiksIGx3ZCA9IDIpDQoNCg0KDQpgYGANCg0KDQojIyBRdWVzdGlvbiAzLjUgDQoNCig1KS4gV3JpdGUgYSBzaG9ydCBzdW1tYXJ5IHRvIGNvbXBhcmUgdGhlIHR3byBzYW1wbGluZyBkaXN0cmlidXRpb25zIG9mIHRoZSBzYW1wbGUgbWVhbiBvZiB0aGUgbG9nbm9ybWFsIGRpc3RyaWJ1dGlvbi4NCg0KVGhlIGRlc2NyaXB0aW9uIGJlbG93IHJlZmVycyB0byB0aGUgYmVoYXZpb3Igb2YgdGhlIGtlcm5lbCBkZW5zaXR5IGVzdGltYXRvciAoS0RFKSBib290c3RyYXAgZXhjbHVzaXZlbHkgd2hlbiByZWZlcnJpbmcgdG8gdGhlIGJvb3RzdHJhcCBkaXN0cmJ1dGlvbi4NCg0KVGhlIHR3byBtYWpvciBzYW1wbGluZyBkaXN0cmlidXRpb25zIHVzZWQgYWJvdmUgZm9yIHRoZSBzYW1wbGUgbWVhbiBpbmNsdWRlZCBib290c3RyYXAgc2FtcGxpbmcgZGlzdHJpYnV0aW9uIGZvciAkXG11X3tsbn0kIGFuZCBhc3ltcHRvdGljIGRpc3RyaWJ1dGlvbi4gQm90aCBkaXN0cmlidXRpb25zIGFyZSB1c2VkIHRvIGVzdGltYXRlIHRoZSBiZWhhdmlvciBvZiBhIGRpc3RyaWJ1dGlvbiBhbmQgZXN0aW1hdGlvbnMgZm9yIHBvcHVsYXRpb24gcGFyYW1ldGVycy4NCg0KDQpUaGUgYm9vdHN0cmFwcGluZyBkaXN0cmlidXRpb24gaXMgYW4gZW1waXJpY2FsIGVzdGltYXRpb24gb2YgdGhlICRcbXVfe0xOfSQgcGFyYW1ldGVyIGJ5IHRha2luZyByZXBlYXRlZCByYW5kb20gc2FtcGxlcyBmcm9tIHRoZSBvcmlnaW5hbCB3ZWxsIHNhbXBsZSBhbmQgcmVwZWF0ZWRseSBjYWxjdWxhdGluZyBhIG1lYW4gZnJvbSBlYWNoIHNhbXBsZS4gQWxsIG9mIHRoZSBib290c3RyYXBwZWQgc2FtcGxlcyBhcmUgdGhlbiBtZWFuZWQgdG8gcmVhY2ggYW4gJFxtdSQgZXN0aW1hdG9yLiBUaGlzIGlzIGEgc2ltdWxhdGVkIGFwcHJvYWNoIHRvIHRoZSBNTEUgJFxoYXRcbXVfe0xOfSQuIEFzIHRoZSBib290c3RyYXAgcmVzYW1wbGluZyBtZXRob2QgaXMgYW4gaW5kaXJlY3Qgd2F5IHRvIGNhbGN1bGF0ZSBhbmQgZXN0aW1hdG9yLCBhcyBpbiB0aGUgY29sbGVjdGVkIGRpc3RyaWJ1dGlvbiBpcyBub3QgYXNzZXNzZWQgc29sZXkgd2l0aGluIHRoZSBzaW5nbGUgY29sbGVjdGVkIGRpc3RyaWJ1dGlvbiBidXQgdGhlIGVzdGltYXRvciBpcyBjYWxjdWxhdGVkIG92ZXIgdGhlIGVzdGltYXRvciBvdmVyIG9mIGNvbGxlY3Rpb24gb2YgcmVzYW1wbGVzIGZyb20gdGhlIG9yaWdpbmFsbHkgY29sbGVjdGVkIGRpc3RyaWJ1dGlvbi4gUmVwZWF0YWJseSByZXNhbXBsaW5nIGFuZCBjYWxjdWxhdGluZyByYW5kb20gYm9vdHN0cmFwIHZhcmlhYmxlcyB0byB1bHRpbWF0ZWx5IGNhbGN1bGF0ZSB0aGUgcmFuZG9tIHZhcmlhYmxlIGVzdGltYXRvciBvZiBpbnRlcmVzdCwgJFxoYXRcbXVfe0xOfSQuDQoNCldlIHNlZSB0aGUgcmVsYXRpb25zaGlwIGluIHRoZSBGaWd1cmUgYWJvdmUgKGxhc3QgZmlndXJlIGluIHF1ZXN0aW9uIDMuNCkgdGhlIGJvb3RzdHJhcCBnYXVzc2lhbiBrZXJuZWwgZGVuc2l0eSBoYXMgYSBiZXR0ZXIgZml0IHRvIHRoZSBtYXhpbWEgYW5kIG1pbmltdW1zIG9mIHRoZSBkaXN0cmlidXRpb24sIHdoaWxlIHRoZSBhc3ltcHRvdGljIGRpc3RyaWJ1dGlvbiB1bmRlciBwZXJmb3JtcyBpbiBhc3N1bWluZyB0aGUgc2hhcGUgZm9yIHRoZSBtb3N0IG9jY3VycmluZyBkZW5zaXR5IGF0ICRcaGF0XG11X3tMTn0kIGFuZCBoYXMgZmF0dGVyIHRhaWxzIHRoYW4gdGhlIGJvb3RzdHJhcCBLREUsIHN1Z2dlc3RpbmcgYSB3ZWFrZXIgZml0IHRoYW4gdGhlIEtERSBib290c3RyYXAuDQoNClRoZSBtb3JlIHRoZSBib290c3RyYXAgaXMgc2FtcGxlZCwgaXQgY2FuIGJlIGFzc3VtZWQgdGhlIGJvb3RzdHJhcCBlc3RpbWF0b3IgcmVhY2hlcyBjbG9zZXIgdG8gdGhlIHRydWUgZXN0aW1hdG9yLiBJbiBleGFtaW5pbmcgdGhlIGRpZmZlcmVuY2VzIGJldHdlZW4gYSBrZXJuZWwgYW5kIGFzeW1wdG90aWMgZGlzdHJpYnV0aW9uLCB0aGUgYm9vdHN0cmFwIGtlcm5lbCBkZW5zaXR5IGJlc3Qgc3VpdHMgdGhlIGVtcGlyaWNhbCBkYXRhIHJhdGhlciB0aGFuIGFzc3VtaW5nIG5vcm1hbGl0eSB3aXRoIGEgbGFyZ2Ugc2FtcGxlIHNpemUgdG8gbWV0IGFuIGFwcHJveGltYXRpb24gZm9yIHRoZSBhc3ltcHRvdGljIGRpc3RyaWJ1dGlvbi4gQXMgdGhlIGJlc3Qgc3VpdGVkIG5vcm1hbCBkaXN0cmlidXRpb24gaXMgYXNzaWduZWQgdG8gdGhlIGFzeW1wdG90aWMgZGlzdHJpYnV0aW9uIGluIGl0cyBwYXJhbWV0cmljIGFwcHJvYWNoIGluIGFwcHJveGltYXRpb24gcmF0aGVyIHRoYW4gZml0dGluZyBmb3IgdGhlIGRhdGEgZW1waXJpY2FsbHkuIA0KDQpJbiByZWZsZWN0aW9uIGZvciB0aGlzIGxvZ25vcm1hbCBkaXN0cmlidXRpb24gc3BlY2lmaWNhbGx5LCBCb3RoIGRpc3RyaWJ1dGlvbnMgYXJlIHNpbWlsYXIgaW4gc2hhcGUgc2hvd2luZyBhIG5hdHVyYWwgb3JkZXIgcGF0dGVybiBpbiB0aGUgZGF0YSBzZXQsIGluIHdoaWNoIHRoZSBkaXN0cmlidXRpb25zIG1lZXRzIHRoZWlyIHJlc3BlY3RpdmUgY29uZGl0aW9ucy4gQWRkaXRpb25hbGx5LCBib3RoIGRpc3RyaWJ1dGlvbnMgc2hvdyBhIHNpbWlsYXIgdmFsdWUgdG93YXJkcyB0aGUgJFxoYXRcbXVfe0xOfSQsIHRoZSBib290c3RyYXAgYmVpbmcgYHIgZmluYWxfbXVfbG5fTUxFYCBhbmQgdGhlIGFzeW1wdG90aWMgZGlzdHJpYnV0aW9uIGJlaW5nIGByIG11X2xuX2hhdGAuDQoNClRoZSBib290c3RyYXBwZWQgdmFsdWUgZm9yICRcaGF0XG11X3tMTn0kIGlzIGByIGZpbmFsX211X2xuX01MRWAgd2hpY2ggaXMgdmVyeSBjbG9zZSB0byB0aGUgYXN5bXB0b3RpYyBtZWFuIGF0YHIgbXVfbG5faGF0YC4gT3VyIHR3byBkaXN0cmlidXRpb25zIGNhcHR1cmUgdGhlIHByZWRpY3RlZCAkXGhhdFxtdV97TE59JCBzaW1pbGFybHkgc3VnZ2VzdGluZyBzb21lIHJpZ29yIGluIGJvdGggdGVzdHMuIElmIGEgZGVjaXNpb24gbmVlZHMgdG8gYmUgbWFkZSBhYm91dCB3aGljaCBkaXN0cmlidXRpb24gYmVzdCBzdWl0cyB0aGUgbW9kZWwsIHRoZSBib290c3RyYXAgS0RFIHJlc2FtcGluZyBvZmZlcnMgYSBzdHJvbmdlciBmaXQgdG8gdGhlIGhpc3RvZ3JhbSdzIHJhdyBvciBuYXR1cmFsIGRpc3RyaWJ1dGlvbiBzdWdnZXN0aW5nIHRoZSBNTEUgcGFyYW1ldGVycyBkZXJpdmVkIGZyb20gdGhpcyBkaXN0cmlidXRpb24gbWF5IGhhdmUgbW9yZSByaWdvciB0aGFuIHRoZWlyIGFzeW1wdG90aWMgZGlzdHJpYnV0aW9uIGNvdW50ZXJwYXJ0cywgYWx0aG91Z2ggYWdhaW4sIGJvdGggZGlzdHJpYnV0aW9ucyBmb2xsb3cgdmVyeSBzaW1pbGFyIHBhdHRlcm5zIGFuZCBpbmZvcm1hdGlvbi4gQW55IHNlbGVjdGlvbiBtYWRlIGJldHdlZW4gdGhlIHR3byBkaXN0cmlidXRpb25zLCBzaG91bGQgbm90IHZhcnkgYmV0d2VlbiBlYWNoIG90aGVyIHZlcnkgbXVjaCBieSBleWUgYW5kIGdyYXBoIGFuYWx5c2lzLg0KDQojIDQgQm9udXMgUXVlc3Rpb24NCg0KRGVyaXZlIHRoZSBIZXNzaWFuIG1hdHJpeCBieSBjb21wdXRpbmcgdGhlIHNlY29uZC1vcmRlciBwYXJ0aWFsIGRlcml2YXRpdmVzIG9mIHRoZSBsb2ctbGlrZWxpaG9vZCBmdW5jdGlvbg0KKHdpdGggcmVzcGVjdCB0byDOvCBhbmQgz4MyKS4gVGhlbiwgdHJhbnNsYXRlIHRoZSBkZXJpdmVkIEhlc3NpYW4gaW50byBhbiBSIGZ1bmN0aW9uIHRoYXQgdGFrZXMgdGhlIE1MRXMgb2YgdGhlIHBhcmFtZXRlcnMgYW5kIHRoZSBkYXRhIGFzIGlucHV0cyBhbmQgcmV0dXJucyB0aGUgSGVzc2lhbiBtYXRyaXguIEZpbmFsbHksIGNvbXBhcmUgeW91ciBhbmFseXRpY2FsbHkgZGVyaXZlZCBIZXNzaWFuIHdpdGggdGhlIG51bWVyaWNhbCBIZXNzaWFuIHJldHVybmVkIGJ5IG9wdGltKCkuDQoNCg0KYGBge3J9DQoNCmRhdGE9IHdlbGxzaXplICNsb2cod2VsbHNpemUpDQpsb2dfbGlrZV93ZWxsc19oZXNzIDwtIGZ1bmN0aW9uKHBhcmFtcywgZGF0YSkgDQogIHsNCiAgbXUgPSBwYXJhbXNbMV0gICAgICAgIyBzaGFwZSBwYXJhbWV0ZXINCiAgc2lnbWFfc3EgPSBwYXJhbXNbMl0gICMgc2NhbGUgcGFyYW1ldGVyDQogIA0KICANCiAgDQpuIDwtIGxlbmd0aChkYXRhKQ0KICBsb2dfbGlrID0gKC1uLzIgKiBsb2coMipwaSkgLSBuLzIgKiBsb2coc2lnbWFfc3EpIC0gc3VtKGxvZyhkYXRhKSkgLSAoMS8oMipzaWdtYV9zcSkpICogc3VtKChsb2coZGF0YSkgLSBtdSleMikpICN3ZSBmbGlwIHNpZ25zIGluIHRoZSBtYXRyaXggcHJvY2Vzcw0KICANCnJldHVybihsb2dfbGlrKQ0KfQ0KDQoNCg0KDQoNCmxvZ19saWtlbGlob29kX2dyYWRpZW50ID0gZnVuY3Rpb24ocGFyYW1zLCBkYXRhKSANCiAgew0KICBtdSA9IHBhcmFtc1sxXQ0KICBzaWdtYV9zcSA9IHBhcmFtc1syXQ0KICBuID0gbGVuZ3RoKGRhdGEpDQojR3JhZGllbnQgZnVuY3Rpb25zDQoNCiAgDQojIFRha2luZyB0aGUgcGFydGlhbCBkZXJpdmF0aXZlIHdpdGggcmVzcGVjdCB0byBtdQ0KIGRfbXUgPC0gKDEvc2lnbWFfc3EpICogc3VtKGxvZyhkYXRhKSAtIG11KQ0KICANCiAgIyBQYXJ0aWFsIGRlcml2YXRpdmUgd2l0aCByZXNwZWN0IHRvIHNpZ21hX3NxDQogIGRfc2lnbWFfc3EgPC0gLW4vKDIgKiBzaWdtYV9zcSkgKyAoMS8oMiAqIHNpZ21hX3NxXjIpKSAqIHN1bSgobG9nKGRhdGEpIC0gbXUpXjIpDQogIA0KcmV0dXJuKGMoZF9tdSwgZF9zaWdtYV9zcSkpDQp9DQoNCg0KDQphbmFseXRpY2FsX2hlc3NpYW5fZnVuYyA9IGZ1bmN0aW9uKHBhcmFtcywgZGF0YSkgDQogIHsNCiAgbXUgPSBwYXJhbXNbMV0NCiAgc2lnbWFfc3EgPSBwYXJhbXNbMl0NCiAgbiA9IGxlbmd0aChkYXRhKQ0KICANCiNDb21wdXRpbmcgdGhlIHNlY29uZCBkZXJpdmF0aXZlcyBmb3IgbXUgYW5kIHNpZ21hXjINCmQyX211IDwtIC1uIC8gc2lnbWFfc3ENCiAgZDJfc2lnbWFfc3EgPC0gbi8oMiAqIHNpZ21hX3NxXjIpIC0gKDEvc2lnbWFfc3FeMykgKiBzdW0oKGxvZyhkYXRhKSAtIG11KV4yKQ0KICANCiAgZF9tdV9kX3NpZ21hX3NxIDwtIC0oMS9zaWdtYV9zcV4yKSAqIHN1bShsb2coZGF0YSkgLSBtdSkNCiAgDQojIFRoaXMgYW5hbHl0aWNhbGx5IGRlcml2ZWQgbWF0cml4ICAgDQpoZXNzX21hdCA8LSBtYXRyaXgoYyhkMl9tdSwgZF9tdV9kX3NpZ21hX3NxLCBkX211X2Rfc2lnbWFfc3EsIGQyX3NpZ21hX3NxKSxucm93ID0gMiwgYnlyb3cgPSBUUlVFKSAgDQoNCiNyZXR1cm4oYyhkX211LCBkX3NpZ21hX3NxLCBkMl9tdSwgZDJfc2lnbWFfc3EsIGRfbXVfZF9zaWdtYV9zcSkpICAjIFJldHVybiBsb2ctbGlrZWxpaG9vZCAgTk9UIHRoZSBuZWdhdGl2ZSBsb2ctbGlrZWxpaG9vZCBhbmQgZ3JhZGllbnRzDQoNCg0KICByZXR1cm4oaGVzc19tYXQpDQp9DQoNCg0KDQojIEZpbmRpbmcgSW5pdGlhbCBWYWx1ZXMNCiMjIEl0IGlzIGNyaXRpY2FsIHRvIHNlbGVjdCBhcHByb3ByaWF0ZSBpbml0aWFsIHZhbHVlcyB0bw0KIyMgZW5zdXJlIGZhc3QgY29udmVyZ2VuY2UuIEluIGdlbmVyYWwsIHdlIGNhbiB1c2Ugd2hhdGV2ZXINCiMjIG1ldGhvZHMgKHN1Y2ggYXMgTU1FKSB0aGF0IGFyZSBhdmFpbGFibGUgdG8gZ2V0IGFwcHJvcHJpYXRlDQojIyBpbml0aWFsIHZhbHVlcw0KDQoNCiMgVXNpbmcgdGhlIE1MRSBhcyB0aGUgaW5pdGlhbCBwYXJhbWV0ZXIgZXN0aW1hdGVzDQoNCmluaXRpYWxfbXUgPSBtdV9oYXQNCg0KaW5pdGlhbF9zaWdtYV9zcSA9IHNpZ21hX3NxX2hhdA0KDQoNCg0KI21sZV9vcHRpbWl6YXRpb24gPC0gb3B0aW0ocGFyID0gYyhpbml0aWFsX211LGluaXRpYWxfc2lnbWFfc3EpLCBmbiA9IGxvZ19saWtlX3dlbGxzX2hlc3MsIHggPSB3ZWxsc2l6ZSwgaGVzc2lhbiA9IFRSVUUpDQoNCg0KIyBNTEUgdXNpbmcgb3B0aW0oKSB3aXRoIGdyYWRpZW50DQoNCg0KDQptbGVfcmVzdWx0IDwtIG9wdGltKA0KICBwYXIgPSBjKG11X2hhdCwgc2lnbWFfc3FfaGF0KSwgI3N0YXJ0aW5nIHBvaW50IG9mIHRoZSBwcmVkaWN0ZWQgbXUgYW5kIHNpZ21hIGZvciB0aGUgTUxFDQogIGZuID0gbG9nX2xpa2Vfd2VsbHNfaGVzcywgIA0KICBnciA9IGxvZ19saWtlbGlob29kX2dyYWRpZW50LA0KICBkYXRhID0gd2VsbHNpemUsDQogIG1ldGhvZCA9ICJMLUJGR1MtQiIsDQogIGxvd2VyID0gYygtSW5mLCAxZS02KSwNCiAgaGVzc2lhbiA9IFRSVUUsDQogIGNvbnRyb2wgPSBsaXN0KGZuc2NhbGUgPSAtMSkNCikNCg0KDQojIw0KbWxlX3Jlc3VsdA0KDQojQ29tcGFyaW5nIHRoZSBoZXNzaWFuIG1hdHJpY2VzIGRlcml2ZWQgYW5hbHl0aWNhbGx5IGFuZCBvcHRpbSgpDQoNCm51bWVyaWNhbF9oZXNzaWFuICA8LSBtbGVfcmVzdWx0JGhlc3NpYW4NCmFuYWx5dGljYWxfaGVzc2lhbiA8LSBhbmFseXRpY2FsX2hlc3NpYW5fZnVuYyhtbGVfcmVzdWx0JHBhciwgd2VsbHNpemUpDQoNCiMgUHJpbnQgZm9yIHlvdXIgbWlkdGVybSByZXBvcnQNCmNhdCgiLS0tIE51bWVyaWNhbCBIZXNzaWFuIGZyb20gb3B0aW0oKSAtLS1cbiIpDQpwcmludChudW1lcmljYWxfaGVzc2lhbikNCg0KY2F0KCJcbi0tLSBBbmFseXRpY2FsbHkgRGVyaXZlZCBIZXNzaWFuIC0tLVxuIikNCnByaW50KGFuYWx5dGljYWxfaGVzc2lhbikNCg0KYGBgDQpCb3RoIHNob3cgbmVnYXRpdmUgY29ycmVsYXRpb24gYW1vbmcgJFxtdSQgYW5kICRcc2lnbWFeMiQgYW5kIHByZXNlbnQgc2ltaWxhciB2YWx1ZXMuIEJvdGggc2hvdyBzaW1pbGFyaXR5IGluIHRoZWlyIHNhbXBsaW5nIGRpc3RyaWJ1dGlvbi4gDQog