Author: Grace Strobbe


1. Initiate the Project


1.1. Dependencies

#This command loads required packages
library(ggplot2)

2. The Cave Molly and its Ancestors

To wrap our head around some of the basic observations that led Darwin to infer natural selection, we will spend a little bit of time with the cave molly. The cave molly (Poecilia mexicana) is a small species of livebearing fish that occurs in a couple of small caves in Southern Mexico. One of the caves, the Cueva Luna Azufre, has a wetted area of only 39 square-meters. Even though the available habitat is really small, there has been an isolated population of cave mollies in this cave for several thousand years. Interestingly, mollies also occur in adjacent surface habitats. In the picture below, you can see the a male and a female of the surface (top two pictures) and the cave form (bottom two pictures) side by side.


3. The Struggle for Existence

The first set of observations that led Darwin to infer the process of natural selection related to the imbalance of organisms’ reproductive power and limitations of resource availability. Quantifying the effective reproductive output and resource availability in nature can be difficult. However, what we can do is to measure proxies for these traits and then use simple mathematical models to test whether our predictions and inferences are valid. Here, we use exponential and logistic population growth models to explore whether there is really a struggle for existence in cave mollies.


3.1. Observation 1: Populations Have a Huge Reproductive Potential

Even large animals with long generation times have an incredible reproductive potential. Cave mollies—as many other cave organisms—have a comparatively low fecundity, and females only give birth to one or two fully developed young at a time. Life history analyses based on female longevity and fecundity have revealed that the average female gives birth to about 3 offspring over her life; not exactly what you would call huge reproductive potential, right? But in reality, it is not the reproductive potential of individuals that counts, but the reproductive potential of populations. To illustrate, we want you to model population growth for a hypothetical population of cave mollies. Specifically, use the code below to simulate and graph the population growth of an initial cave molly population of 2 individuals (the initial colonizers of the cave).

How many generations would it take for the population to grow to a million? Under what circumstances you might see population growth like this? Do you think Darwin’s observation that “species have great potential fertility” holds true for cave mollies?

#Choose an initial population size
N0 = 2

#Choose the average number of offspring
b = 3

#Choose a range of generations you want to estimate population size for
t = 0:15

#Calculate the population size for each generation
N = N0*b^t

#Merge the results of the simulation into a single table
final.results <- as.data.frame(cbind(t,N))

#You can view the results by just calling the data frame
final.results

#Plot the results, make sure you properly label the axes
ggplot(final.results, aes(x=t, y=N)) + 
  geom_point() + 
  xlab("Generation") + 
  ylab("Population size") +
  theme_classic()

The population would reach one million individuals by the twelfth generation of cave mollies, although the only way this population growth could occur is if there was enough living space and sufficient nutrients within the habitat. Darwin’s observation most likely holds true for the mollies as shown by the data and the growth in the fifth genration.


3.2. Observation 2: Natural Resources are Limited

Exponential growth only occurs in very specific circumstances. In a cave that is only the fraction of the size of a football field, you would obviously never find a cave molly population of a million. The logistic model more accurately describes population growth in nature. Based on our past analyses, we estimate the population growth coefficient (𝛌) to be around 1.3 and the carrying capacity (K) of the cave around 360 individuals.

How long would it take for the population to reach the carrying capacity if there were two initial colonizers? What do you think determines K for the population of cave mollies in the Cueva Luna Azufre?

#Choose an initial population size
N0 = 2
#Choose population growth rate
lamda = 1.3
#Choose a range of generations you want to estimate population size for
t = range(12,13,14,15)
#Choose a carrying capacity
K = 360
#Calculate the population size for each generation
N = (N0*K)/(N0+(K-N0)*exp(-lamda*t))
#Merge the results of the simulation into a single table
final.results <- as.data.frame(cbind(t,N))
#Use the ggplot function to plot the results, make sure you properly label the axes
ggplot(final.results, aes(x=t, y=N)) + 
  geom_point() + 
  xlab("Generation") + 
  ylab("Population") +
  theme_classic()

It will take fifteen generations for the population to reach its carrying capacity. The factors involved include amount of resources such as nutrients which would limit the number of mollies that are able to survive in the cave enviroment.


3.3. Where Do All the Missing Offspring Go?

Compare the two models (exponential and logistic) that were ran with the same initial parameters. What do the different outcomes mean for individual offspring that are born in any given generation? How might this discrepancy important in the context of evolution?

In the exponential model all the offspring are able to somehow survive and effectively reproduce which in reality is impossible and unrealistic. Whereas in the logistic model less of the offspring are able to survive which in turn means there is less chance for evolution to occur within the population. The main difference between the two models is the ability for evolution to occur within the population.


4. Individuals Vary in Their Traits

Another of Darwin’s key observation was just how variable individuals of the same species are. Let’s explore some of that variation in cave mollies. To do that, we first need to load some data into R. These data were collected as part of my dissertation and include the following variables: habitat (cave or surface), sex (male or female), standard length (in mm, from the snout to the caudal fin base), eye diameter (in mm), head length (in mm), head width (in mm), predorsal length (in mm, from the snout to the insertion of the dorsal fin), and gape width (in mm, from one corner of the mouth to the other).

#Use the read.csv function to import a dataset
morph.data <- read.csv("morphological_variation.csv", fileEncoding = 'UTF-8-BOM')
morph.data

4.1. Comparing Body Size Variation Within and Between Populations

A simple way to compare variation within and between populations is to plot a frequency histogram (which represents the raw counts) along with a density plot (which represents the approximated statistical distribution). You can generate a histogram with the geom_histogram() function and designate any trait you may want as the x axis. You can calculate the density with aes(y=..density..) within geom_histogram() and then plot it with geom_density(). Note that when you have more than two groups (in our case we have samples from a cave and a surface population), you can visualize them separately by designating a different color for each group in the aesthetics (fill=Habitat).

When you visualize body size variation in this manner what do you observe? Is there more variation within or between populations?

#Use the ggplot function to graph the histogram (see: http://www.sthda.com/english/wiki/ggplot2-histogram-plot-quick-start-guide-r-software-and-data-visualization)
ggplot(morph.data, aes(x=Standard.length, fill=Habitat)) + 
  geom_histogram(aes(y=..density..), position = "dodge") +
  geom_density(alpha=0.5)+
  xlab("Standard Length") + 
  ylab("Density") +
  theme_classic()
`stat_bin()` using `bins = 30`. Pick better value with
`binwidth`.

In the graph proves that there are similar size variations between the cave populations and the surface populations of the cave mollies. There seems to be more variation inside the population than outside of it.


4.2. Comparing Predorsal Length Variation Within and Between Populations

Let’s also compare a second trait, predorsal length. With the previous graph you hopefully saw how variable overall body size is within populations. If we want to compare other traits, we have to account for that. We want to know whether variation in predorsal length is due to variation in size (small fish have small predorsal lengths) or whether other patterns might be at play. To do so, we can calculate the residual predorsal length as from a regression between predorsal and standard length:

#Calculating regression line
fit1 <- lm(Predorsal.length ~ Standard.length, data = morph.data)

#Extract residuals and create a new variable res.predorsal in the morph.data data frame
morph.data$res.predorsal <- residuals(fit1)

You can then use the new variable to plot the residual predorsal length, which is corrected for body size:

##Use the ggplot function to graph the histogram and color data based on habitat
ggplot(morph.data, aes(x=Standard.length, fill=Habitat)) +
  geom_histogram(aes(y=..density..)) +
  geom_density(alpha=0.5)+
  xlab("Relative Predorsal Length") + 
  ylab("Density") +
  theme_classic()
`stat_bin()` using `bins = 30`. Pick better value with
`binwidth`.

When you plot relative predorsal length, what do you observe? How does variation in predorsal length vary within and between populations, and how does it compare to variation in standard length?

