xref: /netbsd/sys/arch/shark/shark/scr.c (revision d7e68fde)
1 /*	$NetBSD: scr.c,v 1.36 2023/06/29 21:01:21 andvar Exp $	*/
2 
3 /*
4  * Copyright 1997
5  * Digital Equipment Corporation. All rights reserved.
6  *
7  * This software is furnished under license and may be used and
8  * copied only in accordance with the following terms and conditions.
9  * Subject to these conditions, you may download, copy, install,
10  * use, modify and distribute this software in source and/or binary
11  * form. No title or ownership is transferred hereby.
12  *
13  * 1) Any source code used, modified or distributed must reproduce
14  *    and retain this copyright notice and list of conditions as
15  *    they appear in the source file.
16  *
17  * 2) No right is granted to use any trade name, trademark, or logo of
18  *    Digital Equipment Corporation. Neither the "Digital Equipment
19  *    Corporation" name nor any trademark or logo of Digital Equipment
20  *    Corporation may be used to endorse or promote products derived
21  *    from this software without the prior written permission of
22  *    Digital Equipment Corporation.
23  *
24  * 3) This software is provided "AS-IS" and any express or implied
25  *    warranties, including but not limited to, any implied warranties
26  *    of merchantability, fitness for a particular purpose, or
27  *    non-infringement are disclaimed. In no event shall DIGITAL be
28  *    liable for any damages whatsoever, and in particular, DIGITAL
29  *    shall not be liable for special, indirect, consequential, or
30  *    incidental damages or damages for lost profits, loss of
31  *    revenue or loss of use, whether such damages arise in contract,
32  *    negligence, tort, under statute, in equity, at law or otherwise,
33  *    even if advised of the possibility of such damage.
34  */
35 
36 /*
37 **++
38 **
39 **  FACILITY:
40 **
41 **    Driver for smart card
42 **
43 **  ABSTRACT:
44 **
45 **    The driver provides access to a Smart Card for the DNARD.
46 **
47 **    There is no Smart Card silicon.  Several i/o pins
48 **    connect to the pads on the Smart Card, and the driver is
49 **    is responsible for driving the signals in accordance with
50 **    ISO 7816-3 (the Smart Card spec)
51 **
52 **    This driver puts a high load on the system due to the need
53 **    to interrupt at a high rate (up to 50 kHz) during bit detection.
54 **
55 **
56 **    The driver is dived into the standard top half ioctl, and bottom
57 **    half interrupt.  The interrupt is FIQ, which requires its own stack.
58 **    disable_interrupts and restore_interrupts must be used to protect from
59 **    a FIQ.  Since splxxx functions do not use this, the bottom half cannot
60 **    use any standard functions (ie like wakeup, timeout, etc.
61 **    Thus the communication from the bottom half
62 **    to the top half uses a "done" bit called masterDone.  This bit
63 **    is set by the master state machine when all bottom half work is
64 **    complete.  The top half checks/sleeps on this masterDone bit.
65 **
66 **    The FIQ is driven by Timer 2 (T2)in the sequoia.  All times are
67 **    referenced to T2 counts.
68 **
69 **    The bottom half is done as a several linked state machines.
70 **    The top level machine is the maserSM (ie master State Machine).  This
71 **    machine calls mid level protocol machines, ie ATRSM (Answer To Reset
72 **    State Machine), t0SendSM (T=0 Send State Machine), and t0RecvSM (T=0 Recv
73 **    State Machine).  These mid level protocol machines in turn call low level
74 **    bit-bashing machines, ie coldResetSM, t0SendByteSM, T0RecvByteSM.
75 **
76 **    Smart Cards are driven in a command/response mode.  Ie you issue a command
77 **    to the Smart Card and it responds.  This command/response mode is reflected
78 **    in the structure of the driver.  Ie the ioctl gets a command, it
79 **    gives it to the bottom half to execute and goes to sleep.  The bottom half
80 **    executes the command and gets the response to from the card and then
81 **    notifies the top half that it has completed.  Commands usually complete
82 **    in under a second.
83 **
84 **
85 **
86 **  AUTHORS:
87 **
88 **    E. J. Grohn
89 **    Digital Equipment Corporation.
90 **
91 **  CREATION DATE:
92 **
93 **    27-July-97
94 **
95 **--
96 */
97 
98 /*
99 **
100 **  INCLUDE FILES
101 **
102 */
103 
104 #include <sys/cdefs.h>
105 __KERNEL_RCSID(0, "$NetBSD: scr.c,v 1.36 2023/06/29 21:01:21 andvar Exp $");
106 
107 #include "opt_ddb.h"
108 
109 #include <sys/param.h>
110 #include <sys/systm.h>
111 #include <sys/ioctl.h>
112 /* #include <sys/select.h> */
113 /* #include <sys/tty.h> */
114 #include <sys/proc.h>
115 #include <sys/conf.h>
116 /* #include <sys/file.h> */
117 /* #include <sys/uio.h> */
118 #include <sys/kernel.h>
119 /* #include <sys/syslog.h> */
120 #include <sys/types.h>
121 #include <sys/device.h>
122 #include <dev/isa/isavar.h>
123 #include <arm/cpufunc.h>
124 
125 
126 /* SCR_DEBUG is the master switch for turning on debugging */
127 //#define SCR_DEBUG 1
128 #ifdef SCR_DEBUG
129     #define KERNEL_DEBUG
130     #ifdef DDB
131         #define DEBUGGER printf("file = %s, line = %d\n",__FILE__,__LINE__);Debugger()
132     #else
133         #define DEBUGGER panic("file = %s, line = %d",__FILE__,__LINE__);
134     #endif
135 #else
136     #define DEBUGGER
137 #endif
138 
139 
140 #include <machine/kerndebug.h>
141 //#include <machine/intr.h>
142 #include <dev/ic/i8253reg.h>
143 #include <shark/shark/hat.h>
144 #include <shark/shark/sequoia.h>
145 #include <machine/scrio.h>
146 
147 
148 
149 
150 /*
151 **
152 **  MACRO DEFINITIONS
153 **
154 */
155 
156 
157 #define scr_lcr scr_cfcr
158 
159 /*
160 ** Macro to extract the minor device number from the device Identifier
161 */
162 #define SCRUNIT(x)      (minor(x))
163 
164 /*
165 ** some macros to assist in debugging
166 */
167 #ifdef SCR_DEBUG
168     #define KERNEL_DEBUG
169     #define ASSERT(f)	        do { if (!(f)) { DEBUGGER;} }while(0)
170     #define TOGGLE_TEST_PIN()   scrToggleTestPin()
171     #define INVALID_STATE_CMD(sc,state,cmd)  invalidStateCmd(sc,state,cmd,__LINE__);
172 #else
173     #define ASSERT(f)
174     #define TOGGLE_TEST_PIN()
175     //#define INVALID_STATE_CMD(sc,state,cmd)  panic("scr: invalid state/cmd, sc = %X, state = %X, cmd = %X, line = %d",sc,state,cmd,__LINE__);
176     #define INVALID_STATE_CMD(sc,state,cmd)  sc->bigTrouble = true;
177 
178 #endif
179 
180 
181 /*
182 ** The first and last bytes of the debug control variables is reserved for
183 ** the standard KERN_DEBUG_xxx macros, so we can tailor the middle two bytes
184 */
185 #define SCRPROBE_DEBUG_INFO			0x00000100
186 #define SCRATTACH_DEBUG_INFO		0x00000200
187 #define SCROPEN_DEBUG_INFO			0x00000400
188 #define SCRCLOSE_DEBUG_INFO			0x00000800
189 #define SCRREAD_DEBUG_INFO			0x00001000
190 #define SCRWRITE_DEBUG_INFO			0x00002000
191 #define SCRIOCTL_DEBUG_INFO			0x00004000
192 #define MASTER_SM_DEBUG_INFO		0x00008000
193 #define COLD_RESET_SM_DEBUG_INFO	0x00010000
194 #define ATR_SM_DEBUG_INFO			0x00020000
195 #define T0_RECV_BYTE_SM_DEBUG_INFO	0x00040000
196 #define T0_SEND_BYTE_SM_DEBUG_INFO	0x00080000
197 #define T0_RECV_SM_DEBUG_INFO		0x00100000
198 #define T0_SEND_SM_DEBUG_INFO		0x00200000
199 
200 
201 int scrdebug =  //SCRPROBE_DEBUG_INFO	    |
202                 //SCRATTACH_DEBUG_INFO	|
203                 //SCROPEN_DEBUG_INFO		|
204                 //SCRCLOSE_DEBUG_INFO		|
205                 //SCRREAD_DEBUG_INFO		|
206                 //SCRWRITE_DEBUG_INFO		|
207                 //SCRIOCTL_DEBUG_INFO		|
208                 //MASTER_SM_DEBUG_INFO	|
209                 //COLD_RESET_SM_DEBUG_INFO|
210                 //ATR_SM_DEBUG_INFO		|
211                 //T0_RECV_BYTE_SM_DEBUG_INFO |
212                 //T0_SEND_BYTE_SM_DEBUG_INFO  |
213                 //T0_RECV_SM_DEBUG_INFO		|
214                 //T0_SEND_SM_DEBUG_INFO		|
215                 0;
216 
217 
218 
219 
220 
221 
222 /*
223 ** the bottom half of the driver is done as several linked state machines
224 ** below are all the states of the machines, and the commands that are
225 ** sent to each machine
226 */
227 
228 /* commands to Master State Machine from ioctl */
229 #define 	mcOn				0x0100		/* ioctl on */
230 #define		mcT0DataSend		0x0102		/* ioctl send */
231 #define		mcT0DataRecv		0x0103		/* ioctl recv */
232 
233 /* commands to Master State Machine from lower state machines */
234 #define		mcColdReset			0x0105		/* cold reset finished  */
235 #define		mcATR				0x0106		/* ATR has finished */
236 #define		mcT0Send			0x0108		/* T0 send finished */
237 #define		mcT0Recv			0x010a		/* T0 recv finished */
238 
239 /* states in Master state machine (ms = Master State) */
240 #define		msIdleOff		    0x0200      /* in idle state, card powered off */
241 #define		msColdReset		    0x0201      /* turning on power, clock, reset */
242 #define		msATR			    0x0202      /* getting ATR sequence from card */
243 #define		msIdleOn		    0x0203      /* idle, put card powered on */
244 #define		msT0Send		    0x0204      /* sending T0 data */
245 #define		msT0Recv		    0x0205      /* recving T0 data */
246 
247 
248 
249 
250 /* commands to T0 send state machine  */
251 #define 	t0scStart			0x0300      /* start  */
252 #define		t0scTWorkWaiting	0x0301      /* work waiting timeout */
253 
254 /* states in T0 send state machine */
255 #define 	t0ssIdle			0x0400      /* idle state */
256 #define		t0ssSendHeader		0x0401		/* send 5 header bytes */
257 #define		t0ssRecvProcedure	0x0402      /* wait for procedure byte */
258 #define		t0ssSendByte		0x0403      /* send 1 byte */
259 #define		t0ssSendData		0x0404      /* send all bytes */
260 #define		t0ssRecvSW1			0x0405      /* wait for sw1 */
261 #define		t0ssRecvSW2			0x0406      /* wait for sw2 */
262 
263 
264 
265 
266 
267 /* commands to T0 recv state machine */
268 #define 	t0rcStart			0x0500      /* start */
269 #define		t0rcTWorkWaiting	0x0501      /* work waiting timeout */
270 
271 /* states in T0 recv state machine */
272 #define 	t0rsIdle			0x0600      /* idle state */
273 #define		t0rsSendHeader		0x0601		/* send 5 header bytes */
274 #define		t0rsRecvProcedure	0x0602      /* wait for procedure byte */
275 #define		t0rsRecvByte		0x0603      /* recv 1 byte */
276 #define		t0rsRecvData		0x0604      /* recv all bytes */
277 #define		t0rsRecvSW1			0x0605      /* wait for sw1 */
278 #define		t0rsRecvSW2			0x0606      /* wait for sw2 */
279 
280 
281 
282 /* commands to Cold Reset state machine */
283 #define		crcStart		    0x0900      /* start */
284 #define		crcT2			    0x0902		/* timeout T2 ISO 7816-3, P6, Figure 2 */
285 
286 /* states in cold reset state machine */
287 #define		crsIdle			    0x0a00      /* idle */
288 #define		crsT2Wait		    0x0a01      /* wait for T2 ISO 7816-3.P6. Figure 2 */
289 
290 
291 
292 
293 
294 /* commands to Answer To Reset (ATR) state machine */
295 #define		atrcStart			0x0b00      /* start */
296 #define		atrcT3				0x0b04      /* got T3 timeout */
297 #define		atrcTWorkWaiting	0x0b05      /* work waiting timeout */
298 
299 /* states in Answer To Reset (ATR) state machine */
300 #define		atrsIdle		    0x0c00      /* idle */
301 #define		atrsTS			    0x0c01		/* looking for TS, (initial bytes)	*/
302 #define		atrsT0			    0x0c02		/* looking for T0, (format bytes)	*/
303 #define		atrsTABCD		    0x0c03		/* looking for TAx (interface bytes)*/
304 #define		atrsTK			    0x0c04		/* looking for TK  (history bytes)		*/
305 #define		atrsTCK			    0x0c05		/* looking for TCK (check bytes		*/
306 
307 
308 /* commands to T0 Recv Byte state machine */
309 #define		t0rbcStart			0x0d00      /* start */
310 #define		t0rbcAbort			0x0d01      /* abort */
311 #define		t0rbcTFindStartEdge	0x0d02		/* start bit edge search */
312 #define		t0rbcTFindStartMid	0x0d03		/* start bit mid search */
313 #define		t0rbcTClockData		0x0d04		/* data bit search */
314 #define		t0rbcTErrorStart	0x0d05		/* start to send error  */
315 #define		t0rbcTErrorStop		0x0d06		/* stop sending error	*/
316 
317 /* states in T0 Recv Byte state machine */
318 #define		t0rbsIdle			0x0e00      /* idle */
319 #define		t0rbsFindStartEdge  0x0e01		/* looking for start bit */
320 #define		t0rbsFindStartMid   0x0e02		/* looking for start bit */
321 #define		t0rbsClockData		0x0e03		/* looking for data bits */
322 #define		t0rbsSendError		0x0e04		/* output error bit */
323 
324 
325 
326 
327 /* commands to T0 Send Byte state machine */
328 #define		t0sbcStart			0x0f00      /* start the machine */
329 #define		t0sbcAbort			0x0f01      /* abort the machine */
330 #define		t0sbcTGuardTime		0x0f02		/* guard time finished */
331 #define		t0sbcTClockData		0x0f03		/* clock time finished     */
332 #define		t0sbcTError			0x0f04		/* start to send error  */
333 #define		t0sbcTResend		0x0f05		/* if parity error, then wait unfill we can re-send */
334 
335 
336 
337 /* states in T0 Send Byte state machine */
338 #define		t0sbsIdle			0x1000      /* idle */
339 #define		t0sbsWaitGuardTime	0x1001		/* wait for guard time to finish */
340 #define		t0sbsClockData		0x1002		/* clocking out data & parity */
341 #define		t0sbsWaitError		0x1003		/* waiting for error indicator */
342 #define		t0sbsWaitResend		0x1004		/* waiting to start re-send if error */
343 
344 
345 
346 
347 /*
348 ** generic middle level state machine commands
349 ** sent by T0 Send Byte & T0 recv Byte to T0 Send and T0 Recv
350 */
351 #define		gcT0RecvByte		0x1100      /* receive finished */
352 #define		gcT0RecvByteErr		0x1101      /* receive got error */
353 #define		gcT0SendByte		0x1102      /* send finished */
354 #define		gcT0SendByteErr		0x1103      /* send got error */
355 
356 
357 
358 
359 
360 
361 /*
362 **
363 ** below are definitions associated with Smart Card
364 **
365 */
366 
367 
368 /*
369 ** Frequency of clock sent to card
370 ** NCI's card is running at 1/2 freq, so in debug we can make
371 ** use of this to toggle more debug signals and still be within
372 ** interrupt time budget
373 */
374 #ifdef  SCR_DEBUG
375     #define CARD_FREQ_DEF			(3579000/2)
376 #else
377     #define CARD_FREQ_DEF			(3579000)
378 #endif
379 
380 
381 
382 /* byte logic level and msb/lsb coding */
383 #define CONVENTION_UNKNOWN		        0
384 #define CONVENTION_INVERSE		        1
385 #define CONVENTION_DIRECT		        2
386 #define CONVENIONT_INVERSE_ID			0x3f
387 #define CONVENTION_DIRECT_FIX			0x3b
388 #define CONVENTION_DIRECT_ID			0x23
389 
390 
391 /* macros that help us set the T2 count for bit bashing */
392 #define CLK_COUNT_START	        (((372   * TIMER_FREQ) / sc->cardFreq) /5)
393 #define CLK_COUNT_DATA	        (((372   * TIMER_FREQ) / sc->cardFreq)   )
394 #define START_2_DATA            5
395 
396 /* default settings to use if not specified in ATR */
397 #define N_DEFAULT			    0		/* guard time default */
398 #define Fi_DEFAULT			    372		/* clock rate conversion default */
399 #define Di_DEFAULT			    1		/* bit rate adjustment factor */
400 #define Wi_DEFAULT			    10		/* waiting time */
401 
402 
403 /* table for clock rate adjustment in ATR */
404 int FI2Fi[16] = {372, 372, 558, 744,1116,1488,1860,   0,
405                    0, 512, 768,1024,1536,2048,   0,   0};
406 
407 /* table for bit rate adjustment   in ATR*/
408 int DI2Di[16] = {  0,   1,   2,   4,   8,   16, 32,   0,
409                   12,  20,   0,   0,   0,    0,  0,   0};
410 
411 /* values of atrY in the ATR sequence*/
412 #define ATR_Y_TA	0x10
413 #define ATR_Y_TB	0x20
414 #define ATR_Y_TC	0x40
415 #define ATR_Y_TD	0x80
416 
417 /* T0,T1,etc  information in ATR sequence*/
418 #define PROTOCOL_T0 0x0001			/* bit 0 for T0 */
419 #define PROTOCOL_T1 0x0002			/* bit 1 for T1 */
420 #define PROTOCOL_T2 0x0004			/* bit 2 for T2*/
421 #define PROTOCOL_T3 0x0008			/* bit 3 for T3*/
422 /* etc  */
423 
424 
425 /* timeouts for various places - see ISO 7816-3 */
426 #define T_t2					((300   * TIMER_FREQ) / sc->cardFreq)
427 #define T_t3					((40000 * (TIMER_FREQ/1024)) / (sc->cardFreq/1024))
428 #define T_WORK_WAITING			(((960 * sc->Wi * sc->Fi ) / (sc->cardFreq/1024))  * (TIMER_FREQ/1024))
429 #define PARITY_ERROR_MAX 3		/* maximum parity errors on 1 byte before giving up  */
430 
431 /*
432 ** its possible for the HAT to wedge.  If that happens, all timing is sick, so
433 ** we use timeout below (driven of system sleeps) as a "watchdog"
434 */
435 #define MAX_FIQ_TIME     5      /* maximum time we are willing to run the FIQ */
436 
437 
438 /* used to decode T0 commands */
439 #define CMD_BUF_INS_OFF		    1	    /* offset to INS in header */
440 #define CMD_BUF_DATA_LEN_OFF    4	    /* offset to data length in header */
441 
442 
443 /*
444 **
445 ** DATA STRUCTURES
446 **
447 */
448 typedef unsigned char BYTE;
449 
450 /* our soft c structure */
451 struct scr_softc
452 {
453     int     open;
454 
455     /* configuration information */
456     int     status;                 /* status to be returned */
457     int     cardFreq;               /* freq supplied to card */
458     int     convention;             /* ie direct or inverse */
459     int     protocolType;           /* bit 0 indicates T0, bit 1 indicates T1,etc */
460     int     N;                      /* guard time  */
461     int     Fi;                     /* clock rate */
462     int     Di;                     /* bit rate adjustment */
463     int     Wi;                     /* work waiting time */
464     int     clkCountStartRecv;      /* count for clock start bits on recv */
465     int     clkCountDataRecv;       /* count for clock data  bits on recv*/
466     int     clkCountDataSend;       /* count for clock data  bits on send */
467 
468     /* state machines */
469     int     masterS ;
470     int     t0RecvS;
471     int     t0SendS;
472     int     coldResetS;
473     int     ATRS;
474     int     t0RecvByteS;
475     int     t0SendByteS;
476 
477     /* extra stuff kept for t0send state machine */
478     int     commandCount;           /* number of command bytes sent */
479     int     dataCount;              /* number of data bytes send/recv */
480     int     dataMax;                /* max number of data bytes to send/recv */
481 
482     /* extra stuff kept for t0RecvByteS, t0SendByteS machines */
483     void    (*t0ByteParent)(struct scr_softc *,int);  /* state machine that is controlling this SM */
484     int     shiftBits;              /* number of bits shifted	*/
485     BYTE    shiftByte;              /* intermediate value of bit being shifted */
486     BYTE    dataByte;               /* actual value of byte */
487     int     shiftParity;            /* value of parity */
488     int     shiftParityCount;       /* number of retries due to parity error */
489 
490     /* extra stuff kept for ATR machine */
491     int     atrY;       /* indicates if TA,TB,TC,TD is to follow */
492     int     atrK;       /* number of historical characters*/
493     int     atrKCount;  /* progressive could of historical characters*/
494     int     atrTABCDx;  /* the 'i' in TA(i), TB(i), TC(i) and TD(i) */
495     int     atrFi;      /* value of Fi */
496     int     atrDi;      /* value of Di */
497 
498     int masterDone; /* flag used by bottom half to tell top half its done */
499     int bigTrouble; /* david/jim, remove this when the dust settles  */
500 
501     /* pointers used by ioctl */
502     ScrOn * pIoctlOn;   /* pointer to on ioctl data */
503     ScrT0 * pIoctlT0;   /* pointer to T0 ioctl data */
504 };
505 
506 /* number of devices */
507 static int devices = 0;
508 
509 /* used as reference for tsleep */
510 static int tsleepIdent;
511 
512 
513 /*
514 ** only 1 device is using the hat at any one time
515 ** variable below must be acquired using splhigh before using the hat
516 */
517 static int hatLock = false;
518 
519 
520 
521 
522 /*
523 ** data structures associated with our timeout queue that we run for the
524 ** bottom half of the driver
525 */
526 
527 /* timeout callout structure */
528 typedef struct callout_t
529 {
530     struct callout_t *c_next;                       /* next callout in queue */
531     struct scr_softc *c_sc;                         /* soft c */
532     int     c_arg;                                  /* function argument */
533     void    (*c_func)(struct scr_softc*,int); /* function to call */
534     int     c_time;                                 /* ticks to the event */
535 }Callout;
536 
537 /* actual callout array */
538 #define  SCR_CLK_CALLOUT_COUNT 10
539 static Callout  scrClkCalloutArray[SCR_CLK_CALLOUT_COUNT];
540 
541 /* callout lists */
542 static Callout *scrClkCallFree;                     /* free queue */
543 static Callout  scrClkCallTodo;                     /* todo queue */
544 
545 /*
546 ** information kept for the clock/FIQ that drives our timeout queue
547 */
548 static int scrClkEnable = 0;                   /* true if clock enabled */
549 static void myHatWedge(int nFIQs);             /* callback that informs us if FIQ has wedged */
550 static int scrClkCount;                        /* number used to set t2 that drives FIQ */
551 
552 #define HATSTACKSIZE 1024                       /* size of stack used during a FIQ */
553 static unsigned char hatStack[HATSTACKSIZE];   /* actual stack used during a FIQ */
554 
555 
556 
557 
558 
559 
560 
561 
562 
563 
564 
565 
566 /*
567 **
568 **  FUNCTIONAL PROTOTYPES
569 **
570 */
571 
572 /*
573 **
574 ** functions in top half of driver
575 **
576 */
577 
578 /* configure routines */
579 int     scrprobe(device_t, cfdata_t, void *);
580 void    scrattach(device_t, device_t, void *);
581 
582 static void   initStates(struct scr_softc * sc);
583 
584 
585 
586 
587 /*
588 **
589 ** functions in bottom half of driver
590 **
591 */
592 
593 /* top level state machine */
594 static void   masterSM(struct scr_softc * sc,int cmd);
595 
596 /* mid level state machines, ie protocols  */
597 static void   t0SendSM(struct scr_softc * sc,int cnd);
598 static void   t0RecvSM(struct scr_softc * sc,int cnd);
599 static void   ATRSM(struct scr_softc * sc,int cnd);
600 
601 /* low level state machines, ie bash hardware bits */
602 static void   coldResetSM(struct scr_softc * sc,int cnd);
603 
604 static void   t0SendByteSM(struct scr_softc * sc,int cnd);
605 static void   t0RecvByteSM(struct scr_softc * sc,int cnd);
606 
607 static void   cardOff(struct scr_softc * sc);
608 
609 /*
610 ** functions used for our own timeout routines.
611 ** we cannot use system ones as we are running at a spl level
612 ** that can interrupt the system timeout routines
613 */
614 static void scrClkInit(void);
615 static void scrClkStart(struct scr_softc* sc,int countPerTick);
616 static void scrClkAdj(int count);
617 static void scrClkStop(void);
618 static void hatClkIrq(int count);
619 
620 static void scrTimeout(void (*func)(struct scr_softc*,int), struct scr_softc*, int arg, int count);
621 static void scrUntimeout(void (*func)(struct scr_softc*,int), struct scr_softc*, int arg);
622 
623 
624 /* debug functions */
625 #ifdef SCR_DEBUG
626     static void invalidStateCmd(struct scr_softc* sc,int state,int cmd, int line);
627     static char * getText(int x);
628 #endif
629 
630 
631 
632 
633 
634 CFATTACH_DECL_NEW(scr, sizeof(struct scr_softc),
635     scrprobe, scrattach, NULL, NULL);
636 
637 extern struct cfdriver scr_cd;
638 
639 dev_type_open(scropen);
640 dev_type_close(scrclose);
641 dev_type_ioctl(scrioctl);
642 
643 const struct cdevsw scr_cdevsw = {
644 	.d_open = scropen,
645 	.d_close = scrclose,
646 	.d_read = noread,
647 	.d_write = nowrite,
648 	.d_ioctl = scrioctl,
649 	.d_stop = nostop,
650 	.d_tty = notty,
651 	.d_poll = nopoll,
652 	.d_mmap = nommap,
653 	.d_kqfilter = nokqfilter,
654 	.d_discard = nodiscard,
655 	.d_flag = D_TTY
656 };
657 
658 /*
659 **++
660 **  FUNCTIONAL DESCRIPTION:
661 **
662 **      scrProbe
663 **
664 **     This is the probe routine for the Smart Card.  Because the
665 **     Smart Card is hard wired, there is no probing to perform.  The
666 **     function ensures that a successful problem occurs only once.
667 **
668 **  FORMAL PARAMETERS:
669 **
670 **     parent  - input  : pointer to the parent device
671 **     match   - not used
672 **     aux     - output : pointer to an isa_attach_args structure.
673 **
674 **  IMPLICIT INPUTS:
675 **
676 **     none.
677 **
678 **  IMPLICIT OUTPUTS:
679 **
680 **     none.
681 **
682 **  FUNCTION VALUE:
683 **
684 **     0 - Probe failed to find the requested device.
685 **     1 - Probe successfully talked to the device.
686 **
687 **  SIDE EFFECTS:
688 **
689 **     none.
690 **--
691 */
692 int
scrprobe(device_t parent,cfdata_t match,void * aux)693 scrprobe(device_t parent, cfdata_t match, void *aux)
694 {
695     struct isa_attach_args  *ia = aux;
696     int                     rv = 0;
697 
698     KERN_DEBUG (scrdebug, SCRPROBE_DEBUG_INFO,("scrprobe: called, name = %s\n",
699                                                device_cfdata(parent)->cf_name));
700 
701     if (device_is_a(parent, "ofisascr") && devices == 0)
702     {
703         /* set "devices" to ensure that we respond only once */
704         devices++;
705 
706         /* tell the caller that we are not using any resource */
707 	ia->ia_nio = 0;
708 	ia->ia_niomem = 0;
709 	ia->ia_nirq = 0;
710 	ia->ia_ndrq = 0;
711         rv = 1;
712 
713 
714         KERN_DEBUG (scrdebug, SCRPROBE_DEBUG_INFO,("scrprobe: successful \n"));
715 
716     }
717 
718 
719     return (rv);
720 
721 } /* End scrprobe() */
722 
723 
724 /*
725 **++
726 **  FUNCTIONAL DESCRIPTION:
727 **
728 **      scrattach
729 **
730 **      Initialize the clock and state machines
731 **
732 **  FORMAL PARAMETERS:
733 **
734 **      parent - input  : pointer to my parents device structure.
735 **      self   - output : pointer to my softc with device structure at front.
736 **      aux    - input  : pointer to the isa_attach_args structure.
737 **
738 **  IMPLICIT INPUTS:
739 **
740 **      nill
741 **
742 **  IMPLICIT OUTPUTS:
743 **
744 **      scrconsinit - clock callout functions set
745 **                    state machines all at idle
746 **
747 **  FUNCTION VALUE:
748 **
749 **      none.
750 **
751 **  SIDE EFFECTS:
752 **
753 **      none.
754 **--
755 */
756 void
scrattach(device_t parent,device_t self,void * aux)757 scrattach(device_t parent, device_t self, void *aux)
758 {
759     struct scr_softc       *sc = device_private(self);
760 
761     printf("\n");
762     if (device_is_a(parent, "ofisascr"))
763     {
764         KERN_DEBUG (scrdebug, SCRATTACH_DEBUG_INFO,("scrattach: called \n"));
765 
766         /* set initial state machine values */
767         scrClkInit();
768         initStates(sc);
769         sc->open = false;
770     }
771 
772     else
773     {
774         panic("scrattach: not on an ISA bus, attach impossible");
775     } /* End else we aren't on ISA and we can't handle it */
776 
777 
778     return;
779 } /* End scrattach() */
780 
781 
782 /*
783 **++
784 **  FUNCTIONAL DESCRIPTION:
785 **
786 **      initStates
787 **
788 **      sets the state of all machines to idle
789 **
790 **  FORMAL PARAMETERS:
791 **
792 **      sc    -  Pointer to the softc structure.
793 **
794 **  IMPLICIT INPUTS:
795 **
796 **      nill
797 **
798 **  IMPLICIT OUTPUTS:
799 **
800 **      nill
801 **
802 **  FUNCTION VALUE:
803 **
804 **      nill
805 **
806 **  SIDE EFFECTS:
807 **
808 **      nill
809 **--
810 */
initStates(struct scr_softc * sc)811 static void initStates(struct scr_softc * sc)
812 {
813     sc->masterS         = msIdleOff;
814     sc->t0RecvS         = t0rsIdle;
815     sc->t0SendS         = t0ssIdle;
816     sc->coldResetS      = crsIdle;
817     sc->ATRS            = atrsIdle;
818     sc->t0RecvByteS     = t0rbsIdle;
819     sc->t0SendByteS     = t0sbsIdle;
820 }
821 
822 
823 
824 /*
825 **++
826 **  FUNCTIONAL DESCRIPTION:
827 **
828 **     scrOpen
829 **
830 **     Opens the driver.  We only let the device be opened
831 **     once for security reasons
832 **
833 **  FORMAL PARAMETERS:
834 **
835 **     dev  - input : Device identifier consisting of major and minor numbers.
836 **     flag - input : Indicates if this is a blocking I/O call.
837 **     mode - not used.
838 **     l    - input : Pointer to the lwp structure of the light weight process
839 **            performing the open.
840 **
841 **  IMPLICIT INPUTS:
842 **
843 **     none.
844 **
845 **  IMPLICIT OUTPUTS:
846 **
847 **     none.
848 **
849 **  FUNCTION VALUE:
850 **
851 **     ENXIO   - invalid device specified for open.
852 **     EBUSY   - The unit is already open
853 **
854 **  SIDE EFFECTS:
855 **
856 **     none.
857 **--
858 */
scropen(dev_t dev,int flag,int mode,struct lwp * l)859 int scropen(dev_t dev, int flag, int mode, struct lwp *l)
860 {
861     struct scr_softc     *sc;
862 
863     KERN_DEBUG (scrdebug, SCROPEN_DEBUG_INFO,
864                 ("scropen: called with minor device %d and flag 0x%x\n",
865                  SCRUNIT(dev), flag));
866 
867     sc = device_lookup_private(&scr_cd, SCRUNIT(dev));
868     if (!sc)
869     {
870         KERN_DEBUG (scrdebug, SCROPEN_DEBUG_INFO,("\t scropen, return ENXIO\n"));
871         return (ENXIO);
872     }
873 
874 
875     // david,jim - remove ifdef this when NCI can cope with only 1 open
876 #if 0
877     if (sc->open)
878     {
879 
880         KERN_DEBUG (scrdebug, SCROPEN_DEBUG_INFO,("\t scropen, return EBUSY\n"));
881         return (EBUSY);
882     }
883 
884 
885     /* set all initial conditions */
886     sc->open = true;
887 #endif
888 
889     KERN_DEBUG (scrdebug, SCROPEN_DEBUG_INFO,("scropen: success \n"));
890     /* Now invoke the line discipline open routine
891     */
892 
893     return 0;
894 
895 } /* End scropen() */
896 
897 
898 /*
899 **++
900 **  FUNCTIONAL DESCRIPTION:
901 **
902 **     This function closed the driver
903 **
904 **  FORMAL PARAMETERS:
905 **
906 **     dev  - input : Device identifier consisting of major and minor numbers.
907 **     flag - Not used.
908 **     mode - Not used.
909 **     p    - Not used.
910 **
911 **  IMPLICIT INPUTS:
912 **
913 **     scr_cd  - used to locate the softc structure for the device unit
914 **               identified by dev.
915 **
916 **  IMPLICIT OUTPUTS:
917 **
918 **     The device is put into an idle state.
919 **
920 **  FUNCTION VALUE:
921 **
922 **     0 - Always returns success.
923 **
924 **  SIDE EFFECTS:
925 **
926 **     none.
927 **--
928 */
scrclose(dev_t dev,int flag,int mode,struct lwp * l)929 int scrclose(dev_t dev, int flag, int mode, struct lwp *l)
930 {
931 #if 0
932     struct scr_softc   *sc  = device_lookup_private(&scr_cd, SCRUNIT(dev));
933 #endif
934 
935     KERN_DEBUG (scrdebug, SCRCLOSE_DEBUG_INFO,
936                 ("scrclose: called for minor device %d flag 0x%x\n",
937                  SCRUNIT(dev), flag));
938 
939     // david,jim - remove ifdef this when NCI can cope with only 1 open
940 #if 0
941     /* Check we are open in the first place
942     */
943     if (sc->open)
944     {
945         /* put everything in the idle state */
946         scrClkInit();
947         initStates(sc);
948         sc->open = false;
949 
950     }
951 
952 
953     else
954     {
955         KERN_DEBUG (scrdebug, SCRCLOSE_DEBUG_INFO,("\t scrclose, device not open\n"));
956     }
957 #endif
958 
959     KERN_DEBUG (scrdebug, SCRCLOSE_DEBUG_INFO,("scrclose exiting\n"));
960     return(0);
961 }
962 
963 /*
964 **++
965 **  FUNCTIONAL DESCRIPTION:
966 **
967 **     This routine is responsible for performing I/O controls.
968 **
969 **      There are 4 commands.  Status, On, T0 and Off.
970 **
971 **      Status checks to see if the card is inserted.  This command
972 **      does not use the state machines
973 **
974 **      On turns the card on and gets the ATR sequence from the card.
975 **      This command does use the state machines
976 **
977 **      T0 is used to read and write the card.  This command does use
978 **      the state machines
979 **
980 **      Off turns the card off.  This command does not use the state
981 **      machines.
982 **
983 **
984 **  FORMAL PARAMETERS:
985 **
986 **     dev - input :  Device identifier consisting of major and minor numbers.
987 **     cmd - input : The requested IOCTL command to be performed.
988 **                   See scrio.h for details
989 **
990 **
991 **                   Bit Position      { 3322222222221111111111
992 **                                     { 10987654321098765432109876543210
993 **                   Meaning           | DDDLLLLLLLLLLLLLGGGGGGGGCCCCCCCC
994 **
995 **                   D - Command direction, in/out/both.
996 **                   L - Command argument length.
997 **                   G - Command group, 't' used for tty.
998 **                   C - Actual command enumeration.
999 **
1000 **     data - input/output : Direction depends on the command.
1001 **     flag - input : Not used by us but passed to line discipline and ttioctl
1002 **     l    - input : pointer to lwp structure of user.
1003 **
1004 **  IMPLICIT INPUTS:
1005 **
1006 **     none.
1007 **
1008 **  IMPLICIT OUTPUTS:
1009 **
1010 **     sc->masterS      state of master state machine
1011 **
1012 **
1013 **  FUNCTION VALUE:
1014 **
1015 **      ENOTTY   if not correct ioctl
1016 **
1017 **
1018 **  SIDE EFFECTS:
1019 **
1020 **--
1021 */
1022 int
scrioctl(dev_t dev,u_long cmd,void * data,int flag,struct lwp * l)1023 scrioctl(dev_t dev, u_long cmd, void *data, int flag, struct lwp *l)
1024 {
1025     struct scr_softc*   sc = device_lookup_private(&scr_cd, SCRUNIT(dev));
1026 
1027     int                 error = 0;          /* error value returned */
1028     int                 masterDoneRetries= 0;         /* nuber of times we looked at masterDone */
1029     int                 done;               /* local copy of masterDone */
1030 
1031     ScrStatus *         pIoctlStatus;       /* pointer to status ioctl */
1032     ScrOff *            pIoctlOff;          /* pointer to off ioctl */
1033 
1034     u_int               savedInts;          /* saved interrupts */
1035     int                 s;                  /* saved spl value */
1036 
1037 
1038 
1039     KERN_DEBUG (scrdebug, SCRIOCTL_DEBUG_INFO,
1040                 ("scrioctl: called for device 0x%x, command 0x%lx, "
1041                  "flag 0x%x\n",
1042                  SCRUNIT(dev), cmd, flag));
1043 
1044 
1045 
1046     switch (cmd)
1047     {
1048         /*
1049         ** get the status of the card, ie is it in, in but off, in and on
1050         */
1051         case SCRIOSTATUS:
1052             pIoctlStatus = (ScrStatus*)data;
1053             if (scrGetDetect())
1054             {
1055                 savedInts = disable_interrupts(I32_bit | F32_bit);
1056                 if (sc->masterS == msIdleOn)
1057                 {
1058                     pIoctlStatus->status = CARD_ON;
1059                 }
1060                 else
1061                 {
1062                     ASSERT(sc->masterS == msIdleOff);
1063                     pIoctlStatus->status = CARD_INSERTED;
1064                 }
1065                 restore_interrupts(savedInts);
1066             }
1067 
1068             else
1069             {
1070                 pIoctlStatus->status = CARD_REMOVED;
1071             }
1072             break;
1073 
1074 
1075 
1076         /*
1077         ** turn the card on and get the ATR sequence
1078         */
1079         case SCRIOON:
1080             sc->pIoctlOn = (ScrOn*)data;
1081             // acquire the hat lock.
1082             while (1)
1083             {
1084                 s = splhigh();
1085                 if(!hatLock)
1086                 {
1087                     hatLock = true;
1088                     splx(s);
1089                     break;
1090                 }
1091                 splx(s);
1092 
1093                 tsleep(&tsleepIdent ,PZERO,"hat", 1);
1094             }
1095 
1096 
1097             // check to see if the card is in
1098             if(!scrGetDetect())
1099             {
1100                 initStates(sc);
1101                 cardOff(sc);
1102                 // do not  call scrClkInit() as it is idle already
1103                 sc->pIoctlOn->status = ERROR_CARD_REMOVED;
1104             }
1105 
1106 
1107             // check to see if we are already on
1108             else if(sc->masterS == msIdleOn)
1109             {
1110                 sc->pIoctlOn->status = ERROR_CARD_ON;
1111             }
1112 
1113             // card was in, card is off, so lets start it
1114             else
1115             {
1116                 // set up the top half
1117                 sc->masterDone = false;
1118                 sc->bigTrouble = false;    /* david/jim, remove this when the dust settles  */
1119 
1120 
1121 
1122                 // start bottom half
1123                 scrClkStart (sc,400);
1124                 savedInts = disable_interrupts(I32_bit | F32_bit);
1125                 masterSM(sc,mcOn);
1126                 restore_interrupts(savedInts);
1127 
1128 
1129 
1130                 // see if bottom half done
1131                 while (1)
1132                 {
1133                     // check that we have not looped too many times
1134                     if(masterDoneRetries >= MAX_FIQ_TIME * hz)
1135                     {
1136 //printf("MAX_FIQ_TIME reached \n");
1137                         // big problems, so reset bottom
1138                         savedInts = disable_interrupts(I32_bit | F32_bit);
1139                         scrClkInit();
1140                         initStates(sc);
1141                         cardOff(sc);
1142                         sc->status = ERROR_CARD_REMOVED;
1143                         sc->masterDone = true;
1144                         restore_interrupts(savedInts);
1145                         // dont stop clock, done at bottom of case
1146                     }
1147                     masterDoneRetries++;
1148 
1149                     // get done bit
1150                     savedInts = disable_interrupts(I32_bit | F32_bit);
1151                     done =  sc->masterDone;
1152                     restore_interrupts(savedInts);
1153 
1154                     // see if all done
1155                     if(done)
1156                     {
1157                         break;
1158                     }
1159 
1160 
1161                     // wait for a while
1162                     tsleep(&tsleepIdent ,PZERO,"hat", 1);
1163                 }
1164 
1165 
1166                 // stop bottom half
1167                 scrClkStop();
1168 
1169 
1170                 /* need to fix up count bits in non hat interrupt time, so */
1171                 if (sc->status == ERROR_OK)
1172                 {
1173                     sc->clkCountStartRecv = CLK_COUNT_START;
1174                     sc->clkCountDataRecv  = sc->clkCountStartRecv * START_2_DATA;
1175                     sc->clkCountDataSend  = CLK_COUNT_DATA;
1176                 }
1177 
1178 
1179 
1180                 /* takes while to turn off all lines, so keep out of hat */
1181                 if (sc->masterS != msIdleOn)
1182                 {
1183                     cardOff(sc);
1184                 }
1185                 // get the status back from the state machine
1186                 sc->pIoctlOn->status = sc->status;
1187 
1188 
1189             }
1190 
1191 
1192             // release  the hat lock.
1193             s = splhigh();
1194             ASSERT(hatlock);
1195             hatLock = false;
1196             splx(s);
1197 
1198             // david,jim hack to stop ioctl memcpy problem, to be removed when problem fixed ejg
1199             if (sc->pIoctlOn->status != ERROR_OK)
1200             {
1201                 sc->pIoctlOn->atrLen = 0;
1202             }
1203             break;
1204 
1205 
1206         /*
1207         ** turn the card off
1208         */
1209         case SCRIOOFF:
1210             pIoctlOff = (ScrOff*)data;
1211             // card off does not requires any  state processing, so do work here
1212             initStates(sc);
1213             cardOff(sc);
1214             // do not  call scrClkInit() as it is idle already
1215             pIoctlOff->status = ERROR_OK;
1216             break;
1217 
1218 
1219         /*
1220         ** do a T0 read or write
1221         */
1222         case SCRIOT0:
1223             sc->pIoctlT0 = (ScrT0*)data;
1224 
1225             // acquire the hat lock.
1226             while (1)
1227             {
1228                 s = splhigh();
1229                 if(!hatLock)
1230                 {
1231                     hatLock = true;
1232                     splx(s);
1233                     break;
1234                 }
1235                 splx(s);
1236 
1237                 tsleep(&tsleepIdent ,PZERO,"hat", 1);
1238             }
1239 
1240             // check to see if the card is in
1241             if(!scrGetDetect())
1242             {
1243                 initStates(sc);
1244                 cardOff(sc);
1245                 // do not  call scrClkInit() as it is idle already
1246                 sc->pIoctlT0->status = ERROR_CARD_REMOVED;
1247             }
1248 
1249 
1250             // check to see if card is off
1251             else if(sc->masterS == msIdleOff)
1252             {
1253                 sc->pIoctlT0->status = ERROR_CARD_OFF;
1254             }
1255 
1256             // card was in, card is on, lets do command
1257             else
1258 
1259             {
1260                 // set up the top half
1261                 sc->masterDone = false;
1262                 sc->bigTrouble = false;    /* david/jim, remove this when the dust settles  */
1263 
1264                 // start bottom half
1265                 scrClkStart (sc,sc->clkCountDataSend);
1266                 savedInts = disable_interrupts(I32_bit | F32_bit);
1267                 if (sc->pIoctlT0->writeBuffer)
1268                 {
1269                     masterSM(sc,mcT0DataSend);
1270                 }
1271                 else
1272                 {
1273                     masterSM(sc,mcT0DataRecv);
1274                 }
1275                 restore_interrupts(savedInts);
1276 
1277 
1278                // see if bottom half done
1279                while (1)
1280                {
1281                      // check that we have not looped too many times
1282                      if(masterDoneRetries >= MAX_FIQ_TIME * hz)
1283                      {
1284 //printf("MAX_FIQ_TIME reached \n");
1285                         // big problems, so reset bottom
1286                         savedInts = disable_interrupts(I32_bit | F32_bit);
1287                         scrClkInit();
1288                         initStates(sc);
1289                         cardOff(sc);
1290                         sc->status = ERROR_CARD_REMOVED;
1291                         sc->masterDone = true;
1292                         restore_interrupts(savedInts);
1293                      }
1294                      masterDoneRetries++;
1295 
1296 
1297                     // get done bit
1298                     savedInts = disable_interrupts(I32_bit | F32_bit);
1299                     done =  sc->masterDone;
1300                     restore_interrupts(savedInts);
1301 
1302 
1303                     // see if all done
1304                     if(done)
1305                     {
1306                         break;
1307                     }
1308 
1309 
1310                     // wait for a while
1311                     tsleep(&tsleepIdent ,PZERO,"hat", 1);
1312 	       }
1313 
1314                 // stop bottom half
1315                 scrClkStop();
1316 
1317 
1318 
1319                 // get the status back from the state machine
1320                 sc->pIoctlT0->status = sc->status;
1321             }
1322 
1323 
1324             // release  the hat lock.
1325             s = splhigh();
1326             hatLock = false;
1327             splx(s);
1328 
1329 
1330 
1331             // david, jim hack to stop ioctl memcpy problem, to be removed when problem fixed ejg
1332             if (sc->pIoctlT0->status != ERROR_OK)
1333             {
1334                 sc->pIoctlT0->dataLen = 0;
1335             }
1336             break;
1337 
1338         default:
1339             KERN_DEBUG (scrdebug, SCRIOCTL_DEBUG_INFO,("\t scrioctl: unknown command, ENOTTY \n"));
1340             error = ENOTTY;
1341             break;
1342     }
1343 
1344 
1345 
1346     KERN_DEBUG (scrdebug, SCRIOCTL_DEBUG_INFO,
1347                 ("scrioctl: exiting with sc->status %d\n", error));
1348     return (error);
1349 } /* End scrioctl */
1350 
1351 
1352 
1353 
1354 
1355 
1356 /*
1357 **
1358 ** All functions below this point are the bottom half of the driver
1359 **
1360 ** All are called during a FIQ, except for some functions in masterSM which
1361 ** provides the interface between the bottom half and top half of
1362 ** the driver (nb masterDone() helps masterSM() out with this interface
1363 ** between top and bottom parts of the driver.
1364 **
1365 */
1366 
1367 
1368 /*
1369 **++
1370 **  FUNCTIONAL DESCRIPTION:
1371 **
1372 **      masterSM
1373 **
1374 **      This state machine implements the top level state control  It
1375 **      receives commands to turn the card on, and do T0 reads and T0 writes
1376 **      from the scrioctl.  It then calls mid level state machine to action
1377 **      these commands.
1378 **
1379 **      This machine is the only machine to keep state between scrioctl calls.
1380 **      Between calls, the state will be either msIdleOff, or msIdleOn.  msIdleOff
1381 **      indicates that no signals are applied to the card.  msidleOn indicates that
1382 **      power and clock are supplied to the card, and that the card has performed
1383 **      a successful ATR sequence.
1384 **
1385 **      This routine gets called during FIQ interrupts and from scrioctl.  It is a
1386 **      requirement that the scrioctl disables interrupts before calling this function.
1387 **
1388 **      NB:- there is no way for the machine to get from msIdleOn to msIdleOff.  Since
1389 **      this is just a matter of turning all signals off and resetting state machines,
1390 **      scrioctl takes a shortcut and resets everything itself.   Ie it hits everything
1391 **      with a big hammer!!
1392 **
1393 **  FORMAL PARAMETERS:
1394 **
1395 **      sc      -  Pointer to the softc structure.
1396 **      cmd     -  command to the state machine, can be from ioctl, or mid level SM
1397 **
1398 **  IMPLICIT INPUTS:
1399 **
1400 **      sc->masterS     state of this machine
1401 **      sc->pIoctlT0    pointer to T0 ioctl
1402 **
1403 **  IMPLICIT OUTPUTS:
1404 **
1405 **
1406 **  FUNCTION VALUE:
1407 **
1408 **      nill
1409 **
1410 **  SIDE EFFECTS:
1411 **
1412 **      power and clock applied to card if successful ATR
1413 **--
1414 */
masterSM(struct scr_softc * sc,int cmd)1415 static void masterSM(struct scr_softc * sc,int cmd)
1416 {
1417 
1418     if (sc->bigTrouble) return;     // david,jim , remove this when dust settles
1419 
1420     switch (sc->masterS)
1421     {
1422         case msIdleOff:
1423             switch (cmd)
1424             {
1425                 case mcOn:
1426                     if (scrGetDetect())
1427                     {
1428                         /*
1429                         ** the card is off, and we want it on
1430                         */
1431 
1432                         /* set initial values */
1433                         sc->status          = 0;
1434                         sc->convention      = CONVENTION_UNKNOWN;
1435                         sc->protocolType    = 0;
1436                         sc->N               = N_DEFAULT;
1437                         sc->Fi              = Fi_DEFAULT;
1438                         sc->Di              = Di_DEFAULT;
1439                         sc->Wi              = Wi_DEFAULT;
1440                         sc->cardFreq        = CARD_FREQ_DEF;
1441                         sc->clkCountStartRecv = CLK_COUNT_START;
1442                         sc->clkCountDataRecv  = sc->clkCountStartRecv * START_2_DATA;
1443                         sc->clkCountDataSend  = CLK_COUNT_DATA;
1444 
1445                         /* get coldResetSM  to turn on power, clock, reset */
1446                         sc->masterS = msColdReset;
1447                         coldResetSM(sc,crcStart);
1448                     }
1449                     else
1450                     {
1451                         /* card not inserted, so just set status and give up */
1452                         sc->status = ERROR_CARD_REMOVED;
1453                         sc->masterDone = true;
1454                     }
1455                     break;
1456 
1457                 default:
1458                     INVALID_STATE_CMD(sc,sc->masterS,cmd);
1459                     break;
1460             }
1461             break;
1462 
1463         case msColdReset:
1464             switch (cmd)
1465             {
1466                 case mcColdReset:
1467                     /*
1468                     ** coldResetSM has turned on power, clock , reset
1469                     ** tell ATRSM to get the ATR sequence from the card
1470                     */
1471                     sc->masterS = msATR;
1472                     ATRSM(sc,atrcStart);
1473                     break;
1474 
1475                 default:
1476                     INVALID_STATE_CMD(sc,sc->masterS,cmd);
1477                     break;
1478             }
1479             break;
1480 
1481         case msATR:
1482             switch (cmd)
1483             {
1484                 case mcATR:
1485                     /*
1486                     ** ATRSM has tried to get ATR sequence, so give
1487                     ** back results to scrioctl.  ATR sequence data
1488                     ** was copied directly into ioctl data area, so
1489                     ** no need to copy data
1490                     */
1491                     if(sc->status == ERROR_OK)
1492                     {
1493                         sc->masterS = msIdleOn;
1494                     }
1495                     else
1496                     {
1497                         sc->masterS = msIdleOff;
1498                     }
1499                     sc->masterDone = true;
1500                     break;
1501 
1502 
1503                 default:
1504                     INVALID_STATE_CMD(sc,sc->masterS,cmd);
1505                     break;
1506             }
1507             break;
1508 
1509         case msIdleOn:
1510             switch (cmd)
1511             {
1512                 // nb there is no command to go to the IdleOff state.  This
1513                 // is a reset of the state machine, so is done in ioctl
1514 
1515                 case mcT0DataSend:
1516                     /*
1517                     ** card is on, and we want to T0 Send, so
1518                     ** as t0SendSM to do work
1519                     */
1520                     sc->status  = ERROR_OK;
1521                     sc->masterS = msT0Send;
1522                     t0SendSM(sc,t0scStart);
1523                     break;
1524 
1525                 case mcT0DataRecv:
1526                     /*
1527                     ** card is on, and we want to T0 Recv, so
1528                     ** as t0RecvSM to do work
1529                     */
1530                     sc->status  = ERROR_OK;
1531                     sc->masterS = msT0Recv;
1532                     t0RecvSM(sc,t0rcStart);
1533                     break;
1534 
1535                 default:
1536                     INVALID_STATE_CMD(sc,sc->masterS,cmd);
1537                     break;
1538             }
1539 
1540             break;
1541 
1542         case msT0Send:
1543             switch (cmd)
1544             {
1545                 case mcT0Send:
1546                     /*
1547                     ** t0SendSM has tried to send , so lets give back results
1548                     */
1549                     sc->masterS = msIdleOn;
1550                     sc->masterDone = true;
1551                     break;
1552 
1553                 default:
1554                     INVALID_STATE_CMD(sc,sc->masterS,cmd);
1555                     break;
1556             }
1557             break;
1558 
1559         case msT0Recv:
1560             switch (cmd)
1561             {
1562                 case mcT0Recv:
1563                     /*
1564                     ** t0RecvSM has tried to recv , so lets give back results
1565                     ** data was written directly into ioctl data area, so we
1566                     ** do not  need to copy any data
1567                     */
1568                     sc->pIoctlT0->dataLen = sc->dataCount;
1569                     sc->masterS = msIdleOn;
1570                     sc->masterDone = true;
1571                     break;
1572 
1573                 default:
1574                     INVALID_STATE_CMD(sc,sc->masterS,cmd);
1575                     break;
1576             }
1577             break;
1578 
1579         default:
1580             INVALID_STATE_CMD(sc,sc->masterS,cmd);
1581             break;
1582 
1583     }
1584 }
1585 
1586 
1587 
1588 
1589 /*
1590 **++
1591 **  FUNCTIONAL DESCRIPTION:
1592 **
1593 **      t0SendSM
1594 **
1595 **      This is the T=0 Send State Machine.  It is responsible
1596 **      for performing the send part of the ISO 7816-3 T=0
1597 **      protocol.  It is mid level protocol state machine.
1598 **
1599 **      Once started, this machine is driven entirely via the
1600 **      FIQ/timeout structure .
1601 **
1602 **
1603 **
1604 **  FORMAL PARAMETERS:
1605 **
1606 **      sc      -  Pointer to the softc structure.
1607 **      cmd     -  command to this machine
1608 **
1609 **  IMPLICIT INPUTS:
1610 **
1611 **      sc->t0SendS             state of this machine
1612 **      sc->pIoctlT0->command   command to send to card
1613 **      sc->pIoctlT0->data      data to send to card
1614 **
1615 **  IMPLICIT OUTPUTS:
1616 **
1617 **      sc->status              error status from this machine
1618 **      sc->pIoctlT0->sw1       command status from card
1619 **      sc->pIoctlT0->sw2       command status from card
1620 **      sc->status              error status from this machine
1621 **
1622 **  FUNCTION VALUE:
1623 **
1624 **      nill
1625 **
1626 **  SIDE EFFECTS:
1627 **
1628 **      nill
1629 **--
1630 */
t0SendSM(struct scr_softc * sc,int cmd)1631 static void   t0SendSM         (struct scr_softc * sc, int cmd)
1632 {
1633     if (sc->bigTrouble) return;     // david,jim , remove this when dust settles
1634     /*
1635     ** check for major failures that are common to most states
1636     */
1637     if (cmd == t0scTWorkWaiting ||
1638         cmd == gcT0RecvByteErr  ||
1639         cmd == gcT0SendByteErr
1640         )
1641     {
1642         switch(cmd)
1643         {
1644             case t0scTWorkWaiting:
1645                 ASSERT(sc->t0SendS != t0ssIdle);
1646 
1647                 /* kill all lower machines */
1648                 t0SendByteSM(sc,t0sbcAbort);
1649                 t0RecvByteSM(sc,t0rbcAbort);
1650 
1651                 /* set status */
1652                 sc->status = ERROR_WORK_WAITING;
1653                 break;
1654 
1655             case gcT0RecvByteErr:   // fall through
1656             case gcT0SendByteErr:
1657                 scrUntimeout(t0SendSM, sc, t0scTWorkWaiting);
1658                 // done set status, already set in lower machine
1659                 break;
1660 
1661             default:
1662                 INVALID_STATE_CMD(sc, sc->t0SendS,cmd);
1663                 break;
1664         }
1665 
1666         /* change states */
1667         sc->t0SendS = t0ssIdle;
1668         masterSM(sc,mcT0Send);
1669         return;
1670     }
1671 
1672     switch (sc->t0SendS)
1673     {
1674         case t0ssIdle:
1675             switch (cmd)
1676             {
1677                 case t0scStart:
1678                     /* set initial values */
1679                     sc->t0SendS = t0ssSendHeader;
1680                     sc->t0ByteParent = t0SendSM;
1681                     sc->commandCount = 0;
1682                     sc->dataCount = 0;
1683                     sc->dataMax = sc->pIoctlT0->command[CMD_BUF_DATA_LEN_OFF];
1684                     sc->dataByte = sc->pIoctlT0->command[sc->commandCount];
1685 
1686                     // get a byte
1687                     t0SendByteSM(sc,t0sbcStart);
1688                     break;
1689 
1690                 default:
1691                     INVALID_STATE_CMD(sc, sc->t0SendS,cmd);
1692                     break;
1693             }
1694             break;
1695 
1696         case t0ssSendHeader:
1697             switch (cmd)
1698             {
1699                 case gcT0SendByte:
1700                     sc->commandCount++;
1701                     if (sc->commandCount < CMD_BUF_LEN)
1702                     {
1703                         sc->dataByte = sc->pIoctlT0->command[sc->commandCount];
1704                         t0SendByteSM(sc,t0sbcStart);
1705                     }
1706                     else
1707                     {
1708                         ASSERT(sc->commandCount == CMD_BUF_LEN);
1709 
1710                         sc->t0SendS = t0ssRecvProcedure;
1711                         scrTimeout(t0SendSM,sc,t0scTWorkWaiting,T_WORK_WAITING);
1712                         t0RecvByteSM(sc,t0rbcStart);
1713                     }
1714                     break;
1715 
1716                 default:
1717                     INVALID_STATE_CMD(sc, sc->t0SendS,cmd);
1718                     break;
1719             }
1720             break;
1721 
1722         case t0ssRecvProcedure:
1723             switch (cmd)
1724             {
1725                 case gcT0RecvByte:
1726                     scrUntimeout(t0SendSM, sc,t0scTWorkWaiting);
1727                     /* see if we should send all remaining bytes */
1728                     if ( (sc->dataByte == sc->pIoctlT0->command[CMD_BUF_INS_OFF])          ||
1729                          (sc->dataByte == (sc->pIoctlT0->command[CMD_BUF_INS_OFF] ^ 0x01))   )
1730                     {
1731                         ASSERT(sc->dataCount < sc->dataMax);
1732                         sc->t0SendS = t0ssSendData;
1733                         sc->dataByte = sc->pIoctlT0->data[sc->dataCount];
1734                         t0SendByteSM(sc,t0sbcStart);
1735                         sc->dataCount++;
1736                     }
1737 
1738                     /* see if we should send one data byte */
1739                     else if ((sc->dataByte == (sc->pIoctlT0->command[CMD_BUF_INS_OFF]  ^ 0xFF)) ||
1740                              (sc->dataByte == (sc->pIoctlT0->command[CMD_BUF_INS_OFF]  ^ 0xFE)) )
1741                     {
1742                         ASSERT(sc->dataCount < sc->dataMax);
1743                         sc->t0SendS = t0ssSendByte;
1744                         sc->dataByte = sc->pIoctlT0->data[ sc->dataCount];
1745                         t0SendByteSM(sc,t0sbcStart);
1746                         sc->dataCount++;
1747                     }
1748 
1749                     /* see if we should extend the work waiting period */
1750                     else if (sc->dataByte == 0x60)
1751                     {
1752                         t0RecvByteSM(sc,t0rbcStart);
1753                         scrTimeout(t0SendSM,sc,t0scTWorkWaiting,T_WORK_WAITING);
1754                     }
1755 
1756 #ifdef ORIGINAL_SW1_CODE /* XXX XXX XXX cgd */
1757                     /* see if we have a SW1 byte */
1758                     else if ( ((sc->dataByte & 0xf0)  == 0x60) || ((sc->dataByte & 0xf0)  == 0x90)
1759                               &&
1760                               sc->dataByte != 0x60)
1761 #else /* XXX XXX XXX cgd */
1762                     /* see if we have a SW1 byte */
1763                     else if ( ( ((sc->dataByte & 0xf0)  == 0x60) || ((sc->dataByte & 0xf0)  == 0x90) )
1764                               &&
1765                               sc->dataByte != 0x60)
1766 #endif /* XXX XXX XXX cgd */
1767                     {
1768                         sc->pIoctlT0->sw1 = sc->dataByte;
1769                         sc->t0SendS = t0ssRecvSW2;
1770                         t0RecvByteSM(sc,t0rbcStart);
1771                         scrTimeout(t0SendSM,sc,t0scTWorkWaiting,T_WORK_WAITING);
1772                     }
1773 
1774                     /* got bad data byte, log error and get out */
1775                     else
1776                     {
1777                         sc->status = ERROR_BAD_PROCEDURE_BYTE;
1778 
1779                         /* change state */
1780                         sc->t0SendS = t0ssIdle;
1781                         masterSM(sc,mcT0Send);
1782                     }
1783                     break;
1784 
1785                 default:
1786                     INVALID_STATE_CMD(sc, sc->t0SendS,cmd);
1787                     break;
1788             }
1789             break;
1790 
1791         case t0ssSendByte:
1792             switch (cmd)
1793             {
1794                 case gcT0SendByte:
1795                     if (sc->dataCount < sc->dataMax)
1796                     {
1797                         sc->t0SendS = t0ssRecvProcedure;
1798                     }
1799 
1800                     /* wait for sw1 byte */
1801                     else
1802                     {
1803                         ASSERT(sc->dataCount == sc->dataMax);
1804                         sc->t0SendS = t0ssRecvSW1;
1805                     }
1806 
1807                     // ask for another byte
1808                     t0RecvByteSM(sc,t0rbcStart);
1809                     scrTimeout(t0SendSM,sc,t0scTWorkWaiting,T_WORK_WAITING);
1810                     break;
1811 
1812                 default:
1813                     INVALID_STATE_CMD(sc, sc->t0SendS,cmd);
1814                     break;
1815             }
1816             break;
1817 
1818         case t0ssSendData:
1819             switch (cmd)
1820             {
1821                 case gcT0SendByte:
1822                     /* send data */
1823                     if (sc->dataCount < sc->dataMax)
1824                     {
1825                         sc->t0SendS = t0ssSendData;
1826                         sc->dataByte = sc->pIoctlT0->data[ sc->dataCount];
1827                         t0SendByteSM(sc,t0sbcStart);
1828                         sc->dataCount++;
1829                     }
1830 
1831                     /* wait for sw1 byte */
1832                     else
1833                     {
1834                         ASSERT(sc->dataCount == sc->dataMax);
1835                         sc->t0SendS = t0ssRecvSW1;
1836                         t0RecvByteSM(sc,t0rbcStart);
1837                         scrTimeout(t0SendSM,sc,t0scTWorkWaiting,T_WORK_WAITING);
1838                     }
1839                     break;
1840 
1841                 default:
1842                     INVALID_STATE_CMD(sc, sc->t0SendS,cmd);
1843                     break;
1844             }
1845             break;
1846 
1847         case t0ssRecvSW1:
1848             switch (cmd)
1849             {
1850                 case gcT0RecvByte:
1851                     scrUntimeout(t0SendSM, sc,t0scTWorkWaiting);
1852                     sc->pIoctlT0->sw1 = sc->dataByte;
1853                     sc->t0SendS = t0ssRecvSW2;
1854                     t0RecvByteSM(sc,t0rbcStart);
1855                     scrTimeout(t0SendSM,sc,t0scTWorkWaiting,T_WORK_WAITING);
1856                     break;
1857                 default:
1858                     INVALID_STATE_CMD(sc, sc->t0SendS,cmd);
1859                     break;
1860             }
1861             break;
1862 
1863         case t0ssRecvSW2:
1864             switch (cmd)
1865             {
1866                 case gcT0RecvByte:
1867                     scrUntimeout(t0SendSM, sc,t0scTWorkWaiting);
1868                     sc->pIoctlT0->sw2 = sc->dataByte;
1869                     sc->t0SendS = t0ssIdle;
1870                     masterSM(sc,mcT0Send);
1871                     break;
1872 
1873                 default:
1874                     INVALID_STATE_CMD(sc, sc->t0SendS,cmd);
1875                     break;
1876             }
1877             break;
1878 
1879         default:
1880             INVALID_STATE_CMD(sc, sc->t0SendS,cmd);
1881             break;
1882     }
1883 }
1884 
1885 
1886 
1887 /*
1888 **++
1889 **  FUNCTIONAL DESCRIPTION:
1890 **
1891 **      t0RecvSM
1892 **
1893 **      This is the T=0 Recv State Machine.  It is responsible
1894 **      for performing the recv part of the ISO 7816-3 T=0
1895 **      protocol.   It is mid level protocol state machine.
1896 **
1897 **      Once started, this machine is driven entirely via the
1898 **      FIQ/timeout structure .
1899 **
1900 **  FORMAL PARAMETERS:
1901 **
1902 **      sc      -  Pointer to the softc structure.
1903 **      cmd     -  command to this machine
1904 **
1905 **  IMPLICIT INPUTS:
1906 **
1907 **      sc->t0RecvS             state of this machine
1908 **      sc->pIoctlT0->command   command to send to card
1909 **
1910 **  IMPLICIT OUTPUTS:
1911 **
1912 **      sc->pIoctlT0->data      data from card
1913 **      sc->pIoctlT0->dataLen   size of data from card
1914 **      sc->pIoctlT0->sw1       command status from card
1915 **      sc->pIoctlT0->sw2       command status from card
1916 **      sc->status              error status from this machine
1917 **
1918 **  FUNCTION VALUE:
1919 **
1920 **      nill
1921 **
1922 **  SIDE EFFECTS:
1923 **
1924 **      nill
1925 **--
1926 */
t0RecvSM(struct scr_softc * sc,int cmd)1927 static void   t0RecvSM (struct scr_softc * sc,int cmd)
1928 {
1929     if (sc->bigTrouble) return;     // david,jim , remove this when dust settles
1930 
1931     /*
1932     ** check for major failures that are common to most states
1933     */
1934     if (cmd == t0rcTWorkWaiting ||
1935         cmd == gcT0RecvByteErr  ||
1936         cmd == gcT0SendByteErr  )
1937 
1938     {
1939         switch(cmd)
1940         {
1941 
1942             case t0rcTWorkWaiting:
1943                 ASSERT(sc->t0RecvS != t0rsIdle);
1944 
1945                 /* kill all lower level machines */
1946                 t0SendByteSM(sc,t0sbcAbort);
1947                 t0RecvByteSM(sc,t0rbcAbort);
1948 
1949                 /* set status */
1950                 sc->status = ERROR_WORK_WAITING;
1951                 break;
1952 
1953             case gcT0RecvByteErr:       // fall through
1954             case gcT0SendByteErr:
1955                 /* kill all the timers */
1956                 scrUntimeout(t0RecvSM, sc,t0rcTWorkWaiting);
1957                 break;
1958 
1959             default:
1960                 INVALID_STATE_CMD(sc, sc->t0RecvS,cmd);
1961                 break;
1962 
1963         }
1964 
1965 
1966 
1967         /* change state */
1968         sc->t0RecvS = t0rsIdle;
1969         masterSM(sc,mcT0Recv);
1970 
1971         /* all done */
1972         return;
1973     }
1974 
1975     switch (sc->t0RecvS)
1976     {
1977         case t0rsIdle:
1978             switch (cmd)
1979             {
1980                 case t0rcStart:
1981                     /* set initial values */
1982                     sc->t0RecvS = t0rsSendHeader;
1983                     sc->t0ByteParent = t0RecvSM;
1984                     sc->commandCount = 0;
1985                     sc->dataCount = 0;
1986                     sc->dataMax = sc->pIoctlT0->command[CMD_BUF_DATA_LEN_OFF];
1987                     if (sc->dataMax == 0)
1988                     {
1989                         sc->dataMax = 256;
1990                     }
1991                     sc->dataByte = sc->pIoctlT0->command[sc->commandCount];
1992                     t0SendByteSM(sc,t0sbcStart);
1993                     break;
1994 
1995                 default:
1996                     INVALID_STATE_CMD(sc, sc->t0RecvS,cmd);
1997                     break;
1998             }
1999             break;
2000 
2001         case t0rsSendHeader:
2002             switch (cmd)
2003             {
2004                 case gcT0SendByte:
2005                     sc->commandCount++;
2006                     if (sc->commandCount < CMD_BUF_LEN)
2007                     {
2008                         sc->dataByte = sc->pIoctlT0->command[sc->commandCount];
2009                         t0SendByteSM(sc,t0sbcStart);
2010                     }
2011                     else
2012                     {
2013                         ASSERT(sc->commandCount == CMD_BUF_LEN);
2014 
2015                         sc->t0RecvS = t0rsRecvProcedure;
2016                         scrTimeout(t0RecvSM,sc,t0rcTWorkWaiting,T_WORK_WAITING);
2017                         t0RecvByteSM(sc,t0rbcStart);
2018                     }
2019                     break;
2020 
2021                 default:
2022                     INVALID_STATE_CMD(sc, sc->t0RecvS,cmd);
2023                     break;
2024             }
2025             break;
2026 
2027         case t0rsRecvProcedure:
2028             switch (cmd)
2029             {
2030                 case gcT0RecvByte:
2031                     scrUntimeout(t0RecvSM, sc,t0rcTWorkWaiting);
2032 
2033                     /* see if we should recv all remaining bytes */
2034                     if ( (sc->dataByte == sc->pIoctlT0->command[CMD_BUF_INS_OFF])          ||
2035                          (sc->dataByte == (sc->pIoctlT0->command[CMD_BUF_INS_OFF] ^ 0x01))   )
2036                     {
2037                         ASSERT(sc->dataCount < sc->dataMax);
2038 
2039                         sc->t0RecvS = t0rsRecvData;
2040                         scrTimeout(t0RecvSM,sc,t0rcTWorkWaiting,T_WORK_WAITING);
2041                         t0RecvByteSM(sc,t0rbcStart);
2042                     }
2043 
2044                     /* see if we should send one data byte */
2045                     else if ((sc->dataByte == (sc->pIoctlT0->command[CMD_BUF_INS_OFF]  ^ 0xFF)) ||
2046                              (sc->dataByte == (sc->pIoctlT0->command[CMD_BUF_INS_OFF]  ^ 0xFE)) )
2047                     {
2048                         ASSERT(sc->dataCount < sc->dataMax);
2049                         sc->t0RecvS = t0rsRecvByte;
2050                         scrTimeout(t0RecvSM,sc,t0rcTWorkWaiting,T_WORK_WAITING);
2051                         t0RecvByteSM(sc,t0rbcStart);
2052                     }
2053 
2054                     /* see if we should extend the work waiting period */
2055                     else if (sc->dataByte == 0x60)
2056                     {
2057                         t0RecvByteSM(sc,t0rbcStart);
2058                         scrTimeout(t0RecvSM,sc,t0rcTWorkWaiting,T_WORK_WAITING);
2059                     }
2060 
2061 #ifdef ORIGINAL_SW1_CODE /* XXX XXX XXX cgd */
2062                     /* see if we have a SW1 byte */
2063                     else if ( ((sc->dataByte & 0xf0)  == 0x60) || ((sc->dataByte & 0xf0)  == 0x90)
2064                               &&
2065                               sc->dataByte != 0x60)
2066 #else /* XXX XXX XXX cgd */
2067                     /* see if we have a SW1 byte */
2068                     else if ( ( ((sc->dataByte & 0xf0)  == 0x60) || ((sc->dataByte & 0xf0)  == 0x90) )
2069                               &&
2070                               sc->dataByte != 0x60)
2071 #endif /* XXX XXX XXX cgd */
2072                     {
2073                         sc->pIoctlT0->sw1 = sc->dataByte;
2074                         sc->t0RecvS = t0rsRecvSW2;
2075                         t0RecvByteSM(sc,t0rbcStart);
2076                         scrTimeout(t0RecvSM,sc,t0rcTWorkWaiting,T_WORK_WAITING);
2077                     }
2078 
2079                     /* got bad data byte, log error and get out */
2080                     else
2081                     {
2082                         sc->status = ERROR_BAD_PROCEDURE_BYTE;
2083 
2084                         /* change state */
2085                         sc->t0RecvS = t0rsIdle;
2086                         masterSM(sc,mcT0Recv);
2087                     }
2088                     break;
2089 
2090                 default:
2091                     INVALID_STATE_CMD(sc, sc->t0RecvS,cmd);
2092                     break;
2093             }
2094             break;
2095 
2096         case t0rsRecvByte:
2097             switch (cmd)
2098             {
2099                 case gcT0RecvByte:
2100                     /* clock in byte */
2101                     scrUntimeout(t0RecvSM, sc,t0rcTWorkWaiting);
2102                     sc->pIoctlT0->data[sc->dataCount] = sc->dataByte;
2103                     sc->dataCount++;
2104 
2105 
2106                     if (sc->dataCount < sc->dataMax)
2107                     {
2108                         /* get procedure byte */
2109                         sc->t0RecvS = t0rsRecvProcedure;
2110                     }
2111 
2112                     else
2113                     {
2114                         ASSERT(sc->dataCount == sc->dataMax);
2115                         sc->t0RecvS = t0rsRecvSW1;
2116                     }
2117 
2118                     // ask for another byte
2119                     scrTimeout(t0RecvSM,sc,t0rcTWorkWaiting,T_WORK_WAITING);
2120                     t0RecvByteSM(sc,t0rbcStart);
2121                     break;
2122 
2123                 default:
2124                     INVALID_STATE_CMD(sc, sc->t0RecvS,cmd);
2125                     break;
2126             }
2127             break;
2128 
2129         case t0rsRecvData:
2130             switch (cmd)
2131             {
2132                 case gcT0RecvByte:
2133                     /* clock in data */
2134                     scrUntimeout(t0RecvSM, sc,t0rcTWorkWaiting);
2135                     sc->pIoctlT0->data[sc->dataCount] = sc->dataByte;
2136                     sc->dataCount++;
2137 
2138                     /* decide if we have all data */
2139                     if (sc->dataCount >= sc->dataMax)
2140                     {
2141                         KERN_DEBUG (scrdebug, T0_RECV_SM_DEBUG_INFO,("\t\tt0RecvSM: changing state to t0rsRecvSW1\n"));
2142                         ASSERT(sc->dataCount == sc->dataMax);
2143                         sc->t0RecvS = t0rsRecvSW1;
2144                     }
2145 
2146                     /* ask for another byte */
2147                     scrTimeout(t0RecvSM,sc,t0rcTWorkWaiting,T_WORK_WAITING);
2148                     t0RecvByteSM(sc,t0rbcStart);
2149                     break;
2150 
2151                 default:
2152                     INVALID_STATE_CMD(sc, sc->t0RecvS,cmd);
2153                     break;
2154             }
2155             break;
2156 
2157         case t0rsRecvSW1:
2158             switch (cmd)
2159             {
2160                 case gcT0RecvByte:
2161                     scrUntimeout(t0RecvSM, sc,t0rcTWorkWaiting);
2162                     sc->pIoctlT0->sw1 = sc->dataByte;
2163 
2164                     sc->t0RecvS = t0rsRecvSW2;
2165                     t0RecvByteSM(sc,t0rbcStart);
2166                     scrTimeout(t0RecvSM,sc,t0rcTWorkWaiting,T_WORK_WAITING);
2167                     break;
2168                 default:
2169                     INVALID_STATE_CMD(sc, sc->t0RecvS,cmd);
2170                     break;
2171             }
2172             break;
2173 
2174         case t0rsRecvSW2:
2175             switch (cmd)
2176             {
2177                 case gcT0RecvByte:
2178                     scrUntimeout(t0RecvSM, sc,t0rcTWorkWaiting);
2179                     sc->pIoctlT0->sw2 = sc->dataByte;
2180 
2181                     sc->t0RecvS = t0rsIdle;
2182                     masterSM(sc,mcT0Recv);
2183                     break;
2184 
2185                 default:
2186                     INVALID_STATE_CMD(sc, sc->t0RecvS,cmd);
2187                     break;
2188             }
2189             break;
2190 
2191         default:
2192             INVALID_STATE_CMD(sc, sc->t0RecvS,cmd);
2193             break;
2194     }
2195 }
2196 
2197 
2198 /*
2199 **++
2200 **  FUNCTIONAL DESCRIPTION:
2201 **
2202 **      coldResetSM
2203 **
2204 **      This state machine switches on the power, clock and reset pins
2205 **      in the correct order/timing.
2206 **      It is a low level bit-bashing state machine.
2207 **
2208 **
2209 **  FORMAL PARAMETERS:
2210 **
2211 **      sc      -  Pointer to the softc structure.
2212 **      cmd     -  command to this machine
2213 **
2214 **  IMPLICIT INPUTS:
2215 **
2216 **      sc->coldResetS     state of this machine
2217 **
2218 **  IMPLICIT OUTPUTS:
2219 **
2220 **      nill
2221 **
2222 **  FUNCTION VALUE:
2223 **
2224 **      nill
2225 **
2226 **  SIDE EFFECTS:
2227 **
2228 **      signals to card are on
2229 **--
2230 */
coldResetSM(struct scr_softc * sc,int cmd)2231 static void   coldResetSM(struct scr_softc * sc,int cmd)
2232 {
2233     if (sc->bigTrouble) return;     // david,jim , remove this when dust settles
2234 
2235     switch (sc->coldResetS)
2236     {
2237         case    crsIdle:
2238             switch (cmd)
2239             {
2240                 case crcStart:
2241                     scrSetReset(true);
2242                     scrSetClock(true);
2243                     scrSetDataHighZ();
2244                     scrSetPower(true);
2245 
2246                     /* start a t2 timer */
2247                     scrTimeout(coldResetSM,sc,crcT2,T_t2);
2248                     sc->coldResetS = crsT2Wait;
2249                     break;
2250 
2251                 default:
2252                     INVALID_STATE_CMD(sc,sc->masterS,cmd);
2253                     break;
2254             }
2255             break;
2256 
2257         case    crsT2Wait:
2258             switch (cmd)
2259             {
2260                 case crcT2:
2261                     /* turn off rst */
2262                     scrSetReset(false);
2263 
2264                     /* tell master state machine that we are all done */
2265                     sc->coldResetS = crsIdle;
2266                     masterSM(sc,mcColdReset);
2267                     break;
2268 
2269                 default:
2270                     INVALID_STATE_CMD(sc,sc->masterS,cmd);
2271                     break;
2272             }
2273             break;
2274 
2275 
2276         default:
2277             INVALID_STATE_CMD(sc,sc->coldResetS,cmd);
2278             break;
2279     }
2280 }
2281 
2282 /*
2283 **++
2284 **  FUNCTIONAL DESCRIPTION:
2285 **
2286 **      ATRSM
2287 **
2288 **      This is the Answer To Reset State Machine.  It is responsible
2289 **      for performing the Answer To Reset as specified in ISO 7816-3.
2290 **      It is mid level protocol state machine.
2291 **
2292 **      Once started, this machine is driven entirely via the
2293 **      FIQ/timeout structure.
2294 **
2295 **
2296 **      During the first byte, we have to check if the card is operating
2297 **      at full speed or half speed.  The first couple of bits are
2298 **      checked to see if it is 1/2 speed, and if so, the clock is changed
2299 **      and the state adjustes
2300 **
2301 **      At the end of the first byte we have to determine the logic being
2302 **      used by the card, ie is it active high/low and msb/lsb.
2303 **
2304 **
2305 **  FORMAL PARAMETERS:
2306 **
2307 **      sc      -  Pointer to the softc structure.
2308 **      cmd     -  command to this machine
2309 **
2310 **  IMPLICIT INPUTS:
2311 **
2312 **      sc->pIoctlAtr->atr      data from card
2313 **      sc->pIoctlT0->sw1       command status from card
2314 **      sc->pIoctlT0->sw2       command status from card
2315 **      sc->status              error status from this machine
2316 **
2317 **  IMPLICIT OUTPUTS:
2318 **
2319 **      sc->pIoctlOn->atrBuf    data from ATR sequence
2320 **      sc->pIoctlOn->atrLen    size of data from ATR sequence
2321 **      sc->status              error status from this machine
2322 **
2323 **
2324 **  FUNCTION VALUE:
2325 **
2326 **      nill
2327 **
2328 **  SIDE EFFECTS:
2329 **
2330 **      nill
2331 **--
2332 */
ATRSM(struct scr_softc * sc,int cmd)2333 static void ATRSM (struct scr_softc * sc,int cmd)
2334 {
2335     int lc;
2336     int tck;
2337 
2338     if (sc->bigTrouble) return;     // david,jim , remove this when dust settles
2339 
2340     /*
2341     ** check for major failures that are common to most states
2342     */
2343     if (cmd == atrcT3            ||
2344         cmd == atrcTWorkWaiting  ||
2345         cmd == gcT0RecvByteErr
2346         )
2347     {
2348         switch(cmd)
2349         {
2350             case atrcT3:
2351                 scrUntimeout (ATRSM,sc,atrcTWorkWaiting);
2352                 sc->status = ERROR_ATR_T3;
2353                 t0RecvByteSM(sc,t0rbcAbort);
2354                 break;
2355 
2356             case atrcTWorkWaiting:
2357                 scrUntimeout (ATRSM,sc,atrcT3);
2358                 sc->status = ERROR_WORK_WAITING;
2359                 t0RecvByteSM(sc,t0rbcAbort);
2360                 break;
2361 
2362             case gcT0RecvByteErr:
2363                 scrUntimeout (ATRSM,sc,atrcT3);
2364                 scrUntimeout (ATRSM,sc,atrcTWorkWaiting);
2365                 /* done set status, its already set */
2366                 break;
2367 
2368             default:
2369                 INVALID_STATE_CMD(sc,sc->ATRS,cmd);
2370                 break;
2371         }
2372 
2373         /* change state */
2374         sc->ATRS = atrsIdle;
2375         masterSM(sc,mcATR);
2376         return;
2377     }
2378 
2379     switch (sc->ATRS)
2380     {
2381         case    atrsIdle:
2382             switch (cmd)
2383             {
2384                 case atrcStart:
2385                     /* lets start looking */
2386                     sc->ATRS = atrsTS;
2387                     sc->pIoctlOn->atrLen = 0;
2388                     sc->t0ByteParent = ATRSM;
2389                     scrTimeout(ATRSM,sc,atrcT3,T_t3 *2);  /* by 2 to accommodate 1/2 freq cards */
2390                     t0RecvByteSM(sc,t0rbcStart);
2391                     break;
2392 
2393                 default:
2394                     INVALID_STATE_CMD(sc,sc->ATRS,cmd);
2395                     break;
2396             }
2397             break;
2398 
2399         case atrsTS:
2400             switch (cmd)
2401             {
2402                 case gcT0RecvByte:
2403                     scrUntimeout(ATRSM,sc,atrcT3);
2404                     sc->pIoctlOn->atrBuf[sc->pIoctlOn->atrLen] = sc->dataByte;
2405                     sc->pIoctlOn->atrLen++;
2406                     if(sc->pIoctlOn->atrLen >= ATR_BUF_MAX)
2407                     {
2408                         #ifdef SCR_DEBUG
2409                             DEBUGGER;
2410                         #endif
2411                         sc->status = ERROR_ATR_TCK;
2412                         sc->ATRS = atrsIdle;
2413                         masterSM(sc,mcATR);
2414                     }
2415                     else
2416                     {
2417                         /* move onto recv T0 */
2418                         sc->ATRS = atrsT0;
2419                         scrTimeout(ATRSM,sc,atrcTWorkWaiting,T_WORK_WAITING);
2420                         t0RecvByteSM(sc,t0rbcStart);
2421                     }
2422                     break;
2423 
2424                 default:
2425                     INVALID_STATE_CMD(sc,sc->ATRS,cmd);
2426                     break;
2427             }
2428             break;
2429 
2430         case atrsT0:
2431             switch (cmd)
2432             {
2433                 case gcT0RecvByte:
2434                     scrUntimeout(ATRSM,sc,atrcTWorkWaiting);
2435                     sc->pIoctlOn->atrBuf[sc->pIoctlOn->atrLen] = sc->dataByte;
2436                     sc->pIoctlOn->atrLen++;
2437                     if(sc->pIoctlOn->atrLen >= ATR_BUF_MAX)
2438                     {
2439                         #ifdef SCR_DEBUG
2440                             printf("atrLen >= ATR_BUF_MAX\n");
2441                             DEBUGGER;
2442                         #endif
2443                         sc->status = ERROR_ATR_TCK;
2444                         sc->ATRS = atrsIdle;
2445                         masterSM(sc,mcATR);
2446                     }
2447                     else
2448                     {
2449                         /* store Y & K */
2450                         sc->atrY = sc->dataByte & 0xf0;
2451                         sc->atrK = sc->dataByte & 0x0f;
2452 
2453                         sc->atrTABCDx = 1;
2454                         sc->atrKCount = 1;
2455 
2456                         /* if there are no TDx following set T0 protocol */
2457                         if (!ISSET(sc->atrY,ATR_Y_TD))
2458                         {
2459                             sc->protocolType    = PROTOCOL_T0;
2460                         }
2461 
2462 
2463                         if (sc->atrY)
2464                         {
2465 
2466                             sc->ATRS = atrsTABCD;
2467                             scrTimeout(ATRSM,sc,atrcTWorkWaiting,T_WORK_WAITING);
2468                             t0RecvByteSM(sc,t0rbcStart);
2469                         }
2470 
2471                         else if (sc->atrK)
2472                         {
2473                             sc->ATRS = atrsTK;
2474                             scrTimeout(ATRSM,sc,atrcTWorkWaiting,T_WORK_WAITING);
2475                             t0RecvByteSM(sc,t0rbcStart);
2476                         }
2477 
2478                         else if (sc->protocolType != PROTOCOL_T0)
2479                         {
2480                             sc->ATRS = atrsTCK;
2481                             scrTimeout(ATRSM,sc,atrcTWorkWaiting,T_WORK_WAITING);
2482                             t0RecvByteSM(sc,t0rbcStart);
2483                         }
2484 
2485                         else /* got all of ATR */
2486                         {
2487                             sc->ATRS = atrsIdle;
2488                             masterSM(sc,mcATR);
2489                         }
2490                     }
2491                     break;
2492 
2493 
2494                 default:
2495                     INVALID_STATE_CMD(sc,sc->ATRS,cmd);
2496                     break;
2497             }
2498             break;
2499 
2500 
2501         case atrsTABCD:
2502             switch (cmd)
2503             {
2504                 case gcT0RecvByte:
2505                     scrUntimeout(ATRSM,sc,atrcTWorkWaiting);
2506                     sc->pIoctlOn->atrBuf[sc->pIoctlOn->atrLen] = sc->dataByte;
2507                     sc->pIoctlOn->atrLen++;
2508                     if(sc->pIoctlOn->atrLen >= ATR_BUF_MAX)
2509                     {
2510                         #ifdef SCR_DEBUG
2511                             printf("atrLen >= ATR_BUF_MAX\n");
2512                             DEBUGGER;
2513                         #endif
2514                         sc->status = ERROR_ATR_TCK;
2515                         sc->ATRS = atrsIdle;
2516                         masterSM(sc,mcATR);
2517                     }
2518                     else
2519                     {
2520                         if (sc->atrY & ATR_Y_TA)
2521                         {
2522                             sc->atrY &= ~ATR_Y_TA;
2523                             if (sc->atrTABCDx == 1)
2524                             {
2525                                 sc->Fi = FI2Fi[((sc->dataByte >> 4) & 0x0f)];
2526                                 if (sc->Fi == 0)
2527                                 {
2528                                     sc->status = ERROR_ATR_FI_INVALID;
2529                                     sc->Fi = Fi_DEFAULT;
2530                                 }
2531 
2532                                 sc->Di = DI2Di[(sc->dataByte & 0x0f)];
2533                                 if (sc->Di == 0)
2534                                 {
2535                                     sc->status = ERROR_ATR_DI_INVALID;
2536                                     sc->Di = Di_DEFAULT;
2537                                 }
2538 
2539                             }
2540                         }
2541 
2542                         else if (sc->atrY & ATR_Y_TB)
2543                         {
2544                             sc->atrY &= ~ATR_Y_TB;
2545                         }
2546 
2547                         else if (sc->atrY & ATR_Y_TC)
2548                         {
2549                             sc->atrY &= ~ATR_Y_TC;
2550                             if (sc->atrTABCDx == 1)
2551                             {
2552                                 sc->N = sc->dataByte;
2553                             }
2554 
2555                             if (sc->atrTABCDx == 2)
2556                             {
2557                                 sc->Wi = sc->dataByte;
2558                             }
2559                         }
2560 
2561                         else
2562                         {
2563                             ASSERT(sc->atrY & ATR_Y_TD);
2564                             sc->atrY &= ~ATR_Y_TD;
2565 
2566                             /* copy across the y section of TD */
2567                             sc->atrY    =    sc->dataByte;
2568                             sc->atrY &= 0xf0;
2569 
2570                             /* step to the next group of TABCD */
2571                             sc->atrTABCDx++;
2572 
2573                             /* store protocols */
2574                             sc->protocolType = (1 << (sc->dataByte &0x0f));
2575                         }
2576 
2577 
2578                         /* see what we should do next */
2579                         if (sc->atrY)
2580                         {
2581                             /* just stay in the same state */
2582                             scrTimeout(ATRSM,sc,atrcTWorkWaiting,T_WORK_WAITING);
2583                             t0RecvByteSM(sc,t0rbcStart);
2584                         }
2585 
2586                         else if (sc->atrK)
2587                         {
2588                             sc->ATRS = atrsTK;
2589                             scrTimeout(ATRSM,sc,atrcTWorkWaiting,T_WORK_WAITING);
2590                             t0RecvByteSM(sc,t0rbcStart);
2591                         }
2592 
2593                         else if (sc->protocolType != PROTOCOL_T0)
2594                         {
2595                             sc->ATRS = atrsTCK;
2596                             scrTimeout(ATRSM,sc,atrcTWorkWaiting,T_WORK_WAITING);
2597                             t0RecvByteSM(sc,t0rbcStart);
2598                         }
2599 
2600                         else /* got all of ATR */
2601                         {
2602                             sc->ATRS = atrsIdle;
2603                             masterSM(sc,mcATR);
2604                         }
2605                     }
2606 
2607                     break;
2608 
2609 
2610                 default:
2611                     INVALID_STATE_CMD(sc,sc->ATRS,cmd);
2612                     break;
2613             }
2614             break;
2615 
2616         case atrsTK:
2617             switch (cmd)
2618             {
2619                 case gcT0RecvByte:
2620                     scrUntimeout(ATRSM,sc,atrcTWorkWaiting);
2621                     sc->pIoctlOn->atrBuf[sc->pIoctlOn->atrLen] = sc->dataByte;
2622                     sc->pIoctlOn->atrLen++;
2623                     if(sc->pIoctlOn->atrLen >= ATR_BUF_MAX)
2624                     {
2625                         #ifdef SCR_DEBUG
2626                             printf("atrLen >= ATR_BUF_MAX\n");
2627                             DEBUGGER;
2628                         #endif
2629                         sc->status = ERROR_ATR_TCK;
2630                         sc->ATRS = atrsIdle;
2631                         masterSM(sc,mcATR);
2632                     }
2633                     else
2634                     {
2635 
2636                         if (sc->atrKCount < sc->atrK)
2637                         {
2638                             sc->atrKCount++;
2639                             scrTimeout(ATRSM,sc,atrcTWorkWaiting,T_WORK_WAITING);
2640                             t0RecvByteSM(sc,t0rbcStart);
2641                         }
2642 
2643 
2644                         else if (sc->protocolType != PROTOCOL_T0)
2645                         {
2646                             sc->ATRS = atrsTCK;
2647                             scrTimeout(ATRSM,sc,atrcTWorkWaiting,T_WORK_WAITING);
2648                             t0RecvByteSM(sc,t0rbcStart);
2649                         }
2650 
2651                         else /* got all of ATR */
2652                         {
2653                             sc->ATRS = atrsIdle;
2654                             masterSM(sc,mcATR);
2655                         }
2656                     }
2657                     break;
2658 
2659                 default:
2660                     INVALID_STATE_CMD(sc,sc->ATRS,cmd);
2661                     break;
2662             }
2663             break;
2664 
2665         case atrsTCK:
2666             switch (cmd)
2667             {
2668                 case gcT0RecvByte:
2669                     scrUntimeout(ATRSM,sc,atrcTWorkWaiting);
2670                     sc->pIoctlOn->atrBuf[sc->pIoctlOn->atrLen] = sc->dataByte;
2671                     sc->pIoctlOn->atrLen++;
2672                     if(sc->pIoctlOn->atrLen >= ATR_BUF_MAX)
2673                     {
2674                         #ifdef SCR_DEBUG
2675                             printf("atrLen >= ATR_BUF_MAX\n");
2676                             DEBUGGER;
2677                         #endif
2678                         sc->status = ERROR_ATR_TCK;
2679                         sc->ATRS = atrsIdle;
2680                         masterSM(sc,mcATR);
2681                     }
2682                     else
2683                     {
2684                         tck = 0;
2685                         for (lc = 1; lc < sc->pIoctlOn->atrLen-1; lc++)
2686                         {
2687                             tck ^= sc->pIoctlOn->atrBuf[lc];
2688                         }
2689 
2690                         if (tck == sc->pIoctlOn->atrBuf[sc->pIoctlOn->atrLen-1])
2691                         {
2692                             sc->ATRS = atrsIdle;
2693                             masterSM(sc,mcATR);
2694                         }
2695                         else
2696                         {
2697                             sc->status = ERROR_ATR_TCK;
2698                             sc->ATRS = atrsIdle;
2699                             masterSM(sc,mcATR);
2700                         }
2701                     }
2702                     break;
2703 
2704                 default:
2705                     INVALID_STATE_CMD(sc,sc->ATRS,cmd);
2706                     break;
2707             }
2708             break;
2709 
2710 
2711 
2712         default:
2713             INVALID_STATE_CMD(sc,sc->ATRS,cmd);
2714             break;
2715     }
2716 }
2717 
2718 
2719 
2720 /*
2721 **++
2722 **  FUNCTIONAL DESCRIPTION:
2723 **
2724 **      t0RecvByteSM
2725 **
2726 **      This state machine attempts to read 1 byte from a card.
2727 **      It is a low level bit-bashing state machine.
2728 **
2729 **      Data from the card is async, so the machine scans at
2730 **      5 times the data rate looking for a state bit.  Once
2731 **      a start bit has been found, it waits for the middle of
2732 **      the bit and starts sampling at the bit rate.
2733 **
2734 **      Several mid level machines can use this machine, so the value
2735 **      sc->t0ByteParent is used to point to back to the mid level machine
2736 **
2737 **
2738 **  FORMAL PARAMETERS:
2739 **
2740 **      sc      -  Pointer to the softc structure.
2741 **      cmd     -  command to this machine
2742 **
2743 **  IMPLICIT INPUTS:
2744 **
2745 **      sc->t0RecvByteS     state of this machine
2746 **      sc->t0ByteParent    mid level machine that started this machine
2747 **
2748 **  IMPLICIT OUTPUTS:
2749 **
2750 **      sc->shiftByte       byte read from the card
2751 **      sc->status          error value if could not read byte
2752 **
2753 **  FUNCTION VALUE:
2754 **
2755 **      nill
2756 **
2757 **  SIDE EFFECTS:
2758 **
2759 **      nill
2760 **--
2761 */
t0RecvByteSM(struct scr_softc * sc,int cmd)2762 static void   t0RecvByteSM(struct scr_softc* sc,int cmd)
2763 {
2764     if (sc->bigTrouble) return;     // david,jim , remove this when dust settles
2765 
2766     if (cmd == t0rbcAbort)
2767     {
2768         /* kill all the timers */
2769         scrUntimeout(t0RecvByteSM, sc,t0rbcTFindStartEdge);
2770         scrUntimeout(t0RecvByteSM, sc,t0rbcTFindStartMid);
2771         scrUntimeout(t0RecvByteSM, sc,t0rbcTClockData);
2772         scrUntimeout(t0RecvByteSM, sc,t0rbcTErrorStart);
2773         scrUntimeout(t0RecvByteSM, sc,t0rbcTErrorStop);
2774 
2775         scrSetDataHighZ();
2776         sc->t0RecvByteS = t0rbsIdle;
2777         return;
2778     }
2779 
2780 
2781     switch (sc->t0RecvByteS)
2782     {
2783         case t0rbsIdle:
2784             switch (cmd)
2785             {
2786                 case t0rbcStart:
2787                     /* set initial conditions */
2788                     sc->shiftBits   = 0;
2789                     sc->shiftByte   = 0;
2790                     sc->shiftParity = 0;
2791                     sc->shiftParityCount = 0;
2792                     scrClkAdj(sc->clkCountStartRecv); /* recv data clock running at 5 times */
2793 
2794                     /* check if start bit is already here */
2795                     //if (scrGetData())
2796                     if (1)
2797                     {
2798                         /* didn't find it, keep looking */
2799                         scrTimeout(t0RecvByteSM,sc,t0rbcTFindStartEdge,sc->clkCountStartRecv);
2800                         sc->t0RecvByteS = t0rbsFindStartEdge;
2801                     }
2802                     else
2803                     {
2804                         /* found start bit, look for mid bit */
2805                         scrTimeout(t0RecvByteSM,sc,t0rbcTFindStartMid,sc->clkCountStartRecv);
2806                         sc->t0RecvByteS = t0rbsFindStartMid;
2807                     }
2808                     break;
2809 
2810 
2811 
2812                 default:
2813                     INVALID_STATE_CMD(sc, sc->t0RecvByteS,cmd);
2814                     break;
2815             }
2816             break;
2817 
2818 
2819         case    t0rbsFindStartEdge:
2820             switch (cmd)
2821             {
2822                 case t0rbcTFindStartEdge:
2823                     if (scrGetData())
2824                     {
2825                         /* didn't find it, keep looking */
2826                         scrTimeout(t0RecvByteSM,sc,t0rbcTFindStartEdge,sc->clkCountStartRecv);
2827                     }
2828                     else
2829                     {
2830                         /* found start bit, look for mid bit */
2831                         scrTimeout(t0RecvByteSM,sc,t0rbcTFindStartMid,sc->clkCountStartRecv * 2);
2832                         sc->t0RecvByteS = t0rbsFindStartMid;
2833                     }
2834                     break;
2835 
2836 
2837                 default:
2838                     INVALID_STATE_CMD(sc, sc->t0RecvByteS,cmd);
2839                     break;
2840             }
2841             break;
2842 
2843         case    t0rbsFindStartMid:
2844             switch (cmd)
2845             {
2846                 case t0rbcTFindStartMid:
2847                     if (scrGetData())
2848                     {
2849                         /* found glitch, so just go back to hunting */
2850                         scrTimeout(t0RecvByteSM,sc,t0rbcTFindStartEdge,sc->clkCountStartRecv);
2851                         sc->t0RecvByteS = t0rbsFindStartEdge;
2852                     }
2853                     else
2854                     {
2855                         /* found start bit, start clocking in data */
2856                         TOGGLE_TEST_PIN();
2857                         scrTimeout(t0RecvByteSM,sc,t0rbcTClockData,sc->clkCountDataRecv);
2858                         sc->t0RecvByteS = t0rbsClockData;
2859                     }
2860                     break;
2861 
2862 
2863                 default:
2864                     INVALID_STATE_CMD(sc, sc->t0RecvByteS,cmd);
2865                     break;
2866             }
2867             break;
2868 
2869 
2870         case    t0rbsClockData:
2871             TOGGLE_TEST_PIN();
2872             switch (cmd)
2873             {
2874                 case t0rbcTClockData:
2875                     if (sc->shiftBits < 8)
2876                     {
2877                         if (sc->convention == CONVENTION_INVERSE ||
2878                             sc->convention == CONVENTION_UNKNOWN)
2879                         {
2880                             /* logic 1 is low, msb is first */
2881                             sc->shiftByte <<= 1;
2882                             sc->shiftByte &=  0xfe;
2883                             if (!scrGetData())
2884                             {
2885                                 sc->shiftByte |= 0x01;
2886                                 sc->shiftParity++;
2887                             }
2888                         }
2889                         else
2890                         {
2891                             ASSERT(sc->convention == CONVENTION_DIRECT);
2892                             /* logic 1 is high, lsb is first */
2893                             sc->shiftByte = sc->shiftByte >> 1;
2894                             sc->shiftByte &=  0x7f;
2895                             if (scrGetData())
2896                             {
2897                                 sc->shiftParity++;
2898                                 sc->shiftByte |= 0x80;
2899                             }
2900                         }
2901                         sc->shiftBits++;
2902 
2903 
2904                         /* in TS byte, check if we have a card that works at 1/2 freq */
2905                         if (sc->convention == CONVENTION_UNKNOWN  &&   /* in TS byte */
2906                             sc->shiftBits == 3 &&                     /* test at bit 3 in word */
2907                             sc->shiftByte == 4 &&                     /* check for 1/2 freq pattern */
2908                             sc->cardFreq  == CARD_FREQ_DEF)           /* only do this if at full freq */
2909                         {
2910                             /* adjust counts down to 1/2 freq */
2911                             sc->cardFreq        = CARD_FREQ_DEF / 2;
2912                             sc->clkCountStartRecv   = sc->clkCountStartRecv *2;
2913                             sc->clkCountDataRecv    = sc->clkCountDataRecv  *2;
2914                             sc->clkCountDataSend    = sc->clkCountDataSend  *2;
2915 
2916 
2917                             /* adjust this so that we have clocked in only first bit of TS */
2918                             sc->shiftParity = 0;
2919                             sc->shiftByte   = 0;
2920                             sc->shiftBits   = 1;
2921 
2922                             scrTimeout(t0RecvByteSM,sc,t0rbcTClockData,(sc->clkCountDataRecv * 3) /4);
2923                         }
2924                         else
2925                         {
2926                             scrTimeout(t0RecvByteSM,sc,t0rbcTClockData,sc->clkCountDataRecv);
2927                         }
2928                     }
2929 
2930                     /* clock in parity bit  */
2931                     else if (sc->shiftBits == 8)
2932                     {
2933                         if (sc->convention == CONVENTION_INVERSE)
2934                         {
2935                             if (!scrGetData())
2936                             {
2937                                 sc->shiftParity++;
2938                             }
2939                         }
2940                         else if (sc->convention == CONVENTION_DIRECT)
2941                         {
2942                             if (scrGetData())
2943                             {
2944                                 sc->shiftParity++;
2945                             }
2946                         }
2947 
2948 
2949                         else
2950                         {
2951                             /* sc->convention not set so sort it out */
2952                             ASSERT(sc->convention == CONVENTION_UNKNOWN);
2953                             if (sc->shiftByte == CONVENIONT_INVERSE_ID && scrGetData())
2954                             {
2955                                 sc->convention = CONVENTION_INVERSE;
2956                                 sc->shiftParity = 0;    /* force good parity */
2957                             }
2958 
2959                             else if (sc->shiftByte == CONVENTION_DIRECT_ID && scrGetData())
2960                             {
2961                                 sc->shiftByte = CONVENTION_DIRECT_FIX;
2962                                 sc->convention = CONVENTION_DIRECT;
2963                                 sc->shiftParity = 0;    /* force good parity */
2964                             }
2965 
2966                             else
2967                             {
2968                                 sc->shiftParity = 1; /* force bad parity */
2969                             }
2970                         }
2971 
2972 
2973                         if ((sc->shiftParity & 01) == 0)
2974                         {
2975                             sc->shiftBits++;
2976                             scrTimeout(t0RecvByteSM,sc,t0rbcTClockData,sc->clkCountDataRecv);
2977                         }
2978                         else
2979                         {
2980                             /* got parity error */
2981                             if (sc->shiftParityCount < PARITY_ERROR_MAX)
2982                             {
2983                                 sc->shiftParityCount++;
2984                                 scrTimeout(t0RecvByteSM,sc,t0rbcTErrorStart,sc->clkCountDataRecv);
2985                                 sc->t0RecvByteS = t0rbsSendError;
2986                             }
2987                             else
2988 
2989                             {
2990                                 /* too many parity errors, just give up on this sc->dataByte */
2991                                 sc->status = ERROR_PARITY;
2992                                 sc->t0RecvByteS = t0rbsIdle;
2993                                 sc->t0ByteParent(sc,gcT0RecvByteErr);
2994                             }
2995                         }
2996                     }
2997 
2998                     else
2999                     {
3000                         sc->dataByte = sc->shiftByte;
3001                         sc->t0RecvByteS = t0rbsIdle;
3002                         sc->t0ByteParent(sc,gcT0RecvByte);
3003                     }
3004                     break;
3005 
3006                 default:
3007                     INVALID_STATE_CMD(sc, sc->t0RecvByteS,cmd);
3008                     break;
3009             }
3010             break;
3011 
3012 
3013         case    t0rbsSendError:
3014             TOGGLE_TEST_PIN();
3015             switch (cmd)
3016             {
3017                 case t0rbcTErrorStart:
3018                     /* start sending error bit */
3019                     scrSetData(false);
3020                     scrTimeout(t0RecvByteSM,sc,t0rbcTErrorStop,sc->clkCountDataRecv * 2);
3021                     break;
3022 
3023                 case t0rbcTErrorStop:
3024                     /* stop sending parity error & reset information*/
3025                     scrSetData(true);
3026                     sc->shiftBits   = 0;
3027                     sc->shiftByte   = 0;
3028                     sc->shiftParity = 0;
3029 
3030                     /* start looking for start bit */
3031                     scrTimeout(t0RecvByteSM,sc,t0rbcTFindStartEdge,1);
3032                     sc->t0RecvByteS = t0rbsFindStartEdge;
3033                     break;
3034 
3035                 default:
3036                     INVALID_STATE_CMD(sc, sc->t0RecvByteS,cmd);
3037                     break;
3038             }
3039             break;
3040 
3041 
3042         default:
3043             INVALID_STATE_CMD(sc, sc->t0RecvByteS,cmd);
3044             break;
3045     }
3046 }
3047 
3048 /*
3049 **++
3050 **  FUNCTIONAL DESCRIPTION:
3051 **
3052 **      t0SendByteSM
3053 **
3054 **      This state machine writes 1 byte to a card.
3055 **      It is a low level bit-bashing state machine.
3056 **
3057 **
3058 **      Several mid level machines can use this machine, so the value
3059 **      sc->t0ByteParent is used to point to back to the mid level machine
3060 **
3061 **  FORMAL PARAMETERS:
3062 **
3063 **      sc      -  Pointer to the softc structure.
3064 **      cmd     -  command to this machine
3065 **
3066 **  IMPLICIT INPUTS:
3067 **
3068 **      sc->t0SendByteS     state of this machine
3069 **      sc->shiftByte       byte to write to the card
3070 **
3071 **  IMPLICIT OUTPUTS:
3072 **
3073 **      sc->status          error value if could not read byte
3074 **
3075 **  FUNCTION VALUE:
3076 **
3077 **      nill
3078 **
3079 **  SIDE EFFECTS:
3080 **
3081 **      nill
3082 **--
3083 */
3084 //int bigTroubleTest = 0;
t0SendByteSM(struct scr_softc * sc,int cmd)3085 static void t0SendByteSM (struct scr_softc * sc,int cmd)
3086 {
3087     //if(bigTroubleTest == 2000)
3088     //{
3089     //    INVALID_STATE_CMD(sc, sc->t0SendByteS,cmd);
3090     //    bigTroubleTest = 0;
3091     //}
3092     //
3093     //bigTroubleTest++;
3094 
3095     if (sc->bigTrouble) return;     // david,jim , remove this when dust settles
3096 
3097     if (cmd == t0sbcAbort)
3098     {
3099         /* kill all the timers */
3100         scrUntimeout(t0SendByteSM, sc, t0sbcTGuardTime);
3101         scrUntimeout(t0SendByteSM, sc, t0sbcTClockData);
3102         scrUntimeout(t0SendByteSM, sc, t0sbcTError);
3103 
3104         scrSetDataHighZ();
3105         return;
3106     }
3107 
3108 
3109     switch (sc->t0SendByteS)
3110     {
3111         case t0sbsIdle:
3112             switch (cmd)
3113             {
3114                 case t0sbcStart:
3115                     /* set initial conditions */
3116                     sc->shiftBits   = 0;
3117                     sc->shiftParity = 0;
3118                     sc->shiftParityCount = 0;
3119                     sc->shiftByte = sc->dataByte;
3120 
3121                     scrClkAdj(sc->clkCountDataSend); /* send data clock running at 1 ETU  */
3122 
3123                     /* check if we have to wait for guard time */
3124                     if (0) /* possible optimization here */
3125                     {
3126                         /* can send start bit now */
3127                         scrTimeout(t0SendByteSM,sc,t0sbcTClockData,sc->clkCountDataSend);
3128                         scrSetData(false);
3129                         sc->t0SendByteS = t0sbsClockData;
3130                     }
3131                     else
3132                     {
3133                         /* need to wait for guard time */
3134                         scrTimeout(t0SendByteSM,sc,t0sbcTGuardTime,sc->clkCountDataSend * (12 + sc->N));
3135                         sc->t0SendByteS = t0sbsWaitGuardTime;
3136 
3137                     }
3138                     break;
3139 
3140                 default:
3141                     INVALID_STATE_CMD(sc, sc->t0SendByteS,cmd);
3142                     break;
3143             }
3144             break;
3145 
3146 
3147         case t0sbsWaitGuardTime:
3148             switch (cmd)
3149             {
3150                 case t0sbcTGuardTime:
3151                     TOGGLE_TEST_PIN();
3152                     /*  set start bit */
3153                     scrTimeout(t0SendByteSM,sc,t0sbcTClockData,sc->clkCountDataSend);
3154                     scrSetData(false);
3155                     sc->t0SendByteS = t0sbsClockData;
3156                     break;
3157 
3158                 default:
3159                     INVALID_STATE_CMD(sc, sc->t0SendByteS,cmd);
3160                     break;
3161             }
3162             break;
3163 
3164 
3165         case t0sbsClockData:
3166             switch (cmd)
3167             {
3168                 case t0sbcTClockData:
3169                     TOGGLE_TEST_PIN();
3170                     /* clock out data bit */
3171                     if (sc->shiftBits < 8)
3172                     {
3173                         if (sc->convention == CONVENTION_INVERSE)
3174                         {
3175                             if (sc->shiftByte & 0x80)
3176                             {
3177                                 scrSetData(false);
3178                                 sc->shiftParity++;
3179                             }
3180                             else
3181                             {
3182                                 scrSetData(true);
3183                             }
3184                             sc->shiftByte = sc->shiftByte << 1;
3185                         }
3186                         else
3187                         {
3188                             ASSERT(sc->convention == CONVENTION_DIRECT);
3189                             if (sc->shiftByte & 0x01)
3190                             {
3191                                 scrSetData(true);
3192                                 sc->shiftParity++;
3193                             }
3194                             else
3195                             {
3196                                 scrSetData(false);
3197                             }
3198                             sc->shiftByte = sc->shiftByte >> 1;
3199                         }
3200                         sc->shiftBits++;
3201                         scrTimeout(t0SendByteSM,sc,t0sbcTClockData,sc->clkCountDataSend);
3202                     }
3203 
3204                     /* clock out parity bit */
3205                     else if (sc->shiftBits == 8)
3206                     {
3207                         if ( ((sc->shiftParity & 0x01) &&  (sc->convention == CONVENTION_INVERSE))  ||
3208                              (!(sc->shiftParity & 0x01) && (sc->convention == CONVENTION_DIRECT))     )
3209                         {
3210                             scrSetData(false);
3211                         }
3212                         else
3213                         {
3214                             scrSetData(true);
3215                         }
3216                         sc->shiftBits++;
3217                         scrTimeout(t0SendByteSM,sc,t0sbcTClockData,sc->clkCountDataSend);
3218                     }
3219 
3220                     /* all data shifted out, move onto next state */
3221                     else
3222                     {
3223                         ASSERT(sc->shiftBits > 8);
3224                         scrSetData(true);
3225                         scrTimeout(t0SendByteSM,sc,t0sbcTError,sc->clkCountDataSend);
3226                         sc->t0SendByteS = t0sbsWaitError;
3227                     }
3228                     break;
3229 
3230                 default:
3231                     INVALID_STATE_CMD(sc, sc->t0SendByteS,cmd);
3232                     break;
3233             }
3234             break;
3235 
3236         case t0sbsWaitError:
3237             switch (cmd)
3238             {
3239                 case t0sbcTError:
3240                     /* no error indicated*/
3241                     if (scrGetData())
3242                     {
3243                         sc->t0SendByteS = t0sbsIdle;
3244                         sc->t0ByteParent(sc,gcT0SendByte);
3245                     }
3246 
3247                     /* got error */
3248                     else
3249                     {
3250                         /* got parity error */
3251                         if (sc->shiftParityCount < PARITY_ERROR_MAX)
3252                         {
3253                             sc->shiftParityCount++;
3254                             scrTimeout(t0SendByteSM,sc,t0sbcTResend,sc->clkCountDataSend * 2);
3255                             sc->t0SendByteS = t0sbsWaitResend;
3256                         }
3257                         else
3258                         {
3259                             /* too many parity errors, just give up on this sc->dataByte */
3260                             sc->status = ERROR_PARITY;
3261                             sc->t0SendByteS = t0sbsIdle;
3262                             sc->t0ByteParent(sc,gcT0SendByteErr);
3263                         }
3264                     }
3265                     break;
3266 
3267                 default:
3268                     INVALID_STATE_CMD(sc, sc->t0SendByteS,cmd);
3269                     break;
3270             }
3271             break;
3272 
3273         case t0sbsWaitResend:
3274             switch (cmd)
3275             {
3276                 case t0sbcTResend:
3277                     sc->shiftBits   = 0;
3278                     sc->shiftParity = 0;
3279                     sc->shiftByte = sc->dataByte;
3280                     /*  set start bit */
3281 
3282                     scrTimeout(t0SendByteSM,sc,t0sbcTClockData,sc->clkCountDataSend);
3283                     scrSetData(false);
3284                     sc->t0SendByteS = t0sbsClockData;
3285                     break;
3286 
3287                 default:
3288                     INVALID_STATE_CMD(sc, sc->t0SendByteS,cmd);
3289                     break;
3290             }
3291             break;
3292 
3293 
3294         default:
3295             INVALID_STATE_CMD(sc, sc->t0SendByteS,cmd);
3296             break;
3297     }
3298 }
3299 
3300 
3301 
3302 
3303 
3304 
3305 
3306 
3307 
3308 
3309 
3310 /*
3311 **++
3312 **  FUNCTIONAL DESCRIPTION:
3313 **
3314 **      cardOff
3315 **
3316 **      Turn all signals to the card off
3317 **
3318 **  FORMAL PARAMETERS:
3319 **
3320 **      sc      -  Pointer to the softc structure.
3321 **
3322 **  IMPLICIT INPUTS:
3323 **
3324 **      nill
3325 **
3326 **  IMPLICIT OUTPUTS:
3327 **
3328 **      nill
3329 **
3330 **  FUNCTION VALUE:
3331 **
3332 **      nill
3333 **
3334 **  SIDE EFFECTS:
3335 **
3336 **      nill
3337 **--
3338 */
cardOff(struct scr_softc * sc)3339 static void   cardOff  (struct scr_softc * sc)
3340 {
3341     scrSetReset(true);
3342     scrSetDataHighZ();
3343     scrSetClock(false);
3344     scrSetPower(false);
3345 }
3346 
3347 
3348 
3349 
3350 /*
3351 **
3352 **
3353 **    **************** timer routines ***************
3354 **
3355 */
3356 
3357 /*
3358 **++
3359 **  FUNCTIONAL DESCRIPTION:
3360 **
3361 **      scrClkInit
3362 **
3363 **      Init the callout queues.  The callout queues are used
3364 **      by the timeout/untimeout queues
3365 **
3366 **  FORMAL PARAMETERS:
3367 **
3368 **      nill
3369 **
3370 **  IMPLICIT INPUTS:
3371 **
3372 **      nill
3373 **
3374 **  IMPLICIT OUTPUTS:
3375 **
3376 **      nill
3377 **
3378 **  FUNCTION VALUE:
3379 **
3380 **      nill
3381 **
3382 **  SIDE EFFECTS:
3383 **
3384 **      nill
3385 **--
3386 */
scrClkInit(void)3387 static void scrClkInit(void)
3388 {
3389 
3390     int lc;
3391     Callout *c;
3392     Callout *new;
3393 
3394     scrClkCallTodo.c_next = NULL;
3395     scrClkCallFree = &scrClkCalloutArray[0];
3396     c = scrClkCallFree;
3397 
3398     for (lc = 1; lc < SCR_CLK_CALLOUT_COUNT; lc++)
3399     {
3400         new = &scrClkCalloutArray[lc];
3401         c->c_next = new;
3402         c = new;
3403     }
3404 
3405     c->c_next = NULL;
3406 }
3407 
3408 
3409 /*
3410 **++
3411 **  FUNCTIONAL DESCRIPTION:
3412 **
3413 **      scrClkStart
3414 **
3415 **      This function starts the clock running.  The clock is reall the
3416 **      HAT clock (High Available Timer) that is using a FIQ (fast interrupt
3417 **      request).
3418 **
3419 **  FORMAL PARAMETERS:
3420 **
3421 **      sc              -  Pointer to the softc structure.
3422 **      countPerTick    -  value for T2 timer  that drives FIQ
3423 **
3424 **  IMPLICIT INPUTS:
3425 **
3426 **      nill
3427 **
3428 **  IMPLICIT OUTPUTS:
3429 **
3430 **      nill
3431 **
3432 **  FUNCTION VALUE:
3433 **
3434 **      nill
3435 **
3436 **  SIDE EFFECTS:
3437 **
3438 **      nill
3439 **--
3440 */
scrClkStart(struct scr_softc * sc,int countPerTick)3441 static void scrClkStart(struct scr_softc * sc,int countPerTick)
3442 {
3443     u_int savedInts;
3444 
3445     savedInts = disable_interrupts(I32_bit | F32_bit);
3446 
3447 
3448 
3449     ASSERT(scrClkCallTodo.c_next == NULL);
3450     ASSERT(!scrClkEnable);
3451     scrClkEnable = 1;
3452     scrClkCount = countPerTick;
3453 
3454     hatClkOn(countPerTick,
3455              hatClkIrq,
3456              0xdeadbeef,
3457              hatStack + HATSTACKSIZE - sizeof(unsigned),
3458              myHatWedge);
3459 
3460     restore_interrupts(savedInts);
3461 }
3462 
3463 /*
3464 **++
3465 **  FUNCTIONAL DESCRIPTION:
3466 **
3467 **      scrClkAdj
3468 **
3469 **      Adjusts the frequence of the clock
3470 **
3471 **  FORMAL PARAMETERS:
3472 **
3473 **      count   -  new value for T2 timer that drives FIQ
3474 **
3475 **  IMPLICIT INPUTS:
3476 **
3477 **      nill
3478 **
3479 **  IMPLICIT OUTPUTS:
3480 **
3481 **      nill
3482 **
3483 **  FUNCTION VALUE:
3484 **
3485 **      nill
3486 **
3487 **  SIDE EFFECTS:
3488 **
3489 **      nill
3490 **--
3491 */
scrClkAdj(int count)3492 static void scrClkAdj (int count)
3493 {
3494     u_int savedInts;
3495 
3496     if (count != scrClkCount)
3497     {
3498         savedInts = disable_interrupts(I32_bit | F32_bit);
3499 
3500         ASSERT(scrClkEnable);
3501 
3502         scrClkCount = count;
3503         hatClkAdjust(count);
3504 
3505         restore_interrupts(savedInts);
3506     }
3507 }
3508 
3509 /*
3510 **++
3511 **  FUNCTIONAL DESCRIPTION:
3512 **
3513 **      scrClkStop
3514 **
3515 **      Stops the clock
3516 **
3517 **  FORMAL PARAMETERS:
3518 **
3519 **      nill
3520 **
3521 **
3522 **  IMPLICIT INPUTS:
3523 **
3524 **      nill
3525 **
3526 **  IMPLICIT OUTPUTS:
3527 **
3528 **      nill
3529 **
3530 **  FUNCTION VALUE:
3531 **
3532 **      nill
3533 **
3534 **  SIDE EFFECTS:
3535 **
3536 **      nill
3537 **--
3538 */
scrClkStop(void)3539 static void scrClkStop(void)
3540 {
3541     u_int savedInts;
3542     savedInts = disable_interrupts(I32_bit | F32_bit);
3543 
3544     ASSERT(scrClkEnable);
3545     scrClkEnable = 0;
3546     ASSERT(scrClkCallTodo.c_next == NULL);
3547     hatClkOff();
3548 
3549     restore_interrupts(savedInts);
3550 }
3551 
3552 
3553 
3554 /*
3555 **++
3556 **  FUNCTIONAL DESCRIPTION:
3557 **
3558 **      hatClkIrq
3559 **
3560 **      This is what the HAT clock calls.   This call drives
3561 **      the timeout queues, which in turn drive the state machines
3562 **
3563 **      Be very carefully when calling a timeout as the function
3564 **      that is called may in turn do timeout/untimeout calls
3565 **      before returning
3566 **
3567 **  FORMAL PARAMETERS:
3568 **
3569 **      int x       - not used
3570 **
3571 **  IMPLICIT INPUTS:
3572 **
3573 **      nill
3574 **
3575 **  IMPLICIT OUTPUTS:
3576 **
3577 **      nill
3578 **
3579 **  FUNCTION VALUE:
3580 **
3581 **      nill
3582 **
3583 **  SIDE EFFECTS:
3584 **
3585 **      a timeout may be called if it is due
3586 **--
3587 */
hatClkIrq(int x)3588 static void hatClkIrq(int  x)
3589 {
3590     register Callout *p1;
3591     register int needsoft =0;
3592     register Callout *c;
3593     register int arg;
3594     register void (*func)(struct scr_softc*,int);
3595     struct scr_softc * sc;
3596 
3597     ASSERT(scrClkEnable);
3598     for (p1 = scrClkCallTodo.c_next; p1 != NULL; p1 = p1->c_next)
3599     {
3600         p1->c_time -= scrClkCount;
3601 
3602         if (p1->c_time > 0)
3603         {
3604             break;
3605         }
3606         needsoft = 1;
3607         if (p1->c_time == 0)
3608         {
3609             break;
3610         }
3611     }
3612 
3613 
3614     if (needsoft)
3615     {
3616         while ((c = scrClkCallTodo.c_next) != NULL && c->c_time <= 0)
3617         {
3618             func = c->c_func;
3619             sc = c->c_sc;
3620             arg = c->c_arg;
3621             scrClkCallTodo.c_next = c->c_next;
3622             c->c_next = scrClkCallFree;
3623             scrClkCallFree = c;
3624             (*func)(sc,arg);
3625         }
3626     }
3627 }
3628 
3629 /*
3630 **++
3631 **  FUNCTIONAL DESCRIPTION:
3632 **
3633 **      myHatWedge
3634 **
3635 **      Called if the HAT timer becomes clogged/wedged.  Not
3636 **      used by this driver, we let upper layers recover
3637 **      from this condition
3638 **
3639 **  FORMAL PARAMETERS:
3640 **
3641 **      int nFIQs - not used
3642 **
3643 **  IMPLICIT INPUTS:
3644 **
3645 **      nill
3646 **
3647 **  IMPLICIT OUTPUTS:
3648 **
3649 **      nill
3650 **
3651 **  FUNCTION VALUE:
3652 **
3653 **      nill
3654 **
3655 **  SIDE EFFECTS:
3656 **
3657 **      nill
3658 **--
3659 */
myHatWedge(int nFIQs)3660 static void myHatWedge(int nFIQs)
3661 {
3662     #ifdef DEBUG
3663         printf("myHatWedge: nFIQ = %d\n",nFIQs);
3664     #endif
3665 }
3666 
3667 
3668 
3669 /*
3670 **++
3671 **  FUNCTIONAL DESCRIPTION:
3672 **
3673 **      scrTimeout
3674 **
3675 **	    Execute a function after a specified length of time.
3676 **
3677 **
3678 **  FORMAL PARAMETERS:
3679 **
3680 **      ftn     -   function to execute
3681 **      sc      -   pointer to soft c
3682 **      arg     -   argument passed to function
3683 **      count   -   number of T2 counts for timeout
3684 **
3685 **  IMPLICIT INPUTS:
3686 **
3687 **      nill
3688 **
3689 **  IMPLICIT OUTPUTS:
3690 **
3691 **      nill
3692 **
3693 **  FUNCTION VALUE:
3694 **
3695 **      nill
3696 **
3697 **  SIDE EFFECTS:
3698 **
3699 **      nill
3700 **--
3701 */
3702 
3703 static void
scrTimeout(void (* ftn)(struct scr_softc *,int),struct scr_softc * sc,int arg,int count)3704 scrTimeout(
3705     void (*ftn)(struct scr_softc*,int),
3706     struct scr_softc* sc,
3707     int arg,
3708     int count)
3709 {
3710 
3711     register Callout *new, *p, *t;
3712     ASSERT(scrClkEnable);
3713 
3714 
3715     if (count <= 0)
3716     {
3717         count = 1;
3718     }
3719 
3720 
3721     /* Fill in the next free fcallout structure. */
3722     if (scrClkCallFree == NULL)
3723     {
3724         panic("timeout table full");
3725     }
3726 
3727     new = scrClkCallFree;
3728     scrClkCallFree = new->c_next;
3729     new->c_sc  = sc;
3730     new->c_arg = arg;
3731     new->c_func = ftn;
3732 
3733     /*
3734      * The time for each event is stored as a difference from the time
3735      * of the previous event on the queue.  Walk the queue, correcting
3736      * the counts argument for queue entries passed.  Correct the counts
3737      * value for the queue entry immediately after the insertion point
3738      * as well.  Watch out for negative c_time values; these represent
3739      * overdue events.
3740      */
3741     for (p = &scrClkCallTodo; (t = p->c_next) != NULL && count > t->c_time; p = t)
3742     {
3743         if (t->c_time > 0)
3744         {
3745             count -= t->c_time;
3746         }
3747     }
3748 
3749 
3750     new->c_time = count;
3751     if (t != NULL)
3752     {
3753         t->c_time -= count;
3754     }
3755 
3756     /* Insert the new entry into the queue. */
3757     p->c_next = new;
3758     new->c_next = t;
3759 }
3760 
3761 /*
3762 **++
3763 **  FUNCTIONAL DESCRIPTION:
3764 **
3765 **      scrUntimeout
3766 **
3767 **	    Cancel previous timeout function call.
3768 **
3769 **  FORMAL PARAMETERS:
3770 **
3771 **      ftn     - function of timeout to cancel
3772 **      sc      - sc  of timeout to cancel
3773 **      arg     - arg of timeout to cancel
3774 **
3775 **  IMPLICIT INPUTS:
3776 **
3777 **      nill
3778 **
3779 **  IMPLICIT OUTPUTS:
3780 **
3781 **      nill
3782 **
3783 **  FUNCTION VALUE:
3784 **
3785 **      nill
3786 **
3787 **  SIDE EFFECTS:
3788 **
3789 **      nill
3790 **--
3791 */
3792 static void
scrUntimeout(void (* ftn)(struct scr_softc *,int),struct scr_softc * sc,int arg)3793 scrUntimeout(
3794     void (*ftn)(struct scr_softc*, int),
3795     struct scr_softc* sc,
3796     int arg)
3797 {
3798     register Callout *p, *t;
3799     ASSERT(scrClkEnable);
3800 
3801     for (p = &scrClkCallTodo; (t = p->c_next) != NULL; p = t)
3802     {
3803         if (t->c_func == ftn && t->c_sc == sc && t->c_arg == arg)
3804         {
3805             /* Increment next entry's count. */
3806             if (t->c_next && t->c_time > 0)
3807             {
3808                 t->c_next->c_time += t->c_time;
3809             }
3810 
3811             /* Move entry from fcallout queue to scrClkCallFree queue. */
3812             p->c_next = t->c_next;
3813             t->c_next = scrClkCallFree;
3814             scrClkCallFree = t;
3815             break;
3816         }
3817     }
3818 }
3819 
3820 
3821 
3822 
3823 
3824 
3825 
3826 
3827 
3828 
3829 
3830 
3831 
3832 
3833 
3834 /******************* routines used only during debugging */
3835 #ifdef SCR_DEBUG
3836 
3837 /*
3838 **++
3839 **  FUNCTIONAL DESCRIPTION:
3840 **
3841 **      invalidStateCmd
3842 **
3843 **      Debugging function.  Printout information about problem
3844 **      and then kick in the debugger or panic
3845 **
3846 **  FORMAL PARAMETERS:
3847 **
3848 **      sc      - pointer to soft c
3849 **      state   - state of machine
3850 **      cmd     - command of machine
3851 **      line    - line that problem was detected
3852 **
3853 **
3854 **  IMPLICIT INPUTS:
3855 **
3856 **      nill
3857 **
3858 **  IMPLICIT OUTPUTS:
3859 **
3860 **      nill
3861 **
3862 **  FUNCTION VALUE:
3863 **
3864 **      nill
3865 **
3866 **  SIDE EFFECTS:
3867 **
3868 **      nill
3869 **--
3870 */
invalidStateCmd(struct scr_softc * sc,int state,int cmd,int line)3871 void invalidStateCmd (struct scr_softc* sc,int state,int cmd,int line)
3872 {
3873     printf("INVALID_STATE_CMD: sc = %X, state = %X, cmd = %X, line = %d\n",sc,state,cmd,line);
3874     DEBUGGER;
3875 }
3876 
3877 /*
3878 **++
3879 **  FUNCTIONAL DESCRIPTION:
3880 **
3881 **      getText
3882 **
3883 **      Get text representation of state or command
3884 **
3885 **  FORMAL PARAMETERS:
3886 **
3887 **      x   - state or command
3888 **
3889 **  IMPLICIT INPUTS:
3890 **
3891 **      nill
3892 **
3893 **  IMPLICIT OUTPUTS:
3894 **
3895 **      nill
3896 **
3897 **  FUNCTION VALUE:
3898 **
3899 **      nill
3900 **
3901 **  SIDE EFFECTS:
3902 **
3903 **      nill
3904 **--
3905 */
getText(int x)3906 char * getText(int x)
3907 {
3908     switch (x)
3909     {
3910             /* commands to Master State Machine (mc = Master Command )*/
3911         case    mcOn:               return "mcOn";
3912         case    mcT0DataSend:       return "mcT0DataSend";
3913         case    mcT0DataRecv:       return "mcT0DataRecv";
3914         case    mcColdReset:        return "mcColdReset";
3915         case    mcATR:              return "mcATR";
3916         case    mcT0Send:           return "mcT0Send";
3917         case    mcT0Recv:           return "mcT0Recv";
3918 
3919             /* states in Master state machine (ms = Master State) */
3920         case    msIdleOff:          return "msIdleOff";
3921         case    msColdReset:        return "msColdReset";
3922         case    msATR:              return "msATR";
3923         case    msIdleOn:           return "msIdleOn";
3924         case    msT0Send:           return "msT0Send";
3925         case    msT0Recv:           return "msT0Recv";
3926 
3927 
3928 
3929             /* commands to T0 send state machine */
3930         case    t0scStart:          return "t0scStart";
3931         case    t0scTWorkWaiting:   return "t0scTWorkWaiting";
3932 
3933 
3934             /* states in T0 send state machine */
3935         case    t0ssIdle:           return "t0ssIdle";
3936         case    t0ssSendHeader:     return "t0ssSendHeader";
3937         case    t0ssRecvProcedure:  return "t0ssRecvProcedu";
3938         case    t0ssSendByte:       return "t0ssSendByte";
3939         case    t0ssSendData:       return "t0ssSendData";
3940         case    t0ssRecvSW1:        return "t0ssRecvSW1";
3941         case    t0ssRecvSW2:        return "t0ssRecvSW2";
3942 
3943 
3944             /* commands to T0 recv state machine */
3945         case t0rcStart:             return "t0rcStart";
3946         case t0rcTWorkWaiting:      return "t0rcTWorkWaiting";
3947 
3948             /* states in T0 recv state machine */
3949         case t0rsIdle:              return "t0rsIdle";
3950         case t0rsSendHeader:        return "t0rsSendHeader";
3951         case t0rsRecvProcedure:     return "t0rsRecvProcedure";
3952         case t0rsRecvByte:          return "t0rsRecvByte";
3953         case t0rsRecvData:          return "t0rsRecvData";
3954         case t0rsRecvSW1:           return "t0rsRecvSW1";
3955         case t0rsRecvSW2:           return "t0rsRecvSW2";
3956 
3957 
3958 
3959 
3960 
3961             /* commands to Answer To Reset (ATR) state machine */
3962         case    atrcStart:      return "atrcStart";
3963         case    atrcT3:         return "0x0b04";
3964         case    atrcTWorkWaiting: return "atrcTWorkWaiting";
3965 
3966 
3967             /* states in in Anser To Reset (ATR) state machine */
3968         case    atrsIdle:        return "atrsIdle";
3969         case    atrsTS:          return "atrsTS";
3970         case    atrsT0:          return "atrsT0";
3971         case    atrsTABCD:       return "atrsTABCD";
3972         case    atrsTK:          return "atrsTK";
3973         case    atrsTCK:         return "atrsTCK";
3974 
3975 
3976 
3977             /* commands to T0 Recv Byte state machine */
3978         case    t0rbcStart:         return "t0rbcStart";
3979         case    t0rbcAbort:         return "t0rbcAbort";
3980 
3981         case    t0rbcTFindStartEdge:return "t0rbcTFindStartEdge";
3982         case    t0rbcTFindStartMid: return "t0rbcTFindStartMid";
3983         case    t0rbcTClockData:    return "t0rbcTClockData";
3984         case    t0rbcTErrorStart:   return "t0rbcTErrorStart";
3985         case    t0rbcTErrorStop:    return "t0rbcTErrorStop";
3986 
3987             /* states in in TO Recv Byte state machine */
3988         case    t0rbsIdle:          return "t0rbsIdle";
3989         case    t0rbsFindStartEdge: return "t0rbcFindStartEdge";
3990         case    t0rbsFindStartMid:  return "t0rbcFindStartMid";
3991         case    t0rbsClockData:     return "t0rbcClockData";
3992         case    t0rbsSendError:     return "t0rbcSendError";
3993 
3994 
3995             /* commands to T0 Send Byte  state machine */
3996         case    t0sbcStart:         return "t0sbcStart";
3997         case    t0sbcAbort:         return "t0sbcAbort";
3998         case    t0sbcTGuardTime:    return "t0sbcTGuardTime";
3999         case    t0sbcTClockData:    return "t0sbcTClockData";
4000         case    t0sbcTError:        return "t0sbcTError";
4001         case    t0sbcTResend:       return "t0sbcTResend";
4002 
4003             /* states in in T0 Send Byte state machine */
4004         case    t0sbsIdle:          return "t0sbsIdle";
4005         case    t0sbsClockData:     return "t0sbsClockData";
4006         case    t0sbsWaitError:     return "t0sbsWaitError";
4007         case    t0sbsWaitResend:    return "t0sbsWaitResend";
4008         case    t0sbsWaitGuardTime: return "t0sbsWaitGuardTime";
4009 
4010 
4011         case    gcT0RecvByte:       return     "gcT0RecvByte";
4012         case gcT0RecvByteErr:       return "gcT0RecvByteErr";
4013         case gcT0SendByte:          return "gcT0SendByte";
4014         case gcT0SendByteErr:       return "gcT0SendByteErr";
4015 
4016 
4017         case crcStart:              return "crcStart";
4018         case crcT2:                 return "crcT2";
4019 
4020 
4021         default:
4022             printf("unknown case, %x\n",x);
4023             break;
4024     }
4025     return "???";
4026 }
4027 
4028 #endif /*  SCR_DEBUG */
4029