~ubuntu-branches/ubuntu/jaunty/pcsc-lite/jaunty-security

« back to all changes in this revision

Viewing changes to src/atrhandler.c

  • Committer: Bazaar Package Importer
  • Author(s): Ludovic Rousseau
  • Date: 2004-06-13 21:45:56 UTC
  • mfrom: (1.1.1 upstream)
  • mto: This revision was merged to the branch mainline in revision 3.
  • Revision ID: james.westby@ubuntu.com-20040613214556-zio7hrzkz9wwtffx
Tags: 1.2.9-beta2-2
* debian/rules: add -lpthread to LDFLAGS so that pthread_* symbols are
  included in the library (problem only seen on mips and mipsel).
  Closes: #253629
* debian/control: make libpcsclite-dev and libpcsclite1 at Priority:
  optional so that other packages at Priority: optional can use them.
  Closes: #249374

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/******************************************************************
2
 
 
3
 
        MUSCLE SmartCard Development ( http://www.linuxnet.com )
4
 
            Title  : atrhandler.c
5
 
            Author : David Corcoran
6
 
            Date   : 7/27/99
7
 
            License: Copyright (C) 1999 David Corcoran
8
 
                     <corcoran@linuxnet.com> 
9
 
            Purpose: This keeps track of smartcard protocols,
10
 
                     timing issues, and atr handling.
11
 
 
12
 
********************************************************************/ 
 
1
/*
 
2
 * This keeps track of smartcard protocols, timing issues
 
3
 * and ATR handling.
 
4
 *
 
5
 * MUSCLE SmartCard Development ( http://www.linuxnet.com )
 
6
 *
 
7
 * Copyright (C) 1999
 
8
 *  David Corcoran <corcoran@linuxnet.com>
 
9
 *
 
10
 * $Id: atrhandler.c,v 1.6 2003/10/18 17:19:36 aet-guest Exp $
 
11
 */
13
12
 
 
13
#include "config.h"
14
14
#include <syslog.h>
 
15
#include <string.h>
15
16
 
16
 
#include "config.h"
17
17
#include "wintypes.h"
18
18
#include "pcsclite.h"
19
19
#include "atrhandler.h"
20
20
 
21
 
/* Uncomment the following for ATR debugging */
22
 
/* #define ATR_DEBUG 1 */
23
 
 
24
 
