Дипломы, курсовые, рефераты, контрольные...
Срочная помощь в учёбе

Шифрование данных с помощью алгоритма DES

КурсоваяПомощь в написанииУзнать стоимостьмоей работы

В начале над ключом шифра выполняется операция B, которая сводится к выбору определенных бит и их перестановке, как это показано в таблице 6. Причем, первые четыре строки определяют, как выбираются биты последовательности C (0) (первым битом C (0) будет бит 57 бит ключа шифра, затем бит 49 и т. д., а последними битами биты 44 и 36 ключа шифра), а следующие четыре строки — как выбираются биты… Читать ещё >

Шифрование данных с помощью алгоритма DES (реферат, курсовая, диплом, контрольная)

Муниципальное образовательное учреждение Средняя общеобразовательная школа № 1

Курсовой проект по информатике и программированию на тему:

Шифрование данных с помощью алгоритма DES

Выполнила: Мартьянова Юлия Ученица 10 «А» класса Руководитель: Еремеев С.В.

Муром 2011

1. Процесс шифрования алгоритма DES5

1.1 Процесс расшифрования

1.2 Процесс получения ключей

2. Спецификация программы

2.1 Список процедур и функций

2.2 Описание интерфейса пользователя Заключение Список использованной литературы Приложение, А Приложение Б

В данной работе рассматривается разработка приложения для шифрования данных с помощью алгоритма DES. Данное приложение предназначено для шифрования и защиты информации. Полученное индивидуальное задание по курсовой работе было выполнено в среде программирования DELPHI 7. Эта среда выбрана, так как она глубоко изучалась во время обучения, и хорошо отражает современные возможности программирования. В результате выполнения задания была создана программа, которая сочетает в себе: лёгкость в обращении, простоту интерфейса, возможность легко протестировать.

Данная программа наглядно демонстрирует сущность работы алгоритма шифрования данных DES (DataEncryptionSystem).

DES представляет собой блочный шифр, он шифрует данные 64-битовыми блоками. С одного конца алгоритма вводится 64-битовый блок открытого текста, а с другого конца выходит 64-битовый блок шифротекста. DES является симметричным алгоритмом: для шифрования и дешифрования используются одинаковые алгоритм и ключ (за исключением небольших отличий в использовании ключа).

Длина ключа равна 56 битам. (Ключ обычно представляется 64-битовым числом, но каждый восьмой бит используется для проверки четности и игнорируется.) Безопасность полностью определяется ключом.

При описании алгоритма шифрования используются следующие обозначения. Если L и R — последовательности бит, то через LR будем обозначать конкатенацию (операция склеивания объектов линейной структуры, обычно строк) последовательностей L и R, т. е. последовательность бит, размерность которой равна сумме размерностей L и R. В этой последовательности биты последовательности R следуют за битами последовательности L. Конкатенация битовых строк является ассоциативной, то есть запись ABCDE, означает, что за битами последовательности A, следуют, биты последовательности B, затем C и т. д. Символом + будем обозначать операцию побитового сложения.

1. Процесс шифрования алгоритма DES

Схема шифрования алгоритма DES указана на Рис.1

Процесс шифрования данных поясняется Рис.2

Исходный текст — блок 64 бит.

Процесс шифрования состоит в начальной перестановке, 16 циклах шифрования и конечной перестановке.

Рис. 1 Схема шифрования алгоритма DES

Сначала 64 бита входной последовательности перестанавливаются в соответствии с таблицей 1. Таким образом, бит 58 входной последовательности становится битом 1, бит 50 — 2 и т. д.

Таблица 1

Начальная перестановка

Затем выполняется итеративный процесс шифрования, который описывается следующими формулами:

L (i)=R (i-1), i=1,2,…, 16.

R (i)=L (i-1) + F (R (i-1), K (i)), i=1,2,…, 16.

Функция F называется функцией шифрования. Ее аргументами являются последовательность R, полученная на предыдущем шаге, и 48-битовый ключ K (i), который является результатом функции преобразования 64-битового ключа шифра.

На последнем шаге итерации (результат повторного применения какой-либо математической операции) будут получены последовательности L (16) и R (16), которые конкатенируются в 64-х битовую последовательность R (16)L (16). Видно, что в полученной последовательности 64 бита,

перестанавливаются в соответствии с таблицей 2. Как легко видеть данная перестановка является обратной по отношению к начальной (см. таблицу 1).

Таблица 2

" Конечная перестановка"

