Пример #1
0
/*****************************************************************************
 *
 *					WriteUSB
 *
 ****************************************************************************/
status_t WriteUSB(unsigned int reader_index, unsigned int length,
	unsigned char *buffer)
{
	int rv;
	int actual_length;
	char debug_header[] = "-> 121234 ";

	(void)snprintf(debug_header, sizeof(debug_header), "-> %06X ",
		(int)reader_index);

	DEBUG_XXD(debug_header, buffer, length);

	rv = libusb_bulk_transfer(usbDevice[reader_index].dev_handle,
		usbDevice[reader_index].bulk_out, buffer, length,
		&actual_length, USB_WRITE_TIMEOUT);

	if (rv < 0)
	{
		DEBUG_CRITICAL5("write failed (%d/%d): %d %s",
			usbDevice[reader_index].bus_number,
			usbDevice[reader_index].device_address, rv, strerror(errno));

		if (ENODEV == errno)
			return STATUS_NO_SUCH_DEVICE;

		return STATUS_UNSUCCESSFUL;
	}

	return STATUS_SUCCESS;
} /* WriteUSB */
Пример #2
0
/*****************************************************************************
 *
 *					WriteUSB
 *
 ****************************************************************************/
status_t WriteUSB(unsigned int reader_index, unsigned int length,
	unsigned char *buffer)
{
	int rv;
	char debug_header[] = "-> 121234 ";

	(void)snprintf(debug_header, sizeof(debug_header), "-> %06X ",
		(int)reader_index);

	DEBUG_XXD(debug_header, buffer, length);

	rv = usb_bulk_write(usbDevice[reader_index].handle,
		usbDevice[reader_index].bulk_out, (char *)buffer, length,
		USB_WRITE_TIMEOUT);

	if (rv < 0)
	{
		DEBUG_CRITICAL4("usb_bulk_write(%s/%s): %s",
			usbDevice[reader_index].dirname, usbDevice[reader_index].filename,
			strerror(errno));

		if (ENODEV == errno)
			return STATUS_NO_SUCH_DEVICE;

		return STATUS_UNSUCCESSFUL;
	}

	return STATUS_SUCCESS;
} /* WriteUSB */
/*****************************************************************************
 *
 *					WriteUSB
 *
 ****************************************************************************/
status_t WriteUSB(unsigned int reader_index, unsigned int length,
	unsigned char *buffer)
{
	int rv;
	char debug_header[] = "-> 121234 ";
	int pos;
	int len;
	int delayed = FALSE;

	(void)snprintf(debug_header, sizeof(debug_header), "-> %06X ",
		(int)reader_index);

	DEBUG_XXD(debug_header, buffer, length);

	// Fix APG8201 and ACR85 ICC cannot receive command properly
	// Add delay for APG8201 and ACR85 ICC
	if ((usbDevice[reader_index].ccid.readerID == ACS_APG8201) ||
		(usbDevice[reader_index].ccid.readerID == ACS_ACR85_PINPAD_READER_ICC))
	{
		delayed = TRUE;
	}

	// Send command by dividing number of packets
	pos = 0;
	while (length > 0)
	{
		if (length > usbDevice[reader_index].bulkOutMaxPacketSize)
			len = usbDevice[reader_index].bulkOutMaxPacketSize;
		else
			len = length;

		rv = usb_bulk_write(usbDevice[reader_index].handle,
			usbDevice[reader_index].bulk_out, (char *)buffer + pos, len,
			USB_WRITE_TIMEOUT);

		if (rv < 0)
		{
			DEBUG_CRITICAL4("usb_bulk_write(%s/%s): %s",
				usbDevice[reader_index].dirname, usbDevice[reader_index].filename,
				strerror(errno));

			if (ENODEV == errno)
				return STATUS_NO_SUCH_DEVICE;

			return STATUS_UNSUCCESSFUL;
		}

		if (delayed)
		{
			// Delay 10 ms
			if (length > usbDevice[reader_index].bulkOutMaxPacketSize)
				usleep(10 * 1000);
		}

		pos += len;
		length -= len;
	}

	return STATUS_SUCCESS;
} /* WriteUSB */
Пример #4
0
int
PPS_Exchange (int lun, BYTE * params, unsigned *length, unsigned char *pps1)
{
  BYTE confirm[PPS_MAX_LENGTH];
  unsigned len_request, len_confirm;
  int ret;

  len_request = PPS_GetLength (params);
  params[len_request - 1] = PPS_GetPCK(params, len_request - 1);

  DEBUG_XXD ("PPS: Sending request: ", params, len_request);

  /* Send PPS request */
  if (CCID_Transmit (lun, len_request, params, isCharLevel(lun) ? 4 : 0, 0)
	!= IFD_SUCCESS)
    return PPS_ICC_ERROR;

  /* Get PPS confirm */
  len_confirm = sizeof(confirm);
  if (CCID_Receive (lun, &len_confirm, confirm, NULL) != IFD_SUCCESS)
    return PPS_ICC_ERROR;

  DEBUG_XXD ("PPS: Receiving confirm: ", confirm, len_confirm);

  if (!PPS_Match (params, len_request, confirm, len_confirm))
    ret = PPS_HANDSAKE_ERROR;
  else
    ret = PPS_OK;

  *pps1 = 0x11;	/* default TA1 */

  /* if PPS1 is echoed */
  if (PPS_HAS_PPS1 (params) && PPS_HAS_PPS1 (confirm))
      *pps1 = confirm[2];

  /* Copy PPS handsake */
  memcpy (params, confirm, len_confirm);
  (*length) = len_confirm;

  return ret;
}
Пример #5
0
/*****************************************************************************
 *
 *				ReadChunk: read a minimum number of bytes
 *
 *****************************************************************************/
