|
Antwort |
qwertz543221
(Gast)
n/a Beiträge |
#1
bei der implementierung des keyschedule beim AES bin ich auf probleme gestossen.
folgende quellen nutze ich http://www.cs.bc.edu/~straubin/cs381...ingles2004.swf http://en.wikipedia.org/wiki/Rijndael_key_schedule http://cboard.cprogramming.com/c-pro...-standard.html Frage 1: der algorithmus zur generierung der rundenschlüssel weist fehler auf, die rundenschlüssel werden nicht richtig erstellt.(http://en.wikipedia.org/wiki/Rijndael_key_schedule) Frage 2: nutzung der rundenschlüssel /allgemeiner ablauf ich habe die befürchgung, dass die rundenschlüssel nicht richtig genutzt werden. evtl beim entshclpsseln falsche reihenfolge? habe bereits einige quellen gesucht, die den algorithmus verständlich widergeben. quellcode im anhang, wäre es mlgich ein paar erläuterungen zu geben? |
Zitat |
Registriert seit: 28. Jun 2006 Ort: Düsseldorf 936 Beiträge Delphi XE2 Professional |
#2
Darf ich fragen warum du dir die Mühe machst, das ganze neu zu implementieren?
Gruß
Cookie |
Zitat |
qwertz543221
(Gast)
n/a Beiträge |
#3
ja gut man könnte es auch einfacher haben^^
aber ich schreibe eigentlich gerne die dinge selbst. jetzt ist es ja auch schon fast fertig (erstentwurf für die allg. struktur, soll später noch optimiert werden) |
Zitat |
qwertz543221
(Gast)
n/a Beiträge |
#4
habe es nun wie folgt:
Delphi-Quellcode:
hier von diesem code generierte output (expanded key) für input
type
Tkey128 = Array [1 .. 176] Of Byte; Function Taes.Expandkey(Var Key: Tinput; Var Expandedkey: Tkey128): Byte; //expands given key (128,192,256 bit, determined by bitlen variable) to (176,208,240 bytes) //blocksize=16=>keysize 128 bit //result:= the number of rounds (10,12,14) determined by new keylength //SRC= http://www.samiam.org/key-schedule.html //http://cboard.cprogramming.com/c-programming/87805-%5Btutorial%5D-implementing-advanced-encryption-standard.html Var I, Rconiterator, A, C: Integer; Temp: Tword; Begin I := 1; While I <= Length(Key) Do Begin Expandedkey[I] := Key[I]; Inc(I); End; Rconiterator := 1; C := 17; While C <= 176 Do Begin { Copy the temporary variable over from the last 4-byte- block } A := 1; While A <= 4 Do Begin //showmessage(inttostr(a)+';'+inttostr(c)); Temp[A] := Expandedkey[A + C - 4]; Inc(A); End; //Every four blocks (of four bytes) run keyschedule_core If C Mod 16 = 0 Then Begin Keyschedule_core(Temp, Rconiterator, 0); Inc(Rconiterator); End; A := 1; While A <= 4 Do Begin Expandedkey[C] := Expandedkey[C - 16] Xor Temp[A]; Inc(C); Inc(A); End; End; Result := 11; //number of rounds for 128 bit keys End; 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 58 00 00 58 00 00 58 00 58 58 00 58 0E 00 58 0E C2 58 0E 9A 0E 0E C2 0E 53 9A 0E 0B 7A 0E 53 74 C7 0B 7A 5D 0E 74 9F 00 53 05 0E 58 2A 00 0B 5E C7 00 24 9A B6 50 05 B6 53 00 B8 0B 0A B8 00 54 CC 00 70 56 B6 20 53 00 EB 53 B8 E0 F4 00 E0 A0 CC E0 D0 9A B6 F0 C9 B6 13 9A 0E F3 B4 0E 13 14 98 F3 C4 02 96 34 CB 20 65 51 2E 96 B4 20 85 A0 98 76 64 9A 96 50 51 B6 D5 00 98 43 7E B8 C6 DE 28 B0 BA B2 96 EA E3 20 D5 E3 B8 96 B4 00 50 6A 98 E0 D0 2A F2 3A C9 D2 F5 2A 6A 63 8C laut http://www.samiam.org/key-schedule.html sollte der key allerdings lauten (ich hoffe das stimmt) 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 62 63 63 63 62 63 63 63 62 63 63 63 62 63 63 63 9b 98 98 c9 f9 fb fb aa 9b 98 98 c9 f9 fb fb aa 90 97 34 50 69 6c cf fa f2 f4 57 33 0b 0f ac 99 ee 06 da 7b 87 6a 15 81 75 9e 42 b2 7e 91 ee 2b 7f 2e 2b 88 f8 44 3e 09 8d da 7c bb f3 4b 92 90 ec 61 4b 85 14 25 75 8c 99 ff 09 37 6a b4 9b a7 21 75 17 87 35 50 62 0b ac af 6b 3c c6 1b f0 9b 0e f9 03 33 3b a9 61 38 97 06 0a 04 51 1d fa 9f b1 d4 d8 e2 8a 7d b9 da 1d 7b b3 de 4c 66 49 41 b4 ef 5b cb 3e 92 e2 11 23 e9 51 cf 6f 8f 18 8e |
Zitat |
qwertz543221
(Gast)
n/a Beiträge |
#5
Habe es hinbekommen:
Delphi-Quellcode:
Function Taes.Expandkey(Key: Tinput; Var Expandedkey: Tkey128): Byte;
//expands given key (128,192,256 bit, determined by bitlen variable) to (176,208,240 bytes) //blocksize=16=>keysize 128 bit //result:= the number of rounds (10,12,14) determined by new keylength //SRC= http://www.samiam.org/key-schedule.html //http://cboard.cprogramming.com/c-programming/87805-%5Btutorial%5D-implementing-advanced-encryption-standard.html Var I, Rconiterator, A, C: Integer; Temp: Tword; Begin I := 1; While I <= Length(Key) Do Begin Expandedkey[I] := Key[I]; Inc(I); End; { inc(i); while i<=length(expandedkey) do begin expandedkey[i]:=0; inc(i); end; } Rconiterator := 1; C := Length(Key) + 1; //17 While C <= 176 Do Begin { Copy the temporary variable over from the last 4-byte- block } A := 1; While A <= 4 Do Begin //showmessage(inttostr(a)+';'+inttostr(c)); Temp[A] := Expandedkey[A + C - 5]; //ok Inc(A); End; //Every four blocks (of four bytes) do a complex calculation If ((C - 1) Mod 16 = 0) Then Begin Keyschedule_core(Temp, Rconiterator, 0); Inc(Rconiterator); End; A := 1; While A <= 4 Do Begin //Expandedkey[C+1] := Expandedkey[C - 16] Xor Temp[A]; Expandedkey[C] := Expandedkey[C - 16] Xor Temp[A]; Inc(C); Inc(A); End; End; Result := 11; //number of rounds for 128 bit keys End; |
Zitat |
qwertz543221
(Gast)
n/a Beiträge |
#6
Könnte jemand testvektoren für aes 128 (text,key,chiffre) zur überprüfung angeben?
ich habe jetzt den algorithmus in zwei unterschiedlichen programmen(einmal gesondert in einer unit, und einmal mit anderen algorithmen zusammen) und habe bei beiden differente ausgaben. kann es an der klassendefinition und den jeweiligen zugriffsrechten zusammenhängen? hier sind zwei ausgabebeispiele bei gleichem input: BenutzerSchlüssel: test01af5 Eingabe: Testvektor Ausgabe 1: cLffabrarTFxNvtjTNYDHG (base64) Ausgabe 2: dnwm0e+gYhWhRaVn1X2GX0 (~) anbei der quelltext für ausgabe 1
Delphi-Quellcode:
Unit Mainprogram;
Interface Uses Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, Dialogs, StdCtrls, Crypto, ExtCtrls,Advanced_Encryption_Standard; Type TForm1 = Class(TForm) Button1: TButton; Memo1: TMemo; LabeledEdit1: TLabeledEdit; Button2: TButton; Procedure Button1Click(Sender: TObject); Procedure Button2Click(Sender: TObject); Private Public { Public declarations } End; Var Form1: TForm1; Aes: Taes; Data: Tdata; //datenverarbeitung und ausgabe Implementation {$R *.dfm} Procedure TForm1.Button1Click(Sender: TObject); Var Text, Key: String; Begin Text := Memo1.Text; Key := Labelededit1.Text; Text := Aes.Aes_text(Text, Key, Aes.Keysize128, 0); Text := Data.Base64(Text, 0); // Text := Data.Str_tohex(Text, Length(Text)); Memo1.Text := Text; End; Procedure TForm1.Button2Click(Sender: TObject); Var Text, Key: String; Begin Text := Memo1.Text; Key := Labelededit1.Text; // Text := Data.Str_fromhex(Text); Text := Data.Base64(Text, 1); Text := Aes.Aes_text(Text, Key, Aes.Keysize128, 1); Memo1.Text := Text; End; Initialization Data := Tdata.Create; Aes := Taes.Create; Finalization Aes.Free; Data.Free; End. Unit Advanced_Encryption_Standard; Interface {$RANGECHECKS on} {$OPTIMIZATION ON} {$OVERFLOWCHECKS on} Uses Messages, SysUtils, Classes, StdCtrls; Type // 128 bit /16 byte /4*4 blocks for 128 bit key Trow = Array [1 .. 4] Of Byte; Tcolumn = Array [1 .. 4] Of Byte; Tstate = Array [1 .. 4] Of Trow; Tword = Array [1 .. 4] Of Byte; Tinput = Array [1 .. 16] Of Byte; //to fill a custom state { expanded key arrays 128 bit input block =>176 bytes=>11 16 byte blocks 192 bit input block=>208 bytes=> 8 24 byte bocks 256 bit input block=>240 bytes=> 7 32 byte blocks } Tkey128 = Array [1 .. 176] Of Byte; Tkey192 = Array [1 .. 208] Of Byte; Tkey256 = Array [1 .. 240] Of Byte; Tsubkeys128 = Array [1 .. 11] Of Tstate; //counters i,j:=1<= 4 Taes = Class // Public Var Testroundkey: Tstate; //for initalization keyschedule test Testexpandedkey128: Tkey128; Testcount: Integer; Const Keysize128 = 128; Keysize192 = 192; Keysize256 = 256; Function Aes_text(Var Text, Key: String; Bitlen: Integer; Mode: Byte): String; Private Var Mixcolstate: Tstate; Mixcolinvstate: Tstate; Expandedkey128: Tkey128; Expandedkey192: Tkey192; Expandedkey256: Tkey256; Keys: Array Of String; Const Teststatearray: Tinput = (1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16); Sbox: Array [0 .. 255] Of Byte = // 0 1 2 3 4 5 6 7 8 9 A B C D E F ($63, $7C, $77, $7B, $F2, $6B, $6F, $C5, $30, $01, $67, $2B, $FE, $D7, $AB, $76, //0 $CA, $82, $C9, $7D, $FA, $59, $47, $F0, $AD, $D4, $A2, $AF, $9C, $A4, $72, $C0, //1 $B7, $FD, $93, $26, $36, $3F, $F7, $CC, $34, $A5, $E5, $F1, $71, $D8, $31, $15, //2 $04, $C7, $23, $C3, $18, $96, $05, $9A, $07, $12, $80, $E2, $EB, $27, $B2, $75, //3 $09, $83, $2C, $1A, $1B, $6E, $5A, $A0, $52, $3B, $D6, $B3, $29, $E3, $2F, $84, //4 $53, $D1, $00, $ED, $20, $FC, $B1, $5B, $6A, $CB, $BE, $39, $4A, $4C, $58, $CF, //5 $D0, $EF, $AA, $FB, $43, $4D, $33, $85, $45, $F9, $02, $7F, $50, $3C, $9F, $A8, //6 $51, $A3, $40, $8F, $92, $9D, $38, $F5, $BC, $B6, $DA, $21, $10, $FF, $F3, $D2, //7 $CD, $0C, $13, $EC, $5F, $97, $44, $17, $C4, $A7, $7E, $3D, $64, $5D, $19, $73, //8 $60, $81, $4F, $DC, $22, $2A, $90, $88, $46, $EE, $B8, $14, $DE, $5E, $0B, $DB, //9 $E0, $32, $3A, $0A, $49, $06, $24, $5C, $C2, $D3, $AC, $62, $91, $95, $E4, $79, //A $E7, $C8, $37, $6D, $8D, $D5, $4E, $A9, $6C, $56, $F4, $EA, $65, $7A, $AE, $08, //B $BA, $78, $25, $2E, $1C, $A6, $B4, $C6, $E8, $DD, $74, $1F, $4B, $BD, $8B, $8A, //C $70, $3E, $B5, $66, $48, $03, $F6, $0E, $61, $35, $57, $B9, $86, $C1, $1D, $9E, //D $E1, $F8, $98, $11, $69, $D9, $8E, $94, $9B, $1E, $87, $E9, $CE, $55, $28, $DF, //E $8C, $A1, $89, $0D, $BF, $E6, $42, $68, $41, $99, $2D, $0F, $B0, $54, $BB, $16); //F Invsbox: Array [0 .. 255] Of Byte = // 0 1 2 3 4 5 6 7 8 9 A B C D E F ($52, $09, $6A, $D5, $30, $36, $A5, $38, $BF, $40, $A3, $9E, $81, $F3, $D7, $FB, //0 $7C, $E3, $39, $82, $9B, $2F, $FF, $87, $34, $8E, $43, $44, $C4, $DE, $E9, $CB, //1 $54, $7B, $94, $32, $A6, $C2, $23, $3D, $EE, $4C, $95, $0B, $42, $FA, $C3, $4E, //2 $08, $2E, $A1, $66, $28, $D9, $24, $B2, $76, $5B, $A2, $49, $6D, $8B, $D1, $25, //3 $72, $F8, $F6, $64, $86, $68, $98, $16, $D4, $A4, $5C, $CC, $5D, $65, $B6, $92, //4 $6C, $70, $48, $50, $FD, $ED, $B9, $DA, $5E, $15, $46, $57, $A7, $8D, $9D, $84, //5 $90, $D8, $AB, $00, $8C, $BC, $D3, $0A, $F7, $E4, $58, $05, $B8, $B3, $45, $06, //6 $D0, $2C, $1E, $8F, $CA, $3F, $0F, $02, $C1, $AF, $BD, $03, $01, $13, $8A, $6B, //7 $3A, $91, $11, $41, $4F, $67, $DC, $EA, $97, $F2, $CF, $CE, $F0, $B4, $E6, $73, //8 $96, $AC, $74, $22, $E7, $AD, $35, $85, $E2, $F9, $37, $E8, $1C, $75, $DF, $6E, //9 $47, $F1, $1A, $71, $1D, $29, $C5, $89, $6F, $B7, $62, $0E, $AA, $18, $BE, $1B, //A $FC, $56, $3E, $4B, $C6, $D2, $79, $20, $9A, $DB, $C0, $FE, $78, $CD, $5A, $F4, //B $1F, $DD, $A8, $33, $88, $07, $C7, $31, $B1, $12, $10, $59, $27, $80, $EC, $5F, //C $60, $51, $7F, $A9, $19, $B5, $4A, $0D, $2D, $E5, $7A, $9F, $93, $C9, $9C, $EF, //D $A0, $E0, $3B, $4D, $AE, $2A, $F5, $B0, $C8, $EB, $BB, $3C, $83, $53, $99, $61, //E $17, $2B, $04, $7E, $BA, $77, $D6, $26, $E1, $69, $14, $63, $55, $21, $0C, $7D); //F Procedure Aes128_Keyschedule_test(Var Keys: Array Of String); Procedure Keyschedule_core(Var Word: Tword; Iteration: Integer; Mode: Byte); Function Multcolumn(Column: Tcolumn; Mode: Byte): Tcolumn; Function Galois_mult(A, B: Byte): Byte; //http://en.wikipedia.org/wiki/Rijndael_mix_columns Procedure Shiftrows(Var State: Tstate; Mode: Byte); Procedure Rotate(Var Value: Tword; Mode: Byte); // rotate(1d 2c 3a 4f) = 2c 3a 4f 1d Procedure AddRoundKey(Var State: Tstate; Roundkey: Tstate); Function Getsboxvalue(Index: Byte): Byte; Function Getinvsboxvalue(Index: Byte): Byte; Function Rcon(Index: Byte): Integer; Function Expandkey(Key: Tinput; Var Expandedkey: Tkey128): Byte; Overload; //result=number of rounds Function Generatesubkeys(Expandedkey: Tkey128): Tsubkeys128; Function Expandkey(Key: Tinput; Var Expandedkey: Tkey192): Byte; Overload; //result=number of rounds Function Expandkey(Key: Tinput; Var Expandedkey: Tkey256): Byte; Overload; //result=number of rounds Procedure Mixcolumns(Var State: Tstate; Mode: Byte); Procedure Subbytes(Var State: Tstate; Mode: Byte); Overload; Procedure Subbytes(Var Word: Tword)Overload; Procedure Showstate(State: Tstate; Memo: Tmemo); Function Texttostate(Substr: String): Tstate; Function Texttokey(Key: String): Tinput; Function Keytostate(Data: Tinput): Tstate; Function Statetotext(State: Tstate): String; Procedure Aes(Roundcount: Byte; Var State: Tstate; Keys: Tsubkeys128; Mode: Byte); End; Implementation { src: http://en.wikipedia.org/wiki/Rijndael_mix_columns: A c# example Multiplication in Rijndael's galois field is a little more complicated. The procedure is as follows: * Take two eight-bit numbers, a and b, and an eight-bit product p * Set the product to zero. * Make a copy of a and b, which we will simply call a and b in the rest of this algorithm * Run the following loop eight times: 1. If the low bit of b is set, exclusive or the product p by the value of a 2. Keep track of whether the high (eighth from left) bit of a is set to one 3. Rotate a one bit to the left, discarding the high bit, and making the low bit have a value of zero 4. If a's hi bit had a value of one prior to this rotation, exclusive or a with the hexadecimal number 0x1b 5. Rotate b one bit to the right, discarding the low bit, and making the high (eighth from left) bit have a value of zero. 6. The product p now has the product of a and b } //------------------------------------------------------------------------------ { The Key Schedule is responsible for expanding a short key into a larger key, whose parts are used during the different iterations. Each key size is expanded to a different size: An 128 bit key is expanded to an 176 byte key. An 192 bit key is expanded to an 208 byte key. An 256 bit key is expanded to an 240 byte key. There is a relation between the cipher key size, the number of rounds and the ExpandedKey size. For an 128-bit key, there is one initial AddRoundKey operation plus there are 10 rounds and each rounds need a new 16 byte key, therefor we require 10+1 RoundKeys of 16 byte, which equals 176 byte. The same logic can be applied to the two other cipher key sizes. The general formula is that: ExpandedKeySize = (nbrRounds+1) * BlockSize } Procedure Taes.Aes128_Keyschedule_test(Var Keys: Array Of String); Var I, J, K: Integer; Aes128: Array Of Tkey128; Begin Setlength(Aes128, Length(Keys)); J := 0; While J < 3 Do Begin Keys[J] := ''; I := 1; While I <= 16 Do Begin Case J Of 1: Keys[J] := Keys[J] + Chr(0); { should be: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 62 63 63 63 62 63 63 63 62 63 63 63 62 63 63 63 9B 98 98 C9 F9 FB FB AA 9B 98 98 C9 F9 FB FB AA 90 97 34 50 69 6C CF FA F2 F4 57 33 0B 0F AC 99 EE 06 DA 7B 87 6A 15 81 75 9E 42 B2 7E 91 EE 2B 7F 2E 2B 88 F8 44 3E 09 8D DA 7C BB F3 4B 92 90 EC 61 4B 85 14 25 75 8C 99 FF 09 37 6A B4 9B A7 21 75 17 87 35 50 62 0B AC AF 6B 3C C6 1B F0 9B 0E F9 03 33 3B A9 61 38 97 06 0A 04 51 1D FA 9F B1 D4 D8 E2 8A 7D B9 DA 1D 7B B3 DE 4C 66 49 41 B4 EF 5B CB 3E 92 E2 11 23 E9 51 CF 6F 8F 18 8E } 2: Keys[J] := Keys[J] + Chr(Strtoint('$FF')); { should be: FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF E8 E9 E9 E9 17 16 16 16 E8 E9 E9 E9 17 16 16 16 AD AE AE 19 BA B8 B8 0F 52 51 51 E6 45 47 47 F0 09 0E 22 77 B3 B6 9A 78 E1 E7 CB 9E A4 A0 8C 6E E1 6A BD 3E 52 DC 27 46 B3 3B EC D8 17 9B 60 B6 E5 BA F3 CE B7 66 D4 88 04 5D 38 50 13 C6 58 E6 71 D0 7D B3 C6 B6 A9 3B C2 EB 91 6B D1 2D C9 8D E9 0D 20 8D 2F BB 89 B6 ED 50 18 DD 3C 7D D1 50 96 33 73 66 B9 88 FA D0 54 D8 E2 0D 68 A5 33 5D 8B F0 3F 23 32 78 C5 F3 66 A0 27 FE 0E 05 14 A3 D6 0A 35 88 E4 72 F0 7B 82 D2 D7 85 8C D7 C3 26 } 3: Keys[J] := Keys[J] + Chr(I - 1); { should be: 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F D6 AA 74 FD D2 AF 72 FA DA A6 78 F1 D6 AB 76 FE B6 92 CF 0B 64 3D BD F1 BE 9B C5 00 68 30 B3 FE B6 FF 74 4E D2 C2 C9 BF 6C 59 0C BF 04 69 BF 41 47 F7 F7 BC 95 35 3E 03 F9 6C 32 BC FD 05 8D FD 3C AA A3 E8 A9 9F 9D EB 50 F3 AF 57 AD F6 22 AA 5E 39 0F 7D F7 A6 92 96 A7 55 3D C1 0A A3 1F 6B 14 F9 70 1A E3 5F E2 8C 44 0A DF 4D 4E A9 C0 26 47 43 87 35 A4 1C 65 B9 E0 16 BA F4 AE BF 7A D2 54 99 32 D1 F0 85 57 68 10 93 ED 9C BE 2C 97 4E 13 11 1D 7F E3 94 4A 17 F3 07 A7 8B 4D 2B 30 C5 } End; Inc(I); End; Expandkey(Texttokey(Keys[J]), Aes128[J]); Keys[J] := ''; K := 1; While K <= Length(Aes128[J]) Do Begin Keys[J] := Keys[J] + Inttohex(Aes128[J][K], 2) + Chr(32); If K Mod 16 = 0 Then Keys[J] := Keys[J] + #13#10; Inc(K); End; Inc(J); End; End; Procedure Taes.Keyschedule_core(Var Word: Tword; Iteration: Integer; Mode: Byte); Begin Rotate(Word, Mode); Subbytes(Word); Word[1] := Word[1] Xor Byte(Rcon(Iteration)); End; Function Taes.Galois_mult(A, B: Byte): Byte; //http://en.wikipedia.org/wiki/Rijndael_mix_columns Var P, Counter, Hi_bit_set: Byte; Aa, Bb: Byte; Begin Aa := A; Bb := B; P := 0; Counter := 0; While Counter < 8 Do Begin If (Bb And 1) <> 0 Then P := P Xor Aa; Hi_bit_set := Byte(Aa And $80); //Mod 256; Aa := Byte(Aa Shl 1); If Hi_bit_set <> 0 Then Aa := Byte(Aa Xor $1b); //x^8+x^4+x^3+x^2+x+1 Bb := Bb Shr 1; Inc(Counter); End; Result := P; End; Function Taes.Multcolumn(Column: Tcolumn; Mode: Byte): Tcolumn; //multiplies a column with the MDS matrix { mds= 2 3 1 1 1 2 3 1 1 1 2 3 3 1 1 2 mdsinv= 14 11 13 9 9 14 11 13 13 9 14 11 11 13 9 14 where + = xor, x = galois-multiplication } Begin Case Mode Of 0: Begin Result[1] := (((Galois_mult(2, Column[1]) Xor Galois_mult(3, Column[2])) Xor Galois_mult (1, Column[3])) Xor Galois_mult(1, Column[4])); Result[2] := (((Galois_mult(1, Column[1]) Xor Galois_mult(2, Column[2])) Xor Galois_mult (3, Column[3])) Xor Galois_mult(1, Column[4])); Result[3] := (((Galois_mult(1, Column[1]) Xor Galois_mult(1, Column[2])) Xor Galois_mult (2, Column[3])) Xor Galois_mult(3, Column[4])); Result[4] := (((Galois_mult(3, Column[1]) Xor Galois_mult(1, Column[2])) Xor Galois_mult (1, Column[3])) Xor Galois_mult(2, Column[4])); End; 1: Begin Result[1] := (((Galois_mult(14, Column[1]) Xor Galois_mult(11, Column[2])) Xor Galois_mult (13, Column[3])) Xor Galois_mult(9, Column[4])); Result[2] := (((Galois_mult(9, Column[1]) Xor Galois_mult(14, Column[2])) Xor Galois_mult (11, Column[3])) Xor Galois_mult(13, Column[4])); Result[3] := (((Galois_mult(13, Column[1]) Xor Galois_mult(9, Column[2])) Xor Galois_mult (14, Column[3])) Xor Galois_mult(11, Column[4])); Result[4] := (((Galois_mult(11, Column[1]) Xor Galois_mult(13, Column[2])) Xor Galois_mult (9, Column[3])) Xor Galois_mult(14, Column[4])); End; End; End; Procedure Taes.Mixcolumns(Var State: Tstate; Mode: Byte); Var Column: Tcolumn; I, J: Integer; Begin //identify columns J := 1; While J <= 4 Do Begin I := 1; While I <= 4 Do Begin Column[I] := State[I][J]; Inc(I); End; Column := Multcolumn(Column, Mode); I := 1; While I <= 4 Do Begin State[I][J] := Column[I]; Inc(I); End; Inc(J); End; End; Procedure Taes.Subbytes(Var State: Tstate; Mode: Byte); //ok Var X: Byte; I, J: Integer; Begin I := 1; While I <= 4 Do Begin J := 1; While J <= 4 Do Begin X := State[I][J]; Case Mode Of 0: X := Sbox[X]; 1: X := Invsbox[X]; End; State[I][J] := X; Inc(J); End; Inc(I); End; End; Procedure Taes.Subbytes(Var Word: Tword); Var I: Integer; Begin I := 1; While I <= 4 Do Begin Word[I] := GetSBoxValue(Word[I]); Inc(I); End; End; Function Taes.Rcon(Index: Byte): Integer; Var C, B: Integer; Begin If Index = 0 Then Result := $8d Else Begin C := 1; While Index <> 1 Do Begin B := C And $80; C := C Shl 1; If B = $80 Then C := C Xor $1b; Dec(Index); End; Result := C; End; End; (* orig c code: ----------------- { unsigned char c=1; if(in == 0) return 0; while(in != 1) { unsigned char b; b = c & 0x80; c <<= 1; if(b == 0x80) { c ^= 0x1b; } in--; } return c; } ----------------- *) Function Taes.Expandkey(Key: Tinput; Var Expandedkey: Tkey128): Byte; //correct! //expands given key (128,192,256 bit, determined by bitlen variable) to (176,208,240 bytes) //blocksize=16=>keysize 128 bit //result:= the number of rounds (10,12,14) determined by new keylength //SRC= http://www.samiam.org/key-schedule.html //http://cboard.cprogramming.com/c-programming/87805-%5Btutorial%5D-implementing-advanced-encryption-standard.html Var I, Rconiterator, A, C: Integer; Temp: Tword; Begin I := 1; While I <= Length(Key) Do Begin Expandedkey[I] := Key[I]; Inc(I); End; Rconiterator := 1; C := Length(Key) + 1; //17 While C <= 176 Do Begin { Copy the temporary variable over from the last 4-byte- block } A := 1; While A <= 4 Do Begin Temp[A] := Expandedkey[A + C - 5]; Inc(A); End; If ((C - 1) Mod 16 = 0) Then Begin Keyschedule_core(Temp, Rconiterator, 0); Inc(Rconiterator); End; A := 1; While A <= 4 Do Begin Expandedkey[C] := Expandedkey[C - 16] Xor Temp[A]; Inc(C); Inc(A); End; End; Result := 11; //number of rounds for 128 bit keys End; Function Taes.Generatesubkeys(Expandedkey: Tkey128): Tsubkeys128; Var I, J, K: Byte; X: Byte; Subkeystate: Tstate; Subkey: Tinput; Begin I := 1; X := 1; While I < Length(Expandedkey) Do Begin J := I; K := 1; While K <= 16 Do Begin Subkey[K] := Expandedkey[J]; Inc(K); Inc(J); End; Subkeystate := Keytostate(Subkey); Result[X] := Subkeystate; Inc(X); I := J; End; End; Function Taes.Expandkey(Key: Tinput; Var Expandedkey: Tkey192): Byte; //expands given key (128,192,256 bit, determined by bitlen variable) to (176,208,240 bytes) //blocksize=16=>keysize 128 bit //result:=new keylength(determines the number of rounds (10,12,14) //SRC= http://www.samiam.org/key-schedule.html //http://cboard.cprogramming.com/c-programming/87805-%5Btutorial%5D-implementing-advanced-encryption-standard.html Var I: Integer; Currentsize, Size: Integer; Rconiteration: Integer; Temp: Tword; Begin Rconiteration := 1; Size := Length(Key); I := 1; While I <= 4 Do Begin Temp[I] := 0; Inc(I); End; Currentsize := 0; I := 1; While I <= Size Do Begin Expandedkey[I] := Key[I]; Inc(I); End; Currentsize := Currentsize + Size; // assign the previous 4 bytes to the temporary value t While Currentsize < Length(Expandedkey) Do Begin I := 1; While I <= 4 Do Begin Temp[I] := Expandedkey[(Currentsize - 4) + I]; Inc(I); End; //every 16,24,32 bytes (respective length of tinput) we apply the core schedule to t and increment rconIteration afterwards If Currentsize Mod Size = 0 Then Begin Keyschedule_core(Temp, Rconiteration + 1, 0); Inc(Rconiteration); End; { We XOR t with the four-byte block 16,24,32 bytes before the new expanded key. * This becomes the next four bytes in the expanded key. } I := 1; While I <= 4 Do Begin Expandedkey[Currentsize] := Expandedkey[Currentsize - Size] Xor Temp[I]; Inc(Currentsize); Inc(I); End; End; Result := 12; //number of rounds for 192 bit keys End; Function Taes.Expandkey(Key: Tinput; Var Expandedkey: Tkey256): Byte; //expands given key (128,192,256 bit, determined by bitlen variable) to (176,208,240 bytes) //blocksize=16=>keysize 128 bit //result:=new keylength(determines the number of rounds (10,12,14) //SRC= http://www.samiam.org/key-schedule.html //http://cboard.cprogramming.com/c-programming/87805-%5Btutorial%5D-implementing-advanced-encryption-standard.html Var I: Integer; Currentsize, Size: Integer; Rconiteration: Integer; Temp: Tword; Begin Rconiteration := 1; Size := Length(Key); I := 1; While I <= 4 Do Begin Temp[I] := 0; Inc(I); End; Currentsize := 0; I := 1; While I <= Size Do Begin Expandedkey[I] := Key[I]; Inc(I); End; Currentsize := Currentsize + Size; // assign the previous 4 bytes to the temporary value t While Currentsize < Length(Expandedkey) Do Begin I := 1; While I <= 4 Do Begin Temp[I] := Expandedkey[(Currentsize - 4) + I]; Inc(I); End; //every 16,24,32 bytes (respective length of tinput) we apply the core schedule to t and increment rconIteration afterwards If Currentsize Mod Size = 0 Then Begin Keyschedule_core(Temp, Rconiteration + 1, 0); Inc(Rconiteration); End; //applies only to 256 bit keys: For 256-bit keys, we add an extra sbox to the calculation If (Size = 32) And (Currentsize Mod Size = 16) Then Begin I := 1; While I <= 4 Do Begin Temp[I] := Getsboxvalue(Temp[I]); Inc(I); End; End; { We XOR t with the four-byte block 16,24,32 bytes before the new expanded key. * This becomes the next four bytes in the expanded key. } I := 1; While I <= 4 Do Begin Expandedkey[Currentsize] := Expandedkey[Currentsize - Size] Xor Temp[I]; Inc(Currentsize); Inc(I); End; End; Result := 14; //number of rounds for 256 bit keys End; Function Taes.Texttostate(Substr: String): Tstate; //max length 16!! Var I, J: Integer; Row: Trow; Begin If Length(Substr) > 16 Then Begin Raise Exception.Create('No valid substring length'); Exit; End; I := 1; While I <= 4 Do Begin J := 1; While J <= 4 Do Begin Row[J] := Ord(Substr[J + 4 * (I - 1)]); Inc(J); End; Result[I] := Row; Inc(I); End; End; Function Taes.Keytostate(Data: Tinput): Tstate; Var I, J: Integer; Row: Trow; Begin I := 1; While I <= 4 Do Begin J := 1; While J <= 4 Do Begin Row[J] := Ord(Data[J + 4 * (I - 1)]); Inc(J); End; Result[I] := Row; Inc(I); End; End; Function Taes.Statetotext(State: Tstate): String; Var I, J: Int64; Begin Result := ''; I := 1; While I <= 4 Do Begin J := 1; While J <= 4 Do Begin Result := Result + Chr(State[I][J]); Inc(J); End; Inc(I); End; End; Function Taes.Texttokey(Key: String): Tinput; Var I: Byte; Begin If Length(Key) > 16 Then Raise Exception.Create('Keylength not accepted. Must be <=16') Else Begin I := 1; While I <= Length(Key) Do Begin Result[I] := Ord(Key[I]); Inc(I); End; While I < 16 Do Begin Result[I] := 0; Inc(I); End; End; End; Procedure Taes.Showstate(State: Tstate; Memo: Tmemo); Var I, J: Integer; Row: Trow; R: String; Begin I := 1; While I <= 4 Do Begin J := 1; R := ''; While J <= 4 Do Begin Row[J] := State[I][J]; R := R + Inttostr(Row[J]) + Chr(32); Inc(J); End; Memo.Lines.Add(R); Inc(I); End; End; Procedure Taes.Shiftrows(Var State: Tstate; Mode: Byte); //ok Function Rowshift(Row: Trow; Count, Mode: Byte): Trow; Var I, K: Integer; Begin I := 1; While I <= 4 Do Begin If Mode = 0 Then Begin K := (I + Count); If K > 4 Then K := K - 4; End Else If Mode = 1 Then Begin K := (I - Count); If K < 1 Then K := K + 4; End; Result[I] := Row[K]; Inc(I); End; End; Var I: Integer; Begin If (Mode = 0) Or (Mode = 1) Then Begin I := 1; While I <= 4 Do Begin State[I] := Rowshift(State[I], I - 1, Mode); Inc(I); End; End Else Exit; End; // rotate(1d 2c 3a 4f) = 2c 3a 4f 1d //tword is 4byte long, Rotation 8 bit (=1byte) to the left=shifting one entry to the left Procedure Taes.Rotate(Var Value: Tword; Mode: Byte); Var I, J: Byte; Result: Tword; Begin Case Mode Of 0: Begin I := 1; While I <= 4 Do Begin J := I + 1; If J > 4 Then J := J - 4; Result[I] := Value[J]; Inc(I); End; End; 1: Begin I := 1; While I <= 4 Do Begin J := I - 1; If J <= 0 Then J := J + 4; Result[I] := Value[J]; Inc(I); End; End; End; Value := Result; End; Procedure Taes.AddRoundKey(Var State: Tstate; Roundkey: Tstate); Var I, J: Integer; Begin I := 1; While I <= 4 Do Begin J := 1; While J <= 4 Do //one row Begin State[I][J] := State[I][J] Xor Roundkey[I][J]; Inc(J); End; Inc(I); End; End; Function Taes.Getsboxvalue(Index: Byte): Byte; Begin Result := Sbox[Index]; End; Function Taes.Getinvsboxvalue(Index: Byte): Byte; Begin Result := Invsbox[Index]; End; Procedure Taes.Aes(Roundcount: Byte; Var State: Tstate; Keys: Tsubkeys128; Mode: Byte); Var I: Integer; Begin If Mode = 0 Then Begin I := 1; Addroundkey(State, Keys[I]); Inc(I); While I <= Roundcount - 1 Do Begin Subbytes(State, Mode); Shiftrows(State, Mode); Mixcolumns(State, Mode); Addroundkey(State, Keys[I]); Inc(I); End; // final round : Subbytes(State, Mode); Shiftrows(State, Mode); Addroundkey(State, Keys[I]); End Else Begin I := Roundcount; //decryption= go backwards from last step on Addroundkey(State, Keys[I]); Shiftrows(State, Mode); Subbytes(State, Mode); I := I - 1; While I >= 2 Do Begin Addroundkey(State, Keys[I]); Mixcolumns(State, Mode); Shiftrows(State, Mode); Subbytes(State, Mode); Dec(I); End; Addroundkey(State, Keys[I]); End; End; Function Taes.Aes_text(Var Text, Key: String; Bitlen: Integer; Mode: Byte): String; Var Substr: String; I, J, Textlen: Int64; State: Tstate; Keystate: Tinput; Roundcount: Integer; Subkeys: Tsubkeys128; Begin Textlen := Length(Text); //padding While Textlen Mod 16 <> 0 Do Begin Text := Text + Chr(0); Inc(Textlen); End; Keystate := Texttokey(Key); Case Bitlen Of 128: Roundcount := Expandkey(Keystate, Expandedkey128); 192: Roundcount := Expandkey(Keystate, Expandedkey192); 256: Roundcount := Expandkey(Keystate, Expandedkey256); Else Begin Result := Text; Raise Exception.Create('Keysize not accepted.'); End; End; Subkeys := Generatesubkeys(Expandedkey128); If Roundcount <> -1 Then Begin I := 1; While I <= Textlen Do Begin J := I; Substr := ''; While J < I + 16 Do Begin Substr := Substr + Text[J]; Inc(J); End; State := Texttostate(Substr); Aes(Roundcount, State, Subkeys, Mode); Substr := Statetotext(State); Result := Result + Substr; I := J; End; End Else Result := Text; //an error occurred End; End. besten dank |
Zitat |
Registriert seit: 25. Sep 2004 79 Beiträge Delphi XE7 Professional |
#7
Zitat:
Könnte jemand testvektoren für aes 128 (text,key,chiffre) zur überprüfung angeben?
|
Zitat |
qwertz543221
(Gast)
n/a Beiträge |
#8
vielen dank
noch eine andere frage, in welcher reihenfolge werden die blöcke eingelesen, zeilen oder spaltenweise? beispiel 16 inputbits 00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f wie folgt? (reihenweise) 00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f oder so (spaltenweise) 00 04 08 0c 01 05 09 0d 02 06 0a 0e 03 07 0b 0f |
Zitat |
qwertz543221
(Gast)
n/a Beiträge |
#9
ok danke an alle. ich habe nun die von blackseven zur verfügung gestellten testwerte erlangt
|
Zitat |
Ansicht |
Linear-Darstellung |
Zur Hybrid-Darstellung wechseln |
Zur Baum-Darstellung wechseln |
ForumregelnEs ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.
BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus. Trackbacks are an
Pingbacks are an
Refbacks are aus
|
|
Nützliche Links |
Heutige Beiträge |
Sitemap |
Suchen |
Code-Library |
Wer ist online |
Alle Foren als gelesen markieren |
Gehe zu... |
LinkBack |
LinkBack URL |
About LinkBacks |