Полученная последовательность из 64 бит и будет являться зашифрованной последовательностью.

Рис. 2 Процесс шифрования данных

1.1 Процесс расшифрования

Процесс расшифрования данных является инверсным по отношению к процессу шифрования. Все действия должны быть выполнены в обратном порядке. Это означает, что расшифровываемые данные сначала переставляются в соответствии с таблицей 1, а затем над последовательностью бит R (16)L (16) выполняется те же действия, что и в процессе зашифрования, но в обратном порядке. Итеративный процесс расшифрования описан следующими формулами:

R (i-1)=L (i), i =16, 15, …, 1

L (i-1)=R (i)+F (L (i), K (i)), i=16, 15, …, 1.

На последнем шаге итерации будут получены последовательности L (0) и R (0), которые конкатенируются в 64 битовую последовательность L (0)R (0). В полученной последовательности 64 бита перестанавливаются в соответствии с таблицей 2. Результат преобразования — исходная последовательность бит (расшифрованное 64-битовое значение).

Функция шифрования F (R, K) схематически показана на рисунке 3. Для вычисления значения функции F используется функция E (расширение 32 бит до 48), функции S (1), S (2),…, S (8) преобразование 6-битового числа в 4-битовое) и функция P (перестановка бит в 32-битовой последовательности). Приведем определения этих функций. Аргументами функции шифрования являются R (32 бита) и K (48 бит). Результат функции E® есть 48-битовое число, которое складывается по модулю 2 с числом K. Таким образом, получается 48-битовая последовательность, которая рассматривается, как конкатенация 8 строк длиной по 6 бит (т.е.)

B (1)B (2)B (3)B (4)B (5)B (6)B (7)B (8)

Результат функции S (i)B (i) — 4 битовая последовательность, которую будем обозначать L (i). В результате конкатенаций всех 8 полученных последовательностей L (i) имеем 32-битовую последовательность

L=L (1)L (2)L (3)L (4)L (5)L (6)L (7)L (8).

Наконец, для получения результат функции шифрования надо переставить биты последовательности L. Для этого применяется функция перестановки P (L).

Функция расширения Е, выполняющая расширение 32 бит до 48, определяется таблицей 3. В соответствии с этой таблицей первые три бита Е® — это биты 32,1 и 2, а последние — 31,32,1.

Рис. 3

Таблица 3

Функция расширения Е

Функция S (i), которая преобразует 6-битовые числа в 4-битовые, определяется таблицей 4.

Таблица 4

" Функции преобразования S (i)" S (1)

S (2)

S (3)

S (4)

S (5)

S (6)

S (7)

S (8)

К таблице 4 требуются дополнительные пояснения. Каждая из функций S (i)B (i) преобразует 6-битовый код в 4-битовый выход по следующему алгоритму:

· первый и последний биты входной последовательности B, определяют номер строки k;

· второй, третий, четвертый и пятый биты последовательности B задают номер колонки l;

· результат преобразования выбирается из строки k и колонки l.

Предположим, что B=11 011. Тогда S (1)(B)=0101. Действительно, k=1, l=13. В колонке 13 строки 1 задано значение 5, которое и является значением функции S (1)(11 011).

Функция перестановки бит P (L), также используемая для определения функции шифрования, задается значениями, приведенными в таблице 5. В последовательности L 32 перестанавливается так, чтобы бит 16 стал первым битом, бит 7 — вторым и т. д.

Таблица 5

" Функция перестановки P"

1.2 Процесс получения ключей

Чтобы завершить описание алгоритма шифрования данных, осталось привести алгоритм получение ключей K (i), i=1,2,…, 16, размерностью в 48 бит. Ключи K (i) определяются по 64-битовому ключу шифра как это показано на рисунке 4.

Рис.4

В начале над ключом шифра выполняется операция B, которая сводится к выбору определенных бит и их перестановке, как это показано в таблице 6. Причем, первые четыре строки определяют, как выбираются биты последовательности C (0) (первым битом C (0) будет бит 57 бит ключа шифра, затем бит 49 и т. д., а последними битами биты 44 и 36 ключа шифра), а следующие четыре строки — как выбираются биты последовательности D (0) (т.е. последовательность D (0) будем состоять из битов 63,55,…, 12, 4 ключа шифра).

Таблица 6

Функция перестановки и выбора последовательности B

