smartcard 0.4.10-x86-mswin32-60 → 0.4.11-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.
- data/CHANGELOG +2 -0
 - data/Manifest +1 -1
 - data/lib/smartcard/gp/des.rb +7 -4
 - data/lib/smartcard/gp/gp_card_mixin.rb +51 -22
 - data/lib/smartcard/iso/iso_card_mixin.rb +3 -1
 - data/lib/smartcard/pcsc.so +0 -0
 - data/smartcard.gemspec +4 -4
 - data/test/gp/gp_card_mixin_compat_test.rb +99 -0
 - data/test/gp/gp_card_mixin_test.rb +1 -1
 - data/test/iso/iso_card_mixin_test.rb +4 -0
 - metadata +5 -3
 
    
        data/CHANGELOG
    CHANGED
    
    
    
        data/Manifest
    CHANGED
    
    | 
         @@ -31,10 +31,10 @@ lib/smartcard/iso/jcop_remote_transport.rb 
     | 
|
| 
       31 
31 
     | 
    
         
             
            lib/smartcard/iso/pcsc_transport.rb
         
     | 
| 
       32 
32 
     | 
    
         
             
            lib/smartcard/iso/transport.rb
         
     | 
| 
       33 
33 
     | 
    
         
             
            lib/smartcard/pcsc/pcsc_exception.rb
         
     | 
| 
       34 
     | 
    
         
            -
            smartcard.gemspec
         
     | 
| 
       35 
34 
     | 
    
         
             
            test/gp/asn1_ber_test.rb
         
     | 
| 
       36 
35 
     | 
    
         
             
            test/gp/cap_loader_test.rb
         
     | 
| 
       37 
36 
     | 
    
         
             
            test/gp/des_test.rb
         
     | 
| 
      
 37 
     | 
    
         
            +
            test/gp/gp_card_mixin_compat_test.rb
         
     | 
| 
       38 
38 
     | 
    
         
             
            test/gp/gp_card_mixin_test.rb
         
     | 
| 
       39 
39 
     | 
    
         
             
            test/gp/hello.apdu
         
     | 
| 
       40 
40 
     | 
    
         
             
            test/gp/hello.cap
         
     | 
    
        data/lib/smartcard/gp/des.rb
    CHANGED
    
    | 
         @@ -29,10 +29,13 @@ module Des 
     | 
|
| 
       29 
29 
     | 
    
         
             
              #   data:: the data to be encrypted or decrypted
         
     | 
| 
       30 
30 
     | 
    
         
             
              #   iv:: initialization vector
         
     | 
| 
       31 
31 
     | 
    
         
             
              #   decrypt:: if +false+ performs encryption, otherwise performs decryption
         
     | 
| 
      
 32 
     | 
    
         
            +
              #   use_ecb:: if +false+, uses the CBC mode, otherwise uses ECB
         
     | 
| 
       32 
33 
     | 
    
         
             
              #
         
     | 
| 
       33 
34 
     | 
    
         
             
              # Returns the encrypted / decrypted data.
         
     | 
| 
       34 
     | 
    
         
            -
              def self.crypt(key, data, iv = nil, decrypt = false)
         
     | 
| 
       35 
     | 
    
         
            -
                cipher_name = key.length == 8 ? 'DES 
     | 
| 
      
 35 
     | 
    
         
            +
              def self.crypt(key, data, iv = nil, decrypt = false, use_ecb = false)
         
     | 
| 
      
 36 
     | 
    
         
            +
                cipher_name = key.length == 8 ? 'DES' : 'DES-EDE'
         
     | 
| 
      
 37 
     | 
    
         
            +
                cipher_name += use_ecb ? '' : '-CBC'
         
     | 
| 
      
 38 
     | 
    
         
            +
                
         
     | 
| 
       36 
39 
     | 
    
         
             
                cipher = OpenSSL::Cipher::Cipher.new cipher_name
         
     | 
| 
       37 
40 
     | 
    
         
             
                decrypt ? cipher.decrypt : cipher.encrypt
         
     | 
| 
       38 
41 
     | 
    
         
             
                cipher.key = key
         
     | 
| 
         @@ -55,13 +58,13 @@ module Des 
     | 
|
| 
       55 
58 
     | 
    
         
             
                crypt(key, data[-8, 8], iv)
         
     | 
| 
       56 
59 
     | 
    
         
             
              end
         
     | 
| 
       57 
60 
     | 
    
         | 
| 
       58 
     | 
    
         
            -
              def self.mac_3des(key, data)
         
     | 
| 
      
 61 
     | 
    
         
            +
              def self.mac_3des(key, data, iv = nil)
         
     | 
| 
       59 
62 
     | 
    
         
             
                # Output transformation: add 80, then 00 until it's block-sized.
         
     | 
| 
       60 
63 
     | 
    
         
             
                data = data + "\x80"
         
     | 
| 
       61 
64 
     | 
    
         
             
                data += "\x00" * (8 - data.length % 8) unless data.length % 8 == 0
         
     | 
| 
       62 
65 
     | 
    
         | 
| 
       63 
66 
     | 
    
         
             
                # The MAC is the last block from 3DES-encrypting the data.
         
     | 
| 
       64 
     | 
    
         
            -
                crypt(key, data)[-8, 8]
         
     | 
| 
      
 67 
     | 
    
         
            +
                crypt(key, data, iv)[-8, 8]
         
     | 
| 
       65 
68 
     | 
    
         
             
              end
         
     | 
| 
       66 
69 
     | 
    
         
             
            end  # module Smartcard::Gp::Des
         
     | 
