OpenCores
URL https://opencores.org/ocsvn/apbtoaes128/apbtoaes128/trunk

Subversion Repositories apbtoaes128

[/] [apbtoaes128/] [trunk/] [rtl/] [datapath.v] - Blame information for rev 8

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 redbear
//////////////////////////////////////////////////////////////////
2
////
3
////
4
////    AES CORE BLOCK
5
////
6
////
7
////
8 7 redbear
//// This file is part of the APB to I2C project
9 2 redbear
////
10 7 redbear
//// http://www.opencores.org/cores/apbi2c/
11 2 redbear
////
12
////
13
////
14
//// Description
15
////
16
//// Implementation of APB IP core according to
17
////
18
//// aes128_spec IP core specification document.
19
////
20
////
21
////
22
//// To Do: Things are right here but always all block can suffer changes
23
////
24
////
25
////
26
////
27
////
28
//// Author(s): - Felipe Fernandes Da Costa, fefe2560@gmail.com
29
////              Julio Cesar 
30
////
31
///////////////////////////////////////////////////////////////// 
32
////
33
////
34
//// Copyright (C) 2009 Authors and OPENCORES.ORG
35
////
36
////
37
////
38
//// This source file may be used and distributed without
39
////
40
//// restriction provided that this copyright statement is not
41
////
42
//// removed from the file and that any derivative work contains
43
//// the original copyright notice and the associated disclaimer.
44
////
45
////
46
//// This source file is free software; you can redistribute it
47
////
48
//// and/or modify it under the terms of the GNU Lesser General
49
////
50
//// Public License as published by the Free Software Foundation;
51
//// either version 2.1 of the License, or (at your option) any
52
////
53
//// later version.
54
////
55
////
56
////
57
//// This source is distributed in the hope that it will be
58
////
59
//// useful, but WITHOUT ANY WARRANTY; without even the implied
60
////
61
//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
62
////
63
//// PURPOSE. See the GNU Lesser General Public License for more
64
//// details.
65
////
66
////
67
////
68
//// You should have received a copy of the GNU Lesser General
69
////
70
//// Public License along with this source; if not, download it
71
////
72
//// from http://www.opencores.org/lgpl.shtml
73
////
74
////
75
///////////////////////////////////////////////////////////////////
76
module datapath
77
(
78
        // OUTPUTS
79
        output [31:0] col_bus,
80
        output [31:0] key_bus,
81
        output [31:0] iv_bus,
82
        output end_aes,
83
        // INPUTS
84
        input [31:0] bus_in,
85
        input [ 1:0] data_type,
86
        input [ 1:0] rk_sel,
87
        input [ 1:0] key_out_sel,
88
        input [ 3:0] round,
89
        input [ 2:0] sbox_sel,
90
        input [ 3:0] iv_en,
91
        input [ 3:0] iv_sel_rd,
92
        input [ 3:0] col_en_host,
93
        input [ 3:0] col_en_cnt_unit,
94
        input [ 3:0] key_host_en,
95
        input [ 3:0] key_en,
96
        input [ 1:0] key_sel_rd,
97
        input [ 1:0] col_sel,
98
        input [ 1:0] col_sel_host,
99
        input end_comp,
100
        input key_sel,
101
        input key_init,
102
        input bypass_rk,
103
        input bypass_key_en,
104
        input first_block,
105
        input last_round,
106
        input iv_cnt_en,
107
        input iv_cnt_sel,
108
        input enc_dec,
109
        input mode_ctr,
110
        input mode_cbc,
111
        input key_gen,
112
        input key_derivation_en,
113
        input rst_n,
114
        input clk
115
);
116
 
117
//`include "include/control_unit_params.vh"
118
//=============================================================================
119
// SBOX SEL
120
//=============================================================================
121
localparam COL_0 = 3'b000;
122
localparam COL_1 = 3'b001;
123
localparam COL_2 = 3'b010;
124
localparam COL_3 = 3'b011;
125
localparam G_FUNCTION = 3'b100;
126
 
127
//=============================================================================
128
// RK_SEL
129
//=============================================================================
130
localparam COL        = 2'b00;
131
localparam MIXCOL_IN  = 2'b01;
132
localparam MIXCOL_OUT = 2'b10;
133
 
134
//=============================================================================
135
// KEY_OUT_SEL
136
//=============================================================================
137
localparam KEY_0 = 2'b00;
138
localparam KEY_1 = 2'b01;
139
localparam KEY_2 = 2'b10;
140
localparam KEY_3 = 2'b11;
141
 