Как видно из таблицы 6, для генерации последовательностей C (0) и D (0) не используются биты 8,16,25,32,40,48,56 и 64 ключа шифра. Эти биты не влияют на шифрование и могут служить для других целей (например, для контроля по четности). Таким образом, в действительности ключ шифра является 56-битовым. После определения C (0) и D (0) рекурсивно определяются C (i) и D (i), i=1,2,…, 16. Для этого применяются операции сдвига влево на один или два бита в зависимости от номера шага итерации, как это показано в таблице 7.

Операции сдвига выполняются для последовательностей C (i) и D (i) независимо. Например, последовательность C (3) получается, посредством сдвига влево на две позиции последовательности C (2), а последовательность D (3) — посредством сдвига влево на две позиции последовательности D (2). Следует иметь в виду, что выполняется циклический сдвиг влево. Например, единичный сдвиг влево последовательности C (i) приведет к тому, что первый бит C (i) станет последним, и последовательность бит будет следующая: 2,3,…, 28,1.

Таблица 7

Функция сдвига Si

Ключ K (i), определяемый на каждом шаге итерации, есть результат выбора определенных бит из 56-битовой последовательности C (i)D (i) и их перестановки. Другими словами, K (i) = K (C (i)D (i)), где функция K определяется данными, приведенными в таблице 8.

Таблица 8

Функция перестановки и выбора K

Как следует из таблицы 8 первый бит K (i) — это бит 14 последовательности C (i)D (i), второй — бит 17, последний — бит 32.

приложение шифрование ключ процедура

2. Спецификация программы

2.1 Список процедур и функций

· ProcedureTForm1. FormCreate — выполняется, как только создается форма.

· ProcedureTForm1. Button1Click — выполняется при нажатии кнопки «Encode» .

· ProcedureTForm1. Button2Click — выполняется при нажатии кнопки «Decode» .

· ProcedureTForm1. Memo1Change — выполняется при изменении содержимого ТMemo1.

· ProcedureTForm1. Memo1Change — выполняется при изменении содержимого ТMemo2.

· Procedure TForm1. Edit1Change — выполняется при изменении содержимого TEdit1.

· FunctionBinToInt — перевод из двоичного представления числа в целочисленный десятичный тип.

· FunctionIntToBin — перевод из десятичного представления числа в двоичный тип с использованием указателей, выделением и освобождением памяти под этот процесс.

· FunctionBinToStr — перевод бинарных чисел в их строковый эквивалент.

· FunctionStrToBin — переводит строку содержащую бинарный код в соответствующее бинарное число.

· FunctionAnsiStrToBin — перевод строки символов в бинарное число.

· FunctionBinToAnsiStr — перевод бинарных комбинаций в строку символов.

· ProcedureCopyBits — процедура для побитового копирования данных из одной переменной в другую.

· FunctionConcatBits — функция для побитового объединения данных двух переменных.

· FunctionGetPermutedKey — первоначальная перестановка ключа в соответствии с таблицей перестановки с отбрасыванием каждого 8-го бита (бита четности).

· FunctionGetPermutedKey2 — перестановка со сжатием. После сдвига выбирается 48 из 56-ти битов.

· FunctionGetSplitKey — 56-ти битовый ключ делится на две 28-и битовых половины затем половины циклически сдвигаются влево на один или два бита.

· FunctionGetConcatKey — функция для объединения сгенерированного ключа после перестановки с расширением.

· FunctionGetIPKey — начальная перестановка. (Служит для облегчения побайтной загрузки открытого текста в микросхему DES).

· FunctionGetF — правая половина данных увеличивается до 48 битов с помощью перестановки с расширением, объединяется посредством XOR с 48 битами смещенного и переставленного ключа, проходит через 8 S-блоков, образуя 32 новых бита и переставляется снова.

· FunctionGetSBox — функция реализует 8 S-блоков. Каждый S-блок представляет собой таблицу из двух строк и 16-ти столбцов. По 6-ти входным битам S-блока определяется, под какими номерами столбцов и строк искать выходное значение.

· FunctionGetReverseIP — конечная (обратная) перестановка.

· ProcedureReverceSubKeys — обратная перестановка подключа.

· FunctionDESEncode — основная функция шифрующая данные. Переводит ключ в бинарный вид, получение сгенерированного ключа, перевод исходного текста в бинарный вид, начальная перестановка, блок разбивается на два 32-битных половины, затем выполняется 16 этапов одинаковых действий (функция GetF), после 16 -го этапа правая и левая половины объединяются и алгоритм завершается обратной перестнаовкой.

