TP1 Java Corrige

18
S. Bouzefrane 1 Interaction avec la carte à l’aide d’un programme Java - CNAM TP2 : Interaction avec la carte à puce à l’aide d’un programme Java sous Windows Samia BOUZEFRANE http://cedric.cnam.fr/~bouzefra/pfsem10-11.html [email protected] Laboratoire CEDRIC Chaire Systèmes Embarqués et Enfouis CNAM

Transcript of TP1 Java Corrige

Page 1: TP1 Java Corrige

S. Bouzefrane

1 Interaction avec la carte à l’aide d’un programme Java - CNAM

TP2 : Interaction avec la carte à puce

à l’aide d’un programme Java

sous Windows

Samia BOUZEFRANE

http://cedric.cnam.fr/~bouzefra/pfsem10-11.html

[email protected]

Laboratoire CEDRIC

Chaire Systèmes Embarqués et Enfouis

CNAM

Page 2: TP1 Java Corrige

S. Bouzefrane

2 Interaction avec la carte à l’aide d’un programme Java - CNAM

Page 3: TP1 Java Corrige

S. Bouzefrane

3 Interaction avec la carte à l’aide d’un programme Java - CNAM

1. API JSR 268 JSR 268 définit une API Java pour permettre la communication avec les cartes à puce

en utilisant le protocole ISO 7816-4. Il permet ainsi aux applications écrites en Java

1.6 d’interagir avec des applications qui tournent sur la carte à puce, en utilisant

Linux ou Windows.

Description du Package javax.smartcardio

Classe et Constructeur Méthodes de la classe

ATR : Réponse à un Reset Answer To Reset

ATR(byte[] atr) construit un ATR à partir d’un tableau d’octets.

boolean equals(Object obj) Compares the specified object with this ATR

for equality. byte[] getBytes()

Returns a copy of the bytes in this ATR. String toString()

Returns a string representation of this ATR. …

Card : Etablissement de connexions

Protected Card() construit un objet Card.

abstract void disconnect(boolean reset)

déconnexion de la carte. abstract ATR getATR()

retourne l’ATR de la carte. abstract String getProtocol()

retourne le protocole de cette carte. abstract CardChannel getBasicChannel() retourne le CardChannel d’un canal logique de base…

Page 4: TP1 Java Corrige

S. Bouzefrane

4 Interaction avec la carte à l’aide d’un programme Java - CNAM

CardChannel : Connexion logique à la carte à puce

protected CardChannel() construit un objet CardChannel

abstract void close() ferme le CardChannel

abstract ResponseAPDU transmit(CommandAPDU command) envoie la commande APDU vers la carte et retourne une réponse APDU.

CardTerminal :Création d’un lecteur de carte

protected CardTerminal(TerminalFactory factory) construit un nouvel objet CardTerminal

abstract Card connect(String protocol) établit une connexion avec la carte.

abstract String getName()

retourne le nom du lecteur. abstract boolean isCardPresent () retourne vrai si la carte est présente dans le lecteur, faux sinon.

CommandAPDU : Une commande APDU tel que éfini dans ISO 7816-4 CommandAPDU(byte[] apdu) construit une commande APDU à partir d’un tableau d’octets.

CommandAPDU(byte cla, byte ins, byte p1, byte p2) construit une commande APDU à partir des 4 octets de l’entête.

etc.

byte[] getBytes()

retourne une copie des octets de l’APDU. byte getCLA()

retourne la valeur de CLA. byte getINS()

retourne la valeur en octet de INS. byte getP1()

retourne la valeur en octet du paramètre P1. byte getP2()

retourne la valeur en octet du paramètre P2. int getNe()

retourne le nombre maximal d’octets attendus en réponse.

etc.

Page 5: TP1 Java Corrige

S. Bouzefrane

5 Interaction avec la carte à l’aide d’un programme Java - CNAM

ResponseAPDU : la réponse APDU tel que défini dans ISO 7816-4