static int ReadChunk(unsigned int reader_index, unsigned char *buffer,
	int buffer_length, int min_length)
{
	int fd = serialDevice[reader_index].fd;
# ifndef S_SPLINT_S
	fd_set fdset;
# endif
	struct timeval t;
	int i, rv = 0;
	int already_read;
	char debug_header[] = "<- 123456 ";

	(void)snprintf(debug_header, sizeof(debug_header), "<- %06X ",
		reader_index);

	already_read = 0;
	while (already_read < min_length)
	{
		/* use select() to, eventually, timeout */
		FD_ZERO(&fdset);
		FD_SET(fd, &fdset);
		t.tv_sec = serialDevice[reader_index].ccid.readTimeout / 1000;
		t.tv_usec = (serialDevice[reader_index].ccid.readTimeout - t.tv_sec*1000)*1000;

		i = select(fd+1, &fdset, NULL, NULL, &t);
		if (i == -1)
		{
			DEBUG_CRITICAL2("select: %s", strerror(errno));
			return -1;
		}
		else
			if (i == 0)
			{
				DEBUG_COMM2("Timeout! (%d ms)", serialDevice[reader_index].ccid.readTimeout);
				return -1;
			}

		rv = read(fd, buffer + already_read, buffer_length - already_read);
		if (rv < 0)
		{
			DEBUG_COMM2("read error: %s", strerror(errno));
			return -1;
		}

		DEBUG_XXD(debug_header, buffer + already_read, rv);

		already_read += rv;
		DEBUG_COMM3("read: %d, to read: %d", already_read,
			min_length);
	}

	return already_read;
} /* ReadChunk */
Пример #6
0
/*****************************************************************************
 *
 *					ReadUSB
 *
 ****************************************************************************/