| 
       67 
70 
     | 
    
         | 
| 
         @@ -63,10 +63,18 @@ module GpCardMixin 
     | 
|
| 
       63 
63 
     | 
    
         
             
                                :data => host_challenge
         
     | 
| 
       64 
64 
     | 
    
         
             
                response = {
         
     | 
| 
       65 
65 
     | 
    
         
             
                  :key_diversification => raw[0, 10],
         
     | 
| 
       66 
     | 
    
         
            -
                  :key_version => raw[10], :protocol_id => raw[11],
         
     | 
| 
       67 
     | 
    
         
            -
                  :counter => raw[12, 2].pack('C*').unpack('n').first,
         
     | 
| 
       68 
     | 
    
         
            -
                  :challenge => raw[14, 6], :auth => raw[20, 8]
         
     | 
| 
      
 66 
     | 
    
         
            +
                  :key_version => raw[10], :protocol_id => raw[11], :auth => raw[20, 8]
         
     | 
| 
       69 
67 
     | 
    
         
             
                }
         
     | 
| 
      
 68 
     | 
    
         
            +
                case response[:protocol_id]
         
     | 
| 
      
 69 
     | 
    
         
            +
                when 1
         
     | 
| 
      
 70 
     | 
    
         
            +
                  response[:challenge] = raw[12, 8]
         
     | 
| 
      
 71 
     | 
    
         
            +
                when 2
         
     | 
| 
      
 72 
     | 
    
         
            +
                  response.merge! :counter => raw[12, 2].pack('C*').unpack('n').first,
         
     | 
| 
      
 73 
     | 
    
         
            +
                                  :challenge => raw[14, 6] 
         
     | 
| 
      
 74 
     | 
    
         
            +
                else
         
     | 
| 
      
 75 
     | 
    
         
            +
                  raise "Unimplemented Secure Channel protocol #{response[:protocol_id]}"
         
     | 
| 
      
 76 
     | 
    
         
            +
                end
         
     | 
| 
      
 77 
     | 
    
         
            +
                response
         
     | 
| 
       70 
78 
     | 
    
         
             
              end
         
     | 
| 
       71 
79 
     | 
    
         | 
| 
       72 
80 
     | 
    
         
             
              # Wrapper around iso_apdu! that adds a MAC to the APDU.
         
     | 
| 
         @@ -76,11 +84,13 @@ module GpCardMixin 
     | 
|
| 
       76 
84 
     | 
    
         
             
                apdu_data[:data] = (apdu_data[:data] || []) + [0, 0, 0, 0, 0, 0, 0, 0]
         
     | 
| 
       77 
85 
     | 
    
         | 
| 
       78 
86 
     | 
    
         
             
                apdu_bytes = Smartcard::Iso::IsoCardMixin.serialize_apdu(apdu_data)[0...-9]
         
     | 
| 
       79 
     | 
    
         
            -
                mac = Des. 
     | 
| 
       80 
     | 
    
         
            -
             
     | 
| 
      
 87 
     | 
    
         
            +
                mac = Des.send @gp_secure_channel_mac,
         
     | 
| 
      
 88 
     | 
    
         
            +
                               @gp_secure_channel_keys[:cmac], apdu_bytes.pack('C*'),
         
     | 
| 
      
 89 
     | 
    
         
            +
                               @gp_secure_channel_keys[:mac_iv]
         
     | 
| 
       81 
90 
     | 
    
         
             
                @gp_secure_channel_keys[:mac_iv] = mac
         
     | 
| 
       82 
91 
     | 
    
         | 
| 
       83 
92 
     | 
    
         
             
                apdu_data[:data][apdu_data[:data].length - 8, 8] = mac.unpack('C*')
         
     | 
| 
      
 93 
     | 
    
         
            +
                apdu_data[:le] = false
         
     | 
| 
       84 
94 
     | 
    
         
             
                iso_apdu! apdu_data
         
     | 
| 
       85 
95 
     | 
    
         
             
              end
         
     | 
| 
       86 
96 
     | 
    
         | 
| 
         @@ -117,32 +127,51 @@ module GpCardMixin 
     | 
|
| 
       117 
127 
     | 
    
         
             
              def secure_channel(keys = gp_development_keys)
         
     | 
| 
       118 
128 
     | 
    
         
             
                host_challenge = Des.random_bytes 8
         
     | 
| 
       119 
129 
     | 
    
         
             
                card_info = gp_setup_secure_channel host_challenge.unpack('C*')
         
     | 
| 
       120 
     | 
    
         
            -
                card_counter = [card_info[:counter]].pack('n')
         
     | 
| 
       121 
130 
     | 
    
         
             
                card_challenge = card_info[:challenge].pack('C*')
         
     | 
| 
       122 
131 
     | 
    
         | 
| 
       123 
132 
     | 
    
         
             
                # Compute session keys.
         
     | 
| 
       124 
133 
     | 
    
         
             
                session_keys = {}
         
     | 
| 
       125 
     | 
    
         
            -
                 
     | 
| 
       126 
     | 
    
         
            -
                 
     | 
| 
       127 
     | 
    
         
            -
             
     | 
| 
       128 
     | 
    
         
            -
             
     | 
| 
       129 
     | 
    
         
            -
             
     | 
| 
       130 
     | 
    
         
            -
             
     | 
| 
       131 
     | 
    
         
            -
             
     | 
| 
       132 
     | 
    
         
            -
             
     | 
| 
      
 134 
     | 
    
         
            +
                case card_info[:protocol_id]
         
     | 
