Praktikum Pernyataan Kondisional dan Perulangan pada Python dan R

Logo

Chandra Rizal Alamsyah

Student Majoring in Data Science at ITSB

NIM: 52250068

Email:

R Programming Data Science Statistics

1 Tujuan Praktikum

Tujuan dari praktikum ini adalah:

  1. Memahami penggunaan pernyataan kondisional (if, if-else, if-elif-else) dalam pemrograman.

  2. Mengimplementasikan perulangan menggunakan for loop dan while loop.

  3. Memahami fungsi break untuk menghentikan perulangan dan continue/next untuk melewati iterasi tertentu.

  4. Menerapkan konsep tersebut untuk menganalisis dataset sederhana mengenai data karyawan.

Konsep ini mengacu pada materi Control Flow pada modul pemrograman data science yang menjelaskan bagaimana program dapat mengambil keputusan dan melakukan proses berulang terhadap data.

2 Dataset yang Digunakan

Dataset dummy yang digunakan dalam praktikum ini adalah sebagai berikut:

library(DT)
# Membuat dataset karyawan
employees <- data.frame(
  ID = c(1,2,3,4,5),
  Nama = c("Bagas","Joan","Alya","Dwi","Nabil"),
  Usia = c(25,30,27,35,40),
  Gaji = c(5000,7000,6500,10000,12000),
  Posisi = c("Staff","Supervisor","Staff","Manager","Director"),
  Performa = c("Good","Very Good","Average","Good","Very Good")
)

# Menampilkan dataset
datatable(employees)

Dataset ini digunakan untuk melakukan analisis sederhana seperti perhitungan bonus dan seleksi data berdasarkan kondisi tertentu.

3 Pernyataan Kondisional (Conditional Statements)

Dalam modul dijelaskan bahwa conditional statements digunakan untuk menentukan tindakan program berdasarkan kondisi tertentu.

Pada praktikum ini bonus karyawan ditentukan berdasarkan performa:

  • Very Good → 20% dari gaji

  • Good → 10% dari gaji

  • Average → 5% dari gaji

3.1 Implementasi

library(DT)
employees <- data.frame(
  name = c("Bagas","Joan","Alya","Dwi","Nabil"),
  age = c(25,30,27,35,40),
  salary = c(5000,7000,6500,10000,12000),
  position = c("Staff","Supervisor","Staff","Manager","Director"),
  performance = c("Good","Very Good","Average","Good","Very Good")
)
employees$bonus <- 0

for(i in 1:nrow(employees)){
  
  if(employees$performance[i] == "Very Good"){
    
    employees$bonus[i] <- employees$salary[i] * 0.20
    
  } else if(employees$performance[i] == "Good"){
    
    employees$bonus[i] <- employees$salary[i] * 0.10
    
  } else {
    
    employees$bonus[i] <- employees$salary[i] * 0.05
  }
}
datatable(
  employees,
  options = list(
    pageLength = 5,
    autoWidth = TRUE
  ),
  caption = "Employee Bonus Report"
)

3.1.1 Visualisasi Bonus Karyawan

3.1.2 Interpretasi

Berdasarkan visualisasi bonus karyawan, terlihat bahwa performa kerja dan besarnya gaji mempengaruhi jumlah bonus yang diterima. Karyawan dengan performa Very Good memperoleh bonus lebih besar karena mendapatkan 20% dari gaji, sedangkan performa Good mendapatkan 10% dan Average sebesar 5%. Selain itu, semakin tinggi gaji karyawan maka semakin besar pula nominal bonus yang diterima karena bonus dihitung berdasarkan persentase gaji. Pada data tersebut, Nabil memiliki bonus tertinggi karena memiliki gaji paling besar dan performa Very Good, sementara Alya memiliki bonus terendah karena performanya berada pada kategori Average. Hal ini menunjukkan bahwa sistem bonus dirancang untuk memberikan penghargaan lebih kepada karyawan dengan kinerja yang lebih baik.

4 Perulangan (Loops)

Perulangan digunakan untuk memproses data secara berulang hingga kondisi tertentu terpenuhi.

Jenis perulangan yang digunakan dalam praktikum ini adalah:

  • For Loop

  • While Loop

  • Break

  • Continue / Next

4.1 For Loop (Menampilkan Gaji > 6000)

# Memanggil library untuk tabel interaktif
library(DT)

# Menyimpan hasil karyawan dengan gaji > 6000
high_salary <- data.frame()

for(i in 1:nrow(employees)){

  if(employees$salary[i] > 6000){

    high_salary <- rbind(
      high_salary,
      data.frame(
        Name = employees$name[i],
        Salary = employees$salary[i]
      )
    )

  }
}

# Menampilkan hasil dalam tabel interaktif
datatable(
  high_salary,
  options = list(
    pageLength = 5,
    autoWidth = TRUE
  ),
  caption = "Daftar Karyawan Dengan Gajih lebih dari 6000"
)

4.1.1 Interpretasi

Berdasarkan hasil pengolahan data menggunakan perulangan dan kondisi pada bahasa pemrograman R, program melakukan proses penyaringan data karyawan dengan kriteria gaji lebih dari 6000. Setiap data karyawan pada dataset employees diperiksa satu per satu, kemudian data yang memenuhi kondisi tersebut dimasukkan ke dalam dataset baru bernama high_salary. Dataset ini hanya berisi dua informasi utama, yaitu nama karyawan dan besar gaji.

Hasil dari proses tersebut menunjukkan bahwa terdapat beberapa karyawan yang memiliki gaji di atas 6000, yaitu Joan, Alya, Dwi, dan Nabil. Data ini kemudian ditampilkan dalam bentuk tabel interaktif menggunakan library DT, sehingga pengguna dapat melihat, mengurutkan, dan menelusuri data dengan lebih mudah.

Secara keseluruhan, hasil output ini menunjukkan bahwa sebagian besar karyawan dalam dataset memiliki tingkat gaji yang relatif tinggi karena berada di atas batas yang telah ditentukan, yaitu 6000. Informasi ini dapat digunakan sebagai dasar untuk melakukan analisis lebih lanjut, seperti evaluasi struktur gaji atau pengelompokan karyawan berdasarkan tingkat pendapatan.

4.2 While Loop (Berhenti saat Manager ditemukan)

library(DT)

result <- data.frame()

i <- 1

while(i <= nrow(employees)){
  
  result <- rbind(
    result,
    data.frame(
      Name = employees$name[i],
      Position = employees$position[i]
    )
  )
  
  if(employees$position[i] == "Manager"){
    break
  }
  
  i <- i + 1
}

datatable(
  result,
  options = list(
    pageLength = 5,
    autoWidth = TRUE
  ),
  caption = "Daftar Karyawan Sampai Manajer"
)

4.2.1 Interpretasi

