2016-04-09 16 views
0

Java Kartı 2.1.2 SDK ve GPShell kullanarak aygıtla iletişim kurma yolunda bir proje oluşturuyorum. GpShell'den helloworld örneğini test ettim ve Basit APDU göndermek için. Daha büyük .cap dosyaya apdu göndermeyi deneyin Ancak cihaz Java Kart 80 Kb flash var olmasına rağmen bana bir hafıza problemi gibi görünüyor below.It uygulamacığından kod parçalarını ekliJava Kartı Akıllı kartla bir iletişim hatası algılandı

send_APDU() returns 0x8010002F (A communications error with the smart card has b 
een detected. Retry the operation. 
) 

bana aşağıdaki hatayı veriyor ve neredeyse 2 Kb RAM. Eclipse simülatöründe uygulama iyi çalışıyor.

TwineCipher.java

public class TwineCipher implements IConsts{ 

    /** 
    * The 80 bits of cipher twine 
    */ 

    public static final short MAX_MEMORY_TEMPORARY=32; 
    private static TwineCipher ref_twineCipher_80 = null; 
    private static TwineCipher ref_twineCipher_128 = null; 

    public byte[] temp = JCSystem.makeTransientByteArray(MAX_MEMORY_TEMPORARY,JCSystem.CLEAR_ON_DESELECT); 
    public byte[] rk = JCSystem.makeTransientByteArray((short) ((short)36*8),JCSystem.CLEAR_ON_DESELECT); 

    private static byte [] roundconst = 
     { 
       0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x03, 0x06, 0x0c, 0x18, 0x30, 0x23, 0x05, 0x0a, 0x14, 0x28, 0x13, 0x26, 
       0x0f, 0x1e, 0x3c, 0x3b, 0x35, 0x29, 0x11, 0x22, 0x07, 0x0e, 0x1c, 0x38, 0x33, 0x25, 0x09, 0x12, 0x24, 0x0b, 
     }; 

    private static short [] shufinv = {1, 2, 11, 6, 3, 0, 9, 4, 7, 10, 13, 14, 5, 8, 15, 12}; 
    private static short [] shuf = { 5, 0, 1, 4, 7, 12, 3, 8, 13, 6, 9, 2, 15, 10, 11, 14}; 
    private static byte [] sbox = {0x0C, 0x00, 0x0F, 0x0A, 0x02, 0x0B, 0x09, 0x05, 0x08, 0x03, 0x0D, 0x07, 0x01, 0x0E, 0x06, 0x04}; 
    private static byte [] data_enc = new byte[16]; 

    public static TwineCipher getInstance(byte type,byte[] key) 
    { 
     switch(type) 
     { 
      case TWINE_CIPHER_80: 
       if(ref_twineCipher_80 != null) 
        return ref_twineCipher_80; 
       ref_twineCipher_80 = new TwineCipher(key,TWINE_CIPHER_80); 
       return ref_twineCipher_80; 
      case TWINE_CIPHER_128: 
       if(ref_twineCipher_128 != null) 
        return ref_twineCipher_128; 
       ref_twineCipher_128 = new TwineCipher(key,TWINE_CIPHER_128); 
       return ref_twineCipher_128; 
      default: 
       ISOException.throwIt(ISO7816.SW_COMMAND_NOT_ALLOWED); 
     } 
     ISOException.throwIt(ISO7816.SW_COMMAND_NOT_ALLOWED); 
     return null; 
    } 

    public static TwineCipher getInstance(byte type) 
    { 
     switch(type) 
     { 
      case TWINE_CIPHER_80: 
       if(ref_twineCipher_80 != null) 
        return ref_twineCipher_80; 
       ref_twineCipher_80 = new TwineCipher(); 
       return ref_twineCipher_80; 
      case TWINE_CIPHER_128: 
       if(ref_twineCipher_128 != null) 
        return ref_twineCipher_128; 
       ref_twineCipher_128 = new TwineCipher(); 
       return ref_twineCipher_128; 
      default: 
       ISOException.throwIt(ISO7816.SW_COMMAND_NOT_ALLOWED); 
     } 
     ISOException.throwIt(ISO7816.SW_COMMAND_NOT_ALLOWED); 
     return null; 
    } 
    private TwineCipher(byte[] key,byte keySize) 
    { 
     switch(keySize) 
     { 
      case TWINE_CIPHER_80: 
       expand80Key(key); 
       break; 
      case TWINE_CIPHER_128: 
       expand128Key(key); 
       break; 
      default: 
       ISOException.throwIt(ISO7816.SW_WRONG_LENGTH); 
     } 
    } 
    private TwineCipher() 
    { 

    } 