| 
      
 135 
     | 
    
         
            +
                when 1  # Secure Channel 01 (GlobalPlatform 2.0)
         
     | 
| 
      
 136 
     | 
    
         
            +
                  derivation_data = card_challenge[4, 4] + host_challenge[0, 4] +
         
     | 
| 
      
 137 
     | 
    
         
            +
                                    card_challenge[0, 4] + host_challenge[4, 4]
         
     | 
| 
      
 138 
     | 
    
         
            +
                  session_keys[:cmac] = Des.crypt keys[:smac], derivation_data,
         
     | 
| 
      
 139 
     | 
    
         
            +
                                                  nil, false, true
         
     | 
| 
      
 140 
     | 
    
         
            +
                  session_keys[:rmac] = session_keys[:cmac]
         
     | 
| 
      
 141 
     | 
    
         
            +
                  session_keys[:senc] = Des.crypt keys[:senc], derivation_data,
         
     | 
| 
      
 142 
     | 
    
         
            +
                                                  nil, false, true
         
     | 
| 
      
 143 
     | 
    
         
            +
                  session_keys[:dek] = keys[:dek].dup
         
     | 
| 
      
 144 
     | 
    
         
            +
                  
         
     | 
| 
      
 145 
     | 
    
         
            +
                  card_auth = Des.mac_3des session_keys[:senc],
         
     | 
| 
      
 146 
     | 
    
         
            +
                                           host_challenge + card_challenge
         
     | 
| 
      
 147 
     | 
    
         
            +
                  host_auth = Des.mac_3des session_keys[:senc],
         
     | 
| 
      
 148 
     | 
    
         
            +
                                           card_challenge + host_challenge
         
     | 
| 
      
 149 
     | 
    
         
            +
                  @gp_secure_channel_mac = :mac_3des
         
     | 
| 
      
 150 
     | 
    
         
            +
                when 2  # Secure Channel 02 (GlobalPlatform 2.1+)
         
     | 
| 
      
 151 
     | 
    
         
            +
                  card_counter = [card_info[:counter]].pack('n')
         
     | 
| 
      
 152 
     | 
    
         
            +
                  derivation_data = "\x01\x01" + card_counter + "\x00" * 12
         
     | 
| 
      
 153 
     | 
    
         
            +
                  session_keys[:cmac] = Des.crypt keys[:smac], derivation_data    
         
     | 
| 
      
 154 
     | 
    
         
            +
                  derivation_data[0, 2] = "\x01\x02"
         
     | 
| 
      
 155 
     | 
    
         
            +
                  session_keys[:rmac] = Des.crypt keys[:smac], derivation_data
         
     | 
| 
      
 156 
     | 
    
         
            +
                  derivation_data[0, 2] = "\x01\x82"
         
     | 
| 
      
 157 
     | 
    
         
            +
                  session_keys[:senc] = Des.crypt keys[:senc], derivation_data
         
     | 
| 
      
 158 
     | 
    
         
            +
                  derivation_data[0, 2] = "\x01\x81"
         
     | 
| 
      
 159 
     | 
    
         
            +
                  session_keys[:dek] = Des.crypt keys[:dek], derivation_data
         
     | 
| 
      
 160 
     | 
    
         
            +
             
     | 
| 
      
 161 
     | 
    
         
            +
                  card_auth = Des.mac_3des session_keys[:senc],
         
     | 
| 
      
 162 
     | 
    
         
            +
                      host_challenge + card_counter + card_challenge
         
     | 
| 
      
 163 
     | 
    
         
            +
                  host_auth = Des.mac_3des session_keys[:senc],
         
     | 
| 
      
 164 
     | 
    
         
            +
                      card_counter + card_challenge + host_challenge
         
     | 
| 
      
 165 
     | 
    
         
            +
                  @gp_secure_channel_mac = :mac_retail
         
     | 
| 
      
 166 
     | 
    
         
            +
                else
         
     | 
| 
      
 167 
     | 
    
         
            +
                  raise "Unimplemented Secure Channel #{card_info[:protocol_id]}"
         
     | 
| 
      
 168 
     | 
    
         
            +
                end
         
     | 
| 
       133 
169 
     | 
    
         
             
                session_keys[:mac_iv] = "\x00" * 8
         
     | 
| 
       134 
170 
     | 
    
         
             
                @gp_secure_channel_keys = session_keys
         
     | 
| 
       135 
171 
     | 
    
         | 
| 
       136 
     | 
    
         
            -
                # Compute authentication cryptograms.
         
     | 
| 
       137 
     | 
    
         
            -
                card_auth = Des.mac_3des session_keys[:senc],
         
     | 
| 
       138 
     | 
    
         
            -
                    host_challenge + card_counter + card_challenge
         
     | 
| 
       139 
     | 
    
         
            -
                host_auth = Des.mac_3des session_keys[:senc],
         
     | 
| 
       140 
     | 
    
         
            -
                    card_counter + card_challenge + host_challenge
         
     | 
| 
       141 
     | 
    
         
            -
                    
         
     | 
| 
       142 
172 
     | 
    
         
             
                unless card_auth == card_info[:auth].pack('C*')
         
     | 
| 
       143 
173 
     | 
    
         
             
                  raise 'Card authentication invalid' 
         
     | 
| 
       144 
     | 
    
         
            -
                end 
     | 
| 
       145 
     | 
    
         
            -
             
     | 
| 
      
 174 
     | 
    
         
            +
                end
         
     | 
| 
       146 
175 
     | 
    
         
             
                gp_lock_secure_channel host_auth.unpack('C*')
         
     | 
