Introduction
Bayesian reasoning is a cornerstone of probabilistic inference,
allowing us to update beliefs as new data arrives. In simple terms,
Bayes’ rule can incorporate prior (auxiliary) information into models to
improve their performance. Its applications range from traditional
statistical modeling in fields such as medical diagnosis, spam
filtering, and finance, to modern data science and machine learning.
This module first reviews Bayes’ rule for dependent events, then
extends it to dependent discrete and continuous random variables.
Finally, we relax the assumption of conditional dependence to introduce
the well‑known naive Bayes predictive models, one of the most
practically important predictive models in machine learning and data
science.
Bayes’ Rule for
Dependent Events
Mathematical Formulation
Let\(A\)and\(B\)be two dependent events with \(P(B) > 0\). Bayes’ rule follows from the
definition of conditional probability:
\[
P(A|B) = \frac{P(B|A)P(A)}{P(B)}
\]
\(P(A)\): Prior probability of
\(A\) (initial belief, prior
information, auxiliary information). \(P(B|A)\): Likelihood of observing \(B\) given \(A\). The observed information from data.
\(P(B)\): Marginal probability of
\(B\), often computed using the law of
total probability}. \(P(A|B)\):
Posterior probability of \(A\) given
evidence \(B\). The model with
incorporated auxiliary information
If \(A\) has multiple mutually
exclusive states \(A_1, A_2, \dots,
A_n\):
\[
P(A_i|B) = \frac{P(B|A_i)P(A_i)}{\sum_{j=1}^n P(B|A_j)P(A_j)}
\]
Example: Medical Diagnosis
Problem: Some assumptions about the population and
the performance of the test:
A disease affects \(1\%\) of a
population. This is general information can be found at population
level.
Test sensitivity \(P(\text{Positive}|\text{Disease}) = 0.95\).
This information is based on the clinical trials in which the
participants’ disease status is known.
Test specificity \(P(\text{Negative}|\text{No Disease}) =
0.90\). This information is also based on the clinical
trials.
Given a positive test, what is the probability the patient has the
disease? This information is needed for physician to make clinical
decision.
Solution:
- Some Notations:
- \(D+\): event has
disease
- \(D-\): event has no
disease
- \(T+\): event test
positive
- \(T-\): event test
negative
- Given Info:
- \(P(D+) = 0.01\)
- \(P(T+ | D+) = 0.95\)
- \(P(T- | D-) = 0.90\)
- We want to find \(P(D+|T+)\).
First, compute \(P(T+|D+) =
0.95\).
\[P(T+|D-) = 1 -
P(\text{Negative}|\text{No Disease}) = 0.10\].
Using the following law of total probability:
\[
P(T+) = P(T+\cap D+) + P(T+ \cap D-) = P(T+|D+)P(D+) + P(T+|D-)P(D-)
\]
\[
P(T+) = 0.95 \times 0.01 + 0.10 \times 0.99 = 0.0095 + 0.099 = 0.1085
\]
Bayes’ rule:
\[
P(D+|T+) = \frac{P(T+|D+)P(D+)}{P(T+)} = \frac{0.95 \times 0.01}{0.1085}
\approx 0.0876 = 8.76\%
\]
Despite the positive test, the posterior probability is low because
the prior is very low.
Example 2: Bayes rule on multiple event: Suppose a
factory has three machines \(B_1, B_2,
B_3\) making widgets. Denote \(D =
\text{Defective}\). Given the following information
- Machine \(B_1\) makes 50% of
widgets: \(P(B_1)=0.5\).
- Machine \(B_2\) makes 30%: \(P(B_2)=0.3\).
- Machine \(B_3\) makes 20%: \(P(B_3)=0.2\).
Defect rates of each machine are given by:
- \(P(\text{D} \mid B_1) = 0.01\): 1%
of the products produced by machine \(B_1\) were defective.
- \(P(\text{D} \mid B_2) = 0.02\): 2%
of the products produced by machine \(B_2\) were defective.
- \(P(\text{D} \mid B_3) = 0.05\): 5%
of the products produced by machine \(B_3\) were defective.
include_graphics("BayesRule.png")

