6263 IDPrime .NET Integ Guide
6263 IDPrime .NET Integ Guide
All information herein is either public information or is the property of and owned solely by Gemalto NV. and/or its subsidiaries
who shall have and keep the sole right to file patent applications or any other kind of intellectual property protection in
connection with such information.
Nothing herein shall be construed as implying or granting to you any rights, by license, grant or otherwise, under any
intellectual and/or industrial property rights of or concerning any of Gemaltos information.
This document can be used for informational, non-commercial, internal and personal use only provided that:
The copyright notice below, the confidentiality and proprietary legend and this full warning notice appear in all copies.
This document shall not be posted on any network computer or broadcast in any media and no modification of any part of
this document shall be made.
Use for any other purpose is expressly prohibited and may result in severe civil and criminal liabilities.
The information contained in this document is provided AS IS without any warranty of any kind. Unless otherwise expressly
agreed in writing, Gemalto makes no warranty as to the value or accuracy of information contained herein.
The document could include technical inaccuracies or typographical errors. Changes are periodically added to the information
herein. Furthermore, Gemalto reserves the right to make any change or improvement in the specifications data, information,
and the like described herein, at any time.
Gemalto hereby disclaims all warranties and conditions with regard to the information contained herein, including all
implied warranties of merchantability, fitness for a particular purpose, title and non-infringement. In no event shall
Gemalto be liable, whether in contract, tort or otherwise, for any indirect, special or consequential damages or any
damages whatsoever including but not limited to damages resulting from loss of use, data, profits, revenues, or
customers, arising out of or in connection with the use or performance of information contained in this document.
Gemalto does not and shall not warrant that this product will be resistant to all possible attacks and shall not incur,
and disclaims, any liability in this respect. Even if each product is compliant with current security standards in force
on the date of their design, security mechanisms' resistance necessarily evolves according to the state of the art in
security and notably under the emergence of new attacks. Under no circumstances, shall Gemalto be held liable for
any third party actions and in particular in case of any successful attack against systems or equipment
incorporating Gemalto products. Gemalto disclaims any liability with respect to security for direct, indirect,
incidental or consequential damages that result from any use of its products. It is further stressed that independent
testing and verification by the person using the product is particularly encouraged, especially in any application in
which defective, incorrect or insecure functioning could result in damage to persons or property, denial of service or
loss of privacy.
2007-14 Gemalto. All rights reserved. Gemalto and the Gemalto logo are trademarks and service marks of Gemalto N.V.
and/or its subsidiaries and are registered in certain countries. All other trademarks and service marks, whether registered or
not in specific countries, are the property of their respective owners.
Printed in France.
www.gemalto.com
x
Who Should Read This Book . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . x
Documentation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . x
Conventions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . xi
Windows Versions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . xi
Typographical Conventions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . xi
PART I
Chapter 1
13
Background . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Why .NET on a Smart Card? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
IDPrime .NET Card Application Development . . . . . . . . . . . . . . . . . . . . . . . . . . .
IDPrime .NET Card Characteristics . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Card Contents . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
File System . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
CardConfig.xml File . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Access Manager Applications . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Additional Contents . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Assemblies . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Data Files . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Smart Card Profile . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
13
13
14
14
14
14
15
17
17
17
17
18
Contents
Introduction
iv
Chapter 3
19
19
20
20
21
23
Assemblies . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Assemblies on the IDPrime .NET . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Assembly Security . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Loading Assemblies . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Application Domains . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Implementation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Differences between IDPrime .NET Application Domains and Standard .NET
Application Domains . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Application Lifecycle . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Loading . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Installation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Execution . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Termination . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Unloading . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Remoting . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Remoting in the .NET Smart Card Framework . . . . . . . . . . . . . . . . . . . . . . . . . .
Channels and Ports . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Using Custom Sinks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Why Make a Custom Sink? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
What Are the Limitations? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Designing a Custom Sink . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Using a Custom Sink . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Garbage Collection . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Garbage Collection . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
The GCControlAttribute . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
File System . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Key Points about the IDPrime .NET File System . . . . . . . . . . . . . . . . . . . . . . . .
Example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Data Storage . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Data Stored in Persistent Memory . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Data Stored in Volatile Memory . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
MemoryStreams . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Transactions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Why Transactions? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
How Transactions Work . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Out-of-Transaction Objects . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Security . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Access Manager . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Application Security . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Data Security . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Supporting Legacy Infrastructure . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Who Should Read This Section? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
The Problem with Legacy Applications . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Using Attributes to Manage APDUs . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Returning Data from the Card . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Handling Incorrect Requested Lengths . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Card Reset Event . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
23
23
24
24
25
25
25
26
26
26
26
26
26
27
27
28
29
32
32
32
32
33
34
34
34
35
35
35
36
36
36
37
37
37
37
38
39
40
41
44
45
45
45
45
47
47
47
Contents
Chapter 4
Chapter 5
Chapter 6
47
48
48
48
49
Card Explorer
51
Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Starting Card Explorer . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Connecting to the IDPrime .NET Card . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Toolbar . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Tab Layout . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Select Smartcard Reader Details . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Explorer Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Services Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Access Manager . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Card Element Properties . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Card Properties . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Folder/Directory and File Properties . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Public Key Tokens . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Identifying an Assembly . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Controlling Access to a File or Folder on the Card . . . . . . . . . . . . . . . . . . . . . . .
Managing Folders and Files . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Managing Folders . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Managing Files . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
51
51
51
53
54
55
56
58
59
60
60
63
67
67
67
68
68
70
72
72
72
73
74
74
74
Getting Started
76
vi
Chapter 7
Chapter 8
88
88
88
89
90
Code Samples
91
General Instructions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
SecureSession . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Description . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Running the Sample . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Code Extract . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
APDUAttribute . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Description . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Execution . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Code Extract . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Transactions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Description . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Execution . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Code Extract . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
91
92
92
93
93
96
96
96
96
97
97
97
97
Client-Side Components
98
SmartCard_Stub . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 98
Referencing the ContentManager from Your Project . . . . . . . . . . . . . . . . . . . . . 98
SmartCard.Runtime . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 99
Client Remoting Components . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 99
CardAccessor Class . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 99
AccessManagerClient Interface . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 99
C++ Marshaller . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 100
Why a C++ Marshaller? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 100
Where Can I Find the C++ Marshaller? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 100
Using the Marshaller . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 100
PART II
APDU ENCODING
Chapter 9
APDU Encoding
102
Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
APDU Format . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Argument Encoding . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Payload with length > FF . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
MSCM Answer Interpretation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
The APDUs Exchange Flow . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
102
102
103
104
105
105
106
106
106
106
107
107
107
109
110
Chapter 10
Contents
vii
110
111
111
112
112
112
113
113
PART III
CONFIGURING PARAMETERS
Chapter 11
Configuring Parameters
115
Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Configurable Parameters (.NET Minidriver Assembly) . . . . . . . . . . . . . . . . . . . . . .
Using SetCardProperty . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Using Installation Parameters . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Configurable Parameters (IDGo 5000 Bio) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
115
115
115
120
122
Troubleshooting
124
Communication Problems . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
The Easy Checklist . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Further Steps . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
SSO Option Deactivation Problem . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
124
124
124
125
126
Appendix A
Appendix B
Terminology
135
Abbreviations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 135
Glossary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 136
References
138
Standards and Specifications . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 138
Recommended Reading . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 139
Useful Web Site Addresses . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 139
viii
List of Figures
Figure 1 - .NET Smart Card . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
Figure 2 - IDPrime .NET On-Card and Off-Card Components . . . . . . . . . . . . . . . . . . 6
Figure 3 - The Smart Card CP User Interface . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7
Figure 4 - The Smart Card Verification CP User Interface . . . . . . . . . . . . . . . . . . . . . 8
Figure 5 - Microsoft Base CSP vs. Vendor-Specific Custom CSP . . . . . . . . . . . . . . 10
Figure 6 - .NET Card Explorer . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 15
Figure 7 - Example of CardConfig.xml File . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 16
Figure 8 - Libraries and Profiles Relationship . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 19
Figure 9 - Client - Server Communication Using Channels and Ports . . . . . . . . . . . 28
Figure 10 - Sample Server Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30
Figure 11 - Sample Client Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 31
Figure 12 - .NET Remoting Architecture with Custom Sinks . . . . . . . . . . . . . . . . . . . 32
Figure 13 - Properties Page for Assembly . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 43
Figure 14 - Share With Dialog . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 43
Figure 15 - Select Smart Card Reader dialog box . . . . . . . . . . . . . . . . . . . . . . . . . . . 52
Figure 16 - Log on to .NET Smart Card dialog box . . . . . . . . . . . . . . . . . . . . . . . . . . 52
Figure 17 - Card Explorer Toolbar . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 53
Figure 18 - Card Explorer Explorer Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54
Figure 19 - Card Explorer Services Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54
Figure 20 - Select Smartcard Reader Dialog Box . . . . . . . . . . . . . . . . . . . . . . . . . . . 55
Figure 21 - Card Explorer - Explorer Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 56
Figure 22 - Card Explorer Services Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 58
Figure 23 - Card Explorer - Card Element Properties . . . . . . . . . . . . . . . . . . . . . . . . 60
Figure 24 - Card Properties - General Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 61
Figure 25 - Card Properties - Advanced Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 62
Figure 26 - Folder Properties - General Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 63
Figure 27 - File Properties - Security Tab . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 64
Figure 28 - Share With... Dialog Box . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 65
Figure 29 - Modifying Permissions for a Public Key Token . . . . . . . . . . . . . . . . . . . . 66
Figure 30 - Contextual Menu for Folders . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 68
Figure 31 - The Open Dialog Box . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 69
Figure 32 - Contextual Menu for Executable Files . . . . . . . . . . . . . . . . . . . . . . . . . . 70
Figure 33 - Add-In Manager . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 73
Figure 34 - New Project Dialog Box (netCard Server) . . . . . . . . . . . . . . . . . . . . . . . . 74
Figure 35 - New Project Dialog Box (netCard Client Console) . . . . . . . . . . . . . . . . . 75
Figure 36 - New Blank Solution (Server Applications) . . . . . . . . . . . . . . . . . . . . . . . . 76
Figure 37 - New Project Dialog Box (netCard Server) . . . . . . . . . . . . . . . . . . . . . . . . 77
Figure 38 - New Blank Solution (Server Applications) . . . . . . . . . . . . . . . . . . . . . . . . 82
Figure 39 - New Project Dialog Box (netCard Client Console) . . . . . . . . . . . . . . . . . 83
Figure 40 - New Project (No On-card Templates) . . . . . . . . . . . . . . . . . . . . . . . . . . . 86
Figure 41 - Advanced Build Settings (No On-card Templates) . . . . . . . . . . . . . . . . . 86
Figure 42 - Add Reference (No On-card Templates) . . . . . . . . . . . . . . . . . . . . . . . . 87
Figure 43 - Add Reference (SmartCard_Stub) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 98
List of Tables
Table 1 - The Smart Card Profile . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Table 2 - Card Explorer Toolbar Icons Descriptions . . . . . . . . . . . . . . . . . . . . . . . . .
Table 3 - Select Smartcard Reader Options . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Table 4 - Card Element Descriptions and Menu Options . . . . . . . . . . . . . . . . . . . . .
Table 5 - Card Services . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Table 6 - Menu Options . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Table 7 - Card Properties - General Tab Elements . . . . . . . . . . . . . . . . . . . . . . . . . .
19
53
55
57
58
59
61
Contents
ix
.NET Smart Card Framework, the class libraries and managed runtime
environment in which applications execute on a .NET card
Part 1: .NET Technology describes the main concepts behind .NET and shows you
how to develop client and server applications.
Part 2: APDU Encoding provides information about how to code APDUs to call
methods.
Part 3: Configuring Parameters lists the parameters that can be configured using
the SetCardProperty method or by loading the card module assembly and
executing it by specifying the parameters you want to change from their defaults.
Documentation
For documentation about IDPrime .NET Cards, please go to Gemalto Product Catalog
and consult the Download section at http://www.gemalto.com/products/dotnet_card/
Introduction
This document describes Gemaltos IDPrime .NET smart cards, including their
architecture and general concepts about .NET technology. .NET Card technology
includes:
Introduction
xi
Conventions
The following conventions are used in this document:
Windows Versions
Where this document refers to Windows 7 and 8, it is equally applicable to Windows
Server 2008 R2 and Windows Server 2012.
Typographical Conventions
.NET Smart Cards documentation uses the following typographical conventions to
assist the reader of this document.
Convention
Example
Description
Bold
Type myscript.dll
>
Part I
1
Smart Card Background
The IDPrime .NET Card is a new-generation smart card. This section provides some
background about smart cards in general.
A smart card
A physical device or interface that enables data exchange between the smart card
and applications running on a host system
Smart Card
A conventional, contact-type smart card looks like a credit card with an embedded
integrated circuit chip. Its physical characteristics are defined by ISO 7816-1.
Here's an example of a conventional contact-type smart card.
Figure 1 - .NET Smart Card
The plastic media of the card may be printed to include a range of information,
including company logos and photos (for example, for scenarios in which the smart
card will also serve as an identification badge).
The working part of the smart card is the chip embedded at left center and includes:
The CPU (integrated circuit microprocessor). The chip in most smart cards is an 8or 16-bit microprocessor, usually using the Motorola 6805 or Intel 8051 instruction
set, with clock speeds up to 5 MHz. The chip in the IDPrime .NET card is a 32-bit
microprocessor.
Device/Interface
The most commonly deployed device to connect a smart card with a host system in
order to exchange data is a smart card reader. The reader is attached to the host
system using a serial, USB, or PC Card connection. The smart card is inserted into the
reader and when the card's contact points are correctly aligned, communication
between the smart card and the host system can be initiated.
A contactless smart card communicates with the host system using electromagnetic
fields using an antenna that is built into the card. Physical proximity to a card reader/
terminal that also includes an antenna triggers initiation of a communication protocol
that allows data exchange.
Because USB-capable smart cards incorporate the USB interface electronics normally
found in a smart card reader on the card itself, a USB-capable smart card interfaces
directly with the host system through a USB port. A conventional form factor USBcapable card uses a special receptacle (resembling a standard smart card reader but
containing no electronics) plugged into a USB port, while a cut-down format USBcapable card is inserted into a dongle that plugs directly into the USB port.
Operating System
The operating system is typically responsible for managing communication and
memory operations between the chip and any applications running on the smart card. If
the card supports Cryptography, the operating system may also provide an interface to
cryptographic hardware.
Applications
In order for a smart card to be useful, it must perform some operations that are
understood by a terminal or other external smart card reader. Smart card applications
range from a simple electronic purse to implementation of complex cryptographic
algorithms for digital security.
Traditionally, smart card applications were developed for a specific chip, and were
written in C by a specialized community of smart card developers. These applications
would be written to the chip at production time, and could not be changed after the card
was issued. This model of application development had some deficiencies. Moving
your application to a new type of chip meant rebuilding and possibly redesigning your
application for the new chip. Since applications needed to be written to the chip at
production time, the entire lifecycle of the smart card needed to be known in advance there would be no way to change the application in the field.
In the late 1990's, smart card application development changed radically. Smart card
companies released smart cards known as Java Cards, which contained a Java
interpreter. By writing applications in Java, smart card developers could insulate
themselves from the details of the specific chip hardware. Also, Java applications were
stored in non-volatile but erasable memory, so new applications could be loaded to the
card even after the card was in the hands of a user. Although the Java Card
represented a significant step forward in smart card development, it did not completely
isolate the developer from the protocols of the smart card. Developers were still
responsible for managing the communication between the card and the off-card
terminal.
The IDPrime .NET Card contains an IL interpreter that allows users to develop
applications for the smart card using the ECMA .NET standard. Applications can be
developed in any language that can be compiled to IL.
The following two software components are present only on smart cards that have
interpreters:
Runtime Environment
The runtime environment consists of two components. The first is an interpreter that is
responsible for running applications that are loaded to the card. The second
component is a collection of libraries that support applications. On a Java Card, these
libraries would contain the types and methods that are part of the Java Card API. On
the IDPrime .NET Card, these libraries contain a subset of the ECMA .NET libraries.
Loader
Since applications on cards with runtime environments can be loaded after the card is
produced, there must be a software component that is responsible for loading these
components to the card. The Loader on the IDPrime .NET Card is responsible for
several tasks:
Verifying that the assembly being loaded to the card is properly signed.
Ensuring that all types used by the assembly are already present on the card
The Loader is also responsible for removing applications from the card.
Windows 7 and 8 (and Server 2008 R2 and Server 2012): The base CSP is V7 and
is integrated already in Windows 7 and 8.
Windows Vista (and Server 2008): The base CSP is V6. For Vista SP1, base CSP
V6 is already integrated in Vista. However for pre-SP1 base CSP V6 needs to be
downloaded via Windows Update.
Windows XP and Server 2003: The base CSP is V5. The base CSP V5 must be
downloaded via Windows Update.
The IDPrime .NET Solution consists of both on-card and off-card components, as
shown in Figure 2. These include the card module assembly that resides on the
IDPrime .NET smart card itself, and some libraries known as the minidriver .dll, that
must be installed in the Windows System directory on the client computer.
This section describes the architecture for Windows 7 and 8 and the differences that
exist for the Vista and XP versions.
The Windows System directory differs according to the version of Windows as
follows:
For Windows XP, Vista and 32-bit OS version of Windows 7 and 8 - All components
are installed in C:\Windows\system32
For 64-bit OS version of Windows 7 and 8 - The 64-bit components are installed in
C:\Windows\system32 and the 32-bit components are installed in C:\Windows\
SysWOW64.
On-Card Components
IDPrime .NET includes the following on-card components:
Card Module Assembly (Gemalto) This is the oncard module for the
Minidriver. It is compliant with the Microsoft Minidriver v7 specification and paired
with the off-card minidriver dll library.
Off-Card Components
IDPrime .NET requires the following client libraries to be installed in the Windows
System directory (see previous page). Some implement a User Interface as shown in
Figures 3 and 4.
Base CSP v7: Minidriver based and integrated in Windows 7 and 8. This provides
the standard Windows 7 and 8 Credentials GUIs for user authentication.
It is the CP that manages the secure desktop functions such as smart card logon.
Its GUI is shown in Figure 3.
Figure 3 - The Smart Card CP User Interface
Gemalto has developed the IDGo 800 credential provider (CP) for Windows 7 and 8
which can manage up to 6 user PINs, each with its own PIN policy. The IDGo 800 CP
is an optional feature which, if installed, replaces the standard MS CPs (in Figure 3
and Figure 4).
You may also find the following link useful which lists various source codes and
describes their use:
http://msdn.microsoft.com/en-us/library/aa388162%28v=VS.85%29.aspx
10
Any Cryptographic
Application
Using CAPI
CAPI-based Crypto
Application
CAPI-based Crypto
Application
Vendor-Specific CSP
WinSCard API
(WinSCard.DLL)
Smart Card #1
Smart Card #3
11
Wide range of hybrid card options for combined physical and logical access control
Wide range of form factor: ID1 standard format, SIM-size format, card modules,
various USB token devices
High performance level based on 32-bit RISC secure chip (CC EAL 5+) with
cryptographic capability: On board key generation, true Random Number
Generator, RSA, DES/3DES, AES-256, Hash SHA1 / SHA256 / HMAC / MD5
Middleware Architecture
Compliance with Microsoft Base CSP / Crypto API and Minidriver v7 specifications:
No proprietary middleware to install on the user PC
Automatic download of the minidriver from the Microsoft Update site (Windows 7
and 8 and corresponing Windows Server versions)
Support of PKCS#11 crypto. architecture on Windows, Mac OS, Linux and UNIXlike Operating Systems.
OTP based on OATH event based specifications, with live and self provisioning
capabilities as option, EMV CAP version as option
12
Logon
Encryption of e-mails, files, directories, volumes, hard disks, USB memory tokens
High level of integration with Microsoft OS: Windows XP, Vista, Seven and
associated Server versions
Office
Exchange
Internet Explorer
EFS
Remote Desktop
For an updated list of IDPrime .NET cards compliant applications, please refer to the
IDPrime .NET pages http://www.gemalto.com/products/dotnet_card/.
2
The IDPrime .NET Card
The IDPrime .NET Card is a post-issuance programmable smart card. This new card is
based on technology from HiveMinded that is a subset of ECMA standards (language,
CLR, framework) for .NET. The IDPrime .NET Card was introduced by Gemalto in
2002 as an on-card application programming solution for .NET infrastructures. The
IDPrime .NET Card technology offers support for multi-language application
programming using an appropriate subset of the .NET class libraries. This subset has
been tailored for smart card applications, and provides an optimized runtime
environment on the smart card to enable communication between the card and
terminal using .NET remoting, ensure secure simultaneous execution of multiple
applications, and exploit many other .NET framework features.
Background
The IDPrime .NET Card is a new type of post-issuance programmable smart card. First
demonstrated in 2002, the card is designed to work with .NET platform applications.
Movement of more processing to the card for enhanced security and portability.
A managed runtime environment that is tailored for smart cards. The .NET Smart
Card Framework runtime environment (also called the .NET Smart Card
Framework common language runtime or CLR), is described in Common
Language Runtime (CLR) on page 20.
14
.NET Card technology includes application development tools that are fully
integrated into VisualStudio.NET, the standard development environment for .NET
applications.
Because .NET concepts are carried into the IDPrime .NET Card technology, the
learning curve for the growing developer base of .NET software engineers who
want to begin programming for IDPrime .NET cards is very short.
In addition, a key benefit to developing applications for the IDPrime .NET Cardis the
communication model, which enables developers to move away from the APDU-centric
communication architecture that is an underlying constraint on other programmable
smart card platforms. Instead, communication between the IDPrime .NET Card and the
host system uses a subset of the .NET Remoting feature, which is potentially capable
of supporting standard, widely-understood protocols (for example, XML, SOAP, HTTP),
as well as the traditional 7816-4 protocol APDU commands.
Card Contents
A new IDPrime .NET Card contains the .NET Smart Card Framework: the .NET Smart
Card Framework libraries and common language runtime (CLR). In addition to the
framework, the card contains a file system, a configuration file, and servers that enable
you to communicate with the card in order to do work.
As you work with the IDPrime .NET Card, you may add new assemblies or data files to
the card.
File System
When you connect to a new card the first time, the Card Explorer display shows that
the card contains a file system, a set of initial folders, and some initial files:
15
C:\Pub (public)
C:\System (contains the class libraries and any other libraries that are meant to be
accessible to all applications)
D:\Pub (public; pre-loaded with the CardConfig.xml file, which identifies aspects of
the card's capability to work with host-side applications)
Note: While the CardConfig.xml file is found in the D:\pub directory, which is readable
by all users on the card, its contents can be changed only by the cards admin user.
New files and folders can be added to the file system, subject to user permissions.
Files and folders can also be deleted from the card.
CardConfig.xml File
The CardConfig.xml file is pre-loaded on the IDPrime .NET Card and is stored in the
D:\Pub directory. The CardConfig.xml file contains information that can identify aspects
of the IDPrime .NET Card's capability to work with host-side applications.
Figure 7 shows an example of the contents of a CardConfig.xml file.
16
17
ContentManager
This is pre-loaded in the card (C:\System\SmartCard.dll). When a client application
queries the card to learn what services are available on the card, the Content
Management server responds by providing a list of available services.
SampleAccessManager
This is a sample from the SDK.
Additional Contents
As you develop applications for the card, you will install additional assemblies and data
files to the card.
Assemblies
Applications (.exe files) and libraries (.dll files) can be added to the card. While
execution of applications on the IDPrime .NET Card is not subject to user permissions,
managing applications and libraries (for example, adding new application files) on the
card is based on role-based access to the folders in which the application files are
found.
Default card permissions permit users with the Guest user role to add applications and
libraries to the \pub folders only. By default, the Admin user can add applications and
library files anywhere in the file system. Other users can add applications and libraries
as permitted by the user-code, path-access definition configured for each user on the
card at user creation time.
Note: The Guest role applies only to SmartAccessManager and does not exist in
Microsoft Card Module (MSCM). MSCM has Admin, User and Everyone roles
only.
The rules that govern applications permissions to access other applications or libraries
are based on the public key token list of the requested resource.
Application and library files are uploaded to the card using the Card Explorer tool,
either as a stand-alone application or as a Visual Studio .NET Add-in. In the Card
Explorer, identify a folder on the card to which you have access, right-click the folder,
and select Add > New File. In the Open dialog box, navigate to the application or
library file on the host system that you want to add to the card, and click Open. The file
is copied to the selected folder on the card.
Data Files
Files that are not executables or libraries can be added to the card, subject to user
permissions. The primary limitation is the amount of available non-volatile memory
(EEPROM) on the card.
Generally, data files are stored on smart cards so that access to the data contained
within the files can be controlled.
18
For example, key files associated with cryptographic services can be stored on the
IDPrime .NET Card. When the owner of the IDPrime .NET Card wants to perform an
operation that requires the key files (for example, to encrypt an e-mail message), he or
she attaches the card to the host system and provides authentication information (often
a PIN) in order to access the key files stored on the card.
Data files can also be stored on an IDPrime .NET Card for reasons unrelated to
cryptographic operations. Because data stored on an IDPrime .NET Card is not only
secure, it is also conveniently portable; a file might be loaded onto a card simply to
transport the file from one physical location to another.
Data files are added to specific folders within the D: file system, subject to user
permissions. Default card permissions permit users with the Guest user role to add
files to the D:\pub folder only. By default, the Admin user can add data files anywhere
in the D: file system. Other users can add data files as permitted by the user-data,
path-access definition configured for each user on the card at user creation time.
Note: Again, the Guest role applies only to SmartAccessManager.
Data files can be uploaded to the card using the Card Explorer tool. In the Card
Explorer, identify a folder on the card to which you have access, right-click the folder,
and select Add > New File. In the Open dialog box, navigate to the file on the host
system that you want to add to the card, and click Open. The file is copied to the
selected folder on the card. Data files can also be copied to the card using the standard
Windows Explorer drag-and-drop mechanism.
Compact profile, which allows implementation on devices like mobile phones and
personal digital assistants (PDAs).
The graphic shows the relationship between the libraries and the three current .NET
profiles.
19
The Smart card profile (colored purple in the above figure) includes a strict subset of
the two .NET libraries that make up the Kernel profile, plus one new, smart cardfocused library as listed in the following table.
Table 1 - The Smart Card Profile
File
Description
mscorlib.dll
system.xml.dll*
SmartCard.dll
20
Links the card-resident binary (on-card application) and manages execution of the
code throughout its lifecycle.
For more information about the application lifecycle implementation in the .NET Smart
Card Framework CLR, see Application Lifecycle on page 26.
The application domain model enables support for multiple applications running
simultaneously and securely on one IDPrime .NET Card. The safety and integrity of
each application is assured, because data in one application domain cannot directly
reference data in another domain.
For more information about the application domain implementation in the .NET Smart
Card Framework CLR, see Application Domains on page 25.
Garbage collection
Garbage collection eliminates the need for programmers to explicitly free memory
when an application no longer needs it; instead, a system thread periodically examines
all objects in the managed heap and removes any object to which all references have
disappeared. .NET Smart Card Framework implements a tailored garbage collection
mechanism that is well-suited to the resource constraints and particular needs of smart
cards.
For more information about the garbage collection implementation in the .NET Smart
Card Framework CLR, see Garbage Collection on page 34.
Remoting management
Exception handling
21
Transaction management
The .NET Smart Card Framework supports a persistent transaction model that ensures
the integrity of data on the IDPrime .NET Card, despite frequent and sometimes
unpredictable physical removal of the card from the system or terminal with which it is
communicating. The transaction management system includes a new caching
technology that greatly increases the speed of writes to EEPROM, while still
maintaining data integrity.
For more information about the transaction management implementation in the .NET
Smart Card Framework CLR, see Transactions on page 37.
Very similar to Data Security; that is, a public key token is required for an assembly to
access a dependent library. To enable a library to be shared with another assembly,
the corresponding public key token must be added as an attribute. Security policy is
determined by the Access Manager.
A common language runtime (CLR) that contains the elements needed to manage
applications loaded onto an IDPrime .NET Card (see Common Language Runtime
(CLR) on page 20 for details).
A special upload file format optimized for smart card profile devices. This is an
alternative that produces a much smaller (by a factor of 4) binary file than a full
.NET assembly, better suited to the constraints of a smart card.
The .NET Smart Card Framework has been adapted to accommodate the smart
card memory model, in which an application is stored in persistent memory and
activated when an external application talks to it.
Non-vector arrays (arrays with more than one dimension or with lower bounds
other than zero) are not supported in the .NET Smart Card Framework.
The varargs feature set (supports variable length argument lists and runtime-typed
pointers) is not supported in the .NET Smart Card Framework. However, the .NET
Smart Card Framework supports runtime-typed pointers.
Assembly scope names are ignored in the .NET Smart Card Framework, and types
are identified by their name alone. Two types with the same name in different
assemblies are considered to be identical. Only the method signature default
calling convention is supported.
There are no implicit types in the .NET Smart Card Framework CLR. All types are
explicitly defined in the metadata loaded into the CLR. In the presence of multiple
loaded assemblies, it is possible to have multiple definitions for types that might
normally be implicit. However, the CLR treats these multiple definitions as if there
was a single one; there is no way to distinguish if there is one definition or several.
Asynchronous calls are not supported in the .NET Smart Card Framework.
22
New slot member overriding is not supported in the .NET Smart Card Framework.
The existing slot for member overriding is supported.
(Class Layout) Only autolayout of classes is supported in the .NET Smart Card
Framework. (The loader is free to lay out the class in any way it sees fit.)
The zero init flag is not supported in the .NET Smart Card Framework; local and
memory pools are never initialized to zero.
Locks and threads are not supported the in .NET Smart Card Framework;
therefore, any types associated with these constructs are not supported.
The security descriptor method state is not supported in the .NET Smart Card
Framework.
3
Concepts and Models
The .NET Smart Card Framework supports runtime features that are described in
Chapter 2 - The IDPrime .NET Card. This chapter, expands on those descriptions.
Assemblies
Compiled .NET software is typically distributed in the form of assemblies. Assemblies
perform a number of different functions in .NET, including containing the executable
code as well as defining type, security, and reference boundaries. Microsofts .NET
Framework Developer Center provides detailed documentation of various aspects of
.NET assemblies in . We assume that you are familiar with concepts related to
Microsoft .NET assemblies.
The IDPrime .NET Card uses assemblies in the same manner as a Microsoft .NET
environment. However, IDPrime .NET assemblies go through a conversion process in
order to optimize for space usage and to ensure that the assembly does not use types
that are unsupported on the card. This conversion process is hidden from the user, and
is performed automatically at compilation time when developing an application using
Visual Studio .NET.
Assemblies loaded to the card must be strong name signed (see Glossary).
Assemblies that are not strong name signed will be rejected by the smart card. The
manifest (see Glossary) of the signed assembly contains the public key of the key
pair used for the signature, which enables certain functionalities such as:
It allows the smart card runtime to verify the integrity of an assembly being
loaded.
The public key token associated with the assembly is used to grant or deny the
assembly access to certain file system resources, and to grant or deny interapplication remoting calls.
Because assemblies and types on the card are considered unique after they are
signed, it is not possible to download more than one copy of an assembly to the
card, even if the assemblies are in different directories. It is, however, possible to
have two assemblies that contain the same types and namespaces, as long as the
two assemblies are not signed with the same key.
24
An executable assembly can use the types defined in the library assembly even if
they do not reside in the same directory.
The IDPrime .NET Card has only limited support for Reflection. Only
System.Reflection.Assembly and System.Reflection.AssemblyName classes with
few methods are supported.
IDPrime .NET assemblies can register themselves for deletion. An assembly might
choose to do this, for example, when the application has expired (for example, a
coupon application) or when an application felt it was under attack. For details on
the self-deletion process, please refer to the online help (OLH) documentation in
Start > Programs > .NET Smartcard Framework SDK > X.X.XXX > Help >
.NETSmartcardFramework.
Assembly Security
Security privileges of an assembly are controlled primarily by the public key token of
the assembly. One assembly can grant or deny access to its methods or data by
adding or removing the public key token of another assembly to or from its access
control lists. For more details see Data Security on page 44.
When a new assembly is developed and loaded in the .NET card, it is recommended
that this assembly does not use the card file system, or at least does not store any
critical data in the card file system. The critical data of the assembly will be better
protected if kept in the assemblys private memory.
Loading Assemblies
Assemblies can be loaded to the card using the IDPrime .NET Card Explorer tool, an
NAnt Task, or an API exposed by the SmartCard.CardAccessor.CardAccessor class.
For example:
// This code loads an assembly from the D:\Projects directory of the
// local hard drive to the C:\Pub directory of the card, and then
// executes the assembly.
CardAccessor ca = new CardAccessor("Schlumberger Reflex USB v2");
ca.LoadAssembly(@"D:\Projects\MyAssembly.exe", @"C:\Pub");
ca.ExecuteAssembly(@"C:\Pub\MyAssembly.exe");
For more details on the CardAccessor API, see the IDPrime .NET Smart Card
Client API documentation in Start > Programs > .NET Smartcard Framework
SDK > X.X.XXX > Help > .NETSmartcardClientAPI.
25
Application Domains
The application domain model enables support for multiple applications running
simultaneously and securely on one .NET Card. In the .NET Smart Card Framework
runtime, every application executes in a secure, isolated execution area, which
enforces strict firewalls between applications and helps maintain data integrity. Data in
one domain cannot be accessed from any other domain. For more details about the
.NET application domain model, see Microsofts .NET Framework Developer Center.
Implementation
The .NET Smart Card Framework uses the type System.AppDomain to isolate running
instances of applications from one another by executing each instance in an isolated
environment. The safety and integrity of each application is assured, because data in
one application domain cannot directly reference data in another domain.
An application domain serves as the container for assemblies and types when loaded
into memory at runtime. It can be useful to think about an application domain as the
logical equivalent of a process in a Win32 application. Similar to processes, application
domains can be started and stopped independently.
The ExecuteAssembly method of an AppDomain can only be executed from off the
card, either through the Card Explorer or through the
SmartCard.CardAccessor.CardAccessor API (see the IDPrime .NET Smart Card
Client API documentation in Start > Programs > .NET Smartcard Framework
SDK > X.X.XXX > Help > .NETSmartcardClientAPI. In the OLH, see
SmartCard.Accessor > CardAccessor Class.
If an application domain does not create a service, the application domain will be
garbage collected. For example, if application alpha.exe does not create a service,
the .exe file will remain on the card after execution, but there will be no running
application domain. If alpha.exe DOES create a service, the alpha.exe application
domain continues to run (even after the Main method exits) until the service is
deleted.
For example:
if (timesUsed > 10)
AppDomain.Unload(AppDomain.CurrentDomain);
26
Application Lifecycle
An IDPrime .NET Card application is managed by the common language runtime
(CLR) throughout its lifecycle, beginning when it is converted to a binary format that
can be loaded onto the card.
Loading
An IDPrime .NET Card application can be created using any supported .NET
programming language (for example, C# or VisualBasic.NET). After the code is written,
it is compiled to .NETs Microsoft intermediary language (MSIL) format. This
compilation produces a standard .NET assembly.
Before it is loaded onto the card, the .NET assembly is converted from its standard
compiled form to the .NET Smart Card Framework's card-resident binary format, which
produces a much smaller (by a factor of 4) binary than a full .NET assembly. The
converted binary is called a card-resident binary. The converted binary must be strongname signed. This is the application file that is loaded onto the IDPrime .NET Card.
Installation
Each executable binary has a single entry point, a method of the following form:
public static int Main
After successfully loading and linking a new binary onto the card, the Main method is
called to execute an application-specific installation. The application must also register
its remote types with the .NET Smart Card Framework runtime to allow clients to
remote call methods on the newly installed application.
See Remoting on page 27 for more information about remoting.
Execution
The .NET Smart Card Framework implements a client/server model, in which the host
system or terminal is the client, and the IDPrime .NET Card is the server. Interaction is
always initiated by the client using a request/reply protocol.
Server applications running on the card are persistent; that is, the applications do not
terminate when power is turned off (when the card is removed from the reader or
terminal) or the card is reset. If one of these events occurs, when the card is
reconnected, the application's state does not change from its previous state.
See Transactions on page 37 for more information about transaction persistence.
Termination
A service on the card stops running when the service is unregistered. You can do this
both programmatically and by using the Card Explorer tool. When the service is
unregistered, the running instance is deleted, and its memory is reclaimed by the
garbage collector.
Unloading
After a service has been terminated, the binary containing that service can be removed
from the card. A loaded assembly that is still exposing a service cannot be unloaded.
The service must be terminated first.
27
Remoting
Remoting in the .NET Framework allows one operating system process or program to
communicate with another process running on the same computer, or on two
computers connected by a local network or the Internet.
.NET remoting provides an abstract approach to inter-process communication that
separates the remotable object from a specific client- or server-application domain and
from a specific mechanism of communication. As a result, it is flexible and easily
customizable.
The .NET Smart Card Framework extends standard .NET remoting and allows a
program executing on a PC to communicate with a process running on an IDPrime
.NET Card, and also allows a program running in one application domain to access
code or data in a process running in another application domain within the IDPrime
.NET Card. For more information about application domains, see Application
Domains on page 25.
28
Figure 9 illustrates how the client and server communicate using channels and
named ports in the .NET Framework.
In the .NET Smart Card Framework, identifying a specific port to associate with a
channel is not always feasible, so a new mechanism for specifying the channel mode
has been created. See Server Sample Code on page 29 for details about creating a
.NET Smart Card Framework server that makes objects available for remoting.
In the .NET Framework, your client code also creates a channel associated with a
specific port, and then uses the Activator class to obtain a reference to the remote
object. You identify a remote object with the URL of the computer on which it is located,
the name of the remote class, and a URI that you assign.
In the .NET Smart Card Framework, you also use the Activator class to obtain a
reference to the remote object, using the new mechanism for specifying the channel
mode previously mentioned.
The APDUChannel supports URL's of the format:
"apdu://<name of the smart card reader>:<the port on which the service
is registered>/<the name of the service>"
For example:
"apdu://Gemalto Reflex USB v2:2222/CardService"
In addition to explicitly naming the reader to connect to, you can also use the reserved
names promptDialog and selfDiscover. The promptDialog mechanism displays a
dialog box and allows the user to select which reader to use. The selfDiscover
mechanism attempts to find the requested service by attempting to connect to any
.NET smart cards attached to the machine.
A simple .NET Smart Card Framework remoting example follows.
29
Example
Server Sample Code
First, create the server, which listens for calls from clients and connects them to the
remotable class. Here's what the code does:
1
Registers the channel with the .NET Smart Card Framework infrastructure; in the
sample code:
ChannelServices.RegisterChannel(chan)
The first argument identifies the class being registered; in the sample code:
typeof(MyRemoteClass)
The second argument specifies the URI for the class; in the sample code:
MyServiceURI. The client will use this URI when calling the class.
The third argument specifies that if there are multiple calls to the class (from more
than one client), they will all be serviced by the same instance of the class, in the
sample code: WellKnownObjectMode.Singleton. The two available modes
are:
SingleCall - Single Call objects service one and only one request coming in.
Single Call objects are useful in scenarios where the objects are required to do
a finite amount of work. Single Call objects are usually not required to store
state information, and they cannot hold state information between method calls.
Singleton - Singleton objects service multiple clients and, hence, share data by
storing state information between client invocations. They are useful in cases in
which data needs to be shared explicitly between clients and also in which the
overhead of creating and maintaining objects is substantial.
30
Creates an APDUClientChannel.
Registers the channel with the .NET Smart Card Framework infrastructure.
The Activator.GetObject() method accepts two arguments: The first is the type
of the remote class, which you can obtain by using the typeof() method with the class's
namespace and name as argument; the second argument has the following parts:
apdu:// - identifies the protocol; apdu is specified because the client and the
server are using an APDUChannel for communication.
<mode> - identifies the card connection mode to work around the fact that in the
.NET Smart Card context, the port through which the secure channel will work
cannot always be identified. In the sample code, the mode is prompt:unknown,
which means that the application will display a dialog box in which the user will be
required to select the reader in which the .NET Smart Card is inserted and active.
31
Description
prompt
<hard-coded reader>
SelfDiscover
The application searches for a card containing the service that the
application is requesting. If the application does not find a suitable
card, the Select Card Reader dialog box is displayed, and the
user must select the reader to use.
SelfDiscoverNoPrompt
The application searches for a card containing the service that the
application is requesting. If the application does not find a suitable
card, an exception is thrown. This mode is primarily used for an
application that is not allowed to display dialog boxes, for
example, Windows services.
The URI associated with the remote class, which must match the URI established
by the server; in the sample code: MyServiceUri.
System;
System.Runtime.Remoting;
System.Runtime.Remoting.Channels;
System.Runtime.Remoting.Channels.APDU;
using RemotingServerDemo;
namespace RemotingClientDemo
{
public class Client
{
public static int Main(string [] args)
{
APDUClientChannel chan = new APDUClientChannel();
ChannelServices.RegisteredChannel(chan);
MyRemoteClass obj = (MyRemoteClass)
Activator.GetObject(typeof(RemotingServerDemo.MyRemoteClass),
"apdu://prompt/MyServiceUri");
Console.WriteLine(obj.SayHello("John");
return 0;
}
}
}
32
33
34
Garbage Collection
The .NET Smart Card Framework Common Language Runtime (CLR) includes
automatic memory management using a mechanism called garbage collection.
Garbage Collection
The garbage collection feature eliminates the need for programmers to explicitly free
memory when an application no longer needs it; instead, the runtime manages
memory. All objects are instantiated while under the control of the managed runtime,
and the code is verifiably type-safe. The garbage collector then detects when there are
no longer any program references to an object, and deletes all objects that are no
longer required, freeing up memory previously allocated to those objects.
In the .NET Smart Card Framework runtime, garbage collection takes place in
response to the following events:
After execution of a remoting call in which either a new object was allocated, or an
uncaught exception is thrown. This is an important point to note, because if your
method does not allocate an object, the garbage collector will not be invoked. You
can force garbage collection in a method that does not allocate an object by using
the GCControlAttribute
Note that unlike garbage collection on other platforms, the .NET Smart Card
Framework garbage collection does not take place during execution of an application
or during allocation of objects or arrays, nor does garbage collection automatically
execute when the system runs out of memory. This means that if you are creating a
large group of objects and setting them to null, they will not be collected until the end of
the remoting call. Because of this constraint, you need to design your application in
such a way that it does not rely on memory being freed immediately after objects are
set to null or no longer referenced. Since a smart card is a resource-constrained
device, it is recommended that you should try to keep object creation and deletion to a
minimum. More object creation and deletion implies more garbage collection time,
which might impact the performance of the application.
The GCControlAttribute
Although the standard behavior of the garbage control system satisfies most
programming needs, there are times when you may wish to exercise more control over
the garbage collection process. The GCControlAttribute allows you to either force or
skip garbage collection after a remoting method.
For example:
[GCControl(GCControlMode.Force)]
void MyMethod()
{
myMemberArray = null;
}
35
Normally, garbage collection would not be invoked after this method, since there is no
object allocation in the method. However, in this case, garbage collection will still be
invoked because we've used the GCAttribute with the GCControlMode.Force
parameter. This might be useful if myMemberArray was large, and we wanted this
memory to be available for the next remoting call.
Alternatively, we might want to skip garbage collection on a given method:
[GCControl(GCControlMode.Skip)]
void MyMethod()
{
myMemberArray = new byte[3];
}
Normally the above method would invoke garbage collection since there has been an
object allocation. However, for performance reasons, a developer might want to skip
garbage collection for this method. Using GCControlMode.Skip causes the system to
skip garbage collection for this method.
File System
The IDPrime .NET Card contains a file system that is fully accessible within the card
from the standard .NET System.IO namespace. The file system provides developers a
mechanism to separate their data from their code. This allows developers to replace an
assembly with an updated version without losing data that might be associated with
that assembly.
Only one FileStream may be open on a given file at any time. This means that it is
important to release FileStreams after returning from remoting calls in order to
avoid blocking another FileStream object from accessing the file.
FileStreams are closed when the card is Reset or when it is removed from the
reader. It is never safe to assume that a FileStream is open and valid unless you
have created or opened the stream in the same remoting call.
In this version of the card, file names are case sensitive. For example, the file
readme.txt is not the same file as Readme.txt.
Security of the file system is enforced by both the card's operating system using
token-based security (see Data Security on page 44), and by the current Access
Manager using role-based security (see Access Manager on page 40).
Example
The following example shows on-card manipulation of the file system by attempting to
create a file in each of the subdirectories of D:\Pub
public void Example(string filename, byte [] data)
{
string [] dirs = Directory.GetDirectories(@"D:\Pub");
foreach (string directory in dirs)
{
FileStream fs = new FileStream(@"D:\Pub\" + directory + @"\" +
filename,
36
FileMode.Create);
fs.Write(data, 0, data.Length);
fs.Close();
}
}
Data Storage
The IDPrime .NET Card contains both persistent memory and volatile memory that are
used for data storage. The persistent memory acts as persistent storage for the card data persists in it even after the card is removed from a smart card reader. Volatile
memory is reset when the card loses power and cannot be used for persistent storage.
37
MemoryStreams
There exists a special case of objects that exist in both persistent and volatile memory.
The MemoryStream object itself is in persistent memory, but the data to which it is
pointing will exist in volatile memory. When a card is reset, any memory streams are
disposed, and the data to which those streams pointed is lost. Memory streams provide
a fast mechanism for manipulating arrays of byte data because the data is manipulated
in fast volatile memory rather than slower persistent memory.
Transactions
The .NET Smart Card Framework supports a persistent transaction model that ensures
the integrity of data on the IDPrime .NET Card, despite frequent and sometimes
unpredictable physical removal of the card from the system or terminal with which it is
communicating.
Why Transactions?
A smart card can be removed from a reader at unpredictable times. When the removal
occurs, the card will lose power immediately. This can be a serious problem if you were
in the middle of updating a sequence of object fields. For example, you might be
updating an address in an object. If you update the street field, but the card is
removed before you update the city field, you could end up with an address that is
completely incorrect. You need a way to ensure that either all of the updates take
place, or none of them do.
Card removals are not the only interruption that you might worry about. You might be
concerned that an exception could be thrown in the middle of some field updates that
could leave the card in an inconsistent state. In this case, you would want a mechanism
for rolling back any field updates to the original state.
Example
In this example, the Increment method is marked as a transaction using the
Transaction attribute.
[Transaction]
private void Increment ()
{
counter++;
if (counter > 10)
{
throw new BadCountException();
}
}
38
In the example, a counter is incremented, and if the counter is greater than 10, an
exception is thrown. The exception is not caught in this method. (It is intended to be
caught by the caller.) Because executing the method results in an uncaught exception,
the sub-transaction aborts and any changes made by this method are rolled back. The
result is that the value of the counter will never exceed 10.
Out-of-Transaction Objects
Although in general, you would like to roll back any modifications made to your card if
the operation is interrupted, there may be cases where you might want the method to
be under transaction, but for a particular field of an object to be out of transaction.
One motivation for this is the PIN class. You can imagine that the logic for a PIN class
might be for the caller to send PIN data to a method, and the method would then pass
the data to the PIN object. If the data does not match the PIN, the number of remaining
tries on the PIN is decreased, and the method returns. What we want to avoid is for an
attacker to be able to try a PIN, cut power to the card if it fails, and have the number of
remaining tries reset by a transaction.
To avoid this type of attack, the .NET framework provides an OutOfTransaction
attribute that can be applied to the fields of an object. Fields annotated by this attribute
are always considered to be out of transaction. That means that even if it is used
inside a method that is under transaction, the field will not be rolled back to its previous
state if the transaction is interrupted. The PIN class of the card is built using an
OutOfTransaction attribute.
Here's an example of the OutOfTransaction attribute in action:
using System;
using System.Diagnostics;
using SmartCard;
using SmartCard.Services;
public class MySecureCounter
{
[OutOfTransaction]
byte counter;
public void Increase()
{
counter++;
}
public byte Value
{
get
{
return counter;
}
}
}
public class Test
{
MySecureCounter secCount = new MySecureCounter()
[Transaction]
public void TestWithAbortedTransaction()
39
{
secCount.Increase();
throw new Exception(); // abort
}
public void TestWithoutTransaction()
{
secCount.Increase();
throw new Exception(); // abort
}
static void Main()
{
Test test = new Test();
Debug.WriteLine("initial value = " test.secCount.Value);
// expect test.secCount.Value = 0
try
{
test.TestWithoutTransaction();
}
catch {}
Debug.WriteLine("second value = " test.secCount.Value);
// expect test.secCount.Value=1
try
{
test.TestWithAbortedTransaction();
}
catch {}
Debug.WriteLine("third value = " test.secCount.Value);
// expect test.secCount.Value = 1
}
}
Security
Security in the IDPrime .NET Card is generally discussed in one of three contexts:
Application Security. Applications deployed to the IDPrime .NET Card are always
signed assemblies. The public key token of these signed assemblies is used to
grant or deny privileges to a given application. For example, a library assembly
installed on the card might restrict unknown assemblies from using its API.
Data Security. Data for IDPrime .NET applications can be stored either internally
to the application or in the IDPrime .NET file system. Applications making use of
the file system can be assured that file-based data is secured by access control
lists associated with the public key tokens of on-card assemblies.
40
Access Manager
The resources such as files, directories, assemblies and their management in IDPrime
.NET Card are accessible using the ContentManager service (described later in the
documentation). Since these resources should only be accessed and managed by
authorized entities, mechanisms for authentication and authorization are required. It is
also envisioned that during the life cycle of the card, these mechanisms may need to
be changed. For example, a manufacturer of a smart card may trust a particular kind of
authentication mechanism that an issuer of the same smart card may think is
insufficient and weak. IDPrime .NET Card provides a flexible and extensible application
model such that any actor (provided it has authorization) in the lifecycle of the smart
card can implement its own authentication and authorization mechanisms. Some of the
authentication mechanisms for smart cards that are prevalent today are PINs, mutual
authentication using symmetric key algorithms, Biometric and so on.
The service that implements the above-mentioned authentication and authorization
specifics is called an AccessManager service. Like all other services, an
AccessManager service is a .NET Remoting application and is developed with the
requirement that it should extend an abstract class SmartCard.AccessManager of the
SmartCard.dll library.
The SmartCard.AccessManager class provides two abstract methods that should be
overridden by the extending class. These methods are:
AccessManagerRegistrationPolicyCheck(string objectUri,string
assemblyPath) : As mentioned above, the AccessManager can only be changed by
an authorized entity, and this method provides a way to determine if an
authenticated authority has the privileges to do so. This method is called when the
RegisterAccessManager method of ContentService is invoked. The name of
the service that is to be made the new AccessManager and the path to the
assembly containing the implementation class are passed as arguments. If the
current AccessManager does not entertain this request, an
UnauthorizedAccessException is thrown.
41
The IDPrime .NET Card shipped in the SDK contains an AccessManager service
called SampleAccessManager, which uses username/password-based authentication
and controls the access to resources using a role-based security mechanism. It is
described in detail in SampleAccessManager on page 49.
Application Security
This section discusses issues related to ensuring the integrity and authenticity of cardresident binaries, as well as ensuring the security of applications running on the card.
The .NET Assembly is converted to an interim binary format. These are the
components of the interim binary that is produced by conversion:
metadata
code
public key
Note: The metadata for a card-resident binary consists only of name and version
information for the binary (in contrast to the metadata in a full .NET assembly, which
includes a much larger set of data describing the assembly).
2
A hash is computed (using the SHA1 algorithm) based on the interim binary's
components, and then the hash is encrypted using the private key associated with
the interim binary's public key pair. The encrypted hash (which is also called the
signature) is stored as part of the binary. The components of the binary after
addition of the signature are:
metadata
code
public key
signature
A binary that includes a signature is ready for upload to the IDPrime .NET Card, where
it becomes a card-resident binary. The binary can be loaded using the CardManager
service, the Card Explorer, or the CardAccessor library, which provides a wrapper for
CM methods.
During upload of the binary to the card, each block of data is checked for accuracy
(unrelated to integrity/authenticity). If all blocks are loaded successfully, a hash is
computed using the public key, which has been extracted from the binary on the card.
The encrypted hash (signature) loaded onto the card is then decrypted, also using the
public key.
If the decrypted signature matches the hash computed on the card using the public
key, both the integrity and authenticity of the data are proven. Integrity is demonstrated
because the hash values match. Authenticity is demonstrated because the public key
can only be in the .binary loaded onto the card if the private key was known.
If the values do not match, the data integrity and authenticity of the binary cannot be
assured, and a BadImageFormatException exception is thrown. (The binary is not
loaded to the card.)
42
metadata
code
public key
signature
When the original .NET assembly is converted to the card-resident binary format, the
resulting binary file (.bin) is stored in the original assembly as a resource. After the .bin
file is embedded, the original .NET assembly is re-signed so that the data in the .bin file
is accounted for in the original .NET assembly's encrypted hash (signature).
Thus a post-conversion .NET assembly consists of these components:
metadata
code
public key
.bin resource
new signature
The .NET assembly hash is stored in the converted binary and gets loaded onto the
card along with the rest of the data in the card-resident binary. If needed, this hash
value can be used to match the card-resident binary to the original .NET assembly on
the desktop.
Open the properties page for assembly A2 and click the Security tab (as shown in
Figure 13).
43
Click Add to open the Share With dialog box (Figure 14).
44
If the A1 assembly is in the card, choose From On Card Assembly, select the
A1 assembly from the list
Click New Public Key Token by typing or pasting the public key token for
assembly A1.
In Permissions, check the boxes that correspond to the access rights you want to
grant to the public key token attribute.
Access rules enforced by the current Access Manager define who is able to add
public key token attributes to an assembly.
Click OK.
If an assembly does not have any public key token (PBTK) attributes, it is considered to
be public; that is, the assembly is accessible by all other assemblies. For example,
assemblies located in C:\System (including mscorlib.dll and SmartCard.dll) are
accessible to all assemblies. You can confirm that an assembly is public by viewing its
properties; click the Security tab and verify that the Public Key Tokens list is empty.
Data Security
The IDPrime .NET card supports two different types of data storage on the card. In the
first type of storage, data is stored as objects in the Application Domain of its host
assembly. (See Application Domains on page 25.) In the second type of storage, data
is stored in the IDPrime .NET File System. (See File System on page 35.)
It separates an application from the data it uses. This allows you to delete an
application and install a new version without having to worry about otherwise
preserving data.
45
It simplifies sharing data. For example, one application might have information
about the shipping address of the card owner. If this were stored in a file that was
accessible to other applications, the same shipping address would be accessible to
those applications.
The fact that the file system can be used for data sharing requires that there be policies
in place to enforce ownership and sharing privileges on files in the file system.
Data files in the IDPrime .NET card are protected using a public key token system that
is very similar to that used by applications (see Application Security on page 41).
Each file has two sets of privileges associated with it:
The public privileges define what any application can do to the file. For example, a
file could have a public Read privilege, which would allow any application to read
from the file.
The private privileges are assigned to individual public key tokens. For example, a
file might assign read privileges to a particular public key token that is trusted by
the application.
By default, when a file is created using the System.IO namespace, no public privileges
are assigned to that file, and the public key token of the assembly that created the file is
the only public key token in the private privileges set. The creating assembly has full
privileges to control the file. If an assembly with a public key token that is not in the
private privileges set attempts to perform an operation that is forbidden in the public
set, an UnauthorizedAccessException is thrown.
46
[APDUException(typeof(CryptographicException), (short)0x6512)]
[APDUException(null, (short)0x6514)]
[APDU("B0300000",Mask = "00000F0F")]
public void GenerateKeyPair([APDUParam(APDUHeader.P1)]byte
privateKeyIndex,
[APDUParam(APDUHeader.P2)]byte publicKeyIndex, byte algID, ushort
keySize, byte []
Data)
{
...
}
Broadly, here's what this does: It defines a method GenerateKeyPair that returns no
data and in the normal remoting world would be expecting as arguments 3 bytes,
followed by an unsigned short, followed by a byte array. If you wanted to invoke this
method using remoting, you'd use:
myRemoteObject.GenerateKeyPair(priIndex, pubIndex, algId, keySize,
bData);
However, if instead of using remoting, you send an APDU to the card that matches the
APDU attribute, the following happens:
1
The P1 byte from the APDU is packed into the first argument.
The P2 byte from the APDU is packed into the second argument.
The remainder of the DATA from the APDU is packed into the Data array.
What does it mean for an APDU to match the APDUattribute? Basically the check is:
if ((incomingAPDU & (~Mask)) == APDUAttribute)
So, in our example, any APDU of the form B0300x0x would be dispatched to this
method.
Here are the other rules you need to know for writing APDU's from your IDPrime .NET
application:
Your method must take as parameters only basic numeric types (byte, short, int,
long or their unsigned variants) or a byte array.
If your method takes a byte array as a parameter, the byte array must be the last
parameter, and there can only be one array parameter.
The URI of the application that you marshal when you install the application should
be a string containing the hexadecimal AID (e.g. private const string
REMOTE_OBJECT_URI = A00000000101;. By doing this, your application will
respond to standard select APDUs. In the case of the above sample, 00 A4 04 00
06 A0 00 00 00 01 01 would select the assembly.
Additionally, you can define a method to be called anytime that your application is
selected using APDU's.
[APDU("SELECT")]
public void Select(MemoryStream AID)
47
{
// Do anything you want to do when selected here...
}
All open FileStream objects are closed. Further attempts to use these objects result
in an ObjectDisposedException being thrown.
A CardReset event is triggered. An application can listen for this event to perform
any operations that might be necessary to reset the card. For example, you might
wish to reset data or fields that might be specific to your session.
48
Card Services
This sections describes two services that help you communicate with the card.
ContentManager
The Content Manager service is installed on the card during personalization at the
factory. This service allows you to manage the lifecycle of the card by managing the file
system, setting card properties, and loading/unloading assemblies. The Content
Manager can be used either from on-card applications or off-card applications. To
access the Content Manager from off-card applications, you can obtain a proxy to the
Content Manager using standard remoting techniques, or you can use the off-card
SmartCard.CardAccessor library, which provides an interface to the on-card
ContentManager application and does not require the calling application to use
remoting directly.
Features
Broadly, the ContentManager application allows you to do the following:
Manage files on the card. This includes creating/deleting both directories and files,
getting/setting properties associated with files, and managing the security settings
associated with a given file or directory.
Manage assemblies on the card. The API provides support for loading applications,
executing assemblies, and unregistering services.
49
Manage card properties. For example, you can set the chip speed, the
communication speed, or the historical parts of the ATR. In addition, you can read
information about the version of the card, free memory available, etc.
Examples
Here's an example of using the ContentManager from an off-card application:
ContentManager cm = (ContentManager)Activator.GetObject(typeof
(ContentManager),"apdu://selfDiscover/ContentManager");
int speed = cm.ChipSpeed;
Here's an example of using the CardManager from an on-card application:
ContentManager cm = (ContentManager)Activator.GetObject(typeof
(ContentManager),"ContentManager");
int speed = cm.ChipSpeed;
Note the close similarities. The on-card application is using the same remoting
mechanisms that the off-card application is using.
More Information
For more information about the ContentManager API, see the online help (OLH)
documentation in Start > Programs > .NET Smartcard Framework SDK >
X.X.XXX > Help > .NETSmartcardFramework.
SampleAccessManager
The SampleAccessManager service extends the SmartCard.AccessManager class.
The Access Manager is responsible for controlling access to system resources such as
the file system and card properties.
Features
You can use the SampleAccessManager application to log on to the card as a user.
This service is responsible for granting or denying privileges to system resources. You
can replace the SampleAccessManager application with a different service that
extends SmartCard.AccessManager. For more details about the AccessManager
model, see Access Manager on page 40.
SampleAccessManager Roles
SampleAccessManager defines four categories of roles that can be associated with the
card:
Administrator has full permissions to modify the card and to control other user
roles.
Power User is defined as a mid-level user with more permissions than a standard
user.
From within the SampleAccessManager client tools, you can create new users and
assign them to one of these roles.
50
SampleAccessManager Rules
SampleAccessManager manages access to the file system based on privileges
assigned to a given user or role. Individual user accounts are assigned separate code
and data directories in which to install their applications. All users have access to the
C:\Pub and D:\Pub directories. A guest user may access only the C:\Pub and D:\Pub
partitions of the card. An administrator is granted full access to the card.
Users can create and delete roles that have lower privileges. For example, the
Administrator can create Power Users and Users, but a Power User would only be
able to create a User account. Also note that a user cannot create a user that has
broader file access privileges than the creating user account. For example, if a Power
User had access to the C:\Users\students directory, they could not create a simple
User who had access to the C:\ or C:\User directories.
In the current implementation, there is only one Administrator account and one Guest
account.
4
Card Explorer
The Card Explorer is the tool available to manage IDPrime .NET Cards. It is part of the
IDPrime .NET SDK. The SDK is available free of charge from the Gemalto.com .NET
pages @ http://www.gemalto.com/products/dotnet_card/resources/
development.html?toggler=0
There are two versions of the SDK available: v2.3 for Visual Studio 2010, and v2.2.181
for all the other VS versions.
Introduction
The Card Explorer is a tool (also available as an add-in to Visual Studio .NET) that
simplifies IDPrime .NET Card management, including viewing a card's content;
managing the card's assemblies, data files, and directories; managing authentication
according to the requirements of the current Access Manager; and creating and
deleting services on the card.
Insert the IDPrime .NET Card into the smart card reader.
Card Explorer
52
In Reader name, select the name of the reader in which the IDPrime .NET Card is
inserted. If necessary, click Details and select other options (see Select
Smartcard Reader Details on page 55). Click OK. In the Card Explorer toolbar, the
Log on icon becomes available.
Everyone
53
Toolbar
The Card Explorer toolbar provides convenient access to perform routine card
management tasks.
Figure 17 - Card Explorer Toolbar
Tooltip
Description
Connect
(Authenticate)
Refresh
(Manage Access)
Run NAnt
Help
Card Explorer
54
Tab Layout
The management features are grouped into two tabs:
The Explorer tab offers a view of the IDPrime .NET Card's contents, and the ability
to manage assemblies, data files, and directories on the card.
See Explorer Tab on page 56 for more information about the elements on the
Explorer tab.
The Services tab provides a view of services running on the IDPrime .NET Card,
and provides features to manage services.
55
See Services Tab on page 58 for more information about the elements on the
Services tab.
This is the bottom bar of the Card Explorer window:
The following information is displayed in the three fields in the bottom bar:
Information pertaining to the current Access Manager, for example, the name of the
current user.
The bottom bar information is always displayed, regardless of which tab is active.
Description
Reader name
Select the name of the reader in which the IDPrime .NET Card is inserted.
Show Readers
Choose whether the Reader name list should be populated with the
names of all readers connected to the machine, all readers with smart
cards currently inserted, or all readers with IDPrime .NET Cards currently
inserted.
Card Explorer
56
In the event more than one reader is attached to the machine, choose
whether the first reader displayed in the Reader name list should be:
The last reader used by this application
The last reader used by any application
No reader (that is, no reader should be pre-selected)
Selfdiscover
Select this check box to cause the application to attempt to find a card
containing the service that the application is requesting. If the service is
available on an attached card, the application connects to the card without
user intervention. (Otherwise, if the service is not located on the card, the
Select Smartcard Reader dialog box displays.)
Remember Settings
Select this check box to save the selections you just made.
Explorer Tab
This is the Card Explorer, Explorer tab.
Figure 21 - Card Explorer - Explorer Tab
57
The following table describes the menu options available for each type of card element:
Table 4 - Card Element Descriptions and Menu Options
Card Element Type
Menu Option
Description
Card
Restart
Memory
Mapping
Properties
Volume/Drive
New Folder
Directory/Folder
Delete
New Folder
Load File
Properties
Execute
Delete
Properties
Delete
View Content
Properties
Executable (.exe)
Card Explorer
58
Services Tab
This is the Card Explorer, Services tab.
Figure 22 - Card Explorer Services Tab
The Services tab displays a list of services currently running on the card. By default,
each card includes the following three services:
Table 5 - Card Services
Service
Description
ContentManager (C:\System\SmartCard.dll)
CardModule (MSCM)
(C:\Gemalto\CardModule.exe)
The card can also contain additional services, for example, an alternative Access
Manager. Each time you instantiate a service on the card, the display changes to list the
new service on the Services tab.
59
If you right-click the name of a service listed in the Services tab, some services display
one or both of the following options:
Table 6 - Menu Options
Menu Option
Description
Delete
Access Manager
An Access Manager service defines the authentication mechanism by which the
information and applications on the card can be accessed. The default Access
Manager, the CLOG service, requires the user to authenticate by providing a username
and password. A different Access Manager might require the user to open a secure
channel by verifying the AUTH, MAC, and KEK keys for the card. An alternative Access
Manager might authenticate using a biometric solution, like verifying the user's
fingerprint.
Because different authentication mechanisms might be appropriate at different stages
in the card's lifecycle, the card's flexible architecture provides an API for authentication
management applications. Any Access Manager application that implements the
IAccessManager interface can provide the authentication mechanism for the card. The
new Access Manager can be loaded onto the card, instantiated, and designated as the
active Access Manager service. At any given time, exactly one Access Manager
service can be active on the card, and the active Access Manager service is marked by
an asterisk in the Services tab display.
These are the steps to change which service should be used for authentication on the
card:
1
Create and load the new Access Manager service (see Access Manager on
page 40 for instructions about creating and loading an alternate Access Manager
server onto the card). Loading also includes instantiation, so the Services tab list
will include the new service.
In the Services tab, right-click the newly-added service and select Set As Access
Manager. In the display, the asterisk now designates the new Access Manager
service.
Note: If you try to designate a service that does not implement the IAccessManager
interface, the operation fails and the old Access Manager remains active.
Card Explorer
60
If you click Properties, a Properties sheet specific to the card element type is
displayed. The ability to view information is based on permissions for the logged on
user. Each label is always displayed, but if permissions for the current user do not allow
access to the information, the details are not visible.
This section describes property details that are displayed for each card element type.
Card Properties
The properties sheet for the card object includes information in two tabs.
This is the card object General tab:
61
These are the elements on the General tab for the card object.
Table 7 - Card Properties - General Tab Elements
Property
Description
Product
Name and vendor of the .NET Smart Card Framework, taken from
the cardconfig.xml file on the card. It also shows version information
for the operating system (OS), Common Language Runtime (CLR)
and converter.
Hardware
Name, vendor, version, and serial number of the chip, taken from
the cardconfig.xml file on the card.
Card Explorer
62
These are the elements on the Advanced tab for the card object.
Table 8 - Card Properties - Advanced Tab Elements
Property
Possible
values
Default
value
Description
Maximum connection
speed (baud)
9600
19200
38400
55800
76800
111600
115200
223200
223200
Chip speed
0 - 100
100
Cryptographic
algorithms supported
63
These are the elements on the General tab for the folder object.
Table 9 - Folder Properties - General Tab Elements
Property
Description
Type
Location
Size
Public Key
Token
Each assembly (.exe or .dll) has an associated public key token. See Public Key
Tokens on page 67 for more information. For other objects (folders and nonassembly files), this field is blank.
Attributes
Card Explorer
64
This is the Security tab for a file (properties are similar for folders/directories):
Figure 27 - File Properties - Security Tab
These are the elements on the Security tab for the folder object.
Table 10 - File Properties - Security Tab Elements
Property
Description
For folders: the public key tokens for applications that are currently
permitted to write files to the selected folder.
For executables: the public key tokens for applications that are
permitted to execute the selected application.
For libraries: the public key tokens for applications that are
permitted to access the selected library.
For other files: the public key tokens for applications that are
permitted to write to the selected file.
Permissions
A list of the permissions associated with the public key token. The
type of permissions listed depends on the type of file being
examined.
Add button
Add a new public key token to the list by selecting an assembly (an
.exe or .dll file) from the list (the public key token for the selected
assembly is added to the list).
Remove button
Lock button
For files, this button makes the current file permissions permanent.
Modify button
65
Choose one of the three basic sources of public key tokens as follows:
Click From On Card Assembly and select an assembly that is already on the
card from the list.
Click From Off Card Assembly to choose an assembly that is off the card and
use the Browse button to select the assembly.
Click New Public Key Token and enter a new 8-byte hexadecimal key token.
In Permissions, you can select the permissions associated with the assembly.
The following tables show the types of permissions that can be set for different
types of files.
Card Explorer
66
Description
Execute
Manage
Whether or not the public key token has permission to change the
security parameters of the assembly.
Description
Add
Whether or not the public key token can add files to the folder.
Delete
Whether or not the public key token can delete files from the folder.
Enumerate
Whether or not the public key token can list the files in the folder.
Manage
Whether or not the public key token can change the security
parameters of the folder.
Description
Read
Write
Whether or not the public key token has permission to change the
security parameters of the assembly.
Manage
Whether or not the public key token can change the security
parameters of the folder.
In the Security tab of the File Properties dialog (shown in Figure 27 on page 64),
select the token whose permissions you want to modify and click Modify.
The dialog changes as shown in Figure 29:
67
Check or uncheck the boxes next to each permission to make your modifications,
then click Apply. The Modify button reappears
To identify an assembly
Identifying an Assembly
Every assembly that is loaded to the card must be strong signed and, therefore, it must
include a public key that identifies it to other applications. The public key token
information (derived from a hash of the public key) for an assembly is found on the
General tab, Public Key Token property.
Card Explorer
68
Managing Folders
When you right-click a folder on the card, a menu becomes available offering several
folder management options.
Figure 30 - Contextual Menu for Folders
Delete
When you right-click any folder on the card, the menu choice Delete is available. If you
click Delete, a Confirm Folder Delete message asks you to confirm that you want to
delete the folder. If you click Yes and your permissions allow you to access the
selected folder, the folder is deleted from the card. Note that you cannot delete a folder
that is not empty.
New Folder
When you right-click any folder on the card, the menu choice New Folder is available.
If you click New Folder and your permissions allow you to access the selected folder,
the new folder is created. You must rename the folder when you create it (while the
name is still highlighted); after the folder object has been created, its name cannot be
changed. A folder cannot be moved after it is created.
69
Load File
When you right-click any folder on the card, the menu choice Load File is available. If
you click Load File, the Open dialog box is displayed.
Figure 31 - The Open Dialog Box
Both assemblies (.exe and .dll files) and data files can be loaded on the card. Navigate
to the file you want to add to the card, and click Open.
If the Access Manager allows the operation and if there is room on the card, the
operation succeeds.
Properties
When you right-click any folder on the card, a menu option to view Properties is
available. See Card Element Properties on page 60 for information about the
properties associated with folders.
Card Explorer
70
Managing Files
When you right-click any file on the card, a context-sensitive menu is displayed. Some
functions are specific to the file type (for example, only a .exe file can be executed,
while the content of uncompiled files only can be viewed).
Here is an example, which is the right-click menu for an executable file.
Figure 32 - Contextual Menu for Executable Files
Execute
When you right-click any executable file on the card, the menu option Execute is
available. If you click Execute and your permissions allow you to access the selected
file, the file is executed.
Delete
When you right-click any file on the card, a menu choice Delete is available. If you click
Delete, a Confirm File Delete message asks you to confirm that you want to delete the
object. If you click Yes and your permissions allow you to access the selected file, the
file is deleted from the card. Note that you cannot delete an assembly that is hosting an
active service. If the assembly hosts a service, you must first delete the service. See
Services Tab on page 58 for information about deleting a service.
View Content
When you right-click any non-binary file on the card, a menu option View Content is
available. File types that are associated with specific applications on your system will
open in those applications.
Save to PC as
When you right-click any non-binary file on the card, a menu option Save to PC as is
available. This enables you to save the file to your PC. It opens the Save file off card
dialog which you use to select the location where you want to save the file.
71
Properties
When you right-click any file on the card, the menu option Properties is available. See
Card Element Properties on page 60 for information about the properties associated
with files.
Restrictions
You are able to perform actions according to the permissions associated with your
logon identity. For example, if you are logged on as a user guest, with permission for
adding files only in the D:\Pub directory, you will be unable to add files in the C:\
Gemalto directory, even if you follow the instructions correctly.
5
Visual Studio .NET
Integration
The v2.2.181 of the .NET Smart Card Framework SDK supports the following versions
of Visual Studio:
v2.3 of the .NET Smart Card Framework SDK supports the following versions of Visual
Studio:
Depending on install-time selections, installing the .NET Smart Card Framework SDK
might make one or both of the following features available within Visual Studio .NET:
Card Explorer, which enables you to manage the contents of an IDPrime .NET
Card that is connected to your computer
Templates to easily create server applications and client applications that can
access services running on an IDPrime .NET card.
73
The CardExplorer add-in module is listed in the Available Add-ins column. Note that if
additional add-in modules to Visual Studio .NET are installed and registered on your
computer, your display will list those add-ins, in addition to the CardExplorer module.
Use the Add-in Manager to perform the following tasks:
To unload the CardExplorer add-in, deselect the check box at the left of the add-in
name, and then click OK. Note that unloading the add-in does not uninstall the
software.
To load the CardExplorer add-in, select the check box at the left of the add-in
name, and then click OK.
It is recommended that you uncheck the command line option for the tool.
Note: The Command Line check box has no meaning. You can clear the check box if
you wish.
See the Visual Studio .NET help for additional information about using the Add-in
Manager.
Errors in the Add-in are generally reported in the Output pane of Visual Studio.
The Add-in automatically chooses the correct build file when you use the NAnt
button. In the stand-alone, you'll need to select the build file for your project.
74
Templates
The .NET Smart Card Framework SDK provides templates that can be used to create
applications for the IDPrime .NET Card. Depending on install-time selections, you
might have Visual C# templates, Visual Basic templates, or both installed on the
machine.
For each programming language, these templates are available:
When you start a project using the netCard Server template, application code and
project files are automatically created as a starting point. See the walkthrough in Using
Templates to Make a Server Application on page 76 for instructions about using the
template to create a simple server application, and for a list of files created by the
template and at compile time.
75
When you start a project using the netCard Client Console template, application code
and project files are automatically created as a starting point. See the walkthrough in
Using Templates to Make a Client Application on page 81 for instructions about using
the template to create a simple client application, and for a list of files created by the
template and at compile time.
6
Getting Started
The walkthroughs provide instructions and examples of applications written for specific
purposes.
In the Visual Studio .NET toolbar, select File > New > Blank Solution.
77
In the New Project dialog box, type in a name for the new solution and select a
location for the solution's files, and then click OK.
The following solution directories and files are created at the location specified:
[solution_location]\SolutionName\
[solution_location]\SolutionName\SolutionName.sln
[solution_location]\SolutionName\SolutionName.suo
In the Visual Studio .NET Solution Explorer, the Solution is displayed like this:
Solution 'SolutionName' (0 projects)
In Solution Explorer, right-click the name of the solution and select Add > New
Project.
In the New Project dialog box, click Visual C# Projects, and then click netCard
Server.
Type in a name for the new project and select a location for the project's files (by
default, the project files are stored under the solution), and then click OK.
The following project directories and files are created at the location specified in the
New Project dialog box:
Getting Started
78
[project_location]\ProjectName\AssemblyInfo.cs
[project_location]\ProjectName\DummyKeyPair.snk
[project_location]\ProjectName\MyServer.cs
[project_location]\ProjectName\MyServices.cs
[project_location]\ProjectName\nant.build
[project_location]\ProjectName\ProjectName.csproj
[project_location]\ProjectName\ProjectName.csproj.user
[project_location]\ProjectName\Readme.txt
[project_location]\ProjectName\bin\Debug\
[project_location]\ProjectName\obj\Debug\
[project_location]\ProjectName\obj\Debug\ProjectName.projdata
[project_location]\ProjectName\obj\Debug\temp\
[project_location]\ProjectName\obj\Debug\TempPE
The DummyKeyPair.snk file is related to strong name signing. All applications added
to the card must be signed. DummyKeyPair.snk is a key pair that you can use to test
your application. Before you distribute your finished application, replace
DummyKeyPair.snk with a specific, non-test key pair.
In the Visual Studio .NET Solution Explorer, the server project is displayed like this:
ProjectName
References
mscorlib
netCard
AssemblyInfo.cs
MyServer.cs
MyServices.cs
nant.build
Readme.txt
79
using
using
using
using
System;
System.Runtime.Remoting;
System.Runtime.Remoting.Channels;
SmartCard.Runtime.Remoting.Channels.APDU;
namespace Server
{
/// <summary>
/// Summary description for MyServer.
/// </summary>
public class MyServer
{
/// <summary>
/// specify the exposed remote object URI.
/// </summary>
private const string REMOTE_OBJECT_URI = "myServerUri";
/// <summary>
/// Register the server onto the card.
/// </summary>
/// <returns></returns>
public static int Main()
{
// Register the channel the server will be listening to.
ChannelServices.RegisterChannel(new APDUServerChannel());
Getting Started
80
<?xml version="1.0"?>
<project name="netCardProject" default="build">
<target name="build" description="load and execute assembly">
<load file="bin\debug\netCard Server1.exe" todir="C:\Pub"
execute="true"
reload="true"
serviceName="myServerUri"/>
</target>
</project>
Make changes to reflect any changes you made in the MyServer.cs file, and then
save. Specifically, if you've updated the service name or executable name, you'll
need to update these elements.
More information about nant
6
Build the server application. See the Visual Studio .NET help for instructions about
building an application. The following files are added to the project:
[project_location]\ProjectName\bin\Debug\ProjectName.exe
[project_location]\ProjectName\bin\Debug\ProjectName.hive
[project_location]\ProjectName\bin\Debug\ProjectName.hmap
[project_location]\ProjectName\bin\Debug\ProjectName.pdb
[project_location]\ProjectName\bin\Debug\stub\AssemblyInfoTemp.cs
[project_location]\ProjectName\bin\Debug\stub\MyServices.cs
[project_location]\ProjectName\bin\Debug\stub\ProjectName_stub.dll
[project_location]\ProjectName\obj\Debug\ProjectName.exe
[project_location]\ProjectName\obj\Debug\ProjectName.pdb
Debugging
The system log, D:\Pub\Console.log, helps in debugging applications. To enable this
feature, include the System.Diagnostics namespace so that you have access to the
Debug class. Strings logged to Debug.WriteLine() appear in the file after the program
has executed. The logging feature is disabled if you compile the code in Release
mode.
You can also debug your card application by developing it in the .NET Framework on
the host side first. This practice makes the host's debugging tools available.
Insert an IDPrime .NET card into a card reader attached to your computer.
In the Card Explorer, click the toolbar logon icon, and type your user name and
password.
In the Card Explorer, right-click the directory into which the server application
should be installed (for example, C:\Pub), and select Add > Load File.
The server application file is added to the card. The service contained in the server
application is not yet running.
81
Starting a Service
To start the service, in the Card Explorer, right-click the server application file, and
select Execute. The service contained in the server application is now running and
available.
To confirm that the new service is running and available to client applications, click the
Services tab, and click the Refresh icon (see Toolbar on page 53). The name of the
service is displayed, along with all other services that are currently running on the card.
Deleting a Service
If you want to delete the server application from the card, these are the steps:
1
In the Card Explorer Services tab, right-click the service made available by the
server application, and select Delete.
In the Card Explorer Explorer tab, right-click the server application file, and select
Delete.
In the Visual Studio .NET toolbar, select File > New > Blank Solution.
Getting Started
82
In the New Project dialog box, type in a name for the new solution and select a
location for the solution's files, and then click OK.
The following solution directories and files are created at the location specified:
[solution_location]\SolutionName\
[solution_location]\SolutionName\SolutionName.sln
[solution_location]\SolutionName\SolutionName.suo
In the Visual Studio .NET Solution Explorer, the Solution is displayed like this:
Solution 'SolutionName' (0 projects)
In Solution Explorer, right-click the name of the solution and select Add > New
Project.
In the New Project dialog box, click Visual C# Projects, and then click netCard
Client Console.
83
Type in a name for the new project and select a location for the project's files (by
default, the project files are stored under the solution), and then click OK.
The following project directories and files are created at the location specified in the
New Project dialog box.
[project_location]\ProjectName\AssemblyInfo.cs
[project_location]\ProjectName\MyClient.cs
[project_location]\ProjectName\ProjectName.csproj
[project_location]\ProjectName\ProjectName.csproj.user
[project_location]\ProjectName\Readme.txt
[project_location]\ProjectName\bin\Debug\
[project_location]\ProjectName\obj\Debug\
[project_location]\ProjectName\obj\Debug\ProjectName.projdata
[project_location]\ProjectName\obj\Debug\temp\
[project_location]\ProjectName\obj\Debug\TempPE\
In the Visual Studio .NET Solution Explorer, the client project is displayed like this:
ProjectName
References
netCard.Runtime.Remoting
System
System.Data
System.Runtime.Remoting
AssemblyInfo.cs
MyClient.cs
Readme.txt
Getting Started
84
using
using
using
using
System;
System.Runtime.Remoting;
System.Runtime.Remoting.Channels;
SmartCard.Runtime.Remoting.Channels.APDU;
// Make sure you add the reference to your server stub dll.
// The stub file is automatically generated for you, under
// [Server Project Output]\Stub).
namespace Client
{
/// <summary>
/// Summary description for MyClient.
/// </summary>
public class MyClient
{
private const string URL = "apdu://promptDialog/myServerUri";
public MyClient()
{
// Create proxy of server
Server.MyServices myServices = new Server.MyServices();
// Example: invoke MyServiceExample.
string result = myServices.MyServiceExample();
// and display the result on the console output.
Console.WriteLine(result);
}
#region Main Method implementation
public static void Main()
{
APDUClientChannel channel = new APDUClientChannel();
// register the communication channel
ChannelServices.RegisterChannel(channel);
// request access to server object
RemotingConfiguration.RegisterWellKnownClientType(typeof
(Server.MyServices), URL);
new MyClient();
// unregister the communication channel
ChannelServices.UnregisterChannel(channel);
}
#endregion
}
}
85
Make changes to reflect any changes you made in the server application source
code file, and save. The sample code shows communication to the card using the
APDU protocol using the PromptDialog mechanism, which means that the
application will prompt the user to identify the reader in which the IDPrime .NET
card is inserted. Two other alternatives are available:
Before building the client application, you must create a link to the server
application be referencing the *_stub.dll file created when the server was built. In
Solution Explorer, right-click the client project's \ProjectName\References, and
select Add Reference. In the Add Reference dialog box, in the .NET tab, click
Browse, and then navigate to the server project's ProjectName\bin\Debug\
ProjectName_stub.dll file, click Open in the Browse dialog box, and then click OK.
The serverProjectName_stub.dll file is added to the project in the client project
[project_location]\ProjectName\bin\Debug directory and in the Visual Studio
.NET Solution Explorer Client Project References.
Build the client application. See the Visual Studio .NET help for instructions about
building an application. The following files are added to the project:
[project_location]\ProjectName\bin\Debug\ProjectName.exe
[project_location]\ProjectName\bin\Debug\ProjectName.pdb
[project_location]\ProjectName\obj\Debug\ProjectName.exe
[project_location]\ProjectName\obj\Debug\ProjectName.pdb
Note: If you are building a project including both a server application and a client
application, set the client application project to be the startup project (right-click the
client project and select Set as Setup Project).
Compiling your source files without a .NET Studio project using either the csc
compiler or nAnt
Getting Started
Enter a name for the project in the Name field, and click OK.
In the left pane of the Property Pages dialog box, click Build.
Check the box Do not reference Mscorlib as shown in the following example:
86
87
This action is required because you must use the version of Mscorlib provided with
the .NET Framework SDK. The following steps discuss how to load the proper
version of Mscorlib.
9
10 In the Microsoft Visual Studio window, open the Solution Explorer if it is not
already open.
11 In the Solution Explorer, right-click References.
12 From the pop-up menu, click Add Reference.
13 In the Add Reference dialog box, click .NET Smart Card Oncard mscorlib.dll,
and click OK, as shown in the following example:
Figure 42 - Add Reference (No On-card Templates)
Getting Started
88
Note that in the preceding example, /nodistlib instructs the compiler not to use the
Microsoft mscorlib. The following switch instructs the compiler to use the version of
mscorlib provided with the .NET Smart Card Framework SDK instead:
/r:"C:\Program Files\Gemalto\NET Smartcard Framework SDK\v2.2.181\
Libraries\On Card\Framework Libraries\mscorlib.dll"
Start with a server project that you have generated using the IDPrime .NET card
server wizard
89
to
using System;
using System.Runtime.Remoting;
using System.Runtime.Remoting.Channels;
#if MICROSOFT
using System.Runtime.Remoting.Channels.Tcp;
#else
using SmartCard.Runtime.Remoting.Channels.APDU;
#endif
3
In your Main method, you need to add another conditional compilation statement to
set up either a TCP or an APDU channel, so
ChannelServices.RegisterChannel(new APDUServerChannel());
becomes
#if MICROSOFT
ChannelServices.RegisterChannel(new TcpServerChannel(2222));
#else
ChannelServices.RegisterChannel(new APDUServerChannel());
#endif
When running in TCP mode, the server will shut down as soon as the Main method
exits. We could avoid this problem by only running in debug mode and putting
break points in, but an easier way to do this is to put a Console.ReadLine into the
Main method before returning. So add:
#if MICROSOFT
Console.ReadLine()
#endif
Start with a client project that you have generated using the IDPrime .NET card
client wizard.
We need to make the same changes that we made in step 2 of Server-Side Code
Changes to the using statements:
using System;
using System.Runtime.Remoting;
using System.Runtime.Remoting.Channels;
#if MICROSOFT
using System.Runtime.Remoting.Channels.Tcp;
#else
using SmartCard.Runtime.Remoting.Channels.APDU;
#endif
Getting Started
90
We'll need to set a conditional compilation statement around the URL to change it
back and forth between TCP and APDU:
#if MICROSOFT
private const string URL = "tcp://localhost:2222/
myServerUri";
#else
private const string URL = "apdu://promptDialog/myServerUri";
#endif
In the server project, under the Advanced tab of the Configuration Properties, you
need to set Do not use Mscorlib to false.
In the references section of the server project, change references from the Gemalto
on-card libraries to the standard Microsoft libraries. You will need to explicitly
include the System.Runtime.Remoting library.
In the references section of the client project, you will need to link to a server stub
library that is generated by the soapsuds application. For more information on the
soapsuds command, see MSDN.
Compile both projects, and you can now start the server in the debugger.
In the server project, under the Advanced tab of the Configuration Properties, you
need to set Do not use Mscorlib to true.
In the references section of the server project, change references from the
Microsoft libraries to the Gemalto on-card libraries.
In the references section of the client project, link to the server stub that is
generated by the IDPrime .NET build process.
Compile both projects, and you can now load the server to the card.
7
Code Samples
The .NET Smart Card Framework SDK includes a rich set of developer guidelines:
sample code, and hints and work arounds. After installation, the sample code can be
found here:
[install_location]\[product version]\Samples\[sample name]
Be sure to check the IDPrime .NET Home page for more examples.
Note: The documentation provided here supersedes the documentation that was
previously released in a Word document in the samples directory.
Table 14 - Samples provided with the SDK
Sample
Description
SecureSession
APDUAttribute
Transactions
General Instructions
The samples are shipped as VS.NET projects, and have not been compiled. Since the
samples are not compiled, the reference table in the client portion of the sample must
usually be updated by hand. Take the following steps to build the projects:
1
Add a new reference to the same stub, which will have been generated when you
compiled the server project. You can find the stub file in the stub directory under
the output directory for the server (debug or release).
Code Samples
92
SecureSession
This sample shows how to establish a secure channel between the on-card service and
a client application, where data is encrypted using a session key. It demonstrates
functionality similar to SSL. In SSL, the transport occurs over the Http channel,
whereas in this case, it will be over the APDU channel.
Description
SecureSession means that the data exchanged between a client and the on-card
service should be encrypted using a symmetric key. The symmetric key is not shared
between the on-card service and client application; rather, it is communicated by the
client application securely to the service and is valid only for one session. Session
here means the communication between a smart card and two resets (see Card Reset
Event on page 47). This symmetric key is called a session key.
The most interesting aspect of this sample is that it shows how to establish secure
sessions using custom sinks. The encryption and decryption of exchanges between the
on-card service and the client are delegated to the custom sink (see Using Custom
Sinks on page 32), instead of being handled within the application itself. This makes
the code in service smaller, portable, and independent of any cryptographic algorithm
being used.
It is also envisioned that many client applications communicate with the on-card
service at the same time using different session keys. This implies the on-card service
needs to have one communication channel per client application (using the custom
sink containing the session key generated by a given client). These channels should be
created and registered dynamically at a port specified by the client application and
should be unregistered at the end of the session.
As mentioned above, the session key is not shared between the service and the client,
and it is securely communicated by the client to the service. In order to ensure secure
communication of the session key, the public key of the RSA key pair pertaining to the
on-card service is used. The Client generates a key 16 bytes in length and encrypts it
with the public key of the on-card service. The Service uses its private key to decrypt
this session key.
The exchange of the session key cannot occur on a secure channel, since the session
key must be exchanged in order to create the secure channel itself. To accomplish the
exchange, the service should have an APDUServerChannel listening at a specific port
(port 46 in our sample) and should provide methods that should not be invoked over
channels using the SecureSessionSink. At first, it would seem that
APDUServerChannel listening on port 46 is an answer to the problem, but it actually
results in a security flaw. People who understand the .NET remoting architecture
should note that there is no explicit link between the transport channel and service. The
system will not prevent the invocation of any service method on any channel in a given
AppDomain. This shows that MyMethodOnSecureChannel() can be invoked on port
46, which does not have any security.
To avoid the above-mentioned problem, APDUServerChannel at port 46 should also
include a custom sink that has the sole purpose of marking when a remote method is
invoked at the channel listening at port 46. This is done by setting a static Boolean
variable accessible by the service. If a method such as MyMethodOnSecureChannel()
is invoked over port 46, the Boolean variable is set to true and implementation of the
MyMethodOnSecureChannel() method expects this flag to be false.
Here are the steps for establishing and communicating over a secure channel:
1
93
Client1 encrypts the session key generated in step 2 and the PIN of the on-card
service using the RSACryptoServiceProvider created in step 1.
The EstablishSecureChannel() method in the card decrypts the PIN and session
key using the private key. It validates if this PIN is correct. If it is, a new
APDUServerChannel listening at the port number passed in the method call is
created and registered with the custom sink called SessionSink.
Code Extract
Below are some code snippets to illustrate the steps described above.
// Create and register a channel at port 46 that uses
// SesssionEstablisherSinkProvider with a ProcessMessage() method set to the
//static Boolean flag
IServerChannelSinkProvider newProvider = new
SessionEstablisherSinkProvider(null, null);
newProvider.Next = new APDUServerFormatterSinkProvider();
APDUServerChannel channel = new APDUServerChannel(newProvider,46);
ChannelServices.RegisterChannel(channel);
// ProcessMessage() method of SessionEstablisherSink
{
// Let's mark the fact that we are coming from SessionEstablisherSink
MyService._onEstablisherChannel = true;
Code Samples
94
95
MyService._onEstablisherChannel = false;
// On reset unregister the channels that were dynamically created and use
SessionSink
....
...
}
// Client calls EstablishSecureChannel at port 46
{
APDUClientChannel channel = new APDUClientChannel("noprovider",null);
ChannelServices.RegisterChannel(channel);
// Connect to the service on the clear channel.
MyService sessionEstablish =
(MyService)Activator.GetObject(typeof(MyService),MYSERVICE_URI_1,"noprovider")
;
// This is the PIN that we share with the card
byte[] pin = new byte[]
{(byte)'f',(byte)'i',(byte)'r',(byte)'s',(byte)'t',(byte)'P',(byte)'i',(byte)'
n'};
// Encrypt the pin and session key using the public key of the card
byte [] encryptedPin = rsaProvider.Encrypt(pin, false);
byte [] encryptedSessionKey = rsaProvider.Encrypt(sessionKey, false);
// Now call the EstablishSecureChannel method of the card using the
encrypted PIN
// and session key. The card will set up an encrypted channel using the
provided
// session key.
sessionEstablish.EstablishSecureChannel(7655, encryptedPin,
encryptedSessionKey);
}
// Client calls MyMethodOnSecureChannel at 7655
{
// Set up a Sink Provider with a SessionSink attached to it using the
// session key as a parameter for creating the SessionSink.
Hashtable properties = new Hashtable();
properties["key"] = sessionKey;
IClientChannelSinkProvider provider = new
APDUClientFormatterSinkProvider();
provider.Next = new SessionSinkProvider(properties);
// Create and register a new channel using the sink provider that we've
// just created.
channel = new APDUClientChannel("SessionSinkClient", provider);
ChannelServices.RegisterChannel(channel);
// Now make a call to get the service again, but this time using the new
//channel.
// Note that we explicitly give the name of the channel as the third
// argument to Activator.GetObject.
MyService service =
(MyService)Activator.GetObject(typeof(MyService),MYSERVICE_URI_2,"SessionSinkC
lient");
// The data being sent to and from the card on the secure channel is now
// encrypted with the session key.
Console.WriteLine(service.MyMethodOnSecureChannel(new byte[] { 1,2,3,4,5}
));
}
Code Samples
96
APDUAttribute
This sample shows how you can use the APDUAttribute to support both legacy
applications and .NET remoting.
Description
The remote methods of the server are decorated with the APDUAttribute, which allows
the IDPrime .NET Card to support communication directly using traditional ISO 7816-4
APDUs. This is important if your application must be backwards-compatible with a
terminal or device that does not support .NET remoting.
The sample illustrates not only the APDUAttribute itself, but the use of the
APDUException attribute, which allows you to translate .NET exceptions into ISO
status words.
Two clients are provided. One is a traditional .NET smart card client application that
uses remoting to communicate with the card. The second is a C++ application that
uses the Winscard API to send APDUs directly to the card.
Execution
Install the 'Gemalto.Samples.APDUAttribute.exe' on the card. You should try running
both the CppClient and RemotingClient against the server.
Code Extract
Here is a sample method from the server application. This method is decorated with
the APDU attribute as well as the APDUException attribute. The remoting client calls
this method by invoking the SampleMethodWhichThrowException method on a proxy
object. The C++ client calls this method by sending the APDU B0340000010x to the
card, where x is passed to the method as a parameter and determines which exception
is thrown.
[APDU("B0340000")]
[APDUException(typeof(ApplicationException), "6D01")]
[APDUException(typeof(ArgumentException),
"6D02")]
[APDUException(typeof(ArgumentNullException), "6D03")]
[APDUException(typeof(ArithmeticException),
"6D04")]
public void SampleMethodWhichThrowException(byte b)
{
WriteLine("SampleMethodWhichThrowException called");
switch(b)
{
case 0x00:
WriteLine("Throwing ApplicationException..");
throw new ApplicationException();
case 0x01:
WriteLine("Throwing ArgumentException..");
throw new ArgumentException();
case 0x02:
WriteLine("Throwing ArgumentNullException..");
throw new ArgumentNullException();
case 0x03:
WriteLine("Throwing ArithmeticException..");
throw new ArithmeticException();
97
}
}
Transactions
This sample shows how to use Transaction attributes (see Transactions on page 37)
to ensure that your card data remains in a well-known state when the card is removed
or an uncaught exception is thrown. It also shows how the TryCounter class can be
used to keep data out of transaction.
Description
The service has two fields: field, which is an int, and tc, which is a TryCounter. It also
has three methods. Each method increments both fields, and then throws an exception
that is not caught on the card. The three methods illustrate the different behaviors
when methods are or are not decorated with the Transaction attribute. In the methods
decorated with the Transaction attribute, any changes made to the int are rolled back
when the exception is thrown. The TryCounter, however, continues to increment,
because the TryCounter is a special class that is not affected by Transactions. One of
the methods (NestedTransaction) calls a method that is not explicitly under transaction
in order to demonstrate that methods that are called by a method under transaction are
also considered to be under transaction.
Execution
Install the Gemalto.Samples.TransactionSample.exe' on the card, and execute the
client on the host.
Code Extract
Here is an extract of a method decorated with the Transaction attribute.
[Transaction]
public void UnderSimpleTransaction()
{
field++;
// field is an int
tc.Value++;
// tc is an instance of the TryCounter class
throw new ApplicationException();
}
In the above sample, the field value will be reset to its original value when the
ApplicationException is thrown, while the TryCounter will be incremented.
8
Client-Side Components
Some components in the .NET Smart Card Framework SDK reside on the client
machine.
SmartCard_Stub
The SmartCard_Stub.dll contains stub declarations for the card's ContentManager
service (described on page 48. You would link to the SmartCard_Stub when you want
to access the ContentManager directly using remoting. The full description of the
ContentManager service is provided in the .NET Card Framework API documentation.
99
Once you have added the SmartCard_Stub to your project, you can use remoting to
connect to the ContentManager service that is pre-installed on the card.
The .NET Smart Card SDK also supplies a client side wrapper for the ContentManager
service called CardAccessor that creates its own remoting connection to the card (see
CardAccessor Class).
SmartCard.Runtime
The SmartCard.Runtime.dll (which we'll refer to from now on as the Client runtime
library) contains several items of interest to developers:
It contains the client remoting framework to allow you to communicate with .NET
smart card services using the standard .NET remoting architecture.
A brief overview of each of these is given here. However, the API for each of these is
described in full in the .NET Smartcard Client API help file.
CardAccessor Class
The CardAccessor class provides a wrapper to the ContentManager class. When using
the CardAccessor class, you do not need to set up remoting channels to access the
ContentManager. This is handled silently by the CardAccessor class.
AccessManagerClient Interface
The IAccessManagerClientInterface allows you to implement a custom client for an
Access Manager (see page 40) that you write. The IAccessManagerClientInterface will
be called by the Card Explorer tool to log you into the card when using a card with your
AccessManager installed. In order for the Card Explorer to find the right
implementation of IAccessManagerClient, you must register your client assembly in the
Config.xml file of your installation \bin directory.
The SDK ships with an AccessManager installed (for example the Card Module). The
full source code is available for both the client and server components. You can find
this source code in the \Samples\src\SampleAccessManager directory of your SDK.
Client-Side Components
100
C++ Marshaller
Why a C++ Marshaller?
The IDPrime .NET card allows application developers to concentrate on building
service interfaces on the card without worrying about the implementation of the APDU
transport protocol. By default, this abstraction takes place using the .NET remoting
architecture. However, you may wish to write an application on the IDPrime .NET card
that does not operate in a .NET environment. This could happen if, for example, you
were writing a service such as a GINA, which would be invoked at boot time, and might
need to launch before the .NET runtime could be loaded.
Part II
APDU Encoding
9
APDU Encoding
Introduction
The services in .NET cards expose methods available to be called from external
applications. At the current stage of .NET card development APDUs provide the means
of transportation for these method calls. Each method call is encoded with its
arguments into one or more APDUs before being sent to the smart card. Part 3 of this
Integration Guide describes how to encode APDUs for a service method call.
Each service in a .NET card has a specific name (URI), an associated type (typeof) and
it listens on a specific port. Each method of a service has a specific name. The
arguments or parameters of the method are formed using the argument values.
All the above information is then encoded to form APDUs for a method call.
APDU Format
Here is the general structure of the APDU encoding for a method call:
APDU = APDU Header + APDU Payload
APDU Payload = [D8] [Service port number (2 bytes)] [6F] [Service Namespace
Hivecode (4 bytes)] [Service Type Hivecode (2 bytes]] [Method Hivecode (2 bytes)]
[Length of service name (2 bytes]] [UTF8 encoded Service name] [Encoded
Arguments]
103
Argument Encoding
Arguments are formed by concatenation of the encoded argument values. Each
argument value is encoded accordingly to its type as follows:
Note: null references for arrays are encoded using a length of FFFFFFFF. null
reference for strings are encoded using a UTF8 representation length of FFFF.
Table 1 shows the possible types and their encoding convention in .NET cards:
Table 15 - Argument Types and Their Encoding
Argument types
Meaning
(.NET)
Encoding
MARSHALLER_TYPE_IN_BOOL
boolean
1 byte
- true : 01
- false: 00
MARSHALLER_TYPE_IN_S1
sbyte
1 byte
MARSHALLER_TYPE_IN_U1
byte
1 byte
MARSHALLER_TYPE_IN_CHAR
char
2 bytes
MARSHALLER_TYPE_IN_S2
short
2 bytes
MARSHALLER_TYPE_IN_U2
ushort
2 bytes
MARSHALLER_TYPE_IN_S4
Int32 (int)
4 bytes
MARSHALLER_TYPE_IN_U4
UInt32 (uint)
4 bytes
MARSHALLER_TYPE_IN_S8
Int64 (long)
8 bytes
MARSHALLER_TYPE_IN_U8
UInt64 (ulong)
8 bytes
MARSHALLER_TYPE_IN_STRING
string
[length (2 bytes)]
+ UTF8 encoded string
- for null string, length is FFFF
MARSHALLER_TYPE_IN_BOOLARRAY
Array of
boolean
[length (4 bytes)] +
[values (1 byte each)]
MARSHALLER_TYPE_IN_S1ARRAY
Array of sbyte
[length (4 bytes)] +
[values (1 byte each)]
MARSHALLER_TYPE_IN_U1ARRAY
Array of byte
[length (4 bytes)] +
[values (1 byte each)]
MARSHALLER_TYPE_IN_MEMORYSTREAM
Memorystream
- the same as
Array of byte
[length (4 bytes)] +
[values (1 byte each)]
MARSHALLER_TYPE_IN_CHARARRAY
Array of chars
[length (4 bytes)] +
[values (2 bytes each)]
APDU Encoding
104
Meaning
(.NET)
Encoding
MARSHALLER_TYPE_IN_S2ARRAY
Array of short
[length (4 bytes)] +
[values (2 bytes each)]
MARSHALLER_TYPE_IN_U2ARRAY
Array of ushort
[length (4 bytes)] +
[values (2 bytes each)]
MARSHALLER_TYPE_IN_S4ARRAY
Array of Int32
[length (4 bytes)] +
[values (4 bytes each)]
MARSHALLER_TYPE_IN_U4ARRAY
Array of UInt32
[length (4 bytes)] +
[values (4 bytes each)]
MARSHALLER_TYPE_IN_STRINGARRAY
Array of string
[length (4 bytes)] +
[each element is encoded as a
string as defined in
MARSHALLER_TYPE_IN_STR
ING]
Null value
null
Y bytes
Z bytes
We will divide W into 3 sections, such that X, Y and Z are all <= 244 bytes.
The payload of the first section (length X) is:
Payload-1 = D8 FFFF || [W (4 bytes)] || [X length (4 bytes)] || [X data bytes]
The payload of the second section (length Y) is:
Payload-2 = D8 FFFF || [Offset = X length (4 bytes)] || [Y length (4 bytes)] || [Y data
bytes]
(The offset is marks the start of the second section and is therefore the length of X)
The payload of the third section (length z) will be:
Payload-3 = D8 FFFF || [Offset = X length + Y length (4 bytes)] || [Z length (4 bytes)] ||
[Z data bytes]
105
(The offset is marks the start of the third section and is therefore the length of X + the
length of Y)
The total payload of the first section (Payload-1) is:
1 (D8) + 2 (FFFF) + 4 (W) + 4 (X) + X <= FF.
i.e. X <= (FF - 1 + 2 + 4 + 4), or X <= F4.
Y and Z must respect the same formula.
The APDU headers for these sub-sections are identical:
80C20000 [Payload-1 length in 1 byte] [Payload-1]
80C20000 [Payload-2 length in 1 byte] [Payload-2]
80C20000 [Payload-3 length in 1 byte] [Payload-3]
The card responses with a status word. This status word may be:
The data may represent an exception or a nominal method call return answer.
10
Hivecodes and Examples
Generic Answer Formation for .NET Card Services
(Except MSCM)
The answer for each method call to a service is formed according to the following
convention:
Answer = [Status (1 byte)] || [Data]
Where:
Status = 01 if everything is ok - method calls successful
= FF if there is an exception
If exception
Data = [Namespace hivecode of the exception] [Type hivecode of exception]
[optional UTF8 encoded exception message]
In the case of no exception, the return and reference parameter values are encoded
according to their argument types as given in Table 15 on page 103. The order is:
1
Computing Hivecodes
Hivecodes are computed by applying an MD5 hash to a particular string.
Namespace Hivecode
Namespace string consists of:
[Public Key Token] || ["."] || [Type namespace].
For example, the Namespace string for a namespace called Company.Stuff of an
assembly having a public key token being 42AA56EAF12382CE would be:
"42AA56EAF12382CE.Company.Stuff".
The corresponding hivecode would be the last 4 bytes of
MD5(42AA56EAF12382CE.Company.Stuff).
107
Type Hivecode
Type string consists of:
[Type Name].
For example, the Type string for a type called Company.Stuff.MyClass would be:
MyClass.
The corresponding hivecode would be the last 2 bytes of MD5(MyClass).
Note: If referring to an array of type, the array information should be ignored, i.e.
MyClass[] would become MyClass
Method Hivecode
Method string consists of:
[Fully qualified Method Name].
For example, the Method string for a method called void Foo(byte b, ref int I, out
short[] sarray)" would be
System.Void Foo(System.Byte,System.Int32,System.Int16[]).
The corresponding hivecode would be the last 2 bytes of
MD5(System.Void Foo(System.Byte,System.Int32,System.Int16[])).
USER = 0x01
ADMIN = 0x02
EVERYONE = 0x03
The access condition list (ACL) is a 3-byte array (3 bytes) that determines the access
rights for the three roles in the following format:
Admin rights || User rights || Everyone rights.
Each byte in the array codes the associated rights for the corresponding card access
role. It is encoded using the following flags (which can be OR-ed):
EXECUTE = 0x01
WRITE = 0x02
READ
= 0x04
108
The Hivecodes differ according to the version of the Microsoft specification. The
hivecodes for the methods in V5 of the Microsoft specification (described in Chapter
11 - Minidriver V5 Methods) are given in Table 16.
Table 16 - Hivecodes for V5
Method info
(name, return type, arguments)
Method
Hivecode
Meaning
byte[] GetChallenge()
FA3B
24FE
Response: cryptogram
generated from challenge using
Admin key.
7E25
Response: cryptogram
generated from challenge using
Access Manager Admin Key.
E08A
506B
6D08
0234
F152
9B2E
6144
int[] QueryFreeSpace()
00E5
int[] QueryKeySizes()
5EE4
BEF1
ACE9
109
Method
Hivecode
F20E
744C
6E2B
9135
E72B
A01B
C4E4
9B0B
FEAB
CFBE
E710
string get_Version()
DEEC
Meaning
The hivecodes for the methods in V6 and V7 of the Microsoft specification (described in
Chapter 12 - Minidriver V6/V7 Methods) are given in Table 17.
Table 17 - Hivecodes for V6/V7
Method info
(name, return type, arguments)
Method
Hivecode
8F0B
5177
BD7B
9967
279C
98D1
8187
B0E4
3D38
Namespace Hivecodes
System
= 00D25D1C
System.IO
= 00D5E6DB
System.Runtime.Remoting.Channels
= 0000886E
Meaning
System.Runtime.Remoting
= 00EB3DD9
System.Security.Cryptography
= 00ACF53B
System.Collections
= 00C5A010
System.Runtime.Remoting.Contexts
= 001F4994
System.Security
= 00964145
System.Reflection
= 0008750F
System.Runtime.remoting.Messaging
= 00DEB940
System.Diagnostics
= 0097995F
System.Runtime.CompilerServices
= 00F63E11
System.Text
= 00702756
SmartCard
= 00F5EFBF
= CE81
System.Int32
= 61C0
System.Int32[]
= 61C1
System.Boolean
= 2227
System.Boolean[]
= 2228
System.SByte
= 767E
System.SByte[]
= 767F
System.UInt16
= D98B
System.UInt16[]
= D98C
System.UInt32
= 95E7
System.UInt32[]
= 95E8
System.Byte
= 45A2
System.Byte[]
= 45A3
System.Char
= 958E
System.Char[]
= 958F
System.Int16
= BC39
System.Int16[]
= BC3A
System.String
= 1127
System.String[]
= 1128
System.Int64
= DEFB
System.Int64[]
= DEFC
System.UInt64
= 71AF
System.UInt64[]
= 71B0
System.IO.MemoryStream = FED7
= D4B0
110
111
System.SystemException
= 28AC
System.OutOfMemoryException
= E14E
System.ArgumentException
= AB8C
System.ArgumentNullException
= 2138
System.NullReferenceException
= C5B8
System.ArgumentOutOfRangeException
= 6B11
System.NotSupportedException
= AA74
System.InvalidCastException
= D24F
System.InvalidOperationException
= FAB4
System.NotImplementedException
= 3CE5
System.ObjectDisposed Exception
= 0FAC
System.UnauthorizedAccessException
= 4697
System.IndexOutOfRangeException
= BF1D
System.FormatException
= F3BF
System.ArithmeticException
= 6683
System.OverflowException
= 20A0
System.BadImageFormatException
= 530A
System.ApplicationException
= B1EA
System.ArrayTypeMismatchException
= 3F88
System.DivideByZeroException
= DFCF
System.MemberAccessException
= F5F3
System.MissingMemberException
= 20BB
System.MissingFieldException
= 7366
System.MissingMethodException
= 905B
System.RankException
= B2AE
System.StackOverflowException
= 0844
System.TypeLoadException
= 048E
System.IO.IOException
= 3BBE
System.IO.DirectoryNotFoundException
= 975A
System.IO.FileNotFoundException
= 07EB
System.Runtime.Remoting.RemotingException
= D52A
System.Security.Cryptography.CryptographicException
= 8FEB
= B18C
= 7616
112
Port is 0005,
Issue an External Authenticate APDU to authenticate the Admin role (the 8-byte
challenge is used as part of this command).
Issue a Log Out APDU command to log out as the Admin role.
Get Challenge
The APDU for the method byte[] GetChallenge() which doesn't require any argument
and whose method hivecode is FA3B is:
APDU = [80C20000 13] [D8] [Port (0005)] [6F] [namespace hivecode (00C04B4E)]
[type hivecode (7FBD)] [method hivecode (FA3B)] [service name length (0004)]
[service name - MSCM (4D53434D)]
Or
APDU = 80C20000 12 D8 0005 6F 00C04B4E 7FBD FA3B 0004 4D53434D
The status word for this APDU is 6112
Get Response
The APDU command to get the data is:
00C0000012
The on-card MSCM service answers with:
00D25D1C 45A3 00000008D90B49AA6690E797
113
External Authenticate
After calculating the card response (for example, the cryptogram value
BC287ED3692474A9) we need to use the method void ExternalAuthenticate(byte[]
response) to send the cryptogram to the card in order to authenticate the Admin role.
The ExternalAuthenticate() method hivecode is 24FE and we need to encode the
response parameter or cryptogram (BC287ED3692474A9) as a byte array of length 8.
So the APDU for the ExternalAuthenticate() method is:
APDU = 80C20000 1E D8 0005 6F 00C04B4E 7FBD 24FE 0004 4D53434D
00000008 BC287ED3692474A9
If the card accepts the cryptogram then it returns 9000 (No data is expected as the
method returns void) else it returns 61xx and an exception is encoded in the answer.
Log Out
If we want to log-out the Admin role, we need to execute the LogOut() method.
The void LogOut(byte role) method hivecode is C4E4 and since we want to log-out
the Admin role, the parameter value is 02. The resulting APDU is:
80C20000 13 D8 0005 6F 00C04B4E 7FBD C4E4 0004 4D53434D 02
Since the method returns void, no data is expected, hence a proper execution would
return directly with the status word 9000.
Part III
Configuring Parameters
11
Configuring Parameters
Introduction
There are two main ways of configuring parameters in Gemaltos .NET cards.
Certain parameters can be configured by loading the card module assembly and
executing it by specifying the parameters you want to change from their defaults.
This chapter lists the parameters that can be configured using either or both of these
two ways.
Note: It is also possible to configure the Maximum Communication Speed and the
Chip Speed by using the Card Explorer. This is explained in Configuring the
Communication and Chip Speed on page 61.
Possible values
Default value
Any
N/A
Any
N/A
Maximum number of
containers allowed in the
card (4 bytes)
Any
N/A
Comments
Configuring Parameters
116
Possible values
Default value
Comments
Any
512 bits
Any
1,024 bits
Any
2,048 bits
Any
256 bits
CARD_READ_ONLY (1 byte)
Read/Write (R/W)
Read Only (RO)
R/W
CARD_CACHE_MODE (1 byte)
Global cache
Session cache
No cache
Global
None
Unique Identifier
None
Normal Alphanumeric
PIN
External PIN (for
Biometrics or PinPad).
Challenge/Response
PIN
No PIN (used for
unprotected keys)
Authentication
Digital Signature
Encryption
Non repudiation
Admin
Primary
Unblock only
Any defined in
CARD_ROLES_LIST
Admin for
Admin Key
Primary for
others
Admin Key
Normal
117
Possible values
Any
Default value
Comments
N/A
Any combination
Any combination
N/A
CARD_X509_ENROLL (1 byte)
Does not support X509
Certificates enrollment
Supports X509 Certificates
enrollment
X509 supported
Configuring Parameters
118
Possible values
Default
value
Comments
1-16
4-255
4-255
255 (0xFF)
Any combination.
Each bit represents
one character set.
example, 0x07
represents the first
three character
sets
1Fh
1-255
Adjacent repeats
allowed
Yes, No
Yes
PIN History
0..10
Allow unblock
Yes, No
Yes
119
Possible values
Default
value
Comments
SSO
Yes, No
No
Yes, No
No
Mandatory character
set
0x00 (no
Mandatory
char. set)
Max. sequence of
characters
1-255
255 (0xFF)
Max. # adjacent
characters
1-255
255 (0xFF)
Checks the PIN values validity against the PIN policy for
the specified role.
Can be used with SetCardProperty but not
GetCardProperty.
CARD_IMPORT_ALLOWED (1 byte)
Key Injection
allowed
0: No
1: Yes
1: Yes
Configuring Parameters
120
Possible values
Default
value
Comments
CARD_IMPORT_CHANGE_ALLOWED (1 byte)
Card Import Allowed
property can be
changed or not
0: No
1: Yes
1: Yes
CARD_VERSION_INFO (4 bytes)
Card module
assembly version
number
Returned by GetCardProperty.
Cannot be set with SetCardProperty
CARD_SECURE_AM (1 byte)
Access Manager
Admin Key
0: No
1: Yes
0: No
CARD_UNBLOCK-FP_SYNC (1 byte)
Unblock PIN also
unblocks FP
authentication
0: No
1: Yes
0: No
Possible values
Default value
Sample
-i
None
-i
-r
None
-s
None
-s
-c
Value multiple of 8
bytes
8 bytes
-c:16
-p
121
Possible values
Default value
Sample
-f
None
-f
-k
None
-k
-l
None
-l
-u
1 = Yes
0 = No
-u:0
-u:1
-n
1-15
15
-n:12
-n:15
Configuring Parameters
122
Description
Possible values
Default
value
Example
-p
01
-p:01
-p:02
-p:04
-p:08
-a
Admin
-a:pin
-a:admin
-m
Allowed UVMs.
In case the above parameter is set to PIN,
this parameter allows the administrator to
restrict the list of UVMs the user can
choose from.
0F: All
-n
0..10
-n:1
-r
1.. 255
10
-r:5
-r:10
-t
1..10
10
-t:1
-t:7
-t:10
123
Description
Possible values
Default
value
Example
All
(0x03FF)
Both thumbs:
'00000000
00100001'
(0x0021)
Fingers 2,3,7,8:
'00000000
11000110'
(0x00C6).
All fingers and
both thumbs:
'00000011
11111111'
(0x03FF).
1,000 - 1,000,000
10,000
FAR = 1K:
-f: 214748
(result of
0x7fffffff/1000 in
decimal format)
Note: The value
must be in
decimal format
The desired values for these configurable parameters can be set at the time of
production of the cards. Otherwise they could be set through a web or client tool
designed for such a purpose.
A
Troubleshooting
This appendix includes information to help solve problems encountered while
developing IDPrime .NET Card applications.
Communication Problems
The following is a checklist of things to do when you suspect that you are having a
communication problem with your card. For the purposes of this document, a
communication problem is something that occurs when your software seems to be
properly installed, but you can't connect to or see the card.
Check to see if the driver for the reader is installed. To do this, look at your device
manager, and ensure that the reader you are using is visible under the Smart Card
Readers section.
Ensure that the smart card service is running. To do this, look at the service
manager for your machine, and ensure that Smart Card is started.
Further Steps
If another IDPrime .NET Card works in the same reader, there's a good chance that
the non-working card is dead. Please post on the Support forum to check the
replacement policy for your card.
If other (non .NET) cards work in the reader, but your IDPrime .NET Card does not,
it may be that there is a speed negotiation conflict between the cards and your
reader. If you have access to another reader on which the IDPrime .NET Card
works, you can use the Card Explorer tool to set the card to a lower communication
speed. If you have this problem (and whether setting the communication speed
lower fixes the problem or not), please post your issue on the Support forum with
the make and model of your reader. We closely track compatibility problems and
will work to resolve them.
125
B
Marshaller Stub Sample
This appendix describes a C++ visual project sample that reproduces the steps of a
scenario using the stub and marshaller.
The steps to perform are:
1
Choose the certificate/container for PKI operations (the first one in this sample)
Encrypt some data (with RSA software algorithm and card public key)
#define
_WIN32_WINNT
0x0400
#undef UNICODE
#include <stdlib.h>
#include <stdio.h>
#include <conio.h>
#include <ctype.h>
#include <windows.h>
#include <winscard.h>
#include "CardModuleService.h"
#include "zlib/zlib.h"
#include "rsa/cr_rsa.h"
127
BYTE dataToSign[256];
BYTE dataToEncypt[256];
BYTE encryptedData[256];
DWORD dwEncryptedLen;
128
{
try
{
delete mdService;
mdService = NULL;
}
catch(...)
{
}
}
return TRUE;
}
//---------------------------------------------------------------------------//---------------------------------------------------------------------------void main(void)
{
BOOL bRes;
//
// Connect to MiniDriver Service
//
bRes = connectMiniDriver();
if (!bRes)
{
goto _END;
}
//
// Verify User PIN (hard-coded value = "0000")
//
try
{
u1Array *userPIN = new u1Array(4);
memcpy_s(userPIN->GetBuffer(), 4, "0000", 4);
mdService->VerifyPin(1, userPIN);
printf("User PIN verified\n");
// Cleanup
if (userPIN != NULL)
{
delete userPIN;
}
}
catch(...)
{
printf("PIN verification failed :(\n");
goto _END;
}
printf("\n");
//
// Read all certificates and uncompress them
//
for (int i = 0; i < MAX_CONTAINERS; i++)
{
u1Array *compCert = new u1Array(0);
129
130
bContainerIdx = (BYTE)i;
break;
}
}
//
// Get public key of selected container
//
try
{
u1Array *container = new u1Array(0);
container = mdService->GetCAPIContainer(bContainerIdx);
// Scan the container buffer to find the public key value (Modulus /
Exponent) of Exchange key
// See the Integration guide for details about buffer format
BYTE *ptr = container->GetBuffer();
int i = 0;
BYTE keyType;
while (i < (int)container->GetLength())
{
// Key type TLV (Tag = 0x03) - L is coded on 1 byte, V is always 1
byte
if (ptr[i] == 0x03)
{
// Store key type (Exchange or Signature) contained in V
keyType = ptr[i+2];
i += 3; // Skip T, L and V bytes
}
// Public Exponent TLV (Tag = 0x01) - L is coded on 1 byte, V is
always 4 bytes
if (ptr[i] == 0x01)
{
// Store Public Exponent if the current key is the exchange key
(Type = 0x01)
if (keyType == 0x01)
{
memcpy(pubKeyExponent, &ptr[i+2], 4);
}
i += 6; // Skip T, L and V bytes
}
// Public Modulus TLV (Tag = 0x02) - L is coded on 1 byte, V is
variable length
if (ptr[i] == 0x02)
{
// Byte length of Modulus, see the Integration guide for details
about the <<4 bit shift!
dwPubKeyByteLen = (ptr[i+1]<<4);
// Store Public Exponent if the current key is the exchange key
(Type = 0x01)
if (keyType == 0x01)
{
memcpy(pubKeyModulus, &ptr[i+2], dwPubKeyByteLen);
}
131
132
);
// Add SHA-1 hashed data
memcpy(&dataToSign[dwPubKeyByteLen - sizeof(hashData)],
hashData,
sizeof(hashData)
);
// Send the data to sign using RSA raw decryption
try
{
u1Array *signature = new u1Array(0);
u1Array *data = new u1Array(dwPubKeyByteLen);
data->SetBuffer(dataToSign);
// Display data to sign
printf("Data to sign: ");
for (int i = 0; i < (int)data->GetLength(); i++)
{
printf("%02X", data->GetBuffer()[i]);
}
printf("\n");
signature = mdService->PrivateKeyDecrypt(bContainerIdx, // Container
Index
0x01, // Exchange key type
data // Data to sign
);
// Display Signature
printf("Signature: ");
for (int i = 0; i < (int)signature->GetLength(); i++)
{
printf("%02X", signature->GetBuffer()[i]);
}
printf("\n");
// cleanup
if (data != NULL)
{
delete data;
}
if (signature != NULL)
{
delete signature;
}
}
catch(...)
{
printf("Signature failed :(\n");
goto _END;
}
printf("\n");
//
// Decrypt a data with RSA private key in container associated to selected
133
// certificate. In this sample we encrypt a fake 3DES key data with software
// RSA and card public key, then the data is decypted using the card
//
BYTE des3Key[24];
// Fake 3DES key for this sample = 3D...3D (24 bytes)
memset(des3Key, 0x3D, sizeof(des3Key));
// Add PKCS#1 padding for encryption
memset(dataToEncypt, 0x00, sizeof(dataToEncypt));
dataToEncypt[0] = 0x00;
dataToEncypt[1] = 0x02;
memset(&dataToEncypt[2], 0xFF, dwPubKeyByteLen - sizeof(des3Key) - 3);
dataToEncypt[dwPubKeyByteLen - sizeof(des3Key) - 1] = 0x00;
// Add 3DES key data
memcpy(&dataToEncypt[dwPubKeyByteLen - sizeof(des3Key)],
des3Key,
sizeof(des3Key)
);
// Encrypt Data with RSA software and RSA plublic key read from card
R_RSA_PUBLIC_KEY rsaKeyPublic;
rsaKeyPublic.bits = dwPubKeyByteLen*8;
memcpy(rsaKeyPublic.modulus, pubKeyModulus, dwPubKeyByteLen);
memset(rsaKeyPublic.exponent, 0x00, dwPubKeyByteLen) ;
memcpy(&rsaKeyPublic.exponent[dwPubKeyByteLen - 4], pubKeyExponent, 4);
dwEncryptedLen = dwPubKeyByteLen;
RSAPublicBlock(encryptedData,
(unsigned int *)&dwEncryptedLen,
dataToEncypt,
dwPubKeyByteLen,
&rsaKeyPublic
);
// Send the data to RSA raw decryption
try
{
u1Array *clearData = new u1Array(0);
u1Array *data = new u1Array(dwEncryptedLen);
data->SetBuffer(encryptedData);
// Display encrypted data
printf("Encrypted data: ");
for (int i = 0; i < (int)data->GetLength(); i++)
{
printf("%02X", data->GetBuffer()[i]);
}
printf("\n");
clearData = mdService->PrivateKeyDecrypt(bContainerIdx, // Container
Index
0x01, // Exchange key type
);
// Display Decrypted data
printf("Decrypted data: ");
for (int i = 0; i < (int)clearData->GetLength(); i++)
{
printf("%02X", clearData->GetBuffer()[i]);
}
printf("\n");
// cleanup
if (data != NULL)
{
delete data;
}
if (clearData != NULL)
{
delete clearData;
}
}
catch(...)
{
printf("Signature failed :(\n");
goto _END;
}
printf("\n");
_END:
//
// Release MiniDriver Service
//
releaseMiniDriver();
//
// pCertificate array cleanup
//
for (int i = 0; i < MAX_CONTAINERS; i++)
{
if (pCertificate[i].pData != NULL)
{
free(pCertificate[i].pData);
}
}
printf("Press a key to exit...");
getch();
}
134
ACL
AD
Application Domain
API
CLR
CP
Credential Provider
CSP
ECMA
EEPROM
GUID
IL
Intermediate Language
MSCM
MSDN
OLH
Online Help
OS
Operating System
PIN
PKI
RAM
ROM
Read-Only Memory
SSO
Single Sign-on
Terminology
Abbreviations
Terminology
136
Glossary
Application Domain
Admin Key
Base (CSP)
Card Explorer
Certificate
Certificate Authority
Common Language
Runtime (CLR)
Cryptography
Digital Signature
Encryption
137
Gemalto Unique
identifier
Intermediate Language
(IL)
Key
Key Length
Manifest
PKCS#11
Remoting
Sinks
Smart Card Minidriver Specification for Windows Base Cryptographic Service Provider (Base CSP)
and Smart Card Key Storage Provider (KSP), Version 5.07, September 12, 2007 from Microsoft.
Windows Smart Card Minidriver Specification, Version 6.02, March 7, 2008 from Microsoft.
Windows Smart Card Minidriver Specification, Version 7.06, July 1, 2009 from Microsoft.
ISO/IEC 7816: Information Technology Identification cards Integrated circuit cards with contacts
References
139
Recommended Reading
For further reading about IDPrime .NET Cards, please go to the Gemalto product catalog at http://
www.gemalto.com/products/dotnet_card/
Advanced .NET Remoting from Ingo Rammer; APress January 1, 1970); ISBN: 1590590252
Common Language Infrastructure Annotated Standard from James S. Miller, Susann Ragsdale,
Jim Miller; Addison-Wesley Pub Co, 1st edition (October 24, 2003); ISBN: 0321154932
.NET Framework Security from Brian A. LaMacchia, Sebastian Lange, Matthew Lyons, Rudi Martin,
Kevin T. Price; Addison-Wesley Pub Co, 1st edition (April 24, 2002); ISBN 067232184X