· FunctionDESDecode — функция дешифрующая данные. Аналогична функции DESEncode, с отличием, что после получения сгенерированного ключа он реверсируется функцией ReverceSubKeys.

2.2 Описание интерфейса пользователя

Интерфейс программы состоит из одного, главного окна. В верхней части находится поле, в которое необходимо ввести ключ (пароль). Пароль обязательно должен состоять из 8 символов (особенность алгоритма DES).

В поле ниже необходимо ввести текст сообщения, которое необходимо зашифровать. Количество символов должно быть кратно 8, причем переход на новую строку считается как 2 символа. Для облегчения над полем ввода будет отображаться количество введенных символов. При вводе сообщения символы будут автоматически переводится в бинарный код. Это сделано для наглядности работы алгоритма.

После ввода сообщения необходимо нажать кнопку с надписью «Шифровать», чтобы начать шифрование. При несоблюдении условия о кратности 8 будет выдано сообщение об ошибке.

По окончании шифрования в нижнем поле появится зашифрованное сообщение и его бинарная интерпретация.

Для расшифровки сообщения необходимо ввести зашифрованный текст в поле, ввести правильный пароль и нажать кнопку «Расшифровать».

Заключение

Данная программа разрабатывалась в качестве курсовой работы, и не воспроизводит все возможности данного алгоритма. Тем не менее, она решает поставленную на этапе проектирования задачу — «Шифрование данных с помощью алгоритма DES».

Разработанная программа позволяет наглядно ознакомиться с основными принципами алгоритма DES.

1. Брюс Шнайер. Прикладная криптография. Наука (1983).

2. Диффи У., Хеллмен Э. Новое направление в криптографии //ТИ-ИЭР. IT-22 (1976).

3. Диффи У., Хеллмен Э. Защищенность и имитостойкость: введение в криптографию (1979).

4. Система обработки информации. Защита криптографическая. Алгоритм криптографического преобразования. ГОСТ 28 147–89 (1989).

5. http://ru.wikipedia.org/wiki/DES (ссылка)

6. http://cryptogrof.ru/algoritm des

7. http://protect.htmlweb.ru/des.htm

Приложение А

unit Unit1;

interface

uses

Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,

Dialogs, DES, StdCtrls;

type

TForm1 = class (TForm)

Label1: TLabel;

Edit1: TEdit;

Label2: TLabel;

Memo1: TMemo;

Button1: TButton;

Label3: TLabel;

Memo2: TMemo;

Button2: TButton;

Memo3: TMemo;

Label4: TLabel;

Memo4: TMemo;

procedure Button1Click (Sender: TObject);

procedure Button2Click (Sender: TObject);

procedure Memo1Change (Sender: TObject);

procedureFormCreate (Sender: TObject);

procedure Edit1Change (Sender: TObject);

procedure Memo2Change (Sender: TObject);

private

{ Private declarations }

public

Data:TBitString;

end;

var

Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1. Button1Click (Sender: TObject);

Var

I:Integer;

S:String;

begin

IF ((Length (Memo1.Text)mod 8 <> 0) OR (Length (Edit1.Text)mod 8 <> 0))

Then

Begin

MessageBox (Handle,

'Количество букв в сообщении должно быть кратоно 8 (перевод строки

считается за 2 буквы)'+

#10#13'Ключ должен состоять из 8 символов',

Nil, MB_ICONSTOP);

Exit;

End;

SetLength (Data, 0);

I:=1;

While I<=Length (Memo1.Text) Do

Begin

S:=Copy (Memo1.Text, I,8);

Data:=ConcatBits ([Data, DESEncode (S, Edit1. Text)]);

I:=I+8;

End;

Memo2.Text:=BinToAnsiStr (Data);

end;

procedure TForm1. Button2Click (Sender: TObject);

var

I:Integer;

begin

IF ((Length (Memo2.Text)mod 8 <> 0) OR (Length (Edit1.Text)mod 8 <> 0))

Then

Begin

MessageBox (Handle,

'Количество букв в сообщении должно быть кратоно 8 (перевод строки

считается за 2 буквы)'+

#10#13'Ключ должен состоять из 8 символов',

Nil, MB_ICONSTOP);

Exit;

End;

SetLength (Data, 0);

I:=1;

While I<=Length (Memo2.Text) Do

Begin

Data:=ConcatBits ([Data, DESDecode (Copy (Memo2.Text, I,8), Edit1. Text)]);

I:=I+8;

End;

Memo1.Text:=BinToAnsiStr (Data);