| 
       147 
176 
     | 
    
         
             
              end
         
     | 
| 
       148 
177 
     | 
    
         | 
| 
         @@ -55,6 +55,8 @@ module IsoCardMixin 
     | 
|
| 
       55 
55 
     | 
    
         
             
              #   p12:: 2-byte array containing the P1 and P2 bytes in the APDU
         
     | 
| 
       56 
56 
     | 
    
         
             
              #   p1, p2:: the P1 and P2 bytes in the APDU (optional, both default to 0)
         
     | 
| 
       57 
57 
     | 
    
         
             
              #   data:: the extra data in the APDU (optional, defaults to nothing)
         
     | 
| 
      
 58 
     | 
    
         
            +
              #   le:: the expected data length (defaults to 0; set to +false+ to avoid
         
     | 
| 
      
 59 
     | 
    
         
            +
              #        sending an Le byte)
         
     | 
| 
       58 
60 
     | 
    
         
             
              def self.serialize_apdu(apdu_data)
         
     | 
| 
       59 
61 
     | 
    
         
             
                raise 'Unspecified INS in apdu_data' unless apdu_data[:ins]
         
     | 
| 
       60 
62 
     | 
    
         
             
                apdu = [ apdu_data[:cla] || 0, apdu_data[:ins] ]
         
     | 
| 
         @@ -73,7 +75,7 @@ module IsoCardMixin 
     | 
|
| 
       73 
75 
     | 
    
         
             
                else
         
     | 
| 
       74 
76 
     | 
    
         
             
                  apdu << 0
         
     | 
| 
       75 
77 
     | 
    
         
             
                end
         
     | 
| 
       76 
     | 
    
         
            -
                apdu << (apdu_data[:le] || 0)
         
     | 
| 
      
 78 
     | 
    
         
            +
                apdu << (apdu_data[:le] || 0) unless apdu_data[:le] == false
         
     | 
| 
       77 
79 
     | 
    
         
             
                apdu
         
     | 
| 
       78 
80 
     | 
    
         
             
              end
         
     | 
| 
       79 
81 
     | 
    
         | 
    
        data/lib/smartcard/pcsc.so
    CHANGED
    
    | 
         Binary file 
     | 
    
        data/smartcard.gemspec
    CHANGED
    
    | 
         @@ -2,23 +2,23 @@ 
     | 
|
| 
       2 
2 
     | 
    
         | 
| 
       3 
3 
     | 
    
         
             
            Gem::Specification.new do |s|
         
     | 
| 
       4 
4 
     | 
    
         
             
              s.name = %q{smartcard}
         
     | 
| 
       5 
     | 
    
         
            -
              s.version = "0.4. 
     | 
| 
      
 5 
     | 
    
         
            +
              s.version = "0.4.11"
         
     | 
| 
       6 
6 
     | 
    
         
             
              s.platform = %q{x86-mswin32-60}
         
     | 
| 
       7 
7 
     | 
    
         | 
| 
       8 
8 
     | 
    
         
             
              s.required_rubygems_version = Gem::Requirement.new(">= 1.2") if s.respond_to? :required_rubygems_version=
         
     | 
| 
       9 
9 
     | 
    
         
             
              s.authors = ["Victor Costan"]
         
     | 