status_t ReadUSB(unsigned int reader_index, unsigned int * length,
	unsigned char *buffer)
{
	int rv;
	int actual_length;
	char debug_header[] = "<- 121234 ";
	_ccid_descriptor *ccid_descriptor = get_ccid_descriptor(reader_index);
	int duplicate_frame = 0;

read_again:
	(void)snprintf(debug_header, sizeof(debug_header), "<- %06X ",
		(int)reader_index);

	rv = libusb_bulk_transfer(usbDevice[reader_index].dev_handle,
		usbDevice[reader_index].bulk_in, buffer, *length,
		&actual_length, usbDevice[reader_index].ccid.readTimeout);

	if (rv < 0)
	{
		*length = 0;
		DEBUG_CRITICAL5("read failed (%d/%d): %d %s",
			usbDevice[reader_index].bus_number,
			usbDevice[reader_index].device_address, rv, strerror(errno));

		if (ENODEV == errno)
			return STATUS_NO_SUCH_DEVICE;

		return STATUS_UNSUCCESSFUL;
	}

	*length = actual_length;

	DEBUG_XXD(debug_header, buffer, *length);

#define BSEQ_OFFSET 6
	if ((*length >= BSEQ_OFFSET)
		&& (buffer[BSEQ_OFFSET] < *ccid_descriptor->pbSeq -1))
	{
		duplicate_frame++;
		if (duplicate_frame > 10)
		{
			DEBUG_CRITICAL("Too many duplicate frame detected");
			return STATUS_UNSUCCESSFUL;
		}
		DEBUG_INFO("Duplicate frame detected");
		goto read_again;
	}

	return STATUS_SUCCESS;
} /* ReadUSB */
Пример #7
0
/*****************************************************************************
 *
 *					ReadUSB
 *
 ****************************************************************************/
status_t ReadUSB(unsigned int reader_index, unsigned int * length,
	unsigned char *buffer)
{
	int rv;
	char debug_header[] = "<- 121234 ";
	_ccid_descriptor *ccid_descriptor = get_ccid_descriptor(reader_index);
	int duplicate_frame = 0;

read_again:
	(void)snprintf(debug_header, sizeof(debug_header), "<- %06X ",
		(int)reader_index);

	rv = usb_bulk_read(usbDevice[reader_index].handle,
		usbDevice[reader_index].bulk_in, (char *)buffer, *length,
		usbDevice[reader_index].ccid.readTimeout * 1000);

	if (rv < 0)
	{
		*length = 0;
		DEBUG_CRITICAL4("usb_bulk_read(%s/%s): %s",
			usbDevice[reader_index].dirname, usbDevice[reader_index].filename,
			strerror(errno));

		if (ENODEV == errno)
			return STATUS_NO_SUCH_DEVICE;

		return STATUS_UNSUCCESSFUL;
	}

	*length = rv;

	DEBUG_XXD(debug_header, buffer, *length);

#define BSEQ_OFFSET 6
	if ((*length >= BSEQ_OFFSET)
		&& (buffer[BSEQ_OFFSET] < *ccid_descriptor->pbSeq -1))
	{
		duplicate_frame++;
		if (duplicate_frame > 10)
		{
			DEBUG_CRITICAL("Too many duplicate frame detected");
			return STATUS_UNSUCCESSFUL;
		}
		DEBUG_INFO("Duplicate frame detected");
		goto read_again;
	}

	return STATUS_SUCCESS;
} /* ReadUSB */
Пример #8
0
/*****************************************************************************
 *
 *				WriteSerial: Send bytes to the card reader
 *
 *****************************************************************************/
status_t WriteSerial(unsigned int reader_index, unsigned int length,
	unsigned char *buffer)
{
	unsigned int i;
	unsigned char lrc;
	unsigned char low_level_buffer[GEMPCTWIN_MAXBUF];

	char debug_header[] = "-> 123456 ";

	(void)snprintf(debug_header, sizeof(debug_header), "-> %06X ",
		reader_index);

	if (length > GEMPCTWIN_MAXBUF-3)
	{
		DEBUG_CRITICAL3("command too long: %d for max %d",
			length, GEMPCTWIN_MAXBUF-3);
		return STATUS_UNSUCCESSFUL;
	}

	/* header */
	low_level_buffer[0] = 0x03;	/* SYNC */
	low_level_buffer[1] = 0x06;	/* ACK */

	/* CCID command */
	memcpy(low_level_buffer+2, buffer, length);

	/* checksum */
	lrc = 0;
	for(i=0; i<length+2; i++)
		lrc ^= low_level_buffer[i];
	low_level_buffer[length+2] = lrc;

	DEBUG_XXD(debug_header, low_level_buffer, length+3);

	if (write(serialDevice[reader_index].fd, low_level_buffer,
		length+3) != length+3)
	{
		DEBUG_CRITICAL2("write error: %s", strerror(errno));
		return STATUS_UNSUCCESSFUL;
	}

	return STATUS_SUCCESS;
} /* WriteSerial */
Пример #9
0
/*****************************************************************************
 *
 *					WriteUSB
 *
 ****************************************************************************/
