2015-05-17 28 views
5

Sto utilizzando il pacchetto javax.smartcardio per lo sviluppo di applicazioni relative a smart card. Voglio inviare comandi Pseudo ADPU per impostare lo stato LED/LCD del mio lettore.È possibile inviare comandi Pseudo-APDU mentre la scheda non è presente?

Ho trovato che l'unico metodo per inviare comandi APDU a lettore/scheda è CardChannel::transmit, ma deve essere eseguito sulla carta presente.

È possibile inviare comandi Pseudo-APDU mentre la scheda non è presente nel lettore? E i comandi APDU? (Utilizzo di Java)

+0

... L'ho letto come "Smart Cardio". Sono intelligente, lo prometto! Inoltre, cosa significa ADPU?Non l'ho mai visto prima. –

+0

@QPaysTaxes: è preferibile leggerlo come SmartCardInOut;). APDU o Application Data Protocol Unit è un protocollo per inviare comandi alle smart card e ricevere risposta da loro. Semplicemente è una coda di numeri esadecimali. la lunghezza minima di questi comandi è di 4 byte (intestazione del comando) e la lunghezza minima della risposta della carta è di 2 byte (Parole di stato) – Abraham

+0

Dai un'occhiata alla seguente discussione nella comunità di Oracle, sembra che sia lo stesso problema che hai: https : //community.oracle.com/thread/2193998 – Abraham

risposta

3

trovato una soluzione da esempio di card-emul in SDK for PC/SC in http://www.springcard.com. Qui è il mio codice:

import java.util.List; 

import javax.smartcardio.CardException; 
import javax.smartcardio.CardTerminal; 
import javax.smartcardio.TerminalFactory; 

public class TestPcsc { 

    public static void main(String[] args) throws CardException { 

     TerminalFactory tf = TerminalFactory.getDefault(); 
     List<CardTerminal> terminals = tf.terminals().list(); 
     CardTerminal cardTerminal = (CardTerminal) terminals.get(0); 

     byte[] command = { (byte) 0xE0, (byte) 0x00, (byte) 0x00, (byte) 0x29, (byte) 0x01, (byte) 0x00 }; 
     cardTerminal.connect("DIRECT").transmitControlCommand(CONTROL_CODE(), command); 

    } 

    public static int CONTROL_CODE() { 

     String osName = System.getProperty("os.name").toLowerCase(); 
     if (osName.indexOf("windows") > -1) { 
      /* Value used by both MS' CCID driver and SpringCard's CCID driver */ 
      return (0x31 << 16 | 3500 << 2); 
     } 
     else { 
      /* Value used by PCSC-Lite */ 
      return 0x42000000 + 1; 
     } 

    } 

} 

Credo che i punti sono:

  1. Utilizzando DIRECT protocollo per ottenere la 'carta'
  2. Utilizzando Card::transmitControlCommand metodo con il codice ottenuto da funzione CONTROL_CODE (copiato dal codice di esempio, non sono sicuro di quale sia la teoria> _ <)
1

penso che il seguente metodo ha bisogno di una scheda presente nel lettore anche, ma solo per la vostra informazioni che ho postato qui per dire che noi c'è un altro metodo per i comandi terminale di controllo:

Citato da here:

transmitControlCommand:

pubblico byte astratto [] transmitControlCommand (int ControlCode, byte [] comando) tiri CardException

Trasmette un comando di controllo al dispositivo terminale. Questo può essere utilizzato, ad esempio, per controllare le funzioni del terminale come un pad PIN o una biometria incorporati .

Parametri:

ControlCode - il codice di controllo del comando

comando - i dati di comando

Produce:

SecurityException - se un SecurityManager esiste e la il chiamante non ha il permesso richiesto

NullPointerException - se il comando è nullo

CardException - se il funzionamento della scheda non riuscita

IllegalStateException - se l'oggetto carta è stato eliminato tramite il metodo di disconnessione()