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

Subversion Repositories csa

[/] [csa/] [trunk/] [sw_sim/] [csa.c] - Blame information for rev 15

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

Line No. Rev Author Line
1 10 simon111
/*
2
    dvb common scrambling algorithm
3
 
4
    refs:
5
        uk patent: gb 2322 994
6
        uk patent: gb 2322 995
7
        freedec v2.1
8
        iso/iec 13818-1
9
        etr289 / dvb document a007
10
 
11
*/
12
 
13
#include <memory.h>
14 15 simon111
#include <stdio.h>
15 10 simon111
#include "csa.h"
16
 
17
#ifndef NULL
18
#define NULL 0
19
#endif
20
 
21
/* stream cypher */
22
 
23
/*  107 state bits */
24
/*  26 nibbles (4 bit) */
25
/*  +  3 bits */
26
/*  reg A[1]-A[10], 10 nibbles */
27
/*  reg B[1]-B[10], 10 nibbles */
28
/*  reg X,           1 nibble */
29
/*  reg Y,           1 nibble */
30
/*  reg Z,           1 nibble */
31
/*  reg D,           1 nibble */
32
/*  reg E,           1 nibble */
33
/*  reg F,           1 nibble */
34
/*  reg p,           1 bit */
35
/*  reg q,           1 bit */
36
/*  reg r,           1 bit */
37
 
38
int sbox1[0x20] = {2,0,1,1,2,3,3,0, 3,2,2,0,1,1,0,3, 0,3,3,0,2,2,1,1, 2,2,0,3,1,1,3,0};
39
int sbox2[0x20] = {3,1,0,2,2,3,3,0, 1,3,2,1,0,0,1,2, 3,1,0,3,3,2,0,2, 0,0,1,2,2,1,3,1};
40
int sbox3[0x20] = {2,0,1,2,2,3,3,1, 1,1,0,3,3,0,2,0, 1,3,0,1,3,0,2,2, 2,0,1,2,0,3,3,1};
41
int sbox4[0x20] = {3,1,2,3,0,2,1,2, 1,2,0,1,3,0,0,3, 1,0,3,1,2,3,0,3, 0,3,2,0,1,2,2,1};
42
int sbox5[0x20] = {2,0,0,1,3,2,3,2, 0,1,3,3,1,0,2,1, 2,3,2,0,0,3,1,1, 1,0,3,2,3,1,0,2};
43
int sbox6[0x20] = {0,1,2,3,1,2,2,0, 0,1,3,0,2,3,1,3, 2,3,0,2,3,0,1,1, 2,1,1,2,0,3,3,0};
44
int sbox7[0x20] = {0,3,2,2,3,0,0,1, 3,0,1,3,1,2,2,1, 1,0,3,3,0,1,1,2, 2,3,1,0,2,3,0,2};
45
 