    private void expand80Key(byte[] key) 
    { 
     short len_x = 20; 
     short key_size = 10; 
     short iterator = 0,iterator2=0;; 
     byte temp_val=-1; 
     byte temp_val2=-1,temp_val3=-1,temp_val4=-1; 
     short sh=0; 
     // reset the array 
     Util.arrayFillNonAtomic(temp, (short)0, (short)20, IConsts.UNTOUCHED_VALUE); 

     unrowl80ExpandKey(key); 

     for (iterator = 0 ; iterator < 35;iterator ++) 
     { 
      rk[(short)(iterator * 8 + 0)] = temp[1]; 
      rk[(short)(iterator * 8 + 1)] = temp[3]; 
      rk[(short)(iterator * 8 + 2)] = temp[4]; 
      rk[(short)(iterator * 8 + 3)] = temp[6]; 
      rk[(short)(iterator * 8 + 4)] = temp[13]; 
      rk[(short)(iterator * 8 + 5)] = temp[14]; 
      rk[(short)(iterator * 8 + 6)] = temp[15]; 
      rk[(short)(iterator * 8 + 7)] = temp[16]; 

      temp[1] ^= sbox[temp[0]]; 
      temp[4] ^= sbox[temp[16]]; 
      temp_val = roundconst[iterator]; 
      temp[7] ^= temp_val >> 3; 
      temp[19] ^= temp_val & 7; 

      temp_val = temp[0]; 
      temp_val2 = temp[1]; 
      temp_val3 = temp[2]; 
      temp_val4 = temp[3]; 

      for (iterator2 = 0 ; iterator2 < 4;iterator2++) 
      { 
       sh     = (short)(iterator2*4); 
       temp[sh]   = temp[(short)(sh+4)]; 
       temp[(short)(sh+1)] = temp[(short)(sh+5)]; 
       temp[(short)(sh+2)] = temp[(short)(sh+6)]; 
       temp[(short)(sh+3)] = temp[(short)(sh+7)]; 
      } 

      temp[16] = temp_val2; 
      temp[17] = temp_val3; 
      temp[18] = temp_val4; 
      temp[19] = temp_val; 

     } 
     rk[(short)(35 * 8 + 0)] = temp[1]; 
     rk[(short)(35 * 8 + 1)] = temp[3]; 
     rk[(short)(35 * 8 + 2)] = temp[4]; 
     rk[(short)(35 * 8 + 3)] = temp[6]; 
     rk[(short)(35 * 8 + 4)] = temp[13]; 
     rk[(short)(35 * 8 + 5)] = temp[14]; 
     rk[(short)(35 * 8 + 6)] = temp[15]; 
     rk[(short)(35 * 8 + 7)] = temp[16]; 

    } 
    private void expand128Key(byte[] key) 
    { 

    } 