When plotting the relative pre-dorsal length we can observe that the length differs greatly between the cave and surface populations. It appears that as population density is lower, there is more variation, and it becomes more uniform as the density increases which is similar to standard length.


4.3. Comparing Eye Size Variation Within and Between Populations

Using the same approach as for predorsal variation, compare variation in relative eye diameter:

#Your code goes here
morph.data$relative.eye.size <- morph.data$Eye.diameter/morph.data$Standard.length

##Use the ggplot function to graph the histogram and color data based on habitat
ggplot(morph.data, aes(x=relative.eye.size, fill=Habitat)) + 
  geom_histogram(aes(y=..density..), position = "dodge") +
  geom_density(alpha=0.5) +
  theme_classic()
`stat_bin()` using `bins = 30`. Pick better value with
`binwidth`.

What do you observe? How does variation in eye diameter vary within and between populations, and how does it compare to variation in the other traits?

Eye size shows the most variability between populations, the diameter tends to be smaller in the cave population and larger in the surface populations. This difference in eye size is largley due to the fact that there is little light in in the caves so eyesight is an unimportant feature for those specific mollies. Therefor, it makes sense for other traits besides eyesight to be similar.


5. Variation in Traits is Heritable

An avid breeder of fancy pigeons, Darwin observed that specific traits are passed from parents to offspring, even though he had no clue how this might actually work (genetics was not really a thing yet). Even without an ability to conduct molecular genetic analyses, we can estimate heritability of traits by comparing the traits of offspring to the traits of the parents.

Let’s load some data that compares parent and offspring traits in cave mollies. To do this, we brought cave mollies into the lab and bred them under standardized conditions. Data represent the average trait values of the mother and father and of all offspring from a specific brood. The easiest way to compare parent and offspring traits is through a scatter plot, which we already used in Exercise 1. If a trait is heritable, we would expect to see a correlation between parent and offspring traits (e.g., parents with small eyes should have offspring with small eyes).

The following dataset includes measurements of parental and offspring standard length as well as eye size.

#Use the read.csv function to import a dataset
heritability <- read.csv("heritability.csv", fileEncoding = 'UTF-8-BOM')
heritability

5.1. Heritability of Standard Length

First, let us explore whether there is evidence for heritability in standard length.

What do you observe? Is standard length a heritable trait?

ggplot(heritability, aes(x=parent.standard.length, y=offspring.standard.length)) + 
  geom_point() + 
  geom_smooth(method = "lm") +
  xlab("Parent Standard Length") + 
  ylab("Offspring Standard Length") +
  theme_classic()
`geom_smooth()` using formula 'y ~ x'

The points on the graph appear unorganized and essentially meaningless therefore it appears that standard length is not a heritable trait amoung the cave mollies.


5.2. Heritability of Eye Size

Now let us explore whether there is any heritability in eye size. Remember, there is substantial variation in body size, and in such cases, we want to control for body size by calculating residual eye size first.

