1 Introduction

One of the effects of global warming has been the melting of the polar ice at such a rate that it is contributing to the elevation of sealevels.1

In this study, we will take historical data of sealevels from 4 locations and determine the annual rise of sealevels in recent years. The data from 4 locations were chosen (i.e., Chittagong,2 Halifax,3 Singapore,4 and Yap.5) and are marked on the map given below.

Loading required package: maps

2 Research Question

3 Methodology

The following datasets were chosen and downloaded from the University of Hawaii Sea Level Center archive.

Datasets included in this study
File ID CITY, COUNTRY Description LATITUDE, LONGITUDE Dates of record
h124a Chittagong, Bangladesh Flood prone area 22.24700, 91.82500 2007-07-01 to 2018-12-06
h275a Halifax, Canada Large tidal swells 44.667100, -63.58300 1895-10-16 to 2014-08-12
h327a Keppel Harbour, Singapore Busy shallow harbor 1.26300, 103.82200 1981-08-14 to 1990-01-30
h008b Yap, Micronesia Shallow open ocean 9.51700, 138.13300 1969-05-11 to 2018-12-31

The data was cleaned, tidied and transformed using the various libraries associated with Tidyverse6. The ggplot7 package was used to visual the results of analysis of the datasets. The data was prepared and analyzed using the following workflow:

library(tidyverse)
── Attaching packages ──────────────────────────────────────── tidyverse 1.3.1 ──
✓ ggplot2 3.3.5     ✓ purrr   0.3.4
✓ tibble  3.1.3     ✓ dplyr   1.0.7
✓ tidyr   1.1.3     ✓ stringr 1.4.0
✓ readr   2.0.0     ✓ forcats 0.5.1
── Conflicts ─────────────────────────────────────────── tidyverse_conflicts() ──
x dplyr::filter() masks stats::filter()
x dplyr::lag()    masks stats::lag()
x purrr::map()    masks maps::map()
loaddata <- function(cnt) {
   fnames =  c("h124a","h275a","h327a","h008b")
   dat = read_csv(paste("datasets/",fnames[cnt],".csv",sep=""),
                  col_names = c("yr","mon","day","hr","level"),
                  col_types = c("i","i","i","i","i"))
   dat = dat %>% 
       filter(level > -1) %>%
       mutate(tm5 = (as.integer(yr / 5) * 5)) %>%
       select(c(yr,tm5,level))
}
extractregression <- function(lm) {
   llm = summary(lm)
   lllm = round(llm$coefficients[2,1:2],4)
} 
city = c("Chittagong","Halifax","Singapore","Yap")
sumdat = c("City","StartYr","EndYr","Missing","Existing",
           "Annual Rise","err", "Rise5","err5")
colors = rainbow(4)
plot(-1,-1,xlim=c(0,7500),ylim=c(0,0.001),xlab="Sea levels",ylab="Frequency",
     main="Range of sealevels observed")

for (cnt in c(1:4)) {
   dat = loaddata(cnt)
   l = length(dat$yr)
   d = density(dat$level,bw=20)
   lm = lm(dat$level ~ dat$yr)
   lm5 = lm(dat$level ~ dat$tm5) 
   rate = extractregression(lm)
   rate5 = extractregression(lm5)
   lines(d$x,d$y,lwd=2,col=colors[cnt])
   sumdat = rbind(sumdat,c(city[cnt],
         min(dat$yr),max(dat$yr),
         365*24 * (1+max(dat$yr)-min(dat$yr)) - l,l,
         rate[1], rate[2], rate5[1], rate5[2]))
}
legend(5000,0.0008, city,fill=colors)

3.1 Density plots

The range of sealevels experience within a single year or a 5 yr period were calculated this way.

draw_density <- function(cnt,type) {
fnames =  c("h124a","h275a","h327a","h008b")
city = c("Chittagong","Halifax","Singapore","Yap")
   dat = read_csv(paste("datasets/",fnames[cnt],".csv",sep=""),
                  col_names = c("yr","mon","day","hr","level"),
                  col_types = c("i","i","i","i","i"))
   dat2 = dat %>% 
       filter(level > -1) %>%
       mutate(tm5 = (as.integer(yr / 5) * 5)) %>%
       select(c(yr,tm5,level))
   if (type=="Y") {
      lb = ": comparison of yr to yr"
   dat2 %>%
       ggplot(aes(x=level))+
       geom_density(mapping=aes(x=level,color=yr,group=yr))+
       scale_color_gradient(low="#99000066",high="#FFFF0066")+
       labs(title=paste(city[cnt],lb))
   } else {
      lb = ": comparison of 5yr data units"
   dat2 %>%
       ggplot(aes(x=level))+
       geom_density(mapping=aes(x=level,color=tm5,group=tm5),lwd=2)+
       scale_color_gradient(low="#99000066",high="#FFFF0066")+
       labs(title=paste(city[cnt],lb))
}
}

3.2 Boxplots

Boxplots were also drawn to illustrate the progression of the mean sealevel.

draw_boxplot <- function(cnt,type) {
fnames =  c("h124a","h275a","h327a","h008b")
city = c("Chittagong","Halifax","Singapore","Yap")
   dat = read_csv(paste("datasets/",fnames[cnt],".csv",sep=""),
                  col_names = c("yr","mon","day","hr","level"),
                  col_types = c("i","i","i","i","i"))
   dat2 = dat %>% 
       filter(level > -1) %>%
       mutate(tm5 = (as.integer(yr / 5) * 5)) %>%
       select(c(yr,tm5,level))
   if (type=="Y") {
      lb = ": comparison of yr to yr"
   dat2 %>%
       ggplot(aes(x=yr,y=level,group=yr))+
       geom_boxplot(mapping=aes(x=yr,y=level))+
       labs(title=paste(city[cnt],lb))
   } else {
      lb = ": comparison of 5yr data units"
   dat2 %>%
       ggplot(aes(x=tm5,y=level,group=tm5))+
       geom_boxplot(mapping=aes(x=tm5,y=level))+
       labs(title=paste(city[cnt],lb))
}
}