Question: Given a defective widget, what is the
probability it came from machine \(B_3\), \(P(B_3
\mid \text{D})\)?
Solution: First of all, the desired conditional
probability can be re-expressed as
\[
P(B_3 \mid \text{D}) = \frac{P(B_3 \cap D)}{P(D)} = \frac{P(D \mid B_3)
P(B_3)}{P(D)}
\] The probabilities on the numerator are given. We need to find
the probability \(P(D)\) using the
law of total probability in the following. From the
above Venn diagram, we see that
\[
\begin{aligned}
P(D) & =P(B_1 \cap D) + P(B_2 \cap D) + P(B_3 \cap D) \\
&= P(D \mid B_1)P(B_1) + P(D \mid B_2)P(B_2) + P(D \mid
B_3)P(B_3) \\
&= (0.01)(0.5) + (0.02)(0.3) + (0.05)(0.2) \\
&= 0.005 + 0.006 + 0.01 \\
&= 0.021.
\end{aligned}
\]
Therefore,
\[
P(B_3 \mid \text{D}) = \frac{P(D \mid B_3) P(B_3)}{P(D)} =
\frac{0.05\times 0.2}{0.021} = \frac{0.01}{0.021} = 0.476.
\]
Bayes’ Rule for
Discrete Random Variables
For discrete random variables \(X\)
and \(Y\), with pmf \(p_X(x)\) and conditional pmf \(p_{Y|X}(y|x)\):
\[
p_{X|Y}(x|y) = \frac{p_{Y|X}(y|x) p_X(x)}{p_Y(y)}, \quad p_Y(y) =
\sum_{x'} p_{Y|X}(y|x') p_X(x')
\]
This is directly analogous to the event-based version.
Example: Manufacturing Quality Control
Let \(X\) be the true
quality grade of an item (discrete random variable):
\[
X \in \{ \text{Excellent}, \text{Good}, \text{Fair}, \text{Poor} \}
\]
Let \(Y\) be the inspection
result (discrete random variable):
\[
Y \in \{ \text{Pass}, \text{Fail} \}
\]
- Given prior distribution of quality (based on
historical data)
\[
\begin{aligned}
P(X = \text{Excellent}) &= 0.20 \\
P(X = \text{Good}) &= 0.50 \\
P(X = \text{Fair}) &= 0.25 \\
P(X = \text{Poor}) &= 0.05
\end{aligned}
\]
- Inspection accuracy (likelihood) based on data:
Probability of passing inspection given true quality.
\[
\begin{aligned}
P(Y = \text{Pass} \mid X = \text{Excellent}) &= 0.99 \\
P(Y = \text{Pass} \mid X = \text{Good}) &= 0.90 \\
P(Y = \text{Pass} \mid X = \text{Fair}) &= 0.70 \\
P(Y = \text{Pass} \mid X = \text{Poor}) &= 0.10
\end{aligned}
\]
and
\[
\begin{aligned}
P(Y = \text{Fail} \mid X = \text{Excellent}) &= 0.01 \\
P(Y = \text{Fail} \mid X = \text{Good}) &= 0.10 \\
P(Y = \text{Fail} \mid X = \text{Fair}) &= 0.30 \\
P(Y = \text{Fail} \mid X = \text{Poor}) &= 0.90
\end{aligned}
\]
Question: Given an item
fails inspection (\(Y =
\text{Fail}\)). What is the probability distribution over its
true quality grade \(X\)? In other
words, we want to find the distribution of conditional distribution
\(X\mid \text{Fails}\):
\[
P(X = x \mid Y = \text{Fail}) \quad \text{for } x \in \{\text{Ex},
\text{Good}, \text{Fair}, \text{Poor}\}
\]
Solution: Using the Bayes rule,
\[
P(X = x \mid Y = \text{Fail}) = \frac{P[(X=x)\cap
\text{Fails}]}{P(\text{Fails})} = \frac{P[\text{Fails}\mid (X=x)]\times
P(X=x)}{P(\text{Fails})}
\]
For any \(x \in \{\text{Ex}, \text{Good},
\text{Fair}, \text{Poor}\}\), the numerator is calculated from
the given condition. We need to use the law of total
probability to find \(P(\text{Fails})\) in the following.
\[
P(Y = \text{Fail}) = \sum_{\text{all } x} P(Y = \text{Fail} \mid X = x)
P(X = x)
\]
which is explicitly given by
\[
\begin{aligned}
P(Y = \text{Fail}) &= (0.01 \times 0.20) + (0.10 \times 0.50) +
(0.30 \times 0.25) + (0.90 \times 0.05) \\
&= 0.002 + 0.05 + 0.075 + 0.045 \\
&= 0.172
\end{aligned}
\]
Next, we calculate \(P(X = x \mid Y =
\text{Fail}) \quad \text{for } x \in \{\text{Ex}, \text{Good},
\text{Fair}, \text{Poor}\}\) bellow:
Excellent}
\[
P(X = \text{Ex} \mid Y = \text{Fail}) = \frac{0.01 \times 0.20}{0.172} =
\frac{0.002}{0.172} \approx 0.0116
\]
Good
\[
P(X = \text{Good} \mid Y = \text{Fail}) = \frac{0.10 \times 0.50}{0.172}
= \frac{0.05}{0.172} \approx 0.2907
\]
Fair
\[
P(X = \text{Fair} \mid Y = \text{Fail}) = \frac{0.30 \times 0.25}{0.172}
= \frac{0.075}{0.172} \approx 0.4360
\]
Poor
\[
P(X = \text{Poor} \mid Y = \text{Fail}) = \frac{0.90 \times 0.05}{0.172}
= \frac{0.045}{0.172} \approx 0.2616
\]
Because we have to worked with so many probabilities, next, we
summarize the probabilities obtained above in a table.
| Excellent |
0.20 |
0.01 |
0.0116 (1.16%) |
| Good |
0.50 |
0.10 |
0.2907 (29.07%) |
| Fair |
0.25 |
0.30 |
0.4360 (43.60%) |
| Poor |
0.05 |
0.90 |
0.2616 (26.16%) |
The last column contains the (posterior) distribution that we want to
find.
We can use the posterior
distribution from the table above to answer a membership
classification or prediction: For a randomly
selected product that failed the inspection, based on the calculated
posterior distribution (the last column of the table
above), the product is classified into the quality class of
Fair. This means Bayes’ rule can be used as a
classifier, or predictive model.
Bayes’ Rule for
Continuous Random Variables
For continuous random variables \(X\) and \(Y\), we use probability density functions
(pdfs):
\[
f_{X|Y}(x|y) = \frac{f_{Y|X}(y|x) f_X(x)}{f_Y(y)} \propto f_{Y|X}(y|x)
f_X(x), \quad f_Y(y) = \int f_{Y|X}(y|x) f_X(x) dx
\]
\(\propto\) is read
proportional to. We can write \(f_{X|Y}(x|y) \propto f_{Y|X}(y|x) f_X(x)\)
because \(f_Y(y)\) is a normalizing
coefficient (that makes \(f_{X|Y}(x|y)\) a valid density).
To understand the above idea, let’s consider normal random variable
\(Y\) with density function:
\(Y\mid \theta \sim \mathcal{N}(\theta,
\sigma_0^2)\) with known \(\sigma_0^2\) and unknown mean \(\theta\). Assume that \(\theta\) is random and also follows normal
distribution \(\theta \sim \mathcal{N}(\mu_0,
\tau_0^2)\), where both \(\mu_0\) and \(\tau_0\) are known constants.
Don’t be surprise! In Bayesian statistics,
all unknown parameters are random. The distribution of
the unknown parameter is called prior distribution
.
Given observation \(Y = y\), then
the posterior distribution of \(\theta\) given \(Y = y\) is (See the derivation in the
appendix):
\[
\theta|Y=y \sim \mathcal{N}\left( \frac{\sigma_0^{-2}y +
\tau_0^{-2}\mu_0}{\sigma_0^{-2} + \tau_0^{-2}}, \ (\sigma_0^{-2} +
\tau_0^{-2})^{-1} \right)
\]
Note that the precision of a
distribution is defined as the inverse of the
variance. Let \(\eta_0 =
\sigma_0^{-2}\) and \(\lambda_0 =
\tau_0^{-2}\). The above expression can be written as
\[
\theta|Y=y \sim \mathcal{N}\left( \frac{\eta_0y + \lambda_0
\mu_0}{\eta_0 + \lambda_0}, \ (\eta_0 + \lambda_0)^{-1} \right),
\]
which can further rewritten as
\[
\theta|Y=y \sim \mathcal{N}\left( \frac{\eta_0 }{\eta_0 + \lambda_0} y +
\frac{\lambda_0 }{\eta_0 + \lambda_0}\mu_0, \ \frac{1}{\eta_0 +
\lambda_0} \right),
\]
Interpretation: If \(Y|\theta\) and \(\theta\) are both normal random variables,
then \(\theta\mid Y\) is also a normal
random variable. The Bayesian Estimator of the population mean is \(E[\theta \mid Y]\):
\[
{\mu}_{\text{Bayes}} = E[\theta \mid Y] = \frac{\eta_0 }{\eta_0 +
\lambda_0} y + \frac{\lambda_0 }{\eta_0 + \lambda_0}\mu_0
\]
\[
= \frac{\eta_0 }{\eta_0 + \lambda_0} E[y] + \frac{\lambda_0 }{\eta_0 +
\lambda_0}\mu_0.
\]
Therefore,
\[
\hat{\mu}_{\text{Bayes}} =\frac{\eta_0 }{\eta_0 + \lambda_0} \bar{y} +
\frac{\lambda_0 }{\eta_0 + \lambda_0}\mu_0.
\]
That is, the Bayesian estimator of
population mean (i.e., the posterior mean) is equal to the weighted
average of the sample mean (\(\bar{x}\)) and the prior mean (\(\mu_0\)). This is the basis
for Bayesian parameter estimation, where \(\theta\) is an unknown parameter and \(Y\) is observed data. The above formulas
look complex. Next, we use an numerical example to explain the how to
use the above theorem to solve practical questions.
Example: Estimating the mean speed of cars from sensor
readings: We want to estimate the true mean
speed \(S\) of cars passing a
point, using radar measurements \(R\). We have prior knowledge about \(S\), and we get sample measurements \(\bar{r}\) (average of \(n\) radar readings). Let:
\(S\) = true mean speed (unknown
parameter, treated as a random variable in Bayesian inference).
\(R_i\) = \(i\)-th radar speed measurement.
Assume radar measurement errors are normally distributed around the
true speed:
\[
R_i \mid S \sim \mathcal{N}(S, \sigma^2)
\]
where \(\sigma\) is known
measurement standard deviation (here \(\sigma
= 2\) mph). We get \(n\)
independent measurements: \(r_1, r_2, \dots,
r_n\), and compute their sample mean \(\bar{r}\).
Prior Distribution for \(S\)
We need a prior for the true mean speed \(S\) before seeing data. From historical
traffic data, we believe typical mean speeds are around \(\mu_0 = 60\) mph, with some uncertainty
expressed by standard deviation \(\tau =
5\) mph. Thus, we choose a normal prior:
\[
S \sim \mathcal{N}(\mu_0, \tau^2)
\]
\[
S \sim \mathcal{N}(60, 25)
\]
Likelihood of the Data
Given \(S\), the sample mean \(\bar{R}\) of \(n\) measurements has distribution:
\[
\bar{R} \mid S \sim \mathcal{N}\left(S, \frac{\sigma^2}{n}\right)
\]
because:
\[
\bar{R} = \frac{1}{n} \sum_{i=1}^n R_i, \quad \text{Var}(\bar{R} \mid S)
= \frac{\sigma^2}{n}.
\]
Let observed \(\bar{r} = 62\) mph
from \(n = 10\) measurements, and known
\(\sigma = 2\) mph.
Then:
\[
\frac{\sigma^2}{n} = \frac{4}{10} = 0.4
\]
so
\[
\bar{R} \mid S \sim \mathcal{N}(S, 0.4).
\]
Posterior Distribution for \(S\) using Bayes’ Rule
For a normal prior and normal likelihood, the posterior is also
normal. Let:
Prior mean \(\mu_0 = 60\), prior
variance \(\tau^2 = 25\).
Sample mean \(\bar{r} = 62\),
conditional variance \(v = \sigma^2/n =
0.4\).
The posterior mean \(\mu_n\) is:
\[
\mu_n = \frac{ \frac{\mu_0}{\tau^2} + \frac{\bar{r}}{v} }{
\frac{1}{\tau^2} + \frac{1}{v} }
\]
\[
\mu_n = \frac{ \frac{60}{25} + \frac{62}{0.4} }{ \frac{1}{25} +
\frac{1}{0.4} }
\]
\[
\frac{60}{25} = 2.4, \quad \frac{62}{0.4} = 155
\]
Numerator: \(2.4 + 155 = 157.4\).
Denominator: \(\frac{1}{25} + \frac{1}{0.4} =
0.04 + 2.5 = 2.54\).
So:
\[
\mu_n = \frac{157.4}{2.54} \approx 61.97 \ \text{mph}.
\]
Posterior variance \(\tau_n^2\):
\[
\frac{1}{\tau_n^2} = \frac{1}{\tau^2} + \frac{1}{v} = 2.54
\]
\[
\tau_n^2 = \frac{1}{2.54} \approx 0.3937
\]
\[
\tau_n \approx 0.627 \ \text{mph}.
\]
Thus, the posterior distribution is:
\[
S \mid \bar{r} \sim \mathcal{N}(61.97, 0.3937).
\]
Interpretation
We started with prior \(\mathcal{N}(60,
25)\), which was quite uncertain \(\tau
= 5\) mph).
After \(n = 10\) measurements with
sample mean \(62\) mph (slightly above
prior mean), the posterior is much tighter \(\tau_n \approx 0.627\) mph) and centered
near \(61.97\) mph.
The data moved our estimate from \(60\) toward \(62\), but not all the way because the prior
had some weight.
If \(n\) were larger, the posterior
would be even tighter and influenced more by the data.
Final Result in Bayesian Estimation Form
Bayes’ rule:
\[
p(S \mid \bar{r}) \propto p(\bar{r} \mid S) \cdot p(S)
\]
\[
p(\bar{r} \mid S) = \frac{1}{\sqrt{2\pi v}} \exp\left[-\frac{\bar{r} -
S)^2}{2v}\right], \quad v = \frac{\sigma^2}{n}
\]
\[
p(S) = \frac{1}{\sqrt{2\pi \tau^2}} \exp\left[-\frac{(S -
\mu_0)^2}{2\tau^2}\right]
\]
Multiplying and completing the square gives the posterior normal
derived above. Thus:
\[
\text{Posterior mean speed estimate} = 61.97 \ \text{mph}
\]
\[
95\% \ \text{credible interval} \approx 61.97 \pm 1.96 \times 0.627
\approx (60.74, 63.20) \ \text{mph}.
\]
\[
\boxed{61.97 \ \text{mph}}
\]
(with posterior std \(\approx
0.627\) mph)
This is a closed-form update: the posterior mean is a weighted
average of prior mean and data.
Naive Bayes
Prediction
Idea: A supervised classification method based on
Bayes’ rule, with a ``naive’’ assumption: features are conditionally
independent given the class label}.
For a feature vector\(\mathbf{X} = (X_1,
X_2, \dots, X_d)\)and class\(C \in \{1,
\dots, K\}\):
From Bayes’ rule:
\[
P(C=k|\mathbf{X}) \propto P(C=k) \prod_{j=1}^d P(X_j|C=k)
\]
The class with the highest posterior probability is chosen.
Why ``Naive’’?
The conditional independence assumption is often false in practice,
but Naive Bayes still performs well in many applications (text
classification, spam detection) because we only need the
ranking of probabilities to be correct for
classification.
Example: Text Classification (Spam vs. Ham)
Problem: Classify email as spam (\(S\)) or ham (\(H\)) based on word counts.
Training data:
Vocabulary: \(\{\text{buy}, \text{cheap},
\text{meeting}, \text{free}\}\)
Suppose in spam emails:
\(P(\text{buy}|S) = 0.3\),\(P(\text{cheap}|S) = 0.2\),\(P(\text{meeting}|S) = 0.01\),\(P(\text{free}|S) = 0.4\)
In ham emails:\
\(P(\text{buy}|H) = 0.01\),\(P(\text{cheap}|H) = 0.01\),\(P(\text{meeting}|H) = 0.2\),\(P(\text{free}|H) = 0.05\)
Prior:\(P(S) = 0.4\),\(P(H) = 0.6\).
New email: “buy cheap meeting” (ignore other words).
We compute:
\[
P(S|\text{buy, cheap, meeting}) \propto 0.4 \times (0.3 \times 0.2
\times 0.01) = 0.4 \times 0.0006 = 0.00024
\]
\[
P(H|\text{buy, cheap, meeting}) \propto 0.6 \times (0.01 \times 0.01
\times 0.2) = 0.6 \times 0.00002 = 0.000012
\]
Since\(0.00024 > 0.000012\),
classify as SPAM}.
Practical Considerations:
For continuous features, use Gaussian Naive Bayes (assume \(P(X_j|C=k)\) is Gaussian).
Laplace smoothing for discrete features to avoid zero
probabilities.
Works well with high-dimensional data (e.g., text).
Summary
Bayes’ Rule: Foundation for updating beliefs
with evidence.
Variants: Events \(\rightarrow\) discrete random variables
\(\rightarrow\) continuous random
variables (parameter estimation).
Naive Bayes: Simple, fast classification using
conditional independence assumption; widely used in text analysis and
beyond.
The power of Bayesian methods lies in combining prior knowledge with
observed data, making them essential for predictive analysis in
uncertain environments.
Appendix
Bayesian Derivation:
Posterior Distribution for Normal Mean
1. Problem setup
We have:
\[
Y \mid \theta \; \sim \; \mathcal{N}(\theta, \sigma_0^2), \quad
\sigma_0^2 \text{ known}.
\]
\[
\theta \; \sim \; \mathcal{N}(\mu_0, \tau_0^2), \quad \mu_0, \tau_0^2
\text{ known}.
\]
Given data \(Y = y\), we want the
posterior distribution:
\[
p(\theta \mid Y = y).
\]
2. Bayes’ Rule
\[
p(\theta \mid y) = \frac{ p(y \mid \theta) \cdot p(\theta)}{p(y)}.
\]
To make \(p(\theta \mid y)\) a valid
density, i.e., \(\int p(\theta | y) =
1\), equivalently,
\[
p(y) = \int_{-\infty}^{\infty} p(y\mid \theta) p(\theta)d\theta.
\]
The likelihood (given \(\theta\)):
\[
p(y \mid \theta) = \frac{1}{\sqrt{2\pi \sigma_0^2}} \exp\left[ -\frac{(y
- \theta)^2}{2\sigma_0^2} \right].
\]
The prior:
\[
p(\theta) = \frac{1}{\sqrt{2\pi \tau_0^2}} \exp\left[ -\frac{(\theta -
\mu_0)^2}{2\tau_0^2} \right].
\]
3. Combine exponents
\[
p(\theta \mid y) \propto \exp\left[ -\frac{(y - \theta)^2}{2\sigma_0^2}
- \frac{(\theta - \mu_0)^2}{2\tau_0^2} \right].
\]
Expand the quadratics in \(\theta\):
First term:
\[
-\frac{(y - \theta)^2}{2\sigma_0^2} = -\frac{\theta^2}{2\sigma_0^2} +
\frac{y \theta}{\sigma_0^2} - \frac{y^2}{2\sigma_0^2}.
\]
Second term:
\[
-\frac{(\theta - \mu_0)^2}{2\tau_0^2} = -\frac{\theta^2}{2\tau_0^2} +
\frac{\mu_0 \theta}{\tau_0^2} - \frac{\mu_0^2}{2\tau_0^2}.
\]
4. Collect terms in \(\theta\)
The exponent (ignoring constants not depending on \(\theta\)):
Quadratic in \(\theta\):
\[
-\frac{1}{2} \left( \frac{1}{\sigma_0^2} + \frac{1}{\tau_0^2} \right)
\theta^2.
\]
Linear in \(\theta\):
\[
+ \left( \frac{y}{\sigma_0^2} + \frac{\mu_0}{\tau_0^2} \right) \theta.
\]
Constants in \(y, \mu_0\):
\[
-\frac{y^2}{2\sigma_0^2} - \frac{\mu_0^2}{2\tau_0^2}.
\]
Define:
\[
v = \left( \frac{1}{\sigma_0^2} + \frac{1}{\tau_0^2} \right)^{-1}, \quad
\text{(posterior variance)}
\]
\[
m = v \cdot \left( \frac{y}{\sigma_0^2} + \frac{\mu_0}{\tau_0^2}
\right), \quad \text{(posterior mean)}
\]
5. Complete the square
Let \[
A = \frac{1}{\sigma_0^2} + \frac{1}{\tau_0^2}, \quad B =
\frac{y}{\sigma_0^2} + \frac{\mu_0}{\tau_0^2}.
\]
The exponent in \(\theta\) is:
\[
-\frac{1}{2} A \theta^2 + B\theta.
\]
Complete the square:
\[
-\frac{1}{2} A \left[ \theta^2 - \frac{2B}{A} \theta \right]
= -\frac{1}{2} A \left[ \left( \theta - \frac{B}{A} \right)^2 -
\frac{B^2}{A^2} \right].
\]
Thus: \[
-\frac{1}{2} A \theta^2 + B\theta = -\frac{1}{2} A \left( \theta -
\frac{B}{A} \right)^2 + \frac{B^2}{2A}.
\]
So: \[
p(\theta \mid y) \propto \exp\left[ -\frac{1}{2} A \left( \theta -
\frac{B}{A} \right)^2 \right].
\]
6. Identify posterior distribution
This is a normal density:
\[
\theta \mid Y = y \sim \mathcal{N}\left( \frac{B}{A}, \; A^{-1} \right),
\] where
\[
A = \frac{1}{\sigma_0^2} + \frac{1}{\tau_0^2}, \quad B =
\frac{y}{\sigma_0^2} + \frac{\mu_0}{\tau_0^2}.
\]
Mean: \[
\mu_{\text{post}} = \frac{B}{A} = \frac{ \frac{y}{\sigma_0^2} +
\frac{\mu_0}{\tau_0^2} }{ \frac{1}{\sigma_0^2} + \frac{1}{\tau_0^2} }.
\]
Variance: \[
\sigma_{\text{post}}^2 = \frac{1}{ \frac{1}{\sigma_0^2} +
\frac{1}{\tau_0^2} }.
\]
7. Final expression
Using precision notation (\(\eta_0 =
1/\sigma_0^2\), \(\lambda_0 =
1/\tau_0^2\)):
\[
\theta \mid Y = y \; \sim \; \mathcal{N}\left( \frac{\eta_0 y +
\lambda_0 \mu_0}{\eta_0 + \lambda_0}, \; \frac{1}{\eta_0 + \lambda_0}
\right).
\]
In original notation:
\[
\boxed{\theta \mid Y = y \sim \mathcal{N}\left( \frac{\sigma_0^{-2}y +
\tau_0^{-2}\mu_0}{\sigma_0^{-2} + \tau_0^{-2}}, \; (\sigma_0^{-2} +
\tau_0^{-2})^{-1} \right)}.
\]
LS0tDQp0aXRsZTogIkJheWVzIFJ1bGUsIEJheWVzIEluZmVyZW5jZSBhbmQgQXBwbGljYXRpb25zIg0KYXV0aG9yOiAiQ2hlbmcgUGVuZyINCmRhdGU6ICJXZXN0IENoZXN0ZXIgVW5pdmVyc2l0eSINCm91dHB1dDoNCiAgaHRtbF9kb2N1bWVudDogDQogICAgdG9jOiB5ZXMNCiAgICB0b2NfZGVwdGg6IDQNCiAgICB0b2NfZmxvYXQ6IHllcw0KICAgIG51bWJlcl9zZWN0aW9uczogeWVzDQogICAgdG9jX2NvbGxhcHNlZDogeWVzDQogICAgY29kZV9mb2xkaW5nOiBoaWRlDQogICAgY29kZV9kb3dubG9hZDogeWVzDQogICAgc21vb3RoX3Njcm9sbDogeWVzDQogICAgdGhlbWU6IGx1bWVuDQogIHBkZl9kb2N1bWVudDogDQogICAgdG9jOiB5ZXMNCiAgICB0b2NfZGVwdGg6IDQNCiAgICBmaWdfY2FwdGlvbjogeWVzDQogICAgbnVtYmVyX3NlY3Rpb25zOiB5ZXMNCiAgICBmaWdfd2lkdGg6IDMNCiAgICBmaWdfaGVpZ2h0OiAzDQogIHdvcmRfZG9jdW1lbnQ6IA0KICAgIHRvYzogeWVzDQogICAgdG9jX2RlcHRoOiA0DQogICAgZmlnX2NhcHRpb246IHllcw0KICAgIGtlZXBfbWQ6IHllcw0KZWRpdG9yX29wdGlvbnM6IA0KICBjaHVua19vdXRwdXRfdHlwZTogaW5saW5lDQotLS0NCg0KYGBge2NzcywgZWNobyA9IEZBTFNFfQ0KI1RPQzo6YmVmb3JlIHsNCiAgY29udGVudDogIlRhYmxlIG9mIENvbnRlbnRzIjsNCiAgZm9udC13ZWlnaHQ6IGJvbGQ7DQogIGZvbnQtc2l6ZTogMS4yZW07DQogIGRpc3BsYXk6IGJsb2NrOw0KICBjb2xvcjogbmF2eTsNCiAgbWFyZ2luLWJvdHRvbTogMTBweDsNCn0NCg0KDQpkaXYjVE9DIGxpIHsgICAgIC8qIHRhYmxlIG9mIGNvbnRlbnQgICovDQogICAgbGlzdC1zdHlsZTp1cHBlci1yb21hbjsNCiAgICBiYWNrZ3JvdW5kLWltYWdlOm5vbmU7DQogICAgYmFja2dyb3VuZC1yZXBlYXQ6bm9uZTsNCiAgICBiYWNrZ3JvdW5kLXBvc2l0aW9uOjA7DQp9DQoNCmgxLnRpdGxlIHsgICAgLyogbGV2ZWwgMSBoZWFkZXIgb2YgdGl0bGUgICovDQogIGZvbnQtc2l6ZTogMjJweDsNCiAgZm9udC13ZWlnaHQ6IGJvbGQ7DQogIGNvbG9yOiBEYXJrUmVkOw0KICB0ZXh0LWFsaWduOiBjZW50ZXI7DQogIGZvbnQtZmFtaWx5OiAiR2lsbCBTYW5zIiwgc2Fucy1zZXJpZjsNCn0NCg0KaDQuYXV0aG9yIHsgLyogSGVhZGVyIDQgLSBhbmQgdGhlIGF1dGhvciBhbmQgZGF0YSBoZWFkZXJzIHVzZSB0aGlzIHRvbyAgKi8NCiAgZm9udC1zaXplOiAxNXB4Ow0KICBmb250LXdlaWdodDogYm9sZDsNCiAgZm9udC1mYW1pbHk6IHN5c3RlbS11aTsNCiAgY29sb3I6IG5hdnk7DQogIHRleHQtYWxpZ246IGNlbnRlcjsNCn0NCg0KaDQuZGF0ZSB7IC8qIEhlYWRlciA0IC0gYW5kIHRoZSBhdXRob3IgYW5kIGRhdGEgaGVhZGVycyB1c2UgdGhpcyB0b28gICovDQogIGZvbnQtc2l6ZTogMThweDsNCiAgZm9udC13ZWlnaHQ6IGJvbGQ7DQogIGZvbnQtZmFtaWx5OiAiR2lsbCBTYW5zIiwgc2Fucy1zZXJpZjsNCiAgY29sb3I6IERhcmtCbHVlOw0KICB0ZXh0LWFsaWduOiBjZW50ZXI7DQp9DQoNCmgxIHsgLyogSGVhZGVyIDEgLSBhbmQgdGhlIGF1dGhvciBhbmQgZGF0YSBoZWFkZXJzIHVzZSB0aGlzIHRvbyAgKi8NCiAgICBmb250LXNpemU6IDIwcHg7DQogICAgZm9udC13ZWlnaHQ6IGJvbGQ7DQogICAgZm9udC1mYW1pbHk6ICJUaW1lcyBOZXcgUm9tYW4iLCBUaW1lcywgc2VyaWY7DQogICAgY29sb3I6IGRhcmtyZWQ7DQogICAgdGV4dC1hbGlnbjogY2VudGVyOw0KfQ0KDQpoMiB7IC8qIEhlYWRlciAyIC0gYW5kIHRoZSBhdXRob3IgYW5kIGRhdGEgaGVhZGVycyB1c2UgdGhpcyB0b28gICovDQogICAgZm9udC1zaXplOiAxOHB4Ow0KICAgIGZvbnQtd2VpZ2h0OiBib2xkOw0KICAgIGZvbnQtZmFtaWx5OiAiVGltZXMgTmV3IFJvbWFuIiwgVGltZXMsIHNlcmlmOw0KICAgIGNvbG9yOiBuYXZ5Ow0KICAgIHRleHQtYWxpZ246IGxlZnQ7DQp9DQoNCmgzIHsgLyogSGVhZGVyIDMgLSBhbmQgdGhlIGF1dGhvciBhbmQgZGF0YSBoZWFkZXJzIHVzZSB0aGlzIHRvbyAgKi8NCiAgICBmb250LXNpemU6IDE2cHg7DQogICAgZm9udC13ZWlnaHQ6IGJvbGQ7DQogICAgZm9udC1mYW1pbHk6ICJUaW1lcyBOZXcgUm9tYW4iLCBUaW1lcywgc2VyaWY7DQogICAgY29sb3I6IG5hdnk7DQogICAgdGV4dC1hbGlnbjogbGVmdDsNCn0NCg0KaDQgeyAvKiBIZWFkZXIgNCAtIGFuZCB0aGUgYXV0aG9yIGFuZCBkYXRhIGhlYWRlcnMgdXNlIHRoaXMgdG9vICAqLw0KICAgIGZvbnQtc2l6ZTogMTRweDsNCiAgZm9udC13ZWlnaHQ6IGJvbGQ7DQogICAgZm9udC1mYW1pbHk6ICJUaW1lcyBOZXcgUm9tYW4iLCBUaW1lcywgc2VyaWY7DQogICAgY29sb3I6IGRhcmtyZWQ7DQogICAgdGV4dC1hbGlnbjogbGVmdDsNCn0NCg0KLyogQWRkIGRvdHMgYWZ0ZXIgbnVtYmVyZWQgaGVhZGVycyAqLw0KLmhlYWRlci1zZWN0aW9uLW51bWJlcjo6YWZ0ZXIgew0KICBjb250ZW50OiAiLiI7DQoNCmJvZHkgeyBiYWNrZ3JvdW5kLWNvbG9yOndoaXRlOyB9DQoNCi5oaWdobGlnaHRtZSB7IGJhY2tncm91bmQtY29sb3I6eWVsbG93OyB9DQoNCnAgeyBiYWNrZ3JvdW5kLWNvbG9yOndoaXRlOyB9DQoNCn0NCmBgYA0KDQpgYGB7ciBzZXR1cCwgaW5jbHVkZT1GQUxTRX0NCiMgY29kZSBjaHVuayBzcGVjaWZpZXMgd2hldGhlciB0aGUgUiBjb2RlLCB3YXJuaW5ncywgYW5kIG91dHB1dCANCiMgd2lsbCBiZSBpbmNsdWRlZCBpbiB0aGUgb3V0cHV0IGZpbGVzLg0KaWYgKCFyZXF1aXJlKCJrbml0ciIpKSB7DQogICBpbnN0YWxsLnBhY2thZ2VzKCJrbml0ciIpDQogICBsaWJyYXJ5KGtuaXRyKQ0KfQ0KaWYgKCFyZXF1aXJlKCJwYW5kZXIiKSkgew0KICAgaW5zdGFsbC5wYWNrYWdlcygicGFuZGVyIikNCiAgIGxpYnJhcnkocGFuZGVyKQ0KfQ0KaWYgKCFyZXF1aXJlKCJwc3ljaCIpKSB7DQogIGluc3RhbGwucGFja2FnZXMoInBzeWNoIikNCiAgbGlicmFyeShwc3ljaCkNCn0NCmlmICghcmVxdWlyZSgiUkNvbG9yQnJld2VyIikpIHsNCiAgaW5zdGFsbC5wYWNrYWdlcygiUkNvbG9yQnJld2VyIikNCiAgbGlicmFyeShSQ29sb3JCcmV3ZXIpDQp9DQoNCmlmICghcmVxdWlyZSgiYm9vdCIpKSB7DQogIGluc3RhbGwucGFja2FnZXMoImJvb3QiKQ0KICBsaWJyYXJ5KGJvb3QpDQp9DQppZiAoIXJlcXVpcmUoImVmZnNpemUiKSkgew0KICBpbnN0YWxsLnBhY2thZ2VzKCJlZmZzaXplIikNCiAgbGlicmFyeShlZmZzaXplKQ0KfQ0KIyMgbGlicmFyeShlZmZzaXplKQ0Ka25pdHI6Om9wdHNfY2h1bmskc2V0KGVjaG8gPSBUUlVFLCAgICAgICAjIGluY2x1ZGUgY29kZSBjaHVuayBpbiB0aGUgb3V0cHV0IGZpbGUNCiAgICAgICAgICAgICAgICAgICAgICB3YXJuaW5nID0gRkFMU0UsICAgIyBzb21ldGltZXMsIHlvdSBjb2RlIG1heSBwcm9kdWNlIHdhcm5pbmcgbWVzc2FnZXMsDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICMgeW91IGNhbiBjaG9vc2UgdG8gaW5jbHVkZSB0aGUgd2FybmluZyBtZXNzYWdlcyBpbg0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAjIHRoZSBvdXRwdXQgZmlsZS4gDQogICAgICAgICAgICAgICAgICAgICAgcmVzdWx0cyA9IFRSVUUsICAgICMgeW91IGNhbiBhbHNvIGRlY2lkZSB3aGV0aGVyIHRvIGluY2x1ZGUgdGhlIG91dHB1dA0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAjIGluIHRoZSBvdXRwdXQgZmlsZS4NCiAgICAgICAgICAgICAgICAgICAgICBtZXNzYWdlID0gRkFMU0UsDQogICAgICAgICAgICAgICAgICAgICAgY29tbWVudCA9IE5BDQogICAgICAgICAgICAgICAgICAgICAgKSAgDQpgYGANCg0KXA0KDQojIEludHJvZHVjdGlvbg0KDQpCYXllc2lhbiByZWFzb25pbmcgaXMgYSBjb3JuZXJzdG9uZSBvZiBwcm9iYWJpbGlzdGljIGluZmVyZW5jZSwgYWxsb3dpbmcgdXMgdG8gdXBkYXRlIGJlbGllZnMgYXMgbmV3IGRhdGEgYXJyaXZlcy4gSW4gc2ltcGxlIHRlcm1zLCBCYXllcycgcnVsZSBjYW4gaW5jb3Jwb3JhdGUgcHJpb3IgKGF1eGlsaWFyeSkgaW5mb3JtYXRpb24gaW50byBtb2RlbHMgdG8gaW1wcm92ZSB0aGVpciBwZXJmb3JtYW5jZS4gSXRzIGFwcGxpY2F0aW9ucyByYW5nZSBmcm9tIHRyYWRpdGlvbmFsIHN0YXRpc3RpY2FsIG1vZGVsaW5nIGluIGZpZWxkcyBzdWNoIGFzIG1lZGljYWwgZGlhZ25vc2lzLCBzcGFtIGZpbHRlcmluZywgYW5kIGZpbmFuY2UsIHRvIG1vZGVybiBkYXRhIHNjaWVuY2UgYW5kIG1hY2hpbmUgbGVhcm5pbmcuDQoNClRoaXMgbW9kdWxlIGZpcnN0IHJldmlld3MgQmF5ZXMnIHJ1bGUgZm9yIGRlcGVuZGVudCBldmVudHMsIHRoZW4gZXh0ZW5kcyBpdCB0byBkZXBlbmRlbnQgZGlzY3JldGUgYW5kIGNvbnRpbnVvdXMgcmFuZG9tIHZhcmlhYmxlcy4gRmluYWxseSwgd2UgcmVsYXggdGhlIGFzc3VtcHRpb24gb2YgY29uZGl0aW9uYWwgZGVwZW5kZW5jZSB0byBpbnRyb2R1Y2UgdGhlIHdlbGzigJFrbm93biBuYWl2ZSBCYXllcyBwcmVkaWN0aXZlIG1vZGVscywgb25lIG9mIHRoZSBtb3N0IHByYWN0aWNhbGx5IGltcG9ydGFudCBwcmVkaWN0aXZlIG1vZGVscyBpbiBtYWNoaW5lIGxlYXJuaW5nIGFuZCBkYXRhIHNjaWVuY2UuDQoNCg0KIyBCYXllc+KAmSBSdWxlIGZvciBEZXBlbmRlbnQgRXZlbnRzDQoNCioqTWF0aGVtYXRpY2FsIEZvcm11bGF0aW9uKioNCg0KTGV0JEEkYW5kJEIkYmUgdHdvIGRlcGVuZGVudCBldmVudHMgd2l0aCAkUChCKSA+IDAkLiBCYXllc+KAmSBydWxlIGZvbGxvd3MgZnJvbSB0aGUgZGVmaW5pdGlvbiBvZiBjb25kaXRpb25hbCBwcm9iYWJpbGl0eToNCg0KJCQNClAoQXxCKSA9IFxmcmFje1AoQnxBKVAoQSl9e1AoQil9DQokJA0KDQoqJFAoQSkkOiBQcmlvciBwcm9iYWJpbGl0eSBvZiAkQSQgKGluaXRpYWwgYmVsaWVmLCBwcmlvciBpbmZvcm1hdGlvbiwgYXV4aWxpYXJ5IGluZm9ybWF0aW9uKS4NCiokUChCfEEpJDogTGlrZWxpaG9vZCBvZiBvYnNlcnZpbmcgJEIkIGdpdmVuICRBJC4gVGhlIG9ic2VydmVkIGluZm9ybWF0aW9uIGZyb20gZGF0YS4NCiokUChCKSQ6IE1hcmdpbmFsIHByb2JhYmlsaXR5IG9mICRCJCwgb2Z0ZW4gY29tcHV0ZWQgdXNpbmcgdGhlIGxhdyBvZiB0b3RhbCBwcm9iYWJpbGl0eX0uDQoqJFAoQXxCKSQ6IFBvc3RlcmlvciBwcm9iYWJpbGl0eSBvZiAkQSQgZ2l2ZW4gZXZpZGVuY2UgJEIkLiBUaGUgbW9kZWwgd2l0aCBpbmNvcnBvcmF0ZWQgYXV4aWxpYXJ5IGluZm9ybWF0aW9uDQoNCg0KSWYgJEEkIGhhcyBtdWx0aXBsZSBtdXR1YWxseSBleGNsdXNpdmUgc3RhdGVzICRBXzEsIEFfMiwgXGRvdHMsIEFfbiQ6DQoNCiQkDQpQKEFfaXxCKSA9IFxmcmFje1AoQnxBX2kpUChBX2kpfXtcc3VtX3tqPTF9Xm4gUChCfEFfailQKEFfail9DQokJA0KDQoqKkV4YW1wbGU6IE1lZGljYWwgRGlhZ25vc2lzKioNCg0KKipQcm9ibGVtKio6IFNvbWUgYXNzdW1wdGlvbnMgYWJvdXQgdGhlIHBvcHVsYXRpb24gYW5kIHRoZSBwZXJmb3JtYW5jZSBvZiB0aGUgdGVzdDoNCg0KQSBkaXNlYXNlIGFmZmVjdHMgJDFcJSQgb2YgYSBwb3B1bGF0aW9uLiBUaGlzIGlzIGdlbmVyYWwgaW5mb3JtYXRpb24gY2FuIGJlIGZvdW5kIGF0IHBvcHVsYXRpb24gbGV2ZWwuDQoNClRlc3Qgc2Vuc2l0aXZpdHkgJFAoXHRleHR7UG9zaXRpdmV9fFx0ZXh0e0Rpc2Vhc2V9KSA9IDAuOTUkLiBUaGlzIGluZm9ybWF0aW9uIGlzIGJhc2VkIG9uIHRoZSBjbGluaWNhbCB0cmlhbHMgaW4gd2hpY2ggdGhlIHBhcnRpY2lwYW50cycgZGlzZWFzZSBzdGF0dXMgaXMga25vd24uDQoNClRlc3Qgc3BlY2lmaWNpdHkgJFAoXHRleHR7TmVnYXRpdmV9fFx0ZXh0e05vIERpc2Vhc2V9KSA9IDAuOTAkLiBUaGlzIGluZm9ybWF0aW9uIGlzIGFsc28gYmFzZWQgb24gdGhlIGNsaW5pY2FsIHRyaWFscy4NCg0KR2l2ZW4gYSBwb3NpdGl2ZSB0ZXN0LCB3aGF0IGlzIHRoZSBwcm9iYWJpbGl0eSB0aGUgcGF0aWVudCBoYXMgdGhlIGRpc2Vhc2U/IFRoaXMgaW5mb3JtYXRpb24gaXMgbmVlZGVkIGZvciBwaHlzaWNpYW4gdG8gbWFrZSBjbGluaWNhbCBkZWNpc2lvbi4NCg0KKipTb2x1dGlvbioqOiANCg0KKiAqU29tZSBOb3RhdGlvbnMqOg0KICArICREKyQ6IGV2ZW50ICoqaGFzIGRpc2Vhc2UqKiANCiAgKyAkRC0kOiBldmVudCAqKmhhcyBubyBkaXNlYXNlKioNCiAgKyAkVCskOiBldmVudCAqKnRlc3QgcG9zaXRpdmUqKg0KICArICRULSQ6IGV2ZW50ICoqdGVzdCBuZWdhdGl2ZSoqDQoNCiogKkdpdmVuIEluZm8qOg0KICArICRQKEQrKSA9IDAuMDEkDQogICsgJFAoVCsgfCBEKykgPSAwLjk1JA0KICArICRQKFQtIHwgRC0pID0gMC45MCQNCg0KKiBXZSB3YW50IHRvIGZpbmQgJFAoRCt8VCspJC4NCg0KRmlyc3QsIGNvbXB1dGUgJFAoVCt8RCspID0gMC45NSQuDQoNCiQkUChUK3xELSkgPSAxIC0gUChcdGV4dHtOZWdhdGl2ZX18XHRleHR7Tm8gRGlzZWFzZX0pID0gMC4xMCQkLg0KDQpVc2luZyB0aGUgZm9sbG93aW5nICoqbGF3IG9mIHRvdGFsIHByb2JhYmlsaXR5Kio6DQoNCiQkDQpQKFQrKSA9IFAoVCtcY2FwIEQrKSArIFAoVCsgXGNhcCBELSkgPSBQKFQrfEQrKVAoRCspICsgUChUK3xELSlQKEQtKQ0KJCQNCg0KJCQNClAoVCspID0gMC45NSBcdGltZXMgMC4wMSArIDAuMTAgXHRpbWVzIDAuOTkgPSAwLjAwOTUgKyAwLjA5OSA9IDAuMTA4NQ0KJCQNCg0KQmF5ZXPigJkgcnVsZToNCg0KJCQNClAoRCt8VCspID0gXGZyYWN7UChUK3xEKylQKEQrKX17UChUKyl9ID0gXGZyYWN7MC45NSBcdGltZXMgMC4wMX17MC4xMDg1fSBcYXBwcm94IDAuMDg3NiA9IDguNzZcJQ0KJCQNCg0KRGVzcGl0ZSB0aGUgcG9zaXRpdmUgdGVzdCwgdGhlIHBvc3RlcmlvciBwcm9iYWJpbGl0eSBpcyBsb3cgYmVjYXVzZSB0aGUgcHJpb3IgaXMgdmVyeSBsb3cuDQoNClwNCg0KDQoqKkV4YW1wbGUgMjogQmF5ZXMgcnVsZSBvbiBtdWx0aXBsZSBldmVudCoqOiAgU3VwcG9zZSBhIGZhY3RvcnkgaGFzIHRocmVlIG1hY2hpbmVzICRCXzEsIEJfMiwgQl8zJCBtYWtpbmcgd2lkZ2V0cy4gRGVub3RlICREID0gXHRleHR7RGVmZWN0aXZlfSQuIEdpdmVuIHRoZSBmb2xsb3dpbmcgaW5mb3JtYXRpb24NCg0KKiBNYWNoaW5lICRCXzEkIG1ha2VzIDUwXCUgb2Ygd2lkZ2V0czogJFAoQl8xKT0wLjUkLg0KKiBNYWNoaW5lICRCXzIkIG1ha2VzIDMwXCU6ICRQKEJfMik9MC4zJC4NCiogTWFjaGluZSAkQl8zJCBtYWtlcyAyMFwlOiAkUChCXzMpPTAuMiQuDQoNCkRlZmVjdCByYXRlcyBvZiBlYWNoIG1hY2hpbmUgYXJlIGdpdmVuIGJ5Og0KDQoqICRQKFx0ZXh0e0R9IFxtaWQgQl8xKSA9IDAuMDEkOiAxXCUgb2YgdGhlIHByb2R1Y3RzIHByb2R1Y2VkIGJ5IG1hY2hpbmUgJEJfMSQgd2VyZSBkZWZlY3RpdmUuDQoqICRQKFx0ZXh0e0R9IFxtaWQgQl8yKSA9IDAuMDIkOiAyXCUgb2YgdGhlIHByb2R1Y3RzIHByb2R1Y2VkIGJ5IG1hY2hpbmUgJEJfMiQgd2VyZSBkZWZlY3RpdmUuDQoqICRQKFx0ZXh0e0R9IFxtaWQgQl8zKSA9IDAuMDUkOiA1XCUgb2YgdGhlIHByb2R1Y3RzIHByb2R1Y2VkIGJ5IG1hY2hpbmUgJEJfMyQgd2VyZSBkZWZlY3RpdmUuDQoNCmBgYHtyIGZpZy5hbGlnbj0nY2VudGVyJywgb3V0LndpZHRoPSI0MCUifQ0KaW5jbHVkZV9ncmFwaGljcygiQmF5ZXNSdWxlLnBuZyIpDQpgYGANCg0KKipRdWVzdGlvbioqOiBHaXZlbiBhIGRlZmVjdGl2ZSB3aWRnZXQsIHdoYXQgaXMgdGhlIHByb2JhYmlsaXR5IGl0IGNhbWUgZnJvbSBtYWNoaW5lICRCXzMkLCAkUChCXzMgXG1pZCBcdGV4dHtEfSkkPw0KDQoNCioqU29sdXRpb24qKjogRmlyc3Qgb2YgYWxsLCB0aGUgZGVzaXJlZCBjb25kaXRpb25hbCBwcm9iYWJpbGl0eSBjYW4gYmUgcmUtZXhwcmVzc2VkIGFzDQoNCiQkDQpQKEJfMyBcbWlkIFx0ZXh0e0R9KSA9IFxmcmFje1AoQl8zIFxjYXAgRCl9e1AoRCl9ID0gXGZyYWN7UChEIFxtaWQgQl8zKSBQKEJfMyl9e1AoRCl9DQokJA0KVGhlIHByb2JhYmlsaXRpZXMgb24gdGhlIG51bWVyYXRvciBhcmUgZ2l2ZW4uIFdlIG5lZWQgdG8gZmluZCB0aGUgcHJvYmFiaWxpdHkgJFAoRCkkIHVzaW5nIHRoZSAqKmxhdyBvZiB0b3RhbCBwcm9iYWJpbGl0eSoqIGluIHRoZSBmb2xsb3dpbmcuIEZyb20gdGhlIGFib3ZlIFZlbm4gZGlhZ3JhbSwgd2Ugc2VlIHRoYXQNCg0KDQokJA0KXGJlZ2lue2FsaWduZWR9DQpQKEQpICYgPVAoQl8xIFxjYXAgRCkgKyBQKEJfMiBcY2FwIEQpICsgUChCXzMgXGNhcCBEKSBcXA0KICAgICAmPSBQKEQgXG1pZCBCXzEpUChCXzEpICsgUChEIFxtaWQgQl8yKVAoQl8yKSArIFAoRCBcbWlkIEJfMylQKEJfMykgXFwNCiAgICAgJj0gKDAuMDEpKDAuNSkgKyAoMC4wMikoMC4zKSArICgwLjA1KSgwLjIpIFxcDQogICAgICY9IDAuMDA1ICsgMC4wMDYgKyAwLjAxIFxcDQogICAgICY9IDAuMDIxLg0KXGVuZHthbGlnbmVkfQ0KJCQNCg0KVGhlcmVmb3JlLA0KDQokJA0KUChCXzMgXG1pZCBcdGV4dHtEfSkgPSBcZnJhY3tQKEQgXG1pZCBCXzMpIFAoQl8zKX17UChEKX0gPSBcZnJhY3swLjA1XHRpbWVzIDAuMn17MC4wMjF9ID0gXGZyYWN7MC4wMX17MC4wMjF9ID0gMC40NzYuDQokJA0KDQoNCiMgQmF5ZXPigJkgUnVsZSBmb3IgRGlzY3JldGUgUmFuZG9tIFZhcmlhYmxlcw0KDQpGb3IgZGlzY3JldGUgcmFuZG9tIHZhcmlhYmxlcyAkWCQgYW5kICRZJCwgd2l0aCBwbWYgJHBfWCh4KSQgYW5kIGNvbmRpdGlvbmFsIHBtZiAkcF97WXxYfSh5fHgpJDoNCg0KJCQNCnBfe1h8WX0oeHx5KSA9IFxmcmFje3Bfe1l8WH0oeXx4KSBwX1goeCl9e3BfWSh5KX0sIFxxdWFkIHBfWSh5KSA9IFxzdW1fe3gnfSBwX3tZfFh9KHl8eCcpIHBfWCh4JykNCiQkDQoNClRoaXMgaXMgZGlyZWN0bHkgYW5hbG9nb3VzIHRvIHRoZSBldmVudC1iYXNlZCB2ZXJzaW9uLg0KDQoqKkV4YW1wbGU6IE1hbnVmYWN0dXJpbmcgUXVhbGl0eSBDb250cm9sKioNCg0KTGV0ICRYJCBiZSB0aGUgKip0cnVlIHF1YWxpdHkgZ3JhZGUqKiBvZiBhbiBpdGVtIChkaXNjcmV0ZSByYW5kb20gdmFyaWFibGUpOiAgDQoNCiQkDQpYIFxpbiBceyBcdGV4dHtFeGNlbGxlbnR9LCBcdGV4dHtHb29kfSwgXHRleHR7RmFpcn0sIFx0ZXh0e1Bvb3J9IFx9DQokJA0KDQpMZXQgJFkkIGJlIHRoZSAqKmluc3BlY3Rpb24gcmVzdWx0KiogKGRpc2NyZXRlIHJhbmRvbSB2YXJpYWJsZSk6ICANCg0KJCQNClkgXGluIFx7IFx0ZXh0e1Bhc3N9LCBcdGV4dHtGYWlsfSBcfQ0KJCQNCg0KKiBHaXZlbiAqKnByaW9yIGRpc3RyaWJ1dGlvbioqIG9mIHF1YWxpdHkgKGJhc2VkIG9uIGhpc3RvcmljYWwgZGF0YSkNCg0KJCQNClxiZWdpbnthbGlnbmVkfQ0KUChYID0gXHRleHR7RXhjZWxsZW50fSkgJj0gMC4yMCBcXA0KUChYID0gXHRleHR7R29vZH0pICY9IDAuNTAgXFwNClAoWCA9IFx0ZXh0e0ZhaXJ9KSAmPSAwLjI1IFxcDQpQKFggPSBcdGV4dHtQb29yfSkgJj0gMC4wNQ0KXGVuZHthbGlnbmVkfQ0KJCQNCg0KKiBJbnNwZWN0aW9uIGFjY3VyYWN5ICgqKmxpa2VsaWhvb2QqKikgYmFzZWQgb24gZGF0YTogUHJvYmFiaWxpdHkgb2YgcGFzc2luZyBpbnNwZWN0aW9uIGdpdmVuIHRydWUgcXVhbGl0eS4NCg0KJCQNClxiZWdpbnthbGlnbmVkfQ0KUChZID0gXHRleHR7UGFzc30gXG1pZCBYID0gXHRleHR7RXhjZWxsZW50fSkgJj0gMC45OSBcXA0KUChZID0gXHRleHR7UGFzc30gXG1pZCBYID0gXHRleHR7R29vZH0pICY9IDAuOTAgXFwNClAoWSA9IFx0ZXh0e1Bhc3N9IFxtaWQgWCA9IFx0ZXh0e0ZhaXJ9KSAmPSAwLjcwIFxcDQpQKFkgPSBcdGV4dHtQYXNzfSBcbWlkIFggPSBcdGV4dHtQb29yfSkgJj0gMC4xMA0KXGVuZHthbGlnbmVkfQ0KJCQNCg0KYW5kDQoNCiQkDQpcYmVnaW57YWxpZ25lZH0NClAoWSA9IFx0ZXh0e0ZhaWx9IFxtaWQgWCA9IFx0ZXh0e0V4Y2VsbGVudH0pICY9IDAuMDEgXFwNClAoWSA9IFx0ZXh0e0ZhaWx9IFxtaWQgWCA9IFx0ZXh0e0dvb2R9KSAmPSAwLjEwIFxcDQpQKFkgPSBcdGV4dHtGYWlsfSBcbWlkIFggPSBcdGV4dHtGYWlyfSkgJj0gMC4zMCBcXA0KUChZID0gXHRleHR7RmFpbH0gXG1pZCBYID0gXHRleHR7UG9vcn0pICY9IDAuOTANClxlbmR7YWxpZ25lZH0NCiQkDQoNCioqUXVlc3Rpb24qKjogKipHaXZlbioqIGFuIGl0ZW0gKipmYWlscyBpbnNwZWN0aW9uKiogKCRZID0gXHRleHR7RmFpbH0kKS4gV2hhdCBpcyB0aGUgcHJvYmFiaWxpdHkgZGlzdHJpYnV0aW9uIG92ZXIgaXRzIHRydWUgcXVhbGl0eSBncmFkZSAkWCQ/IEluIG90aGVyIHdvcmRzLCB3ZSB3YW50IHRvIGZpbmQgdGhlIGRpc3RyaWJ1dGlvbiBvZiBjb25kaXRpb25hbCBkaXN0cmlidXRpb24gJFhcbWlkIFx0ZXh0e0ZhaWxzfSQ6DQoNCiQkDQpQKFggPSB4IFxtaWQgWSA9IFx0ZXh0e0ZhaWx9KSBccXVhZCBcdGV4dHtmb3IgfSB4IFxpbiBce1x0ZXh0e0V4fSwgXHRleHR7R29vZH0sIFx0ZXh0e0ZhaXJ9LCBcdGV4dHtQb29yfVx9DQokJA0KDQoqKlNvbHV0aW9uKio6IFVzaW5nIHRoZSBCYXllcyBydWxlLA0KDQokJA0KUChYID0geCBcbWlkIFkgPSBcdGV4dHtGYWlsfSkgPSBcZnJhY3tQWyhYPXgpXGNhcCBcdGV4dHtGYWlsc31dfXtQKFx0ZXh0e0ZhaWxzfSl9ID0gXGZyYWN7UFtcdGV4dHtGYWlsc31cbWlkIChYPXgpXVx0aW1lcyBQKFg9eCl9e1AoXHRleHR7RmFpbHN9KX0NCiQkDQoNCkZvciBhbnkgJHggXGluIFx7XHRleHR7RXh9LCBcdGV4dHtHb29kfSwgXHRleHR7RmFpcn0sIFx0ZXh0e1Bvb3J9XH0kLCB0aGUgbnVtZXJhdG9yIGlzIGNhbGN1bGF0ZWQgZnJvbSB0aGUgZ2l2ZW4gY29uZGl0aW9uLiBXZSBuZWVkIHRvIHVzZSB0aGUgKipsYXcgb2YgdG90YWwgcHJvYmFiaWxpdHkqKiB0byBmaW5kICRQKFx0ZXh0e0ZhaWxzfSkkIGluIHRoZSBmb2xsb3dpbmcuDQoNCiQkDQpQKFkgPSBcdGV4dHtGYWlsfSkgPSBcc3VtX3tcdGV4dHthbGwgfSB4fSBQKFkgPSBcdGV4dHtGYWlsfSBcbWlkIFggPSB4KSBQKFggPSB4KQ0KJCQNCg0Kd2hpY2ggaXMgZXhwbGljaXRseSBnaXZlbiBieQ0KDQokJA0KXGJlZ2lue2FsaWduZWR9DQpQKFkgPSBcdGV4dHtGYWlsfSkgJj0gKDAuMDEgXHRpbWVzIDAuMjApICsgKDAuMTAgXHRpbWVzIDAuNTApICsgKDAuMzAgXHRpbWVzIDAuMjUpICsgKDAuOTAgXHRpbWVzIDAuMDUpIFxcDQomPSAwLjAwMiArIDAuMDUgKyAwLjA3NSArIDAuMDQ1IFxcDQomPSAwLjE3Mg0KXGVuZHthbGlnbmVkfQ0KJCQNCg0KTmV4dCwgd2UgY2FsY3VsYXRlICRQKFggPSB4IFxtaWQgWSA9IFx0ZXh0e0ZhaWx9KSBccXVhZCBcdGV4dHtmb3IgfSB4IFxpbiBce1x0ZXh0e0V4fSwgXHRleHR7R29vZH0sIFx0ZXh0e0ZhaXJ9LCBcdGV4dHtQb29yfVx9JCBiZWxsb3c6DQoNCioqRXhjZWxsZW50fSoqICANCiQkDQpQKFggPSBcdGV4dHtFeH0gXG1pZCBZID0gXHRleHR7RmFpbH0pID0gXGZyYWN7MC4wMSBcdGltZXMgMC4yMH17MC4xNzJ9ID0gXGZyYWN7MC4wMDJ9ezAuMTcyfSBcYXBwcm94IDAuMDExNg0KJCQNCg0KKipHb29kKioNCg0KJCQNClAoWCA9IFx0ZXh0e0dvb2R9IFxtaWQgWSA9IFx0ZXh0e0ZhaWx9KSA9IFxmcmFjezAuMTAgXHRpbWVzIDAuNTB9ezAuMTcyfSA9IFxmcmFjezAuMDV9ezAuMTcyfSBcYXBwcm94IDAuMjkwNw0KJCQNCg0KKipGYWlyKioNCg0KJCQNClAoWCA9IFx0ZXh0e0ZhaXJ9IFxtaWQgWSA9IFx0ZXh0e0ZhaWx9KSA9IFxmcmFjezAuMzAgXHRpbWVzIDAuMjV9ezAuMTcyfSA9IFxmcmFjezAuMDc1fXswLjE3Mn0gXGFwcHJveCAwLjQzNjANCiQkDQoNCioqUG9vcioqICANCg0KJCQNClAoWCA9IFx0ZXh0e1Bvb3J9IFxtaWQgWSA9IFx0ZXh0e0ZhaWx9KSA9IFxmcmFjezAuOTAgXHRpbWVzIDAuMDV9ezAuMTcyfSA9IFxmcmFjezAuMDQ1fXswLjE3Mn0gXGFwcHJveCAwLjI2MTYNCiQkDQoNCkJlY2F1c2Ugd2UgaGF2ZSB0byB3b3JrZWQgd2l0aCBzbyBtYW55IHByb2JhYmlsaXRpZXMsIG5leHQsIHdlIHN1bW1hcml6ZSB0aGUgcHJvYmFiaWxpdGllcyBvYnRhaW5lZCBhYm92ZSBpbiBhIHRhYmxlLg0KDQp8IFF1YWxpdHkgQ2xhc3MgIHwgUHJpb3IgJFAoeCkkfCRQKFx0ZXh0e0ZhaWx9IFxtaWQgWCkkfCBQb3N0ZXJpb3IgJFAoWCBcbWlkIFx0ZXh0e0ZhaWx9KSR8DQp8Oi0tLS0tLS0tLS0tfDotLS0tLS0tLS0tLS0tLXw6LS0tLS0tLS0tLS0tLS0tLXw6LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tfA0KfCAqKkV4Y2VsbGVudCoqIHwgIDAuMjAgfCAgMC4wMSB8ICAwLjAxMTYgKDEuMTZcJSkgfCANCnwgKipHb29kKiogfCAgMC41MCB8ICAwLjEwIHwgIDAuMjkwNyAoMjkuMDdcJSkgfCANCnwgKipGYWlyKiogfCAgMC4yNSB8ICAwLjMwIHwgIDAuNDM2MCAoNDMuNjBcJSkgfCANCnwgKipQb29yKiogfCAgMC4wNSB8ICAwLjkwIHwgIDAuMjYxNiAoMjYuMTZcJSkgfCANCg0KDQpUaGUgbGFzdCBjb2x1bW4gY29udGFpbnMgdGhlIChwb3N0ZXJpb3IpIGRpc3RyaWJ1dGlvbiB0aGF0IHdlIHdhbnQgdG8gZmluZC4NCg0KPGZvbnQgY29sb3IgPSAiZGFya3JlZCI+V2UgY2FuIHVzZSAqKnRoZSBwb3N0ZXJpb3IgZGlzdHJpYnV0aW9uKiogZnJvbSB0aGUgdGFibGUgYWJvdmUgdG8gYW5zd2VyIGEgbWVtYmVyc2hpcCBjbGFzc2lmaWNhdGlvbiBvciBwcmVkaWN0aW9uOjwvZm9udD4gPGZvbnQgY29sb3IgPSAiYmx1ZSI+Rm9yIGEgcmFuZG9tbHkgc2VsZWN0ZWQgcHJvZHVjdCB0aGF0IGZhaWxlZCB0aGUgaW5zcGVjdGlvbiwgYmFzZWQgb24gdGhlIGNhbGN1bGF0ZWQgKipwb3N0ZXJpb3IgZGlzdHJpYnV0aW9uKiogKHRoZSBsYXN0IGNvbHVtbiBvZiB0aGUgdGFibGUgYWJvdmUpLCB0aGUgcHJvZHVjdCBpcyBjbGFzc2lmaWVkIGludG8gdGhlIHF1YWxpdHkgY2xhc3Mgb2YgKipGYWlyKiouPC9mb250PiBUaGlzIG1lYW5zIEJheWVzJyBydWxlIGNhbiBiZSB1c2VkIGFzIGEgKipjbGFzc2lmaWVyKiosIG9yICoqcHJlZGljdGl2ZSBtb2RlbCoqLg0KDQoNCg0KDQojIEJheWVz4oCZIFJ1bGUgZm9yIENvbnRpbnVvdXMgUmFuZG9tIFZhcmlhYmxlcw0KDQpGb3IgY29udGludW91cyByYW5kb20gdmFyaWFibGVzICRYJCBhbmQgJFkkLCB3ZSB1c2UgcHJvYmFiaWxpdHkgZGVuc2l0eSBmdW5jdGlvbnMgKHBkZnMpOg0KDQokJA0KZl97WHxZfSh4fHkpID0gXGZyYWN7Zl97WXxYfSh5fHgpIGZfWCh4KX17Zl9ZKHkpfSBccHJvcHRvIGZfe1l8WH0oeXx4KSBmX1goeCksIFxxdWFkIGZfWSh5KSA9IFxpbnQgZl97WXxYfSh5fHgpIGZfWCh4KSBkeA0KJCQNCg0KJFxwcm9wdG8kIGlzIHJlYWQgKipwcm9wb3J0aW9uYWwgdG8qKi4gV2UgY2FuIHdyaXRlICRmX3tYfFl9KHh8eSkgIFxwcm9wdG8gZl97WXxYfSh5fHgpIGZfWCh4KSQgYmVjYXVzZSAkZl9ZKHkpJCBpcyBhIG5vcm1hbGl6aW5nIGNvZWZmaWNpZW50ICh0aGF0IG1ha2VzICRmX3tYfFl9KHh8eSkkIGEgdmFsaWQgZGVuc2l0eSkuDQoNCg0KVG8gdW5kZXJzdGFuZCB0aGUgYWJvdmUgaWRlYSwgbGV0J3MgY29uc2lkZXIgbm9ybWFsIHJhbmRvbSB2YXJpYWJsZSAkWSQgd2l0aCBkZW5zaXR5IGZ1bmN0aW9uOg0KDQokWVxtaWQgXHRoZXRhIFxzaW0gXG1hdGhjYWx7Tn0oXHRoZXRhLCBcc2lnbWFfMF4yKSQgd2l0aCBrbm93biAkXHNpZ21hXzBeMiQgYW5kIHVua25vd24gbWVhbiAkXHRoZXRhJC4gQXNzdW1lIHRoYXQgJFx0aGV0YSQgaXMgcmFuZG9tIGFuZCBhbHNvIGZvbGxvd3Mgbm9ybWFsIGRpc3RyaWJ1dGlvbiAkXHRoZXRhIFxzaW0gXG1hdGhjYWx7Tn0oXG11XzAsIFx0YXVfMF4yKSQsIHdoZXJlIGJvdGggJFxtdV8wJCBhbmQgJFx0YXVfMCQgYXJlIGtub3duIGNvbnN0YW50cy4gPGZvbnQgY29sb3IgPSAicmVkIj5Eb24ndCBiZSBzdXJwcmlzZSEgSW4gQmF5ZXNpYW4gc3RhdGlzdGljcywgKiphbGwgdW5rbm93biBwYXJhbWV0ZXJzIGFyZSByYW5kb20qKi4gVGhlIGRpc3RyaWJ1dGlvbiBvZiB0aGUgdW5rbm93biBwYXJhbWV0ZXIgaXMgY2FsbGVkICoqcHJpb3IgZGlzdHJpYnV0aW9uKiogLjwvZm9udD4NCg0KR2l2ZW4gb2JzZXJ2YXRpb24gJFkgPSB5JCwgdGhlbiB0aGUgKipwb3N0ZXJpb3IgZGlzdHJpYnV0aW9uKiogb2YgJFx0aGV0YSQgZ2l2ZW4gJFkgPSB5JCBpcyAoU2VlIHRoZSBkZXJpdmF0aW9uIGluIHRoZSBhcHBlbmRpeCk6DQoNCiQkDQpcdGhldGF8WT15IFxzaW0gXG1hdGhjYWx7Tn1cbGVmdCggXGZyYWN7XHNpZ21hXzBeey0yfXkgKyBcdGF1XzBeey0yfVxtdV8wfXtcc2lnbWFfMF57LTJ9ICsgXHRhdV8wXnstMn19LCBcIChcc2lnbWFfMF57LTJ9ICsgXHRhdV8wXnstMn0pXnstMX0gXHJpZ2h0KQ0KJCQNCg0KPGZvbnQgY29sb3IgPSAicmVkIj5Ob3RlIHRoYXQgdGhlICoqcHJlY2lzaW9uIG9mIGEgZGlzdHJpYnV0aW9uKiogaXMgZGVmaW5lZCBhcyB0aGUgKippbnZlcnNlIG9mIHRoZSB2YXJpYW5jZSoqLjwvZm9udD4gTGV0ICRcZXRhXzAgPSBcc2lnbWFfMF57LTJ9JCBhbmQgJFxsYW1iZGFfMCA9IFx0YXVfMF57LTJ9JC4gVGhlIGFib3ZlIGV4cHJlc3Npb24gY2FuIGJlIHdyaXR0ZW4gYXMNCg0KJCQNClx0aGV0YXxZPXkgXHNpbSBcbWF0aGNhbHtOfVxsZWZ0KCBcZnJhY3tcZXRhXzB5ICsgXGxhbWJkYV8wIFxtdV8wfXtcZXRhXzAgKyBcbGFtYmRhXzB9LCBcIChcZXRhXzAgKyBcbGFtYmRhXzApXnstMX0gXHJpZ2h0KSwNCiQkDQoNCndoaWNoIGNhbiBmdXJ0aGVyIHJld3JpdHRlbiBhcw0KDQokJA0KXHRoZXRhfFk9eSBcc2ltIFxtYXRoY2Fse059XGxlZnQoIFxmcmFje1xldGFfMCB9e1xldGFfMCArIFxsYW1iZGFfMH0geSArIFxmcmFje1xsYW1iZGFfMCB9e1xldGFfMCArIFxsYW1iZGFfMH1cbXVfMCwgXCBcZnJhY3sxfXtcZXRhXzAgKyBcbGFtYmRhXzB9IFxyaWdodCksDQokJA0KDQoqKkludGVycHJldGF0aW9uKio6IElmICRZfFx0aGV0YSQgYW5kICRcdGhldGEkIGFyZSBib3RoIG5vcm1hbCByYW5kb20gdmFyaWFibGVzLCB0aGVuICRcdGhldGFcbWlkIFkkIGlzIGFsc28gYSBub3JtYWwgcmFuZG9tIHZhcmlhYmxlLiBUaGUgQmF5ZXNpYW4gRXN0aW1hdG9yIG9mIHRoZSBwb3B1bGF0aW9uIG1lYW4gaXMgJEVbXHRoZXRhIFxtaWQgWV0kOg0KDQokJA0Ke1xtdX1fe1x0ZXh0e0JheWVzfX0gPSBFW1x0aGV0YSBcbWlkIFldID0gXGZyYWN7XGV0YV8wIH17XGV0YV8wICsgXGxhbWJkYV8wfSB5ICsgXGZyYWN7XGxhbWJkYV8wIH17XGV0YV8wICsgXGxhbWJkYV8wfVxtdV8wDQokJA0KDQokJA0KPSBcZnJhY3tcZXRhXzAgfXtcZXRhXzAgKyBcbGFtYmRhXzB9IEVbeV0gKyBcZnJhY3tcbGFtYmRhXzAgfXtcZXRhXzAgKyBcbGFtYmRhXzB9XG11XzAuIA0KJCQNCg0KVGhlcmVmb3JlLA0KDQokJA0KXGhhdHtcbXV9X3tcdGV4dHtCYXllc319ID1cZnJhY3tcZXRhXzAgfXtcZXRhXzAgKyBcbGFtYmRhXzB9IFxiYXJ7eX0gKyBcZnJhY3tcbGFtYmRhXzAgfXtcZXRhXzAgKyBcbGFtYmRhXzB9XG11XzAuIA0KJCQNCg0KVGhhdCBpcywgPGZvbnQgY29sb3IgPSAicmVkIj4qKnRoZSBCYXllc2lhbiBlc3RpbWF0b3Igb2YgcG9wdWxhdGlvbiBtZWFuIChpLmUuLCB0aGUgcG9zdGVyaW9yIG1lYW4pIGlzIGVxdWFsIHRvIHRoZSB3ZWlnaHRlZCBhdmVyYWdlIG9mIHRoZSBzYW1wbGUgbWVhbiAoJFxiYXJ7eH0kKSBhbmQgdGhlIHByaW9yIG1lYW4gKCRcbXVfMCQpKiouPC9mb250PiAgVGhpcyBpcyB0aGUgYmFzaXMgZm9yIEJheWVzaWFuIHBhcmFtZXRlciBlc3RpbWF0aW9uLCB3aGVyZSAkXHRoZXRhJCBpcyBhbiB1bmtub3duIHBhcmFtZXRlciBhbmQgJFkkIGlzIG9ic2VydmVkIGRhdGEuIFRoZSBhYm92ZSBmb3JtdWxhcyBsb29rIGNvbXBsZXguIE5leHQsIHdlIHVzZSBhbiBudW1lcmljYWwgZXhhbXBsZSB0byBleHBsYWluIHRoZSBob3cgdG8gdXNlIHRoZSBhYm92ZSB0aGVvcmVtIHRvIHNvbHZlIHByYWN0aWNhbCBxdWVzdGlvbnMuDQoNCg0KDQoqKkV4YW1wbGU6IEVzdGltYXRpbmcgdGhlIG1lYW4gc3BlZWQgb2YgY2FycyBmcm9tIHNlbnNvciByZWFkaW5ncyoqOiBXZSB3YW50IHRvIGVzdGltYXRlIHRoZSAqKnRydWUgbWVhbiBzcGVlZCoqICRTJCBvZiBjYXJzIHBhc3NpbmcgYSBwb2ludCwgdXNpbmcgKipyYWRhciBtZWFzdXJlbWVudHMqKiAkUiQuIFdlIGhhdmUgcHJpb3Iga25vd2xlZGdlIGFib3V0ICRTJCwgYW5kIHdlIGdldCBzYW1wbGUgbWVhc3VyZW1lbnRzICRcYmFye3J9JCAoYXZlcmFnZSBvZiAkbiQgcmFkYXIgcmVhZGluZ3MpLiBMZXQ6DQoNCiogJFMkID0gdHJ1ZSBtZWFuIHNwZWVkICh1bmtub3duIHBhcmFtZXRlciwgdHJlYXRlZCBhcyBhIHJhbmRvbSB2YXJpYWJsZSBpbiBCYXllc2lhbiBpbmZlcmVuY2UpLg0KDQoqICRSX2kkID0gJGkkLXRoIHJhZGFyIHNwZWVkIG1lYXN1cmVtZW50Lg0KDQoNCkFzc3VtZSByYWRhciBtZWFzdXJlbWVudCBlcnJvcnMgYXJlIG5vcm1hbGx5IGRpc3RyaWJ1dGVkIGFyb3VuZCB0aGUgdHJ1ZSBzcGVlZDoNCg0KJCQNClJfaSBcbWlkIFMgXHNpbSBcbWF0aGNhbHtOfShTLCBcc2lnbWFeMikNCiQkDQoNCndoZXJlICRcc2lnbWEkIGlzIGtub3duIG1lYXN1cmVtZW50IHN0YW5kYXJkIGRldmlhdGlvbiAoaGVyZSAkXHNpZ21hID0gMiQgbXBoKS4gV2UgZ2V0ICRuJCBpbmRlcGVuZGVudCBtZWFzdXJlbWVudHM6ICRyXzEsIHJfMiwgXGRvdHMsIHJfbiQsIGFuZCBjb21wdXRlIHRoZWlyIHNhbXBsZSBtZWFuICRcYmFye3J9JC4NCg0KKipQcmlvciBEaXN0cmlidXRpb24gZm9yICRTJCoqDQoNCldlIG5lZWQgYSBwcmlvciBmb3IgdGhlIHRydWUgbWVhbiBzcGVlZCAkUyQgYmVmb3JlIHNlZWluZyBkYXRhLiBGcm9tIGhpc3RvcmljYWwgdHJhZmZpYyBkYXRhLCB3ZSBiZWxpZXZlIHR5cGljYWwgbWVhbiBzcGVlZHMgYXJlIGFyb3VuZCAkXG11XzAgPSA2MCQgbXBoLCB3aXRoIHNvbWUgdW5jZXJ0YWludHkgZXhwcmVzc2VkIGJ5IHN0YW5kYXJkIGRldmlhdGlvbiAkXHRhdSA9IDUkIG1waC4gVGh1cywgd2UgY2hvb3NlIGEgbm9ybWFsIHByaW9yOg0KDQokJA0KUyBcc2ltIFxtYXRoY2Fse059KFxtdV8wLCBcdGF1XjIpDQokJA0KDQoNCiQkDQpTIFxzaW0gXG1hdGhjYWx7Tn0oNjAsIDI1KQ0KJCQNCg0KKipMaWtlbGlob29kIG9mIHRoZSBEYXRhKioNCg0KR2l2ZW4gJFMkLCB0aGUgc2FtcGxlIG1lYW4gJFxiYXJ7Un0kIG9mICRuJCBtZWFzdXJlbWVudHMgaGFzIGRpc3RyaWJ1dGlvbjoNCg0KJCQNClxiYXJ7Un0gXG1pZCBTIFxzaW0gXG1hdGhjYWx7Tn1cbGVmdChTLCBcZnJhY3tcc2lnbWFeMn17bn1ccmlnaHQpDQokJA0KDQpiZWNhdXNlOg0KDQokJA0KXGJhcntSfSA9IFxmcmFjezF9e259IFxzdW1fe2k9MX1ebiBSX2ksIFxxdWFkIFx0ZXh0e1Zhcn0oXGJhcntSfSBcbWlkIFMpID0gXGZyYWN7XHNpZ21hXjJ9e259Lg0KJCQNCg0KTGV0IG9ic2VydmVkICRcYmFye3J9ID0gNjIkIG1waCBmcm9tICRuID0gMTAkIG1lYXN1cmVtZW50cywgYW5kIGtub3duICRcc2lnbWEgPSAyJCBtcGguDQoNClRoZW46DQoNCiQkDQpcZnJhY3tcc2lnbWFeMn17bn0gPSBcZnJhY3s0fXsxMH0gPSAwLjQNCiQkDQoNCnNvDQoNCiQkDQpcYmFye1J9IFxtaWQgUyBcc2ltIFxtYXRoY2Fse059KFMsIDAuNCkuDQokJA0KDQoqKlBvc3RlcmlvciBEaXN0cmlidXRpb24gZm9yICRTJCB1c2luZyBCYXllcycgUnVsZSoqDQoNCkZvciBhIG5vcm1hbCBwcmlvciBhbmQgbm9ybWFsIGxpa2VsaWhvb2QsIHRoZSBwb3N0ZXJpb3IgaXMgYWxzbyBub3JtYWwuIExldDoNCg0KKiBQcmlvciBtZWFuICRcbXVfMCA9IDYwJCwgcHJpb3IgdmFyaWFuY2UgJFx0YXVeMiA9IDI1JC4NCg0KKiBTYW1wbGUgbWVhbiAkXGJhcntyfSA9IDYyJCwgY29uZGl0aW9uYWwgdmFyaWFuY2UgJHYgPSBcc2lnbWFeMi9uID0gMC40JC4NCg0KDQpUaGUgcG9zdGVyaW9yIG1lYW4gJFxtdV9uJCBpczoNCg0KJCQNClxtdV9uID0gXGZyYWN7IFxmcmFje1xtdV8wfXtcdGF1XjJ9ICsgXGZyYWN7XGJhcntyfX17dn0gfXsgXGZyYWN7MX17XHRhdV4yfSArIFxmcmFjezF9e3Z9IH0NCiQkDQoNCiQkDQpcbXVfbiA9IFxmcmFjeyBcZnJhY3s2MH17MjV9ICsgXGZyYWN7NjJ9ezAuNH0gfXsgXGZyYWN7MX17MjV9ICsgXGZyYWN7MX17MC40fSB9DQokJA0KDQokJA0KXGZyYWN7NjB9ezI1fSA9IDIuNCwgXHF1YWQgXGZyYWN7NjJ9ezAuNH0gPSAxNTUNCiQkDQoNCk51bWVyYXRvcjogJDIuNCArIDE1NSA9IDE1Ny40JC4gRGVub21pbmF0b3I6ICRcZnJhY3sxfXsyNX0gKyBcZnJhY3sxfXswLjR9ID0gMC4wNCArIDIuNSA9IDIuNTQkLg0KDQpTbzoNCg0KJCQNClxtdV9uID0gXGZyYWN7MTU3LjR9ezIuNTR9IFxhcHByb3ggNjEuOTcgXCBcdGV4dHttcGh9Lg0KJCQNCg0KUG9zdGVyaW9yIHZhcmlhbmNlICRcdGF1X25eMiQ6DQoNCiQkDQpcZnJhY3sxfXtcdGF1X25eMn0gPSBcZnJhY3sxfXtcdGF1XjJ9ICsgXGZyYWN7MX17dn0gPSAyLjU0DQokJA0KDQokJA0KXHRhdV9uXjIgPSBcZnJhY3sxfXsyLjU0fSBcYXBwcm94IDAuMzkzNw0KJCQNCg0KJCQNClx0YXVfbiBcYXBwcm94IDAuNjI3IFwgXHRleHR7bXBofS4NCiQkDQoNClRodXMsIHRoZSBwb3N0ZXJpb3IgZGlzdHJpYnV0aW9uIGlzOg0KDQokJA0KUyBcbWlkIFxiYXJ7cn0gXHNpbSBcbWF0aGNhbHtOfSg2MS45NywgMC4zOTM3KS4NCiQkDQoNCioqSW50ZXJwcmV0YXRpb24qKg0KDQpXZSBzdGFydGVkIHdpdGggcHJpb3IgJFxtYXRoY2Fse059KDYwLCAyNSkkLCB3aGljaCB3YXMgcXVpdGUgdW5jZXJ0YWluICRcdGF1ID0gNSQgbXBoKS4NCg0KQWZ0ZXIgJG4gPSAxMCQgbWVhc3VyZW1lbnRzIHdpdGggc2FtcGxlIG1lYW4gJDYyJCBtcGggKHNsaWdodGx5IGFib3ZlIHByaW9yIG1lYW4pLCB0aGUgcG9zdGVyaW9yIGlzIG11Y2ggdGlnaHRlciAkXHRhdV9uIFxhcHByb3ggMC42MjckIG1waCkgYW5kIGNlbnRlcmVkIG5lYXIgJDYxLjk3JCBtcGguDQoNClRoZSBkYXRhIG1vdmVkIG91ciBlc3RpbWF0ZSBmcm9tICQ2MCQgdG93YXJkICQ2MiQsIGJ1dCBub3QgYWxsIHRoZSB3YXkgYmVjYXVzZSB0aGUgcHJpb3IgaGFkIHNvbWUgd2VpZ2h0Lg0KDQpJZiAkbiQgd2VyZSBsYXJnZXIsIHRoZSBwb3N0ZXJpb3Igd291bGQgYmUgZXZlbiB0aWdodGVyIGFuZCBpbmZsdWVuY2VkIG1vcmUgYnkgdGhlIGRhdGEuDQoNCioqRmluYWwgUmVzdWx0IGluIEJheWVzaWFuIEVzdGltYXRpb24gRm9ybSoqDQoNCkJheWVzJyBydWxlOg0KDQokJA0KcChTIFxtaWQgXGJhcntyfSkgXHByb3B0byBwKFxiYXJ7cn0gXG1pZCBTKSBcY2RvdCBwKFMpDQokJA0KDQokJA0KcChcYmFye3J9IFxtaWQgUykgPSBcZnJhY3sxfXtcc3FydHsyXHBpIHZ9fSBcZXhwXGxlZnRbLVxmcmFje1xiYXJ7cn0gLSBTKV4yfXsydn1ccmlnaHRdLCBccXVhZCB2ID0gXGZyYWN7XHNpZ21hXjJ9e259DQokJA0KDQokJA0KcChTKSA9IFxmcmFjezF9e1xzcXJ0ezJccGkgXHRhdV4yfX0gXGV4cFxsZWZ0Wy1cZnJhY3soUyAtIFxtdV8wKV4yfXsyXHRhdV4yfVxyaWdodF0NCiQkDQoNCk11bHRpcGx5aW5nIGFuZCBjb21wbGV0aW5nIHRoZSBzcXVhcmUgZ2l2ZXMgdGhlIHBvc3RlcmlvciBub3JtYWwgZGVyaXZlZCBhYm92ZS4gVGh1czoNCg0KJCQNClx0ZXh0e1Bvc3RlcmlvciBtZWFuIHNwZWVkIGVzdGltYXRlfSA9IDYxLjk3IFwgXHRleHR7bXBofQ0KJCQNCg0KJCQNCjk1XCUgXCBcdGV4dHtjcmVkaWJsZSBpbnRlcnZhbH0gXGFwcHJveCA2MS45NyBccG0gMS45NiBcdGltZXMgMC42MjcgXGFwcHJveCAoNjAuNzQsIDYzLjIwKSBcIFx0ZXh0e21waH0uDQokJA0KDQokJA0KXGJveGVkezYxLjk3IFwgXHRleHR7bXBofX0NCiQkDQoNCih3aXRoIHBvc3RlcmlvciBzdGQgJFxhcHByb3ggMC42MjckIG1waCkNCg0KDQoNClRoaXMgaXMgYSBjbG9zZWQtZm9ybSB1cGRhdGU6IHRoZSBwb3N0ZXJpb3IgbWVhbiBpcyBhIHdlaWdodGVkIGF2ZXJhZ2Ugb2YgcHJpb3IgbWVhbiBhbmQgZGF0YS4NCg0KDQoNCg0KIyBOYWl2ZSBCYXllcyBQcmVkaWN0aW9uDQoNCioqSWRlYSoqOiBBIHN1cGVydmlzZWQgY2xhc3NpZmljYXRpb24gbWV0aG9kIGJhc2VkIG9uIEJheWVz4oCZIHJ1bGUsIHdpdGggYSBgYG5haXZlJycgYXNzdW1wdGlvbjogZmVhdHVyZXMgYXJlIGNvbmRpdGlvbmFsbHkgaW5kZXBlbmRlbnQgZ2l2ZW4gdGhlIGNsYXNzIGxhYmVsfS4NCg0KRm9yIGEgZmVhdHVyZSB2ZWN0b3IkXG1hdGhiZntYfSA9IChYXzEsIFhfMiwgXGRvdHMsIFhfZCkkYW5kIGNsYXNzJEMgXGluIFx7MSwgXGRvdHMsIEtcfSQ6DQoNCkZyb20gQmF5ZXPigJkgcnVsZToNCg0KJCQNClAoQz1rfFxtYXRoYmZ7WH0pIFxwcm9wdG8gUChDPWspIFxwcm9kX3tqPTF9XmQgUChYX2p8Qz1rKQ0KJCQNCg0KVGhlIGNsYXNzIHdpdGggdGhlIGhpZ2hlc3QgcG9zdGVyaW9yIHByb2JhYmlsaXR5IGlzIGNob3Nlbi4NCg0KKipXaHkgYGBOYWl2ZScnPyoqDQoNClRoZSBjb25kaXRpb25hbCBpbmRlcGVuZGVuY2UgYXNzdW1wdGlvbiBpcyBvZnRlbiBmYWxzZSBpbiBwcmFjdGljZSwgYnV0IE5haXZlIEJheWVzIHN0aWxsIHBlcmZvcm1zIHdlbGwgaW4gbWFueSBhcHBsaWNhdGlvbnMgKHRleHQgY2xhc3NpZmljYXRpb24sIHNwYW0gZGV0ZWN0aW9uKSBiZWNhdXNlIHdlIG9ubHkgbmVlZCB0aGUgKipyYW5raW5nKiogb2YgcHJvYmFiaWxpdGllcyB0byBiZSBjb3JyZWN0IGZvciBjbGFzc2lmaWNhdGlvbi4NCg0KKipFeGFtcGxlOiBUZXh0IENsYXNzaWZpY2F0aW9uIChTcGFtIHZzLiBIYW0pKioNCg0KKipQcm9ibGVtKio6IENsYXNzaWZ5IGVtYWlsIGFzIHNwYW0gKCRTJCkgb3IgaGFtICgkSCQpIGJhc2VkIG9uIHdvcmQgY291bnRzLg0KDQoqKlRyYWluaW5nIGRhdGEqKjoNCg0KVm9jYWJ1bGFyeTogJFx7XHRleHR7YnV5fSwgXHRleHR7Y2hlYXB9LCBcdGV4dHttZWV0aW5nfSwgXHRleHR7ZnJlZX1cfSQNCg0KU3VwcG9zZSBpbiBzcGFtIGVtYWlsczoNCg0KJFAoXHRleHR7YnV5fXxTKSA9IDAuMyQsJFAoXHRleHR7Y2hlYXB9fFMpID0gMC4yJCwkUChcdGV4dHttZWV0aW5nfXxTKSA9IDAuMDEkLCRQKFx0ZXh0e2ZyZWV9fFMpID0gMC40JA0KDQpJbiBoYW0gZW1haWxzOlxcDQoNCiRQKFx0ZXh0e2J1eX18SCkgPSAwLjAxJCwkUChcdGV4dHtjaGVhcH18SCkgPSAwLjAxJCwkUChcdGV4dHttZWV0aW5nfXxIKSA9IDAuMiQsJFAoXHRleHR7ZnJlZX18SCkgPSAwLjA1JA0KDQpQcmlvcjokUChTKSA9IDAuNCQsJFAoSCkgPSAwLjYkLg0KDQpOZXcgZW1haWw6ICJidXkgY2hlYXAgbWVldGluZyIgKGlnbm9yZSBvdGhlciB3b3JkcykuDQoNCldlIGNvbXB1dGU6DQoNCiQkDQpQKFN8XHRleHR7YnV5LCBjaGVhcCwgbWVldGluZ30pIFxwcm9wdG8gMC40IFx0aW1lcyAoMC4zIFx0aW1lcyAwLjIgXHRpbWVzIDAuMDEpID0gMC40IFx0aW1lcyAwLjAwMDYgPSAwLjAwMDI0DQokJA0KDQokJA0KUChIfFx0ZXh0e2J1eSwgY2hlYXAsIG1lZXRpbmd9KSBccHJvcHRvIDAuNiBcdGltZXMgKDAuMDEgXHRpbWVzIDAuMDEgXHRpbWVzIDAuMikgPSAwLjYgXHRpbWVzIDAuMDAwMDIgPSAwLjAwMDAxMg0KJCQNCg0KU2luY2UkMC4wMDAyNCA+IDAuMDAwMDEyJCwgY2xhc3NpZnkgYXMgU1BBTX0uDQoNCioqUHJhY3RpY2FsIENvbnNpZGVyYXRpb25zKio6IA0KDQoqIEZvciBjb250aW51b3VzIGZlYXR1cmVzLCB1c2UgR2F1c3NpYW4gTmFpdmUgQmF5ZXMgKGFzc3VtZSAkUChYX2p8Qz1rKSQgaXMgR2F1c3NpYW4pLg0KDQoqIExhcGxhY2Ugc21vb3RoaW5nIGZvciBkaXNjcmV0ZSBmZWF0dXJlcyB0byBhdm9pZCB6ZXJvIHByb2JhYmlsaXRpZXMuDQoNCiogV29ya3Mgd2VsbCB3aXRoIGhpZ2gtZGltZW5zaW9uYWwgZGF0YSAoZS5nLiwgdGV4dCkuDQoNCg0KIyBTdW1tYXJ5DQoNCiogKipCYXllc+KAmSBSdWxlKio6IEZvdW5kYXRpb24gZm9yIHVwZGF0aW5nIGJlbGllZnMgd2l0aCBldmlkZW5jZS4NCg0KKiAqKlZhcmlhbnRzKio6IEV2ZW50cyAkXHJpZ2h0YXJyb3ckIGRpc2NyZXRlIHJhbmRvbSB2YXJpYWJsZXMgJFxyaWdodGFycm93JCBjb250aW51b3VzIHJhbmRvbSB2YXJpYWJsZXMgKHBhcmFtZXRlciBlc3RpbWF0aW9uKS4NCg0KKiAqKk5haXZlIEJheWVzKio6IFNpbXBsZSwgZmFzdCBjbGFzc2lmaWNhdGlvbiB1c2luZyBjb25kaXRpb25hbCBpbmRlcGVuZGVuY2UgYXNzdW1wdGlvbjsgd2lkZWx5IHVzZWQgaW4gdGV4dCBhbmFseXNpcyBhbmQgYmV5b25kLg0KDQoNClRoZSBwb3dlciBvZiBCYXllc2lhbiBtZXRob2RzIGxpZXMgaW4gY29tYmluaW5nIHByaW9yIGtub3dsZWRnZSB3aXRoIG9ic2VydmVkIGRhdGEsIG1ha2luZyB0aGVtIGVzc2VudGlhbCBmb3IgcHJlZGljdGl2ZSBhbmFseXNpcyBpbiB1bmNlcnRhaW4gZW52aXJvbm1lbnRzLg0KDQoNCiMgQXBwZW5kaXggDQoNCiMjIEJheWVzaWFuIERlcml2YXRpb246IFBvc3RlcmlvciBEaXN0cmlidXRpb24gZm9yIE5vcm1hbCBNZWFuDQoNCioqMS4gUHJvYmxlbSBzZXR1cCoqDQoNCldlIGhhdmU6DQoNCiQkDQpZIFxtaWQgXHRoZXRhIFw7IFxzaW0gXDsgXG1hdGhjYWx7Tn0oXHRoZXRhLCBcc2lnbWFfMF4yKSwgXHF1YWQgXHNpZ21hXzBeMiBcdGV4dHsga25vd259Lg0KJCQNCg0KJCQNClx0aGV0YSBcOyBcc2ltIFw7IFxtYXRoY2Fse059KFxtdV8wLCBcdGF1XzBeMiksIFxxdWFkIFxtdV8wLCBcdGF1XzBeMiBcdGV4dHsga25vd259Lg0KJCQNCg0KR2l2ZW4gZGF0YSAkWSA9IHkkLCB3ZSB3YW50IHRoZSBwb3N0ZXJpb3IgZGlzdHJpYnV0aW9uOg0KDQokJA0KcChcdGhldGEgXG1pZCBZID0geSkuDQokJA0KDQoqKjIuIEJheWVzJyBSdWxlKioNCg0KJCQNCnAoXHRoZXRhIFxtaWQgeSkgPSBcZnJhY3sgcCh5IFxtaWQgXHRoZXRhKSBcY2RvdCBwKFx0aGV0YSl9e3AoeSl9Lg0KJCQNCg0KVG8gbWFrZSAkcChcdGhldGEgXG1pZCB5KSQgYSB2YWxpZCBkZW5zaXR5LCBpLmUuLCAkXGludCBwKFx0aGV0YSB8IHkpID0gMSQsIGVxdWl2YWxlbnRseSwNCg0KDQokJA0KcCh5KSA9IFxpbnRfey1caW5mdHl9XntcaW5mdHl9IHAoeVxtaWQgXHRoZXRhKSBwKFx0aGV0YSlkXHRoZXRhLg0KJCQNCg0KDQpUaGUgbGlrZWxpaG9vZCAoZ2l2ZW4gJFx0aGV0YSQpOg0KDQokJA0KcCh5IFxtaWQgXHRoZXRhKSA9IFxmcmFjezF9e1xzcXJ0ezJccGkgXHNpZ21hXzBeMn19IFxleHBcbGVmdFsgLVxmcmFjeyh5IC0gXHRoZXRhKV4yfXsyXHNpZ21hXzBeMn0gXHJpZ2h0XS4NCiQkDQoNClRoZSBwcmlvcjoNCg0KJCQNCnAoXHRoZXRhKSA9IFxmcmFjezF9e1xzcXJ0ezJccGkgXHRhdV8wXjJ9fSBcZXhwXGxlZnRbIC1cZnJhY3soXHRoZXRhIC0gXG11XzApXjJ9ezJcdGF1XzBeMn0gXHJpZ2h0XS4NCiQkDQoNCioqMy4gQ29tYmluZSBleHBvbmVudHMqKg0KDQokJA0KcChcdGhldGEgXG1pZCB5KSBccHJvcHRvIFxleHBcbGVmdFsgLVxmcmFjeyh5IC0gXHRoZXRhKV4yfXsyXHNpZ21hXzBeMn0gLSBcZnJhY3soXHRoZXRhIC0gXG11XzApXjJ9ezJcdGF1XzBeMn0gXHJpZ2h0XS4NCiQkDQoNCkV4cGFuZCB0aGUgcXVhZHJhdGljcyBpbiAkXHRoZXRhJDoNCg0KRmlyc3QgdGVybToNCg0KJCQNCi1cZnJhY3soeSAtIFx0aGV0YSleMn17MlxzaWdtYV8wXjJ9ID0gLVxmcmFje1x0aGV0YV4yfXsyXHNpZ21hXzBeMn0gKyBcZnJhY3t5IFx0aGV0YX17XHNpZ21hXzBeMn0gLSBcZnJhY3t5XjJ9ezJcc2lnbWFfMF4yfS4NCiQkDQoNClNlY29uZCB0ZXJtOg0KDQokJA0KLVxmcmFjeyhcdGhldGEgLSBcbXVfMCleMn17Mlx0YXVfMF4yfSA9IC1cZnJhY3tcdGhldGFeMn17Mlx0YXVfMF4yfSArIFxmcmFje1xtdV8wIFx0aGV0YX17XHRhdV8wXjJ9IC0gXGZyYWN7XG11XzBeMn17Mlx0YXVfMF4yfS4NCiQkDQoNCioqNC4gQ29sbGVjdCB0ZXJtcyBpbiAkXHRoZXRhJCoqDQoNCg0KVGhlIGV4cG9uZW50IChpZ25vcmluZyBjb25zdGFudHMgbm90IGRlcGVuZGluZyBvbiAkXHRoZXRhJCk6DQoNClF1YWRyYXRpYyBpbiAkXHRoZXRhJDogIA0KDQokJA0KLVxmcmFjezF9ezJ9IFxsZWZ0KCBcZnJhY3sxfXtcc2lnbWFfMF4yfSArIFxmcmFjezF9e1x0YXVfMF4yfSBccmlnaHQpIFx0aGV0YV4yLg0KJCQNCg0KTGluZWFyIGluICRcdGhldGEkOiAgDQoNCiQkDQorIFxsZWZ0KCBcZnJhY3t5fXtcc2lnbWFfMF4yfSArIFxmcmFje1xtdV8wfXtcdGF1XzBeMn0gXHJpZ2h0KSBcdGhldGEuDQokJA0KDQpDb25zdGFudHMgaW4gJHksIFxtdV8wJDogIA0KDQokJA0KLVxmcmFje3leMn17MlxzaWdtYV8wXjJ9IC0gXGZyYWN7XG11XzBeMn17Mlx0YXVfMF4yfS4NCiQkDQoNCkRlZmluZToNCg0KJCQNCnYgPSBcbGVmdCggXGZyYWN7MX17XHNpZ21hXzBeMn0gKyBcZnJhY3sxfXtcdGF1XzBeMn0gXHJpZ2h0KV57LTF9LCBccXVhZCBcdGV4dHsocG9zdGVyaW9yIHZhcmlhbmNlKX0NCiQkDQoNCiQkDQptID0gdiBcY2RvdCBcbGVmdCggXGZyYWN7eX17XHNpZ21hXzBeMn0gKyBcZnJhY3tcbXVfMH17XHRhdV8wXjJ9IFxyaWdodCksIFxxdWFkIFx0ZXh0eyhwb3N0ZXJpb3IgbWVhbil9DQokJA0KDQoqKjUuIENvbXBsZXRlIHRoZSBzcXVhcmUqKg0KDQpMZXQgDQokJA0KQSA9IFxmcmFjezF9e1xzaWdtYV8wXjJ9ICsgXGZyYWN7MX17XHRhdV8wXjJ9LCBccXVhZCBCID0gXGZyYWN7eX17XHNpZ21hXzBeMn0gKyBcZnJhY3tcbXVfMH17XHRhdV8wXjJ9Lg0KJCQNCg0KVGhlIGV4cG9uZW50IGluICRcdGhldGEkIGlzOg0KDQokJA0KLVxmcmFjezF9ezJ9IEEgXHRoZXRhXjIgKyBCXHRoZXRhLg0KJCQNCg0KQ29tcGxldGUgdGhlIHNxdWFyZToNCg0KJCQNCi1cZnJhY3sxfXsyfSBBIFxsZWZ0WyBcdGhldGFeMiAtIFxmcmFjezJCfXtBfSBcdGhldGEgXHJpZ2h0XSANCj0gLVxmcmFjezF9ezJ9IEEgXGxlZnRbIFxsZWZ0KCBcdGhldGEgLSBcZnJhY3tCfXtBfSBccmlnaHQpXjIgLSBcZnJhY3tCXjJ9e0FeMn0gXHJpZ2h0XS4NCiQkDQoNClRodXM6DQokJA0KLVxmcmFjezF9ezJ9IEEgXHRoZXRhXjIgKyBCXHRoZXRhID0gLVxmcmFjezF9ezJ9IEEgXGxlZnQoIFx0aGV0YSAtIFxmcmFje0J9e0F9IFxyaWdodCleMiArIFxmcmFje0JeMn17MkF9Lg0KJCQNCg0KU286DQokJA0KcChcdGhldGEgXG1pZCB5KSBccHJvcHRvIFxleHBcbGVmdFsgLVxmcmFjezF9ezJ9IEEgXGxlZnQoIFx0aGV0YSAtIFxmcmFje0J9e0F9IFxyaWdodCleMiBccmlnaHRdLg0KJCQNCg0KKio2LiBJZGVudGlmeSBwb3N0ZXJpb3IgZGlzdHJpYnV0aW9uKioNCg0KVGhpcyBpcyBhIG5vcm1hbCBkZW5zaXR5Og0KDQokJA0KXHRoZXRhIFxtaWQgWSA9IHkgXHNpbSBcbWF0aGNhbHtOfVxsZWZ0KCBcZnJhY3tCfXtBfSwgXDsgQV57LTF9IFxyaWdodCksDQokJA0Kd2hlcmUgIA0KJCQNCkEgPSBcZnJhY3sxfXtcc2lnbWFfMF4yfSArIFxmcmFjezF9e1x0YXVfMF4yfSwgXHF1YWQgQiA9IFxmcmFje3l9e1xzaWdtYV8wXjJ9ICsgXGZyYWN7XG11XzB9e1x0YXVfMF4yfS4NCiQkDQoNCk1lYW46DQokJA0KXG11X3tcdGV4dHtwb3N0fX0gPSBcZnJhY3tCfXtBfSA9IFxmcmFjeyBcZnJhY3t5fXtcc2lnbWFfMF4yfSArIFxmcmFje1xtdV8wfXtcdGF1XzBeMn0gfXsgXGZyYWN7MX17XHNpZ21hXzBeMn0gKyBcZnJhY3sxfXtcdGF1XzBeMn0gfS4NCiQkDQoNClZhcmlhbmNlOg0KJCQNClxzaWdtYV97XHRleHR7cG9zdH19XjIgPSBcZnJhY3sxfXsgXGZyYWN7MX17XHNpZ21hXzBeMn0gKyBcZnJhY3sxfXtcdGF1XzBeMn0gfS4NCiQkDQoNCioqNy4gRmluYWwgZXhwcmVzc2lvbioqDQoNClVzaW5nIHByZWNpc2lvbiBub3RhdGlvbiAoJFxldGFfMCA9IDEvXHNpZ21hXzBeMiQsICRcbGFtYmRhXzAgPSAxL1x0YXVfMF4yJCk6DQoNCiQkDQpcdGhldGEgXG1pZCBZID0geSBcOyBcc2ltIFw7IFxtYXRoY2Fse059XGxlZnQoIFxmcmFje1xldGFfMCB5ICsgXGxhbWJkYV8wIFxtdV8wfXtcZXRhXzAgKyBcbGFtYmRhXzB9LCBcOyBcZnJhY3sxfXtcZXRhXzAgKyBcbGFtYmRhXzB9IFxyaWdodCkuDQokJA0KDQpJbiBvcmlnaW5hbCBub3RhdGlvbjoNCg0KJCQNClxib3hlZHtcdGhldGEgXG1pZCBZID0geSBcc2ltIFxtYXRoY2Fse059XGxlZnQoIFxmcmFje1xzaWdtYV8wXnstMn15ICsgXHRhdV8wXnstMn1cbXVfMH17XHNpZ21hXzBeey0yfSArIFx0YXVfMF57LTJ9fSwgXDsgKFxzaWdtYV8wXnstMn0gKyBcdGF1XzBeey0yfSleey0xfSBccmlnaHQpfS4NCiQkDQoNCg==