Beispiel #1
0
int32_t ICC_Async_CardWrite (struct s_reader *reader, unsigned char *command, uint16_t command_len, unsigned char *rsp, uint16_t *lr)
{
#ifdef HAVE_PCSC
	if (reader->typ == R_PCSC)
 	  return (pcsc_reader_do_api(reader, command, rsp, lr, command_len));
#endif
	*lr = 0; //will be returned in case of error

	int32_t ret;

	LOCK_SC8IN1;

	int32_t try = 1;
	do {
	 switch (reader->protocol_type) {
		if (try > 1)
			cs_log("Warning: reader %s needed try nr %i, next ECM has some delay:", reader->label, try);
		case ATR_PROTOCOL_TYPE_T0:
			ret = Protocol_T0_Command (reader, command, command_len, rsp, lr);
			break;
		case ATR_PROTOCOL_TYPE_T1:
			ret = Protocol_T1_Command (reader, command, command_len, rsp, lr);
			if (ret != OK) {
				//try to resync
				unsigned char resync[] = { 0x21, 0xC0, 0x00, 0xE1 };
				Protocol_T1_Command (reader, resync, sizeof(resync), rsp, lr);
				reader->ifsc = DEFAULT_IFSC;
			}
			break;
		case ATR_PROTOCOL_TYPE_T14:
			ret = Protocol_T14_ExchangeTPDU (reader, command, command_len, rsp, lr);
			break;
		default:
			cs_log("Error, unknown protocol type %i",reader->protocol_type);
			ret = ERROR;
	 }
	try++;
	} while ((try < 3) && (ret != OK)); //always do one retry when failing

	UNLOCK_SC8IN1;

	if (ret) {
		cs_debug_mask(D_TRACE, "ERROR, function call Protocol_T0_Command returns error.");
		return ERROR;
	}

	cs_ddump_mask(D_READER, rsp, *lr, "answer from cardreader %s:", reader->label);
	return OK;
}

int32_t ICC_Async_SetTimings (struct s_reader * reader, uint32_t wait_etu)
{
	reader->read_timeout = ETU_to_ms(reader, wait_etu);
	cs_debug_mask(D_IFD, "Setting timeout to %i", wait_etu);
	return OK;
}
Beispiel #2
0
int32_t ICC_Async_CardWrite(struct s_reader *reader, unsigned char *command, uint16_t command_len, unsigned char *rsp, uint16_t *lr)
{
	int32_t ret;

	*lr = 0; //will be returned in case of error
	if(reader->crdr.card_write)
	{
		call(reader->crdr.card_write(reader, command, rsp, lr, command_len));
		return OK;
	}

	if(reader->crdr.lock)
		{ reader->crdr.lock(reader); }

	int32_t try = 1;
	uint16_t type = 0;
	do
	{
		switch(reader->protocol_type)
		{
			if(try > 1)
					rdr_log(reader, "Warning: needed try nr %i, next ECM has some delay", try);
		case ATR_PROTOCOL_TYPE_T0:
			ret = Protocol_T0_Command(reader, command, command_len, rsp, lr);
			type = 0;
			break;
		case ATR_PROTOCOL_TYPE_T1:
			ret = Protocol_T1_Command(reader, command, command_len, rsp, lr);
			type = 1;
			if(ret != OK && !reader->crdr.skip_t1_command_retries)
			{
				//try to resync
				rdr_log(reader, "Resync error: readtimeouts %d/%d (max/min) us, writetimeouts %d/%d (max/min) us", reader->maxreadtimeout, reader->minreadtimeout, reader->maxwritetimeout, reader->minwritetimeout);
				unsigned char resync[] = { 0x21, 0xC0, 0x00, 0xE1 };
				ret = Protocol_T1_Command(reader, resync, sizeof(resync), rsp, lr);
				if(ret == OK)
				{
					//reader->ifsc = DEFAULT_IFSC; //tryfix cardtimeouts: ifsc is setup at card init, on resync it should not return to default_ifsc
					rdr_log(reader, "T1 Resync command succesfull ifsc = %i", reader->ifsc);
					ret = ERROR;
				}
				else
				{
					rdr_log(reader, "T1 Resync command error, trying to reactivate!");
					ATR atr;
					ICC_Async_Activate(reader, &atr, reader->deprecated);
					if(reader->crdr.unlock)
						{ reader->crdr.unlock(reader); }
					return ERROR;
				}
			}
			break;
		case ATR_PROTOCOL_TYPE_T14:
			ret = Protocol_T14_ExchangeTPDU(reader, command, command_len, rsp, lr);
			type = 14;
			break;
		default:
			rdr_log(reader, "ERROR: Unknown protocol type %i", reader->protocol_type);
			type = 99; // use 99 for unknown.
			ret = ERROR;
		}
		try++;
	}
	while((try < 3) && (ret != OK));    //always do one retry when failing

	if(reader->crdr.unlock)
		{ reader->crdr.unlock(reader); }

	if(ret)
	{
		rdr_debug_mask(reader, D_TRACE, "ERROR: Protocol_T%d_Command returns error", type);
		return ERROR;
	}

	rdr_ddump_mask(reader, D_READER, rsp, *lr, "Answer from cardreader:");
	return OK;
}

int32_t ICC_Async_GetTimings(struct s_reader *reader, uint32_t wait_etu)
{
	int32_t timeout = ETU_to_us(reader, wait_etu);
	rdr_debug_mask(reader, D_IFD, "Setting timeout to %i ETU (%d us)", wait_etu, timeout);
	return timeout;
}