end;

procedure TForm1. Memo1Change (Sender: TObject);

begin

IF Memo1. Text<>'' Then

Memo3.Text:=BinToStr (AnsiStrToBin (Memo1.Text))

Else Memo3. Clear;

Label2.Caption:='Message — ('+IntToStr (Length (Memo1.Text))+'

characters)';

end;

procedure TForm1. FormCreate (Sender: TObject);

begin

Memo1.OnChange (Self);

Edit1.OnChange (Self);

end;

procedure TForm1. Edit1Change (Sender: TObject);

begin

Label4.Caption:=IntToStr (Length (Edit1.Text))+' characters';

end;

procedure TForm1. Memo2Change (Sender: TObject);

begin

IF Memo2. Text<>'' Then

Memo4.Text:=BinToStr (AnsiStrToBin (Memo2.Text))

Else Memo4. Clear;

Label3.Caption:='Encoded message — ('+IntToStr (Length (Memo2.Text))+'

characters)';

end;

end.

Приложение Б

unit DES;

interface

Uses Windows, Classes, SysUtils, Math, Dialogs;

Type

TBitString = Array of Boolean;

PBitString = ^TBitString;

TSplitKeyParts = record

C:TBitString;

D:TBitString;

end;

TSplitKey = Array[0.16]Of TSplitKeyParts;

TConcatKey = Array[0.15]Of TBitString;

TIPKeyParts = record

L:TBitString;

R:TBitString;

end;

TIPKey = Array[0.16]OF TIPKeyParts;

Const

DES_PC1:Array[0.55] Of Byte = (57,49,41,33,25,17,9,

1,58,50,42,34,26,18,

10,2,59,51,43,35,27,

19,11,3,60,52,44,36,

63,55,47,39,31,23,15,

7,62,54,46,38,30,22,

14,6,61,53,45,37,29,

21,13,5,28,20,12,4);

DES_PC2:Array[0.47] Of Byte = (14,17,11,24,1,5,

3,28,15,6,21,10,

23,19,12,4,26,8,

16,7,27,20,13,2,

41,52,31,37,47,55,

30,40,51,45,33,48,

44,49,39,56,34,53,

46,42,50,36,29,32);

DES_IP:Array[0.63] Of Byte = (58,50,42,34,26,18,10,2,

60,52,44,36,28,20,12,4,

62,54,46,38,30,22,14,6,

64,56,48,40,32,24,16,8,

57,49,41,33,25,17,9,1,

59,51,43,35,27,19,11,3,

61,53,45,37,29,21,13,5,

63,55,47,39,31,23,15,7);

DES_E:Array[0.47] Of Byte = (32,1,2,3,4,5,

4,5,6,7,8,9,

8,9,10,11,12,13,

12,13,14,15,16,17,

16,17,18,19,20,21,

20,21,22,23,24,25,

24,25,26,27,28,29,

28,29,30,31,32,1);

S_BOXES:Array[0.7,0.3,0.15]Of Byte = (

((14,04,13,01,02,15,11,08,03,10,06,12,05,09,00,07),

(00,15,07,04,14,02,13,01,10,06,12,11,09,05,03,08),

(04,01,14,08,13,06,02,11,15,12,09,07,03,10,05,00),

(15,12,08,02,04,09,01,07,05,11,03,14,10,00,06,13)),

((15,01,08,14,06,11,03,04,09,07,02,13,12,00,05,10),

(03,13,04,07,15,02,08,14,12,00,01,10,06,09,11,05),

(00,14,07,11,10,04,13,01,05,08,12,06,09,03,02,15),

(13,08,10,01,03,15,04,02,11,06,07,12,00,05,14,09)),

((10,00,09,14,06,03,15,05,01,13,12,07,11,04,02,08),

(13,07,00,09,03,04,06,10,02,08,05,14,12,11,15,01),

(13,06,04,09,08,15,03,00,11,01,02,12,05,10,14,07),

(01,10,13,00,06,09,08,07,04,15,14,03,11,05,02,12)),

((07,13,14,03,00,06,09,10,01,02,08,05,11,12,04,15),

(13,08,11,05,06,15,00,03,04,07,02,12,01,10,14,09),

(10,06,09,00,12,11,07,13,15,01,03,14,05,02,08,04),

(13,15,00,06,10,01,13,08,09,04,05,11,12,07,02,14)),

((02,12,04,01,07,10,11,06,08,05,03,15,13,00,14,09),

(14,11,02,12,04,07,13,01,05,00,15,10,03,08,09,06),

(04,02,01,11,10,13,07,08,15,09,12,05,06,03,00,14),

(11,08,12,07,01,14,02,13,06,15,00,09,10,04,05,03)),

((12,01,10,15,09,02,06,08,00,13,03,04,14,07,05,11),

(10,15,04,02,07,12,09,05,06,01,13,14,00,11,03,08),

(09,14,15,05,02,08,12,03,07,00,04,10,01,13,11,06),

(04,03,02,12,09,05,15,10,11,14,01,04,06,00,08,13)),

((04,11,02,14,15,00,08,13,03,12,09,07,05,10,06,01),

(13,00,11,07,04,09,01,10,14,03,05,12,02,15,08,06),

(01,04,11,13,12,03,07,14,10,15,06,08,00,05,09,02),

(06,11,13,08,01,04,10,07,09,05,00,15,14,02,03,12)),

((13,02,08,04,06,15,11,01,10,09,03,14,05,00,12,07),

(01,15,13,08,10,03,07,04,12,05,06,11,00,14,09,02),

(07,11,04,01,09,12,14,02,00,06,10,13,15,03,05,08),

(02,01,14,07,04,10,08,13,15,12,09,00,03,05,06,11)));