142
//=============================================================================
143
// COL_SEL
144
//=============================================================================
145
localparam SHIFT_ROWS = 2'b00;
146
localparam ADD_RK_OUT = 2'b01;
147
localparam INPUT      = 2'b10;
148
 
149
//=============================================================================
150
// KEY_SEL
151
//=============================================================================
152
localparam KEY_HOST = 1'b0;
153
localparam KEY_OUT  = 1'b1;
154
 
155
//=============================================================================
156
// KEY_EN
157
//=============================================================================
158
localparam KEY_DIS  = 4'b0000;
159
localparam EN_KEY_0 = 4'b0001;
160
localparam EN_KEY_1 = 4'b0010;
161
localparam EN_KEY_2 = 4'b0100;
162
localparam EN_KEY_3 = 4'b1000;
163
localparam KEY_ALL  = 4'b1111;
164
 
165
//=============================================================================
166
// COL_EN
167
//=============================================================================
168
localparam COL_DIS  = 4'b0000;
169
localparam EN_COL_0 = 4'b0001;
170
localparam EN_COL_1 = 4'b0010;
171
localparam EN_COL_2 = 4'b0100;
172
localparam EN_COL_3 = 4'b1000;
173
localparam COL_ALL  = 4'b1111;
174
 
175
//=============================================================================
176
// IV_CNT_SEL
177
//=============================================================================
178
localparam IV_CNT = 1'b1;
179
localparam IV_BUS = 1'b0;
180
 
181
//=============================================================================
182
// ENABLES
183
//=============================================================================
184
localparam ENABLE = 1'b1;
185
localparam DISABLE = 1'b0;
186
 
187
reg [31 : 0] col     [0:3];
188
reg [31 : 0] key     [0:3];
189
reg [31 : 0] key_host[0:3];
190
reg [31 : 0] bkp     [0:3];
191
reg [31 : 0] bkp_1   [0:3];
192
reg [31 : 0] iv      [0:3];
193
 
194
reg  [127 : 0] col_in;
195
reg  [ 31 : 0] data_in;
196
reg  [ 31 : 0] add_rd_key_in;
197
reg  [ 31 : 0] sbox_input;
198
reg  [ 31 : 0] key_mux_out;
199
reg  [ 31 : 0] iv_mux_out;
200
reg  [ 31 : 0] bkp_mux_out;
201
 
202
wire [127 : 0] key_in, key_out;
203
wire [127 : 0] sr_input;
204
wire [127 : 0] sr_enc, sr_dec;
205
wire [ 31 : 0] add_rk_out;
206
wire [ 31 : 0] sbox_out_enc;
207
wire [ 31 : 0] sbox_out_dec;
208
wire [ 31 : 0] g_in;
209
wire [ 31 : 0] mix_out_enc;
210
wire [ 31 : 0] mix_out_dec;
211
wire [ 31 : 0] add_rd;
212
wire [ 31 : 0] bus_swap;
213
wire [ 31 : 0] iv_bkp_mux;
214
wire [ 31 : 0] xor_input_bkp_iv;
215
wire [ 31 : 0] sr_input_0;
216
wire [ 31 : 0] sr_input_3;
217
wire [  3 : 0] key_en_sel;
218
wire [  3 : 0] bkp_en;
219
wire [  3 : 0] col_en;
220
wire [  1 : 0] key_mux_sel;
221
wire [  1 : 0] rk_sel_mux;
222
wire [  1 : 0] col_sel_w_bypass;
223
wire [  3 : 0] col_en_w_bypass;
224
wire rk_out_sel;
225
wire add_rk_sel;
226
wire key_sel_mux;
227
wire key1_mux_cnt;
228
wire enc_dec_sbox;
229
 
230
reg [31 : 0] sbox_pp2;
231
reg [ 3 : 0] col_en_cnt_unit_pp1;
232
reg [ 3 : 0] col_en_cnt_unit_pp2;
233
reg [ 3 : 0] key_en_pp1;
234
reg [ 3 : 0] round_pp1;
235
reg [ 1 : 0] col_sel_pp1;
236
reg [ 1 : 0] col_sel_pp2;
237
reg [ 1 : 0] key_out_sel_pp1;
238
reg [ 1 : 0] key_out_sel_pp2;
239
reg [ 1 : 0] rk_sel_pp1;
240
reg [ 1 : 0] rk_sel_pp2;
241
reg key_sel_pp1;
242
reg rk_out_sel_pp1, rk_out_sel_pp2;
243
reg last_round_pp1, last_round_pp2;
244 7 redbear
//reg end_aes_pp2;//end_aes_pp1, end_aes_pp2;
245 2 redbear
 
