kaoh / globalplatform

C library + command-line for Open- / GlobalPlatform smart cards
https://kaoh.github.io/globalplatform/
Other
72 stars 30 forks source link

Length of Install Parameters field is not coded correctly for install_for_install #92

Open davidmru opened 8 months ago

davidmru commented 8 months ago

The length of the parameters field is not coded as ber-len in the command install_for_install Ref 11.5.2.3.2 Data Field for INSTALL [for install] GlobalPlatform Technology Card Specification Version 2.3.1 image

koh-osug commented 8 months ago

Only a single byte is used which is good enough for 128 bytes. So far this was always sufficient. Do you have a card supporting more? Then I would need one to verify a patch for this.

davidmru commented 8 months ago

I have an applet which install Parameters field is more than 128 bytes (147 0x93). The install for install command is successful when the Length is coded as berlen (8193). I have a card which accept Length of Install Parameters field > 0x80

koh-osug commented 8 months ago

So, this means you have already patched the source code? Can you please share the code snippet?

davidmru commented 8 months ago

No, I built the apdu command install for install manually, then I used the command send_apdu to send it to the card. However I checked the source code [ https://github.com/kaoh/globalplatform/blob/master/globalplatform/src/globalplatform.c#L3261 ] I think the correction below might solve the issue:

//[line 3291] buf[i++] = 0x02; // install parameter field length hiByte = 0x02; // tag C9 + length byte (C9LL) if (installParametersLength > 0) { hiByte += (BYTE)installParametersLength; } if (uiccSystemSpecParamsLength > 0) { hiByte += 2; hiByte += (BYTE)uiccSystemSpecParamsLength; }

if (nonVolatileDataSpaceLimit > 0 || volatileDataSpaceLimit > 0 || simSpecParamsLength > 0) {
    hiByte += 2; // 0xEF LL
}
if (nonVolatileDataSpaceLimit > 0) {
    hiByte += 4;
}
if (volatileDataSpaceLimit > 0) {
    hiByte += 4;
}
if (simSpecParamsLength > 0) {
    hiByte += (BYTE)simSpecParamsLength + 2;
}

//Set Length of Install Parameters field if(hiByte > 255){ buf[i++] = 0x82 buf[i++] = hiByte >> 8; buf[i++] = hiByte & 0x00FF; }else if(hiByte > 127){ buf[i++] = 0x81; buf[i++] = hiByte;
}else{ buf[i++] = hiByte; }

But I have not tested

koh-osug commented 8 months ago

I have pushed a fix to the branch https://github.com/kaoh/globalplatform/tree/install_params_size. Do you need a binary to test it or can you compile it on your own for testing it? The README in https://github.com/kaoh/globalplatform/tree/install_params_size should give the instructions how to build it, Windows build be more involved.

davidmru commented 8 months ago

I checked the fix, I noticed that it is the Application Specific Parameters (tag C9) which length has been coded as ber-tlv. However the tag C9 should never be greater than (127 - LV(ControlInfo) - LV(InstanceAID) [ see install method ] . May be the comment: hiByte = 0x02; // tag C9 + length byte (C9LL) in the snippet I posted is confusing. The value 02 represent the tag and the length byte of the tag C9.

The length which has to be corrected is the length of the parameters field (see table 11-43 in the first post). The table below show the content of the parameters field: image REF: GlobalPlatform Technology Card Specification Version 2.3.1

koh-osug commented 8 months ago

Next try. Pushed an update.