46
void stream_cypher(int init, unsigned char *CK, unsigned char *sb, unsigned char *cb) {
47
    int i,j;
48
    int in1;        /*  most  significant nibble of input byte */
49
    int in2;        /*  least significant nibble of input byte */
50
    int op;
51
    int extra_B;
52
    int s1,s2,s3,s4,s5,s6,s7;
53
    int next_A1;
54
    int next_B1;
55
    int next_E;
56
 
57
    static int A[11];
58
    static int B[11];
59
    static int X;
60
    static int Y;
61
    static int Z;
62
    static int D;
63
    static int E;
64
    static int F;
65
    static int p;
66
    static int q;
67
    static int r;
68
 
69
    /*  reset */
70
    if (init) {
71
        /*  load first 32 bits of CK into A[1]..A[8] */
72
        /*  load last  32 bits of CK into B[1]..B[8] */
73
        /*  all other regs = 0 */
74
        A[1] = (CK[0] >> 4) & 0xf;
75
        A[2] = (CK[0] >> 0) & 0xf;
76
        A[3] = (CK[1] >> 4) & 0xf;
77
        A[4] = (CK[1] >> 0) & 0xf;
78
        A[5] = (CK[2] >> 4) & 0xf;
79
        A[6] = (CK[2] >> 0) & 0xf;
80
        A[7] = (CK[3] >> 4) & 0xf;
81
        A[8] = (CK[3] >> 0) & 0xf;
82
        A[9] = 0;
83
        A[10] = 0;
84
        B[1] = (CK[4] >> 4) & 0xf;
85
        B[2] = (CK[4] >> 0) & 0xf;
86
        B[3] = (CK[5] >> 4) & 0xf;
87
        B[4] = (CK[5] >> 0) & 0xf;
88
        B[5] = (CK[6] >> 4) & 0xf;
89
        B[6] = (CK[6] >> 0) & 0xf;
90
        B[7] = (CK[7] >> 4) & 0xf;
91
        B[8] = (CK[7] >> 0) & 0xf;
92
        B[9] = 0;
93
        B[10] = 0;
94
 
95
        X=0;
96
        Y=0;
97
        Z=0;
98
        D=0;
99
        E=0;
100
        F=0;
101
        p=0;
102
        q=0;
103
        r=0;
104
    } /* init */
105
 
106
    /*  8 bytes per operation */
107
    for(i=0; i<8; i++) {
108
        if (init) {
109
            in1 = (sb[i] >> 4) & 0x0f;
110
            in2 = (sb[i] >> 0) & 0x0f;
111
        } /* init */
112
        op = 0;
113
        /*  2 bits per iteration */
114
        for(j=0; j<4; j++) {
115
            /*  from A[1]..A[10], 35 bits are selected as inputs to 7 s-boxes */
116
            /*  5 bits input per s-box, 2 bits output per s-box */
117
            s1 = sbox1[ (((A[4]>>0)&1)<<4) | (((A[1]>>2)&1)<<3) | (((A[6]>>1)&1)<<2) | (((A[7]>>3)&1)<<1) | (((A[9]>>0)&1)<<0) ];
118
            s2 = sbox2[ (((A[2]>>1)&1)<<4) | (((A[3]>>2)&1)<<3) | (((A[6]>>3)&1)<<2) | (((A[7]>>0)&1)<<1) | (((A[9]>>1)&1)<<0) ];
119
            s3 = sbox3[ (((A[1]>>3)&1)<<4) | (((A[2]>>0)&1)<<3) | (((A[5]>>1)&1)<<2) | (((A[5]>>3)&1)<<1) | (((A[6]>>2)&1)<<0) ];
120
            s4 = sbox4[ (((A[3]>>3)&1)<<4) | (((A[1]>>1)&1)<<3) | (((A[2]>>3)&1)<<2) | (((A[4]>>2)&1)<<1) | (((A[8]>>0)&1)<<0) ];
121
            s5 = sbox5[ (((A[5]>>2)&1)<<4) | (((A[4]>>3)&1)<<3) | (((A[6]>>0)&1)<<2) | (((A[8]>>1)&1)<<1) | (((A[9]>>2)&1)<<0) ];
122
            s6 = sbox6[ (((A[3]>>1)&1)<<4) | (((A[4]>>1)&1)<<3) | (((A[5]>>0)&1)<<2) | (((A[7]>>2)&1)<<1) | (((A[9]>>3)&1)<<0) ];
123
            s7 = sbox7[ (((A[2]>>2)&1)<<4) | (((A[3]>>0)&1)<<3) | (((A[7]>>1)&1)<<2) | (((A[8]>>2)&1)<<1) | (((A[8]>>3)&1)<<0) ];
124
 
125
            /*  use 4x4 xor to produce extra nibble for T3 */
126
            extra_B = ( ((B[3]&1)<<3) ^ ((B[6]&2)<<2) ^ ((B[7]&4)<<1) ^ ((B[9]&8)>>0) ) |
127
                      ( ((B[6]&1)<<2) ^ ((B[8]&2)<<1) ^ ((B[3]&8)>>1) ^ ((B[4]&4)>>0) ) |
128
                      ( ((B[5]&8)>>2) ^ ((B[8]&4)>>1) ^ ((B[4]&1)<<1) ^ ((B[5]&2)>>0) ) |
129
                      ( ((B[9]&4)>>2) ^ ((B[6]&8)>>3) ^ ((B[3]&2)>>1) ^ ((B[8]&1)>>0) ) ;
130
 
131
            /*  T1 = xor all inputs */
132
            /*  in1,in2, D are only used in T1 during initialisation, not generation */
133
            next_A1 = A[10] ^ X;
134
            if (init)
135
                                next_A1 = next_A1 ^ D ^ ((j % 2) ? in2 : in1);
136
 
137
            /*  T2 =  xor all inputs */
138
            /*  in1,in2 are only used in T1 during initialisation, not generation */
139
            /*  if p=0, use this, if p=1, rotate the result left */
140
            next_B1 = B[7] ^ B[10] ^ Y;
141
            if (init)
142
                                next_B1 = next_B1 ^ ((j % 2) ? in1 : in2);
143
 
144
            /*  if p=1, rotate left */
145
            if (p)
146
                                next_B1 = ( (next_B1 << 1) | ((next_B1 >> 3) & 1) ) & 0xf;
147
 
148
            /*  T3 = xor all inputs */
149
            D = E ^ Z ^ extra_B;
150
 
151
            /*  T4 = sum, carry of Z + E + r */
152
            next_E = F;
153
            if (q) {
154
                F = Z + E + r;
155
                /*  r is the carry */
156
                r = (F >> 4) & 1;
157
                F = F & 0x0f;
158
            } /* q */
159
            else {
160
                F = E;
161
            }
162
            E = next_E;
163
 
164
            A[10] = A[9];
165
            A[9] = A[8];
166
            A[8] = A[7];
167
            A[7] = A[6];
168
            A[6] = A[5];
169
            A[5] = A[4];
170
            A[4] = A[3];
171
            A[3] = A[2];
172
            A[2] = A[1];
173
            A[1]= next_A1;
174
 
175
            B[10] = B[9];
176
            B[9] = B[8];
177
            B[8] = B[7];
178
            B[7] = B[6];
179
            B[6] = B[5];
180
            B[5] = B[4];
181
            B[4] = B[3];
182
            B[3] = B[2];
183
            B[2] = B[1];
184
            B[1] = next_B1;
185
 
186
            X = ((s4&1)<<3) | ((s3&1)<<2) | (s2&2) | ((s1&2)>>1);
187
            Y = ((s6&1)<<3) | ((s5&1)<<2) | (s4&2) | ((s3&2)>>1);
188
            Z = ((s2&1)<<3) | ((s1&1)<<2) | (s6&2) | ((s5&2)>>1);
189
            p = (s7&2)>>1;
190
            q = (s7&1);
191
 
192
            /*  require 4 loops per output byte */
193
            /*  2 output bits are a function of the 4 bits of D */
194
            /*  xor 2 by 2 */
195
            op = (op << 2)^ ( (((D^(D>>1))>>1)&2) | ((D^(D>>1))&1) );
196
        }
197
        /*  return input data during init */
198
        cb[i] = (init) ? sb[i] : op;
199
    }
200
}
201
 