DES_P:Array[0.31] Of Byte = (16,7,20,21,

29,12,28,17,

1,15,23,26,

5,18,31,10,

2,8,24,14,

32,27,3,9,

19,13,30,6,

22,11,4,25);

DES_REVERSE_IP:Array[0.63] Of Byte = (40,8,48,16,56,24,64,32,

39,7,47,15,55,23,63,31,

38,6,46,14,54,22,62,30,

37,5,45,13,53,21,61,29,

36,4,44,12,52,20,60,28,

35,3,43,11,51,19,59,27,

34,2,42,10,50,18,58,26,

33,1,41,9,49,17,57,25);

DES_LSH:Array[0.15] Of Byte = (1,1,2,2,2,2,2,2,1,2,2,2,2,2,2,1);

Function BinToInt (S:TBitString):Integer;

Function IntToBin (N:Integer;Precision:Integer=8):TBitString;

Function BinToStr (Bits:TBitString):String;

Function StrToBin (S:String):TBitString;

Function AnsiStrToBin (S:String; Zeroes: Boolean=True):TBitString;

Function BinToAnsiStr (Bits:TBitString):String;

Procedure CopyBits (VarDest:TBitString; Source: TBitString; NBits: Integer);

Function ConcatBits (Bits:Array Of TBitString):TBitString;

Function DESEncode (S, Key: String):TBitString;

Function DESDecode (S, Key: String):TBitString;

Function GetPermutedKey (Key:TBitString):TBitString;

Function GetPermutedKey2(Key:TBitString):TBitString;

Function GetSplitKey (Key:TBitString):TSplitKey;

Function GetConcatKey (Key:TSplitKey):TConcatKey;

Function GetIPKey (M:TBitString; ConcatKey: TConcatKey):TIPKey;

Function GetF (R, K: TBitString):TBitString;

Function GetSBox (Index:Integer; T: TBitString):TBitString;

Function GetReverseIP (RL:TBitString):TBitString;

Procedure ReverseSubKeys (VarKeys:TConcatKey);

implementation

Function ConcatBits (Bits:Array Of TBitString):TBitString;

Var

I, C: Integer;

Begin

SetLength (Result, 0);

For C:=0 To Length (Bits)-1 Do

Begin

SetLength (Result, Length (Result)+Length (Bits[C]));

For I:=0 To Length (Bits[C])-1 Do

Result[Length (Result)-Length (Bits[C])+I]: =Bits[C][I];

End;

End;

Procedure CopyBits (VarDest:TBitString; Source: TBitString; NBits: Integer);

Var

I:Integer;

Begin

SetLength (Dest, NBits);

For I:=0 To NBits-1 Do

Dest[I]: =Source[I];

End;

Function BinToInt (S: TBitString): Integer;

Var

L, I: Integer;

Begin

Result:=0;

L:=Length (S);

IF L=0 Then

Raise EConvertError. Create ('Specified bit string is zero length');

For I:=L-1 DownTo 0 Do

Result:=Result+Ord (S[I])*Trunc (Power (2,L-I-1));

End;

Function IntToBin (N:Integer; Precision: Integer):TBitString;

Var

BitList:TList;

Bit:PBoolean;

Begin