3.3 Summary of the datasets

knitr::kable(sumdat[,c(1:5)])
sumdat City StartYr EndYr Missing Existing
Chittagong 2007 2018 8402 96718
Halifax 1895 2014 233879 817321
Singapore 1981 1990 14309 73291
Yap 1969 2018 42280 395720

4 Results

Each country has a different story to tell. The analysis of the datasets are displayed in the following table. Summary plots for the range of sealevels experienced over 5 year periods are given for each country in the following sections.

sumdat[1,c(6:9)] = c("Freq:","Yr by yr","Freq:","5yr")
knitr::kable(sumdat[,c(1,6:9)])
Estimate Std. Error Estimate Std. Error
sumdat City Freq: Yr by yr Freq: 5yr
Chittagong -4.4997 1.3383 -2.4598 1.1955
Halifax 2.7503 0.0186 2.7555 0.0186
Singapore 12.0778 1.0691 10.1245 1.0331
Yap 2.6788 0.0426 2.5486 0.0425

4.1 Year to year comparisons

  • Chittagong, Bangladesh
draw_density(1,"Y")

  • Halifax, Canada
draw_density(2,"Y")

  • Singapore
draw_density(3,"Y")

  • Yap, Micronesia
draw_density(4,"Y")

5 Summary

5.1 Chittagong

draw_density(1,"T")

draw_boxplot(1,"Y")

  • The sensors are on a buoy in the estuary from a major river flowing from Myanmar.
  • Near 60% of Bangladesh’s land mass was flooded (>2m) annually during rainy season.
  • The river flooding was severe (>4 m) before the river was dredged.
  • Dredging changed the lowtide readings but the high tide readings continued to increase with time.
  • The progress being made in dredging and flood prevention (10cm per yr) masks whatever effects increasing sealevel might be (2mm per yr)

5.2 Halifax

draw_density(2,"T")

draw_boxplot(2,"Y")

  • Sensors on a buoy at the mouth of the harbor.
  • The tidal bay changes the shape of the tidal curve but helps to given constant readings.
  • Initially the sealevels were constant but the rise in sealevel has been ongoing for 100 years.

5.3 Singapore

draw_density(3,"T")

draw_boxplot(3,"Y")

  • Dredging and widening of the channel contributed to height of the tides.
  • Changes in rain patterns and flash flooding of 1980 contributed to a rise the sealevel readings.
  • After 1980, the sea levels have a consistent rise.

5.4 Yap

draw_density(4,"T")

draw_boxplot(4,"Y")

  • Sensors were located on an offshore buoy where they were not bothered by tidal resistance of the shoreline.
  • The tidal levels were far more regular than other harbor readings.
  • There seems to a steady increment since 1990, the increase in the size and number of typhoons have had an effect of the sea level measured in recent years..

In short, the tides have been rising approximately 2mm per year around the globe. However, storms, flooding, earthquake driven tsunamis, and even the daily tides create short term local variations that can mask the effects of global sea changes. However, long term studies particularly of offshore buoys clearly illustrate the trend towards higher tides over time. However, data from offshore buoys were often lost particularly in the yearly years of operation.

6 Reference


  1. David Guggenhiem, 2006. An Inconvenient Truth. A documentary film based on Al Gore’s slide presentation. Released by Paramount Films↩︎

  2. University of Hawaii Sea Level Center, 2016. Legacy Data Archives: Readings from Chittagong, Bangladesh: http://uhslc.soest.hawaii.edu/data/csv/rqds/indian/hourly/h124a.csv↩︎

  3. University of Hawaii Sea Level Center, 2016. Legacy Data Archives: Readings from Halifax, Canada: Downloaded from http://uhslc.soest.hawaii.edu/data/csv/rqds/atlantic/hourly/h275a.csv↩︎

  4. University of Hawaii Sea Level Center, 2016. Legacy Data Archives: Readings from Keppel Harbor, Singapore. Downloaded from http://uhslc.soest.hawaii.edu/data/csv/rqds/pacific/hourly/h327a.csv↩︎

  5. University of Hawaii Sea Level Center, 2016. Legacy Data Archives: Readings from Yap, Micronesia. Downloaded from http://uhslc.soest.hawaii.edu/data/csv/rqds/pacific/hourly/h008b.csv↩︎

  6. Hadly Wickham et al., (2019). Welcome to the tidyverse. Journal of Open Source Software, 4(43), 1686↩︎

  7. Hadly Wickham, 2016. ggplot2: Elegant Graphics for Data Analysis. Springer-Verlag, New York.↩︎

