Re: [PHP-DEV] preg_replace oddity [exploitable]

2003-02-03 Thread James E. Flemer
On Mon, 3 Feb 2003, Maxim Maletsky wrote:

> "James E. Flemer" <[EMAIL PROTECTED]> wrote... :
>
> > I found a more evil example:
> >
> >  >   $a = "___! `rm -rf /tmp/sess_*` !___";
> >   $b = preg_replace("/!(.*)!/e", "print(\\1);", $a);
> > ?>
> >
> > This happily executes "rm -rf /tmp/sess_*".  I will not
> > give out more examples, but if one examines the code for
> > addslashes() it is quite obvious what you can an cannot do
> > here.  Thus it is clearly a Bad Thing for someone to use
> > preg_replace with the /e modifier and not use quotes around
> > the \\n or $n backrefs.
> >
> > The docs should be updated to include a very noticeable
> > warning about this hole.  I am contemplating possible
> > solutions for this problem...
--snip--
>
> In fact, /e eval()uates the code. It does with the replaced result just
> what eval() does with a string PHP code. At most, it could be noted in
> docs.

Yes, I am aware of that, that is what /e is for.  The issue
is not that it eval()s the code, the issue is weather or
not the backrefs (\\1 or $1 etc) are enclosed in single
quotes.  The preg_replace()  code calls php_addslashes() on
the backref data, so if the backref is enclosed in quotes
then there is no way to do anything malicious.  However if
a PHP coder writes a script that uses preg_replace()
without placing quotes around a backref, and the subject
(arg 1) of the function can be supplied by the remote user,
then the remote user can easily insert potentially
dangerous code that will be executed on the server with the
running permision of the web server.

Now consider the use of this expliot in conjunction with a
know local-user expliot for some OS.  PHP provides
convinient easy access to execute arbitrary commands as a
local user...  I think it should be explicitly stated in
the docs for preg_replace() that Bad Things can occur if
backrefs are not enclosed in single quotes, and that mildly
bad things can occur if they are enclosed in double quotes
(i.e. variable expansion of possibly sensative local
variables).

-James


-- 
PHP Development Mailing List 
To unsubscribe, visit: http://www.php.net/unsub.php




Re: [PHP-DEV] preg_replace oddity [exploitable]

2003-02-03 Thread Maxim Maletsky

"James E. Flemer" <[EMAIL PROTECTED]> wrote... :

> I found a more evil example:
> 
>$a = "___! `rm -rf /tmp/sess_*` !___";
>   $b = preg_replace("/!(.*)!/e", "print(\\1);", $a);
> ?>
> 
> This happily executes "rm -rf /tmp/sess_*".  I will not
> give out more examples, but if one examines the code for
> addslashes() it is quite obvious what you can an cannot do
> here.  Thus it is clearly a Bad Thing for someone to use
> preg_replace with the /e modifier and not use quotes around
> the \\n or $n backrefs.
> 
> The docs should be updated to include a very noticeable
> warning about this hole.  I am contemplating possible
> solutions for this problem...
> 
> Also as a side note, it does not seem to be possible to use
> 'echo' as part of the expression, print must be used.  (Yes
> I know why, just pointing it out.)
> 
> -James
> 
> 
> On Thu, 30 Jan 2003, James E. Flemer wrote:
> 
> > Can someone explain what is going on here:
> >
> > --- foo.php ---
> >  >   $a = "___! 52); echo(42 !___";
> >   $b = preg_replace("/!(.*)!/e", "print(\\1);", $a);
> >   print("\n---\na: $a\nb: $b\n");
> > ?>
> > --- end ---
> > --- output ---
> > 52
> > ---
> > a: ___! 52); echo(42 !___
> > b: ___1___
> > --- end ---
> >
> > I understand that one is supposed to use single quotes
> > around the \\1 in the above preg_replace.  But what happens
> > when they do not?  Clearly the echo(42); is not executed,
> > and it is not printed by print().  Even more interesting is
> > if you put something like echo(\"42 in $a, then you get a
> > bunch of errors including:
> >   Fatal error - Failed evaluating code:
> >   print( 52); echo(\"42 );


In fact, /e eval()uates the code. It does with the replaced result just
what eval() does with a string PHP code. At most, it could be noted in
docs.



--
Maxim Maletsky
[EMAIL PROTECTED]


-- 
PHP Development Mailing List 
To unsubscribe, visit: http://www.php.net/unsub.php




Re: [PHP-DEV] preg_replace oddity [exploitable]

2003-02-02 Thread James E. Flemer
I found a more evil example:



This happily executes "rm -rf /tmp/sess_*".  I will not
give out more examples, but if one examines the code for
addslashes() it is quite obvious what you can an cannot do
here.  Thus it is clearly a Bad Thing for someone to use
preg_replace with the /e modifier and not use quotes around
the \\n or $n backrefs.

The docs should be updated to include a very noticeable
warning about this hole.  I am contemplating possible
solutions for this problem...

Also as a side note, it does not seem to be possible to use
'echo' as part of the expression, print must be used.  (Yes
I know why, just pointing it out.)

-James


On Thu, 30 Jan 2003, James E. Flemer wrote:

> Can someone explain what is going on here:
>
> --- foo.php ---
>$a = "___! 52); echo(42 !___";
>   $b = preg_replace("/!(.*)!/e", "print(\\1);", $a);
>   print("\n---\na: $a\nb: $b\n");
> ?>
> --- end ---
> --- output ---
> 52
> ---
> a: ___! 52); echo(42 !___
> b: ___1___
> --- end ---
>
> I understand that one is supposed to use single quotes
> around the \\1 in the above preg_replace.  But what happens
> when they do not?  Clearly the echo(42); is not executed,
> and it is not printed by print().  Even more interesting is
> if you put something like echo(\"42 in $a, then you get a
> bunch of errors including:
>   Fatal error - Failed evaluating code:
>   print( 52); echo(\"42 );
>
> It seems like preg_replace() is doing some strange things,
> and might be something that could be exploitable if a
> remote user can supply the first argument, and the second
> argument does not enclose \\n options.
>
> -James
>
>
>


-- 
PHP Development Mailing List 
To unsubscribe, visit: http://www.php.net/unsub.php