3 #include "cscrypt/bn.h"
4 #include "reader-common.h"
6 static int32_t RSA_CNX(struct s_reader
*reader
, unsigned char *msg
, unsigned char *mod
, unsigned char *exp
, uint32_t cta_lr
, uint32_t modbytes
, uint32_t expbytes
)
9 uint32_t n
= 0, pre_size
= 0, size
= 0;
11 BIGNUM
*bn_mod
, *bn_exp
, *bn_data
, *bn_res
;
12 unsigned char data
[64];
15 pre_size
= 2 + 4 + msg
[5];
16 /*size of data to decryption*/
17 if(msg
[1] > (pre_size
- 2))
18 { size
= msg
[1] - pre_size
+ 2; }
20 if(cta_lr
> (pre_size
+ size
) &&
21 size
>= modbytes
&& size
< 128)
27 rdr_log_dbg(reader
, D_READER
, "RSA Error in RSA_CNX");
31 bn_mod
= BN_CTX_get(ctx
);
32 bn_exp
= BN_CTX_get(ctx
);
33 bn_data
= BN_CTX_get(ctx
);
34 bn_res
= BN_CTX_get(ctx
);
37 BN_bin2bn(mod
, modbytes
, bn_mod
); // rsa modulus
38 BN_bin2bn(exp
, expbytes
, bn_exp
); // exponent
39 BN_bin2bn(msg
+ pre_size
, modbytes
, bn_data
);
40 BN_mod_exp(bn_res
, bn_data
, bn_exp
, bn_mod
, ctx
);
42 n
= BN_bn2bin(bn_res
, data
);
46 /*Check if second round is needed*/
49 /*check if length of data from first RSA round will be enough to padding rest of data*/
50 if((n
+ size
) >= modbytes
)
53 /*move the remaining data at the beginning of the buffer*/
54 memcpy(msg
, msg
+ pre_size
, size
);
55 /*padding buffer with data from first round*/
56 memcpy(msg
+ size
, data
+ (n
- (modbytes
- size
)), modbytes
- size
);
58 BN_bin2bn(msg
, modbytes
, bn_data
);
59 BN_mod_exp(bn_res
, bn_data
, bn_exp
, bn_mod
, ctx
);
60 n
= BN_bn2bin(bn_res
, data
);
62 { ret
= -1; } /*RSA key is probably wrong*/
65 { ret
= -3; } /*wrong size of data for second round*/
69 { memcpy(msg
, data
, n
); }
74 { ret
= -2; } /*wrong size of data*/
79 static time_t chid_date(const uchar
*ptr
, char *buf
, int32_t l
)
83 memset(&timeinfo
, 0, sizeof(struct tm
));
86 timeinfo
.tm_year
= 90 + (ptr
[1] >> 4) + (((ptr
[0] >> 5) & 7) * 10);
87 timeinfo
.tm_mon
= (ptr
[1] & 0xf) - 1;
88 timeinfo
.tm_mday
= ptr
[0] & 0x1f;
89 timeinfo
.tm_isdst
= -1;
90 rc
= mktime(&timeinfo
);
91 strftime(buf
, l
, "%Y/%m/%d", &timeinfo
);
96 static int32_t read_record(struct s_reader
*reader
, const uchar
*cmd
, const uchar
*data
, uchar
*cta_res
)
99 uchar insCA
[] = {0xDD, 0xCA, 0x00, 0x00, 0x00};
101 write_cmd(cmd
, data
); // select record
102 if(cta_res
[0] != 0x98)
105 insCA
[4] = cta_res
[1]; // get len
106 write_cmd(insCA
, NULL
); // read record
107 if((cta_res
[cta_lr
- 2] != 0x90) || (cta_res
[cta_lr
- 1]))
112 static uint8_t PairingECMRotation(struct s_reader
*reader
, const ECM_REQUEST
*er
, int32_t n
)
114 unsigned char cta_res
[CTA_RES_LEN
] = {0x00};
115 uchar ins26
[] = {0xDD, 0x26, 0x00, 0x00, 0x03, 0x10, 0x01, 0x00};
116 uint8_t cnxcurrecm
= 0;
118 if(0x0 != reader
->rsa_mod
[0] && n
> 3 &&
119 0x54 == er
->ecm
[n
- 3] &&
120 0x02 == er
->ecm
[n
- 2] &&
121 0x00 == er
->ecm
[n
- 1])
126 if((0 == reader
->cnxlastecm
) != (0 == cnxcurrecm
))
128 if(0 == cnxcurrecm
) // not paired
133 if(read_record(reader
, ins26
, ins26
+ 5, cta_res
) <= 0)
134 { rdr_log(reader
, "PairingECMRotation - ERROR"); }
136 reader
->cnxlastecm
= cnxcurrecm
;
140 static int32_t conax_card_init(struct s_reader
*reader
, ATR
*newatr
)
142 unsigned char cta_res
[CTA_RES_LEN
];
144 static const uchar ins26
[] = {0xDD, 0x26, 0x00, 0x00, 0x03, 0x10, 0x01, 0x40};
145 uchar ins82
[] = {0xDD, 0x82, 0x00, 0x00, 0x11, 0x11, 0x0f, 0x01, 0xb0, 0x0f, 0xff, \
146 0xff, 0xfb, 0x00, 0x00, 0x09, 0x04, 0x0b, 0x00, 0xe0, 0x30, 0x2b
152 if((hist_size
< 4) || (memcmp(hist
, "0B00", 4)))
155 reader
->caid
= 0xB00;
157 if((n
= read_record(reader
, ins26
, ins26
+ 5, cta_res
)) <= 0) { return ERROR
; } // read caid, card-version
159 for(i
= 0; i
< n
; i
+= cta_res
[i
+ 1] + 2)
163 cardver
= cta_res
[i
+ 2];
166 reader
->caid
= (cta_res
[i
+ 2] << 8) | cta_res
[i
+ 3];
169 // Ins82 command needs to use the correct CAID reported in nano 0x28
170 ins82
[17] = (reader
->caid
>> 8) & 0xFF;
171 ins82
[18] = (reader
->caid
) & 0xFF;
173 if((n
= read_record(reader
, ins82
, ins82
+ 5, cta_res
)) <= 0) { return ERROR
; } // read serial
177 for(j
= 0, i
= 2; i
< n
; i
+= cta_res
[i
+ 1] + 2)
181 if(cta_res
[i
+ 5] != 0x00)
183 memcpy(reader
->hexserial
, &cta_res
[i
+ 3], 6);
187 memcpy(reader
->sa
[j
], &cta_res
[i
+ 5], 4);
194 memset(reader
->prid
, 0x00, sizeof(reader
->prid
));
196 rdr_log_sensitive(reader
, "type: Conax, caid: %04X, serial: {%llu}, hex serial: {%02x%02x%02x%02x}, card: v%d",
197 reader
->caid
, (unsigned long long) b2ll(6, reader
->hexserial
), reader
->hexserial
[2],
198 reader
->hexserial
[3], reader
->hexserial
[4], reader
->hexserial
[5], cardver
);
200 rdr_log(reader
, "Providers: %d", reader
->nprov
);
202 for(j
= 0; j
< reader
->nprov
; j
++)
204 rdr_log(reader
, "Provider: %d Provider-Id: %06X", j
+ 1, b2i(4, reader
->prid
[j
]));
205 rdr_log_sensitive(reader
, "Provider: %d SharedAddress: {%08X}", j
+ 1, b2i(4, reader
->sa
[j
]));
211 static int32_t conax_send_pin(struct s_reader
*reader
)
214 unsigned char insPIN
[] = { 0xDD, 0xC8, 0x00, 0x00, 0x07, 0x1D, 0x05, 0x01, 0x00, 0x00, 0x00, 0x00 }; //Last four are the Pin-Code
215 memcpy(insPIN
+ 8, reader
->pincode
, 4);
217 write_cmd(insPIN
, insPIN
+ 5);
218 rdr_log_dbg(reader
, D_READER
, "Sent pincode to card.");
223 static int32_t conax_do_ecm(struct s_reader
*reader
, const ECM_REQUEST
*er
, struct s_ecm_answer
*ea
)
226 int32_t i
, j
, n
, num_dw
= 0, rc
= 0;
227 unsigned char insA2
[] = { 0xDD, 0xA2, 0x00, 0x00, 0x00 };
228 unsigned char insCA
[] = { 0xDD, 0xCA, 0x00, 0x00, 0x00 };
230 unsigned char exp
[] = {0x01, 0x00, 0x01};
231 unsigned char buf
[256];
233 if((n
= check_sct_len(er
->ecm
, 3)) < 0)
238 if(0x0 != PairingECMRotation(reader
, er
, n
))
239 { buf
[2] = 2; } // card will answer with encrypted dw
243 memcpy(buf
+ 3, er
->ecm
, n
);
246 write_cmd(insA2
, buf
); // write Header + ECM
248 while((cta_res
[cta_lr
- 2] == 0x98) && // Antwort
249 ((insCA
[4] = cta_res
[cta_lr
- 1]) > 0) && (insCA
[4] != 0xFF))
251 write_cmd(insCA
, NULL
); //Codeword auslesen
253 if((cta_res
[cta_lr
- 2] == 0x98) ||
254 ((cta_res
[cta_lr
- 2] == 0x90)))
256 /*checks if answer is encrypted with RSA algo and decrypts it if needed*/
257 if(0x81 == cta_res
[0] && 2 == cta_res
[2] >> 5) /*81 XX 5X*/
259 if(0x00 == cta_res
[cta_lr
- 1])
260 { rc
= RSA_CNX(reader
, cta_res
, reader
->rsa_mod
, exp
, cta_lr
, 64u, 3u); }
262 { rc
= -4; } /*card has no right to decode this channel*/
266 for(i
= 0; i
< cta_lr
- 2 && num_dw
< 2; i
+= cta_res
[i
+ 1] + 2)
271 if((cta_res
[i
+ 1] >= 0xD) && !((n
= cta_res
[i
+ 4]) & 0xFE))
274 memcpy(ea
->cw
+ (n
<< 3), cta_res
+ i
+ 7, 8);
279 if((cta_res
[i
+ 1] == 0x02 && cta_res
[i
+ 2] == 0x00 && cta_res
[i
+ 3] == 0x00) || \
280 (cta_res
[i
+ 1] == 0x02 && cta_res
[i
+ 2] == 0x40 && cta_res
[i
+ 3] == 0x00))
282 else if(strcmp(reader
->pincode
, "none"))
284 conax_send_pin(reader
);
285 write_cmd(insA2
, buf
); // write Header + ECM
287 while((cta_res
[cta_lr
- 2] == 0x98) && // Antwort
288 ((insCA
[4] = cta_res
[cta_lr
- 1]) > 0) && (insCA
[4] != 0xFF))
290 write_cmd(insCA
, NULL
); //Codeword auslesen
292 if((cta_res
[cta_lr
- 2] == 0x98) ||
293 ((cta_res
[cta_lr
- 2] == 0x90) && (!cta_res
[cta_lr
- 1])))
295 for(j
= 0; j
< cta_lr
- 2; j
+= cta_res
[j
+ 1] + 2)
296 if((cta_res
[j
] == 0x25) && // access: is cw
297 (cta_res
[j
+ 1] >= 0xD) && // 0xD: 5 header + 8 cw
298 !((n
= cta_res
[j
+ 4]) & 0xFE)) // cw idx must be 0 or 1
301 memcpy(ea
->cw
+ (n
<< 3), cta_res
+ j
+ 7, 8);
316 rdr_log(reader
, "conax decode ECM problem - RSA key is probably faulty");
319 rdr_log(reader
, "conax RSA pairing - wrong size of data");
322 rdr_log(reader
, "conax RSA pairing- wrong size of data for second round");
324 rdr_log(reader
, "card has no right to decode this channel");
328 /* answer 9011 - conax smart card need reset */
329 if(2 <= cta_lr
&& 0x90 == cta_res
[cta_lr
- 2] &&
330 0x11 == cta_res
[cta_lr
- 1])
332 rdr_log(reader
, "conax card hangs - reset is required");
333 reader
->card_status
= UNKNOWN
;
342 static int32_t conax_get_emm_type(EMM_PACKET
*ep
, struct s_reader
*rdr
)
347 rdr_log_dbg(rdr
, D_EMM
, "Entered conax_get_emm_type ep->emm[2]=%02x", ep
->emm
[2]);
349 for(i
= 0; i
< rdr
->nprov
; i
++)
351 ok
= (!memcmp(&ep
->emm
[6], rdr
->sa
[i
], 4));
358 memset(ep
->hexserial
, 0, 8);
359 memcpy(ep
->hexserial
, &ep
->emm
[6], 4);
360 rdr_log_dbg_sensitive(rdr
, D_EMM
, "SHARED, ep->hexserial = {%s}", cs_hexdump(1, ep
->hexserial
, 8, tmp_dbg
, sizeof(tmp_dbg
)));
365 if(!memcmp(&ep
->emm
[6], rdr
->hexserial
+ 2, 4))
368 memset(ep
->hexserial
, 0, 8);
369 memcpy(ep
->hexserial
+ 2, &ep
->emm
[6], 4);
370 rdr_log_dbg_sensitive(rdr
, D_EMM
, "UNIQUE, ep->hexserial = {%s}", cs_hexdump(1, ep
->hexserial
, 8, tmp_dbg
, sizeof(tmp_dbg
)));
376 rdr_log_dbg(rdr
, D_EMM
, "GLOBAL");
377 memset(ep
->hexserial
, 0, 8);
383 static int32_t conax_get_emm_filter(struct s_reader
*rdr
, struct s_csystem_emm_filter
**emm_filters
, unsigned int *filter_count
)
385 if(*emm_filters
== NULL
)
387 const unsigned int max_filter_count
= 2 + rdr
->nprov
;
388 if(!cs_malloc(emm_filters
, max_filter_count
* sizeof(struct s_csystem_emm_filter
)))
391 struct s_csystem_emm_filter
*filters
= *emm_filters
;
396 filters
[idx
].type
= EMM_GLOBAL
;
397 filters
[idx
].enabled
= 0; // FIXME: dont see any conax global EMM yet
398 filters
[idx
].filter
[0] = 0x82;
399 filters
[idx
].mask
[0] = 0xFF;
400 filters
[idx
].filter
[8] = 0x70;
401 filters
[idx
].mask
[8] = 0xFF;
404 for(prov
= 0; prov
< rdr
->nprov
; prov
++)
406 filters
[idx
].type
= EMM_SHARED
;
407 filters
[idx
].enabled
= 1;
408 filters
[idx
].filter
[0] = 0x82;
409 filters
[idx
].mask
[0] = 0xFF;
410 memcpy(&filters
[idx
].filter
[4], rdr
->sa
[prov
], 4);
411 memset(&filters
[idx
].mask
[4], 0xFF, 4);
415 filters
[idx
].type
= EMM_UNIQUE
;
416 filters
[idx
].enabled
= 1;
417 filters
[idx
].filter
[0] = 0x82;
418 filters
[idx
].mask
[0] = 0xFF;
419 memcpy(&filters
[idx
].filter
[4], rdr
->hexserial
+ 2, 4);
420 memset(&filters
[idx
].mask
[4], 0xFF, 4);
429 static int32_t conax_do_emm(struct s_reader
*reader
, EMM_PACKET
*ep
)
432 unsigned char insCA
[] = { 0xDD, 0xCA, 0x00, 0x00, 0x00 };
433 unsigned char insEMM
[] = { 0xDD, 0x84, 0x00, 0x00, 0x00 };
434 unsigned char buf
[255];
437 const int32_t l
= ep
->emm
[2];
442 memcpy(buf
+ 2, ep
->emm
, buf
[1]);
443 write_cmd(insEMM
, buf
);
445 if(cta_res
[0] == 0x98)
447 insCA
[4] = cta_res
[1];
448 write_cmd(insCA
, NULL
);
451 rc
= ((cta_res
[0] == 0x90) && (cta_res
[1] == 0x00));
459 static int32_t conax_card_info(struct s_reader
*reader
)
462 int32_t type
, i
, j
, k
= 0, n
= 0, l
;
464 char provname
[32], pdate
[32], chid
[32];
465 static const uchar insC6
[] = {0xDD, 0xC6, 0x00, 0x00, 0x03, 0x1C, 0x01, 0x00};
466 static const uchar ins26
[] = {0xDD, 0x26, 0x00, 0x00, 0x03, 0x1C, 0x01, 0x01};
467 uchar insCA
[] = {0xDD, 0xCA, 0x00, 0x00, 0x00};
468 char *txt
[] = { "Package", "PPV-Event" };
469 static const uchar
*cmd
[] = { insC6
, ins26
};
470 time_t start_t
= 0, end_t
= 0;
471 uint32_t cxclass
= 0;
473 cs_clear_entitlement(reader
); // reset the entitlements
475 for(type
= 0; type
< 2; type
++)
478 write_cmd(cmd
[type
], cmd
[type
] + 5);
479 while(cta_res
[cta_lr
- 2] == 0x98)
481 insCA
[4] = cta_res
[cta_lr
- 1]; // get len
482 write_cmd(insCA
, NULL
); // read
483 if((cta_res
[cta_lr
- 2] == 0x90) || (cta_res
[cta_lr
- 2] == 0x98))
485 for(j
= 0; j
< cta_lr
- 2; j
+= cta_res
[j
+ 1] + 2)
487 provid
= (cta_res
[j
+ 2 + type
] << 8) | cta_res
[j
+ 3 + type
];
489 for(k
= 0, i
= j
+ 4 + type
; (i
< j
+ cta_res
[j
+ 1]); i
+= cta_res
[i
+ 1] + 2)
494 l
= (cta_res
[i
+ 1] < (sizeof(provname
) - 1)) ? cta_res
[i
+ 1] : sizeof(provname
) - 1;
495 memcpy(provname
, cta_res
+ i
+ 2, l
);
501 rdr_log(reader
, "%s: %d, id: %04X%s, date: %s - %s, name: %s", txt
[type
], ++n
, provid
, chid
, pdate
, pdate
+ 16, trim(provname
));
503 // add entitlements to list
504 cs_add_entitlement(reader
, reader
->caid
, b2ll(4, reader
->prid
[0]), provid
, cxclass
, start_t
, end_t
, type
+ 1, 1);
509 if(k
== 0) { start_t
= chid_date(cta_res
+ i
+ 2, pdate
, 15); }
510 else { end_t
= chid_date(cta_res
+ i
+ 2, pdate
+ 16, 15) /* add 23:59:59 here: */ + 0x1517F; }
513 case 0x20: // Provider classes
514 case 0x90: // (?) not sure what this is, saw it once in log
515 snprintf(chid
, sizeof(chid
), ", classes: %02X%02X%02X%02X", cta_res
[i
+ 2], cta_res
[i
+ 3], cta_res
[i
+ 4] , cta_res
[i
+ 5]);
516 cxclass
= b2ll(4, &cta_res
[i
+ 2]);
520 rdr_log(reader
, "%s: %d, id: %04X%s, date: %s - %s, name: %s", txt
[type
], ++n
, provid
, chid
, pdate
, pdate
+ 16, trim(provname
));
522 // add entitlements to list
523 cs_add_entitlement(reader
, reader
->caid
, b2ll(4, reader
->prid
[0]), provid
, cxclass
, start_t
, end_t
, type
+ 1, 1);
528 rdr_log(reader
, "ready for requests");
532 const struct s_cardsystem reader_conax
=
535 .caids
= (uint16_t[]){ 0x0B, 0 },
536 .do_emm
= conax_do_emm
,
537 .do_ecm
= conax_do_ecm
,
538 .card_info
= conax_card_info
,
539 .card_init
= conax_card_init
,
540 .get_emm_type
= conax_get_emm_type
,
541 .get_emm_filter
= conax_get_emm_filter
,