LS0tCnRpdGxlOiAiVGhlIHJpc2Ugb2Ygc2VhIGxldmVscyBpbiByZWNlbnQgeWVhcnMiCmF1dGhvcjogIkRyIFJvYmVydCBCYXR6aW5nZXIsIFBheWFwIFVuaXZlcnNpdHkgRGVwdC4gb2YgQ29tcHV0ZXIgU2NpZW5jZSIKZGF0ZTogIjIwIEp1bHkgMjAyMSIKb3V0cHV0OgogIGh0bWxfbm90ZWJvb2s6CiAgICB0b2M6IHRydWUKICAgIHRvY19kZXB0aDogMwogICAgbnVtYmVyX3NlY3Rpb246IHRydWUKICAgIGhpZ2hsaWdodDogdGFuZ28KICAgIHRoZW1lOiB1bml0ZWQKICBwZGZfZG9jdW1lbnQ6IGRlZmF1bHQKYWJzdHJhY3Q6ICJUaGlzIGV4ZXJjaXNlIGlzIHVzZXMgZGF0YSBmcm9tIHRoZSBhcmNoaXZlIG9mIHRoZSBVbml2ZXJzaXR5IG9mIEhhd2FpaSBTZWEgTGV2ZWwgQ2VudGVyIHRvIGRldGVybWluZSB0aGUgcmF0ZSBvZiBjaGFuZ2UgaW4gdGhlIHNlYSBsZXZlbCBpbiByZWNlbnQgeWVhcnMuXG5cbiIKLS0tCgojIEludHJvZHVjdGlvbgoKT25lIG9mIHRoZSBlZmZlY3RzIG9mIGdsb2JhbCB3YXJtaW5nIGhhcyBiZWVuIHRoZSBtZWx0aW5nIG9mIHRoZSBwb2xhciBpY2UgYXQgc3VjaCBhIHJhdGUgdGhhdCBpdCBpcyBjb250cmlidXRpbmcgdG8gdGhlIGVsZXZhdGlvbiBvZiBzZWFsZXZlbHMuW15HdWdnZW5oZWltXQoKW15HdWdnZW5oZWltXTogRGF2aWQgR3VnZ2VuaGllbSwgMjAwNi4gQW4gSW5jb252ZW5pZW50IFRydXRoLiBBIGRvY3VtZW50YXJ5IGZpbG0gYmFzZWQgb24gQWwgR29yZSdzIHNsaWRlIHByZXNlbnRhdGlvbi4gUmVsZWFzZWQgYnkgUGFyYW1vdW50IEZpbG1zIAoKSW4gdGhpcyBzdHVkeSwgd2Ugd2lsbCB0YWtlIGhpc3RvcmljYWwgZGF0YSBvZiBzZWFsZXZlbHMgZnJvbSA0IGxvY2F0aW9ucyBhbmQgZGV0ZXJtaW5lIHRoZSBhbm51YWwgcmlzZSBvZiBzZWFsZXZlbHMgaW4gcmVjZW50IHllYXJzLiBUaGUgZGF0YSBmcm9tIDQgbG9jYXRpb25zIHdlcmUgY2hvc2VuIChpLmUuLCBDaGl0dGFnb25nLFteaDEyNGFdIEhhbGlmYXgsW15oMjc1YV0gU2luZ2Fwb3JlLFteaDMyN2FdIGFuZCBZYXAuW15oMDA4Yl0pIGFuZCBhcmUgbWFya2VkIG9uIHRoZSBtYXAgZ2l2ZW4gYmVsb3cuCgpbXmgxMjRhXTogVW5pdmVyc2l0eSBvZiBIYXdhaWkgU2VhIExldmVsIENlbnRlciwgMjAxNi4gTGVnYWN5IERhdGEgQXJjaGl2ZXM6IFJlYWRpbmdzIGZyb20gQ2hpdHRhZ29uZywgQmFuZ2xhZGVzaDogaHR0cDovL3Voc2xjLnNvZXN0Lmhhd2FpaS5lZHUvZGF0YS9jc3YvcnFkcy9pbmRpYW4vaG91cmx5L2gxMjRhLmNzdgoKW15oMjc1YV06IFVuaXZlcnNpdHkgb2YgSGF3YWlpIFNlYSBMZXZlbCBDZW50ZXIsIDIwMTYuIExlZ2FjeSBEYXRhIEFyY2hpdmVzOiBSZWFkaW5ncyBmcm9tIEhhbGlmYXgsIENhbmFkYTogRG93bmxvYWRlZCBmcm9tIGh0dHA6Ly91aHNsYy5zb2VzdC5oYXdhaWkuZWR1L2RhdGEvY3N2L3JxZHMvYXRsYW50aWMvaG91cmx5L2gyNzVhLmNzdiAKClteaDMyN2FdOiBVbml2ZXJzaXR5IG9mIEhhd2FpaSBTZWEgTGV2ZWwgQ2VudGVyLCAyMDE2LiBMZWdhY3kgRGF0YSBBcmNoaXZlczogUmVhZGluZ3MgZnJvbSBLZXBwZWwgSGFyYm9yLCBTaW5nYXBvcmUuIERvd25sb2FkZWQgZnJvbSAgaHR0cDovL3Voc2xjLnNvZXN0Lmhhd2FpaS5lZHUvZGF0YS9jc3YvcnFkcy9wYWNpZmljL2hvdXJseS9oMzI3YS5jc3YKClteaDAwOGJdOiBVbml2ZXJzaXR5IG9mIEhhd2FpaSBTZWEgTGV2ZWwgQ2VudGVyLCAyMDE2LiBMZWdhY3kgRGF0YSBBcmNoaXZlczogUmVhZGluZ3MgZnJvbSBZYXAsIE1pY3JvbmVzaWEuIERvd25sb2FkZWQgZnJvbSBodHRwOi8vdWhzbGMuc29lc3QuaGF3YWlpLmVkdS9kYXRhL2Nzdi9ycWRzL3BhY2lmaWMvaG91cmx5L2gwMDhiLmNzdgoKCgpgYGB7cixlY2hvPUZBTFNFfQpsaWJyYXJ5KG1hcGRhdGEpCm1hcCgnd29ybGRIaXJlcycseGxpbT1jKC05MCwxNTUpLHlsaW09YygtNTUsODYpKQp0aXRsZSgiTWFwIG9mIExvY2F0aW9ucyBTdHVkaWVkIikKcG9seWdvbihjKC0xMDAsLTEwMCwxNjAsMTYwKSxjKC02MCw5MCw5MCwtNjApLGNvbD0iIzY2OTljYzY2IikKcG9pbnRzKGMoOTEuODI1MDAsICAtNjMuNTgzMDAsICAxMDMuODIyMCwxMzguMTMzMDApLAogICAgICAgYygyMi4yNDcwMCw0NC42NjcwMCwxLjI2MzAwLDkuNTE3MDApLGNvbD0icmVkIixwY2g9MTkpCnRleHQoICBjKDkxLjgyNTAwLCAgLTYzLjU4MzAwLCAgMTAzLjgyMjArNSwxMzguMTMzMDArMiksCiAgICAgICBjKDIyLjI0NzAwLTEsNDQuNjY3MDAtNCwxLjI2MzAwLTUsOS41MTcwMCksCiAgICAgICBjKCJDaGl0dGFnb25nIiwgIkhhbGlmYXgiLCAiU2luZ2Fwb3JlIiwgIllhcCIpLAogICAgICAgcG9zPWMoMyw0LDIsMyksY2V4PTEuMixjb2w9InJlZCIpCmBgYCAgICAgICAgICAKCiMgUmVzZWFyY2ggUXVlc3Rpb24KCgojIE1ldGhvZG9sb2d5CgpUaGUgZm9sbG93aW5nIGRhdGFzZXRzIHdlcmUgY2hvc2VuIGFuZCBkb3dubG9hZGVkIGZyb20gdGhlIFVuaXZlcnNpdHkgb2YgSGF3YWlpIFNlYSBMZXZlbCBDZW50ZXIgYXJjaGl2ZS4KClRhYmxlOiBEYXRhc2V0cyBpbmNsdWRlZCBpbiB0aGlzIHN0dWR5CgorLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0tKwp8IEZpbGUgSUQgfCBDSVRZLCBDT1VOVFJZICB8IERlc2NyaXB0aW9uICAgICAgICB8IExBVElUVURFLCBMT05HSVRVREUgfCBEYXRlcyBvZiByZWNvcmQgfAorPT09PT09PT09Kz09PT09PT09PT09PT09PT0rPT09PT09PT09PT09PT09PT09PT0rPT09PT09PT09PT09PT09PT09PT09Kz09PT09PT09PT09PT09PT09Kwp8IGgxMjRhICAgfCBDaGl0dGFnb25nLCAgICB8IEZsb29kIHByb25lIGFyZWEgICB8IDIyLjI0NzAwLCA5MS44MjUwMCAgfCAyMDA3LTA3LTAxIHRvICAgfAp8ICAgICAgICAgfCBCYW5nbGFkZXNoICAgICB8ICAgICAgICAgICAgICAgICAgICB8ICAgICAgICAgICAgICAgICAgICAgfCAyMDE4LTEyLTA2ICAgICAgfAorLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0tKwp8IGgyNzVhICAgfCBIYWxpZmF4LCAgICAgICB8IExhcmdlIHRpZGFsIHN3ZWxscyB8IDQ0LjY2NzEwMCwgLTYzLjU4MzAwfCAxODk1LTEwLTE2IHRvICAgfAp8ICAgICAgICAgfCBDYW5hZGEgICAgICAgICB8ICAgICAgICAgICAgICAgICAgICB8ICAgICAgICAgICAgICAgICAgICAgfCAyMDE0LTA4LTEyICAgICAgfAorLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0tKwp8IGgzMjdhICAgfCBLZXBwZWwgSGFyYm91cix8IEJ1c3kgc2hhbGxvdyBoYXJib3J8IDEuMjYzMDAsIDEwMy44MjIwMCAgfCAxOTgxLTA4LTE0IHRvICAgfAp8ICAgICAgICAgfCBTaW5nYXBvcmUgICAgICB8ICAgICAgICAgICAgICAgICAgICB8ICAgICAgICAgICAgICAgICAgICAgfCAxOTkwLTAxLTMwICAgICAgfAorLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0tKwp8IGgwMDhiICAgfCBZYXAsICAgICAgICAgICB8IFNoYWxsb3cgb3BlbiBvY2VhbiB8ICA5LjUxNzAwLCAxMzguMTMzMDAgfCAxOTY5LTA1LTExIHRvICAgfAp8ICAgICAgICAgfCBNaWNyb25lc2lhICAgICB8ICAgICAgICAgICAgICAgICAgICB8ICAgICAgICAgICAgICAgICAgICAgfCAyMDE4LTEyLTMxICAgICAgfAorLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0tKwoKCgpUaGUgZGF0YSB3YXMgY2xlYW5lZCwgdGlkaWVkIGFuZCB0cmFuc2Zvcm1lZCB1c2luZyB0aGUgdmFyaW91cyBsaWJyYXJpZXMgYXNzb2NpYXRlZCB3aXRoIFRpZHl2ZXJzZVtedGlkeXZlcnNlXS4gVGhlIGdncGxvdFteZ2dwbG90XSBwYWNrYWdlIHdhcyB1c2VkIHRvIHZpc3VhbCB0aGUgcmVzdWx0cyBvZiBhbmFseXNpcyBvZiB0aGUgZGF0YXNldHMuIFRoZSBkYXRhIHdhcyBwcmVwYXJlZCBhbmQgYW5hbHl6ZWQgdXNpbmcgdGhlIGZvbGxvd2luZyB3b3JrZmxvdzoKCltedGlkeXZlcnNlXTogSGFkbHkgV2lja2hhbSBldCBhbC4sICgyMDE5KS4gV2VsY29tZSB0byB0aGUgdGlkeXZlcnNlLiBKb3VybmFsIG9mIE9wZW4gU291cmNlIFNvZnR3YXJlLCA0KDQzKSwgMTY4NgoKW15nZ3Bsb3RdOiAgSGFkbHkgV2lja2hhbSwgMjAxNi4gZ2dwbG90MjogRWxlZ2FudCBHcmFwaGljcyBmb3IgRGF0YSBBbmFseXNpcy4gU3ByaW5nZXItVmVybGFnLCBOZXcgWW9yay4KCmBgYHtyfQpsaWJyYXJ5KHRpZHl2ZXJzZSkKYGBgCgoqIFRoZSBDU1YgdmVyc2lvbnMgb2YgdGhlIGhvdXJseSBkYXRhc2V0cyB3ZXJlIGRvd25sb2FkZWQgZm9yIHRoZSB0YXJnZXQgbG9jYXRpb25zLiBUaGUgZWFjaCBkYXRhc2V0IHdhcyBsb2FkZWQgaW50byBSIGFuZCB0cmltbWVkIGZvciBhbmFseXNpcy4gVGhlIG1pc3NpbmcgZGF0YSBwb2ludHMgYW5kIHVudXNlZCBjb2x1bW5zIHdlcmUgcmVtb3ZlZCBmcm9tIGVhY2ggb2YgZGF0YXNldHMuCgoKYGBge3J9CmxvYWRkYXRhIDwtIGZ1bmN0aW9uKGNudCkgewogICBmbmFtZXMgPSAgYygiaDEyNGEiLCJoMjc1YSIsImgzMjdhIiwiaDAwOGIiKQogICBkYXQgPSByZWFkX2NzdihwYXN0ZSgiZGF0YXNldHMvIixmbmFtZXNbY250XSwiLmNzdiIsc2VwPSIiKSwKICAgICAgICAgICAgICAgICAgY29sX25hbWVzID0gYygieXIiLCJtb24iLCJkYXkiLCJociIsImxldmVsIiksCiAgICAgICAgICAgICAgICAgIGNvbF90eXBlcyA9IGMoImkiLCJpIiwiaSIsImkiLCJpIikpCiAgIGRhdCA9IGRhdCAlPiUgCiAgICAgICBmaWx0ZXIobGV2ZWwgPiAtMSkgJT4lCiAgICAgICBtdXRhdGUodG01ID0gKGFzLmludGVnZXIoeXIgLyA1KSAqIDUpKSAlPiUKICAgICAgIHNlbGVjdChjKHlyLHRtNSxsZXZlbCkpCn0KYGBgCgoqIEFubnVhbCBhbmQgZGVjYWRlIGF2ZXJhZ2VzIHdlcmUgY2FsY3VsYXRlZCBmb3IgdGhlIGRhdGEgc2V0cy4gQW4gb3ZlcmFsbCBwbG90IG9mIHRoZSB2YXJpYXRpb24gd2FzIG1hZGUuIFJlZ3Jlc3Npb24gYW5hbHlzaXMgd2VyZSB1c2VkIHRvIGRldGVybWluZSB0aGUgYW5udWFsIHJhdGUgb2YgY2hhbmdlLiBUaGUgYW5udWFsIHJhdGUgYW5kIGl0cyBzdGFuZGFyZCBlcnJvciB3ZXJlIGV4dHJhY3RlZCBmcm9tIHRoZSByZWdyZXNzaW9uIHN1bW1hcnkuCgpgYGB7cn0KZXh0cmFjdHJlZ3Jlc3Npb24gPC0gZnVuY3Rpb24obG0pIHsKICAgbGxtID0gc3VtbWFyeShsbSkKICAgbGxsbSA9IHJvdW5kKGxsbSRjb2VmZmljaWVudHNbMiwxOjJdLDQpCn0gCmBgYAoKKiBUaGUgZGF0YXNldHMgd2VyZSByZWxvYWRlZCBhbmQgc3ViamVjdGVkIHRvIGxpbmVhciByZWdyZXNzaW9uIHRvIGRldGVybWluZSB0aGUgYW5udWFsIHJhdGUgb2YgaW5jcmVtZW50LgoKYGBge3J9CmNpdHkgPSBjKCJDaGl0dGFnb25nIiwiSGFsaWZheCIsIlNpbmdhcG9yZSIsIllhcCIpCnN1bWRhdCA9IGMoIkNpdHkiLCJTdGFydFlyIiwiRW5kWXIiLCJNaXNzaW5nIiwiRXhpc3RpbmciLAogICAgICAgICAgICJBbm51YWwgUmlzZSIsImVyciIsICJSaXNlNSIsImVycjUiKQpjb2xvcnMgPSByYWluYm93KDQpCnBsb3QoLTEsLTEseGxpbT1jKDAsNzUwMCkseWxpbT1jKDAsMC4wMDEpLHhsYWI9IlNlYSBsZXZlbHMiLHlsYWI9IkZyZXF1ZW5jeSIsCiAgICAgbWFpbj0iUmFuZ2Ugb2Ygc2VhbGV2ZWxzIG9ic2VydmVkIikKCmZvciAoY250IGluIGMoMTo0KSkgewogICBkYXQgPSBsb2FkZGF0YShjbnQpCiAgIGwgPSBsZW5ndGgoZGF0JHlyKQogICBkID0gZGVuc2l0eShkYXQkbGV2ZWwsYnc9MjApCiAgIGxtID0gbG0oZGF0JGxldmVsIH4gZGF0JHlyKQogICBsbTUgPSBsbShkYXQkbGV2ZWwgfiBkYXQkdG01KSAKICAgcmF0ZSA9IGV4dHJhY3RyZWdyZXNzaW9uKGxtKQogICByYXRlNSA9IGV4dHJhY3RyZWdyZXNzaW9uKGxtNSkKICAgbGluZXMoZCR4LGQkeSxsd2Q9Mixjb2w9Y29sb3JzW2NudF0pCiAgIHN1bWRhdCA9IHJiaW5kKHN1bWRhdCxjKGNpdHlbY250XSwKICAgICAgICAgbWluKGRhdCR5ciksbWF4KGRhdCR5ciksCiAgICAgICAgIDM2NSoyNCAqICgxK21heChkYXQkeXIpLW1pbihkYXQkeXIpKSAtIGwsbCwKICAgICAgICAgcmF0ZVsxXSwgcmF0ZVsyXSwgcmF0ZTVbMV0sIHJhdGU1WzJdKSkKfQpsZWdlbmQoNTAwMCwwLjAwMDgsIGNpdHksZmlsbD1jb2xvcnMpCmBgYAoKIyMgRGVuc2l0eSBwbG90cwoKVGhlIHJhbmdlIG9mIHNlYWxldmVscyBleHBlcmllbmNlIHdpdGhpbiBhIHNpbmdsZSB5ZWFyIG9yIGEgNSB5ciBwZXJpb2Qgd2VyZSBjYWxjdWxhdGVkIHRoaXMgd2F5LgoKYGBge3J9CmRyYXdfZGVuc2l0eSA8LSBmdW5jdGlvbihjbnQsdHlwZSkgewpmbmFtZXMgPSAgYygiaDEyNGEiLCJoMjc1YSIsImgzMjdhIiwiaDAwOGIiKQpjaXR5ID0gYygiQ2hpdHRhZ29uZyIsIkhhbGlmYXgiLCJTaW5nYXBvcmUiLCJZYXAiKQogICBkYXQgPSByZWFkX2NzdihwYXN0ZSgiZGF0YXNldHMvIixmbmFtZXNbY250XSwiLmNzdiIsc2VwPSIiKSwKICAgICAgICAgICAgICAgICAgY29sX25hbWVzID0gYygieXIiLCJtb24iLCJkYXkiLCJociIsImxldmVsIiksCiAgICAgICAgICAgICAgICAgIGNvbF90eXBlcyA9IGMoImkiLCJpIiwiaSIsImkiLCJpIikpCiAgIGRhdDIgPSBkYXQgJT4lIAogICAgICAgZmlsdGVyKGxldmVsID4gLTEpICU+JQogICAgICAgbXV0YXRlKHRtNSA9IChhcy5pbnRlZ2VyKHlyIC8gNSkgKiA1KSkgJT4lCiAgICAgICBzZWxlY3QoYyh5cix0bTUsbGV2ZWwpKQogICBpZiAodHlwZT09IlkiKSB7CiAgICAgIGxiID0gIjogY29tcGFyaXNvbiBvZiB5ciB0byB5ciIKICAgZGF0MiAlPiUKICAgICAgIGdncGxvdChhZXMoeD1sZXZlbCkpKwogICAgICAgZ2VvbV9kZW5zaXR5KG1hcHBpbmc9YWVzKHg9bGV2ZWwsY29sb3I9eXIsZ3JvdXA9eXIpKSsKICAgICAgIHNjYWxlX2NvbG9yX2dyYWRpZW50KGxvdz0iIzk5MDAwMDY2IixoaWdoPSIjRkZGRjAwNjYiKSsKICAgICAgIGxhYnModGl0bGU9cGFzdGUoY2l0eVtjbnRdLGxiKSkKICAgfSBlbHNlIHsKICAgICAgbGIgPSAiOiBjb21wYXJpc29uIG9mIDV5ciBkYXRhIHVuaXRzIgogICBkYXQyICU+JQogICAgICAgZ2dwbG90KGFlcyh4PWxldmVsKSkrCiAgICAgICBnZW9tX2RlbnNpdHkobWFwcGluZz1hZXMoeD1sZXZlbCxjb2xvcj10bTUsZ3JvdXA9dG01KSxsd2Q9MikrCiAgICAgICBzY2FsZV9jb2xvcl9ncmFkaWVudChsb3c9IiM5OTAwMDA2NiIsaGlnaD0iI0ZGRkYwMDY2IikrCiAgICAgICBsYWJzKHRpdGxlPXBhc3RlKGNpdHlbY250XSxsYikpCn0KfQpgYGAKCiMjIEJveHBsb3RzCgpCb3hwbG90cyB3ZXJlIGFsc28gZHJhd24gdG8gaWxsdXN0cmF0ZSB0aGUgcHJvZ3Jlc3Npb24gb2YgdGhlIG1lYW4gc2VhbGV2ZWwuCgpgYGB7cn0KZHJhd19ib3hwbG90IDwtIGZ1bmN0aW9uKGNudCx0eXBlKSB7CmZuYW1lcyA9ICBjKCJoMTI0YSIsImgyNzVhIiwiaDMyN2EiLCJoMDA4YiIpCmNpdHkgPSBjKCJDaGl0dGFnb25nIiwiSGFsaWZheCIsIlNpbmdhcG9yZSIsIllhcCIpCiAgIGRhdCA9IHJlYWRfY3N2KHBhc3RlKCJkYXRhc2V0cy8iLGZuYW1lc1tjbnRdLCIuY3N2IixzZXA9IiIpLAogICAgICAgICAgICAgICAgICBjb2xfbmFtZXMgPSBjKCJ5ciIsIm1vbiIsImRheSIsImhyIiwibGV2ZWwiKSwKICAgICAgICAgICAgICAgICAgY29sX3R5cGVzID0gYygiaSIsImkiLCJpIiwiaSIsImkiKSkKICAgZGF0MiA9IGRhdCAlPiUgCiAgICAgICBmaWx0ZXIobGV2ZWwgPiAtMSkgJT4lCiAgICAgICBtdXRhdGUodG01ID0gKGFzLmludGVnZXIoeXIgLyA1KSAqIDUpKSAlPiUKICAgICAgIHNlbGVjdChjKHlyLHRtNSxsZXZlbCkpCiAgIGlmICh0eXBlPT0iWSIpIHsKICAgICAgbGIgPSAiOiBjb21wYXJpc29uIG9mIHlyIHRvIHlyIgogICBkYXQyICU+JQogICAgICAgZ2dwbG90KGFlcyh4PXlyLHk9bGV2ZWwsZ3JvdXA9eXIpKSsKICAgICAgIGdlb21fYm94cGxvdChtYXBwaW5nPWFlcyh4PXlyLHk9bGV2ZWwpKSsKICAgICAgIGxhYnModGl0bGU9cGFzdGUoY2l0eVtjbnRdLGxiKSkKICAgfSBlbHNlIHsKICAgICAgbGIgPSAiOiBjb21wYXJpc29uIG9mIDV5ciBkYXRhIHVuaXRzIgogICBkYXQyICU+JQogICAgICAgZ2dwbG90KGFlcyh4PXRtNSx5PWxldmVsLGdyb3VwPXRtNSkpKwogICAgICAgZ2VvbV9ib3hwbG90KG1hcHBpbmc9YWVzKHg9dG01LHk9bGV2ZWwpKSsKICAgICAgIGxhYnModGl0bGU9cGFzdGUoY2l0eVtjbnRdLGxiKSkKfQp9CmBgYAoKIyMgU3VtbWFyeSBvZiB0aGUgZGF0YXNldHMKCmBgYHtyfQprbml0cjo6a2FibGUoc3VtZGF0WyxjKDE6NSldKQpgYGAKCiMgUmVzdWx0cwoKRWFjaCBjb3VudHJ5IGhhcyBhIGRpZmZlcmVudCBzdG9yeSB0byB0ZWxsLiBUaGUgYW5hbHlzaXMgb2YgdGhlIGRhdGFzZXRzIGFyZSBkaXNwbGF5ZWQgaW4gdGhlIGZvbGxvd2luZyB0YWJsZS4gU3VtbWFyeSBwbG90cyBmb3IgdGhlIHJhbmdlIG9mIHNlYWxldmVscyBleHBlcmllbmNlZCBvdmVyIDUgeWVhciBwZXJpb2RzIGFyZSBnaXZlbiBmb3IgZWFjaCBjb3VudHJ5IGluIHRoZSBmb2xsb3dpbmcgc2VjdGlvbnMuCgoKYGBge3J9CnN1bWRhdFsxLGMoNjo5KV0gPSBjKCJGcmVxOiIsIllyIGJ5IHlyIiwiRnJlcToiLCI1eXIiKQprbml0cjo6a2FibGUoc3VtZGF0WyxjKDEsNjo5KV0pCmBgYAoKIyMgWWVhciB0byB5ZWFyIGNvbXBhcmlzb25zIAoKKiAqKkNoaXR0YWdvbmcsIEJhbmdsYWRlc2gqKgoKYGBge3Isb3V0LndpZHRoPSI5MCUiLGZpZy53aWR0aD03LGZpZy5oZWlnaHQ9NH0gICAgICAKZHJhd19kZW5zaXR5KDEsIlkiKQpgYGAKCgoKKiAqKkhhbGlmYXgsIENhbmFkYSoqCgpgYGB7cn0KZHJhd19kZW5zaXR5KDIsIlkiKQpgYGAKCiogKipTaW5nYXBvcmUqKgoKYGBge3J9CmRyYXdfZGVuc2l0eSgzLCJZIikKYGBgCgoqICoqWWFwLCBNaWNyb25lc2lhKioKCmBgYHtyfQpkcmF3X2RlbnNpdHkoNCwiWSIpCmBgYAoKCiMgU3VtbWFyeQoKIyMgQ2hpdHRhZ29uZwoKYGBge3Isb3V0LndpZHRoPSI1MCUiLGVjaG89RkFMU0V9CmtuaXRyOjppbmNsdWRlX2dyYXBoaWNzKCJzbGlkZXMvQ2hpdHRhZ29uZy5qcGciKQpgYGAKCmBgYHtyLG91dC53aWR0aD0iOTAlIixmaWcud2lkdGg9NyxmaWcuaGVpZ2h0PTR9ICAgICAgCmRyYXdfZGVuc2l0eSgxLCJUIikKYGBgCgpgYGB7cn0KZHJhd19ib3hwbG90KDEsIlkiKQpgYGAKCiogVGhlIHNlbnNvcnMgYXJlIG9uIGEgYnVveSBpbiB0aGUgZXN0dWFyeSBmcm9tIGEgbWFqb3Igcml2ZXIgZmxvd2luZyBmcm9tIE15YW5tYXIuCiogTmVhciA2MCUgb2YgQmFuZ2xhZGVzaCdzIGxhbmQgbWFzcyB3YXMgZmxvb2RlZCAoPjJtKSBhbm51YWxseSBkdXJpbmcgcmFpbnkgc2Vhc29uLiAKKiBUaGUgcml2ZXIgZmxvb2Rpbmcgd2FzIHNldmVyZSAoPjQgbSkgYmVmb3JlIHRoZSByaXZlciB3YXMgZHJlZGdlZC4KKiBEcmVkZ2luZyBjaGFuZ2VkIHRoZSBsb3d0aWRlIHJlYWRpbmdzIGJ1dCB0aGUgaGlnaCB0aWRlIHJlYWRpbmdzIGNvbnRpbnVlZCB0byBpbmNyZWFzZSB3aXRoIHRpbWUuCiogVGhlIHByb2dyZXNzIGJlaW5nIG1hZGUgaW4gZHJlZGdpbmcgYW5kIGZsb29kIHByZXZlbnRpb24gKDEwY20gcGVyIHlyKSBtYXNrcyB3aGF0ZXZlciBlZmZlY3RzIGluY3JlYXNpbmcgc2VhbGV2ZWwgbWlnaHQgYmUgKDJtbSBwZXIgeXIpCgojIyBIYWxpZmF4CgpgYGB7cixvdXQud2lkdGg9IjUwJSIsZWNobz1GQUxTRX0Ka25pdHI6OmluY2x1ZGVfZ3JhcGhpY3MoInNsaWRlcy9IYWxpZmF4LmpwZyIpCmBgYAoKYGBge3Isb3V0LndpZHRoPSI5MCUiLGZpZy53aWR0aD03LGZpZy5oZWlnaHQ9NH0KZHJhd19kZW5zaXR5KDIsIlQiKQpgYGAKYGBge3J9CmRyYXdfYm94cGxvdCgyLCJZIikKYGBgCiogU2Vuc29ycyBvbiBhIGJ1b3kgYXQgdGhlIG1vdXRoIG9mIHRoZSBoYXJib3IuCiogVGhlIHRpZGFsIGJheSBjaGFuZ2VzIHRoZSBzaGFwZSBvZiB0aGUgdGlkYWwgY3VydmUgYnV0IGhlbHBzIHRvIGdpdmVuIGNvbnN0YW50IHJlYWRpbmdzLgoqIEluaXRpYWxseSB0aGUgc2VhbGV2ZWxzIHdlcmUgY29uc3RhbnQgYnV0IHRoZSByaXNlIGluIHNlYWxldmVsIGhhcyBiZWVuIG9uZ29pbmcgZm9yIDEwMCB5ZWFycy4KCgojIyBTaW5nYXBvcmUKCmBgYHtyLG91dC53aWR0aD0iNTAlIixlY2hvPUZBTFNFfQprbml0cjo6aW5jbHVkZV9ncmFwaGljcygic2xpZGVzL1NpbmdhcG9yZS5qcGciKQpgYGAKCmBgYHtyLG91dC53aWR0aD0iOTAlIixmaWcud2lkdGg9NyxmaWcuaGVpZ2h0PTR9CmRyYXdfZGVuc2l0eSgzLCJUIikKYGBgCmBgYHtyfQpkcmF3X2JveHBsb3QoMywiWSIpCmBgYAoKKiBEcmVkZ2luZyBhbmQgd2lkZW5pbmcgb2YgdGhlIGNoYW5uZWwgY29udHJpYnV0ZWQgdG8gaGVpZ2h0IG9mIHRoZSB0aWRlcy4KKiBDaGFuZ2VzIGluIHJhaW4gcGF0dGVybnMgYW5kIGZsYXNoIGZsb29kaW5nIG9mIDE5ODAgY29udHJpYnV0ZWQgdG8gYSByaXNlIHRoZSBzZWFsZXZlbCByZWFkaW5ncy4KKiBBZnRlciAxOTgwLCB0aGUgc2VhIGxldmVscyBoYXZlIGEgY29uc2lzdGVudCByaXNlLgoKCiMjIFlhcAoKYGBge3Isb3V0LndpZHRoPSI1MCUiLGVjaG89RkFMU0V9CmtuaXRyOjppbmNsdWRlX2dyYXBoaWNzKCJzbGlkZXMvWWFwLmpwZyIpCmBgYAoKYGBge3Isb3V0LndpZHRoPSI5MCUiLGZpZy53aWR0aD03LGZpZy5oZWlnaHQ9NH0KZHJhd19kZW5zaXR5KDQsIlQiKQpgYGAKCmBgYHtyfQpkcmF3X2JveHBsb3QoNCwiWSIpCmBgYAoKKiBTZW5zb3JzIHdlcmUgbG9jYXRlZCBvbiBhbiBvZmZzaG9yZSBidW95IHdoZXJlIHRoZXkgd2VyZSBub3QgYm90aGVyZWQgYnkgdGlkYWwgcmVzaXN0YW5jZSBvZiB0aGUgc2hvcmVsaW5lLgoqIFRoZSB0aWRhbCBsZXZlbHMgd2VyZSBmYXIgbW9yZSByZWd1bGFyIHRoYW4gb3RoZXIgaGFyYm9yIHJlYWRpbmdzLgoqIFRoZXJlIHNlZW1zIHRvIGEgc3RlYWR5IGluY3JlbWVudCBzaW5jZSAxOTkwLCB0aGUgaW5jcmVhc2UgaW4gdGhlIHNpemUgYW5kIG51bWJlciBvZiB0eXBob29ucyBoYXZlIGhhZCBhbiBlZmZlY3Qgb2YgdGhlIHNlYSBsZXZlbCBtZWFzdXJlZCBpbiByZWNlbnQgeWVhcnMuLgoKCkluIHNob3J0LCB0aGUgdGlkZXMgaGF2ZSBiZWVuIHJpc2luZyBhcHByb3hpbWF0ZWx5IDJtbSBwZXIgeWVhciBhcm91bmQgdGhlIGdsb2JlLiBIb3dldmVyLCBzdG9ybXMsIGZsb29kaW5nLCBlYXJ0aHF1YWtlIGRyaXZlbiB0c3VuYW1pcywgYW5kIGV2ZW4gdGhlIGRhaWx5IHRpZGVzIGNyZWF0ZSBzaG9ydCB0ZXJtIGxvY2FsIHZhcmlhdGlvbnMgdGhhdCBjYW4gbWFzayB0aGUgZWZmZWN0cyBvZiBnbG9iYWwgc2VhIGNoYW5nZXMuIEhvd2V2ZXIsIGxvbmcgdGVybSBzdHVkaWVzIHBhcnRpY3VsYXJseSBvZiBvZmZzaG9yZSBidW95cyBjbGVhcmx5IGlsbHVzdHJhdGUgdGhlIHRyZW5kIHRvd2FyZHMgaGlnaGVyIHRpZGVzIG92ZXIgdGltZS4gSG93ZXZlciwgZGF0YSBmcm9tIG9mZnNob3JlIGJ1b3lzIHdlcmUgb2Z0ZW4gbG9zdCBwYXJ0aWN1bGFybHkgaW4gdGhlIHllYXJseSB5ZWFycyBvZiBvcGVyYXRpb24uIAoKIyBSZWZlcmVuY2UK