Berdasarkan hasil eksekusi program, kode tersebut menggunakan struktur perulangan while untuk membaca data karyawan pada dataset employees secara berurutan mulai dari baris pertama. Pada setiap iterasi, program akan mengambil informasi nama karyawan dan posisi jabatan, kemudian menyimpannya ke dalam dataset baru yang bernama result.

Proses perulangan akan terus berjalan hingga program menemukan karyawan yang memiliki posisi “Manager”. Ketika kondisi tersebut terpenuhi, perintah break akan menghentikan perulangan sehingga program tidak melanjutkan pembacaan data berikutnya. Dengan demikian, dataset result hanya berisi data karyawan dari baris pertama hingga karyawan yang memiliki posisi Manager.

Hasil akhir kemudian ditampilkan dalam bentuk tabel interaktif menggunakan library DT, yang memungkinkan pengguna untuk melihat data dengan lebih rapi serta melakukan pencarian atau pengurutan data secara langsung.

Secara keseluruhan, output dari program ini menunjukkan proses pengambilan sebagian data secara bertahap hingga mencapai kondisi tertentu, yaitu ketika ditemukan jabatan Manager. Pendekatan ini dapat digunakan untuk memahami bagaimana kontrol perulangan dan kondisi penghentian (break) bekerja dalam pengolahan data menggunakan bahasa pemrograman R.

4.3 Break (Berhenti jika Gaji > 10000)

library(DT)

result <- data.frame()

for(i in 1:nrow(employees)){
  
  if(employees$salary[i] > 10000){
    break
  }
  
  result <- rbind(
    result,
    data.frame(
      Nama = employees$name[i],
      Gaji = employees$salary[i]
    )
  )
}

datatable(
  result,
  options = list(
    pageLength = 5,
    autoWidth = TRUE
  ),
  caption = "Daftar Karyawan (Berhenti jika Gaji > 10000)"
)

4.3.1 Interpretasi

Berdasarkan hasil eksekusi program, kode tersebut menggunakan struktur perulangan for untuk membaca data karyawan pada dataset employees secara berurutan. Pada setiap iterasi, program akan memeriksa nilai gaji (salary) dari masing-masing karyawan.

Jika ditemukan karyawan dengan gaji lebih dari 10000, maka perintah break akan dijalankan sehingga perulangan langsung dihentikan dan program tidak melanjutkan proses ke data berikutnya. Sebelum kondisi tersebut terjadi, data nama karyawan dan gaji akan disimpan terlebih dahulu ke dalam dataset baru yang bernama result.

Hasil dari proses tersebut kemudian ditampilkan dalam bentuk tabel interaktif menggunakan library DT, sehingga pengguna dapat melihat data dengan lebih rapi serta melakukan pencarian atau pengurutan data secara langsung.

Secara keseluruhan, output ini menunjukkan bahwa program hanya menampilkan data karyawan hingga sebelum ditemukan karyawan dengan gaji lebih dari 10000. Hal ini menunjukkan penggunaan kontrol break dalam perulangan untuk menghentikan proses pengambilan data ketika suatu kondisi tertentu terpenuhi.

4.4 Continue / Next (Melewati Performa Average)

library(DT)

filtered <- data.frame()

for(i in 1:nrow(employees)){
  
  if(employees$performance[i] == "Average"){
    next
  }
  
  filtered <- rbind(
    filtered,
    data.frame(
      Nama = employees$name[i],
      Performa = employees$performance[i]
    )
  )
}

datatable(
  filtered,
  options = list(
    pageLength = 5,
    autoWidth = TRUE
  ),
  caption = "Employees with Performance Above Average"
)

4.4.1 Interpretasi

Berdasarkan hasil eksekusi program, kode tersebut menggunakan struktur perulangan for untuk membaca setiap data karyawan pada dataset employees. Pada setiap iterasi, program memeriksa nilai performance dari masing-masing karyawan.

Jika terdapat karyawan dengan performa “Average”, maka perintah next akan dijalankan sehingga program akan melewati data tersebut dan langsung melanjutkan ke iterasi berikutnya tanpa memasukkannya ke dalam dataset hasil. Sebaliknya, jika performa karyawan bukan “Average”, maka data nama karyawan dan kategori performanya akan disimpan ke dalam dataset baru yang bernama filtered.

Hasil dari proses tersebut kemudian ditampilkan dalam bentuk tabel interaktif menggunakan library DT, sehingga pengguna dapat melihat data dengan lebih rapi serta melakukan pencarian atau pengurutan data secara langsung.

Secara keseluruhan, output ini menunjukkan bahwa tabel yang ditampilkan hanya berisi karyawan dengan performa di atas kategori Average, yaitu karyawan dengan performa Good dan Very Good. Hal ini menunjukkan bagaimana penggunaan perintah next dalam perulangan dapat digunakan untuk mengabaikan data yang tidak memenuhi kriteria tertentu dalam proses pengolahan data.

5 Kesimpulan

Berdasarkan praktikum yang dilakukan dapat disimpulkan bahwa:

  1. Pernyataan kondisional memungkinkan program membuat keputusan berdasarkan kondisi tertentu.

  2. Perulangan (loops) mempermudah pemrosesan data yang jumlahnya banyak.

  3. Break digunakan untuk menghentikan perulangan ketika kondisi terpenuhi.

  4. Continue (Python) atau Next (R) digunakan untuk melewati iterasi tertentu tanpa menghentikan seluruh perulangan.

  5. Konsep ini sangat penting dalam analisis data dan pemrograman data science, terutama saat memproses dataset yang lebih besar.

6 Referensi

Data Science Labs. Data Science Programming – Syntax and Control Flow. https://bookdown.org/dsciencelabs/data_science_programming/02-Syntax-and-Control-Flow.html#practicum

