Skip to content

Commit

Permalink
ensure usb_msg_hdr contains raw message length
Browse files Browse the repository at this point in the history
we want to ensure that the length of every (current or future) message
can be determined by looking at cardemu_usb_msg_hdr.msg_len, rather than
having a length that is relative to the respective specific command.
  • Loading branch information
laf0rge committed Mar 18, 2016
1 parent b8f9450 commit d295b92
Show file tree
Hide file tree
Showing 4 changed files with 21 additions and 12 deletions.
8 changes: 5 additions & 3 deletions firmware/src_simtrace/card_emu.c
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,8 @@ static void flush_rx_buffer(struct card_handle *ch)

/* store length of data payload fild in header */
rd = (struct cardemu_usb_msg_rx_data *) rctx->data;
rd->hdr.data_len = rctx->idx;
rd->data_len = rctx->idx;
rd->hdr.msg_len = sizeof(*rd) + rd->data_len;

llist_add_tail(&rctx->list, &ch->usb_tx_queue);
req_ctx_set_state(rctx, RCTX_S_USB_TX_PENDING);
Expand Down Expand Up @@ -229,7 +230,8 @@ static void flush_pts(struct card_handle *ch)

ptsi = (struct cardemu_usb_msg_pts_info *) rctx->data;
ptsi->hdr.msg_type = CEMU_USB_MSGT_DO_PTS;
ptsi->hdr.data_len = serialize_pts(ptsi->req, ch->pts.req);
ptsi->hdr.msg_len = sizeof(*ptsi);
ptsi->pts_len = serialize_pts(ptsi->req, ch->pts.req);
serialize_pts(ptsi->resp, ch->pts.resp);

llist_add_tail(&rctx->list, &ch->usb_tx_queue);
Expand Down Expand Up @@ -701,7 +703,7 @@ static int tx_byte_tpdu(struct card_handle *ch)
}

/* check if the buffer has now been fully transmitted */
if ((rctx->idx >= td->hdr.data_len) ||
if ((rctx->idx >= td->data_len) ||
(td->data + rctx->idx >= rctx->data + rctx->tot_len)) {
if (td->flags & CEMU_DATA_F_PB_AND_RX) {
/* we have just sent the procedure byte and now
Expand Down
14 changes: 10 additions & 4 deletions firmware/src_simtrace/cardemu_prot.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,8 @@ enum cardemu_usb_msg_type {
struct cardemu_usb_msg_hdr {
uint8_t msg_type; /* enum cardemu_usb_msg_type */
uint8_t seq_nr; /* sequence number */
uint16_t data_len; /* length of optional data field */
uint16_t msg_len; /* length of message including hdr */
uint8_t data[0];
} __attribute__ ((packed));

/* indicates a TPDU header is present in this message */
Expand All @@ -64,23 +65,26 @@ struct cardemu_usb_msg_cardinsert {
/* CEMU_USB_MSGT_DT_SET_ATR */
struct cardemu_usb_msg_set_atr {
struct cardemu_usb_msg_hdr hdr;
/* variable-length ATR data (hdr.data_len) */
uint8_t atr_len;
/* variable-length ATR data */
uint8_t atr[0];
} __attribute__ ((packed));

/* CEMU_USB_MSGT_DT_TX_DATA */
struct cardemu_usb_msg_tx_data {
struct cardemu_usb_msg_hdr hdr;
uint32_t flags;
/* variable-length TPDU data (hdr.data_len) */
uint16_t data_len;
/* variable-length TPDU data */
uint8_t data[0];
} __attribute__ ((packed));

/* CEMU_USB_MSGT_DO_RX_DATA */
struct cardemu_usb_msg_rx_data {
struct cardemu_usb_msg_hdr hdr;
uint32_t flags;
/* variable-length TPDU data (hdr.data_len) */
uint16_t data_len;
/* variable-length TPDU data */
uint8_t data[0];
} __attribute__ ((packed));

Expand All @@ -105,6 +109,7 @@ struct cardemu_usb_msg_status {
/* CEMU_USB_MSGT_DO_PTS */
struct cardemu_usb_msg_pts_info {
struct cardemu_usb_msg_hdr hdr;
uint8_t pts_len;
/* PTS request as sent from reader */
uint8_t req[6];
/* PTS response as sent by card */
Expand All @@ -117,6 +122,7 @@ struct cardemu_usb_msg_error {
uint8_t severity;
uint8_t subsystem;
uint16_t code;
uint8_t msg_len;
/* human-readable error message */
uint8_t msg[0];
} __attribute__ ((packed));
Expand Down
2 changes: 1 addition & 1 deletion firmware/src_simtrace/mode_cardemu.c
Original file line number Diff line number Diff line change
Expand Up @@ -305,7 +305,7 @@ static void dispatch_usb_command(struct req_ctx *rctx, struct cardem_inst *ci)
break;
case CEMU_USB_MSGT_DT_SET_ATR:
atr = (struct cardemu_usb_msg_set_atr *) hdr;
card_emu_set_atr(ci->ch, atr->atr, hdr->data_len);
card_emu_set_atr(ci->ch, atr->atr, atr->atr_len);
req_ctx_put(rctx);
break;
case CEMU_USB_MSGT_DT_CARDINSERT:
Expand Down
9 changes: 5 additions & 4 deletions firmware/test/card_emu_tests.c
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,7 @@ static void dump_rctx(struct req_ctx *rctx)
case CEMU_USB_MSGT_DO_RX_DATA:
rxd = (struct cardemu_usb_msg_rx_data *)mh;
printf(" flags=%x, data=", rxd->flags);
for (i = 0; i < mh->data_len; i++)
for (i = 0; i < rxd->data_len; i++)
printf(" %02x", rxd->data[i]);
printf("\n");
break;
Expand All @@ -162,13 +162,13 @@ static void get_and_verify_rctx(int state, const uint8_t *data, unsigned int len
case RCTX_S_USB_TX_PENDING:
td = (struct cardemu_usb_msg_tx_data *) rctx->data;
assert(td->hdr.msg_type == CEMU_USB_MSGT_DO_RX_DATA);
assert(td->hdr.data_len == len);
assert(td->data_len == len);
assert(!memcmp(td->data, data, len));
break;
#if 0
case RCTX_S_UART_RX_PENDING:
rd = (struct cardemu_usb_msg_rx_data *) rctx->data;
assert(rd->hdr.data_len == len);
assert(rd->data_len == len);
assert(!memcmp(rd->data, data, len));
break;
#endif
Expand Down Expand Up @@ -229,8 +229,9 @@ static void host_to_device_data(const uint8_t *data, uint16_t len, unsigned int
cardemu_hdr_set(&rd->hdr, CEMU_USB_MSGT_DT_TX_DATA);
rd->flags = flags;
/* copy data and set length */
rd->hdr.data_len = len;
rd->data_len = len;
memcpy(rd->data, data, len);
rd->hdr.msg_len = sizeof(*rd) + len;

/* hand the req_ctx to the UART transmit code */
req_ctx_set_state(rctx, RCTX_S_UART_TX_PENDING);
Expand Down

0 comments on commit d295b92

Please sign in to comment.