| 
       10 
     | 
    
         
            -
              s.date = %q{2009-11- 
     | 
| 
      
 10 
     | 
    
         
            +
              s.date = %q{2009-11-16}
         
     | 
| 
       11 
11 
     | 
    
         
             
              s.description = %q{Interface with ISO 7816 smart cards.}
         
     | 
| 
       12 
12 
     | 
    
         
             
              s.email = %q{victor@costan.us}
         
     | 
| 
       13 
13 
     | 
    
         
             
              s.extra_rdoc_files = ["BUILD", "CHANGELOG", "LICENSE", "README", "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.rb", "lib/smartcard/gp/asn1_ber.rb", "lib/smartcard/gp/cap_loader.rb", "lib/smartcard/gp/des.rb", "lib/smartcard/gp/gp_card_mixin.rb", "lib/smartcard/iso/apdu_error.rb", "lib/smartcard/iso/auto_configurator.rb", "lib/smartcard/iso/iso_card_mixin.rb", "lib/smartcard/iso/jcop_remote_protocol.rb", "lib/smartcard/iso/jcop_remote_server.rb", "lib/smartcard/iso/jcop_remote_transport.rb", "lib/smartcard/iso/pcsc_transport.rb", "lib/smartcard/iso/transport.rb", "lib/smartcard/pcsc/pcsc_exception.rb"]
         
     | 
| 
       14 
     | 
    
         
            -
              s.files = ["BUILD", "CHANGELOG", "LICENSE", "Manifest", "README", "Rakefile", "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.rb", "lib/smartcard/gp/asn1_ber.rb", "lib/smartcard/gp/cap_loader.rb", "lib/smartcard/gp/des.rb", "lib/smartcard/gp/gp_card_mixin.rb", "lib/smartcard/iso/apdu_error.rb", "lib/smartcard/iso/auto_configurator.rb", "lib/smartcard/iso/iso_card_mixin.rb", "lib/smartcard/iso/jcop_remote_protocol.rb", "lib/smartcard/iso/jcop_remote_server.rb", "lib/smartcard/iso/jcop_remote_transport.rb", "lib/smartcard/iso/pcsc_transport.rb", "lib/smartcard/iso/transport.rb", "lib/smartcard/pcsc/pcsc_exception.rb", " 
     | 
| 
      
 14 
     | 
    
         
            +
              s.files = ["BUILD", "CHANGELOG", "LICENSE", "Manifest", "README", "Rakefile", "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.rb", "lib/smartcard/gp/asn1_ber.rb", "lib/smartcard/gp/cap_loader.rb", "lib/smartcard/gp/des.rb", "lib/smartcard/gp/gp_card_mixin.rb", "lib/smartcard/iso/apdu_error.rb", "lib/smartcard/iso/auto_configurator.rb", "lib/smartcard/iso/iso_card_mixin.rb", "lib/smartcard/iso/jcop_remote_protocol.rb", "lib/smartcard/iso/jcop_remote_server.rb", "lib/smartcard/iso/jcop_remote_transport.rb", "lib/smartcard/iso/pcsc_transport.rb", "lib/smartcard/iso/transport.rb", "lib/smartcard/pcsc/pcsc_exception.rb", "test/gp/asn1_ber_test.rb", "test/gp/cap_loader_test.rb", "test/gp/des_test.rb", "test/gp/gp_card_mixin_compat_test.rb", "test/gp/gp_card_mixin_test.rb", "test/gp/hello.apdu", "test/gp/hello.cap", "test/iso/auto_configurator_test.rb", "test/iso/iso_card_mixin_test.rb", "test/iso/iso_exception_test.rb", "test/iso/jcop_remote_test.rb", "test/pcsc/containers_test.rb", "test/pcsc/smoke_test.rb", "tests/ts_pcsc_ext.rb", "smartcard.gemspec", "lib/smartcard/pcsc.so"]
         
     | 
| 
       15 
15 
     | 
    
         
             
              s.homepage = %q{http://www.costan.us/smartcard}
         
     | 
| 
       16 
16 
     | 
    
         
             
              s.rdoc_options = ["--line-numbers", "--inline-source", "--title", "Smartcard", "--main", "README"]
         
     | 
| 
       17 
17 
     | 
    
         
             
              s.require_paths = ["lib", "ext"]
         
     | 
| 
       18 
18 
     | 
    
         
             
              s.rubyforge_project = %q{smartcard}
         
     | 
| 
       19 
19 
     | 
    
         
             
              s.rubygems_version = %q{1.3.5}
         
     | 
| 
       20 
20 
     | 
    
         
             
              s.summary = %q{Interface with ISO 7816 smart cards.}
         
     | 
| 
       21 
     | 
    
         
            -
              s.test_files = ["test/gp/asn1_ber_test.rb", "test/gp/cap_loader_test.rb", "test/gp/des_test.rb", "test/gp/gp_card_mixin_test.rb", "test/iso/auto_configurator_test.rb", "test/iso/iso_card_mixin_test.rb", "test/iso/iso_exception_test.rb", "test/iso/jcop_remote_test.rb", "test/pcsc/containers_test.rb", "test/pcsc/smoke_test.rb"]
         
     | 
| 
      
 21 
     | 
    
         
            +
              s.test_files = ["test/gp/asn1_ber_test.rb", "test/gp/cap_loader_test.rb", "test/gp/des_test.rb", "test/gp/gp_card_mixin_compat_test.rb", "test/gp/gp_card_mixin_test.rb", "test/iso/auto_configurator_test.rb", "test/iso/iso_card_mixin_test.rb", "test/iso/iso_exception_test.rb", "test/iso/jcop_remote_test.rb", "test/pcsc/containers_test.rb", "test/pcsc/smoke_test.rb"]
         
     | 
| 
       22 
22 
     | 
    
         | 
| 
       23 
23 
     | 
    
         
             
              if s.respond_to? :specification_version then
         
     | 
| 
       24 
24 
     | 
    
         
             
                current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
         
     | 
| 
         @@ -0,0 +1,99 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # Author:: Victor Costan
         
     | 
| 
      
 2 
     | 
    
         
            +
            # Copyright:: Copyright (C) 2008 Massachusetts Institute of Technology
         
     | 
| 
      
 3 
     | 
    
         
            +
            # License:: MIT
         
     | 
| 
      
 4 
     | 
    
         
            +
             
     | 
| 
      
 5 
     | 
    
         
            +
            require 'smartcard'
         
     | 
| 
      
 6 
     | 
    
         
            +
             
     | 
| 
      
 7 
     | 
    
         
            +
            require 'test/unit'
         
     | 
| 
      
 8 
     | 
    
         
            +
             
     | 
| 
      
 9 
     | 
    
         
            +
            require 'rubygems'
         
     | 
| 
      
 10 
     | 
    
         
            +
            require 'flexmock/test_unit'
         
     | 
| 
      
 11 
     | 
    
         
            +
             
     | 
| 
      
 12 
     | 
    
         
            +
             
     | 
| 
      
 13 
     | 
    
         
            +
            # Tests the GlobalPlatform code against old (secure channel 01) cards.
         
     | 
| 
      
 14 
     | 
    
         
            +
            class GpCardMixinCompatTest < Test::Unit::TestCase
         
     | 
| 
      
 15 
     | 
    
         
            +
              GpCardMixin = Smartcard::Gp::GpCardMixin
         
     | 
| 
      
 16 
     | 
    
         
            +
              
         
     | 
| 
      
 17 
     | 
    
         
            +
              # The sole purpose of this class is wrapping the mixin under test.
         
     | 
| 
      
 18 
     | 
    
         
            +
              class MixinWrapper
         
     | 
| 
      
 19 
     | 
    
         
            +
                include GpCardMixin
         
     | 
| 
      
 20 
     | 
    
         
            +
              end
         
     | 
| 
      
 21 
     | 
    
         
            +
              
         
     | 
| 
      
 22 
     | 
    
         
            +
              def setup
         
     | 
| 
      
 23 
     | 
    
         
            +
                @host_auth = [0x00, 0x65, 0x07, 0x37, 0xD4, 0xB8, 0xDF, 0xDE, 0xD0, 0x7B,
         
     | 
| 
      
 24 
     | 
    
         
            +
                              0xAA, 0xA2, 0xDE, 0xDE, 0x82, 0x8B]    
         
     | 
| 
      
 25 
     | 
    
         
            +
                @host_challenge = [0x83, 0x6B, 0x31, 0x7D, 0xE1, 0x57, 0x45, 0x53]
         
     | 
| 
      
 26 
     | 
    
         
            +
                @max_apdu_length = 0x0F
         
     | 
| 
      
 27 
     | 
    
         
            +
              end
         
     | 
| 
      
 28 
     | 
    
         
            +
             
     | 
| 
      
 29 
     | 
    
         
            +
              def mock_card_manager_query(channel_mock)
         
     | 
| 
      
 30 
     | 
    
         
            +
                flexmock(channel_mock).should_receive(:exchange_apdu).
         
     | 
| 
      
 31 
     | 
    
         
            +
                    with([0x00, 0xA4, 0x04, 0x00, 0x00, 0x00]).
         
     | 
| 
      
 32 
     | 
    
         
            +
                    and_return([0x6F, 16, 0x84, 8, 0xA0, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00,
         
     | 
| 
      
 33 
     | 
    
         
            +
                                0x00, 0xA5, 4, 0x9F, 0x65, 1, 0x0F, 0x90, 0x00])    
         
     | 
| 
      
 34 
     | 
    
         
            +
              end
         
     | 
| 
      
 35 
     | 
    
         
            +
              
         
     | 
| 
      
 36 
     | 
    
         
            +
              def test_gp_card_manager_aid
         
     | 
| 
      
 37 
     | 
    
         
            +
                mock = MixinWrapper.new
         
     | 
| 
      
 38 
     | 
    
         
            +
                mock_card_manager_query mock
         
     | 
| 
      
 39 
     | 
    
         
            +
                golden = [0xA0, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00]
         
     | 
| 
      
 40 
     | 
    
         
            +
                assert_equal golden, mock.gp_card_manager_aid
         
     | 
| 
      
 41 
     | 
    
         
            +
              end
         
     | 
| 
      
 42 
     | 
    
         
            +
              
         
     | 
| 
      
 43 
     | 
    
         
            +
              def mock_card_manager_select(channel_mock)
         
     | 
| 
      
 44 
     | 
    
         
            +
                flexmock(channel_mock).should_receive(:exchange_apdu).
         
     | 
| 
      
 45 
     | 
    
         
            +
                    with([0x00, 0xA4, 0x04, 0x00, 0x08, 0xA0, 0x00, 0x00, 0x00, 0x03, 0x00,
         
     | 
| 
      
 46 
     | 
    
         
            +
                          0x00, 0x00, 0x00]).
         
     | 
| 
      
 47 
     | 
    
         
            +
                    and_return([0x6F, 16, 0x84, 8, 0xA0, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00,
         
     | 
| 
      
 48 
     | 
    
         
            +
                                0x00, 0xA5, 4, 0x9F, 0x65, 1, 0x0F, 0x90, 0x00])    
         
     | 
| 
      
 49 
     | 
    
         
            +
              end
         
     | 
| 
      
 50 
     | 
    
         
            +
                
         
     | 
| 
      
 51 
     | 
    
         
            +
              def test_select_application
         
     | 
| 
      
 52 
     | 
    
         
            +
                mock = MixinWrapper.new
         
     | 
| 
      
 53 
     | 
    
         
            +
                mock_card_manager_query mock
         
     | 
| 
      
 54 
     | 
    
         
            +
                mock_card_manager_select mock
         
     | 
| 
      
 55 
     | 
    
         
            +
                app_data = mock.select_application mock.gp_card_manager_aid
         
     | 
| 
      
 56 
     | 
    
         
            +
             
     | 
| 
      
 57 
     | 
    
         
            +
                golden = { :aid => mock.gp_card_manager_aid, :max_apdu_length => 0x0F }
         
     | 
| 
      
 58 
     | 
    
         
            +
                assert_equal golden, app_data
         
     | 
| 
      
 59 
     | 
    
         
            +
              end
         
     | 
| 
      
 60 
     | 
    
         
            +
                
         
     | 
| 
      
 61 
     | 
    
         
            +
              def mock_channel_setup(channel_mock)
         
     | 
| 
      
 62 
     | 
    
         
            +
                flexmock(channel_mock).should_receive(:exchange_apdu).
         
     | 
| 
      
 63 
     | 
    
         
            +
                   with([0x80, 0x50, 0x00, 0x00, 0x08, 0x83, 0x6B, 0x31, 0x7D, 0xE1, 0x57,
         
     | 
| 
      
 64 
     | 
    
         
            +
                         0x45, 0x53, 0x00]).
         
     | 
| 
      
 65 
     | 
    
         
            +
                   and_return([0x00, 0x00, 0x63, 0x06, 0x00, 0x22, 0x04, 0x91, 0x06, 0x77,
         
     | 
| 
      
 66 
     | 
    
         
            +
                               0xFF, 0x01, 0xB8, 0xAA, 0x0E, 0xF4, 0xD5, 0x56, 0x77, 0x90,
         
     | 
| 
      
 67 
     | 
    
         
            +
                               0x84, 0x03, 0xF4, 0x96, 0x93, 0x1E, 0x30, 0x48, 0x90, 0x00])
         
     | 
| 
      
 68 
     | 
    
         
            +
                flexmock(Smartcard::Gp::Des).should_receive(:random_bytes).with(8).
         
     | 
| 
      
 69 
     | 
    
         
            +
                                             and_return(@host_challenge.pack('C*'))    
         
     | 
| 
      
 70 
     | 
    
         
            +
              end
         
     | 
| 
      
 71 
     | 
    
         
            +
              
         
     | 
| 
      
 72 
     | 
    
         
            +
              def test_gp_setup_secure_channel
         
     | 
| 
      
 73 
     | 
    
         
            +
                mock = MixinWrapper.new
         
     | 
| 
      
 74 
     | 
    
         
            +
                mock_channel_setup mock
         
     | 
| 
      
 75 
     | 
    
         
            +
                golden = {
         
     | 
| 
      
 76 
     | 
    
         
            +
                    :key_diversification => [0x00, 0x00, 0x63, 0x06, 0x00, 0x22, 0x04, 0x91,
         
     | 
| 
      
 77 
     | 
    
         
            +
                                             0x06, 0x77],
         
     | 
| 
      
 78 
     | 
    
         
            +
                    :key_version => 0xFF, :protocol_id => 1,
         
     | 
| 
      
 79 
     | 
    
         
            +
                    :challenge => [0xB8, 0xAA, 0x0E, 0xF4, 0xD5, 0x56, 0x77, 0x90],
         
     | 
| 
      
 80 
     | 
    
         
            +
                    :auth => [0x84, 0x03, 0xF4, 0x96, 0x93, 0x1E, 0x30, 0x48]
         
     | 
| 
      
 81 
     | 
    
         
            +
                }
         
     | 
| 
      
 82 
     | 
    
         
            +
                assert_equal golden, mock.gp_setup_secure_channel(@host_challenge)
         
     | 
| 
      
 83 
     | 
    
         
            +
              end
         
     | 
| 
      
 84 
     | 
    
         
            +
              
         
     | 
| 
      
 85 
     | 
    
         
            +
              def mock_channel_lock(channel_mock)
         
     | 
| 
      
 86 
     | 
    
         
            +
                flexmock(channel_mock).should_receive(:exchange_apdu).
         
     | 
| 
      
 87 
     | 
    
         
            +
                   with([0x84, 0x82, 0x00, 0x00, 0x10, 0xC2, 0x3F, 0x1D, 0x4D, 0xA5, 0x5F,
         
     | 
| 
      
 88 
     | 
    
         
            +
                         0xC7, 0x5F, 0x6C, 0x3A, 0x7A, 0x06, 0x05, 0xB4, 0xAE, 0x18]).
         
     | 
| 
      
 89 
     | 
    
         
            +
                   and_return([0x90, 0x00])  
         
     | 
| 
      
 90 
     | 
    
         
            +
              end
         
     | 
| 
      
 91 
     | 
    
         
            +
              
         
     | 
| 
      
 92 
     | 
    
         
            +
              def test_secure_channel
         
     | 
| 
      
 93 
     | 
    
         
            +
                mock = MixinWrapper.new
         
     | 
| 
      
 94 
     | 
    
         
            +
                mock_channel_setup mock
         
     | 
| 
      
 95 
     | 
    
         
            +
                mock_channel_lock mock
         
     | 
| 
      
 96 
     | 
    
         
            +
             
     | 
| 
      
 97 
     | 
    
         
            +
                mock.secure_channel
         
     | 
| 
      
 98 
     | 
    
         
            +
              end
         
     | 
| 
      
 99 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -89,7 +89,7 @@ class GpCardMixinTest < Test::Unit::TestCase 
     | 
|
| 
       89 
89 
     | 
    
         
             
              def mock_channel_lock(channel_mock)
         
     | 
| 
       90 
90 
     | 
    
         
             
                flexmock(channel_mock).should_receive(:exchange_apdu).
         
     | 
| 
       91 
91 
     | 
    
         
             
                   with([0x84, 0x82, 0x00, 0x00, 0x10, 0x00, 0x65, 0x07, 0x37, 0xD4, 0xB8,
         
     | 
| 
       92 
     | 
    
         
            -
                         0xDF, 0xDE, 0xD0, 0x7B, 0xAA, 0xA2, 0xDE, 0xDE, 0x82, 0x8B 
     | 
| 
      
 92 
     | 
    
         
            +
                         0xDF, 0xDE, 0xD0, 0x7B, 0xAA, 0xA2, 0xDE, 0xDE, 0x82, 0x8B]).
         
     | 
| 
       93 
93 
     | 
    
         
             
                   and_return([0x90, 0x00])  
         
     | 
| 
       94 
94 
     | 
    
         
             
              end
         
     | 
| 
       95 
95 
     | 
    
         | 
| 
         @@ -42,6 +42,10 @@ class IsoCardMixinTest < Test::Unit::TestCase 
     | 
|
| 
       42 
42 
     | 
    
         
             
                             s[:cla => 0x80, :ins => 0x0F, :p1 => 0xBA, :p2 => 0xBE,
         
     | 
| 
       43 
43 
     | 
    
         
             
                               :data => [0x31, 0x41, 0x59]],
         
     | 
| 
       44 
44 
     | 
    
         
             
                             'Specified everything'
         
     | 
| 
      
 45 
     | 
    
         
            +
                assert_equal [0x80, 0x0F, 0xBA, 0xBE, 0x03, 0x31, 0x41, 0x59],
         
     | 
| 
      
 46 
     | 
    
         
            +
                             s[:cla => 0x80, :ins => 0x0F, :p1 => 0xBA, :p2 => 0xBE,
         
     | 
| 
      
 47 
     | 
    
         
            +
                               :data => [0x31, 0x41, 0x59], :le => false],
         
     | 
| 
      
 48 
     | 
    
         
            +
                             'Specified everything, Le=false'
         
     | 
| 
       45 
49 
     | 
    
         
             
                assert_raise(RuntimeError, 'Did not specify INS') do
         
     | 
| 
       46 
50 
     | 
    
         
             
                  s[:cla => 0x80, :p1 => 0xBA, :p2 => 0xBE, :data => [0x31, 0x41, 0x59]]
         
     | 
| 
       47 
51 
     | 
    
         
             
                end
         
     | 
    
        metadata
    CHANGED
    
    | 
         @@ -1,7 +1,7 @@ 
     | 
|
| 
       1 
1 
     | 
    
         
             
            --- !ruby/object:Gem::Specification 
         
     | 
| 
       2 
2 
     | 
    
         
             
            name: smartcard
         
     | 
| 
       3 
3 
     | 
    
         
             
            version: !ruby/object:Gem::Version 
         
     | 
| 
       4 
     | 
    
         
            -
              version: 0.4. 
     | 
| 
      
 4 
     | 
    
         
            +
              version: 0.4.11
         
     | 
| 
       5 
5 
     | 
    
         
             
            platform: x86-mswin32-60
         
     | 
| 
       6 
6 
     | 
    
         
             
            authors: 
         
     | 
| 
       7 
7 
     | 
    
         
             
            - Victor Costan
         
     | 
| 
         @@ -9,7 +9,7 @@ autorequire: 
     | 
|
| 
       9 
9 
     | 
    
         
             
            bindir: bin
         
     | 
| 
       10 
10 
     | 
    
         
             
            cert_chain: []
         
     | 
| 
       11 
11 
     | 
    
         | 
| 
       12 
     | 
    
         
            -
            date: 2009-11- 
     | 
| 
      
 12 
     | 
    
         
            +
            date: 2009-11-16 00:00:00 -05:00
         
     | 
| 
       13 
13 
     | 
    
         
             
            default_executable: 
         
     | 
| 
       14 
14 
     | 
    
         
             
            dependencies: 
         
     | 
| 
       15 
15 
     | 
    
         
             
            - !ruby/object:Gem::Dependency 
         
     | 
| 
         @@ -124,10 +124,10 @@ files: 
     | 
|
| 
       124 
124 
     | 
    
         
             
            - lib/smartcard/iso/pcsc_transport.rb
         
     | 
| 
       125 
125 
     | 
    
         
             
            - lib/smartcard/iso/transport.rb
         
     | 
| 
       126 
126 
     | 
    
         
             
            - lib/smartcard/pcsc/pcsc_exception.rb
         
     | 
| 
       127 
     | 
    
         
            -
            - smartcard.gemspec
         
     | 
| 
       128 
127 
     | 
    
         
             
            - test/gp/asn1_ber_test.rb
         
     | 
| 
       129 
128 
     | 
    
         
             
            - test/gp/cap_loader_test.rb
         
     | 
| 
       130 
129 
     | 
    
         
             
            - test/gp/des_test.rb
         
     | 
| 
      
 130 
     | 
    
         
            +
            - test/gp/gp_card_mixin_compat_test.rb
         
     | 
| 
       131 
131 
     | 
    
         
             
            - test/gp/gp_card_mixin_test.rb
         
     | 
| 
       132 
132 
     | 
    
         
             
            - test/gp/hello.apdu
         
     | 
| 
       133 
133 
     | 
    
         
             
            - test/gp/hello.cap
         
     | 
| 
         @@ -138,6 +138,7 @@ files: 
     | 
|
| 
       138 
138 
     | 
    
         
             
            - test/pcsc/containers_test.rb
         
     | 
| 
       139 
139 
     | 
    
         
             
            - test/pcsc/smoke_test.rb
         
     | 
| 
       140 
140 
     | 
    
         
             
            - tests/ts_pcsc_ext.rb
         
     | 
| 
      
 141 
     | 
    
         
            +
            - smartcard.gemspec
         
     | 
| 
       141 
142 
     | 
    
         
             
            - lib/smartcard/pcsc.so
         
     | 
| 
       142 
143 
     | 
    
         
             
            has_rdoc: true
         
     | 
| 
       143 
144 
     | 
    
         
             
            homepage: http://www.costan.us/smartcard
         
     | 
| 
         @@ -177,6 +178,7 @@ test_files: 
     | 
|
| 
       177 
178 
     | 
    
         
             
            - test/gp/asn1_ber_test.rb
         
     | 
| 
       178 
179 
     | 
    
         
             
            - test/gp/cap_loader_test.rb
         
     | 
| 
       179 
180 
     | 
    
         
             
            - test/gp/des_test.rb
         
     | 
| 
      
 181 
     | 
    
         
            +
            - test/gp/gp_card_mixin_compat_test.rb
         
     | 
| 
       180 
182 
     | 
    
         
             
            - test/gp/gp_card_mixin_test.rb
         
     | 
| 
       181 
183 
     | 
    
         
             
            - test/iso/auto_configurator_test.rb
         
     | 
| 
       182 
184 
     | 
    
         
             
            - test/iso/iso_card_mixin_test.rb
         
     |