LS0tDQp0aXRsZTogIiINCmF1dGhvcjogIkNoYW5kcmEgUml6YWwgQWxhbXN5YWggKDUyMjUwMDY4KSINCmRhdGU6ICJgciBmb3JtYXQoU3lzLkRhdGUoKSwgJyVkICVCICVZJylgIg0Kb3V0cHV0Og0KICBybWRmb3JtYXRzOjpyZWFkdGhlZG93bjoNCiAgICBzZWxmX2NvbnRhaW5lZDogdHJ1ZSANCiAgICBjc3M6IGNzcyBwbHVzIGh0bWwuY3NzDQogICAgdGh1bWJuYWlsczogdHJ1ZSAgICANCiAgICBsaWdodGJveDogdHJ1ZQ0KICAgIGdhbGxlcnk6IHRydWUNCiAgICBudW1iZXJfc2VjdGlvbnM6IHRydWUNCiAgICBsaWJfZGlyOiBsaWJzDQogICAgZGZfcHJpbnQ6ICJwYWdlZCINCiAgICBjb2RlX2ZvbGRpbmc6ICJzaG93Ig0KICAgIGNvZGVfZG93bmxvYWQ6IHllcw0KICAgIA0KLS0tDQoNCjxoMSBjbGFzcz0iaGVhZGVyLXRpdGxlIj5QcmFrdGlrdW0gUGVybnlhdGFhbiBLb25kaXNpb25hbCBkYW4gUGVydWxhbmdhbiBwYWRhIFB5dGhvbiBkYW4gUjwvaDE+DQogIA0KICA8ZGl2IGNsYXNzPSJwcm9maWxlLWNhcmQiPg0KICA8ZGl2IGNsYXNzPSJwcm9maWxlLWltYWdlIj4NCiAgPGltZyBpZD0iRm90byIgc3JjPSJodHRwczovL3Jhdy5naXRodWJ1c2VyY29udGVudC5jb20vY2hhbmRyYTI0MDIwNS1zdWRvL0NoYW5kcmEzL21haW4vR2FudGVuZy5qcGciIGFsdD0iTG9nbyIgc3R5bGU9IndpZHRoOjIwMHB4OyBkaXNwbGF5OiBibG9jazsgbWFyZ2luOiBhdXRvOyI+DQogIDwvZGl2Pg0KICANCiAgPGRpdiBjbGFzcz0icHJvZmlsZS1pbmZvIj4NCiAgPGgyPkNoYW5kcmEgUml6YWwgQWxhbXN5YWg8L2gyPg0KICA8cD5TdHVkZW50IE1ham9yaW5nIGluIERhdGEgU2NpZW5jZSBhdCBJVFNCPC9wPg0KICA8cD4qKk5JTSoqOiA1MjI1MDA2ODwvUD4NCiAgPFA+KipFbWFpbCoqOiBjaGFuZHJhMjQwMjA1QGdtYWlsLmNvbTwvcD4NCiAgDQogIDxkaXYgY2xhc3M9ImJhZGdlcyI+DQogIDxzcGFuIGNsYXNzPSJiYWRnZSBiYWRnZS1ibHVlIj5SIFByb2dyYW1taW5nPC9zcGFuPg0KICA8c3BhbiBjbGFzcz0iYmFkZ2UgYmFkZ2UtcmVkIj5EYXRhIFNjaWVuY2U8L3NwYW4+DQogIDxzcGFuIGNsYXNzPSJiYWRnZSBiYWRnZS1ncmVlbiI+U3RhdGlzdGljczwvc3Bhbj4NCiAgPC9kaXY+DQogIDwvZGl2Pg0KICA8L2Rpdj4NCi0tLSAgDQoNCiMgVHVqdWFuIFByYWt0aWt1bQ0KPGRpdiBjbGFzcz0iaW5mby1ib3giPg0KVHVqdWFuIGRhcmkgcHJha3Rpa3VtIGluaSBhZGFsYWg6DQoNCjEuIE1lbWFoYW1pIHBlbmdndW5hYW4gcGVybnlhdGFhbiBrb25kaXNpb25hbCAoaWYsIGlmLWVsc2UsIGlmLWVsaWYtZWxzZSkgZGFsYW0gcGVtcm9ncmFtYW4uDQoNCjIuIE1lbmdpbXBsZW1lbnRhc2lrYW4gcGVydWxhbmdhbiBtZW5nZ3VuYWthbiBmb3IgbG9vcCBkYW4gd2hpbGUgbG9vcC4NCg0KMy4gTWVtYWhhbWkgZnVuZ3NpIGJyZWFrIHVudHVrIG1lbmdoZW50aWthbiBwZXJ1bGFuZ2FuIGRhbiBjb250aW51ZS9uZXh0IHVudHVrIG1lbGV3YXRpIGl0ZXJhc2kgdGVydGVudHUuDQoNCjQuIE1lbmVyYXBrYW4ga29uc2VwIHRlcnNlYnV0IHVudHVrIG1lbmdhbmFsaXNpcyBkYXRhc2V0IHNlZGVyaGFuYSBtZW5nZW5haSBkYXRhIGthcnlhd2FuLg0KDQpLb25zZXAgaW5pIG1lbmdhY3UgcGFkYSBtYXRlcmkgQ29udHJvbCBGbG93IHBhZGEgbW9kdWwgcGVtcm9ncmFtYW4gZGF0YSBzY2llbmNlIHlhbmcgbWVuamVsYXNrYW4gYmFnYWltYW5hIHByb2dyYW0gZGFwYXQgbWVuZ2FtYmlsIGtlcHV0dXNhbiBkYW4gbWVsYWt1a2FuIHByb3NlcyBiZXJ1bGFuZyB0ZXJoYWRhcCBkYXRhLg0KPC9kaXY+DQoNCiMgRGF0YXNldCB5YW5nIERpZ3VuYWthbg0KPGRpdiBjbGFzcz0iaW5mby1ib3giPg0KRGF0YXNldCBkdW1teSB5YW5nIGRpZ3VuYWthbiBkYWxhbSBwcmFrdGlrdW0gaW5pIGFkYWxhaCBzZWJhZ2FpIGJlcmlrdXQ6DQpgYGB7cn0NCmxpYnJhcnkoRFQpDQojIE1lbWJ1YXQgZGF0YXNldCBrYXJ5YXdhbg0KZW1wbG95ZWVzIDwtIGRhdGEuZnJhbWUoDQogIElEID0gYygxLDIsMyw0LDUpLA0KICBOYW1hID0gYygiQmFnYXMiLCJKb2FuIiwiQWx5YSIsIkR3aSIsIk5hYmlsIiksDQogIFVzaWEgPSBjKDI1LDMwLDI3LDM1LDQwKSwNCiAgR2FqaSA9IGMoNTAwMCw3MDAwLDY1MDAsMTAwMDAsMTIwMDApLA0KICBQb3Npc2kgPSBjKCJTdGFmZiIsIlN1cGVydmlzb3IiLCJTdGFmZiIsIk1hbmFnZXIiLCJEaXJlY3RvciIpLA0KICBQZXJmb3JtYSA9IGMoIkdvb2QiLCJWZXJ5IEdvb2QiLCJBdmVyYWdlIiwiR29vZCIsIlZlcnkgR29vZCIpDQopDQoNCiMgTWVuYW1waWxrYW4gZGF0YXNldA0KZGF0YXRhYmxlKGVtcGxveWVlcykNCmBgYA0KRGF0YXNldCBpbmkgZGlndW5ha2FuIHVudHVrIG1lbGFrdWthbiBhbmFsaXNpcyBzZWRlcmhhbmEgc2VwZXJ0aSBwZXJoaXR1bmdhbiBib251cyBkYW4gc2VsZWtzaSBkYXRhIGJlcmRhc2Fya2FuIGtvbmRpc2kgdGVydGVudHUuDQo8L2Rpdj4NCg0KIyBQZXJueWF0YWFuIEtvbmRpc2lvbmFsIChDb25kaXRpb25hbCBTdGF0ZW1lbnRzKQ0KPGRpdiBjbGFzcz0iaW5mby1ib3giPg0KRGFsYW0gbW9kdWwgZGlqZWxhc2thbiBiYWh3YSBjb25kaXRpb25hbCBzdGF0ZW1lbnRzIGRpZ3VuYWthbiB1bnR1ayBtZW5lbnR1a2FuIHRpbmRha2FuIHByb2dyYW0gYmVyZGFzYXJrYW4ga29uZGlzaSB0ZXJ0ZW50dS4NCg0KUGFkYSBwcmFrdGlrdW0gaW5pIGJvbnVzIGthcnlhd2FuIGRpdGVudHVrYW4gYmVyZGFzYXJrYW4gcGVyZm9ybWE6DQoNCiogVmVyeSBHb29kIOKGkiAyMCUgZGFyaSBnYWppDQoNCiogR29vZCDihpIgMTAlIGRhcmkgZ2FqaQ0KDQoqIEF2ZXJhZ2Ug4oaSIDUlIGRhcmkgZ2FqaQ0KPC9kaXY+DQoNCiMjIEltcGxlbWVudGFzaQ0KPGRpdiBjbGFzcz0iaW5mby1ib3giPg0KYGBge3J9DQpsaWJyYXJ5KERUKQ0KZW1wbG95ZWVzIDwtIGRhdGEuZnJhbWUoDQogIG5hbWUgPSBjKCJCYWdhcyIsIkpvYW4iLCJBbHlhIiwiRHdpIiwiTmFiaWwiKSwNCiAgYWdlID0gYygyNSwzMCwyNywzNSw0MCksDQogIHNhbGFyeSA9IGMoNTAwMCw3MDAwLDY1MDAsMTAwMDAsMTIwMDApLA0KICBwb3NpdGlvbiA9IGMoIlN0YWZmIiwiU3VwZXJ2aXNvciIsIlN0YWZmIiwiTWFuYWdlciIsIkRpcmVjdG9yIiksDQogIHBlcmZvcm1hbmNlID0gYygiR29vZCIsIlZlcnkgR29vZCIsIkF2ZXJhZ2UiLCJHb29kIiwiVmVyeSBHb29kIikNCikNCmVtcGxveWVlcyRib251cyA8LSAwDQoNCmZvcihpIGluIDE6bnJvdyhlbXBsb3llZXMpKXsNCiAgDQogIGlmKGVtcGxveWVlcyRwZXJmb3JtYW5jZVtpXSA9PSAiVmVyeSBHb29kIil7DQogICAgDQogICAgZW1wbG95ZWVzJGJvbnVzW2ldIDwtIGVtcGxveWVlcyRzYWxhcnlbaV0gKiAwLjIwDQogICAgDQogIH0gZWxzZSBpZihlbXBsb3llZXMkcGVyZm9ybWFuY2VbaV0gPT0gIkdvb2QiKXsNCiAgICANCiAgICBlbXBsb3llZXMkYm9udXNbaV0gPC0gZW1wbG95ZWVzJHNhbGFyeVtpXSAqIDAuMTANCiAgICANCiAgfSBlbHNlIHsNCiAgICANCiAgICBlbXBsb3llZXMkYm9udXNbaV0gPC0gZW1wbG95ZWVzJHNhbGFyeVtpXSAqIDAuMDUNCiAgfQ0KfQ0KZGF0YXRhYmxlKA0KICBlbXBsb3llZXMsDQogIG9wdGlvbnMgPSBsaXN0KA0KICAgIHBhZ2VMZW5ndGggPSA1LA0KICAgIGF1dG9XaWR0aCA9IFRSVUUNCiAgKSwNCiAgY2FwdGlvbiA9ICJFbXBsb3llZSBCb251cyBSZXBvcnQiDQopDQpgYGANCjwvZGl2Pg0KDQojIyMgVmlzdWFsaXNhc2kgQm9udXMgS2FyeWF3YW4NCg0KYGBge3IgZWNobyA9IEZBTFNFLCB3YXJuaW5nID0gRkFMU0UsIG1lc3NhZ2UgPSBGQUxTRX0NCiAgDQpsaWJyYXJ5KGdncGxvdDIpDQpsaWJyYXJ5KHBsb3RseSkNCg0KIyBWaXN1YWxpc2FzaSBCb251cyBLYXJ5YXdhbg0KcCA8LSBnZ3Bsb3QoZW1wbG95ZWVzLCBhZXMoDQogIHggPSBuYW1lLA0KICB5ID0gYm9udXMsDQogIGZpbGwgPSBwZXJmb3JtYW5jZSwNCiAgdGV4dCA9IHBhc3RlKA0KICAgICJOYW1lOiIsIG5hbWUsDQogICAgIjxicj5TYWxhcnk6Iiwgc2FsYXJ5LA0KICAgICI8YnI+Qm9udXM6IiwgYm9udXMsDQogICAgIjxicj5QZXJmb3JtYW5jZToiLCBwZXJmb3JtYW5jZQ0KICApDQopKSArDQogIGdlb21fYmFyKHN0YXQgPSAiaWRlbnRpdHkiKSArDQogIGxhYnMoDQogICAgeCA9ICJFbXBsb3llZSBOYW1lIiwNCiAgICB5ID0gIkJvbnVzIEFtb3VudCINCiAgKSArDQogIHRoZW1lX21pbmltYWwoKQ0KDQojIE1lbmd1YmFoIG1lbmphZGkgZ3JhZmlrIGludGVyYWt0aWYNCmdncGxvdGx5KHAsIHRvb2x0aXAgPSAidGV4dCIpDQpgYGANCg0KIyMjIEludGVycHJldGFzaQ0KPGRpdiBjbGFzcz0iaW5mby1ib3giPg0KQmVyZGFzYXJrYW4gdmlzdWFsaXNhc2kgYm9udXMga2FyeWF3YW4sIHRlcmxpaGF0IGJhaHdhIHBlcmZvcm1hIGtlcmphIGRhbiBiZXNhcm55YSBnYWppIG1lbXBlbmdhcnVoaSBqdW1sYWggYm9udXMgeWFuZyBkaXRlcmltYS4gS2FyeWF3YW4gZGVuZ2FuIHBlcmZvcm1hIFZlcnkgR29vZCBtZW1wZXJvbGVoIGJvbnVzIGxlYmloIGJlc2FyIGthcmVuYSBtZW5kYXBhdGthbiAyMCUgZGFyaSBnYWppLCBzZWRhbmdrYW4gcGVyZm9ybWEgR29vZCBtZW5kYXBhdGthbiAxMCUgZGFuIEF2ZXJhZ2Ugc2ViZXNhciA1JS4gU2VsYWluIGl0dSwgc2VtYWtpbiB0aW5nZ2kgZ2FqaSBrYXJ5YXdhbiBtYWthIHNlbWFraW4gYmVzYXIgcHVsYSBub21pbmFsIGJvbnVzIHlhbmcgZGl0ZXJpbWEga2FyZW5hIGJvbnVzIGRpaGl0dW5nIGJlcmRhc2Fya2FuIHBlcnNlbnRhc2UgZ2FqaS4gUGFkYSBkYXRhIHRlcnNlYnV0LCBOYWJpbCBtZW1pbGlraSBib251cyB0ZXJ0aW5nZ2kga2FyZW5hIG1lbWlsaWtpIGdhamkgcGFsaW5nIGJlc2FyIGRhbiBwZXJmb3JtYSBWZXJ5IEdvb2QsIHNlbWVudGFyYSBBbHlhIG1lbWlsaWtpIGJvbnVzIHRlcmVuZGFoIGthcmVuYSBwZXJmb3JtYW55YSBiZXJhZGEgcGFkYSBrYXRlZ29yaSBBdmVyYWdlLiBIYWwgaW5pIG1lbnVuanVra2FuIGJhaHdhIHNpc3RlbSBib251cyBkaXJhbmNhbmcgdW50dWsgbWVtYmVyaWthbiBwZW5naGFyZ2FhbiBsZWJpaCBrZXBhZGEga2FyeWF3YW4gZGVuZ2FuIGtpbmVyamEgeWFuZyBsZWJpaCBiYWlrLg0KPC9kaXY+DQoNCiMgUGVydWxhbmdhbiAoTG9vcHMpDQo8ZGl2IGNsYXNzPSJpbmZvLWJveCI+DQpQZXJ1bGFuZ2FuIGRpZ3VuYWthbiB1bnR1ayBtZW1wcm9zZXMgZGF0YSBzZWNhcmEgYmVydWxhbmcgaGluZ2dhIGtvbmRpc2kgdGVydGVudHUgdGVycGVudWhpLg0KDQpKZW5pcyBwZXJ1bGFuZ2FuIHlhbmcgZGlndW5ha2FuIGRhbGFtIHByYWt0aWt1bSBpbmkgYWRhbGFoOg0KDQoqIEZvciBMb29wDQoNCiogV2hpbGUgTG9vcA0KDQoqIEJyZWFrDQoNCiogQ29udGludWUgLyBOZXh0DQo8L2Rpdj4NCg0KIyMgRm9yIExvb3AgKE1lbmFtcGlsa2FuIEdhamkgPiA2MDAwKQ0KPGRpdiBjbGFzcz0iaW5mby1ib3giPg0KYGBge3J9DQojIE1lbWFuZ2dpbCBsaWJyYXJ5IHVudHVrIHRhYmVsIGludGVyYWt0aWYNCmxpYnJhcnkoRFQpDQoNCiMgTWVueWltcGFuIGhhc2lsIGthcnlhd2FuIGRlbmdhbiBnYWppID4gNjAwMA0KaGlnaF9zYWxhcnkgPC0gZGF0YS5mcmFtZSgpDQoNCmZvcihpIGluIDE6bnJvdyhlbXBsb3llZXMpKXsNCg0KICBpZihlbXBsb3llZXMkc2FsYXJ5W2ldID4gNjAwMCl7DQoNCiAgICBoaWdoX3NhbGFyeSA8LSByYmluZCgNCiAgICAgIGhpZ2hfc2FsYXJ5LA0KICAgICAgZGF0YS5mcmFtZSgNCiAgICAgICAgTmFtZSA9IGVtcGxveWVlcyRuYW1lW2ldLA0KICAgICAgICBTYWxhcnkgPSBlbXBsb3llZXMkc2FsYXJ5W2ldDQogICAgICApDQogICAgKQ0KDQogIH0NCn0NCg0KIyBNZW5hbXBpbGthbiBoYXNpbCBkYWxhbSB0YWJlbCBpbnRlcmFrdGlmDQpkYXRhdGFibGUoDQogIGhpZ2hfc2FsYXJ5LA0KICBvcHRpb25zID0gbGlzdCgNCiAgICBwYWdlTGVuZ3RoID0gNSwNCiAgICBhdXRvV2lkdGggPSBUUlVFDQogICksDQogIGNhcHRpb24gPSAiRGFmdGFyIEthcnlhd2FuIERlbmdhbiBHYWppaCBsZWJpaCBkYXJpIDYwMDAiDQopDQpgYGANCjwvZGl2Pg0KDQojIyMgSW50ZXJwcmV0YXNpDQo8ZGl2IGNsYXNzPSJpbmZvLWJveCI+DQpCZXJkYXNhcmthbiBoYXNpbCBwZW5nb2xhaGFuIGRhdGEgbWVuZ2d1bmFrYW4gcGVydWxhbmdhbiBkYW4ga29uZGlzaSBwYWRhIGJhaGFzYSBwZW1yb2dyYW1hbiBSLCBwcm9ncmFtIG1lbGFrdWthbiBwcm9zZXMgcGVueWFyaW5nYW4gZGF0YSBrYXJ5YXdhbiBkZW5nYW4ga3JpdGVyaWEgZ2FqaSBsZWJpaCBkYXJpIDYwMDAuIFNldGlhcCBkYXRhIGthcnlhd2FuIHBhZGEgZGF0YXNldCBlbXBsb3llZXMgZGlwZXJpa3NhIHNhdHUgcGVyIHNhdHUsIGtlbXVkaWFuIGRhdGEgeWFuZyBtZW1lbnVoaSBrb25kaXNpIHRlcnNlYnV0IGRpbWFzdWtrYW4ga2UgZGFsYW0gZGF0YXNldCBiYXJ1IGJlcm5hbWEgaGlnaF9zYWxhcnkuIERhdGFzZXQgaW5pIGhhbnlhIGJlcmlzaSBkdWEgaW5mb3JtYXNpIHV0YW1hLCB5YWl0dSBuYW1hIGthcnlhd2FuIGRhbiBiZXNhciBnYWppLg0KDQpIYXNpbCBkYXJpIHByb3NlcyB0ZXJzZWJ1dCBtZW51bmp1a2thbiBiYWh3YSB0ZXJkYXBhdCBiZWJlcmFwYSBrYXJ5YXdhbiB5YW5nIG1lbWlsaWtpIGdhamkgZGkgYXRhcyA2MDAwLCB5YWl0dSBKb2FuLCBBbHlhLCBEd2ksIGRhbiBOYWJpbC4gRGF0YSBpbmkga2VtdWRpYW4gZGl0YW1waWxrYW4gZGFsYW0gYmVudHVrIHRhYmVsIGludGVyYWt0aWYgbWVuZ2d1bmFrYW4gbGlicmFyeSBEVCwgc2VoaW5nZ2EgcGVuZ2d1bmEgZGFwYXQgbWVsaWhhdCwgbWVuZ3VydXRrYW4sIGRhbiBtZW5lbHVzdXJpIGRhdGEgZGVuZ2FuIGxlYmloIG11ZGFoLg0KDQpTZWNhcmEga2VzZWx1cnVoYW4sIGhhc2lsIG91dHB1dCBpbmkgbWVudW5qdWtrYW4gYmFod2Egc2ViYWdpYW4gYmVzYXIga2FyeWF3YW4gZGFsYW0gZGF0YXNldCBtZW1pbGlraSB0aW5na2F0IGdhamkgeWFuZyByZWxhdGlmIHRpbmdnaSBrYXJlbmEgYmVyYWRhIGRpIGF0YXMgYmF0YXMgeWFuZyB0ZWxhaCBkaXRlbnR1a2FuLCB5YWl0dSA2MDAwLiBJbmZvcm1hc2kgaW5pIGRhcGF0IGRpZ3VuYWthbiBzZWJhZ2FpIGRhc2FyIHVudHVrIG1lbGFrdWthbiBhbmFsaXNpcyBsZWJpaCBsYW5qdXQsIHNlcGVydGkgZXZhbHVhc2kgc3RydWt0dXIgZ2FqaSBhdGF1IHBlbmdlbG9tcG9rYW4ga2FyeWF3YW4gYmVyZGFzYXJrYW4gdGluZ2thdCBwZW5kYXBhdGFuLg0KPC9kaXY+DQoNCiMjIFdoaWxlIExvb3AgKEJlcmhlbnRpIHNhYXQgTWFuYWdlciBkaXRlbXVrYW4pDQo8ZGl2IGNsYXNzPSJpbmZvLWJveCI+DQpgYGB7cn0NCmxpYnJhcnkoRFQpDQoNCnJlc3VsdCA8LSBkYXRhLmZyYW1lKCkNCg0KaSA8LSAxDQoNCndoaWxlKGkgPD0gbnJvdyhlbXBsb3llZXMpKXsNCiAgDQogIHJlc3VsdCA8LSByYmluZCgNCiAgICByZXN1bHQsDQogICAgZGF0YS5mcmFtZSgNCiAgICAgIE5hbWUgPSBlbXBsb3llZXMkbmFtZVtpXSwNCiAgICAgIFBvc2l0aW9uID0gZW1wbG95ZWVzJHBvc2l0aW9uW2ldDQogICAgKQ0KICApDQogIA0KICBpZihlbXBsb3llZXMkcG9zaXRpb25baV0gPT0gIk1hbmFnZXIiKXsNCiAgICBicmVhaw0KICB9DQogIA0KICBpIDwtIGkgKyAxDQp9DQoNCmRhdGF0YWJsZSgNCiAgcmVzdWx0LA0KICBvcHRpb25zID0gbGlzdCgNCiAgICBwYWdlTGVuZ3RoID0gNSwNCiAgICBhdXRvV2lkdGggPSBUUlVFDQogICksDQogIGNhcHRpb24gPSAiRGFmdGFyIEthcnlhd2FuIFNhbXBhaSBNYW5hamVyIg0KKQ0KYGBgDQo8L2Rpdj4NCg0KIyMjIEludGVycHJldGFzaQ0KPGRpdiBjbGFzcz0iaW5mby1ib3giPg0KQmVyZGFzYXJrYW4gaGFzaWwgZWtzZWt1c2kgcHJvZ3JhbSwga29kZSB0ZXJzZWJ1dCBtZW5nZ3VuYWthbiBzdHJ1a3R1ciBwZXJ1bGFuZ2FuIHdoaWxlIHVudHVrIG1lbWJhY2EgZGF0YSBrYXJ5YXdhbiBwYWRhIGRhdGFzZXQgZW1wbG95ZWVzIHNlY2FyYSBiZXJ1cnV0YW4gbXVsYWkgZGFyaSBiYXJpcyBwZXJ0YW1hLiBQYWRhIHNldGlhcCBpdGVyYXNpLCBwcm9ncmFtIGFrYW4gbWVuZ2FtYmlsIGluZm9ybWFzaSBuYW1hIGthcnlhd2FuIGRhbiBwb3Npc2kgamFiYXRhbiwga2VtdWRpYW4gbWVueWltcGFubnlhIGtlIGRhbGFtIGRhdGFzZXQgYmFydSB5YW5nIGJlcm5hbWEgcmVzdWx0Lg0KDQpQcm9zZXMgcGVydWxhbmdhbiBha2FuIHRlcnVzIGJlcmphbGFuIGhpbmdnYSBwcm9ncmFtIG1lbmVtdWthbiBrYXJ5YXdhbiB5YW5nIG1lbWlsaWtpIHBvc2lzaSAiTWFuYWdlciIuIEtldGlrYSBrb25kaXNpIHRlcnNlYnV0IHRlcnBlbnVoaSwgcGVyaW50YWggYnJlYWsgYWthbiBtZW5naGVudGlrYW4gcGVydWxhbmdhbiBzZWhpbmdnYSBwcm9ncmFtIHRpZGFrIG1lbGFuanV0a2FuIHBlbWJhY2FhbiBkYXRhIGJlcmlrdXRueWEuIERlbmdhbiBkZW1pa2lhbiwgZGF0YXNldCByZXN1bHQgaGFueWEgYmVyaXNpIGRhdGEga2FyeWF3YW4gZGFyaSBiYXJpcyBwZXJ0YW1hIGhpbmdnYSBrYXJ5YXdhbiB5YW5nIG1lbWlsaWtpIHBvc2lzaSBNYW5hZ2VyLg0KDQpIYXNpbCBha2hpciBrZW11ZGlhbiBkaXRhbXBpbGthbiBkYWxhbSBiZW50dWsgdGFiZWwgaW50ZXJha3RpZiBtZW5nZ3VuYWthbiBsaWJyYXJ5IERULCB5YW5nIG1lbXVuZ2tpbmthbiBwZW5nZ3VuYSB1bnR1ayBtZWxpaGF0IGRhdGEgZGVuZ2FuIGxlYmloIHJhcGkgc2VydGEgbWVsYWt1a2FuIHBlbmNhcmlhbiBhdGF1IHBlbmd1cnV0YW4gZGF0YSBzZWNhcmEgbGFuZ3N1bmcuDQoNClNlY2FyYSBrZXNlbHVydWhhbiwgb3V0cHV0IGRhcmkgcHJvZ3JhbSBpbmkgbWVudW5qdWtrYW4gcHJvc2VzIHBlbmdhbWJpbGFuIHNlYmFnaWFuIGRhdGEgc2VjYXJhIGJlcnRhaGFwIGhpbmdnYSBtZW5jYXBhaSBrb25kaXNpIHRlcnRlbnR1LCB5YWl0dSBrZXRpa2EgZGl0ZW11a2FuIGphYmF0YW4gTWFuYWdlci4gUGVuZGVrYXRhbiBpbmkgZGFwYXQgZGlndW5ha2FuIHVudHVrIG1lbWFoYW1pIGJhZ2FpbWFuYSBrb250cm9sIHBlcnVsYW5nYW4gZGFuIGtvbmRpc2kgcGVuZ2hlbnRpYW4gKGJyZWFrKSBiZWtlcmphIGRhbGFtIHBlbmdvbGFoYW4gZGF0YSBtZW5nZ3VuYWthbiBiYWhhc2EgcGVtcm9ncmFtYW4gUi4NCjwvZGl2Pg0KDQojIyBCcmVhayAoQmVyaGVudGkgamlrYSBHYWppID4gMTAwMDApDQo8ZGl2IGNsYXNzPSJpbmZvLWJveCI+DQpgYGB7cn0NCmxpYnJhcnkoRFQpDQoNCnJlc3VsdCA8LSBkYXRhLmZyYW1lKCkNCg0KZm9yKGkgaW4gMTpucm93KGVtcGxveWVlcykpew0KICANCiAgaWYoZW1wbG95ZWVzJHNhbGFyeVtpXSA+IDEwMDAwKXsNCiAgICBicmVhaw0KICB9DQogIA0KICByZXN1bHQgPC0gcmJpbmQoDQogICAgcmVzdWx0LA0KICAgIGRhdGEuZnJhbWUoDQogICAgICBOYW1hID0gZW1wbG95ZWVzJG5hbWVbaV0sDQogICAgICBHYWppID0gZW1wbG95ZWVzJHNhbGFyeVtpXQ0KICAgICkNCiAgKQ0KfQ0KDQpkYXRhdGFibGUoDQogIHJlc3VsdCwNCiAgb3B0aW9ucyA9IGxpc3QoDQogICAgcGFnZUxlbmd0aCA9IDUsDQogICAgYXV0b1dpZHRoID0gVFJVRQ0KICApLA0KICBjYXB0aW9uID0gIkRhZnRhciBLYXJ5YXdhbiAoQmVyaGVudGkgamlrYSBHYWppID4gMTAwMDApIg0KKQ0KYGBgDQo8L2Rpdj4NCg0KIyMjIEludGVycHJldGFzaQ0KPGRpdiBjbGFzcz0iaW5mby1ib3giPg0KQmVyZGFzYXJrYW4gaGFzaWwgZWtzZWt1c2kgcHJvZ3JhbSwga29kZSB0ZXJzZWJ1dCBtZW5nZ3VuYWthbiBzdHJ1a3R1ciBwZXJ1bGFuZ2FuIGZvciB1bnR1ayBtZW1iYWNhIGRhdGEga2FyeWF3YW4gcGFkYSBkYXRhc2V0IGVtcGxveWVlcyBzZWNhcmEgYmVydXJ1dGFuLiBQYWRhIHNldGlhcCBpdGVyYXNpLCBwcm9ncmFtIGFrYW4gbWVtZXJpa3NhIG5pbGFpIGdhamkgKHNhbGFyeSkgZGFyaSBtYXNpbmctbWFzaW5nIGthcnlhd2FuLg0KDQpKaWthIGRpdGVtdWthbiBrYXJ5YXdhbiBkZW5nYW4gZ2FqaSBsZWJpaCBkYXJpIDEwMDAwLCBtYWthIHBlcmludGFoIGJyZWFrIGFrYW4gZGlqYWxhbmthbiBzZWhpbmdnYSBwZXJ1bGFuZ2FuIGxhbmdzdW5nIGRpaGVudGlrYW4gZGFuIHByb2dyYW0gdGlkYWsgbWVsYW5qdXRrYW4gcHJvc2VzIGtlIGRhdGEgYmVyaWt1dG55YS4gU2ViZWx1bSBrb25kaXNpIHRlcnNlYnV0IHRlcmphZGksIGRhdGEgbmFtYSBrYXJ5YXdhbiBkYW4gZ2FqaSBha2FuIGRpc2ltcGFuIHRlcmxlYmloIGRhaHVsdSBrZSBkYWxhbSBkYXRhc2V0IGJhcnUgeWFuZyBiZXJuYW1hIHJlc3VsdC4NCg0KSGFzaWwgZGFyaSBwcm9zZXMgdGVyc2VidXQga2VtdWRpYW4gZGl0YW1waWxrYW4gZGFsYW0gYmVudHVrIHRhYmVsIGludGVyYWt0aWYgbWVuZ2d1bmFrYW4gbGlicmFyeSBEVCwgc2VoaW5nZ2EgcGVuZ2d1bmEgZGFwYXQgbWVsaWhhdCBkYXRhIGRlbmdhbiBsZWJpaCByYXBpIHNlcnRhIG1lbGFrdWthbiBwZW5jYXJpYW4gYXRhdSBwZW5ndXJ1dGFuIGRhdGEgc2VjYXJhIGxhbmdzdW5nLg0KDQpTZWNhcmEga2VzZWx1cnVoYW4sIG91dHB1dCBpbmkgbWVudW5qdWtrYW4gYmFod2EgcHJvZ3JhbSBoYW55YSBtZW5hbXBpbGthbiBkYXRhIGthcnlhd2FuIGhpbmdnYSBzZWJlbHVtIGRpdGVtdWthbiBrYXJ5YXdhbiBkZW5nYW4gZ2FqaSBsZWJpaCBkYXJpIDEwMDAwLiBIYWwgaW5pIG1lbnVuanVra2FuIHBlbmdndW5hYW4ga29udHJvbCBicmVhayBkYWxhbSBwZXJ1bGFuZ2FuIHVudHVrIG1lbmdoZW50aWthbiBwcm9zZXMgcGVuZ2FtYmlsYW4gZGF0YSBrZXRpa2Egc3VhdHUga29uZGlzaSB0ZXJ0ZW50dSB0ZXJwZW51aGkuDQo8L2Rpdj4NCg0KIyMgQ29udGludWUgLyBOZXh0IChNZWxld2F0aSBQZXJmb3JtYSBBdmVyYWdlKQ0KPGRpdiBjbGFzcz0iaW5mby1ib3giPg0KYGBge3J9DQpsaWJyYXJ5KERUKQ0KDQpmaWx0ZXJlZCA8LSBkYXRhLmZyYW1lKCkNCg0KZm9yKGkgaW4gMTpucm93KGVtcGxveWVlcykpew0KICANCiAgaWYoZW1wbG95ZWVzJHBlcmZvcm1hbmNlW2ldID09ICJBdmVyYWdlIil7DQogICAgbmV4dA0KICB9DQogIA0KICBmaWx0ZXJlZCA8LSByYmluZCgNCiAgICBmaWx0ZXJlZCwNCiAgICBkYXRhLmZyYW1lKA0KICAgICAgTmFtYSA9IGVtcGxveWVlcyRuYW1lW2ldLA0KICAgICAgUGVyZm9ybWEgPSBlbXBsb3llZXMkcGVyZm9ybWFuY2VbaV0NCiAgICApDQogICkNCn0NCg0KZGF0YXRhYmxlKA0KICBmaWx0ZXJlZCwNCiAgb3B0aW9ucyA9IGxpc3QoDQogICAgcGFnZUxlbmd0aCA9IDUsDQogICAgYXV0b1dpZHRoID0gVFJVRQ0KICApLA0KICBjYXB0aW9uID0gIkVtcGxveWVlcyB3aXRoIFBlcmZvcm1hbmNlIEFib3ZlIEF2ZXJhZ2UiDQopDQpgYGANCjwvZGl2Pg0KDQojIyMgSW50ZXJwcmV0YXNpDQo8ZGl2IGNsYXNzPSJpbmZvLWJveCI+DQpCZXJkYXNhcmthbiBoYXNpbCBla3Nla3VzaSBwcm9ncmFtLCBrb2RlIHRlcnNlYnV0IG1lbmdndW5ha2FuIHN0cnVrdHVyIHBlcnVsYW5nYW4gZm9yIHVudHVrIG1lbWJhY2Egc2V0aWFwIGRhdGEga2FyeWF3YW4gcGFkYSBkYXRhc2V0IGVtcGxveWVlcy4gUGFkYSBzZXRpYXAgaXRlcmFzaSwgcHJvZ3JhbSBtZW1lcmlrc2EgbmlsYWkgcGVyZm9ybWFuY2UgZGFyaSBtYXNpbmctbWFzaW5nIGthcnlhd2FuLg0KDQpKaWthIHRlcmRhcGF0IGthcnlhd2FuIGRlbmdhbiBwZXJmb3JtYSAiQXZlcmFnZSIsIG1ha2EgcGVyaW50YWggbmV4dCBha2FuIGRpamFsYW5rYW4gc2VoaW5nZ2EgcHJvZ3JhbSBha2FuIG1lbGV3YXRpIGRhdGEgdGVyc2VidXQgZGFuIGxhbmdzdW5nIG1lbGFuanV0a2FuIGtlIGl0ZXJhc2kgYmVyaWt1dG55YSB0YW5wYSBtZW1hc3Vra2FubnlhIGtlIGRhbGFtIGRhdGFzZXQgaGFzaWwuIFNlYmFsaWtueWEsIGppa2EgcGVyZm9ybWEga2FyeWF3YW4gYnVrYW4gIkF2ZXJhZ2UiLCBtYWthIGRhdGEgbmFtYSBrYXJ5YXdhbiBkYW4ga2F0ZWdvcmkgcGVyZm9ybWFueWEgYWthbiBkaXNpbXBhbiBrZSBkYWxhbSBkYXRhc2V0IGJhcnUgeWFuZyBiZXJuYW1hIGZpbHRlcmVkLg0KDQpIYXNpbCBkYXJpIHByb3NlcyB0ZXJzZWJ1dCBrZW11ZGlhbiBkaXRhbXBpbGthbiBkYWxhbSBiZW50dWsgdGFiZWwgaW50ZXJha3RpZiBtZW5nZ3VuYWthbiBsaWJyYXJ5IERULCBzZWhpbmdnYSBwZW5nZ3VuYSBkYXBhdCBtZWxpaGF0IGRhdGEgZGVuZ2FuIGxlYmloIHJhcGkgc2VydGEgbWVsYWt1a2FuIHBlbmNhcmlhbiBhdGF1IHBlbmd1cnV0YW4gZGF0YSBzZWNhcmEgbGFuZ3N1bmcuDQoNClNlY2FyYSBrZXNlbHVydWhhbiwgb3V0cHV0IGluaSBtZW51bmp1a2thbiBiYWh3YSB0YWJlbCB5YW5nIGRpdGFtcGlsa2FuIGhhbnlhIGJlcmlzaSBrYXJ5YXdhbiBkZW5nYW4gcGVyZm9ybWEgZGkgYXRhcyBrYXRlZ29yaSBBdmVyYWdlLCB5YWl0dSBrYXJ5YXdhbiBkZW5nYW4gcGVyZm9ybWEgR29vZCBkYW4gVmVyeSBHb29kLiBIYWwgaW5pIG1lbnVuanVra2FuIGJhZ2FpbWFuYSBwZW5nZ3VuYWFuIHBlcmludGFoIG5leHQgZGFsYW0gcGVydWxhbmdhbiBkYXBhdCBkaWd1bmFrYW4gdW50dWsgbWVuZ2FiYWlrYW4gZGF0YSB5YW5nIHRpZGFrIG1lbWVudWhpIGtyaXRlcmlhIHRlcnRlbnR1IGRhbGFtIHByb3NlcyBwZW5nb2xhaGFuIGRhdGEuDQo8L2Rpdj4NCg0KDQojIEtlc2ltcHVsYW4NCjxkaXYgY2xhc3M9ImluZm8tYm94Ij4NCkJlcmRhc2Fya2FuIHByYWt0aWt1bSB5YW5nIGRpbGFrdWthbiBkYXBhdCBkaXNpbXB1bGthbiBiYWh3YToNCg0KMS4gUGVybnlhdGFhbiBrb25kaXNpb25hbCBtZW11bmdraW5rYW4gcHJvZ3JhbSBtZW1idWF0IGtlcHV0dXNhbiBiZXJkYXNhcmthbiBrb25kaXNpIHRlcnRlbnR1Lg0KDQoyLiBQZXJ1bGFuZ2FuIChsb29wcykgbWVtcGVybXVkYWggcGVtcm9zZXNhbiBkYXRhIHlhbmcganVtbGFobnlhIGJhbnlhay4NCg0KMy4gQnJlYWsgZGlndW5ha2FuIHVudHVrIG1lbmdoZW50aWthbiBwZXJ1bGFuZ2FuIGtldGlrYSBrb25kaXNpIHRlcnBlbnVoaS4NCg0KNC4gQ29udGludWUgKFB5dGhvbikgYXRhdSBOZXh0IChSKSBkaWd1bmFrYW4gdW50dWsgbWVsZXdhdGkgaXRlcmFzaSB0ZXJ0ZW50dSB0YW5wYSBtZW5naGVudGlrYW4gc2VsdXJ1aCBwZXJ1bGFuZ2FuLg0KDQo1LiBLb25zZXAgaW5pIHNhbmdhdCBwZW50aW5nIGRhbGFtIGFuYWxpc2lzIGRhdGEgZGFuIHBlbXJvZ3JhbWFuIGRhdGEgc2NpZW5jZSwgdGVydXRhbWEgc2FhdCBtZW1wcm9zZXMgZGF0YXNldCB5YW5nIGxlYmloIGJlc2FyLg0KPC9kaXY+DQoNCiMgUmVmZXJlbnNpDQo8ZGl2IGNsYXNzPSJpbmZvLWJveCI+DQpEYXRhIFNjaWVuY2UgTGFicy4NCkRhdGEgU2NpZW5jZSBQcm9ncmFtbWluZyDigJMgU3ludGF4IGFuZCBDb250cm9sIEZsb3cuDQpodHRwczovL2Jvb2tkb3duLm9yZy9kc2NpZW5jZWxhYnMvZGF0YV9zY2llbmNlX3Byb2dyYW1taW5nLzAyLVN5bnRheC1hbmQtQ29udHJvbC1GbG93Lmh0bWwjcHJhY3RpY3VtDQo8L2Rpdj4=