202
/* block cypher */
203
 
204
/*  key preparation */
205
unsigned char key_perm[0x40] = {
206
    0x12,0x24,0x09,0x07,0x2A,0x31,0x1D,0x15,0x1C,0x36,0x3E,0x32,0x13,0x21,0x3B,0x40,
207
    0x18,0x14,0x25,0x27,0x02,0x35,0x1B,0x01,0x22,0x04,0x0D,0x0E,0x39,0x28,0x1A,0x29,
208
    0x33,0x23,0x34,0x0C,0x16,0x30,0x1E,0x3A,0x2D,0x1F,0x08,0x19,0x17,0x2F,0x3D,0x11,
209
    0x3C,0x05,0x38,0x2B,0x0B,0x06,0x0A,0x2C,0x20,0x3F,0x2E,0x0F,0x03,0x26,0x10,0x37,
210
};
211
 
212
/*  block - sbox */
213
unsigned char block_sbox[0x100] = {
214
    0x3A,0xEA,0x68,0xFE,0x33,0xE9,0x88,0x1A,0x83,0xCF,0xE1,0x7F,0xBA,0xE2,0x38,0x12,
215
    0xE8,0x27,0x61,0x95,0x0C,0x36,0xE5,0x70,0xA2,0x06,0x82,0x7C,0x17,0xA3,0x26,0x49,
216
    0xBE,0x7A,0x6D,0x47,0xC1,0x51,0x8F,0xF3,0xCC,0x5B,0x67,0xBD,0xCD,0x18,0x08,0xC9,
217
    0xFF,0x69,0xEF,0x03,0x4E,0x48,0x4A,0x84,0x3F,0xB4,0x10,0x04,0xDC,0xF5,0x5C,0xC6,
218
    0x16,0xAB,0xAC,0x4C,0xF1,0x6A,0x2F,0x3C,0x3B,0xD4,0xD5,0x94,0xD0,0xC4,0x63,0x62,
219
    0x71,0xA1,0xF9,0x4F,0x2E,0xAA,0xC5,0x56,0xE3,0x39,0x93,0xCE,0x65,0x64,0xE4,0x58,
220
    0x6C,0x19,0x42,0x79,0xDD,0xEE,0x96,0xF6,0x8A,0xEC,0x1E,0x85,0x53,0x45,0xDE,0xBB,
221
    0x7E,0x0A,0x9A,0x13,0x2A,0x9D,0xC2,0x5E,0x5A,0x1F,0x32,0x35,0x9C,0xA8,0x73,0x30,
222
 
223
    0x29,0x3D,0xE7,0x92,0x87,0x1B,0x2B,0x4B,0xA5,0x57,0x97,0x40,0x15,0xE6,0xBC,0x0E,
224
    0xEB,0xC3,0x34,0x2D,0xB8,0x44,0x25,0xA4,0x1C,0xC7,0x23,0xED,0x90,0x6E,0x50,0x00,
225
    0x99,0x9E,0x4D,0xD9,0xDA,0x8D,0x6F,0x5F,0x3E,0xD7,0x21,0x74,0x86,0xDF,0x6B,0x05,
226
    0x8E,0x5D,0x37,0x11,0xD2,0x28,0x75,0xD6,0xA7,0x77,0x24,0xBF,0xF0,0xB0,0x02,0xB7,
227
    0xF8,0xFC,0x81,0x09,0xB1,0x01,0x76,0x91,0x7D,0x0F,0xC8,0xA0,0xF2,0xCB,0x78,0x60,
228
    0xD1,0xF7,0xE0,0xB5,0x98,0x22,0xB3,0x20,0x1D,0xA6,0xDB,0x7B,0x59,0x9F,0xAE,0x31,
229
    0xFB,0xD3,0xB6,0xCA,0x43,0x72,0x07,0xF4,0xD8,0x41,0x14,0x55,0x0D,0x54,0x8B,0xB9,
230
    0xAD,0x46,0x0B,0xAF,0x80,0x52,0x2C,0xFA,0x8C,0x89,0x66,0xFD,0xB2,0xA9,0x9B,0xC0,
231
};
232
 
