Найти - Пользователи
Полная версия: Шифрование кода Python
Начало » Python для новичков » Шифрование кода Python
1 2 3 4 5 6
george
>я думаю таким же способом можно заюзать и Pyrex
достаточно сильные ограничения (все вкусности языка нельзя использовать)

> даже до pyc не добраться
легко. видел пример в python cookbook, по-моему, через marshal делалось.

Но ссылка на boo интересная
> вот можно его забрать вместе со средой разработки - http://www.sharpdevelop.net/OpenSource/SD/Download/
Андрей Светлов
Как я понимаю, http://boo.codehaus.org

Только это уже не Питон. Сборная солянка, рвущая базовые принципы языка.
У ван Россума волосы должны бы дыбом стать.
А так что… Занятно
george
>Сборная солянка, рвущая базовые принципы языка.
О чем ты?
Андрей Светлов
Это уже не Питон. Достаточно одной статической типизации. И еще множество новых ключевых слов. Меняется как грамматика языка, так и его семантика.
Boo, скорее - попытка создать новый язык, тесно сидящий на CLR, с заимствованием синтаксических конструкций из классического Питона, но никак не его порт а ля IronPython.
Новый, может быть, и получится. Задумка интересная. Только Питон лишь рядом лежал.
Писать нужно по другому и думать по другому тоже. Альтернатива С# - возможно. Но Шарп так легко не сдвинешь.
Так что - совсем новый язык, лишь отчасти похожий на Питон. Примерно как Ява или Шарп похожи на С++.

pyc можно развалить через marshal. Но не в исходник, а в пикод. Так же, как и неоттранслированный CLR экзешник. Разбираться с этим - грустное занятие.
Но если все pyc положить в архив собственного сочинения и приделать коротенький загрузчик по аналогу стандартного zipimport - задача сильно усложняется. Чтобы вытащить pyc потребуется поковыряться с дизассемблером и отладчиком. Как я говорил, такое уже делал. Примерно за день.
Но это уже лирика. Остапа понесло :)
george
>Достаточно одной статической типизации.
Динамическая типизация реализована не хуже Питонной (cm duck type)
есть опция компилятора - все динамически.
>И еще множество новых ключевых слов.
Это да, но можно их и не использовать, если не хочешь использовать доп. фичи , напр. тип видимости, локи объектов, и пр. см на сайте отличия Boo Python, там статья.
>Писать нужно по другому и думать по другому тоже.
Вообще не согласен. Портировал все свои исходники - переделки в основном - библиотечные классы разные. Код заметно уменьшается - на 25-30%.
О разнице в скорости - она фантастическая. Еще немалый плюс - идеальная (бесшовная) интеграция со всеми языками (> 50 на net платформе).
Кусок пиши на Haskell, другой на шарпе, третий на плюсах, и все будет как однородная система.
>отчасти похожий на Питон
все лучшее из Питона взято, lambda заменена на более компактную конструкцию Ruby - {x, y | x + y}.
то бишь попробуйте, проверяйте. от Питона я счас полностью отказался. в пользу Boo разумеется.
george
>pyc можно развалить через marshal. Но не в исходник, а в пикод.
pyc и есть пикод. вот способ восстановления исходника.
совпадение версий надо - иначе могут исключения вылетать

import marshal, dis
f = open('Mail.pyc', ‘rb’)
f.read(8)
s = marshal.load(f)
dis.dis(s)
mnf
Андрей Светлов
Немного переделал загрузчик и zipimporter - чтобы на зип было непохоже. Конечно, можно было дизассемблером расковырять…
Можно уточнить по поводу сложности взлома? Насколько я понимаю pythonXX.dll все же остался снаружи (ведь если слинковаться статически, то нельзя будет использовать внешние .pyd файлы, а они почти всегда нужны). Тогда, мы добавляем свой built-in модуль в pythonXX.dll, который просто сохраняет все загружаемые sys.modules, потом вызываем decompyle, и вот он source code. То же относится и к другим pyd/dll. Может и этой схеме что-то не так, или за это время Вы придумали более надежный способ?
Это действительно интересный вопрос, ведь сейчас за бортом остаются многие профессиональные разработчики, которые (скажем, из-за политики компании) не могут позволить себе распространять исходные тексты программ.
Андрей Светлов
Ага, можно и механизм импорта подкрутить, чтобы все вернуть к виду “как-бы pyc”.

