2013-05-23 41 views
7

Chúng ta biết Python của eval() là ácLàm thế nào an toàn là symPify của sympify (<string>) .evalf()?

http://nedbatchelder.com/blog/201206/eval_really_is_dangerous.html

và chủ đề xuyên suốt StackOverflow đề nghị sử dụng SymPy của evalf().

Là một người mới sử dụng Python, tôi thực sự không thể thuyết phục bản thân rằng evalf() là an toàn vì tôi thiếu kỹ năng. Bất cứ ai có thể xây dựng trên những gì evalf() nào (khác nhau)?

+0

Không có đề xuất nào để sử dụng 'evalf' thay vì' eval' vì chúng không có điểm chung. Có những gợi ý để sử dụng 'sympify' thay vì' eval', nhưng (từ quan điểm bảo mật) chúng bị sai lầm vì chúng giống nhau về cơ bản. – Krastanov

Trả lời

7

Không có gì chung giữa python eval là và sympy evalf (sau này là để tính giá trị số của cây biểu sympy và nó có để làm với phân tích, trong khi eval là tất cả về phân tích một chuỗi và đánh giá nó như là nếu nó là mã). Mặt khác, sympify cũng nguy hiểm như eval, bởi vì nó thực sự sử dụng eval.

Có hai chế độ cơ bản, trong đó sympify được sử dụng và có lẽ đó là một ý tưởng tồi mà họ đã trộn lẫn trong các chức năng tương tự:

  • sympify(some_object) sẽ trả về một đại diện của đối tượng phù hợp hơn để sử dụng trong một CAS, như chuyển int(1) vào sympy.Integer(1)

  • sympify("some_text") sẽ phân tích văn bản gần như trực tiếp thông qua eval (tìm kiếm cho việc nhập khẩu từ sympy.parsing hiện diện trong sympify và theo dõi nó). Nó an toàn hơn vì có một số ràng buộc nhưng nó là không an toàn.

+0

Cảm ơn bạn đã trả lời. Bạn có thể vui lòng xây dựng trên chế độ cơ bản thứ hai, 'sympify (" một số văn bản ")', và làm thế nào điều này có thể được khai thác độc hại? Ví dụ: ví dụ về ví dụ của [Ned Batchelder's eval dangerous] (http://nedbatchelder.com/blog/201206/eval_really_is_dangerous.html) có hoạt động trong SymPy không? EG gọi 'f = sympy.sympify ('__ import __ (" os ")')' không cho tôi một đối tượng có thể gọi được. –

+2

OK, tôi có thể truy cập vào 'subprocess.Popen' bằng cách sử dụng sympify và chạy lệnh hệ thống, EG' f = sympy.sympify ("" "[] .__ class __.__ base __.__ lớp con __() [158] ('ls ') "" ")' liệt kê nội dung thư mục của tôi. Từ đó chỉ là một bước đơn giản để 'rm -rf \'. Làm tốt lắm [@Krastanov] (http://stackoverflow.com/users/669329/krastanov) bạn đã chứng minh rằng sympy là ** không ** an toàn! Sympy nguy hiểm. –