status_t WriteUSB(unsigned int reader_index, unsigned int length,
	unsigned char *buffer)
{
	int rv;
	int actual_length;
	char debug_header[] = "-> 121234 ";

	(void)snprintf(debug_header, sizeof(debug_header), "-> %06X ",
		(int)reader_index);

	if (usbDevice[reader_index].ccid.zlp)
	{ /* Zero Length Packet */
		int dummy_length;

		/* try to read a ZLP so transfer length = 0
		 * timeout of 1 ms */
		(void)libusb_bulk_transfer(usbDevice[reader_index].dev_handle,
			usbDevice[reader_index].bulk_in, NULL, 0, &dummy_length, 1);
	}

	DEBUG_XXD(debug_header, buffer, length);

	rv = libusb_bulk_transfer(usbDevice[reader_index].dev_handle,
		usbDevice[reader_index].bulk_out, buffer, length,
		&actual_length, USB_WRITE_TIMEOUT);

	if (rv < 0)
	{
		DEBUG_CRITICAL5("write failed (%d/%d): %d %s",
			usbDevice[reader_index].bus_number,
			usbDevice[reader_index].device_address, rv, strerror(errno));

		if ((ENODEV == errno) || (LIBUSB_ERROR_NO_DEVICE == rv))
			return STATUS_NO_SUCH_DEVICE;

		return STATUS_UNSUCCESSFUL;
	}

	return STATUS_SUCCESS;
} /* WriteUSB */
Пример #10
0
/*****************************************************************************
 *
 *				ReadSerial: Receive bytes from the card reader
 *
 *****************************************************************************/
status_t ReadSerial(unsigned int reader_index,
	unsigned int *length, unsigned char *buffer)
{
	unsigned char c;
	int rv;
	int echo;
	int to_read;
	int i;

	/* we get the echo first */
	echo = serialDevice[reader_index].echo;

start:
	DEBUG_COMM("start");
	if ((rv = get_bytes(reader_index, &c, 1)) != STATUS_SUCCESS)
		return rv;

	if (c == RDR_to_PC_NotifySlotChange)
		goto slot_change;

	if (c == SYNC)
		goto sync;

	if (c >= 0x80)
	{
		DEBUG_COMM2("time request: 0x%02X", c);
		goto start;
	}

	DEBUG_CRITICAL2("Got 0x%02X", c);
	return STATUS_COMM_ERROR;

slot_change:
	DEBUG_COMM("slot change");
	if ((rv = get_bytes(reader_index, &c, 1)) != STATUS_SUCCESS)
		return rv;

	if (c == CARD_ABSENT)
	{
		DEBUG_COMM("Card removed");
	}
	else
		if (c == CARD_PRESENT)
		{
			DEBUG_COMM("Card inserted");
		}
		else
		{
			DEBUG_COMM2("Unknown card movement: %d", c);
		}
	goto start;

sync:
	DEBUG_COMM("sync");
	if ((rv = get_bytes(reader_index, &c, 1)) != STATUS_SUCCESS)
		return rv;

	if (c == CTRL_ACK)
		goto ack;

	if (c == CTRL_NAK)
		goto nak;

	DEBUG_CRITICAL2("Got 0x%02X instead of ACK/NAK", c);
	return STATUS_COMM_ERROR;

nak:
	DEBUG_COMM("nak");
	if ((rv = get_bytes(reader_index, &c, 1)) != STATUS_SUCCESS)
		return rv;

	if (c != (SYNC ^ CTRL_NAK))
	{
		DEBUG_CRITICAL2("Wrong LRC: 0x%02X", c);
		return STATUS_COMM_ERROR;
	}
	else
	{
		DEBUG_COMM("NAK requested");
		return STATUS_COMM_NAK;
	}

ack:
	DEBUG_COMM("ack");
	/* normal CCID frame */
	if ((rv = get_bytes(reader_index, buffer, 5)) != STATUS_SUCCESS)
		return rv;

	/* total frame size */
	to_read = 10+dw2i(buffer, 1);

	if ((to_read < 10) || (to_read > (int)*length))
	{
		DEBUG_CRITICAL2("Wrong value for frame size: %d", to_read);
		return STATUS_COMM_ERROR;
	}

	DEBUG_COMM2("frame size: %d", to_read);
	if ((rv = get_bytes(reader_index, buffer+5, to_read-5)) != STATUS_SUCCESS)
		return rv;

	DEBUG_XXD("frame: ", buffer, to_read);

	/* lrc */
	DEBUG_COMM("lrc");
	if ((rv = get_bytes(reader_index, &c, 1)) != STATUS_SUCCESS)
		return rv;

	DEBUG_COMM2("lrc: 0x%02X", c);
	for (i=0; i<to_read; i++)
		c ^= buffer[i];

	if (c != (SYNC ^ CTRL_ACK))
		DEBUG_CRITICAL2("Wrong LRC: 0x%02X", c);

	if (echo)
	{
		echo = FALSE;
		goto start;
	}

	/* length of data read */
	*length = to_read;

	return STATUS_SUCCESS;
} /* ReadSerial */
Пример #11
0
/*
 * Send/receive block
 */