    public byte[] encrypt(byte[] src,byte[] dest,short len_src) 
    { 
     Util.arrayFillNonAtomic(temp, (short)0, (short)32, IConsts.UNTOUCHED_VALUE); //reset all values 
                // 16 bytes for first part 
                // 16 bytes for next 
     short iterator=0,iterator2=0,iterator3=0; 
     short START_ITERATOR = 16; 
     for(iterator = 0 ; iterator < len_src ; iterator++) 
     { 
      temp[(short)(2*iterator)] = (byte)((short) (src[iterator] & 0x00FF) >> 4); 
      temp[(short)(2*iterator+1)] = (byte)((short) (src[iterator] & 0x00FF) & 0x0F); 
     } 

     for (iterator = 0 ; iterator < 35 ; iterator ++) 
     { 
      for (iterator2 = 0 ; iterator2 < 8 ; iterator2 ++) 
      { 
       temp[(short)(2*iterator2+1)] ^= sbox[temp[(short)(2*iterator2)]^rk[(short)(iterator*8+iterator2)]]; 

      } 

      for (iterator3 = 0 ; iterator3 < 16;iterator3++) 
      { 
       temp[(short)(shuf[iterator3]+16)] = temp[(short)(iterator3)]; 
      } 
      Util.arrayCopy(temp, (short)16, temp, (short)0, (short)16); 
     } 
     iterator = 35; 
     for (iterator2 = 0; iterator2 < 8 ;iterator2++) 
     { 
      temp[(short)(2*iterator2+1)] ^= sbox[temp[(short)(2*iterator2)]^ rk[(short)(iterator*8+iterator2)]];   
     } 

     for (iterator = 0 ;iterator < 8 ;iterator++) 
     { 
      temp[(short)(24+iterator)] = (byte)(temp[(short)(2*iterator)] << 4 | temp[(short)(2*iterator + 1)]); 
     } 
     Util.arrayCopy(temp, (short)24, dest, (short)(ISO7816.OFFSET_CDATA), (short)8); 
     return temp; // returns bytes from 24 to 32 
    } 
    public byte[] decrypt(byte[] src,byte[] dest,short len_src) 
    { 
     // for this alg len_src is always 8 
     Util.arrayFillNonAtomic(temp, (short)0, (short)32, IConsts.UNTOUCHED_VALUE); //reset all values 
     short iterator=0,iterator2=0,iterator3=0; 
     short START_ITERATOR = 16; 
     for(iterator = 0 ; iterator < len_src ; iterator++) 
     { 
      temp[(short)(2*iterator)] = (byte)((short) (src[iterator] & 0x00FF) >> 4); 
      temp[(short)(2*iterator+1)] = (byte)((short) (src[iterator] & 0x00FF) & 0x0F); 
     } 

     for (iterator = 35 ; iterator > 0 ; iterator --) 
     { 
      for (iterator2 = 0 ; iterator2 < 8 ; iterator2 ++) 
      { 
       temp[(short)(2*iterator2+1)] ^= sbox[temp[(short)(2*iterator2)]^ rk[(short)(iterator*8+iterator2)]]; 
      } 

      for (iterator3 = 0 ; iterator3 < 16;iterator3++) 
      { 
       temp[(short)(shufinv[iterator3]+16)] = temp[(short)(iterator3)]; 
      } 
      Util.arrayCopy(temp, (short)16, temp, (short)0, (short)16); 
     } 
     //FINAL 
     iterator = 0; 
     for (iterator2 = 0; iterator2 < 8 ;iterator2++) 
     { 
      temp[(short)(2*iterator2+1)] ^= sbox[temp[(short)(2*iterator2)]^ rk[(short)(iterator*8+iterator2)]]; 
     } 

     for (iterator = 0 ;iterator < 8 ;iterator++) 
     { 
      temp[(short)(24+iterator)] = (byte)(temp[(short)(2*iterator)] << 4 | temp[(short)(2*iterator + 1)]); 
     } 
     Util.arrayCopy(temp, (short)24, dest, (short)(ISO7816.OFFSET_CDATA), (short)8); 
     return temp; // returns bytes from 24 to 32 indexes 
    } 

    public short process(byte type,byte[] data,short start_offset,short len_data) 
    { 
     Util.arrayCopy(data, start_offset, data_enc, (short) 0, len_data); 
     switch(type) 
     { 
      case OFFSET_P1_ENC: 
       encrypt(data_enc, data, len_data); 
       return (short)8; 
      case OFFSET_P1_DEC: 
       decrypt(data_enc, data, len_data); 
       return (short)8; 
      case OFFSET_P1_GEN: 
       expand80Key(data_enc); 
       return 10; 
      default: 
       return (short)-1; 
     } 

    } 

    private void unrowl80ExpandKey(byte[] key) 
    { 
     temp[(short)(2*0)] = (byte)((short) (key[0] & 0x00FF) >> 4); 
     temp[(short)(2*0 + 1)] = (byte)((short) (key[0] & 0x00FF) & 0x0F); 

     temp[(short)(2*1)] = (byte)((short) (key[1] & 0x00FF) >> 4); 
     temp[(short)(2*1 + 1)] = (byte)((short) (key[1] & 0x00FF) & 0x0F); 

     temp[(short)(2*2)] = (byte)((short) (key[2] & 0x00FF) >> 4); 
     temp[(short)(2*2 + 1)] = (byte)((short) (key[2] & 0x00FF) & 0x0F); 

     temp[(short)(2*3)] = (byte)((short) (key[3] & 0x00FF) >> 4); 
     temp[(short)(2*3 + 1)] = (byte)((short) (key[3] & 0x00FF) & 0x0F); 

     temp[(short)(2*4)] = (byte)((short) (key[4] & 0x00FF) >> 4); 
     temp[(short)(2*4 + 1)] = (byte)((short) (key[4] & 0x00FF) & 0x0F); 

     temp[(short)(2*5)] = (byte)((short) (key[5] & 0x00FF) >> 4); 
     temp[(short)(2*5 + 1)] = (byte)((short) (key[5] & 0x00FF) & 0x0F); 

     temp[(short)(2*6)] = (byte)((short) (key[6] & 0x00FF) >> 4); 
     temp[(short)(2*6 + 1)] = (byte)((short) (key[6] & 0x00FF) & 0x0F); 

     temp[(short)(2*7)] = (byte)((short) (key[7] & 0x00FF) >> 4); 
     temp[(short)(2*7 + 1)] = (byte)((short) (key[7] & 0x00FF) & 0x0F); 

     temp[(short)(2*8)] = (byte)((short) (key[8] & 0x00FF) >> 4); 
     temp[(short)(2*8 + 1)] = (byte)((short) (key[8] & 0x00FF) & 0x0F); 

     temp[(short)(2*9)] = (byte)((short) (key[9] & 0x00FF) >> 4); 
     temp[(short)(2*9 + 1)] = (byte)((short) (key[9] & 0x00FF) & 0x0F); 
    } 
} 