Под сложностью понимаю то, что нужно будет изрядно потрудиться (создавая свой пропатченый pythonXX.dll, как в вашем варианте). Возня немалая, и, будете смеяться, большинству программистов такое будет либо не по силам, либо просто лень (лень чаще, конечго же).
Дальше. Питоновский код после дизассемблера не очень-то похож на исходники. Читать его не очень легко. Но - можно. Можно в результате кропотливого труда и все исходники воспроизвести.
Это примерно так же легко, как посмотреть на С++ с обилием своих же dll (имена светятся) или Яву/Шарп без фускатора. Да и с фускатором люди смотрят… А кто этим занимается? И, главное, ради чего?

Компании обычно нужно, чтобы Мастер Самоделкин не полез интенсивно изучать, модифицировать и распростронять. Подрывая источник дохода. Когда это сильно затруднено (приз не оправдывает затраченные усилия) - схема работает. Независимо от языка программирования. Если нет - то никак не убережешься.

Пример - игры. Компьютерные. Выходит новая игрушка - и быстро появляется патчик к ней. Который отучает от вредных привычек и позволяет передать игру куму-свату-брату. Борются с этим - и бесполезно, похоже. Только Интернет способен как-то защитить online-проект от стремления использовать продукт в обход владельца.
Но кто изучает исходники этой игрушки? Кому оно надо? Взломали, от привычки искать родной CD/DVD отучили - вот вам и счастье. Прилагались бы еще и исходники - поизучали бы желающие. Нет их - ну и ладно. И так хорошо. Играется себе народ, и проблемой исходников не озабочен - он и слова такого не знает.
Yurietc
import marshal, dis
f = open('Mail.pyc', ‘rb’)
f.read(8)
s = marshal.load(f)
dis.dis(s)
Что-то не совсем исходник :