static int t1_xcv(t1_state_t * t1, unsigned char *block, size_t slen,
	size_t rmax)
{
	int n, m;
	_ccid_descriptor *ccid_desc ;
	int oldReadTimeout;
	unsigned int rmax_int;

	DEBUG_XXD("sending: ", block, slen);

	ccid_desc = get_ccid_descriptor(t1->lun);
	oldReadTimeout = ccid_desc->readTimeout;

	if (t1->wtx > 1)
	{
		/* set the new temporary timeout at WTX card request */
		ccid_desc->readTimeout *=  t1->wtx;
		DEBUG_INFO2("New timeout at WTX request: %d sec",
			ccid_desc->readTimeout);
	}

	if (isCharLevel(t1->lun))
	{
		rmax = 3;

		n = CCID_Transmit(t1 -> lun, slen, block, rmax, t1->wtx);
		if (n != IFD_SUCCESS)
			return n;

		/* the second argument of CCID_Receive() is (unsigned int *)
		 * so we can't use &rmax since &rmax is a (size_t *) and may not
		 * be the same on 64-bits architectures for example (iMac G5) */
		rmax_int = rmax;
		n = CCID_Receive(t1 -> lun, &rmax_int, block, NULL);
		rmax = rmax_int;

		if (n == IFD_PARITY_ERROR)
			return -2;
		if (n != IFD_SUCCESS)
			return -1;

		rmax = block[2] + 1;

		n = CCID_Transmit(t1 -> lun, 0, block, rmax, t1->wtx);
		if (n != IFD_SUCCESS)
			return n;

		rmax_int = rmax;
		n = CCID_Receive(t1 -> lun, &rmax_int, &block[3], NULL);
		rmax = rmax_int;
		if (n == IFD_PARITY_ERROR)
			return -2;
		if (n != IFD_SUCCESS)
			return -1;

		n = rmax + 3;
	}
	else
	{
		n = CCID_Transmit(t1 -> lun, slen, block, 0, t1->wtx);
		t1->wtx = 0;	/* reset to default value */
		if (n != IFD_SUCCESS)
			return n;

		/* Get the response en bloc */
		rmax_int = rmax;
		n = CCID_Receive(t1 -> lun, &rmax_int, block, NULL);
		rmax = rmax_int;
		if (n == IFD_PARITY_ERROR)
			return -2;
		if (n != IFD_SUCCESS)
			return -1;

		n = rmax;
	}

	if (n >= 0)
	{
		m = block[2] + 3 + t1->rc_bytes;
		if (m < n)
			n = m;
	}

	if (n >= 0)
		DEBUG_XXD("received: ", block, n);

	/* Restore initial timeout */
	ccid_desc->readTimeout = oldReadTimeout;

	return n;
}