IConst.java arayüzü

public interface IConsts 
{ 
    public static final byte UNTOUCHED_VALUE = 0x50; 
    public static final byte TRUE = 0x01; 
    public static final byte FALSE = 0x00; 

    public static final byte OFFSET_CLA_CIPHERS = (byte) 0x00; 
    public static final byte OFFSET_INS_LIGHT = (byte) 0x11; 


    public static final byte OFFSET_P1_ENC = (byte) 0x21; 
    public static final byte OFFSET_P1_DEC = (byte) 0x22; 
    public static final byte OFFSET_P1_GEN = (byte) 0x23; 

    public static final byte TWINE_CIPHER_80=0x30; 
    public static final byte TWINE_CIPHER_128=0x31; 
    public static final byte LBLOCK_CIPHER=0x32; 
} 

LBlockCipher.java 

    public class LBlockCipher implements IConsts { 


    public static final byte LBLOCK_NBROUNDS = 32; 
    public static final byte LBLOCK_KEY_SIZE = 80; 
    public static final short MEMORY_OUTPUT=32*4; 
    public static final short MEMORY_TEMPORARY=32; 

    static final byte[] S0 = { 14, 9, 15, 0, 13, 4, 10, 11, 1, 2, 8, 3, 7, 6, 12, 5}; 
    static final byte[] S1 = { 4, 11, 14, 9, 15, 13, 0, 10, 7, 12, 5, 6, 2, 8, 1, 3 }; 
    static final byte[] S2 = { 1, 14, 7, 12, 15, 13, 0, 6, 11, 5, 9, 3, 2, 4, 8, 10 }; 
    static final byte[] S3 = { 7, 6, 8, 11, 0, 15, 3, 14, 9, 10, 12, 13, 5, 2, 4, 1 }; 
    static final byte[] S4 = { 14, 5, 15, 0, 7, 2, 12, 13, 1, 8, 4, 9, 11, 10, 6, 3 }; 
    static final byte[] S5 = { 2, 13, 11, 12, 15, 14, 0, 9, 7, 10, 6, 3, 1, 8, 4, 5 }; 
    static final byte[] S6 = { 11, 9, 4, 14, 0, 15, 10, 13, 6, 12, 5, 7, 3, 8, 1, 2 }; 
    static final byte[] S7 = { 13, 10, 15, 0, 14, 4, 9, 11, 2, 1, 8, 3, 7, 5, 12, 6 }; 
    static final byte[] S8 = { 8, 7, 14, 5, 15, 13, 0, 6, 11, 12, 9, 10, 2, 4, 1, 3 }; 
    static final byte[] S9 = { 11, 5, 15, 0, 7, 2, 9, 13, 4, 8, 1, 12, 14, 10, 3, 6 }; 

    public byte[] output = JCSystem.makeTransientByteArray(MEMORY_OUTPUT,JCSystem.CLEAR_ON_DESELECT); 
    public byte[] temp  = JCSystem.makeTransientByteArray(MEMORY_TEMPORARY,JCSystem.CLEAR_ON_DESELECT); 

    private static LBlockCipher m_instance_Cipher = null; 

    public void keySchedule(byte[] key,short start_offset) 
    { 
     // use for keyR offset temp [0 - 3 ] 
     short i = 0 ; 
     output[(short)(0*4+3)] = key[(short)(9 + start_offset)]; 
     output[(short)(0*4+2)] = key[(short)(8 + start_offset)]; 
     output[(short)(0*4+1)] = key[(short)(7 + start_offset)]; 
     output[(short)(0*4+0)] = key[(short)(6 + start_offset)]; 

     for (i = 1;i<32;i++) 
     { 
      temp[3] = key[(short)(9 + start_offset)]; 
      temp[2] = key[(short)(8 + start_offset)]; 
      temp[1] = key[(short)(7 + start_offset)]; 
      temp[0] = key[(short)(6 + start_offset)]; 

      key[(short)(9 + start_offset)] = (byte) ((((key[(short)(6 + start_offset)] & 0x07) << 5) 
              & 0xE0)^(((key[(short)(5 + start_offset)] & 0xF8) >> 3) & 0x1F)); 
      key[(short)(8 + start_offset)] = (byte) ((((key[(short)(5 + start_offset)] 
              & 0x07) << 5) & 0xE0)^(((key[(short)(4 + start_offset)] & 0xF8) >> 3) & 0x1F)); 
      key[(short)(7 + start_offset)] = (byte) ((((key[(short)(4 + start_offset)] 
              & 0x07) << 5) & 0xE0)^(((key[(short)(3 + start_offset)] & 0xF8) >> 3) & 0x1F)); 
      key[(short)(6 + start_offset)] = (byte) ((((key[(short)(3 + start_offset)] 
              & 0x07) << 5) & 0xE0)^(((key[(short)(2 + start_offset)] & 0xF8) >> 3) & 0x1F)); 
      key[(short)(5 + start_offset)] = (byte) ((((key[(short)(2 + start_offset)] & 0x07) << 5) 
              & 0xE0)^(((key[(short)(1 + start_offset)] & 0xF8) >> 3) & 0x1F)); 

      key[(short)(4 + start_offset)] = (byte) ((((key[(short)(1 + start_offset)] & 0x07) << 5) 
              & 0xE0)^(((key[(short)(0 + start_offset)] & 0xF8) >> 3) & 0x1F)); 
      key[(short)(3 + start_offset)] = (byte) ((((key[(short)(0 + start_offset)] & 0x07) << 5) 
              & 0xE0)^(((temp[3] & 0xF8) >> 3) & 0x1F)); 
      key[(short)(2 + start_offset)] = (byte) ((((temp[3] & 0x07) << 5) & 0xE0)^(((temp[2] & 0xF8) >> 3) & 0x1F)); 
      key[(short)(1 + start_offset)] = (byte) ((((temp[2] & 0x07) << 5) & 0xE0)^(((temp[1] & 0xF8) >> 3) & 0x1F)); 
      key[(short)(0 + start_offset)] = (byte) ((((temp[1] & 0x07) << 5) & 0xE0)^(((temp[0] & 0xF8) >> 3) & 0x1F)); 

      key[(short)(9 + start_offset)] = (byte) ((S9[((key[(short)(9 + start_offset)] >> 4) & 0x0F)] << 4) 
              ^S8[(key[(short)(9 + start_offset)] & 0x0F)]); 

      key[(short)(6 + start_offset)] = (byte) (key[(short)(6 + start_offset)]^((i >> 2) & 0x07)); 
      key[(short)(5 + start_offset)] = (byte) (key[(short)(5 + start_offset)]^((i & 0x03) << 6)); 

      output[(short)(i*4 + 3)] = key[(short)(9 + start_offset)]; 
      output[(short)(i*4 + 2)] = key[(short)(8 + start_offset)]; 
      output[(short)(i*4 + 1)] = key[(short)(7 + start_offset)]; 
      output[(short)(i*4 + 0)] = key[(short)(6 + start_offset)];; 
     } 
    } 
    public void OneRound(byte[] x,byte[] k,short offset,short offset_x) 
    { 
     // t - from 5 - 8 tmp from 9 to 12 
     // u8 t[4], tmp[4]; 

     temp[9] = x[(short)(4 + offset_x)]; 
     temp[10] = x[(short)(5 + offset_x)]; 
     temp[11] = x[(short)(6 + offset_x)]; 
     temp[12] = x[(short)(7 + offset_x)]; 

     x[(short)(4 + offset_x)] ^= k[offset]; 
     x[(short)(5 + offset_x)] ^= k[(short)(offset+1)]; 
     x[(short)(6 + offset_x)] ^= k[(short)(offset+2)]; 
     x[(short)(7 + offset_x)] ^= k[(short)(offset+3)]; 

     x[(short)(4 + offset_x)] = (byte) (((S1[((x[(short)(4 + offset_x)]) >> 4) & 0x0F]) << 4) 
           ^S0[(x[(short)(4 + offset_x)] & 0x0F)]); 
     x[(short)(5 + offset_x)] = (byte) (((S3[((x[(short)(5 + offset_x)]) >> 4) & 0x0F]) << 4) 
           ^S2[(x[(short)(5 + offset_x)] & 0x0F)]); 
     x[(short)(6 + offset_x)] = (byte) (((S5[((x[(short)(6 + offset_x)]) >> 4) & 0x0F]) << 4) 
           ^S4[(x[(short)(6 + offset_x)] & 0x0F)]); 
     x[(short)(7 + offset_x)]= (byte) (((S7[((x[(short)(7 + offset_x)]) >> 4) & 0x0F]) << 4) 
           ^S6[(x[(short)(7 + offset_x)] & 0x0F)]); 

     temp[5] = (byte) (((x[(short)(4 + offset_x)] >> 4) & 0x0F)^(x[(short)(5 + offset_x)] & 0xF0)); 
     temp[6] = (byte) ((x[(short)(4 + offset_x)] & 0x0F)^((x[(short)(5 + offset_x)] & 0x0F) << 4)); 
     temp[7] = (byte) (((x[(short)(6 + offset_x)] >> 4) & 0x0F)^(x[(short)(7 + offset_x)] & 0xF0)); 
     temp[8] = (byte) ((x[(short)(6 + offset_x)] & 0x0F)^((x[(short)(7 + offset_x)] & 0x0F) << 4)); 

     x[(short)(4 + offset_x)] = (byte) (x[(short)(3 + offset_x)]^temp[5]); 
     x[(short)(5 + offset_x)] = (byte) (x[(short)(0 + offset_x)]^temp[6]); 
     x[(short)(6 + offset_x)] = (byte) (x[(short)(1 + offset_x)]^temp[7]); 
     x[(short)(7 + offset_x)] = (byte) (x[(short)(2 + offset_x)]^temp[8]); 

     x[(short)(0 + offset_x)] = temp[9]; 
     x[(short)(1 + offset_x)] = temp[10]; 
     x[(short)(2 + offset_x)] = temp[11]; 
     x[(short)(3 + offset_x)] = temp[12]; 


    } 
    public void encrypt(byte[] x,short offset_x) 
    { 
     short i; 
     for (i = 0; i<32; i++) 
     { 
      OneRound(x,output,(short)(4*i),offset_x); 
     } 
    } 
    public void OneRoundInv(byte[] y, byte[] k,short offset,short offset_y) 
    { 
     // t - from 5 - 8 tmp from 9 to 12 
     // u8 t[4], tmp[4]; 

     temp[9] = y[(short)(0 + offset_y)]; 
     temp[10] = y[(short)(1 + offset_y)]; 
     temp[11] = y[(short)(2 + offset_y)]; 
     temp[12] = y[(short)(3 + offset_y)]; 

     y[(short)(0 + offset_y)] = (byte) (y[(short)(0 + offset_y)]^k[offset]); 
     y[(short)(1 + offset_y)] = (byte) (y[(short)(1 + offset_y)]^k[(short)(offset+1)]); 
     y[(short)(2 + offset_y)] = (byte) (y[(short)(2 + offset_y)]^k[(short)(offset+2)]); 
     y[(short)(3 + offset_y)] = (byte) (y[(short)(3 + offset_y)]^k[(short)(offset+3)]); 


     y[(short)(0 + offset_y)] = (byte) (((S1[((y[(short)(0 + offset_y)]) >> 4) & 0x0F]) << 4)^S0[(y[(short)(0 + offset_y)] & 0x0F)]); 
     y[(short)(1 + offset_y)] = (byte) (((S3[((y[(short)(1 + offset_y)]) >> 4) & 0x0F]) << 4)^S2[(y[(short)(1 + offset_y)] & 0x0F)]); 
     y[(short)(2 + offset_y)] = (byte) (((S5[((y[(short)(2 + offset_y)]) >> 4) & 0x0F]) << 4)^S4[(y[(short)(2 + offset_y)] & 0x0F)]); 
     y[(short)(3 + offset_y)] = (byte) (((S7[((y[(short)(3 + offset_y)]) >> 4) & 0x0F]) << 4)^S6[(y[(short)(3 + offset_y)] & 0x0F)]); 


     temp[5] = (byte) (((y[(short)(0 + offset_y)] >> 4) & 0x0F)^(y[(short)(1 + offset_y)] & 0xF0)); 
     temp[6] = (byte) ((y[(short)(0 + offset_y)] & 0x0F)^((y[(short)(1 + offset_y)] & 0x0F) << 4)); 
     temp[7] = (byte) (((y[(short)(2 + offset_y)] >> 4) & 0x0F)^(y[(short)(3 + offset_y)] & 0xF0)); 
     temp[8] = (byte) ((y[(short)(2 + offset_y)] & 0x0F)^((y[(short)(3 + offset_y)] & 0x0F) << 4)); 

     y[(short)(0 + offset_y)] = (byte) (y[(short)(5 + offset_y)]^temp[6]); 
     y[(short)(1 + offset_y)] = (byte) (y[(short)(6 + offset_y)]^temp[7]); 
     y[(short)(2 + offset_y)] = (byte) (y[(short)(7 + offset_y)]^temp[8]); 
     y[(short)(3 + offset_y)] = (byte) (y[(short)(4 + offset_y)]^temp[5]); 

     // PARTIE GAUCHE 
     y[(short)(4 + offset_y)] = temp[9]; 
     y[(short)(5 + offset_y)] = temp[10]; 
     y[(short)(6 + offset_y)] = temp[11]; 
     y[(short)(7 + offset_y)] = temp[12]; 


    } 
    public void decrypt(byte[] x,short offset_x) 
    { 
     short i; 

     for (i = 31; i >= 0; i--) 
     { 
      OneRoundInv(x,output,(short)(i*4),offset_x); 
     } 
    } 

    private LBlockCipher() 
    { 

    } 
    public short process(byte type,byte[] data,short start_offset,short len_data) 
    { 
     Util.arrayCopy(data, start_offset, temp, (short) 16, len_data); 
     switch(type) 
     { 
      case OFFSET_P1_ENC: 
       encrypt(temp,(short)(16)); 
       Util.arrayCopy(temp,(short) 16, data, (short) start_offset, len_data); 
       return (short)8; 
      case OFFSET_P1_DEC: 
       decrypt(temp,(short)(16)); 
       Util.arrayCopy(temp,(short) 16, data, (short) start_offset, len_data); 
       return (short)8; 
      case OFFSET_P1_GEN: 
       keySchedule(temp,(short)(16)); 
       Util.arrayCopy(temp,(short) 16, data, (short) start_offset, len_data); 
       return 10; 
      default: 
       return (short)-1; 
     } 

    } 
    public static LBlockCipher getInstance() 
    { 
     if(m_instance_Cipher == null) 
      m_instance_Cipher = new LBlockCipher(); 
     return m_instance_Cipher; 
    } 

} 

