blob: 516826eb9efa5eaafdcbfd0adbad4eb5983ad35d [file] [log] [blame]
Christina Quastdb7b1ab2015-03-03 12:34:36 +01001/* ----------------------------------------------------------------------------
2 * ATMEL Microcontroller Software Support
3 * ----------------------------------------------------------------------------
4 * Copyright (c) 2009, Atmel Corporation
5 *
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions are met:
10 *
11 * - Redistributions of source code must retain the above copyright notice,
12 * this list of conditions and the disclaimer below.
13 *
14 * Atmel's name may not be used to endorse or promote products derived from
15 * this software without specific prior written permission.
16 *
17 * DISCLAIMER: THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
19 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE
20 * DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
23 * OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
24 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
25 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
26 * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 * ----------------------------------------------------------------------------
28 */
29
Harald Welte5e6e8dc2017-11-28 20:58:06 +010030#include "board.h"
31#include "simtrace.h"
32
Harald Welte2fb59962016-02-28 12:34:26 +010033#ifdef HAVE_CCID
34
Christina Quastdb7b1ab2015-03-03 12:34:36 +010035/*------------------------------------------------------------------------------
36 * Headers
37 *------------------------------------------------------------------------------*/
38
Christina Quastdb7b1ab2015-03-03 12:34:36 +010039#include <string.h>
40
41/*------------------------------------------------------------------------------
42 * Internal definitions
43 *------------------------------------------------------------------------------*/
44/** Maximum ucSize in bytes of the smartcard answer to a command.*/
45#define MAX_ANSWER_SIZE 10
46
47/** Maximum ATR ucSize in bytes.*/
48#define MAX_ATR_SIZE 55
49
Christina Quastdb7b1ab2015-03-03 12:34:36 +010050/*------------------------------------------------------------------------------
51 * Internal variables
52 *------------------------------------------------------------------------------*/
53
54/** ISO7816 pins */
Harald Welte7dd3dfd2016-03-03 12:32:04 +010055static const Pin pinsISO7816[] = { PINS_ISO7816 };
56
Christina Quast53a76082015-03-04 19:01:34 +010057/** Bus switch pins */
Harald Welte7dd3dfd2016-03-03 12:32:04 +010058static const Pin pinsBus[] = { PINS_BUS_DEFAULT };
59
Christina Quast53a76082015-03-04 19:01:34 +010060/* SIMcard power pin */
Harald Welte7dd3dfd2016-03-03 12:32:04 +010061static const Pin pinsPower[] = { PWR_PINS };
62
Christina Quastdb7b1ab2015-03-03 12:34:36 +010063/** ISO7816 RST pin */
Harald Welte7dd3dfd2016-03-03 12:32:04 +010064static const Pin pinIso7816RstMC = PIN_ISO7816_RSTMC;
Christina Quastdb7b1ab2015-03-03 12:34:36 +010065static uint8_t sim_inserted = 0;
66
Harald Welte7dd3dfd2016-03-03 12:32:04 +010067static struct Usart_info usart_info = {
68 .base = USART_SIM,
69 .id = ID_USART_SIM,
70 .state = USART_RCV
71};
Christina Quaste24b9ac2015-04-10 17:44:49 +020072
Christina Quastdb7b1ab2015-03-03 12:34:36 +010073/*------------------------------------------------------------------------------
74 * Optional smartcard detection
75 *------------------------------------------------------------------------------*/
76
Christina Quastdb7b1ab2015-03-03 12:34:36 +010077/** Smartcard detection pin.*/
78static const Pin pinSmartCard = SMARTCARD_CONNECT_PIN;
79
80/**
81 * PIO interrupt service routine. Checks if the smartcard has been connected
82 * or disconnected.
83 */
Harald Welte7dd3dfd2016-03-03 12:32:04 +010084static void ISR_PioSmartCard(const Pin * pPin)
Christina Quastdb7b1ab2015-03-03 12:34:36 +010085{
86/* FIXME: why is pinSmartCard.pio->PIO_ISR the wrong number?
Kévin Redon33d1eb72018-07-08 13:58:12 +020087 printf("+++++ Trying to check for pending interrupts (PIO ISR: 0x%X)\n\r", pinSmartCard.pio->PIO_ISR);
88 printf("+++++ Mask: 0x%X\n\r", pinSmartCard.mask);
Christina Quastdb7b1ab2015-03-03 12:34:36 +010089Output:
Kévin Redon33d1eb72018-07-08 13:58:12 +020090 +++++ Trying to check for pending interrupts (PIO ISR: 0x400)) = 1<<10
91 +++++ Mask: 0x100 = 1<<8
Christina Quastdb7b1ab2015-03-03 12:34:36 +010092*/
Harald Welte7dd3dfd2016-03-03 12:32:04 +010093 // PA10 is DTXD, which is the debug uart transmit pin
Christina Quastdb7b1ab2015-03-03 12:34:36 +010094
Harald Welte7dd3dfd2016-03-03 12:32:04 +010095 printf("Interrupt!!\n\r");
96 /* Check all pending interrupts */
97 // FIXME: this if condition is not always true...
Christina Quastdb7b1ab2015-03-03 12:34:36 +010098// if ( (pinSmartCard.pio->PIO_ISR & pinSmartCard.mask) != 0 )
Harald Welte7dd3dfd2016-03-03 12:32:04 +010099 {
100 /* Check current level on pin */
101 if (PIO_Get(&pinSmartCard) == 0) {
102 sim_inserted = 1;
103 printf("-I- Smartcard inserted\n\r");
104 CCID_Insertion();
105 } else {
106 sim_inserted = 0;
107 printf("-I- Smartcard removed\n\r");
108 CCID_Removal();
109 }
110 }
Christina Quastdb7b1ab2015-03-03 12:34:36 +0100111}
112
113/**
114 * Configures the smartcard detection pin to trigger an interrupt.
115 */
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100116static void ConfigureCardDetection(void)
Christina Quastdb7b1ab2015-03-03 12:34:36 +0100117{
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100118 printf("+++++ Configure PIOs\n\r");
119 PIO_Configure(&pinSmartCard, 1);
120 NVIC_EnableIRQ(PIOA_IRQn);
121 PIO_EnableIt(&pinSmartCard);
Christina Quastdb7b1ab2015-03-03 12:34:36 +0100122}
123
Christina Quastdb7b1ab2015-03-03 12:34:36 +0100124/*-----------------------------------------------------------------------------
125 * Initialization and run
126 *-----------------------------------------------------------------------------*/
Christina Quast53a76082015-03-04 19:01:34 +0100127extern CCIDDriverConfigurationDescriptors configurationDescriptorCCID;
Christina Quastdb7b1ab2015-03-03 12:34:36 +0100128
Harald Welteed75c622017-11-28 21:23:12 +0100129/* Called during USB enumeration after device is enumerated by host */
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100130void CCID_configure(void)
131{
132 CCIDDriver_Initialize();
Christina Quast95d66162015-04-09 22:38:47 +0200133// FIXME: Do we need to set priority?: NVIC_SetPriority( PIOA_IRQn, 10);
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100134 PIO_ConfigureIt(&pinSmartCard, ISR_PioSmartCard);
Christina Quast95d66162015-04-09 22:38:47 +0200135}
136
Harald Welteed75c622017-11-28 21:23:12 +0100137/* called when *different* configuration is set by host */
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100138void CCID_exit(void)
Christina Quastdb7b1ab2015-03-03 12:34:36 +0100139{
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100140 PIO_DisableIt(&pinSmartCard);
141 USART_SetTransmitterEnabled(usart_info.base, 0);
142 USART_SetReceiverEnabled(usart_info.base, 0);
Christina Quastdb7b1ab2015-03-03 12:34:36 +0100143}
144
Harald Welteed75c622017-11-28 21:23:12 +0100145/* called when *CCID* configuration is set by host */
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100146void CCID_init(void)
147{
148 uint8_t pAtr[MAX_ATR_SIZE];
149 uint8_t ucSize;
150
151 // FIXME: do we want to print ATR?
152 /* Initialize Atr buffer */
153 memset(pAtr, 0, sizeof(pAtr));
154
155 ConfigureCardDetection();
156
157 // Configure ISO7816 driver
158 PIO_Configure(pinsISO7816, PIO_LISTSIZE(pinsISO7816));
159 PIO_Configure(pinsBus, PIO_LISTSIZE(pinsBus));
160 PIO_Configure(pinsPower, PIO_LISTSIZE(pinsPower));
161
162 /* power up the card */
163// PIO_Set(&pinsPower[0]);
164
165 ISO7816_Init(&usart_info, CLK_MASTER);
166 USART_SetTransmitterEnabled(usart_info.base, 1);
167 USART_SetReceiverEnabled(usart_info.base, 1);
168
169 ISO7816_Set_Reset_Pin(&pinIso7816RstMC);
170 /* Read ATR */
171 ISO7816_warm_reset();
172
173 ISO7816_Datablock_ATR(pAtr, &ucSize);
174
175 /* Decode ATR and print it */
176 ISO7816_Decode_ATR(pAtr);
177
178 // FIXME. what if smcard is not inserted?
179 if (PIO_Get(&pinSmartCard) == 0) {
180 printf("SIM card inserted\n\r");
181 CCID_Insertion();
182 }
183}
184
Harald Welteed75c622017-11-28 21:23:12 +0100185/* main (idle/busy) loop of this USB configuration */
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100186void CCID_run(void)
Christina Quastdb7b1ab2015-03-03 12:34:36 +0100187{
Christina Quast53a76082015-03-04 19:01:34 +0100188
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100189 //if (USBD_Read(INT, pBuffer, dLength, fCallback, pArgument);
Christina Quast53a76082015-03-04 19:01:34 +0100190
Harald Welte7dd3dfd2016-03-03 12:32:04 +0100191 CCID_SmartCardRequest();
Christina Quastdb7b1ab2015-03-03 12:34:36 +0100192}
Harald Welte2fb59962016-02-28 12:34:26 +0100193#endif