SetLength (Result, 0);

BitList:=TList.Create;

While N>0 Do

Begin

New (Bit);

Bit^:=Boolean (N mod 2);

BitList.Insert (0,Bit);

N:=N div 2;

End;

While BitList. Count

Begin

New (Bit);

Bit^:=False;

BitList.Insert (0,Bit);

End;

For N:=0 To BitList. Count-1 Do

Begin

SetLength (Result, N+1);

Bit:=BitList.Items[N];

Result[N]:=Bit^;

Dispose (Bit);

End;

BitList.Free;

end;

Function AnsiStrToBin (S: String; Zeroes: Boolean):TBitString;

Var

Temp, B: TBitString;

L, I, J:Integer;

Begin

L:=0;

SetLength (Result, L);

SetLength (Temp, L);

SetLength (B, 0);

For I:=1 To Length (S) Do

Begin

B:=IntToBin (Ord (S[I]));

L:=L+Length (B);

SetLength (Temp, L);

For J:=0 To Length (B)-1 Do

Temp[Length (Temp)-Length (B)+J]: =B[J];

End;

Result:=Temp;

End;

Function BinToStr (Bits:TBitString):String;

Var

I, L: Integer;

Begin

Result:='';

L:=Length (Bits);

IF L=0 Then

Raise EConvertError. Create ('Specified bit string is zero length');

For I:=0 To L-1 Do

IF Bits[I] Then Result:=Result+'1'

Else Result:=Result+'0';

End;

Function StrToBin (S:String):TBitString;

Var

I:Integer;

Begin

SetLength (Result, 0);

For I:=1 To Length (S) Do

Begin

IF (S[I]<>'1')And (S[I]<>'0') Then

Raise EConvertError. Create (S+' is invalid binary string');

SetLength (Result, I);

Result[I-1]: =Boolean (StrToInt (S[I]));

End;

End;

Function BinToAnsiStr (Bits:TBitString):String;

Var

I:Integer;

B:TBitString;

Begin

Result:='';

SetLength (B, 8);

I:=0;

While I<=Length (Bits)-8 Do

Begin

CopyMemory (B, Ptr (Integer (Bits)+I), 8);

Result:=Result+Char (BinToInt (B));

Inc (I, 8);

End;

End;

Function GetPermutedKey (Key:TBitString):TBitString;

Var

I:Integer;

Begin

SetLength (Result, Length (DES_PC1));

For I:=0 To Length (DES_PC1)-1 Do

Result[I]: =Key[DES_PC1[I]-1];

End;

Function GetPermutedKey2(Key:TBitString):TBitString;

Var

I:Integer;

Begin

SetLength (Result, Length (DES_PC2));

For I:=0 To Length (DES_PC2)-1 Do

Result[I]: =Key[DES_PC2[I]-1];

End;

Function GetSplitKey (Key:TBitString):TSplitKey;

Function LeftShift (Key:TBitString; N: Integer):TBitString;

Var

I, J: Integer;

Temp:TBitString;

Begin

SetLength (Result, 28);

SetLength (Temp, 28);

For I:=0 To 27 Do

Temp[I]: =Key[I];

For J:=1 To N Do

Begin

For I:=1 To 27 Do

Result[I-1]: =Temp[I];

Result[27]:=Temp[0];

For I:=0 To 27 Do

Temp[I]: =Result[I];

End;

End;

Var

I, J: Integer;

Begin

For J:=1 To 16 Do

Begin

SetLength (Result[J]. C, 28);

SetLength (Result[J].D, 28);

End;

CopyBits (Result[0].C, Key, 28);

CopyBits (Result[0].D, TBitString (Integer (Key)+28), 28);

For I:=1 To 16 Do

Begin

Result[I]. C:=LeftShift (Result[I-1].C, DES_LSH[I-1]);

Result[I].D:=LeftShift (Result[I-1].D, DES_LSH[I-1]);

End;

End;

Function GetConcatKey (Key:TSplitKey):TConcatKey;

Var

I:Integer;

Temp:TBitString;

Begin

For I:=0 To 15 Do

Begin

SetLength (Result[I], 56);

Temp:=ConcatBits ([Key[I+1]. C, Key[I+1].D]);

Result[I]:=GetPermutedKey2(Temp);

End;

End;

Function GetIPKey (M:TBitString; ConcatKey: TConcatKey):TIPKey;

Var

I, J: Integer;

IP, F: TBitString;

Begin

For I:=0 To 16 Do

Begin

