remove autogenerated file
[librfid] / src / rfid_access_mifare_classic.c
1 #include <stdlib.h>
2 #include <stdio.h>
3 #include <string.h>
4
5 #include <librfid/rfid.h>
6 #include <librfid/rfid_access_mifare_classic.h>
7
8 /* parse encoded data structure into c1/c2/c3 */
9 int mfcl_compile_access(u_int8_t *encoded,
10                         const struct mfcl_access_sect *ac)
11 {
12         int b;
13         u_int8_t c1, c2, c3;
14
15         c1 = c2 = c3 = 0;
16
17         for (b = 0; b < 4; b++) {
18                 if (ac->block[b] & 0x01)
19                         c1 |= (1 << b);
20                 if (ac->block[b] & 0x02)
21                         c2 |= (1 << b);
22                 if (ac->block[b] & 0x04)
23                         c3 |= (1 << b);
24         }
25
26         DEBUGP("compile: c1=%u c2=%u c3=%u\n", c1, c2, c3);
27
28         encoded[3] = 0x00;
29         encoded[2] = c2 | (c3 << 4);
30         encoded[1] = (~c3 & 0xf) | (c1 << 4);
31         encoded[0] = (~c1 & 0xf) | ((~c2 & 0xf) << 4);
32
33         return 0;
34 }
35
36 /* parse mifare classic access conditions from card */
37 int mfcl_parse_access(struct mfcl_access_sect *ac, u_int8_t *encoded)
38 {
39         int b;
40
41         u_int8_t c1, c2, c3;
42
43         DEBUGP("encoded: %s\n", rfid_hexdump(encoded, 4));
44
45         c1 = encoded[1] >> 4;
46         c2 = encoded[2] & 0xf;
47         c3 = encoded[2] >> 4;
48
49         DEBUGP("c1=0x%x, c2=0x%x, c3=0x%x\n", c1, c2, c3);
50         
51         memset(ac, 0, sizeof(*ac));
52         for (b = 0; b < 4; b++) {
53                 if (c1 & (1 << b))
54                         ac->block[b] = 0x1;
55                 if (c2 & (1 << b))
56                         ac->block[b] |= 0x2;
57                 if (c3 & (1 << b))
58                         ac->block[b] |= 0x4;
59         };
60
61         /* FIXME: verify the inverted access bits */
62
63         return 0;
64 }
65
66
67 /* functions below here are for our own internal decoded (orthogonal)
68  * format of access bits */
69
70 /* In the order of the table 3.7.3 in MFCL Product Specification Rev. 5.1 */
71 static const struct mfcl_access_exp_block mfcl_exp_data[] = {
72         [0] = {
73                 .read   = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
74                 .write  = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
75                 .inc    = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
76                 .dec    = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
77         },
78         [2] = {
79                 .read   = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
80                 .write  = MFCL_ACCESS_NEVER,
81                 .inc    = MFCL_ACCESS_NEVER,
82                 .dec    = MFCL_ACCESS_NEVER,
83         },
84         [1] = {
85                 .read   = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
86                 .write  = MFCL_ACCESS_KEY_B,
87                 .inc    = MFCL_ACCESS_NEVER,
88                 .dec    = MFCL_ACCESS_NEVER,
89         },
90         [3] = {
91                 .read   = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
92                 .write  = MFCL_ACCESS_KEY_B,
93                 .inc    = MFCL_ACCESS_KEY_B,
94                 .dec    = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
95         },
96         [4] = {
97                 .read   = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
98                 .write  = MFCL_ACCESS_NEVER,
99                 .inc    = MFCL_ACCESS_NEVER,
100                 .dec    = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
101         },
102         [6] = {
103                 .read   = MFCL_ACCESS_KEY_B,
104                 .write  = MFCL_ACCESS_KEY_B,
105                 .inc    = MFCL_ACCESS_NEVER,
106                 .dec    = MFCL_ACCESS_NEVER,
107         },
108         [5] = {
109                 .read   = MFCL_ACCESS_KEY_B,
110                 .write  = MFCL_ACCESS_NEVER,
111                 .inc    = MFCL_ACCESS_NEVER,
112                 .dec    = MFCL_ACCESS_NEVER,
113         },
114         [7] = {
115                 .read   = MFCL_ACCESS_NEVER,
116                 .write  = MFCL_ACCESS_NEVER,
117                 .inc    = MFCL_ACCESS_NEVER,
118                 .dec    = MFCL_ACCESS_NEVER,
119         },
120 };
121
122 static const struct mfcl_access_exp_acc mfcl_exp_trailer[] = {
123         [0] = {
124                 .key_a_rd       = MFCL_ACCESS_NEVER,
125                 .key_a_wr       = MFCL_ACCESS_KEY_A,
126                 .acc_rd         = MFCL_ACCESS_KEY_A,
127                 .acc_wr         = MFCL_ACCESS_NEVER,
128                 .key_b_rd       = MFCL_ACCESS_KEY_A,
129                 .key_b_wr       = MFCL_ACCESS_KEY_A,
130         },
131         [2] = {
132                 .key_a_rd       = MFCL_ACCESS_NEVER,
133                 .key_a_wr       = MFCL_ACCESS_NEVER,
134                 .acc_rd         = MFCL_ACCESS_KEY_A,
135                 .acc_wr         = MFCL_ACCESS_NEVER,
136                 .key_b_rd       = MFCL_ACCESS_KEY_A,
137                 .key_b_wr       = MFCL_ACCESS_NEVER,
138         },
139         [1] = {
140                 .key_a_rd       = MFCL_ACCESS_NEVER,
141                 .key_a_wr       = MFCL_ACCESS_KEY_B,
142                 .acc_rd         = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
143                 .acc_wr         = MFCL_ACCESS_NEVER,
144                 .key_b_rd       = MFCL_ACCESS_NEVER,
145                 .key_b_wr       = MFCL_ACCESS_KEY_B,
146         },
147         [3] = {
148                 .key_a_rd       = MFCL_ACCESS_NEVER,
149                 .key_a_wr       = MFCL_ACCESS_NEVER,
150                 .acc_rd         = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
151                 .acc_wr         = MFCL_ACCESS_NEVER,
152                 .key_b_rd       = MFCL_ACCESS_NEVER,
153                 .key_b_wr       = MFCL_ACCESS_NEVER,
154         },
155         [4] = {
156                 .key_a_rd       = MFCL_ACCESS_NEVER,
157                 .key_a_wr       = MFCL_ACCESS_KEY_A,
158                 .acc_rd         = MFCL_ACCESS_KEY_A,
159                 .acc_wr         = MFCL_ACCESS_KEY_A,
160                 .key_b_rd       = MFCL_ACCESS_KEY_A,
161                 .key_b_wr       = MFCL_ACCESS_KEY_A,
162         },
163         [6] = {
164                 .key_a_rd       = MFCL_ACCESS_NEVER,
165                 .key_a_wr       = MFCL_ACCESS_KEY_B,
166                 .acc_rd         = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
167                 .acc_wr         = MFCL_ACCESS_KEY_B,
168                 .key_b_rd       = MFCL_ACCESS_NEVER,
169                 .key_b_wr       = MFCL_ACCESS_KEY_B,
170         },
171         [5] = {
172                 .key_a_rd       = MFCL_ACCESS_NEVER,
173                 .key_a_wr       = MFCL_ACCESS_NEVER,
174                 .acc_rd         = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
175                 .acc_wr         = MFCL_ACCESS_KEY_B,
176                 .key_b_rd       = MFCL_ACCESS_NEVER,
177                 .key_b_wr       = MFCL_ACCESS_NEVER,
178         },
179         [7] = {
180                 .key_a_rd       = MFCL_ACCESS_NEVER,
181                 .key_a_wr       = MFCL_ACCESS_NEVER,
182                 .acc_rd         = MFCL_ACCESS_KEY_A | MFCL_ACCESS_KEY_B,
183                 .acc_wr         = MFCL_ACCESS_NEVER,
184                 .key_b_rd       = MFCL_ACCESS_NEVER,
185                 .key_b_wr       = MFCL_ACCESS_NEVER,
186         },
187 };
188
189 const char *mfcl_access_str[] = {
190         [MFCL_ACCESS_NEVER] = "NEVER",
191         [MFCL_ACCESS_KEY_A] = "A",
192         [MFCL_ACCESS_KEY_B] = "B",
193         [MFCL_ACCESS_KEY_A|MFCL_ACCESS_KEY_B] = "A|B",
194 };
195
196 void mfcl_access_to_exp(struct mfcl_access_exp_sect *exp,
197                         const struct mfcl_access_sect *sect)
198 {
199         int b;
200         for (b = 0; b < 3; b++)
201                 exp->block[b] = mfcl_exp_data[sect->block[b]];
202         exp->acc = mfcl_exp_trailer[sect->block[3]];
203 }
204
205 char *mfcl_access_exp_stringify(const struct mfcl_access_exp_block *exp)
206 {
207         static char buf[80];
208
209         sprintf(buf, "READ: %s, WRITE: %s, INC: %s, DEC: %s",
210                 mfcl_access_str[exp->read],
211                 mfcl_access_str[exp->write],
212                 mfcl_access_str[exp->inc],
213                 mfcl_access_str[exp->dec]);
214         return buf;
215 }
216
217 char *mfcl_access_exp_acc_stringify(const struct mfcl_access_exp_acc *acc)
218 {
219         static char buf[80];
220
221         sprintf(buf, "KEY_A_RD: %s, KEY_A_WR: %s, ACC_RD: %s, ACC_WR: %s, "
222                 "KEY_B_RD: %s, KEY_B_WR: %s",
223                 mfcl_access_str[acc->key_a_rd],
224                 mfcl_access_str[acc->key_a_wr],
225                 mfcl_access_str[acc->acc_rd],
226                 mfcl_access_str[acc->acc_wr],
227                 mfcl_access_str[acc->key_b_rd],
228                 mfcl_access_str[acc->key_b_wr]);
229         return buf;
230 }