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