ResponseAPDU(byte [] apdu) construit une réponse APDU à partir d’un vecteur d’octets contenant l’APDU complète (données et SW1 et SW2).

byte [] getBytes() retourne une copie de l’APDU en octets.

byte [] getData() retourne une copie en octets des données envoyées en réponse à la commande APDU.

byte getSW1() retourne la valeur en octet de l’état SW1.

byte getSW2() retourne la valeur en octet de l’état SW2. etc.

TerminalFactory : une fabrique pour les objets CardTerminal

CardTerminal getTerminal(String name) retourne le terminal avec le nom spécifié ou null si le terminal spécifié n’existe pas.

static TerminalFactory getDefault() retourne une instance de TerminalFactory par défaut. etc.

II. Outils de développement II.1. Outils matériels

Un lecteur de carte SIM et une carte SIM (le pilote du lecteur ayant été installé

durant le 1er TP).

II.1. Outils logiciels nécessaires

a) Télécharger et installer JDK 1.6 (utiliser le lien suivant pour le télécharger :

(http://java.sun.com/javase/downloads/widget/jdk6.jsp).

b) Télécharger et installer Eclipse galileo pour Windows

(http://www.eclipse.org/downloads/download.php?file=/technology/epp/dow

nloads/release/galileo/SR1/eclipse-java-galileo-SR1-win32.zip).

c) Télécharger l’outil de développement de JavaCard JSR268TK.zip dans un

répertoire local par exemple C:\JavaCard, à partir du lien suivant :

http://cedric.cnam.fr/~bouzefra/cours/cours_SEM/JSR268TK.rar

d) Pour connaître, le nom du lecteur de carte, il faut consulter la base des

registres (Sous Windows, cliquer sur le menu Démarrer et choisir Exécuter

pour exécuter la commande regedit et parcourir le chemin suivant):

Hkey local machine/software / Microsoft/cryptography/calais/readers

Page 6: TP1 Java Corrige

S. Bouzefrane

6 Interaction avec la carte à l’aide d’un programme Java - CNAM

III. Préparation de l’environnement de développement III.1 importer l’API JSR268 de développement sous éclipse :

a) Décompresser le projet c:\JavaCard\JSR268TK.zip dans le même répertoire.

b) Lancer Eclipse.

c) Importer le projet java C:\JavaCard\JSR268TK\JSR268TK\JSR268TK-2 de la

manière suivante :

File ���� Import ���� General ���� Existing Project into WorkSpace ���� Browse

Chercher l’emplacement où vous avez décompressé le ficher JSR268TK.zip. Dans

notre cas c’est : C:\JavaCard\JSR268TK\JSR268TK-2. Sélectionner le répertoire

JSR268TK-2 et puis faire OK.

Les captures d’écran suivantes explicitent cette manipulation.

Cliquer sur le bouton File ensuite sur Import

Page 7: TP1 Java Corrige

S. Bouzefrane

7 Interaction avec la carte à l’aide d’un programme Java - CNAM

Cliquer alors sur le bouton « + » devant General � Cliquer sur Existing Projects into

Workspace

Cliquer alors sur le bouton Browse pour rechercher le projet à importer.

Page 8: TP1 Java Corrige

S. Bouzefrane

8 Interaction avec la carte à l’aide d’un programme Java - CNAM

Cliquer alors sur le bouton + devant C � Cliquer sur + JavaCard � cliquer sur +

JSR268TK � Cliquer sur + JSR268TK �Cliquer sur JSR268TK-2 � Cliquer sur le

bouton OK

Cliquer sur le bouton Finish

Page 9: TP1 Java Corrige

S. Bouzefrane

9 Interaction avec la carte à l’aide d’un programme Java - CNAM

Vous devriez voir cette fenêtre, mais afin de visualiser les packages de ce projet

cliquer sur « + » devant JSR268TK-2

Page 10: TP1 Java Corrige

S. Bouzefrane

10 Interaction avec la carte à l’aide d’un programme Java - CNAM

Vous devriez voir cette fenêtre

Page 11: TP1 Java Corrige

S. Bouzefrane