import marshal, dis
>>> f = open('comparison.pyc', ‘rb’)
>>> f.read(8)
'\xb3\xf2\r\n@\x84\x9cF'
>>> s = marshal.load(f)
>>> dis.dis(s)
1 0 LOAD_CONST 0 (<code object com at 013F9260, file “C:\Python25\comparison.py”, line 1>)
3 MAKE_FUNCTION 0
6 STORE_NAME 0 (com)
9 LOAD_CONST 1 (None)
12 RETURN_VALUE
mnf
Андрей Светлов
Под сложностью понимаю то, что нужно будет изрядно потрудиться (создавая свой пропатченый pythonXX.dll, как в вашем варианте). Возня немалая, и, будете смеяться, большинству программистов такое будет либо не по силам, либо просто лень (лень чаще, конечго же).
Я - не профессионал, но это заняло у меня 14 минут (включая чтение кода, правку и компиляцию):
michael@michael:~/work/patches/python-2.5.1$ cat a.py
def foo():
print ‘hello, world!’
michael@michael:~/work/patches/python-2.5.1$ hexdump -C a.pyc
00000000 6d f2 0d 0a 6e fa c2 46 63 00 00 00 00 00 00 00 |m…n..Fc…….|
00000010 00 01 00 00 00 40 00 00 00 73 0d 00 00 00 64 00 |…..@…s….d.|
00000020 00 84 00 00 5a 00 00 64 01 00 53 28 02 00 00 00 |….Z..d..S(….|
00000030 63 00 00 00 00 00 00 00 00 01 00 00 00 43 00 00 |c…………C..|
00000040 00 73 09 00 00 00 64 01 00 47 48 64 00 00 53 28 |.s….d..GHd..S(|
00000050 02 00 00 00 4e 73 0d 00 00 00 68 65 6c 6c 6f 2c |….Ns….hello,|
00000060 20 77 6f 72 6c 64 21 28 00 00 00 00 28 00 00 00 | world!(….(…|
00000070 00 28 00 00 00 00 28 00 00 00 00 74 04 00 00 00 |.(….(….t….|
00000080 61 2e 70 79 74 03 00 00 00 66 6f 6f 01 00 00 00 |a.pyt….foo….|
00000090 73 02 00 00 00 00 01 4e 28 01 00 00 00 52 01 00 |s……N(….R..|
000000a0 00 00 28 01 00 00 00 52 01 00 00 00 28 00 00 00 |..(….R….(…|
000000b0 00 28 00 00 00 00 52 00 00 00 00 74 01 00 00 00 |.(….R….t….|
000000c0 3f 01 00 00 00 73 00 00 00 00 |?….s….|

Теперь пакуем все в ZIP для py2exe, далее zipimporter будет инициализировать модули, а мы уже вставили fprintf()ы в marshal.c. результат для ZIP с вызовом “import a”:
PyMarshal_ReadObjectFromString: len = 200
0000 | 63 00 00 00 00 00 00 00 00 01 00 00 00 40 00 00
0010 | 00 73 0d 00 00 00 64 00 00 7c 00 00 5a 00 00 64
0020 | 01 00 53 28 02 00 00 00 63 00 00 00 00 00 00 00
0030 | 00 01 00 00 00 43 00 00 00 73 09 00 00 00 64 01
0040 | 00 47 48 64 00 00 53 28 02 00 00 00 4e 73 0d 00
0050 | 00 00 68 65 6c 6c 6f 2c 20 77 6f 72 6c 64 21 28
0060 | 00 00 00 00 28 00 00 00 00 28 00 00 00 00 28 00
0070 | 00 00 00 73 04 00 00 00 61 2e 70 79 74 03 00 00
0080 | 00 66 6f 6f 01 00 00 00 73 02 00 00 00 00 01 4e
0090 | 28 01 00 00 00 52 00 00 00 00 28 00 00 00 00 28
00a0 | 00 00 00 00 28 00 00 00 00 73 04 00 00 00 61 2e
00b0 | 70 79 73 08 00 00 00 3c 6d 6f 64 75 6c 65 3e 01
00c0 | 00 00 00 73 00 00 00 00
Как видим, это и есть тот самый a.pyc без заголовка (8 bytes). Вот и все.

Андрей Светлов
Дальше. Питоновский код после дизассемблера не очень-то похож на исходники. Читать его не очень легко. Но - можно. Можно в результате кропотливого труда и все исходники воспроизвести.
Тут слегка патченый decompyle (a вообще-то, если лень возиться, платная служба есть в сети - всё сделают за вас)
michael@michael:~/work/patches/tmp$ decompyle a.pyc
Wed Aug 15 21:09:01 2007
# emacs-mode: -*- python-*-

def foo():
print ‘hello, world!’


# local variables:
# tab-width: 4
+++ okay decompyling a.pyc 7
decompyled 1 files: 1 okay, 0 failed, 0 verify failed
Wed Aug 15 21:09:01 2007

Совсем как настоящий :) Я уже попробовал и на более серьезных проектах - все работает.

Так что по поводу “изрядно потрудиться” и “кропотливого труда”, как то не согласуется с четвертью часа. Согласитесь?

Я ведь почему начал интересоваться и нашел ваш сайт через googlе: хочется попробовать перевести один небольшой коммерческий проект на python, чтобы оценить плюсы и минусы (и немножко отдохнуть от C++ :) ). Может быть посоветуете какой-нибудь более надежный метод защиты исходного текста (кроме перехода на open-source, лицензионных ограничений и т.п.)?
This is a "lo-fi" version of our main content. To view the full version with more information, formatting and images, please click here.
Powered by DjangoBB