SetLength (Result[I]. L, 32);

SetLength (Result[I].R, 32);

End;

SetLength (IP, 64);

For I:=0 To Length (DES_IP)-1 Do

IP[I]: =M[DES_IP[I]-1];

For I:=0 To 31 Do

Result[0]. L[I]:=IP[I];

For I:=32 To 63 Do

Result[0]. R[I-32]:=IP[I];

For I:=1 To 16 Do

Begin

Result[I]. L:=Result[I-1].R;

F:=GetF (Result[I-1].R, ConcatKey[I-1]);

For J:=0 To 31 Do

Result[I]. R[J]:=Result[I-1].L[J] XOR F[J];

End;

End;

Function GetF (R, K: TBitString):TBitString;

Var

I, J: Integer;

S, E, KE, F, T:TBitString;

Begin

SetLength (E, 48);

For I:=0 To 47 Do

E[I]: =R[DES_E[I]-1];

SetLength (KE, 48);

For I:=0 To 47 Do

KE[I]: =K[I] XOR E[I];

SetLength (T, 6);

SetLength (F, 0);

SetLength (S, 4);

I:=0;

While I<48 Do

Begin

For J:=0 To 6 Do

T[J]: =KE[J+I];

S:=GetSBox (I div 6, T);

F:=ConcatBits ([F, S]);

I:=I+6;

End;

SetLength (Result, 32);

For I:=0 To 31 Do

Result[I]: =F[DES_P[I]-1];

End;

Function GetSBox (Index:Integer; T: TBitString):TBitString;

Var

Val, Row, Col: Integer;

Temp:TBitString;

Begin

SetLength (Result, 4);

SetLength (Temp, 2);

Temp[0]: =T[0];

Temp[1]:=T[5];

Row:=BinToInt (Temp);

SetLength (Temp, 4);

CopyBits (Temp, TBitString (@T[1]), 4);

Col:=BinToInt (Temp);

Val:=S_BOXES[Index, Row, Col];

SetLength (Result, 4);

Result:=IntToBin (Val, 4);

End;

Function GetReverseIP (RL:TBitString):TBitString;

Var

I:Integer;

Begin

SetLength (Result, 64);

For I:=0 To Length (DES_REVERSE_IP)-1 Do

Result[I]: =RL[DES_REVERSE_IP[I]-1];

End;

Procedure ReverseSubKeys (VarKeys:TConcatKey);

Var

I, L: Integer;

T:TBitString;

Begin

SetLength (T, 48);

L:=Length (Keys);

For I:=0 To (L-1)Div 2 Do

Begin

T:=Keys[I];

Keys[I]:=Keys[(L-I)-1];

Keys[(L-I)-1]:=T;

End;

End;

Function DESEncode (S, Key: String):TBitString;

Var

I:Integer;

K:TBitString;

M:TBitString;

RL:TBitString;

Kplus:TBitString;

SplitKey:TSplitKey;

ConcatKey:TConcatKey;

IPKey:TIPKey;

Begin

K:=AnsiStrToBin (Key);

Kplus:=GetPermutedKey (K);

SplitKey:=GetSplitKey (Kplus);

ConcatKey:=GetConcatKey (SplitKey);

M:=AnsiStrToBin (S);

IPKey:=GetIPKey (M, ConcatKey);

SetLength (RL, 64);

For I:=0 To 31 Do

Begin

RL[I]: =IPKey[16].R[I];

RL[I+32]:=IPKey[16].L[I];

End;

RL:=GetReverseIP (RL);

Result:=RL;

End;

Function DESDecode (S, Key: String):TBitString;

Var

I:Integer;

K:TBitString;

M:TBitString;

RL:TBitString;

Kplus:TBitString;

SplitKey:TSplitKey;

ConcatKey:TConcatKey;

IPKey:TIPKey;

Begin

K:=AnsiStrToBin (Key);

Kplus:=GetPermutedKey (K);

SplitKey:=GetSplitKey (Kplus);

ConcatKey:=GetConcatKey (SplitKey);

ReverseSubKeys (ConcatKey);

M:=AnsiStrToBin (S);

IPKey:=GetIPKey (M, ConcatKey);

SetLength (RL, 64);

For I:=0 To 31 Do

Begin

RL[I]: =IPKey[16].R[I];

RL[I+32]:=IPKey[16].L[I];

End;

RL:=GetReverseIP (RL);

Result:=RL;

End;

end.

Показать весь текст
Заполнить форму текущей работой