233
/*  block - perm */
234
unsigned long block_perm[0x100] = {
235
    0x00,0x02,0x80,0x82,0x20,0x22,0xA0,0xA2, 0x10,0x12,0x90,0x92,0x30,0x32,0xB0,0xB2,
236
    0x04,0x06,0x84,0x86,0x24,0x26,0xA4,0xA6, 0x14,0x16,0x94,0x96,0x34,0x36,0xB4,0xB6,
237
    0x40,0x42,0xC0,0xC2,0x60,0x62,0xE0,0xE2, 0x50,0x52,0xD0,0xD2,0x70,0x72,0xF0,0xF2,
238
    0x44,0x46,0xC4,0xC6,0x64,0x66,0xE4,0xE6, 0x54,0x56,0xD4,0xD6,0x74,0x76,0xF4,0xF6,
239
    0x01,0x03,0x81,0x83,0x21,0x23,0xA1,0xA3, 0x11,0x13,0x91,0x93,0x31,0x33,0xB1,0xB3,
240
    0x05,0x07,0x85,0x87,0x25,0x27,0xA5,0xA7, 0x15,0x17,0x95,0x97,0x35,0x37,0xB5,0xB7,
241
    0x41,0x43,0xC1,0xC3,0x61,0x63,0xE1,0xE3, 0x51,0x53,0xD1,0xD3,0x71,0x73,0xF1,0xF3,
242
    0x45,0x47,0xC5,0xC7,0x65,0x67,0xE5,0xE7, 0x55,0x57,0xD5,0xD7,0x75,0x77,0xF5,0xF7,
243
 
244
    0x08,0x0A,0x88,0x8A,0x28,0x2A,0xA8,0xAA, 0x18,0x1A,0x98,0x9A,0x38,0x3A,0xB8,0xBA,
245
    0x0C,0x0E,0x8C,0x8E,0x2C,0x2E,0xAC,0xAE, 0x1C,0x1E,0x9C,0x9E,0x3C,0x3E,0xBC,0xBE,
246
    0x48,0x4A,0xC8,0xCA,0x68,0x6A,0xE8,0xEA, 0x58,0x5A,0xD8,0xDA,0x78,0x7A,0xF8,0xFA,
247
    0x4C,0x4E,0xCC,0xCE,0x6C,0x6E,0xEC,0xEE, 0x5C,0x5E,0xDC,0xDE,0x7C,0x7E,0xFC,0xFE,
248
    0x09,0x0B,0x89,0x8B,0x29,0x2B,0xA9,0xAB, 0x19,0x1B,0x99,0x9B,0x39,0x3B,0xB9,0xBB,
249
    0x0D,0x0F,0x8D,0x8F,0x2D,0x2F,0xAD,0xAF, 0x1D,0x1F,0x9D,0x9F,0x3D,0x3F,0xBD,0xBF,
250
    0x49,0x4B,0xC9,0xCB,0x69,0x6B,0xE9,0xEB, 0x59,0x5B,0xD9,0xDB,0x79,0x7B,0xF9,0xFB,
251
    0x4D,0x4F,0xCD,0xCF,0x6D,0x6F,0xED,0xEF, 0x5D,0x5F,0xDD,0xDF,0x7D,0x7F,0xFD,0xFF,
252
};
253
 