246
assign key_bus = key_mux_out;
247
assign iv_bus = iv_mux_out;
248
 
249
// Input Swap Unit
250
data_swap SWAP_IN
251
(
252
        .data_swap( bus_swap  ),
253
        .data_in  ( bus_in    ),
254
        .swap_type( data_type )
255
);
256
 
257
// Output Swap Unit
258
data_swap SWAP_OUT
259
(
260
        .data_swap( col_bus    ),
261
        .data_in  ( sbox_input ),
262
        .swap_type( data_type  )
263
);
264
 
265
// IV and BKP Muxs
266
always @(*)
267
        begin: IV_BKP_MUX
268
                integer i;
269
                iv_mux_out  = {32{1'b0}};
270
                bkp_mux_out = {32{1'b0}};
271
                for(i = 0; i < 4; i = i + 1)
272
                        begin
273
                                if(col_en[i] | iv_sel_rd[i])
274
                                        begin
275
                                                iv_mux_out  = iv[i];
276
                                                bkp_mux_out = bkp[i];
277
                                        end
278
                        end
279
        end
280
 
281
assign iv_bkp_mux = (first_block && !mode_ctr) ? iv_mux_out : bkp_mux_out;
282
 
283
assign xor_input_bkp_iv = ((enc_dec && !mode_ctr) ? bus_swap : add_rk_out) ^ iv_bkp_mux;
284
 
285
always @(*)
286
        begin
287
                data_in = {32{1'b0}};
288
                case(1'b1)
289
                        mode_cbc:
290
                                data_in = (enc_dec || last_round) ? xor_input_bkp_iv : bus_swap;
291
                        mode_ctr:
292
                                data_in = (last_round) ? xor_input_bkp_iv : iv_mux_out;
293
                        default:
294
                                data_in = bus_swap;
295
                endcase
296
        end
297
 
298
assign bkp_en = ( {4{ mode_cbc && last_round && enc_dec}} & col_en_cnt_unit_pp2) |
299
                ( {4{(mode_cbc && !enc_dec) || mode_ctr}} & col_en_host     );
300
 
301
 
302
// IV and BKP Registers
303
generate
304
        genvar l;
305 7 redbear
 
306
        for(l = 0; l < 4;l=l+1)
307
        begin
308 2 redbear
                always @(posedge clk, negedge rst_n)
309 7 redbear
                begin
310 2 redbear
                                if(!rst_n)
311 7 redbear
                                begin
312 2 redbear
                                                iv[l]    <= {32{1'b0}};
313
                                                bkp[l]   <= {32{1'b0}};
314
                                                bkp_1[l] <= {32{1'b0}};
315 7 redbear
                                end
316 2 redbear
                                else
317 7 redbear
                                begin
318 2 redbear
                                                if(l == 3)
319 7 redbear
                                                begin
320 2 redbear
                                                                if(iv_en[l] || iv_cnt_en)
321 8 redbear
                                                                        //iv[l] <= (iv_cnt_sel) ? iv[l] + 1'b1 : bus_in;
322
                                                                        iv[l] <= (iv_cnt_sel) ? iv[l] : bus_in;
323 7 redbear
                                                end
324 2 redbear
                                                else
325 7 redbear
                                                begin
326 2 redbear
                                                                if(iv_en[l])
327
                                                                        iv[l] <= bus_in;
328 7 redbear
                                                end
329 2 redbear
 
330
                                        if(bkp_en[l])
331 7 redbear
                                                //bkp[l] <= (mode_ctr) ? bus_swap : ((mode_cbc && enc_dec) ? col_in : bkp_1[l]);
332 8 redbear
                                        bkp[l] <= (mode_ctr) ? bus_swap : ((mode_cbc && enc_dec)? col_in[32*(l + 1) - 1 : 32*l] : bkp_1[l]);
333 2 redbear
 
334
                                        if(bkp_en[l])
335 7 redbear
                                                bkp_1[l] <= col_in[32*(l + 1) - 1 : 32*l];
336
                                end
337 2 redbear
                        end
338 7 redbear
 
339
                end
340 2 redbear
endgenerate
341
 
342
assign col_sel_w_bypass = (bypass_rk) ? col_sel : col_sel_pp2;
343
 
344
// Columns Input Multiplexors
345
always @(*)
346
        begin
347
                col_in = {128{1'b0}};
348
                case(col_sel_w_bypass)
349
                        SHIFT_ROWS:
350
                                col_in = (enc_dec) ? sr_enc : sr_dec;
351
                        ADD_RK_OUT:
352
                                col_in = {4{add_rk_out}};
353
                        INPUT:
354
                                col_in = {4{data_in}};
355
                endcase
356
        end
357
 
358
assign col_en_w_bypass = (bypass_rk) ? col_en_cnt_unit : col_en_cnt_unit_pp2;
359
assign col_en = col_en_host | col_en_w_bypass;
360
 
361
// Columns Definition
362
generate
363
        genvar i;
364
        for(i = 0; i < 4; i = i + 1)
365
                always @(posedge clk, negedge rst_n)
366
                        begin
367
                                if(!rst_n)
368
                                        col[3 - i] <= {32{1'b0}};
369
                                else
370
                                if(col_en[3 - i])
371
                                        col[3 - i] <= col_in[32*(i + 1) - 1 : 32*i];
372
                        end
373
endgenerate
374
 
375
// Shift Rows Operation
376
assign sr_input_3 = (enc_dec) ? add_rk_out : col[3];
377
assign sr_input_0 = (enc_dec) ? col[0] : add_rk_out;
378
assign sr_input = {sr_input_0, col[1], col[2], sr_input_3};
379
 
380
shift_rows SHIFT_ROW
381
(
382
        .data_out_enc  ( sr_enc   ),
383
        .data_out_dec  ( sr_dec   ),
384
  .data_in       ( sr_input )
385
);
386
 
387
//SBOX Input Multiplexor
388
always @(*)
389
        begin
390
                sbox_input = {32{1'b0}};
391
                case(sbox_sel | col_sel_host)
392
                        COL_0:
393
                                sbox_input = col[0];
394
                        COL_1:
395
                                sbox_input = col[1];
396
                        COL_2:
397
                                sbox_input = col[2];
398
                        COL_3:
399
                                sbox_input = col[3];
400
                        G_FUNCTION:
401
                                sbox_input = g_in;
402
                endcase
403
        end
404
 
405
// 32 bits SBOX
406
assign enc_dec_sbox = enc_dec | key_gen;
407
 sBox SBOX
408
  (
409
    .sbox_out_enc ( sbox_out_enc ),
410
                .sbox_out_dec ( sbox_out_dec ),
411
    .sbox_in      ( sbox_input   ),
412
    .enc_dec      ( enc_dec_sbox ),
413
                .clk          ( clk          )
414
  );
415
 
416
// Second stage of pipeline
417
always @(posedge clk)
418
        begin
419
                sbox_pp2 <= (enc_dec || mode_ctr) ? sbox_out_enc : sbox_out_dec ^ key_mux_out;
420
        end
421
 
422
assign key_en_sel  = (bypass_key_en) ? key_en : key_en_pp1;
423
assign key_sel_mux = (bypass_key_en) ? key_sel : key_sel_pp1;
424
 
425
// Key registers
426
generate
427
        genvar j;
428
        for(j = 0; j < 4; j = j + 1)
429
                always @(posedge clk, negedge rst_n)
430
                        begin
431
                                if(!rst_n)
432
                                        begin
433
                                                key_host[3 - j] <= {32{1'b0}};
434
                                                key[3 - j] <= {32{1'b0}};
435
                                        end
436
                                else
437
                                        begin
438
                                                if(key_host_en[3 - j] || key_derivation_en)
439
                                                        key_host[3 - j] <= (key_derivation_en) ? key[3 - j] : bus_in;
440
 
441
                                                if(key_en_sel[3 - j] || key_init || key_host_en[3 - j])
442
                                                        key[3 - j] <= (key_sel_mux) ? key_out[32*(j + 1) - 1 : 32*j] : ( (key_host_en[3 - j]) ? bus_in : key_host[3 - j] );
443
                                        end
444
                        end
445
endgenerate
446
 
447
assign key_in = {key[0], key[1], key[2], key[3]};
448
 
449
assign key1_mux_cnt = bypass_key_en & enc_dec;
450
 
451
key_expander KEY_EXPANDER
452
(
453
        .key_out   ( key_out       ),
454
        .g_in              ( g_in          ),
455
        .g_out     ( sbox_out_enc  ),
456
        .key_in    ( key_in        ),
457
        .round     ( round_pp1     ),
458
        .add_w_out ( key1_mux_cnt  ),
459
        .enc_dec   ( enc_dec | key_gen)
460
);
461
 
462
assign key_mux_sel = (bypass_key_en) ? key_out_sel : ( (enc_dec | mode_ctr) ? key_out_sel_pp2 : key_out_sel_pp1 );
463
 
464
// Key Expander Mux
465
always @(*)
466
        begin
467
                key_mux_out = {32{1'b0}};
468
                case(key_mux_sel | key_sel_rd)
469
                        KEY_0:
470
                                key_mux_out = key[0];
471
                        KEY_1:
472
                                key_mux_out = key[1];
473
                        KEY_2:
474
                                key_mux_out = key[2];
475
                        KEY_3:
476
                                key_mux_out = key[3];
477
                endcase
478
        end
479
 
480
  mix_columns MIX_COL
481
  (
482
    .mix_out_enc ( mix_out_enc  ),
483
                .mix_out_dec ( mix_out_dec  ),
484
    .mix_in      ( sbox_pp2     )
485
  );
486
 
487
assign rk_sel_mux = (bypass_rk) ? rk_sel : rk_sel_pp2;
488
 
489
always @(*)
490
        begin
491
                add_rd_key_in = {32{1'b0}};
492
                case(rk_sel_mux)
493
                        COL:
494
                                add_rd_key_in = sbox_input;
495
                        MIXCOL_IN:
496
                                add_rd_key_in = sbox_pp2;
497
                        MIXCOL_OUT:
498
                                add_rd_key_in = mix_out_enc;
499
                endcase
500
        end
501
 
502
// Add Round Key
503
assign add_rd = add_rd_key_in ^ key_mux_out;
504
 
505
assign rk_out_sel = (enc_dec | mode_ctr | bypass_rk);
506
 
507
assign add_rk_sel = (bypass_rk) ? rk_out_sel : rk_out_sel_pp2;
508
 
509
assign add_rk_out = (add_rk_sel) ? add_rd : (last_round_pp2 ? sbox_pp2 : mix_out_dec);
510
 
511 7 redbear
assign end_aes = end_comp;//end_aes_pp2;
512 2 redbear
 
513
// Pipeline Registers for Control Signals
514
always @(posedge clk, negedge rst_n)
515
        begin
516
                if(!rst_n)
517
                        begin
518 7 redbear
                                //end_aes_pp1 <= DISABLE;
519
                                //end_aes_pp2 <= DISABLE;
520 2 redbear
 
521
                                col_sel_pp1 <= INPUT;
522
                                col_sel_pp2 <= INPUT;
523
 
524
                                col_en_cnt_unit_pp1 <= COL_DIS;
525
                                col_en_cnt_unit_pp2 <= COL_DIS;
526
 
527
                                key_sel_pp1 <= KEY_HOST;
528
                                key_en_pp1  <= KEY_DIS;
529
 
530
                                round_pp1 <= 4'b0000;
531
 
532
                                key_out_sel_pp1 <= KEY_0;
533
                                key_out_sel_pp2 <= KEY_0;
534
 
535
                                rk_sel_pp1 <= COL;
536
                                rk_sel_pp2 <= COL;
537
 
538
                                rk_out_sel_pp1 <= 1'b1;
539
                                rk_out_sel_pp2 <= 1'b1;
540
 
541
                                last_round_pp1 <= 1'b1;
542
                                last_round_pp2 <= 1'b0;
543
                        end
544
                else
545
                        begin
546
                                col_sel_pp1 <= col_sel;
547
                                col_sel_pp2 <= col_sel_pp1;
548
 
549
                                if(!bypass_rk)
550
                                        begin
551
                                                col_en_cnt_unit_pp1 <= col_en_cnt_unit;
552
                                                col_en_cnt_unit_pp2 <= col_en_cnt_unit_pp1;
553
                                        end
554
 
555
                                key_sel_pp1 <= key_sel;
556
 
557
                                if(!bypass_key_en)
558
                                        key_en_pp1 <= key_en;
559
 
560
                                round_pp1 <= round;
561
 
562
                                key_out_sel_pp1 <= key_out_sel;
563
                                key_out_sel_pp2 <= key_out_sel_pp1;
564
 
565
                                rk_sel_pp1 <= rk_sel;
566
                                rk_sel_pp2 <= rk_sel_pp1;
567
 
568
                                rk_out_sel_pp1 <= rk_out_sel;
569
                                rk_out_sel_pp2 <= rk_out_sel_pp1;
570
 
571
                                last_round_pp1 <= last_round;
572
                                last_round_pp2 <= last_round_pp1;
573
 
574 7 redbear
                                //end_aes_pp1 <= end_comp;
575
                                //end_aes_pp2 <= end_comp;
576 2 redbear
                        end
577
        end
578
endmodule

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.