##Calculate residual eye sizes
morph.data$heritability$relative.parent.eye.size <- morph.data$parent.eye.size/morph.data$..parent.standard.length
morph.data$heritability$relative.offspring.eye.size <- morph.data$offspring.eye.size/morph.data$offspring.standard.length
Error in `$<-.data.frame`(`*tmp*`, heritability, value = list(relative.parent.eye.size = numeric(0),  : 
  replacement has 498 rows, data has 497

What do you observe? Is standard length a heritable trait?

There seems to be heritability based off the data points which seem to follow a trend line.


6. What Would Happen If…?

Imagine for a moment that smaller fish have a higher likelihood of survival in the cave. Would you expect evolution of body size upon cave colonization?

Imagine for a moment that fish with smaller eyes have a higher likelihood of survival in the cave. Would you expect evolution of eye size upon cave colonization? Justify your response.

If body smaller body size in the mollies increases the chances of survival I would imagine that body size would decrease within the population. The smaller the mollie, the more likely it is to produce offspring which in turn means the spread of genes for smaller body size and a decrease in individuals with larger body size. The same concept applies to smaller eye size as well, so if smaller eyes became more favorable there would be an increase in mollies with smaller eye size in the population.


7. Resources


7.1. Data References

The eye size data was published in the following paper. Other measurements are unpublished data by M. Tobler.


7.2 Resources You Consulted

Consulting additional resources to solve this assignment is absolutely allowed, but failure to disclose those resources is plagiarism. Please list any collaborators you worked with and resources you used below or state that you have not used any.

  • Rpub
LS0tCnRpdGxlOiAiSW50cm9kdWN0aW9uIHRvIFIgTm90ZWJvb2sgYW5kIERhcndpbidzIExvZ2ljIgpvdXRwdXQ6CiAgaHRtbF9ub3RlYm9vazoKICAgIGZpZ19jYXB0aW9uOiB5ZXMKICAgIHRvYzogeWVzCiAgICB0b2NfZGVwdGg6IDMKICAgIHRvY19mbG9hdDogeWVzCiAgcGRmX2RvY3VtZW50OgogICAgdG9jOiB5ZXMKICAgIHRvY19kZXB0aDogJzMnCiAgaHRtbF9kb2N1bWVudDoKICAgIGtlZXBfbWQ6IFRSVUUKLS0tCgojIyBBdXRob3I6IEdyYWNlIFN0cm9iYmUKCi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKIyAxLiBJbml0aWF0ZSB0aGUgUHJvamVjdAoKLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgojIyAxLjEuIERlcGVuZGVuY2llcwoKYGBge3IgbWVzc2FnZT1GQUxTRX0KI1RoaXMgY29tbWFuZCBsb2FkcyByZXF1aXJlZCBwYWNrYWdlcwpsaWJyYXJ5KGdncGxvdDIpCmBgYAoKLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgojIDIuIFRoZSBDYXZlIE1vbGx5IGFuZCBpdHMgQW5jZXN0b3JzCgpUbyB3cmFwIG91ciBoZWFkIGFyb3VuZCBzb21lIG9mIHRoZSBiYXNpYyBvYnNlcnZhdGlvbnMgdGhhdCBsZWQgRGFyd2luIHRvIGluZmVyIG5hdHVyYWwgc2VsZWN0aW9uLCB3ZSB3aWxsIHNwZW5kIGEgbGl0dGxlIGJpdCBvZiB0aW1lIHdpdGggdGhlIGNhdmUgbW9sbHkuIFRoZSBjYXZlIG1vbGx5ICgqUG9lY2lsaWEgbWV4aWNhbmEqKSBpcyBhIHNtYWxsIHNwZWNpZXMgb2YgbGl2ZWJlYXJpbmcgZmlzaCB0aGF0IG9jY3VycyBpbiBhIGNvdXBsZSBvZiBzbWFsbCBjYXZlcyBpbiBTb3V0aGVybiBNZXhpY28uIE9uZSBvZiB0aGUgY2F2ZXMsIHRoZSBDdWV2YSBMdW5hIEF6dWZyZSwgaGFzIGEgd2V0dGVkIGFyZWEgb2Ygb25seSAzOSBzcXVhcmUtbWV0ZXJzLiBFdmVuIHRob3VnaCB0aGUgYXZhaWxhYmxlIGhhYml0YXQgaXMgcmVhbGx5IHNtYWxsLCB0aGVyZSBoYXMgYmVlbiBhbiBpc29sYXRlZCBwb3B1bGF0aW9uIG9mIGNhdmUgbW9sbGllcyBpbiB0aGlzIGNhdmUgZm9yIHNldmVyYWwgdGhvdXNhbmQgeWVhcnMuIEludGVyZXN0aW5nbHksIG1vbGxpZXMgYWxzbyBvY2N1ciBpbiBhZGphY2VudCBzdXJmYWNlIGhhYml0YXRzLiBJbiB0aGUgcGljdHVyZSBiZWxvdywgeW91IGNhbiBzZWUgdGhlIGEgbWFsZSBhbmQgYSBmZW1hbGUgb2YgdGhlIHN1cmZhY2UgKHRvcCB0d28gcGljdHVyZXMpIGFuZCB0aGUgY2F2ZSBmb3JtIChib3R0b20gdHdvIHBpY3R1cmVzKSBzaWRlIGJ5IHNpZGUuCgohW10obW9sbGllcy5wbmcpCgotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCiMgMy4gVGhlIFN0cnVnZ2xlIGZvciBFeGlzdGVuY2UKClRoZSBmaXJzdCBzZXQgb2Ygb2JzZXJ2YXRpb25zIHRoYXQgbGVkIERhcndpbiB0byBpbmZlciB0aGUgcHJvY2VzcyBvZiBuYXR1cmFsIHNlbGVjdGlvbiByZWxhdGVkIHRvIHRoZSBpbWJhbGFuY2Ugb2Ygb3JnYW5pc21zJyByZXByb2R1Y3RpdmUgcG93ZXIgYW5kIGxpbWl0YXRpb25zIG9mIHJlc291cmNlIGF2YWlsYWJpbGl0eS4gUXVhbnRpZnlpbmcgdGhlIGVmZmVjdGl2ZSByZXByb2R1Y3RpdmUgb3V0cHV0IGFuZCByZXNvdXJjZSBhdmFpbGFiaWxpdHkgaW4gbmF0dXJlIGNhbiBiZSBkaWZmaWN1bHQuIEhvd2V2ZXIsIHdoYXQgd2UgY2FuIGRvIGlzIHRvIG1lYXN1cmUgcHJveGllcyBmb3IgdGhlc2UgdHJhaXRzIGFuZCB0aGVuIHVzZSBzaW1wbGUgbWF0aGVtYXRpY2FsIG1vZGVscyB0byB0ZXN0IHdoZXRoZXIgb3VyIHByZWRpY3Rpb25zIGFuZCBpbmZlcmVuY2VzIGFyZSB2YWxpZC4gSGVyZSwgd2UgdXNlIGV4cG9uZW50aWFsIGFuZCBsb2dpc3RpYyBwb3B1bGF0aW9uIGdyb3d0aCBtb2RlbHMgdG8gZXhwbG9yZSB3aGV0aGVyIHRoZXJlIGlzIHJlYWxseSBhIHN0cnVnZ2xlIGZvciBleGlzdGVuY2UgaW4gY2F2ZSBtb2xsaWVzLgoKLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgojIyAzLjEuIE9ic2VydmF0aW9uIDE6IFBvcHVsYXRpb25zIEhhdmUgYSBIdWdlIFJlcHJvZHVjdGl2ZSBQb3RlbnRpYWwKCkV2ZW4gbGFyZ2UgYW5pbWFscyB3aXRoIGxvbmcgZ2VuZXJhdGlvbiB0aW1lcyBoYXZlIGFuIGluY3JlZGlibGUgcmVwcm9kdWN0aXZlIHBvdGVudGlhbC4gQ2F2ZSBtb2xsaWVzLS0tYXMgbWFueSBvdGhlciBjYXZlIG9yZ2FuaXNtcy0tLWhhdmUgYSBjb21wYXJhdGl2ZWx5IGxvdyBmZWN1bmRpdHksIGFuZCBmZW1hbGVzIG9ubHkgZ2l2ZSBiaXJ0aCB0byBvbmUgb3IgdHdvIGZ1bGx5IGRldmVsb3BlZCB5b3VuZyBhdCBhIHRpbWUuIExpZmUgaGlzdG9yeSBhbmFseXNlcyBiYXNlZCBvbiBmZW1hbGUgbG9uZ2V2aXR5IGFuZCBmZWN1bmRpdHkgaGF2ZSByZXZlYWxlZCB0aGF0IHRoZSBhdmVyYWdlIGZlbWFsZSBnaXZlcyBiaXJ0aCB0byBhYm91dCAzIG9mZnNwcmluZyBvdmVyIGhlciBsaWZlOyBub3QgZXhhY3RseSB3aGF0IHlvdSB3b3VsZCBjYWxsIGh1Z2UgcmVwcm9kdWN0aXZlIHBvdGVudGlhbCwgcmlnaHQ/IEJ1dCBpbiByZWFsaXR5LCBpdCBpcyBub3QgdGhlIHJlcHJvZHVjdGl2ZSBwb3RlbnRpYWwgb2YgaW5kaXZpZHVhbHMgdGhhdCBjb3VudHMsIGJ1dCB0aGUgcmVwcm9kdWN0aXZlIHBvdGVudGlhbCBvZiBwb3B1bGF0aW9ucy4gVG8gaWxsdXN0cmF0ZSwgd2Ugd2FudCB5b3UgdG8gbW9kZWwgcG9wdWxhdGlvbiBncm93dGggZm9yIGEgaHlwb3RoZXRpY2FsIHBvcHVsYXRpb24gb2YgY2F2ZSBtb2xsaWVzLiBTcGVjaWZpY2FsbHksIHVzZSB0aGUgY29kZSBiZWxvdyB0byBzaW11bGF0ZSBhbmQgZ3JhcGggdGhlIHBvcHVsYXRpb24gZ3Jvd3RoIG9mIGFuIGluaXRpYWwgY2F2ZSBtb2xseSBwb3B1bGF0aW9uIG9mIDIgaW5kaXZpZHVhbHMgKHRoZSBpbml0aWFsIGNvbG9uaXplcnMgb2YgdGhlIGNhdmUpLgoKSG93IG1hbnkgZ2VuZXJhdGlvbnMgd291bGQgaXQgdGFrZSBmb3IgdGhlIHBvcHVsYXRpb24gdG8gZ3JvdyB0byBhIG1pbGxpb24/IFVuZGVyIHdoYXQgY2lyY3Vtc3RhbmNlcyB5b3UgbWlnaHQgc2VlIHBvcHVsYXRpb24gZ3Jvd3RoIGxpa2UgdGhpcz8gRG8geW91IHRoaW5rIERhcndpbidzIG9ic2VydmF0aW9uIHRoYXQgInNwZWNpZXMgaGF2ZSBncmVhdCBwb3RlbnRpYWwgZmVydGlsaXR5IiBob2xkcyB0cnVlIGZvciBjYXZlIG1vbGxpZXM/CgpgYGB7cn0KI0Nob29zZSBhbiBpbml0aWFsIHBvcHVsYXRpb24gc2l6ZQpOMCA9IDIKCiNDaG9vc2UgdGhlIGF2ZXJhZ2UgbnVtYmVyIG9mIG9mZnNwcmluZwpiID0gMwoKI0Nob29zZSBhIHJhbmdlIG9mIGdlbmVyYXRpb25zIHlvdSB3YW50IHRvIGVzdGltYXRlIHBvcHVsYXRpb24gc2l6ZSBmb3IKdCA9IDA6MTUKCiNDYWxjdWxhdGUgdGhlIHBvcHVsYXRpb24gc2l6ZSBmb3IgZWFjaCBnZW5lcmF0aW9uCk4gPSBOMCpiXnQKCiNNZXJnZSB0aGUgcmVzdWx0cyBvZiB0aGUgc2ltdWxhdGlvbiBpbnRvIGEgc2luZ2xlIHRhYmxlCmZpbmFsLnJlc3VsdHMgPC0gYXMuZGF0YS5mcmFtZShjYmluZCh0LE4pKQoKI1lvdSBjYW4gdmlldyB0aGUgcmVzdWx0cyBieSBqdXN0IGNhbGxpbmcgdGhlIGRhdGEgZnJhbWUKZmluYWwucmVzdWx0cwoKI1Bsb3QgdGhlIHJlc3VsdHMsIG1ha2Ugc3VyZSB5b3UgcHJvcGVybHkgbGFiZWwgdGhlIGF4ZXMKZ2dwbG90KGZpbmFsLnJlc3VsdHMsIGFlcyh4PXQsIHk9TikpICsgCiAgZ2VvbV9wb2ludCgpICsgCiAgeGxhYigiR2VuZXJhdGlvbiIpICsgCiAgeWxhYigiUG9wdWxhdGlvbiBzaXplIikgKwogIHRoZW1lX2NsYXNzaWMoKQoKYGBgCgpUaGUgcG9wdWxhdGlvbiB3b3VsZCByZWFjaCBvbmUgbWlsbGlvbiBpbmRpdmlkdWFscyBieSB0aGUgdHdlbGZ0aCBnZW5lcmF0aW9uIG9mIGNhdmUgbW9sbGllcywgYWx0aG91Z2ggdGhlIG9ubHkgd2F5IHRoaXMgcG9wdWxhdGlvbiBncm93dGggY291bGQgb2NjdXIgaXMgaWYgdGhlcmUgd2FzIGVub3VnaCBsaXZpbmcgc3BhY2UgYW5kIHN1ZmZpY2llbnQgbnV0cmllbnRzIHdpdGhpbiB0aGUgaGFiaXRhdC4gRGFyd2luJ3Mgb2JzZXJ2YXRpb24gbW9zdCBsaWtlbHkgaG9sZHMgdHJ1ZSBmb3IgdGhlIG1vbGxpZXMgYXMgc2hvd24gYnkgdGhlIGRhdGEgYW5kIHRoZSBncm93dGggaW4gdGhlIGZpZnRoIGdlbnJhdGlvbi4gIAoKLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgojIyAzLjIuIE9ic2VydmF0aW9uIDI6IE5hdHVyYWwgUmVzb3VyY2VzIGFyZSBMaW1pdGVkCgpFeHBvbmVudGlhbCBncm93dGggb25seSBvY2N1cnMgaW4gdmVyeSBzcGVjaWZpYyBjaXJjdW1zdGFuY2VzLiBJbiBhIGNhdmUgdGhhdCBpcyBvbmx5IHRoZSBmcmFjdGlvbiBvZiB0aGUgc2l6ZSBvZiBhIGZvb3RiYWxsIGZpZWxkLCB5b3Ugd291bGQgb2J2aW91c2x5IG5ldmVyIGZpbmQgYSBjYXZlIG1vbGx5IHBvcHVsYXRpb24gb2YgYSBtaWxsaW9uLiBUaGUgbG9naXN0aWMgbW9kZWwgbW9yZSBhY2N1cmF0ZWx5IGRlc2NyaWJlcyBwb3B1bGF0aW9uIGdyb3d0aCBpbiBuYXR1cmUuIEJhc2VkIG9uIG91ciBwYXN0IGFuYWx5c2VzLCB3ZSBlc3RpbWF0ZSB0aGUgcG9wdWxhdGlvbiBncm93dGggY29lZmZpY2llbnQgKPCdm4wpIHRvIGJlIGFyb3VuZCAxLjMgYW5kIHRoZSBjYXJyeWluZyBjYXBhY2l0eSAoKksqKSBvZiB0aGUgY2F2ZSBhcm91bmQgMzYwIGluZGl2aWR1YWxzLgoKSG93IGxvbmcgd291bGQgaXQgdGFrZSBmb3IgdGhlIHBvcHVsYXRpb24gdG8gcmVhY2ggdGhlIGNhcnJ5aW5nIGNhcGFjaXR5IGlmIHRoZXJlIHdlcmUgdHdvIGluaXRpYWwgY29sb25pemVycz8gV2hhdCBkbyB5b3UgdGhpbmsgZGV0ZXJtaW5lcyAqSyogZm9yIHRoZSBwb3B1bGF0aW9uIG9mIGNhdmUgbW9sbGllcyBpbiB0aGUgQ3VldmEgTHVuYSBBenVmcmU/CgpgYGB7cn0KI0Nob29zZSBhbiBpbml0aWFsIHBvcHVsYXRpb24gc2l6ZQpOMCA9IDIKI0Nob29zZSBwb3B1bGF0aW9uIGdyb3d0aCByYXRlCmxhbWRhID0gMS4zCiNDaG9vc2UgYSByYW5nZSBvZiBnZW5lcmF0aW9ucyB5b3Ugd2FudCB0byBlc3RpbWF0ZSBwb3B1bGF0aW9uIHNpemUgZm9yCnQgPSByYW5nZSgxMiwxMywxNCwxNSkKI0Nob29zZSBhIGNhcnJ5aW5nIGNhcGFjaXR5CksgPSAzNjAKI0NhbGN1bGF0ZSB0aGUgcG9wdWxhdGlvbiBzaXplIGZvciBlYWNoIGdlbmVyYXRpb24KTiA9IChOMCpLKS8oTjArKEstTjApKmV4cCgtbGFtZGEqdCkpCiNNZXJnZSB0aGUgcmVzdWx0cyBvZiB0aGUgc2ltdWxhdGlvbiBpbnRvIGEgc2luZ2xlIHRhYmxlCmZpbmFsLnJlc3VsdHMgPC0gYXMuZGF0YS5mcmFtZShjYmluZCh0LE4pKQojVXNlIHRoZSBnZ3Bsb3QgZnVuY3Rpb24gdG8gcGxvdCB0aGUgcmVzdWx0cywgbWFrZSBzdXJlIHlvdSBwcm9wZXJseSBsYWJlbCB0aGUgYXhlcwpnZ3Bsb3QoZmluYWwucmVzdWx0cywgYWVzKHg9dCwgeT1OKSkgKyAKICBnZW9tX3BvaW50KCkgKyAKICB4bGFiKCJHZW5lcmF0aW9uIikgKyAKICB5bGFiKCJQb3B1bGF0aW9uIikgKwogIHRoZW1lX2NsYXNzaWMoKQpgYGAKSXQgd2lsbCB0YWtlIGZpZnRlZW4gZ2VuZXJhdGlvbnMgZm9yIHRoZSBwb3B1bGF0aW9uIHRvIHJlYWNoIGl0cyBjYXJyeWluZyBjYXBhY2l0eS4gVGhlIGZhY3RvcnMgaW52b2x2ZWQgaW5jbHVkZSBhbW91bnQgb2YgcmVzb3VyY2VzIHN1Y2ggYXMgbnV0cmllbnRzIHdoaWNoIHdvdWxkIGxpbWl0IHRoZSBudW1iZXIgb2YgbW9sbGllcyB0aGF0IGFyZSBhYmxlIHRvIHN1cnZpdmUgaW4gdGhlIGNhdmUgZW52aXJvbWVudC4gCgotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCiMjIDMuMy4gV2hlcmUgRG8gQWxsIHRoZSBNaXNzaW5nIE9mZnNwcmluZyBHbz8KCkNvbXBhcmUgdGhlIHR3byBtb2RlbHMgKGV4cG9uZW50aWFsIGFuZCBsb2dpc3RpYykgdGhhdCB3ZXJlIHJhbiB3aXRoIHRoZSBzYW1lIGluaXRpYWwgcGFyYW1ldGVycy4gV2hhdCBkbyB0aGUgZGlmZmVyZW50IG91dGNvbWVzIG1lYW4gZm9yIGluZGl2aWR1YWwgb2Zmc3ByaW5nIHRoYXQgYXJlIGJvcm4gaW4gYW55IGdpdmVuIGdlbmVyYXRpb24/IEhvdyBtaWdodCB0aGlzIGRpc2NyZXBhbmN5IGltcG9ydGFudCBpbiB0aGUgY29udGV4dCBvZiBldm9sdXRpb24/CgpJbiB0aGUgZXhwb25lbnRpYWwgbW9kZWwgYWxsIHRoZSBvZmZzcHJpbmcgYXJlIGFibGUgdG8gc29tZWhvdyBzdXJ2aXZlIGFuZCBlZmZlY3RpdmVseSByZXByb2R1Y2Ugd2hpY2ggaW4gcmVhbGl0eSBpcyBpbXBvc3NpYmxlIGFuZCB1bnJlYWxpc3RpYy4gV2hlcmVhcyBpbiB0aGUgbG9naXN0aWMgbW9kZWwgbGVzcyBvZiB0aGUgb2Zmc3ByaW5nIGFyZSBhYmxlIHRvIHN1cnZpdmUgd2hpY2ggaW4gdHVybiBtZWFucyB0aGVyZSBpcyBsZXNzIGNoYW5jZSBmb3IgZXZvbHV0aW9uIHRvIG9jY3VyIHdpdGhpbiB0aGUgcG9wdWxhdGlvbi4gVGhlIG1haW4gZGlmZmVyZW5jZSBiZXR3ZWVuIHRoZSB0d28gbW9kZWxzIGlzIHRoZSBhYmlsaXR5IGZvciBldm9sdXRpb24gdG8gb2NjdXIgd2l0aGluIHRoZSBwb3B1bGF0aW9uLiAKCi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKIyA0LiBJbmRpdmlkdWFscyBWYXJ5IGluIFRoZWlyIFRyYWl0cwoKQW5vdGhlciBvZiBEYXJ3aW4ncyBrZXkgb2JzZXJ2YXRpb24gd2FzIGp1c3QgaG93IHZhcmlhYmxlIGluZGl2aWR1YWxzIG9mIHRoZSBzYW1lIHNwZWNpZXMgYXJlLiBMZXQncyBleHBsb3JlIHNvbWUgb2YgdGhhdCB2YXJpYXRpb24gaW4gY2F2ZSBtb2xsaWVzLiBUbyBkbyB0aGF0LCB3ZSBmaXJzdCBuZWVkIHRvIGxvYWQgc29tZSBkYXRhIGludG8gUi4gVGhlc2UgZGF0YSB3ZXJlIGNvbGxlY3RlZCBhcyBwYXJ0IG9mIG15IGRpc3NlcnRhdGlvbiBhbmQgaW5jbHVkZSB0aGUgZm9sbG93aW5nIHZhcmlhYmxlczogaGFiaXRhdCAoY2F2ZSBvciBzdXJmYWNlKSwgc2V4IChtYWxlIG9yIGZlbWFsZSksIHN0YW5kYXJkIGxlbmd0aCAoaW4gbW0sIGZyb20gdGhlIHNub3V0IHRvIHRoZSBjYXVkYWwgZmluIGJhc2UpLCBleWUgZGlhbWV0ZXIgKGluIG1tKSwgaGVhZCBsZW5ndGggKGluIG1tKSwgaGVhZCB3aWR0aCAoaW4gbW0pLCBwcmVkb3JzYWwgbGVuZ3RoIChpbiBtbSwgZnJvbSB0aGUgc25vdXQgdG8gdGhlIGluc2VydGlvbiBvZiB0aGUgZG9yc2FsIGZpbiksIGFuZCBnYXBlIHdpZHRoIChpbiBtbSwgZnJvbSBvbmUgY29ybmVyIG9mIHRoZSBtb3V0aCB0byB0aGUgb3RoZXIpLgoKYGBge3J9CiNVc2UgdGhlIHJlYWQuY3N2IGZ1bmN0aW9uIHRvIGltcG9ydCBhIGRhdGFzZXQKbW9ycGguZGF0YSA8LSByZWFkLmNzdigibW9ycGhvbG9naWNhbF92YXJpYXRpb24uY3N2IiwgZmlsZUVuY29kaW5nID0gJ1VURi04LUJPTScpCm1vcnBoLmRhdGEKYGBgCgotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCiMjIDQuMS4gQ29tcGFyaW5nIEJvZHkgU2l6ZSBWYXJpYXRpb24gV2l0aGluIGFuZCBCZXR3ZWVuIFBvcHVsYXRpb25zCgpBIHNpbXBsZSB3YXkgdG8gY29tcGFyZSB2YXJpYXRpb24gd2l0aGluIGFuZCBiZXR3ZWVuIHBvcHVsYXRpb25zIGlzIHRvIHBsb3QgYSBmcmVxdWVuY3kgaGlzdG9ncmFtICh3aGljaCByZXByZXNlbnRzIHRoZSByYXcgY291bnRzKSBhbG9uZyB3aXRoIGEgZGVuc2l0eSBwbG90ICh3aGljaCByZXByZXNlbnRzIHRoZSBhcHByb3hpbWF0ZWQgc3RhdGlzdGljYWwgZGlzdHJpYnV0aW9uKS4gWW91IGNhbiBnZW5lcmF0ZSBhIGhpc3RvZ3JhbSB3aXRoIHRoZSBgZ2VvbV9oaXN0b2dyYW0oKWAgZnVuY3Rpb24gYW5kIGRlc2lnbmF0ZSBhbnkgdHJhaXQgeW91IG1heSB3YW50IGFzIHRoZSB4IGF4aXMuIFlvdSBjYW4gY2FsY3VsYXRlIHRoZSBkZW5zaXR5IHdpdGggYGFlcyh5PS4uZGVuc2l0eS4uKWAgd2l0aGluIGBnZW9tX2hpc3RvZ3JhbSgpYCBhbmQgdGhlbiBwbG90IGl0IHdpdGggYGdlb21fZGVuc2l0eSgpYC4gTm90ZSB0aGF0IHdoZW4geW91IGhhdmUgbW9yZSB0aGFuIHR3byBncm91cHMgKGluIG91ciBjYXNlIHdlIGhhdmUgc2FtcGxlcyBmcm9tIGEgY2F2ZSBhbmQgYSBzdXJmYWNlIHBvcHVsYXRpb24pLCB5b3UgY2FuIHZpc3VhbGl6ZSB0aGVtIHNlcGFyYXRlbHkgYnkgZGVzaWduYXRpbmcgYSBkaWZmZXJlbnQgY29sb3IgZm9yIGVhY2ggZ3JvdXAgaW4gdGhlIGFlc3RoZXRpY3MgKGBmaWxsPUhhYml0YXRgKS4KCldoZW4geW91IHZpc3VhbGl6ZSBib2R5IHNpemUgdmFyaWF0aW9uIGluIHRoaXMgbWFubmVyIHdoYXQgZG8geW91IG9ic2VydmU/IElzIHRoZXJlIG1vcmUgdmFyaWF0aW9uIHdpdGhpbiBvciBiZXR3ZWVuIHBvcHVsYXRpb25zPwoKYGBge3IgbWVzc2FnZT1GQUxTRX0KI1VzZSB0aGUgZ2dwbG90IGZ1bmN0aW9uIHRvIGdyYXBoIHRoZSBoaXN0b2dyYW0gKHNlZTogaHR0cDovL3d3dy5zdGhkYS5jb20vZW5nbGlzaC93aWtpL2dncGxvdDItaGlzdG9ncmFtLXBsb3QtcXVpY2stc3RhcnQtZ3VpZGUtci1zb2Z0d2FyZS1hbmQtZGF0YS12aXN1YWxpemF0aW9uKQpnZ3Bsb3QobW9ycGguZGF0YSwgYWVzKHg9U3RhbmRhcmQubGVuZ3RoLCBmaWxsPUhhYml0YXQpKSArIAogIGdlb21faGlzdG9ncmFtKGFlcyh5PS4uZGVuc2l0eS4uKSwgcG9zaXRpb24gPSAiZG9kZ2UiKSArCiAgZ2VvbV9kZW5zaXR5KGFscGhhPTAuNSkrCiAgeGxhYigiU3RhbmRhcmQgTGVuZ3RoIikgKyAKICB5bGFiKCJEZW5zaXR5IikgKwogIHRoZW1lX2NsYXNzaWMoKQpgYGAKCkluIHRoZSBncmFwaCBwcm92ZXMgdGhhdCB0aGVyZSBhcmUgc2ltaWxhciBzaXplIHZhcmlhdGlvbnMgYmV0d2VlbiB0aGUgY2F2ZSBwb3B1bGF0aW9ucyBhbmQgdGhlIHN1cmZhY2UgcG9wdWxhdGlvbnMgb2YgdGhlIGNhdmUgbW9sbGllcy4gVGhlcmUgc2VlbXMgdG8gYmUgbW9yZSB2YXJpYXRpb24gaW5zaWRlIHRoZSBwb3B1bGF0aW9uIHRoYW4gb3V0c2lkZSBvZiBpdC4gCgotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCiMjIDQuMi4gQ29tcGFyaW5nIFByZWRvcnNhbCBMZW5ndGggVmFyaWF0aW9uIFdpdGhpbiBhbmQgQmV0d2VlbiBQb3B1bGF0aW9ucwoKTGV0J3MgYWxzbyBjb21wYXJlIGEgc2Vjb25kIHRyYWl0LCBwcmVkb3JzYWwgbGVuZ3RoLiBXaXRoIHRoZSBwcmV2aW91cyBncmFwaCB5b3UgaG9wZWZ1bGx5IHNhdyBob3cgdmFyaWFibGUgb3ZlcmFsbCBib2R5IHNpemUgaXMgd2l0aGluIHBvcHVsYXRpb25zLiBJZiB3ZSB3YW50IHRvIGNvbXBhcmUgb3RoZXIgdHJhaXRzLCB3ZSBoYXZlIHRvIGFjY291bnQgZm9yIHRoYXQuIFdlIHdhbnQgdG8ga25vdyB3aGV0aGVyIHZhcmlhdGlvbiBpbiBwcmVkb3JzYWwgbGVuZ3RoIGlzIGR1ZSB0byB2YXJpYXRpb24gaW4gc2l6ZSAoc21hbGwgZmlzaCBoYXZlIHNtYWxsIHByZWRvcnNhbCBsZW5ndGhzKSBvciB3aGV0aGVyIG90aGVyIHBhdHRlcm5zIG1pZ2h0IGJlIGF0IHBsYXkuIFRvIGRvIHNvLCB3ZSBjYW4gY2FsY3VsYXRlIHRoZSByZXNpZHVhbCBwcmVkb3JzYWwgbGVuZ3RoIGFzIGZyb20gYSByZWdyZXNzaW9uIGJldHdlZW4gcHJlZG9yc2FsIGFuZCBzdGFuZGFyZCBsZW5ndGg6CgpgYGB7cn0KI0NhbGN1bGF0aW5nIHJlZ3Jlc3Npb24gbGluZQpmaXQxIDwtIGxtKFByZWRvcnNhbC5sZW5ndGggfiBTdGFuZGFyZC5sZW5ndGgsIGRhdGEgPSBtb3JwaC5kYXRhKQoKI0V4dHJhY3QgcmVzaWR1YWxzIGFuZCBjcmVhdGUgYSBuZXcgdmFyaWFibGUgcmVzLnByZWRvcnNhbCBpbiB0aGUgbW9ycGguZGF0YSBkYXRhIGZyYW1lCm1vcnBoLmRhdGEkcmVzLnByZWRvcnNhbCA8LSByZXNpZHVhbHMoZml0MSkKYGBgCgpZb3UgY2FuIHRoZW4gdXNlIHRoZSBuZXcgdmFyaWFibGUgdG8gcGxvdCB0aGUgcmVzaWR1YWwgcHJlZG9yc2FsIGxlbmd0aCwgd2hpY2ggaXMgY29ycmVjdGVkIGZvciBib2R5IHNpemU6CgpgYGB7ciBtZXNzYWdlPUZBTFNFfQojI1VzZSB0aGUgZ2dwbG90IGZ1bmN0aW9uIHRvIGdyYXBoIHRoZSBoaXN0b2dyYW0gYW5kIGNvbG9yIGRhdGEgYmFzZWQgb24gaGFiaXRhdApnZ3Bsb3QobW9ycGguZGF0YSwgYWVzKHg9U3RhbmRhcmQubGVuZ3RoLCBmaWxsPUhhYml0YXQpKSArCiAgZ2VvbV9oaXN0b2dyYW0oYWVzKHk9Li5kZW5zaXR5Li4pKSArCiAgZ2VvbV9kZW5zaXR5KGFscGhhPTAuNSkrCiAgeGxhYigiUmVsYXRpdmUgUHJlZG9yc2FsIExlbmd0aCIpICsgCiAgeWxhYigiRGVuc2l0eSIpICsKICB0aGVtZV9jbGFzc2ljKCkKYGBgCgpXaGVuIHlvdSBwbG90IHJlbGF0aXZlIHByZWRvcnNhbCBsZW5ndGgsIHdoYXQgZG8geW91IG9ic2VydmU/IEhvdyBkb2VzIHZhcmlhdGlvbiBpbiBwcmVkb3JzYWwgbGVuZ3RoIHZhcnkgd2l0aGluIGFuZCBiZXR3ZWVuIHBvcHVsYXRpb25zLCBhbmQgaG93IGRvZXMgaXQgY29tcGFyZSB0byB2YXJpYXRpb24gaW4gc3RhbmRhcmQgbGVuZ3RoPwoKV2hlbiBwbG90dGluZyB0aGUgcmVsYXRpdmUgcHJlLWRvcnNhbCBsZW5ndGggd2UgY2FuIG9ic2VydmUgdGhhdCB0aGUgbGVuZ3RoIGRpZmZlcnMgZ3JlYXRseSBiZXR3ZWVuIHRoZSBjYXZlIGFuZCBzdXJmYWNlIHBvcHVsYXRpb25zLiBJdCBhcHBlYXJzIHRoYXQgYXMgcG9wdWxhdGlvbiBkZW5zaXR5IGlzIGxvd2VyLCB0aGVyZSBpcyBtb3JlIHZhcmlhdGlvbiwgYW5kIGl0IGJlY29tZXMgbW9yZSB1bmlmb3JtIGFzIHRoZSBkZW5zaXR5IGluY3JlYXNlcyB3aGljaCBpcyBzaW1pbGFyIHRvIHN0YW5kYXJkIGxlbmd0aC4gCgotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCiMjIDQuMy4gQ29tcGFyaW5nIEV5ZSBTaXplIFZhcmlhdGlvbiBXaXRoaW4gYW5kIEJldHdlZW4gUG9wdWxhdGlvbnMKClVzaW5nIHRoZSBzYW1lIGFwcHJvYWNoIGFzIGZvciBwcmVkb3JzYWwgdmFyaWF0aW9uLCBjb21wYXJlIHZhcmlhdGlvbiBpbiByZWxhdGl2ZSBleWUgZGlhbWV0ZXI6CgpgYGB7ciBtZXNzYWdlPUZBTFNFfQojWW91ciBjb2RlIGdvZXMgaGVyZQptb3JwaC5kYXRhJHJlbGF0aXZlLmV5ZS5zaXplIDwtIG1vcnBoLmRhdGEkRXllLmRpYW1ldGVyL21vcnBoLmRhdGEkU3RhbmRhcmQubGVuZ3RoCgojI1VzZSB0aGUgZ2dwbG90IGZ1bmN0aW9uIHRvIGdyYXBoIHRoZSBoaXN0b2dyYW0gYW5kIGNvbG9yIGRhdGEgYmFzZWQgb24gaGFiaXRhdApnZ3Bsb3QobW9ycGguZGF0YSwgYWVzKHg9cmVsYXRpdmUuZXllLnNpemUsIGZpbGw9SGFiaXRhdCkpICsgCiAgZ2VvbV9oaXN0b2dyYW0oYWVzKHk9Li5kZW5zaXR5Li4pLCBwb3NpdGlvbiA9ICJkb2RnZSIpICsKICBnZW9tX2RlbnNpdHkoYWxwaGE9MC41KSArCiAgdGhlbWVfY2xhc3NpYygpCmBgYAoKV2hhdCBkbyB5b3Ugb2JzZXJ2ZT8gSG93IGRvZXMgdmFyaWF0aW9uIGluIGV5ZSBkaWFtZXRlciB2YXJ5IHdpdGhpbiBhbmQgYmV0d2VlbiBwb3B1bGF0aW9ucywgYW5kIGhvdyBkb2VzIGl0IGNvbXBhcmUgdG8gdmFyaWF0aW9uIGluIHRoZSBvdGhlciB0cmFpdHM/CgpFeWUgc2l6ZSBzaG93cyB0aGUgbW9zdCB2YXJpYWJpbGl0eSBiZXR3ZWVuIHBvcHVsYXRpb25zLCB0aGUgZGlhbWV0ZXIgdGVuZHMgdG8gYmUgc21hbGxlciBpbiB0aGUgY2F2ZSBwb3B1bGF0aW9uIGFuZCBsYXJnZXIgaW4gdGhlIHN1cmZhY2UgcG9wdWxhdGlvbnMuIFRoaXMgZGlmZmVyZW5jZSBpbiBleWUgc2l6ZSBpcyBsYXJnbGV5IGR1ZSB0byB0aGUgZmFjdCB0aGF0IHRoZXJlIGlzIGxpdHRsZSBsaWdodCBpbiBpbiB0aGUgY2F2ZXMgc28gZXllc2lnaHQgaXMgYW4gdW5pbXBvcnRhbnQgZmVhdHVyZSBmb3IgdGhvc2Ugc3BlY2lmaWMgbW9sbGllcy4gVGhlcmVmb3IsIGl0IG1ha2VzIHNlbnNlIGZvciBvdGhlciB0cmFpdHMgYmVzaWRlcyBleWVzaWdodCB0byBiZSBzaW1pbGFyLiAKCi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKIyA1LiBWYXJpYXRpb24gaW4gVHJhaXRzIGlzIEhlcml0YWJsZQoKQW4gYXZpZCBicmVlZGVyIG9mIGZhbmN5IHBpZ2VvbnMsIERhcndpbiBvYnNlcnZlZCB0aGF0IHNwZWNpZmljIHRyYWl0cyBhcmUgcGFzc2VkIGZyb20gcGFyZW50cyB0byBvZmZzcHJpbmcsIGV2ZW4gdGhvdWdoIGhlIGhhZCBubyBjbHVlIGhvdyB0aGlzIG1pZ2h0IGFjdHVhbGx5IHdvcmsgKGdlbmV0aWNzIHdhcyBub3QgcmVhbGx5IGEgdGhpbmcgeWV0KS4gRXZlbiB3aXRob3V0IGFuIGFiaWxpdHkgdG8gY29uZHVjdCBtb2xlY3VsYXIgZ2VuZXRpYyBhbmFseXNlcywgd2UgY2FuIGVzdGltYXRlIGhlcml0YWJpbGl0eSBvZiB0cmFpdHMgYnkgY29tcGFyaW5nIHRoZSB0cmFpdHMgb2Ygb2Zmc3ByaW5nIHRvIHRoZSB0cmFpdHMgb2YgdGhlIHBhcmVudHMuCgpMZXQncyBsb2FkIHNvbWUgZGF0YSB0aGF0IGNvbXBhcmVzIHBhcmVudCBhbmQgb2Zmc3ByaW5nIHRyYWl0cyBpbiBjYXZlIG1vbGxpZXMuIFRvIGRvIHRoaXMsIHdlIGJyb3VnaHQgY2F2ZSBtb2xsaWVzIGludG8gdGhlIGxhYiBhbmQgYnJlZCB0aGVtIHVuZGVyIHN0YW5kYXJkaXplZCBjb25kaXRpb25zLiBEYXRhIHJlcHJlc2VudCB0aGUgYXZlcmFnZSB0cmFpdCB2YWx1ZXMgb2YgdGhlIG1vdGhlciBhbmQgZmF0aGVyIGFuZCBvZiBhbGwgb2Zmc3ByaW5nIGZyb20gYSBzcGVjaWZpYyBicm9vZC4gVGhlIGVhc2llc3Qgd2F5IHRvIGNvbXBhcmUgcGFyZW50IGFuZCBvZmZzcHJpbmcgdHJhaXRzIGlzIHRocm91Z2ggYSBzY2F0dGVyIHBsb3QsIHdoaWNoIHdlIGFscmVhZHkgdXNlZCBpbiBFeGVyY2lzZSAxLiBJZiBhIHRyYWl0IGlzIGhlcml0YWJsZSwgd2Ugd291bGQgZXhwZWN0IHRvIHNlZSBhIGNvcnJlbGF0aW9uIGJldHdlZW4gcGFyZW50IGFuZCBvZmZzcHJpbmcgdHJhaXRzIChlLmcuLCBwYXJlbnRzIHdpdGggc21hbGwgZXllcyBzaG91bGQgaGF2ZSBvZmZzcHJpbmcgd2l0aCBzbWFsbCBleWVzKS4KClRoZSBmb2xsb3dpbmcgZGF0YXNldCBpbmNsdWRlcyBtZWFzdXJlbWVudHMgb2YgcGFyZW50YWwgYW5kIG9mZnNwcmluZyBzdGFuZGFyZCBsZW5ndGggYXMgd2VsbCBhcyBleWUgc2l6ZS4KCmBgYHtyfQojVXNlIHRoZSByZWFkLmNzdiBmdW5jdGlvbiB0byBpbXBvcnQgYSBkYXRhc2V0Cmhlcml0YWJpbGl0eSA8LSByZWFkLmNzdigiaGVyaXRhYmlsaXR5LmNzdiIsIGZpbGVFbmNvZGluZyA9ICdVVEYtOC1CT00nKQpoZXJpdGFiaWxpdHkKYGBgCgotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCiMjIDUuMS4gSGVyaXRhYmlsaXR5IG9mIFN0YW5kYXJkIExlbmd0aAoKRmlyc3QsIGxldCB1cyBleHBsb3JlIHdoZXRoZXIgdGhlcmUgaXMgZXZpZGVuY2UgZm9yIGhlcml0YWJpbGl0eSBpbiBzdGFuZGFyZCBsZW5ndGguCgpXaGF0IGRvIHlvdSBvYnNlcnZlPyBJcyBzdGFuZGFyZCBsZW5ndGggYSBoZXJpdGFibGUgdHJhaXQ/CgpgYGB7ciBtZXNzYWdlPUZBTFNFfQpnZ3Bsb3QoaGVyaXRhYmlsaXR5LCBhZXMoeD1wYXJlbnQuc3RhbmRhcmQubGVuZ3RoLCB5PW9mZnNwcmluZy5zdGFuZGFyZC5sZW5ndGgpKSArIAogIGdlb21fcG9pbnQoKSArIAogIGdlb21fc21vb3RoKG1ldGhvZCA9ICJsbSIpICsKICB4bGFiKCJQYXJlbnQgU3RhbmRhcmQgTGVuZ3RoIikgKyAKICB5bGFiKCJPZmZzcHJpbmcgU3RhbmRhcmQgTGVuZ3RoIikgKwogIHRoZW1lX2NsYXNzaWMoKQpgYGAKClRoZSBwb2ludHMgb24gdGhlIGdyYXBoIGFwcGVhciB1bm9yZ2FuaXplZCBhbmQgZXNzZW50aWFsbHkgbWVhbmluZ2xlc3MgdGhlcmVmb3JlIGl0IGFwcGVhcnMgdGhhdCBzdGFuZGFyZCBsZW5ndGggaXMgbm90IGEgaGVyaXRhYmxlIHRyYWl0IGFtb3VuZyB0aGUgY2F2ZSBtb2xsaWVzLiAKCi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKIyMgNS4yLiBIZXJpdGFiaWxpdHkgb2YgRXllIFNpemUKCk5vdyBsZXQgdXMgZXhwbG9yZSB3aGV0aGVyIHRoZXJlIGlzIGFueSBoZXJpdGFiaWxpdHkgaW4gZXllIHNpemUuIFJlbWVtYmVyLCB0aGVyZSBpcyBzdWJzdGFudGlhbCB2YXJpYXRpb24gaW4gYm9keSBzaXplLCBhbmQgaW4gc3VjaCBjYXNlcywgd2Ugd2FudCB0byBjb250cm9sIGZvciBib2R5IHNpemUgYnkgY2FsY3VsYXRpbmcgcmVzaWR1YWwgZXllIHNpemUgZmlyc3QuCgpgYGB7ciBtZXNzYWdlPUZBTFNFfQojI0NhbGN1bGF0ZSByZXNpZHVhbCBleWUgc2l6ZXMKbW9ycGguZGF0YSRoZXJpdGFiaWxpdHkkcmVsYXRpdmUucGFyZW50LmV5ZS5zaXplIDwtIG1vcnBoLmRhdGEkcGFyZW50LmV5ZS5zaXplL21vcnBoLmRhdGEkLi5wYXJlbnQuc3RhbmRhcmQubGVuZ3RoCm1vcnBoLmRhdGEkaGVyaXRhYmlsaXR5JHJlbGF0aXZlLm9mZnNwcmluZy5leWUuc2l6ZSA8LSBtb3JwaC5kYXRhJG9mZnNwcmluZy5leWUuc2l6ZS9tb3JwaC5kYXRhJG9mZnNwcmluZy5zdGFuZGFyZC5sZW5ndGgKCgojUGxvdCB0aGUgcmVzdWx0cwpnZ3Bsb3QoPykKYGBgCgpXaGF0IGRvIHlvdSBvYnNlcnZlPyBJcyBzdGFuZGFyZCBsZW5ndGggYSBoZXJpdGFibGUgdHJhaXQ/CgpUaGVyZSBzZWVtcyB0byBiZSBoZXJpdGFiaWxpdHkgYmFzZWQgb2ZmIHRoZSBkYXRhIHBvaW50cyB3aGljaCBzZWVtIHRvIGZvbGxvdyBhIHRyZW5kIGxpbmUuIAoKLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgojIDYuIFdoYXQgV291bGQgSGFwcGVuIElmLi4uPwoKSW1hZ2luZSBmb3IgYSBtb21lbnQgdGhhdCBzbWFsbGVyIGZpc2ggaGF2ZSBhIGhpZ2hlciBsaWtlbGlob29kIG9mIHN1cnZpdmFsIGluIHRoZSBjYXZlLiBXb3VsZCB5b3UgZXhwZWN0IGV2b2x1dGlvbiBvZiBib2R5IHNpemUgdXBvbiBjYXZlIGNvbG9uaXphdGlvbj8KCkltYWdpbmUgZm9yIGEgbW9tZW50IHRoYXQgZmlzaCB3aXRoIHNtYWxsZXIgZXllcyBoYXZlIGEgaGlnaGVyIGxpa2VsaWhvb2Qgb2Ygc3Vydml2YWwgaW4gdGhlIGNhdmUuIFdvdWxkIHlvdSBleHBlY3QgZXZvbHV0aW9uIG9mIGV5ZSBzaXplIHVwb24gY2F2ZSBjb2xvbml6YXRpb24/IEp1c3RpZnkgeW91ciByZXNwb25zZS4KCklmIGJvZHkgc21hbGxlciBib2R5IHNpemUgaW4gdGhlIG1vbGxpZXMgaW5jcmVhc2VzIHRoZSBjaGFuY2VzIG9mIHN1cnZpdmFsIEkgd291bGQgaW1hZ2luZSB0aGF0IGJvZHkgc2l6ZSB3b3VsZCBkZWNyZWFzZSB3aXRoaW4gdGhlIHBvcHVsYXRpb24uIFRoZSBzbWFsbGVyIHRoZSBtb2xsaWUsIHRoZSBtb3JlIGxpa2VseSBpdCBpcyB0byBwcm9kdWNlIG9mZnNwcmluZyB3aGljaCBpbiB0dXJuIG1lYW5zIHRoZSBzcHJlYWQgb2YgZ2VuZXMgZm9yIHNtYWxsZXIgYm9keSBzaXplIGFuZCBhIGRlY3JlYXNlIGluIGluZGl2aWR1YWxzIHdpdGggbGFyZ2VyIGJvZHkgc2l6ZS4gVGhlIHNhbWUgY29uY2VwdCBhcHBsaWVzIHRvIHNtYWxsZXIgZXllIHNpemUgYXMgd2VsbCwgc28gaWYgc21hbGxlciBleWVzIGJlY2FtZSBtb3JlIGZhdm9yYWJsZSB0aGVyZSB3b3VsZCBiZSBhbiBpbmNyZWFzZSBpbiBtb2xsaWVzIHdpdGggc21hbGxlciBleWUgc2l6ZSBpbiB0aGUgcG9wdWxhdGlvbi4gCgotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCiMgNy4gUmVzb3VyY2VzCgotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCiMjIDcuMS4gRGF0YSBSZWZlcmVuY2VzCgpUaGUgZXllIHNpemUgZGF0YSB3YXMgcHVibGlzaGVkIGluIHRoZSBmb2xsb3dpbmcgcGFwZXIuIE90aGVyIG1lYXN1cmVtZW50cyBhcmUgdW5wdWJsaXNoZWQgZGF0YSBieSBNLiBUb2JsZXIuCgotICAgTWNHb3dhbiwgSy4gTC4sIEMuIE4uIFBhc3NvdywgTC4gQXJpYXMgUm9kcmlndWV6LCBNLiBUb2JsZXIgJiBKLiBMLiBLZWxsZXkgKDIwMTkpOiBbRXhwcmVzc2lvbiBhbmFseXNlcyBvZiBjYXZlIG1vbGxpZXMgKCpQb2VjaWxpYSBtZXhpY2FuYSopIHJldmVhbCBrZXkgZ2VuZXMgaW52b2x2ZWQgaW4gdGhlIGVhcmx5IGV2b2x1dGlvbiBvZiBleWUgcmVncmVzc2lvbl0oaHR0cHM6Ly9yb3lhbHNvY2lldHlwdWJsaXNoaW5nLm9yZy9kb2kvMTAuMTA5OC9yc2JsLjIwMTkuMDU1NCkuICpCaW9sb2d5IExldHRlcnMqIDE1ICgxMCk6IDIwMTkwNTU0LgoKLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgojIyA3LjIgUmVzb3VyY2VzIFlvdSBDb25zdWx0ZWQKCkNvbnN1bHRpbmcgYWRkaXRpb25hbCByZXNvdXJjZXMgdG8gc29sdmUgdGhpcyBhc3NpZ25tZW50IGlzIGFic29sdXRlbHkgYWxsb3dlZCwgYnV0IGZhaWx1cmUgdG8gZGlzY2xvc2UgdGhvc2UgcmVzb3VyY2VzIGlzIHBsYWdpYXJpc20uIFBsZWFzZSBsaXN0IGFueSBjb2xsYWJvcmF0b3JzIHlvdSB3b3JrZWQgd2l0aCBhbmQgcmVzb3VyY2VzIHlvdSB1c2VkIGJlbG93IG9yIHN0YXRlIHRoYXQgeW91IGhhdmUgbm90IHVzZWQgYW55LgoKLSBScHViIAo=