short ATRDecodeAtr( PSMARTCARD_EXTENSION psExtension, 
25
 
                    PUCHAR pucAtr, DWORD dwLength ) {
26
 
 
27
 
  USHORT p;
28
 
  UCHAR K, TCK;                     /* MSN of T0/Check Sum     */
29
 
  UCHAR Y1i, T;                     /* MSN/LSN of TDi          */
30
 
  short TAi, TBi, TCi, TDi;         /* Interface characters    */
31
 
 
32
 
  /* Zero out everything */
33
 
  p = K = TCK = Y1i = T = TAi = TBi = TCi = TDi = 0;
34
 
 
35
 
  if ( dwLength < 2 ) {
36
 
    return 0;                       /* Atr must have TS and T0 */
37
 
  }
38
 
 
39
 
  /* Zero out the bitmasks */
40
 
 
41
 
  psExtension->CardCapabilities.AvailableProtocols = 0x00;
42
 
  psExtension->CardCapabilities.CurrentProtocol    = 0x00;
43
 
 
44
 
  /* Decode the TS byte */
45
 
 
46
 
  if ( pucAtr[0] == 0x3F ) {        /* Inverse convention used */
47
 
    psExtension->CardCapabilities.Convention = SCARD_CONVENTION_INVERSE;
48
 
  } else if ( pucAtr[0] == 0x3B ) { /* Direct convention used  */
49
 
    psExtension->CardCapabilities.Convention = SCARD_CONVENTION_DIRECT;
50
 
  } else {
51
 
    memset( psExtension, 0x00, sizeof(SMARTCARD_EXTENSION) );
52
 
    return 0;
53
 
  }
54
 
 
55
 
  /* Here comes the platform dependant stuff */
56
 
 
57
 
                                     /* Decode the T0 byte      */
58
 
  Y1i = pucAtr[1] >> 4;              /* Get the MSN in Y1       */
59
 
  K   = pucAtr[1] & 0x0F;            /* Get the LSN in K        */
60
 
 
61
 
  p = 2;
62
 
 
63
 
#ifdef ATR_DEBUG
64
 
#ifdef USE_SYSLOG
65
 
  syslog( LOG_DEBUG, " Conv %02X, Y1 %02X, K %02X", 
66
 
          psExtension->CardCapabilities.Convention, Y1i, K );
67
 
#else
68
 
  printf(" Conv %02X, Y1 %02X, K %02X\n", psExtension->CardCapabilities.Convention, 
69
 
         Y1i, K );
70
 
#endif
71
 
#endif
72
 
 
73
 
  /* Examine Y1 */
74
 
 
75
 
  do {
76
 
    
77
 
    TAi = (Y1i & 0x01) ? pucAtr[p++] : -1;
78
 
    TBi = (Y1i & 0x02) ? pucAtr[p++] : -1;
79
 
    TCi = (Y1i & 0x04) ? pucAtr[p++] : -1;
80
 
    TDi = (Y1i & 0x08) ? pucAtr[p++] : -1;
81
 
    
82
 
#ifdef ATR_DEBUG
83
 
#ifdef USE_SYSLOG
84
 
    syslog( LOG_DEBUG, " T's %02X %02X %02X %02X", TAi, TBi, TCi, TDi );
85
 
    syslog( LOG_DEBUG, " P %02X", p );
86
 
#else
87
 
    printf(" T's %02X %02X %02X %02X\n", TAi, TBi, TCi, TDi );
88
 
    printf(" P %02X\n", p);
89
 
#endif
90
 
#endif    
91
 
 
92
 
    /* Examine TDi to determine protocol and more */
93
 
    if ( TDi >= 0 ) {
94
 
      Y1i = TDi >> 4;              /* Get the MSN in Y1       */
95
 
      T   = TDi & 0x0F;            /* Get the LSN in K        */
96
 
      
97
 
    /* Set the current protocol TD1               */
98
 
      if ( psExtension->CardCapabilities.CurrentProtocol == 0x00 ) {
99
 
        switch( T ) {
100
 
        case 0:
101
 
          psExtension->CardCapabilities.CurrentProtocol = SCARD_PROTOCOL_T0;
102
 
          break;
103
 
        case 1:
104
 
          psExtension->CardCapabilities.CurrentProtocol = SCARD_PROTOCOL_T1;
105
 
          break;
106
 
        default:
107
 
          return 0;
108
 
        }
109
 
      }
110
 
 
111
 
      if ( T == 0 ) {
112
 
#ifdef ATR_DEBUG
113
 
#ifdef USE_SYSLOG
114
 
        syslog( LOG_DEBUG, "T=0 Protocol Found" );
115
 
#else
116
 
        printf("T=0 Protocol Found\n");
117
 
#endif
118
 
#endif
119
 
        psExtension->CardCapabilities.AvailableProtocols |= SCARD_PROTOCOL_T0;
120
 
        psExtension->CardCapabilities.T0.BGT = 0 ;
121
 
        psExtension->CardCapabilities.T0.BWT = 0;
122
 
        psExtension->CardCapabilities.T0.CWT = 0;
123
 
        psExtension->CardCapabilities.T0.CGT = 0;
124
 
        psExtension->CardCapabilities.T0.WT  = 0;
125
 
      } else if ( T == 1 ) {
126
 
#ifdef ATR_DEBUG
127
 
#ifdef USE_SYSLOG
128
 
        syslog( LOG_DEBUG, "T=1 Protocol Found" );
129
 
#else
130
 
        printf("T=1 Protocol Found\n");
131
 
#endif
132
 
#endif
133
 
        psExtension->CardCapabilities.AvailableProtocols |= SCARD_PROTOCOL_T1;
134
 
        psExtension->CardCapabilities.T1.BGT = 0 ;
135
 
        psExtension->CardCapabilities.T1.BWT = 0;
136
 
        psExtension->CardCapabilities.T1.CWT = 0;
137
 
        psExtension->CardCapabilities.T1.CGT = 0;
138
 
        psExtension->CardCapabilities.T1.WT  = 0;
139
 
      } else {
140
 
        psExtension->CardCapabilities.AvailableProtocols |= T;
141
 
        /* Do nothing for now since other protocols
142
 
           are not supported at this time            */
143
 
      }
144
 
      
145
 
    } else {
146
 
      Y1i = 0;
147
 
    }
148
 
  
149
 
  if ( p > MAX_ATR_SIZE ) {
150
 
    memset( psExtension, 0x00, sizeof(SMARTCARD_EXTENSION) );
151
 
    return 0;
152
 
  }    
153
 
 
154
 
  } while ( Y1i != 0 );
155
 
 
156
 
  /* If TDx is not set then the current must be T0 */
157
 
  if ( psExtension->CardCapabilities.CurrentProtocol == 0x00 ) {
158
 
    psExtension->CardCapabilities.CurrentProtocol     = SCARD_PROTOCOL_T0;
159
 
    psExtension->CardCapabilities.AvailableProtocols |= SCARD_PROTOCOL_T0;
160
 
  }
161
 
 
162
 
  /* Take care of the historical characters */
163
 
 
164
 
  psExtension->ATR.HistoryLength = K;
165
 
  memcpy( psExtension->ATR.HistoryValue, &pucAtr[p], K );
166
 
  
167
 
  p = p + K;
168
 
 
169
 
  /* Check to see if TCK character is included It will 
170
 
     be included if more than T=0 is supported         */
171
 
 
172
 
  if ( psExtension->CardCapabilities.AvailableProtocols & 
173
 
       SCARD_PROTOCOL_T1 ) 
174
 
  {
175
 
    TCK = pucAtr[p++];
176
 
  }
177
 
 
178
 
  memcpy( psExtension->ATR.Value, pucAtr, p );
179
 
  psExtension->ATR.Length = p;  /* modified from p-1 */
180
 
 
181
 
  return 1;
 
21
/*
 
22
 * Uncomment the following for ATR debugging 
 
23
 */
 
24
/*
 
25
 * #define ATR_DEBUG 1 
 
26
 */
 
27
 
 
28
short ATRDecodeAtr(PSMARTCARD_EXTENSION psExtension,
 
29
        PUCHAR pucAtr, DWORD dwLength)
 
30
{
 
31
 
 
32
        USHORT p;
 
33
        UCHAR K, TCK;                           /* MSN of T0/Check Sum */
 
34
        UCHAR Y1i, T;                           /* MSN/LSN of TDi */
 
35
        short TAi, TBi, TCi, TDi;       /* Interface characters */
 
36
 
 
37
        /*
 
38
         * Zero out everything 
 
39
         */
 
40
        p = K = TCK = Y1i = T = TAi = TBi = TCi = TDi = 0;
 
41
 
 
42
        if (dwLength < 2)
 
43
        {
 
44
                return 0;       /* Atr must have TS and T0 */
 
45
        }
 
46
 
 
47
        /*
 
48
         * Zero out the bitmasks 
 
49
         */
 
50
 
 
51
        psExtension->CardCapabilities.AvailableProtocols = 0x00;
 
52
        psExtension->CardCapabilities.CurrentProtocol = 0x00;
 
53
 
 
54
        /*
 
55
         * Decode the TS byte 
 
56
         */
 
57
 
 
58
        if (pucAtr[0] == 0x3F)
 
59
        {       /* Inverse convention used */
 
60
                psExtension->CardCapabilities.Convention =
 
61
                        SCARD_CONVENTION_INVERSE;
 
62
        } else if (pucAtr[0] == 0x3B)
 
63
        {       /* Direct convention used */
 
64
                psExtension->CardCapabilities.Convention = SCARD_CONVENTION_DIRECT;
 
65
        } else
 
66
        {
 
67
                memset(psExtension, 0x00, sizeof(SMARTCARD_EXTENSION));
 
68
                return 0;
 
69
        }
 
70
 
 
71
        /*
 
72
         * Here comes the platform dependant stuff 
 
73
         */
 
74
 
 
75
        /*
 
76
         * Decode the T0 byte 
 
77
         */
 
78
        Y1i = pucAtr[1] >> 4;   /* Get the MSN in Y1 */
 
79
        K = pucAtr[1] & 0x0F;   /* Get the LSN in K */
 
80
 
 
81
        p = 2;
 
82
 
 
83
#ifdef ATR_DEBUG
 
84
        debug_msg("Conv %02X, Y1 %02X, K %02X",
 
85
                psExtension->CardCapabilities.Convention, Y1i, K);
 
86
#endif
 
87
 
 
88
        /*
 
89
         * Examine Y1 
 
90
         */
 
91
 
 
92
        do
 
93
        {
 
94
 
 
95
                TAi = (Y1i & 0x01) ? pucAtr[p++] : -1;
 
96
                TBi = (Y1i & 0x02) ? pucAtr[p++] : -1;
 
97
                TCi = (Y1i & 0x04) ? pucAtr[p++] : -1;
 
98
                TDi = (Y1i & 0x08) ? pucAtr[p++] : -1;
 
99
 
 
100
#ifdef ATR_DEBUG
 
101
                debug_msg("T's %02X %02X %02X %02X", TAi, TBi, TCi, TDi);
 
102
                debug_msg("P %02X", p);
 
103
#endif
 
104
 
 
105
                /*
 
106
                 * Examine TDi to determine protocol and more 
 
107
                 */
 
108
                if (TDi >= 0)
 
109
                {
 
110
                        Y1i = TDi >> 4; /* Get the MSN in Y1 */
 
111
                        T = TDi & 0x0F; /* Get the LSN in K */
 
112
 
 
113
                        /*
 
114
                         * Set the current protocol TD1 
 
115
                         */
 
116
                        if (psExtension->CardCapabilities.CurrentProtocol == 0x00)
 
117
                        {
 
118
                                switch (T)
 
119
                                {
 
120
                                case 0:
 
121
                                        psExtension->CardCapabilities.CurrentProtocol =
 
122
                                                SCARD_PROTOCOL_T0;
 
123
                                        break;
 
124
                                case 1:
 
125
                                        psExtension->CardCapabilities.CurrentProtocol =
 
126
                                                SCARD_PROTOCOL_T1;
 
127
                                        break;
 
128
                                default:
 
129
                                        return 0;
 
130
                                }
 
131
                        }
 
132
 
 
133
                        if (T == 0)
 
134
                        {
 
135
#ifdef ATR_DEBUG
 
136
                                debug_msg("T=0 Protocol Found");
 
137
#endif
 
138
                                psExtension->CardCapabilities.AvailableProtocols |=
 
139
                                        SCARD_PROTOCOL_T0;
 
140
                                psExtension->CardCapabilities.T0.BGT = 0;
 
141
                                psExtension->CardCapabilities.T0.BWT = 0;
 
142
                                psExtension->CardCapabilities.T0.CWT = 0;
 
143
                                psExtension->CardCapabilities.T0.CGT = 0;
 
144
                                psExtension->CardCapabilities.T0.WT = 0;
 
145
                        } else if (T == 1)
 
146
                        {
 
147
#ifdef ATR_DEBUG
 
148
                                debug_msg("T=1 Protocol Found");
 
149
#endif
 
150
                                psExtension->CardCapabilities.AvailableProtocols |=
 
151
                                        SCARD_PROTOCOL_T1;
 
152
                                psExtension->CardCapabilities.T1.BGT = 0;
 
153
                                psExtension->CardCapabilities.T1.BWT = 0;
 
154
                                psExtension->CardCapabilities.T1.CWT = 0;
 
155
                                psExtension->CardCapabilities.T1.CGT = 0;
 
156
                                psExtension->CardCapabilities.T1.WT = 0;
 
157
                        } else
 
158
                        {
 
159
                                psExtension->CardCapabilities.AvailableProtocols |= T;
 
160
                                /*
 
161
                                 * Do nothing for now since other protocols are not
 
162
                                 * supported at this time 
 
163
                                 */
 
164
                        }
 
165
 
 
166
                } else
 
167
                {
 
168
                        Y1i = 0;
 
169
                }
 
170
 
 
171
                if (p > MAX_ATR_SIZE)
 
172
                {
 
173
                        memset(psExtension, 0x00, sizeof(SMARTCARD_EXTENSION));
 
174
                        return 0;
 
175
                }
 
176
 
 
177
        }
 
178
        while (Y1i != 0);
 
179
 
 
180
        /*
 
181
         * If TDx is not set then the current must be T0 
 
182
         */
 
183
        if (psExtension->CardCapabilities.CurrentProtocol == 0x00)
 
184
        {
 
185
                psExtension->CardCapabilities.CurrentProtocol = SCARD_PROTOCOL_T0;
 
186
                psExtension->CardCapabilities.AvailableProtocols |=
 
187
                        SCARD_PROTOCOL_T0;
 
188
        }
 
189
 
 
190
        /*
 
191
         * Take care of the historical characters 
 
192
         */
 
193
 
 
194
        psExtension->ATR.HistoryLength = K;
 
195
        memcpy(psExtension->ATR.HistoryValue, &pucAtr[p], K);
 
196
 
 
197
        p = p + K;
 
198
 
 
199
        /*
 
200
         * Check to see if TCK character is included It will be included if
 
201
         * more than T=0 is supported 
 
202
         */
 
203
 
 
204
        if (psExtension->CardCapabilities.AvailableProtocols &
 
205
                SCARD_PROTOCOL_T1)
 
206
        {
 
207
                TCK = pucAtr[p++];
 
208
        }
 
209
 
 
210
        memcpy(psExtension->ATR.Value, pucAtr, p);
 
211
        psExtension->ATR.Length = p;    /* modified from p-1 */
 
212
 
 
213
        return 1;
182
214
}
183