laforge has uploaded this change for review. ( https://gerrit.osmocom.org/c/osmo-ccid-firmware/+/15695
Change subject: make ccid_main_functionfs use iso7816_fsm and cuart_driver_tty ...................................................................... make ccid_main_functionfs use iso7816_fsm and cuart_driver_tty This works up to the point that we're getting the ATR displayed in pcsc_scan Change-Id: Ic656fff4a9c6b9aaf4b91aa16f66972ad28f8423 --- M ccid/Makefile M ccid/ccid_main_functionfs.c A ccid/ccid_slot_fsm.c 3 files changed, 215 insertions(+), 2 deletions(-) git pull ssh://gerrit.osmocom.org:29418/osmo-ccid-firmware refs/changes/95/15695/1 diff --git a/ccid/Makefile b/ccid/Makefile index 3ab1045..4993550 100644 --- a/ccid/Makefile +++ b/ccid/Makefile @@ -3,7 +3,9 @@ all: ccid_functionfs hub_functionfs cuart_test cuart_fsm_test -ccid_functionfs: ccid_main_functionfs.o logging.o ccid_proto.o ccid_device.o ccid_slot_sim.o +ccid_functionfs: ccid_main_functionfs.o logging.o ccid_proto.o ccid_device.o \ + cuart.o utils_ringbuffer.o cuart_driver_tty.o \ + ccid_slot_fsm.o iso7816_fsm.o $(CC) $(CFLAGS) -o $@ $^ $(LIBS) -laio hub_functionfs: hub_main_functionfs.o diff --git a/ccid/ccid_main_functionfs.c b/ccid/ccid_main_functionfs.c index 5c0bc3b..d45a936 100644 --- a/ccid/ccid_main_functionfs.c +++ b/ccid/ccid_main_functionfs.c @@ -152,6 +152,7 @@ #include "ccid_device.h" #include "ccid_slot_sim.h" +extern struct ccid_slot_ops iso_fsm_slot_ops; #ifndef FUNCTIONFS_SUPPORTS_POLL #include <libaio.h> @@ -528,7 +529,7 @@ signal(SIGUSR1, &signal_handler); - ccid_instance_init(&g_ci, &c_ops, &slotsim_slot_ops, &descriptors.fs_descs.ccid, + ccid_instance_init(&g_ci, &c_ops, &iso_fsm_slot_ops, &descriptors.fs_descs.ccid, data_rates, clock_freqs, "", &ufh); ufh.ccid_handle = &g_ci; diff --git a/ccid/ccid_slot_fsm.c b/ccid/ccid_slot_fsm.c new file mode 100644 index 0000000..06c14f1 --- /dev/null +++ b/ccid/ccid_slot_fsm.c @@ -0,0 +1,210 @@ +/* Code providing a ccid_slot_ops implementation based on iso7716_fsm, + * (which in turn sits on top of card_uart) */ + +#include <unistd.h> +#include <errno.h> + +#include <osmocom/core/msgb.h> +#include <osmocom/core/timer.h> +#include <osmocom/core/logging.h> +#include <osmocom/core/fsm.h> + +#include "ccid_device.h" +#include "cuart.h" +#include "iso7816_fsm.h" + +struct iso_fsm_slot { + /* CCID slot above us */ + struct ccid_slot *cs; + /* main ISO7816-3 FSM instance beneath us */ + struct osmo_fsm_inst *fi; + /* UART beneath the ISO7816-3 FSM */ + struct card_uart *cuart; + /* bSeq of the operation currently in progress */ + uint8_t seq; +}; + +struct iso_fsm_slot_instance { + struct iso_fsm_slot slot[NR_SLOTS]; +}; + +static struct iso_fsm_slot_instance g_si; + +struct iso_fsm_slot *ccid_slot2iso_fsm_slot(struct ccid_slot *cs) +{ + OSMO_ASSERT(cs->slot_nr < ARRAY_SIZE(g_si.slot)); + return &g_si.slot[cs->slot_nr]; +} + +static const uint8_t sysmousim_sjs1_atr[] = { + 0x3B, 0x9F, 0x96, 0x80, 0x1F, 0xC7, 0x80, 0x31, + 0xA0, 0x73, 0xBE, 0x21, 0x13, 0x67, 0x43, 0x20, + 0x07, 0x18, 0x00, 0x00, 0x01, 0xA5 }; + +static const struct ccid_pars_decoded iso_fsm_def_pars = { + .fi = 372, + .di = 1, + .clock_stop = CCID_CLOCK_STOP_NOTALLOWED, + .inverse_convention = false, + .t0 = { + .guard_time_etu = 0, + .waiting_integer = 0, + }, + /* FIXME: T=1 */ +}; + +static void iso_fsm_slot_pre_proc_cb(struct ccid_slot *cs, struct msgb *msg) +{ + /* do nothing; real hardware would update the slot related state here */ +} + +static void iso_fsm_slot_icc_power_on_async(struct ccid_slot *cs, struct msgb *msg, + const struct ccid_pc_to_rdr_icc_power_on *ipo) +{ + struct iso_fsm_slot *ss = ccid_slot2iso_fsm_slot(cs); + + ss->seq = ipo->hdr.bSeq; + LOGPCS(cs, LOGL_DEBUG, "scheduling power-up\n"); + + /* FIXME: do this via a FSM? */ + card_uart_ctrl(ss->cuart, CUART_CTL_RST, true); + card_uart_ctrl(ss->cuart, CUART_CTL_POWER, true); + osmo_fsm_inst_dispatch(ss->fi, ISO7816_E_POWER_UP_IND, NULL); + cs->icc_powered = true; + card_uart_ctrl(ss->cuart, CUART_CTL_CLOCK, true); + usleep(10000); + card_uart_ctrl(ss->cuart, CUART_CTL_RST, false); + osmo_fsm_inst_dispatch(ss->fi, ISO7816_E_RESET_REL_IND, NULL); + + msgb_free(msg); + /* continues in iso_fsm_clot_user_cb once ATR is received */ +} +static void iso_fsm_clot_user_cb(struct osmo_fsm_inst *fi, int event, int cause, void *data) +{ + struct iso_fsm_slot *ss = iso7816_fsm_get_user_priv(fi); + struct ccid_slot *cs = ss->cs; + struct msgb *tpdu, *resp; + + LOGPCS(cs, LOGL_DEBUG, "%s(event=%d, cause=%d, data=%p)\n", __func__, event, cause, data); + + switch (event) { + case ISO7816_E_ATR_DONE_IND: + tpdu = data; + /* FIXME: copy response data over */ + resp = ccid_gen_data_block(cs, ss->seq, CCID_CMD_STATUS_OK, 0, + msgb_data(tpdu), msgb_length(tpdu)); + ccid_slot_send_unbusy(cs, resp); + msgb_free(tpdu); + break; + case ISO7816_E_TPDU_DONE_IND: + tpdu = data; + /* FIXME: copy response data over */ + resp = ccid_gen_data_block(cs, ss->seq, CCID_CMD_STATUS_OK, 0, msgb_l2(tpdu), msgb_l2len(tpdu)); + ccid_slot_send_unbusy(cs, resp); + msgb_free(tpdu); + break; + } +} + +static void iso_fsm_slot_xfr_block_async(struct ccid_slot *cs, struct msgb *msg, + const struct ccid_pc_to_rdr_xfr_block *xfb) +{ + struct iso_fsm_slot *ss = ccid_slot2iso_fsm_slot(cs); + + LOGPCS(cs, LOGL_DEBUG, "scheduling TPDU transfer\n"); + ss->seq = xfb->hdr.bSeq; + osmo_fsm_inst_dispatch(ss->fi, ISO7816_E_XCEIVE_TPDU_CMD, msg); + /* continues in iso_fsm_clot_user_cb once response/error/timeout is received */ +} + + +static void iso_fsm_slot_set_power(struct ccid_slot *cs, bool enable) +{ + struct iso_fsm_slot *ss = ccid_slot2iso_fsm_slot(cs); + + if (enable) { + card_uart_ctrl(ss->cuart, CUART_CTL_POWER, true); + } else { + card_uart_ctrl(ss->cuart, CUART_CTL_POWER, false); + } +} + +static void iso_fsm_slot_set_clock(struct ccid_slot *cs, enum ccid_clock_command cmd) +{ + struct iso_fsm_slot *ss = ccid_slot2iso_fsm_slot(cs); + + switch (cmd) { + case CCID_CLOCK_CMD_STOP: + card_uart_ctrl(ss->cuart, CUART_CTL_CLOCK, false); + break; + case CCID_CLOCK_CMD_RESTART: + card_uart_ctrl(ss->cuart, CUART_CTL_CLOCK, true); + break; + default: + OSMO_ASSERT(0); + } +} + +static int iso_fsm_slot_set_params(struct ccid_slot *cs, enum ccid_protocol_num proto, + const struct ccid_pars_decoded *pars_dec) +{ + /* we always acknowledge all parameters */ + return 0; +} + +static int iso_fsm_slot_set_rate_and_clock(struct ccid_slot *cs, uint32_t freq_hz, uint32_t rate_bps) +{ + /* we always acknowledge all rates/clocks */ + return 0; +} + + +static int iso_fsm_slot_init(struct ccid_slot *cs) +{ + void *ctx = NULL; /* FIXME */ + struct iso_fsm_slot *ss = ccid_slot2iso_fsm_slot(cs); + struct card_uart *cuart = talloc_zero(ctx, struct card_uart); + char id_buf[16]; + char *devname = "/dev/null"; + int rc; + + LOGPCS(cs, LOGL_DEBUG, "%s\n", __func__); + + if (cs->slot_nr == 0) { + cs->icc_present = true; + devname = "/dev/ttyUSB5"; + } + + if (!cuart) + return -ENOMEM; + + snprintf(id_buf, sizeof(id_buf), "SIM%d", cs->slot_nr); + rc = card_uart_open(cuart, "tty", devname); + if (rc < 0) { + talloc_free(cuart); + return rc; + } + ss->fi = iso7816_fsm_alloc(ctx, LOGL_DEBUG, id_buf, cuart, iso_fsm_clot_user_cb, ss); + if (!ss->fi) { + talloc_free(cuart); + return -1; + } + + cs->default_pars = &iso_fsm_def_pars; + ss->cuart = cuart; + ss->cs = cs; + + + return 0; +} + +const struct ccid_slot_ops iso_fsm_slot_ops = { + .init = iso_fsm_slot_init, + .pre_proc_cb = iso_fsm_slot_pre_proc_cb, + .icc_power_on_async = iso_fsm_slot_icc_power_on_async, + .xfr_block_async = iso_fsm_slot_xfr_block_async, + .set_power = iso_fsm_slot_set_power, + .set_clock = iso_fsm_slot_set_clock, + .set_params = iso_fsm_slot_set_params, + .set_rate_and_clock = iso_fsm_slot_set_rate_and_clock, +}; -- To view, visit https://gerrit.osmocom.org/c/osmo-ccid-firmware/+/15695 To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings Gerrit-Project: osmo-ccid-firmware Gerrit-Branch: master Gerrit-Change-Id: Ic656fff4a9c6b9aaf4b91aa16f66972ad28f8423 Gerrit-Change-Number: 15695 Gerrit-PatchSet: 1 Gerrit-Owner: laforge <lafo...@osmocom.org> Gerrit-MessageType: newchange