11 Interaction avec la carte à l’aide d’un programme Java - CNAM

Ci-dessous un schéma qui décrit d’une manière générale les différentes parties de cet

API. Dans le TP sur Java Card, cet environnement nous permettra de développer une

application Java Card (côté client et côté carte).

build.xml : comporte l’exécution de trois programmes deleter : supprimer l’ancienne applet sur la carte. loader : charger la nouvelle applet sur la carte. run : exécuter le programme du terminal.

ManagerConfig.xml : sert à configurer le lecteur de carte à puce en mettant son nom.

SampleTestApplet.java : le squelette de l’applet

Build.xml : sert à compiler SampleTestApplet.java et générer éventuellement le fichier SampleTestApplet.cap qui sera installé sur la carte. Ce fichier comprend bien entendu l’AID de l’applet ainsi que l’AID du package auquel l’applet appartient.

SampleClient.java : la partie du terminal qui va interroger la carte.

Page 12: TP1 Java Corrige

S. Bouzefrane

12 Interaction avec la carte à l’aide d’un programme Java - CNAM

III.2 Configuration de l’environnement de développement :

a) Modification du ManagerConfig.xml en changeant le nom du lecteur.

b) Développement de la partie terminal (SampleClient.java).

c) Exécution de la partie terminal.

a) Modification du ManagerConfig.xml

- La première étape consiste à modifier le fichier ManagerConfig.xml en mettant le

nom de notre lecteur. Ce dernier se trouve dans la base de registres. Nous l’obtenons

de la manière suivante :

Bouton Démarrer ���� Exécuter ���� Taper: regedit

Le nom de lecteur se trouve dans l’emplacement suivant:

Cliquer sur le bouton + devant Hkey local machine ���� + software ���� +

Microsoft ���� + cryptography ���� + calais ���� + readers

- Ouvrir le fichier ManagerConfig.xml (double clique de souris sur le fichier).

Double clique sur Device

Vous pouvez copier ce nom de lecteur clrt+c

Page 13: TP1 Java Corrige

S. Bouzefrane

13 Interaction avec la carte à l’aide d’un programme Java - CNAM

- Enregistrer les modifications en tapant Ctrl+S.

b) Développement de la partie terminal :

-La partie terminal correspond au fichier SampleClient.java .

-Ouvrir le fichier SampleClient.java (double clique de souris sur le fichier).

L’image ci-dessous s’affiche :

Copier le nom de lecteur entre la balise </cad> et </cad>. Faite attention qu’il n’y ait pas d’espace.

Ici une liste des noms des lecteurs en commentaire.

Page 14: TP1 Java Corrige

S. Bouzefrane

14 Interaction avec la carte à l’aide d’un programme Java - CNAM

- Exécuter la partie terminal. Comme dans ce TP, le terminal n’interagit pas avec une

applet sur la carte, la déclaration de l’AID ne sera pas utile.

Cliquer sur « + » devant jsr268.sampleClient .

Cliquer sur le bouton droit de la souris sur le fichier SampleClient.java .

Choisir Run As. Cliquer ensuite sur Java Application.

Déclaration de Constantes

Déclaration de l’AID de l’applet qui va interagir avec cette partie terminal

Page 15: TP1 Java Corrige

S. Bouzefrane

15 Interaction avec la carte à l’aide d’un programme Java - CNAM

Une console affiche le résultat ou d’éventuelles erreurs.

Exercice: En vous basant sur cet environnement, écrire un programme qui affiche l’ATR de la

carte SIM, et qui envoie des commandes APDU pour récupérer quelques informations

telles que l’IMSI, TMSI et le fichier des SMS.

Page 16: TP1 Java Corrige

S. Bouzefrane

16 Interaction avec la carte à l’aide d’un programme Java - CNAM

Corrigé (avec un SELECT rep. GSM et un GET RESPONSE)

