Dear Ludovic
On Mon, Feb 20, 2012 at 11:21 PM, Godfrey Chung
<[email protected]> wrote:
> Compared with acsccid-1.0.3 with ccid-1.4.5, I found that I didn't
> merge your changes for the ControlUSB function. Your function checked
> the return value from libusb_control_transfer(). The returned value
> may be very large and cause DEBUG_XXD to fail. I will do more tests
> tomorrow.
I used APG8201 for testing and reviewed the code from acsccid-1.0.3,
ccid-1.4.5 and pcsc-lite-1.8.2. The problem is not related to libusb
or kernel.
I found that the real problem is in DEBUG_XXD macro which calls
log_xxd from pcsc-lite. From my testing, I got error code "-84" from
usb_control_msg. Because acsccid is missing a check of error code in
ControlUSB, it passed the error code directly to DEBUG_XXD. Then,
pcscd is suddenly terminated with segmentation fault.
In pcsc-lite, log_xxd calls log_xxd_always. log_xxd_always accepts
negative number in len parameter and use the value for the array size
of DebugBuffer.
Suggested code change for acsccid-1.0.3 (src/ccid_usb.c):
Add a error code check after usb_control_msg.
int ControlUSB(int reader_index, int requesttype, int request, int value,
unsigned char *bytes, unsigned int size)
{
int ret;
DEBUG_COMM2("request: 0x%02X", request);
if (0 == (requesttype & 0x80))
DEBUG_XXD("send: ", bytes, size);
ret = usb_control_msg(usbDevice[reader_index].handle, requesttype,
request, value, usbDevice[reader_index].interface, (char
*)bytes, size,
usbDevice[reader_index].ccid.readTimeout * 1000);
if (ret < 0)
{
DEBUG_CRITICAL4("control failed (%s/%s): %s",
usbDevice[reader_index].dirname,
usbDevice[reader_index].filename,
strerror(errno));
return ret;
}
if (requesttype & 0x80)
DEBUG_XXD("receive: ", bytes, ret);
return ret;
} /* ControlUSB */
Suggested code change for ccid-1.4.5 (src/ccid_usb.c):
Use of STATUS_UNSUCCESSFUL as return code is not appropriate.
STATUS_UNSUCCESSFUL is a positive number.
int ControlUSB(int reader_index, int requesttype, int request, int value,
unsigned char *bytes, unsigned int size)
{
int ret;
DEBUG_COMM2("request: 0x%02X", request);
if (0 == (requesttype & 0x80))
DEBUG_XXD("send: ", bytes, size);
ret = libusb_control_transfer(usbDevice[reader_index].dev_handle,
requesttype, request, value, usbDevice[reader_index].interface,
bytes, size, usbDevice[reader_index].ccid.readTimeout);
if (ret < 0)
{
DEBUG_CRITICAL5("control failed (%d/%d): %d %s",
usbDevice[reader_index].bus_number,
usbDevice[reader_index].device_address, ret,
strerror(errno));
return ret; // STATUS_UNSUCCESSFUL;
}
if (requesttype & 0x80)
DEBUG_XXD("receive: ", bytes, ret);
return ret;
} /* ControlUSB */
Regards
Godfrey
_______________________________________________
Muscle mailing list
[email protected]
http://lists.drizzle.com/mailman/listinfo/muscle