Created
August 8, 2020 11:38
-
-
Save Alemiz112/e2785465bc0e492a055a9a42298fd566 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
function virion_infect(Phar $virus, Phar $host, string $virusName): void{ | |
$host->startBuffering(); | |
/* Check to make sure virion.yml exists in the virion */ | |
if(!isset($virus["virion.yml"])){ | |
echo "virion.yml not found"; | |
return; | |
} | |
$virusPath = "phar://" . str_replace(DIRECTORY_SEPARATOR, "/", $virus->getPath()) . "/"; | |
$virionYml = yaml_parse(file_get_contents($virusPath . "virion.yml")); | |
if(!is_array($virionYml)){ | |
echo "Corrupted virion.yml, could not activate virion $virusName"; | |
return; | |
} | |
/* Check to make sure plugin.yml exists in the plugin */ | |
if(!isset($host["plugin.yml"])){ | |
echo "plugin.yml not found in host"; | |
return; | |
} | |
$hostPath = "phar://" . str_replace(DIRECTORY_SEPARATOR, "/", $host->getPath()) . "/"; | |
$pluginYml = yaml_parse(file_get_contents($hostPath . "plugin.yml")); | |
if(!is_array($pluginYml)){ | |
echo "Corrupted plugin.yml found in plugin host"; | |
return; | |
} | |
/* Infection Log. File that keeps all the virions injected into the plugin */ | |
$infectionLog = isset($host["virus-infections.json"]) ? json_decode(file_get_contents($hostPath . "virus-infections.json"), true) : []; | |
/* Virion injection process now starts */ | |
$genus = $virionYml["name"]; | |
$antigen = $virionYml["antigen"]; | |
foreach($infectionLog as $old){ | |
if($old["antigen"] === $antigen){ | |
echo "Plugin is already infected with $virusName"; | |
return; | |
} | |
} | |
$antibody = getPrefix($pluginYml) . $antigen; | |
$infectionLog[$antibody] = $virionYml; | |
echo "Using antibody $antibody for virion $genus ({$antigen})"; | |
$hostPharPath = "phar://" . str_replace(DIRECTORY_SEPARATOR, "/", $host->getPath()); | |
$hostChanges = 0; | |
foreach(new RecursiveIteratorIterator(new RecursiveDirectoryIterator($hostPharPath)) as $name => $chromosome){ | |
if($chromosome->isDir()){ | |
continue; | |
} | |
if($chromosome->getExtension() !== "php"){ | |
continue; | |
} | |
$rel = cut_prefix($name, $hostPharPath); | |
$data = change_dna($original = file_get_contents($name), $antigen, $antibody, $hostChanges); | |
if($data !== ""){ | |
$host[$rel] = $data; | |
} | |
} | |
$restriction = "src/" . str_replace("\\", "/", $antigen) . "/"; | |
$ligase = "src/" . str_replace("\\", "/", $antibody) . "/"; | |
$viralChanges = 0; | |
foreach(new RecursiveIteratorIterator($virus) as $name => $genome){ | |
if($genome->isDir()){ | |
continue; | |
} | |
$rel = cut_prefix($name, "phar://" . str_replace(DIRECTORY_SEPARATOR, "/", $virus->getPath()) . "/"); | |
if(strpos($rel, "resources/") === 0){ | |
$host[$rel] = file_get_contents($name); | |
}elseif(strpos($rel, "src/") === 0){ | |
if(strpos($rel, $restriction) !== 0){ | |
echo "Warning: File $rel in virion is not under the antigen $antigen ($restriction)"; | |
$newRel = $rel; | |
}else{ | |
$newRel = $ligase . cut_prefix($rel, $restriction); | |
} | |
$data = change_dna(file_get_contents($name), $antigen, $antibody, $viralChanges); | |
$host[$newRel] = $data; | |
} | |
} | |
$host["virus-infections.json"] = json_encode($infectionLog); | |
//$virus->stopBuffering(); | |
$host->stopBuffering(); | |
echo "Shaded $hostChanges references in plugin and $viralChanges references in $virusName."; | |
} | |
function getPrefix(array $pluginYml): string{ | |
$main = $pluginYml["main"]; | |
$mainArray = explode("\\", $main); | |
array_pop($mainArray); | |
$path = implode("\\", $mainArray); | |
return $path . "\\libs\\"; | |
} | |
function cut_prefix(string $string, string $prefix): string{ | |
if(strpos($string, $prefix) !== 0){ | |
throw new AssertionError("\$string does not start with \$prefix:\n$string\n$prefix"); | |
} | |
return substr($string, strlen($prefix)); | |
} | |
function change_dna(string $chromosome, string $antigen, string $antibody, &$count = 0): string{ | |
$tokens = token_get_all($chromosome); | |
$tokens[] = ""; // should not be valid though | |
foreach($tokens as $offset => $token){ | |
if(!is_array($token) or $token[0] !== T_WHITESPACE){ | |
list($id, $str, $line) = is_array($token) ? $token : [ | |
-1, | |
$token, | |
$line ?? 1 | |
]; | |
if(isset($init, $current, $prefixToken)){ | |
if($current === "" && $prefixToken === T_USE and $id === T_FUNCTION || $id === T_CONST){ | |
continue; | |
}elseif($id === T_NS_SEPARATOR || $id === T_STRING){ | |
$current .= $str; | |
}elseif(!($current === "" && $prefixToken === T_USE and $id === T_FUNCTION || $id === T_CONST)){ | |
// end of symbol reference | |
if(strpos($current, $antigen) === 0){ // case-sensitive! | |
$new = $antibody . substr($current, strlen($antigen)); | |
for($o = $init + 1; $o < $offset; ++$o){ | |
if($tokens[$o][0] === T_NS_SEPARATOR || $tokens[$o][0] === T_STRING){ | |
$tokens[$o][1] = $new; | |
$new = ""; // will write nothing after the first time | |
} | |
} | |
++$count; | |
}elseif(stripos($current, $antigen) === 0){ | |
throw new RuntimeException("[WARNING] Not replacing FQN $current case-insensitively."); | |
} | |
unset($init, $current, $prefixToken); | |
} | |
}else{ | |
if($id === T_NS_SEPARATOR || $id === T_NAMESPACE || $id === T_USE){ | |
$init = $offset; | |
$current = ""; | |
$prefixToken = $id; | |
} | |
} | |
} | |
} | |
$ret = ""; | |
foreach($tokens as $token){ | |
$ret .= is_array($token) ? $token[1] : $token; | |
} | |
return $ret; | |
} | |
$virus = new Phar($argv[1]); | |
$host = new Phar($argv[2]); | |
virion_infect($virus, $host, $argv[1]); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment