smartcard 0.3.1-x86-mswin32-60

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,207 @@
1
+ /*
2
+ * MUSCLE SmartCard Development ( http://www.linuxnet.com )
3
+ *
4
+ * Copyright (C) 1999-2005
5
+ * David Corcoran <corcoran@linuxnet.com>
6
+ * Ludovic Rousseau <ludovic.rousseau@free.fr>
7
+ *
8
+ * $Id: reader.h.in 2572 2007-06-20 07:24:35Z rousseau $
9
+ */
10
+
11
+ /**
12
+ * @file
13
+ * @brief This keeps a list of defines shared between the driver and the application
14
+ */
15
+
16
+ #ifndef __reader_h__
17
+ #define __reader_h__
18
+
19
+ /*
20
+ * Tags for requesting card and reader attributes
21
+ */
22
+
23
+ #define SCARD_ATTR_VALUE(Class, Tag) ((((ULONG)(Class)) << 16) | ((ULONG)(Tag)))
24
+
25
+ #define SCARD_CLASS_VENDOR_INFO 1 /**< Vendor information definitions */
26
+ #define SCARD_CLASS_COMMUNICATIONS 2 /**< Communication definitions */
27
+ #define SCARD_CLASS_PROTOCOL 3 /**< Protocol definitions */
28
+ #define SCARD_CLASS_POWER_MGMT 4 /**< Power Management definitions */
29
+ #define SCARD_CLASS_SECURITY 5 /**< Security Assurance definitions */
30
+ #define SCARD_CLASS_MECHANICAL 6 /**< Mechanical characteristic definitions */
31
+ #define SCARD_CLASS_VENDOR_DEFINED 7 /**< Vendor specific definitions */
32
+ #define SCARD_CLASS_IFD_PROTOCOL 8 /**< Interface Device Protocol options */
33
+ #define SCARD_CLASS_ICC_STATE 9 /**< ICC State specific definitions */
34
+ #define SCARD_CLASS_SYSTEM 0x7fff /**< System-specific definitions */
35
+
36
+ #define SCARD_ATTR_VENDOR_NAME SCARD_ATTR_VALUE(SCARD_CLASS_VENDOR_INFO, 0x0100)
37
+ #define SCARD_ATTR_VENDOR_IFD_TYPE SCARD_ATTR_VALUE(SCARD_CLASS_VENDOR_INFO, 0x0101)
38
+ #define SCARD_ATTR_VENDOR_IFD_VERSION SCARD_ATTR_VALUE(SCARD_CLASS_VENDOR_INFO, 0x0102)
39
+ #define SCARD_ATTR_VENDOR_IFD_SERIAL_NO SCARD_ATTR_VALUE(SCARD_CLASS_VENDOR_INFO, 0x0103)
40
+ #define SCARD_ATTR_CHANNEL_ID SCARD_ATTR_VALUE(SCARD_CLASS_COMMUNICATIONS, 0x0110)
41
+ #define SCARD_ATTR_ASYNC_PROTOCOL_TYPES SCARD_ATTR_VALUE(SCARD_CLASS_PROTOCOL, 0x0120)
42
+ #define SCARD_ATTR_DEFAULT_CLK SCARD_ATTR_VALUE(SCARD_CLASS_PROTOCOL, 0x0121)
43
+ #define SCARD_ATTR_MAX_CLK SCARD_ATTR_VALUE(SCARD_CLASS_PROTOCOL, 0x0122)
44
+ #define SCARD_ATTR_DEFAULT_DATA_RATE SCARD_ATTR_VALUE(SCARD_CLASS_PROTOCOL, 0x0123)
45
+ #define SCARD_ATTR_MAX_DATA_RATE SCARD_ATTR_VALUE(SCARD_CLASS_PROTOCOL, 0x0124)
46
+ #define SCARD_ATTR_MAX_IFSD SCARD_ATTR_VALUE(SCARD_CLASS_PROTOCOL, 0x0125)
47
+ #define SCARD_ATTR_SYNC_PROTOCOL_TYPES SCARD_ATTR_VALUE(SCARD_CLASS_PROTOCOL, 0x0126)
48
+ #define SCARD_ATTR_POWER_MGMT_SUPPORT SCARD_ATTR_VALUE(SCARD_CLASS_POWER_MGMT, 0x0131)
49
+ #define SCARD_ATTR_USER_TO_CARD_AUTH_DEVICE SCARD_ATTR_VALUE(SCARD_CLASS_SECURITY, 0x0140)
50
+ #define SCARD_ATTR_USER_AUTH_INPUT_DEVICE SCARD_ATTR_VALUE(SCARD_CLASS_SECURITY, 0x0142)
51
+ #define SCARD_ATTR_CHARACTERISTICS SCARD_ATTR_VALUE(SCARD_CLASS_MECHANICAL, 0x0150)
52
+
53
+ #define SCARD_ATTR_CURRENT_PROTOCOL_TYPE SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x0201)
54
+ #define SCARD_ATTR_CURRENT_CLK SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x0202)
55
+ #define SCARD_ATTR_CURRENT_F SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x0203)
56
+ #define SCARD_ATTR_CURRENT_D SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x0204)
57
+ #define SCARD_ATTR_CURRENT_N SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x0205)
58
+ #define SCARD_ATTR_CURRENT_W SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x0206)
59
+ #define SCARD_ATTR_CURRENT_IFSC SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x0207)
60
+ #define SCARD_ATTR_CURRENT_IFSD SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x0208)
61
+ #define SCARD_ATTR_CURRENT_BWT SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x0209)
62
+ #define SCARD_ATTR_CURRENT_CWT SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x020a)
63
+ #define SCARD_ATTR_CURRENT_EBC_ENCODING SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x020b)
64
+ #define SCARD_ATTR_EXTENDED_BWT SCARD_ATTR_VALUE(SCARD_CLASS_IFD_PROTOCOL, 0x020c)
65
+
66
+ #define SCARD_ATTR_ICC_PRESENCE SCARD_ATTR_VALUE(SCARD_CLASS_ICC_STATE, 0x0300)
67
+ #define SCARD_ATTR_ICC_INTERFACE_STATUS SCARD_ATTR_VALUE(SCARD_CLASS_ICC_STATE, 0x0301)
68
+ #define SCARD_ATTR_CURRENT_IO_STATE SCARD_ATTR_VALUE(SCARD_CLASS_ICC_STATE, 0x0302)
69
+ #define SCARD_ATTR_ATR_STRING SCARD_ATTR_VALUE(SCARD_CLASS_ICC_STATE, 0x0303)
70
+ #define SCARD_ATTR_ICC_TYPE_PER_ATR SCARD_ATTR_VALUE(SCARD_CLASS_ICC_STATE, 0x0304)
71
+
72
+ #define SCARD_ATTR_ESC_RESET SCARD_ATTR_VALUE(SCARD_CLASS_VENDOR_DEFINED, 0xA000)
73
+ #define SCARD_ATTR_ESC_CANCEL SCARD_ATTR_VALUE(SCARD_CLASS_VENDOR_DEFINED, 0xA003)
74
+ #define SCARD_ATTR_ESC_AUTHREQUEST SCARD_ATTR_VALUE(SCARD_CLASS_VENDOR_DEFINED, 0xA005)
75
+ #define SCARD_ATTR_MAXINPUT SCARD_ATTR_VALUE(SCARD_CLASS_VENDOR_DEFINED, 0xA007)
76
+
77
+ #define SCARD_ATTR_DEVICE_UNIT SCARD_ATTR_VALUE(SCARD_CLASS_SYSTEM, 0x0001)
78
+ #define SCARD_ATTR_DEVICE_IN_USE SCARD_ATTR_VALUE(SCARD_CLASS_SYSTEM, 0x0002)
79
+ #define SCARD_ATTR_DEVICE_FRIENDLY_NAME_A SCARD_ATTR_VALUE(SCARD_CLASS_SYSTEM, 0x0003)
80
+ #define SCARD_ATTR_DEVICE_SYSTEM_NAME_A SCARD_ATTR_VALUE(SCARD_CLASS_SYSTEM, 0x0004)
81
+ #define SCARD_ATTR_DEVICE_FRIENDLY_NAME_W SCARD_ATTR_VALUE(SCARD_CLASS_SYSTEM, 0x0005)
82
+ #define SCARD_ATTR_DEVICE_SYSTEM_NAME_W SCARD_ATTR_VALUE(SCARD_CLASS_SYSTEM, 0x0006)
83
+ #define SCARD_ATTR_SUPRESS_T1_IFS_REQUEST SCARD_ATTR_VALUE(SCARD_CLASS_SYSTEM, 0x0007)
84
+
85
+ #ifdef UNICODE
86
+ #define SCARD_ATTR_DEVICE_FRIENDLY_NAME SCARD_ATTR_DEVICE_FRIENDLY_NAME_W
87
+ #define SCARD_ATTR_DEVICE_SYSTEM_NAME SCARD_ATTR_DEVICE_SYSTEM_NAME_W
88
+ #else
89
+ #define SCARD_ATTR_DEVICE_FRIENDLY_NAME SCARD_ATTR_DEVICE_FRIENDLY_NAME_A
90
+ #define SCARD_ATTR_DEVICE_SYSTEM_NAME SCARD_ATTR_DEVICE_SYSTEM_NAME_A
91
+ #endif
92
+
93
+ /**
94
+ * Provide source compatibility on different platforms
95
+ */
96
+ #define SCARD_CTL_CODE(code) (0x42000000 + (code))
97
+
98
+ /**
99
+ * TeleTrust Class 2 reader tags
100
+ */
101
+ #define CM_IOCTL_GET_FEATURE_REQUEST SCARD_CTL_CODE(3400)
102
+
103
+ #define FEATURE_VERIFY_PIN_START 0x01 /**< OMNIKEY Proposal */
104
+ #define FEATURE_VERIFY_PIN_FINISH 0x02 /**< OMNIKEY Proposal */
105
+ #define FEATURE_MODIFY_PIN_START 0x03 /**< OMNIKEY Proposal */
106
+ #define FEATURE_MODIFY_PIN_FINISH 0x04 /**< OMNIKEY Proposal */
107
+ #define FEATURE_GET_KEY_PRESSED 0x05 /**< OMNIKEY Proposal */
108
+ #define FEATURE_VERIFY_PIN_DIRECT 0x06 /**< USB CCID PIN Verify */
109
+ #define FEATURE_MODIFY_PIN_DIRECT 0x07 /**< USB CCID PIN Modify */
110
+ #define FEATURE_MCT_READERDIRECT 0x08 /**< KOBIL Proposal */
111
+ #define FEATURE_MCT_UNIVERSAL 0x09 /**< KOBIL Proposal */
112
+ #define FEATURE_IFD_PIN_PROP 0x0A /**< Gemplus Proposal */
113
+ #define FEATURE_ABORT 0x0B /**< SCM Proposal */
114
+
115
+ /* structures used (but not defined) in PCSC Part 10 revision 2.01.02:
116
+ * "IFDs with Secure Pin Entry Capabilities" */
117
+
118
+ #include <inttypes.h>
119
+
120
+ /* Set structure elements aligment on bytes
121
+ * http://gcc.gnu.org/onlinedocs/gcc/Structure_002dPacking-Pragmas.html */
122
+ #if defined(__APPLE__) | defined(sun)
123
+ #pragma pack(1)
124
+ #else
125
+ #pragma pack(push, 1)
126
+ #endif
127
+
128
+ /** the structure must be 6-bytes long */
129
+ typedef struct
130
+ {
131
+ uint8_t tag;
132
+ uint8_t length;
133
+ uint32_t value; /**< This value is always in BIG ENDIAN format as documented in PCSC v2 part 10 ch 2.2 page 2. You can use ntohl() for example */
134
+ } PCSC_TLV_STRUCTURE;
135
+
136
+ /** the wLangId and wPINMaxExtraDigit are 16-bits long so are subject to byte
137
+ * ordering */
138
+ #define HOST_TO_CCID_16(x) @host_to_ccid_16@
139
+ #define HOST_TO_CCID_32(x) @host_to_ccid_32@
140
+
141
+ /** structure used with \ref FEATURE_VERIFY_PIN_DIRECT */
142
+ typedef struct
143
+ {
144
+ uint8_t bTimerOut; /**< timeout is seconds (00 means use default timeout) */
145
+ uint8_t bTimerOut2; /**< timeout in seconds after first key stroke */
146
+ uint8_t bmFormatString; /**< formatting options */
147
+ uint8_t bmPINBlockString; /**< bits 7-4 bit size of PIN length in APDU,
148
+ * bits 3-0 PIN block size in bytes after
149
+ * justification and formatting */
150
+ uint8_t bmPINLengthFormat; /**< bits 7-5 RFU,
151
+ * bit 4 set if system units are bytes, clear if
152
+ * system units are bits,
153
+ * bits 3-0 PIN length position in system units */
154
+ uint16_t wPINMaxExtraDigit; /**< 0xXXYY where XX is minimum PIN size in digits,
155
+ and YY is maximum PIN size in digits */
156
+ uint8_t bEntryValidationCondition; /**< Conditions under which PIN entry should
157
+ * be considered complete */
158
+ uint8_t bNumberMessage; /**< Number of messages to display for PIN verification */
159
+ uint16_t wLangId; /**< Language for messages */
160
+ uint8_t bMsgIndex; /**< Message index (should be 00) */
161
+ uint8_t bTeoPrologue[3]; /**< T=1 block prologue field to use (fill with 00) */
162
+ uint32_t ulDataLength; /**< length of Data to be sent to the ICC */
163
+ uint8_t abData[1]; /**< Data to send to the ICC */
164
+ } PIN_VERIFY_STRUCTURE;
165
+
166
+ /** structure used with \ref FEATURE_MODIFY_PIN_DIRECT */
167
+ typedef struct
168
+ {
169
+ uint8_t bTimerOut; /**< timeout is seconds (00 means use default timeout) */
170
+ uint8_t bTimerOut2; /**< timeout in seconds after first key stroke */
171
+ uint8_t bmFormatString; /**< formatting options */
172
+ uint8_t bmPINBlockString; /**< bits 7-4 bit size of PIN length in APDU,
173
+ * bits 3-0 PIN block size in bytes after
174
+ * justification and formatting */
175
+ uint8_t bmPINLengthFormat; /**< bits 7-5 RFU,
176
+ * bit 4 set if system units are bytes, clear if
177
+ * system units are bits,
178
+ * bits 3-0 PIN length position in system units */
179
+ uint8_t bInsertionOffsetOld; /**< Insertion position offset in bytes for
180
+ the current PIN */
181
+ uint8_t bInsertionOffsetNew; /**< Insertion position offset in bytes for
182
+ the new PIN */
183
+ uint16_t wPINMaxExtraDigit;
184
+ /**< 0xXXYY where XX is minimum PIN size in digits,
185
+ and YY is maximum PIN size in digits */
186
+ uint8_t bConfirmPIN; /**< Flags governing need for confirmation of new PIN */
187
+ uint8_t bEntryValidationCondition; /**< Conditions under which PIN entry should
188
+ * be considered complete */
189
+ uint8_t bNumberMessage; /**< Number of messages to display for PIN verification*/
190
+ uint16_t wLangId; /**< Language for messages */
191
+ uint8_t bMsgIndex1; /**< index of 1st prompting message */
192
+ uint8_t bMsgIndex2; /**< index of 2d prompting message */
193
+ uint8_t bMsgIndex3; /**< index of 3d prompting message */
194
+ uint8_t bTeoPrologue[3]; /**< T=1 block prologue field to use (fill with 00) */
195
+ uint32_t ulDataLength; /**< length of Data to be sent to the ICC */
196
+ uint8_t abData[1]; /**< Data to send to the ICC */
197
+ } PIN_MODIFY_STRUCTURE;
198
+
199
+ /* restore default structure elements alignment */
200
+ #if defined(__APPLE__) | defined(sun)
201
+ #pragma pack()
202
+ #else
203
+ #pragma pack(pop)
204
+ #endif
205
+
206
+ #endif
207
+
@@ -0,0 +1,63 @@
1
+ /*
2
+ * MUSCLE SmartCard Development ( http://www.linuxnet.com )
3
+ *
4
+ * Copyright (C) 1999
5
+ * David Corcoran <corcoran@linuxnet.com>
6
+ *
7
+ * $Id: wintypes.h 2537 2007-05-22 15:02:26Z rousseau $
8
+ */
9
+
10
+ /**
11
+ * @file
12
+ * @brief This keeps a list of Windows(R) types.
13
+ */
14
+
15
+ #ifndef __wintypes_h__
16
+ #define __wintypes_h__
17
+
18
+ #ifdef __cplusplus
19
+ extern "C"
20
+ {
21
+ #endif
22
+
23
+ #if !defined(WIN32)
24
+
25
+ #ifndef BYTE
26
+ typedef unsigned char BYTE;
27
+ #endif
28
+ typedef unsigned char UCHAR;
29
+ typedef unsigned char *PUCHAR;
30
+ typedef unsigned short USHORT;
31
+
32
+ #ifndef __COREFOUNDATION_CFPLUGINCOM__
33
+ typedef unsigned long ULONG;
34
+ typedef void *LPVOID;
35
+ typedef short BOOL;
36
+ #endif
37
+
38
+ typedef unsigned long *PULONG;
39
+ typedef const void *LPCVOID;
40
+ typedef uint32_t DWORD;
41
+ typedef uint32_t *PDWORD;
42
+ typedef uint16_t WORD;
43
+ typedef long LONG;
44
+ typedef const char *LPCSTR;
45
+ typedef const BYTE *LPCBYTE;
46
+ typedef BYTE *LPBYTE;
47
+ typedef DWORD *LPDWORD;
48
+ typedef unsigned char *LPSTR;
49
+
50
+ /* these types were deprecated but still used by old drivers and
51
+ * applications. So just declare and use them. */
52
+ typedef LPSTR LPTSTR;
53
+ typedef LPCSTR LPCTSTR;
54
+
55
+ #else
56
+ #include <windows.h>
57
+ #endif
58
+
59
+ #ifdef __cplusplus
60
+ }
61
+ #endif
62
+
63
+ #endif
data/lib/smartcard.rb ADDED
@@ -0,0 +1 @@
1
+ require 'smartcard/pcsc'
Binary file
@@ -0,0 +1,5 @@
1
+ # Contains information about an exception at the PC/SC layer.
2
+ class Smartcard::PCSC::Exception
3
+ # The error number returned by the failed PC/SC function call. Should be one of the Smartcard::PCSC::SCARD_E_ constants.
4
+ attr_reader :errno
5
+ end
data/smartcard.gemspec ADDED
@@ -0,0 +1,66 @@
1
+
2
+ # Gem::Specification for Smartcard-0.3.1
3
+ # Originally generated by Echoe
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = %q{smartcard}
7
+ s.version = "0.3.1"
8
+ s.platform = %q{x86-mswin32-60}
9
+
10
+ s.specification_version = 2 if s.respond_to? :specification_version=
11
+
12
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
13
+ s.authors = ["Victor Costan"]
14
+ s.date = %q{2008-05-01}
15
+ s.description = %q{Interface with ISO 7816 smart cards.}
16
+ s.email = %q{victor@costan.us}
17
+ s.extra_rdoc_files = ["BUILD", "CHANGELOG", "ext/smartcard_pcsc/extconf.rb", "ext/smartcard_pcsc/pcsc.h", "ext/smartcard_pcsc/pcsc_card.c", "ext/smartcard_pcsc/pcsc_constants.c", "ext/smartcard_pcsc/pcsc_context.c", "ext/smartcard_pcsc/pcsc_exception.c", "ext/smartcard_pcsc/pcsc_io_request.c", "ext/smartcard_pcsc/pcsc_main.c", "ext/smartcard_pcsc/pcsc_multi_strings.c", "ext/smartcard_pcsc/pcsc_namespace.c", "ext/smartcard_pcsc/pcsc_reader_states.c", "ext/smartcard_pcsc/pcsc_surrogate_reader.h", "ext/smartcard_pcsc/pcsc_surrogate_wintypes.h", "lib/smartcard/pcsc_exception.rb", "lib/smartcard.rb", "LICENSE", "README"]
18
+ s.files = ["BUILD", "CHANGELOG", "ext/smartcard_pcsc/extconf.rb", "ext/smartcard_pcsc/pcsc.h", "ext/smartcard_pcsc/pcsc_card.c", "ext/smartcard_pcsc/pcsc_constants.c", "ext/smartcard_pcsc/pcsc_context.c", "ext/smartcard_pcsc/pcsc_exception.c", "ext/smartcard_pcsc/pcsc_io_request.c", "ext/smartcard_pcsc/pcsc_main.c", "ext/smartcard_pcsc/pcsc_multi_strings.c", "ext/smartcard_pcsc/pcsc_namespace.c", "ext/smartcard_pcsc/pcsc_reader_states.c", "ext/smartcard_pcsc/pcsc_surrogate_reader.h", "ext/smartcard_pcsc/pcsc_surrogate_wintypes.h", "lib/smartcard/pcsc_exception.rb", "lib/smartcard.rb", "LICENSE", "Manifest", "README", "test/test_containers.rb", "test/test_smoke.rb", "tests/ts_pcsc_ext.rb", "smartcard.gemspec", "lib/smartcard/pcsc.so"]
19
+ s.has_rdoc = true
20
+ s.homepage = %q{http://www.costan.us/smartcard}
21
+ s.rdoc_options = ["--line-numbers", "--inline-source", "--title", "Smartcard", "--main", "README"]
22
+ s.require_paths = ["lib", "ext"]
23
+ s.rubyforge_project = %q{smartcard}
24
+ s.rubygems_version = %q{1.1.1}
25
+ s.summary = %q{Interface with ISO 7816 smart cards.}
26
+ s.test_files = ["test/test_containers.rb", "test/test_smoke.rb"]
27
+ end
28
+
29
+
30
+ # # Original Rakefile source (requires the Echoe gem):
31
+ #
32
+ # require 'rubygems'
33
+ # gem 'echoe'
34
+ # require 'echoe'
35
+ #
36
+ # Echoe.new('smartcard') do |p|
37
+ # p.project = 'smartcard' # rubyforge project
38
+ #
39
+ # p.author = 'Victor Costan'
40
+ # p.email = 'victor@costan.us'
41
+ # p.summary = 'Interface with ISO 7816 smart cards.'
42
+ # p.url = 'http://www.costan.us/smartcard'
43
+ #
44
+ # p.need_tar_gz = false
45
+ # p.clean_pattern += ['ext/**/*.manifest', 'ext/**/*_autogen.h']
46
+ # p.rdoc_pattern = /^(lib|bin|tasks|ext)|^BUILD|^README|^CHANGELOG|^TODO|^LICENSE|^COPYING$/
47
+ #
48
+ # p.eval = proc do |p|
49
+ # if Platform.windows?
50
+ # p.files += ['lib/smartcard/pcsc.so']
51
+ # p.platform = Gem::Platform::CURRENT
52
+ #
53
+ # # take out the extension info from the gemspec
54
+ # task :postcompile_hacks => [:compile] do
55
+ # p.extensions.clear
56
+ # end
57
+ #
58
+ # task :package => [ :clean, :compile, :postcompile_hacks ]
59
+ # end
60
+ # end
61
+ # end
62
+ #
63
+ # if $0 == __FILE__
64
+ # Rake.application = Rake::Application.new
65
+ # Rake.application.run
66
+ # end
@@ -0,0 +1,53 @@
1
+ require 'test/unit'
2
+ require 'smartcard'
3
+
4
+ class ContainersTest < Test::Unit::TestCase
5
+ def setup
6
+
7
+ end
8
+
9
+ def teardown
10
+
11
+ end
12
+
13
+ # tests the SmartCard::PCSC::ReaderStates container
14
+ def test_reader_states
15
+ reader_states = Smartcard::PCSC::ReaderStates.new(2)
16
+ reader_states.set_current_state_of!(1, Smartcard::PCSC::STATE_ATRMATCH)
17
+ reader_states.set_current_state_of!(0, Smartcard::PCSC::STATE_CHANGED)
18
+ reader_states.set_event_state_of!(0, Smartcard::PCSC::STATE_IGNORE)
19
+ reader_states.set_event_state_of!(1, Smartcard::PCSC::STATE_PRESENT)
20
+ reader_states.set_atr_of!(1, "Ruby\0rocks!")
21
+ reader_states.set_atr_of!(0, "grreat success")
22
+ reader_states.set_reader_name_of!(0, "PC/SC Reader 0")
23
+ reader_states.set_reader_name_of!(1, "CCID Reader 1")
24
+
25
+ assert_equal Smartcard::PCSC::STATE_ATRMATCH, reader_states.current_state_of(1), 'ReaderStates.set_current_state_of! / current_state_of mismatch'
26
+ assert_equal Smartcard::PCSC::STATE_CHANGED, reader_states.current_state_of(0), 'ReaderStates.set_current_state_of! / current_state_of mismatch'
27
+
28
+ assert_equal Smartcard::PCSC::STATE_IGNORE, reader_states.event_state_of(0), 'ReaderStates.set_event_state_of! / event_state_of mismatch'
29
+ assert_equal Smartcard::PCSC::STATE_PRESENT, reader_states.event_state_of(1), 'ReaderStates.set_event_state_of! / event_state_of mismatch'
30
+
31
+ assert_equal "Ruby\0rocks!", reader_states.atr_of(1), 'ReaderStates.set_atr_of! / atr_of mismatch'
32
+ assert_equal "grreat success", reader_states.atr_of(0), 'ReaderStates.set_atr_of! / atr_of mismatch'
33
+
34
+ assert_equal "PC/SC Reader 0", reader_states.reader_name_of(0)
35
+ assert_equal "CCID Reader 1", reader_states.reader_name_of(1)
36
+
37
+ [[5, IndexError], [2, IndexError], [nil, TypeError]].each do |bad_index_test|
38
+ assert_raise bad_index_test[1] do
39
+ reader_states.current_state_of(bad_index_test[0])
40
+ end
41
+ end
42
+ end
43
+
44
+ # tests the SmartCard::PCSC::IoRequest container
45
+ def test_io_request
46
+ io_request = Smartcard::PCSC::IoRequest.new
47
+ [Smartcard::PCSC::PROTOCOL_T0, Smartcard::PCSC::PROTOCOL_T1, Smartcard::PCSC::PROTOCOL_RAW].each do |t_protocol|
48
+ io_request.protocol = t_protocol
49
+ r_protocol = io_request.protocol
50
+ assert_equal r_protocol, t_protocol, 'IoRequest.protocol= / protocol mismatch'
51
+ end
52
+ end
53
+ end
@@ -0,0 +1,22 @@
1
+ require 'test/unit'
2
+ require 'smartcard'
3
+
4
+ class SmokeTest < Test::Unit::TestCase
5
+ def setup
6
+ end
7
+
8
+ def teardown
9
+ end
10
+
11
+ # smoke-test to ensure that the extension loads and can call into the PC/SC library
12
+ def test_smoke
13
+ context = Smartcard::PCSC::Context.new(Smartcard::PCSC::SCOPE_SYSTEM)
14
+
15
+ reader_groups = context.list_reader_groups
16
+ readers1 = context.list_readers reader_groups
17
+ readers2 = context.list_readers reader_groups.first
18
+ readers3 = context.list_readers nil
19
+
20
+ context.release
21
+ end
22
+ end
@@ -0,0 +1,72 @@
1
+ require 'smartcard'
2
+ require 'pp'
3
+
4
+ context = Smartcard::PCSC::Context.new(Smartcard::PCSC::SCOPE_SYSTEM)
5
+
6
+ reader_groups = context.list_reader_groups
7
+ pp reader_groups
8
+ readers1 = context.list_readers reader_groups
9
+ pp readers1
10
+ readers2 = context.list_readers reader_groups.first
11
+ pp readers2
12
+ readers3 = context.list_readers nil
13
+ pp readers3
14
+
15
+ context.cancel
16
+
17
+ reader0 = readers3.first
18
+ puts "Waiting for card in reader: #{reader0}\n"
19
+ reader_states = Smartcard::PCSC::ReaderStates.new(1)
20
+ reader_states.set_reader_name_of!(0, reader0)
21
+ reader_states.set_current_state_of!(0, Smartcard::PCSC::STATE_UNKNOWN)
22
+ while (reader_states.event_state_of(0) & Smartcard::PCSC::STATE_PRESENT) == 0 do
23
+ context.get_status_change reader_states, Smartcard::PCSC::INFINITE_TIMEOUT
24
+ puts "Status change: now it's #{reader_states.event_state_of(0)} and we want #{Smartcard::PCSC::STATE_PRESENT}\n"
25
+ reader_states.acknowledge_events!
26
+ end
27
+
28
+ puts "Connecting to card\n"
29
+ card0 = Smartcard::PCSC::Card.new(context, reader0, Smartcard::PCSC::SHARE_SHARED, Smartcard::PCSC::PROTOCOL_ANY)
30
+
31
+ card0.begin_transaction
32
+ card0.end_transaction Smartcard::PCSC::DISPOSITION_LEAVE
33
+
34
+ begin
35
+ card0.reconnect Smartcard::PCSC::SHARE_EXCLUSIVE, Smartcard::PCSC::PROTOCOL_ANY, Smartcard::PCSC::INITIALIZATION_RESET
36
+ rescue RuntimeException => e
37
+ puts "Card.reconnect threw exception #{e}\n"
38
+ end
39
+
40
+ card_status = card0.status
41
+ pp card_status
42
+ puts "ATR Length: #{card_status[:atr].length}\n"
43
+
44
+ begin
45
+ puts "IFD vendor: #{card0.get_attribute Smartcard::PCSC::ATTR_VENDOR_IFD_VERSION}\n"
46
+ rescue RuntimeError => e
47
+ puts "Card.get_attribute threw exception #{e}\n"
48
+ end
49
+
50
+ puts "Selecting applet\n"
51
+ aid = [0x19, 0x83, 0x12, 0x29, 0x10, 0xba, 0xbe]
52
+ select_apdu = [0x00, 0xA4, 0x04, 0x00, aid.length, aid].flatten
53
+ send_ioreq = {Smartcard::PCSC::PROTOCOL_T0 => Smartcard::PCSC::IOREQUEST_T0,
54
+ Smartcard::PCSC::PROTOCOL_T1 => Smartcard::PCSC::IOREQUEST_T1}[card_status[:protocol]]
55
+ recv_ioreq = Smartcard::PCSC::IoRequest.new
56
+ select_response = card0.transmit(select_apdu.map {|byte| byte.chr}.join(''), send_ioreq, recv_ioreq)
57
+ select_response_str = (0...select_response.length).map { |i| ' %02x' % select_response[i].to_i }.join('')
58
+ puts "Response:#{select_response_str}\n"
59
+
60
+ begin
61
+ # This only works with GemPlus readers... any other suggestions?
62
+ puts "Testing low-level control\n"
63
+ ctl_string = [0x82, 0x01, 0x07, 0x00].map {|byte| byte.chr}.join('')
64
+ ctl_response = card0.control 2049, ctl_string, 4
65
+ pp ctl_response
66
+ rescue RuntimeError => e
67
+ puts "Card.control threw exception #{e}\n"
68
+ end
69
+
70
+ puts "Disconnecting and cleaning up\n"
71
+ card0.disconnect Smartcard::PCSC::DISPOSITION_LEAVE
72
+ context.release