TestApplet.java

public class TestApplet extends Applet 
      implements IConsts { 
    private TestApplet() 
    { 

    } 

    public static void install(byte bArray[], short bOffset, byte bLength) throws ISOException { 
     new TestApplet().register(); 
    } 

    public void process(APDU apdu) throws ISOException { 
     if (selectingApplet()) { 
      return; 
     } 
     byte[] buf = apdu.getBuffer(); 
     if(buf[ISO7816.OFFSET_CLA] != IConsts.OFFSET_CLA_CIPHERS) 
      ISOException.throwIt(ISO7816.SW_CLA_NOT_SUPPORTED); 
     switch (buf[ISO7816.OFFSET_INS]) 
     { 
      case IConsts.OFFSET_INS_LIGHT: 
       processLight(apdu); 
       return; 
      default: 
       break; 
     } 
    } 

    private void processLight(APDU apdu) 
    { 
     //cla and ins are proccessed 
     byte[] buf = apdu.getBuffer(); 
     byte state = (buf[ISO7816.OFFSET_P1]); 
     byte type = (buf[ISO7816.OFFSET_P2]); 
     byte count_data = buf[ISO7816.OFFSET_LC]; 
     if(count_data == 0x00) 
      ISOException.throwIt(ISO7816.SW_WRONG_LENGTH); 
     short len_data = -1; 
     switch(state) 
     { 
      case OFFSET_P1_ENC: 
       switch(type) 
       { 
        case TWINE_CIPHER_80: 
         TwineCipher m_instance = TwineCipher.getInstance(TwineCipher.TWINE_CIPHER_80); 
         len_data = m_instance.process(OFFSET_P1_ENC, buf, (short)(ISO7816.OFFSET_CDATA), count_data); 
         apdu.setOutgoingAndSend(ISO7816.OFFSET_CDATA, len_data); 
         return; 
        case TWINE_CIPHER_128: 
         TwineCipher.getInstance(TwineCipher.TWINE_CIPHER_80); //TODO change that 
         return; 
        case LBLOCK_CIPHER: 
         LBlockCipher m_instance_lblock= LBlockCipher.getInstance(); 
         len_data = m_instance_lblock.process(OFFSET_P1_ENC, buf, (short)(ISO7816.OFFSET_CDATA), count_data); 
         apdu.setOutgoingAndSend(ISO7816.OFFSET_CDATA, len_data); 
         return; 
        default: 
         ISOException.throwIt(ISO7816.SW_CLA_NOT_SUPPORTED); 
       } 
      case OFFSET_P1_DEC: 
       switch(type) 
       { 
        case TwineCipher.TWINE_CIPHER_80: 
         TwineCipher m_instance = TwineCipher.getInstance(TwineCipher.TWINE_CIPHER_80); 
         len_data = m_instance.process(TwineCipher.OFFSET_P1_DEC, buf, (short)(ISO7816.OFFSET_CDATA), count_data); 
         apdu.setOutgoingAndSend(ISO7816.OFFSET_CDATA, len_data); 
         return; 
        case TwineCipher.TWINE_CIPHER_128: 
         TwineCipher.getInstance(TwineCipher.TWINE_CIPHER_80); //TODO change that 
         return; 
        case LBLOCK_CIPHER: 
         LBlockCipher m_instance_lblock= LBlockCipher.getInstance(); 
         len_data = m_instance_lblock.process(OFFSET_P1_DEC, buf, (short)(ISO7816.OFFSET_CDATA), count_data); 
         apdu.setOutgoingAndSend(ISO7816.OFFSET_CDATA, len_data); 
         return; 
        default: 
         ISOException.throwIt(ISO7816.SW_CLA_NOT_SUPPORTED); 
       } 
      case OFFSET_P1_GEN: 
       switch(type) 
       { 
        case TwineCipher.TWINE_CIPHER_80: 
         TwineCipher m_instance = TwineCipher.getInstance(TwineCipher.TWINE_CIPHER_80); 
         len_data = m_instance.process(TwineCipher.OFFSET_P1_GEN, buf, (short)(ISO7816.OFFSET_CDATA), count_data); 
         apdu.setOutgoingAndSend(ISO7816.OFFSET_CDATA, len_data); 
         return; 
        case TwineCipher.TWINE_CIPHER_128: 
         TwineCipher.getInstance(TwineCipher.TWINE_CIPHER_80); //TODO change that 
         return; 
        case LBLOCK_CIPHER: 
         LBlockCipher m_instance_lblock= LBlockCipher.getInstance(); 
         len_data = m_instance_lblock.process(OFFSET_P1_GEN, buf, (short)(ISO7816.OFFSET_CDATA), count_data); 
         apdu.setOutgoingAndSend(ISO7816.OFFSET_CDATA, len_data); 
         return; 
        default: 
         ISOException.throwIt(ISO7816.SW_CLA_NOT_SUPPORTED); 
       } 
       default: 
        break; 
     } 
    } 

} 
+0