package jsr268gp.sampleclient; import jsr268gp.cad.ResponseAPDU ; import jsr268gp.util.Address ; import com.ibm.jc.ATR ; import javax.smartcardio.CardTerminal; import jsr268gp.util.Util; import javax.smartcardio.CommandAPDU; import javax.smartcardio.Card; import javax.smartcardio.TerminalFactory; import javax.smartcardio.CardTerminals; import javax.smartcardio.CardChannel; public class SampleClient { public SampleClient() { super(); // TODO Auto-generated constructor stub } /** * @param args */ public static void main(String[] args) { //Sélectionner votre lecteur de carte //Le nom du lecteur se trouve dans la base de registres : //Hkey local machine/software / Microsoft/cryptography/calais /readers TerminalFactory tf = TerminalFactory. getDefault(); CardTerminals list = tf.terminals(); CardTerminal cad = list.getTerminal( "GENERIC2KXP USB Smart Card Reader 0" ); if (cad == null) { System. out.println( "debug1" ); } try { // Remarque : pour le transtypage de tableau byte vers une variable string en hexa // utiliser la méthode byteArrayToHexString de la classe Util //Etablir la connexion avec la carte à puce Card c = cad.connect( "T=0" ); System. out.println( "Card : " +c); System. out.println( "\n" ); //Afficher l'ATR et sa taille (reset the card) javax.smartcardio.ATR atr = c.getATR(); System. out.println( "ATR : " + Util. byteArrayToHexString(atr.getBytes(), " " )); System. out.println( "Taille " + atr.toString()); System. out.println( "\n" ); //Trouver la commande APDU qui sélectionne le répertoire GSM

Page 17: TP1 Java Corrige

S. Bouzefrane

17 Interaction avec la carte à l’aide d’un programme Java - CNAM

byte[] FIDGSM={0x7F, 0x20}; CommandAPDU capdu = new CommandAPDU((byte)0xA0,( byte)0xA4, ( byte)0x00, ( byte)0x00, FIDGSM); //Afficher la commande APDU System. out.println( "Commande ADPU >" + Util. byteArrayToHexString(capdu.getBytes(), " " )); //Envoyer la commande APDU CardChannel cc = c.getBasicChannel(); javax.smartcardio.ResponseAPDU rapdu = cc.transmit(capdu); //Afficher la réponse APDU System. out.println( "Réponse APDU < " + Util. byteArrayToHexString(rapdu.getBytes(), " " )); // Si (status succes ) alors // if ((rapdu.getSW1()==0x90) && (rapdu.getSW2()==0x00)) //{ //System. out.println( "Succes " ); //System. out.println( "\n" ); //}

// Faire un Get Response A0 C0 00 00 1A capdu = new CommandAPDU((byte)0xA0,( byte)0xC0, ( byte)0x00, ( byte)0x00, (byte)0x1A); System. out.println( "Commande ADPU > " + Util. byteArrayToHexString(capdu.getBytes(), " " )); rapdu = cc.transmit(capdu); System. out.println( "Réponse APDU < " + Util. byteArrayToHexString(rapdu.getBytes(), " " )); // Déconnexion c.disconnect( false); } catch (Exception e) { e.printStackTrace(); System. exit(1); } } }

Résultat d’exécution:

Card : PC/SC card in GENERIC2KXP USB Smart Card Rea der 0, protocol T=0, state OK ATR : 0x3B 0x16 0x94 0x71 0x01 0x01 0x06 0x02 0x00 Taille ATR: 9 bytes Commande ADPU >0xA0 0xA4 0x00 0x00 0x02 0x7F 0x20 Réponse APDU < 0x9F 0x1A Commande ADPU > 0xA0 0xC0 0x00 0x00 0x1A

Page 18: TP1 Java Corrige

S. Bouzefrane

18 Interaction avec la carte à l’aide d’un programme Java - CNAM

Réponse APDU < 0x00 0x00 0x00 0x00 0x7F 0x20 0x02 0x00 0x00 0x00 0x00 0x00 0x0D 0x13 0x00 0x15 0x04 0x00 0x83 0x8A 0x83 0x8A 0 x00 0x01 0x00 0x00 0x90 0x00