Velocity Reviews

Velocity Reviews (http://www.velocityreviews.com/forums/index.php)
-   Python (http://www.velocityreviews.com/forums/f43-python.html)
-   -   Is this a safe use of eval? (http://www.velocityreviews.com/forums/t744102-is-this-a-safe-use-of-eval.html)

Frank Millman 02-24-2011 08:48 AM

Is this a safe use of eval?
 
Hi all

I know that the use of 'eval' is discouraged because of the dangers of
executing untrusted code.

Here is a variation that seems safe to me, but I could be missing something.

I have a class, and the class has one or more methods which accept various
arguments and return a result.

I want to accept a method name and arguments in string form, and 'eval' it
to get the result.

Assume I have an instance called my_inst, and a method called 'calc_area',
with arguments w and h.

I then receive my_string = 'calc_area(100, 200)'.

>>> result = eval('my_inst.{0}'.format(my_string))


This will only work if the string contains a valid method name with valid
arguments.

Can anyone see anything wrong with this?

Thanks

Frank Millman



Paul Rubin 02-24-2011 08:58 AM

Re: Is this a safe use of eval?
 
"Frank Millman" <frank@chagford.com> writes:
> I then receive my_string = 'calc_area(100, 200)'.
>>>> result = eval('my_inst.{0}'.format(my_string))

> This will only work if the string contains a valid method name with
> valid arguments.
>
> Can anyone see anything wrong with this?


Um, yes. What are valid arguments? Are you going to eval them?

If they can only be literals, maybe you could use something like

from ast import literal_eval
method_name = 'calc_area'
args = literal_eval('(100,200)')
result = getattr(my_inst, method_name)(*args)

but even that is risky in a hostile data environment.

Peter Otten 02-24-2011 09:01 AM

Re: Is this a safe use of eval?
 
Frank Millman wrote:

> Hi all
>
> I know that the use of 'eval' is discouraged because of the dangers of
> executing untrusted code.
>
> Here is a variation that seems safe to me, but I could be missing
> something.
>
> I have a class, and the class has one or more methods which accept various
> arguments and return a result.
>
> I want to accept a method name and arguments in string form, and 'eval' it
> to get the result.
>
> Assume I have an instance called my_inst, and a method called 'calc_area',
> with arguments w and h.
>
> I then receive my_string = 'calc_area(100, 200)'.
>
>>>> result = eval('my_inst.{0}'.format(my_string))

>
> This will only work if the string contains a valid method name with valid
> arguments.
>
> Can anyone see anything wrong with this?


How do you prevent that a malicious source sends you

my_string = 'calc_area(__import__("os").system("rm important_file") or 100,
200)'

instead?


Web Dreamer 02-24-2011 03:59 PM

Re: Is this a safe use of eval?
 
Frank Millman a écrit ce jeudi 24 février 2011 09:48 dans
<mailman.366.1298537346.1189.python-list@python.org> :

> Hi all
>
> I know that the use of 'eval' is discouraged because of the dangers of
> executing untrusted code.
>
> Here is a variation that seems safe to me, but I could be missing
> something.
>
> I have a class, and the class has one or more methods which accept various
> arguments and return a result.
>
> I want to accept a method name and arguments in string form, and 'eval' it
> to get the result.
>
> Assume I have an instance called my_inst, and a method called 'calc_area',
> with arguments w and h.
>
> I then receive my_string = 'calc_area(100, 200)'.
>
>>>> result = eval('my_inst.{0}'.format(my_string))

>
> This will only work if the string contains a valid method name with valid
> arguments.


I'd do it that way:

>>> class My_Class(object):

.... def calc_area(self, a, b):
.... return a*b
....
>>> my_inst = My_Class()
>>> my_string = 'calc_area(100, 200)'
>>> my_func_and_args = my_string.split('(')
>>> my_func = my_func_and_args.pop(0)
>>> my_args = my_func_and_args[0].strip(')')
>>> my_args = my_args.split(',')
>>> my_args = [int(arg) for arg in my_args]
>>> if hasattr(my_inst, my_func):

.... getattr(my_inst,my_func)(*my_args)
....
20000


And no eval is ever performed.

--
Web Dreamer


Nobody 02-25-2011 05:15 AM

Re: Is this a safe use of eval?
 
On Thu, 24 Feb 2011 15:24:51 +0200, Frank Millman wrote:

> Thanks, Christian. I had a look at that recipe, but I must say that Paul's
> suggestion is much simpler -
>
> from ast import literal_eval
> method_name = 'calc_area'
> args = literal_eval('(100,200)')
> result = getattr(my_inst, method_name)(*args)
>
> In my case the arguments are all strings or integers, so it looks as if this
> approach should be safe. Do you see any problem with it?


Only that you may need a fairly recent version of the ast module; the
first attempt at literal_eval was a bit too ... literal, e.g. it couldn't
handle negative numbers (Python doesn't have negative integer literals;
evaluating "-10" applies the negation operator to the integer 10).




All times are GMT. The time now is 07:25 AM.

Powered by vBulletin®. Copyright ©2000 - 2014, vBulletin Solutions, Inc.
SEO by vBSEO ©2010, Crawlability, Inc.