254 13 simon111
void key_schedule(unsigned char *CK, int *kk)
255
{
256 10 simon111
    int i,j,k;
257
    int bit[64];
258
    int newbit[64];
259
    int kb[9][8];
260
 
261
    /*  56 steps */
262
    /*  56 key bytes kk(56)..kk(1) by key schedule from CK */
263
 
264
    /*  kb(7,1) .. kb(7,8) = CK(1) .. CK(8) */
265
    kb[7][1] = CK[0];
266
    kb[7][2] = CK[1];
267
    kb[7][3] = CK[2];
268
    kb[7][4] = CK[3];
269
    kb[7][5] = CK[4];
270
    kb[7][6] = CK[5];
271
    kb[7][7] = CK[6];
272
    kb[7][8] = CK[7];
273
 
274
    /*  calculate kb[6] .. kb[1] */
275
    for(i=0; i<7; i++) {
276
        /*  64 bit perm on kb */
277
        for(j=0; j<8; j++) {
278
            for(k=0; k<8; k++) {
279
                bit[j*8+k] = (kb[7-i][1+j] >> (7-k)) & 1;
280
                newbit[key_perm[j*8+k]-1] = bit[j*8+k];
281
            }
282
        }
283
        for(j=0; j<8; j++) {
284
            kb[6-i][1+j] = 0;
285
            for(k=0; k<8; k++) {
286
                kb[6-i][1+j] |= newbit[j*8+k] << (7-k);
287
            }
288
        }
289
    }
290
 
291 15 simon111
#ifdef DEBUG 
292
{
293
        int i;
294
        int *p=(int*)kb;
295
        for(i=65*8-1;i>=8;i--)
296
        {
297
                if(p[i/8]&(1<<(i%8)))
298
                        printf("1");
299
                else
300
                        printf("0");
301
        }
302
        printf("\n");
303
}
304
#endif
305 10 simon111
    /*  xor to give kk */
306
    for(i=0; i<7; i++) {
307
        for(j=0; j<8; j++) {
308
            kk[1+i*8+j] = kb[1+i][1+j] ^ i;
309
        }
310
    }
311
 
312
}
313
 
