2012-11-09 2 views
26

Если я открываю интерактивный режим и тип:Можете ли вы восстановиться после переназначения __builtins__ в python?

__builtins__ = 0 # breaks everything 

я полностью разбитое сессию? Если да, то что происходит за кулисами, чтобы назначить __builtins__ встроенному модулю, который не может обрабатываться интерпретатором? Если нет, как я могу оправиться от этого?

Лишь немногие из моих собственных попыток исправить:

  • Любая попытка импортировать что-нибыдь приводит к ошибке «ImportError не __import__ нашли»
  • все функции я могу использовать, чтобы сделать что-нибудь другое, чем оценить численные выражения разбиты
  • Существует еще одна переменная __package__, которая все еще доступна, но я не знаю, можно ли/как ее использовать.

ответ

29

Обычно вы можете получить доступ ко всему, что вам нужно, даже если __builtins__ удален. Это просто вопрос копания достаточно далеко. Например:

Python 2.7.3 (default, Apr 10 2012, 23:31:26) [MSC v.1500 32 bit (Intel)] on win32 
Type "help", "copyright", "credits" or "license" for more information. 
>>> __builtins__ = 0 
>>> open 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
NameError: name 'open' is not defined 
>>> dir 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
NameError: name 'dir' is not defined 
>>> int 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
NameError: name 'int' is not defined 
>>> float 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
NameError: name 'float' is not defined 
>>> 
>>> __builtins__ = [t for t in().__class__.__bases__[0].__subclasses__() if 'warning' in t.__name__][0]()._module.__builtins__ 
>>> 
>>> open 
<built-in function open> 
>>> int 
<type 'int'> 
>>> float 
<type 'float'> 
>>> 

Для объяснения того, что, черт возьми, только что произошло здесь, читайте Eval really is dangerous, где подобные методы используются, чтобы показать, что вы не можете безопасно выполнять ненадежный код Python.

+0

Просто попробовал запустить его в python 3 .. получил ошибку. Примечательно, что это: [t для t in() .__ класс __.__ основания __ [0] .__ подклассы __(), если «warning» в t .__ name__] расширяется до [] при попытке запустить его. Может быть, это проблема с python 3 vs 2? –

+0

Слайк! Есть ли способ полностью полностью разойти сеанс? – acjay

+4

@HartSimha: Python 2 разрешает ограниченный режим, если встроенные в текущий кадр отличаются от встроенных интерпретаторов.Поскольку ограниченный режим был удален в Python 3, легко изменить этот ответ, чтобы получить '__builtins__' из функции:' __builtins__ = [t для t in() .__ class __.__ base __.__ подклассы __(), если t .__ name__ == 'Sized '] [0] .__ Len __.__ глобалы __ [' __ __ встроенные команды '] '. – eryksun

3

В основном беспорядок с защищенными и зарезервированными именами означает нарушение вашей сессии, иногда без возможности восстановления.

Например, вы можете ввести в оболочку:

True = False # The chaos begins! 

Это не возможно с другими языками программирования, но питона позволяет вам делать то, что вы хотите, даже если это будет нарушать все.

+0

Я получаю SyntaxError при вводе True = False, даже в сломанной оболочке. Если сеанс полностью нарушен, то как \ _ \ _ builtins \ _ \ _ получает назначение на модуль в python в первую очередь. Я предполагаю, что интерпретатор инициализирует его с помощью неясного утверждения и, возможно, своего рода доступ к файлам низкого уровня. Но если нет, то как ** IS ** присваивается. –

+7

Это работает только в Python 2. Python 3 не позволит вам назначать вещи ключевым словам. Но даже в Python 2 это легко исправлено: 'False = (False не False)' и 'True = not False', и вы вернулись к оригиналам. – poke

3

Вы правы; вы можете практически сломать сеанс Python. Я сомневаюсь, что есть способ полностью уничтожить его - видя, что ответ Неда был для меня откровением.

Будучи очень динамичным языком, Python дает вам много веревки, чтобы повесить себя. Не смотри на это как на недостаток; общий лозунг Python гласит, что «мы все соглашаемся с взрослыми здесь». Если вы понимаете язык и действительно знаете, что делаете, у вас есть безумный контроль над всеми аспектами Python.

+2

Это действительно так. Это также является причиной того, почему нет модификаторов доступности, таких как 'public' и' private' для членов. При использовании чего-то вы должны оставаться вне внутренней реализации, если не знаете точно, что делаете. – poke

Смежные вопросы