Kartınıza gönderdiğiniz komutu da eklemenizi rica edebilir miyim? Muhtemelen, emrinizde Le değerini göndermediğin için. – Abraham

+1

@Abraham Ben, Le ile ve Le olmadan, send_apdu -APDU 001123300A0000000000000000000000 've 'send_apdu -APDU 001123300A0000000000000000000000' denemeyi denedim ama aynı cevabı aldım.Bazen şu hatayı alıyorum' Sisteme bağlı bir aygıt çalışmıyor '. – Marga

+0

@Abraham Benim tarafımdan bir sınıf geçiştiriyor. Tüm kodu da içeren postamı güncelleyeceğim. – Marga

cevap

2

APDU tampon veri alanında veri almaya denemeden önce, Sen aşağıdaki yöntemi çağırmalıdır:

APDU nesnesine ilişkin

aksi takdirde bir hata alırsınız.

Sorununuzla ilgili this Q&A ve this Q&A'a bir göz atın.

Değiştirme:

case OFFSET_P1_GEN: 
       switch(type) 
       { 
        case TwineCipher.TWINE_CIPHER_80: 
         TwineCipher m_instance = TwineCipher.getInstance(TwineCipher.TWINE_CIPHER_80); 
         len_data = m_instance.process(TwineCipher.OFFSET_P1_GEN, buf, (short)(ISO7816.OFFSET_CDATA), count_data); 
         apdu.setOutgoingAndSend(ISO7816.OFFSET_CDATA, len_data); 
         return; 
// ...... 

case OFFSET_P1_GEN: 
       switch(type) 
       { 
        case TwineCipher.TWINE_CIPHER_80: 
         TwineCipher m_instance = TwineCipher.getInstance(TwineCipher.TWINE_CIPHER_80); 
         apdu.setIncomingAndReceive(); 
         len_data = m_instance.process(TwineCipher.OFFSET_P1_GEN, buf, (short)(ISO7816.OFFSET_CDATA), count_data); 
         apdu.setOutgoingAndSend(ISO7816.OFFSET_CDATA, len_data); 
         return; 
//..... 

ile TestApplet.java Sadece sorunuzun altında ilk açıklamada belirtilen komut için bu komutun (için sorunu çözecektir ve diğer komutlar için değil, ama aslında etkili değil: D. Bu yüzden iyi bir çizgi bulun ve bu yöntem çağrısını oraya yerleştirin.

+0

Teşekkür ederim. Sorunum çözüldü – Marga