314
void block_decypher(int *kk, unsigned char *ib, unsigned char *bd) {
315
    int i;
316
    int sbox_in;
317
    int sbox_out;
318
    int perm_out;
319
    int R[9];
320
    int next_R8;
321
 
322
    R[1] = ib[0];
323
    R[2] = ib[1];
324
    R[3] = ib[2];
325
    R[4] = ib[3];
326
    R[5] = ib[4];
327
    R[6] = ib[5];
328
    R[7] = ib[6];
329
    R[8] = ib[7];
330
 
331
    /*  loop over kk[56]..kk[1] */
332
    for(i=56; i>0; i--) {
333
        sbox_in = kk[i] ^ R[7];
334
        sbox_out = block_sbox[sbox_in];
335
        perm_out = block_perm[sbox_out];
336
 
337
        next_R8 = R[7];
338
        R[7] = R[6] ^ perm_out;
339
        R[6] = R[5];
340
        R[5] = R[4] ^ R[8] ^ sbox_out;
341
        R[4] = R[3] ^ R[8] ^ sbox_out;
342
        R[3] = R[2] ^ R[8] ^ sbox_out;
343
        R[2] = R[1];
344
        R[1] = R[8] ^ sbox_out;
345
 
346
        R[8] = next_R8;
347
    }
348
 
349
    bd[0] = R[1];
350
    bd[1] = R[2];
351
    bd[2] = R[3];
352
    bd[3] = R[4];
353
    bd[4] = R[5];
354
    bd[5] = R[6];
355
    bd[6] = R[7];
356
    bd[7] = R[8];
357
 
358
}
359
 
360
void set_cws(unsigned char *cws, struct key *key) {
361
        memcpy(key->odd_ck,cws+8,8);
362
        memcpy(key->even_ck,cws,8);
363
        key_schedule(key->odd_ck,key->odd_kk);
364
        key_schedule(key->even_ck,key->even_kk);
365
}
366
 
367
void decrypt(struct key *key, unsigned char *encrypted, unsigned char *decrypted) {
368
    int i,j,offset=4,N;
369
    int *kk=key->even_kk;
370
    unsigned char *ck=key->even_ck;
371
    unsigned char stream[8];
372
    unsigned char ib[8];
373
    unsigned char block[8];
374
    int residue;
375
 
376
        ((unsigned long *) decrypted)[0]=((unsigned long *) encrypted)[0];
377
 
378
        if(decrypted[3]&0x40) {
379
                kk=key->odd_kk;
380
                ck=key->odd_ck;
381
        }
382
 
383
    decrypted[3] &= 0x3f;              /* remove scrambling bits */
384
 
385
    if ((decrypted[3] & 0x20) == 0x20)
386
      offset += (encrypted[4] +1);               /* skip adaption field */
387
 
388
    N = (188 - offset) / 8;
389
    residue = (188 - offset) % 8;
390
 
391
    /*  1st 8 bytes of initialisation */
392
    stream_cypher(1, ck, &encrypted[offset], ib);
393
 
394
    for(j=1; j<(N+1); j++) {
395
                block_decypher(kk, ib, block);
396
 
397
        if (j != N) {
398
            stream_cypher(0, ck, NULL, stream);
399
 
400
            /*  xor sb x stream */
401
            for(i=0; i<8; i++)
402
                ib[i] = encrypted[offset+8*j+i] ^ stream[i];
403
        }
404
        else {
405
            /*  last block - sb[N+1] = IV(initialisation vetor)(=0) */
406
            for(i=0; i<8; i++)  ib[i] = 0;
407
        }
408
 
409
        /*  xor ib x block */
410
        for(i=0; i<8; i++)
411
                 decrypted[offset+8*(j-1)+i] = ib[i] ^ block[i];
412
    } /* for(j=1; j<(N+1); j++) */
413
 
414
    if (residue) {
415
       stream_cypher(0, ck, NULL, stream);
416
       for (i=0;i<residue;i++)
417
        decrypted[188-residue+i] = encrypted[188-residue+i] ^ stream[i];
418
    }
419
 
420
}
421
 

powered by: WebSVN 2.1.0

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