Example #1
0
void CCID_DispatchMessage(void)
{
    uint8_t ErrorCode;

    if(gu8IsBulkOutReady)
    {
        switch(UsbMessageBuffer[OFFSET_BMESSAGETYPE])
        {
        case PC_TO_RDR_ICCPOWERON:
            ErrorCode = PC_to_RDR_IccPowerOn();
            RDR_to_PC_DataBlock(ErrorCode);
            break;
        case PC_TO_RDR_ICCPOWEROFF:
            ErrorCode = PC_to_RDR_IccPowerOff();
            RDR_to_PC_SlotStatus(ErrorCode);
            break;
        case PC_TO_RDR_GETSLOTSTATUS:
            ErrorCode = PC_to_RDR_GetSlotStatus();
            RDR_to_PC_SlotStatus(ErrorCode);
            break;
        case PC_TO_RDR_XFRBLOCK:
            ErrorCode = PC_to_RDR_XfrBlock();
            RDR_to_PC_DataBlock(ErrorCode);
            break;
        case PC_TO_RDR_GETPARAMETERS:
            ErrorCode = PC_to_RDR_GetParameters();
            RDR_to_PC_Parameters(ErrorCode);
            break;
        case PC_TO_RDR_RESETPARAMETERS:
            ErrorCode = PC_to_RDR_ResetParameters();
            RDR_to_PC_Parameters(ErrorCode);
            break;
        case PC_TO_RDR_SETPARAMETERS:
            ErrorCode = PC_to_RDR_SetParameters();
            RDR_to_PC_Parameters(ErrorCode);
            break;
        case PC_TO_RDR_ESCAPE:
            ErrorCode = PC_to_RDR_Escape();
            RDR_to_PC_Escape(ErrorCode);
            break;
        case PC_TO_RDR_ICCCLOCK:
            ErrorCode = PC_to_RDR_IccClock();
            RDR_to_PC_SlotStatus(ErrorCode);
            break;
        case PC_TO_RDR_ABORT:
            ErrorCode = PC_to_RDR_Abort();
            RDR_to_PC_SlotStatus(ErrorCode);
            break;
        case PC_TO_RDR_SETDATARATEANDCLOCKFREQUENCY:
        case PC_TO_RDR_SECURE:
        case PC_TO_RDR_T0APDU:
        case PC_TO_RDR_MECHANICAL:
        default:
            CmdNotSupported();
            break;
        }

        CCID_BulkInMessage();
        gu8IsBulkOutReady = 0;
    }
}
/**
 * Process a APDU using the CCID APDU transfer mode
 *
 * @param ctx Reader context
 * @param lc Length of command APDU
 * @param cmd Command APDU
 * @param lr Length of response APDU
 * @param rsp Response APDU
 * @return 0 on success, -1 on error
 */
static int ccidAPDUProcess (struct scr *ctx,
				   unsigned int  lc,
				   unsigned char *cmd,
				   unsigned int  *lr,
				   unsigned char *rsp)
{
	int rc,r,maxlr;
	unsigned int len;
	unsigned char buf[BUFFMAX],*po,status,error,chain;
	unsigned short level = 0;

	maxlr = *lr;
	*lr = 0;
	po = cmd;
	while (lc > 0) {
		len = lc;
		if (lc > BUFFMAX) {
			if (level)
				level = 3;			// Intermediate extended command
			else
				level = 1;			// First extended command
			len = BUFFMAX;
		} else {
			if (level)
				level = 2;			// Final extended command
		}

		rc = PC_to_RDR_XfrBlock(ctx, len, po, (unsigned char)level);
		if (rc < 0)
			return -1;

		lc -= len;
		po += len;

		len = BUFFMAX;
		rc = RDR_to_PC_DataBlock(ctx, &len, buf, &status, &error, &chain);
		if (rc < 0)
			return -1;
	}

	r = 0;
	while (1) {
		if (len > maxlr) {
			len = maxlr;
			r = ERR_MEMORY;
		}

		memcpy(rsp, buf, len);
		rsp += len;
		maxlr -= len;
		*lr += len;

		if ((chain == 1) || (chain == 3)) {
			rc = PC_to_RDR_XfrBlock(ctx, 0, NULL, 0x10);
			if (rc < 0)
				return -1;
			len = BUFFMAX;
			rc = RDR_to_PC_DataBlock(ctx, &len, buf, &status, &error, &chain);
			if (rc < 0)
				return -1;
			continue;
		}
		break;
	}

	return r;
}
Example #3
-1
/**
  * @brief  CCID_CmdDecode
  *         Parse the commands and Proccess command
  * @param  pdev: device instance
  * @retval None
  */
void CCID_CmdDecode(USB_CORE_HANDLE  *pdev)
{
  uint8_t errorCode;
  
  switch (Ccid_bulkout_data.bMessageType)
  {
  case PC_TO_RDR_ICCPOWERON:
    errorCode = PC_to_RDR_IccPowerOn();
    RDR_to_PC_DataBlock(errorCode);
    break;
  case PC_TO_RDR_ICCPOWEROFF:
    errorCode = PC_to_RDR_IccPowerOff();
    RDR_to_PC_SlotStatus(errorCode);
    break;
  case PC_TO_RDR_GETSLOTSTATUS:
    errorCode = PC_to_RDR_GetSlotStatus();
    RDR_to_PC_SlotStatus(errorCode);
    break;
  case PC_TO_RDR_XFRBLOCK:
    errorCode = PC_to_RDR_XfrBlock();
    RDR_to_PC_DataBlock(errorCode);
    break;
  case PC_TO_RDR_GETPARAMETERS:
    errorCode = PC_to_RDR_GetParameters();
    RDR_to_PC_Parameters(errorCode);
    break;
  case PC_TO_RDR_RESETPARAMETERS:
    errorCode = PC_to_RDR_ResetParameters();
    RDR_to_PC_Parameters(errorCode);
    break;
  case PC_TO_RDR_SETPARAMETERS:
    errorCode = PC_to_RDR_SetParameters();
    RDR_to_PC_Parameters(errorCode);
    break;
  case PC_TO_RDR_ESCAPE:
    errorCode = PC_to_RDR_Escape();
    RDR_to_PC_Escape(errorCode);
    break;
  case PC_TO_RDR_ICCCLOCK:
    errorCode = PC_to_RDR_IccClock();
    RDR_to_PC_SlotStatus(errorCode);
    break;
  case PC_TO_RDR_ABORT:
    errorCode = PC_to_RDR_Abort();
    RDR_to_PC_SlotStatus(errorCode);
    break;
  case PC_TO_RDR_T0APDU:
    errorCode = PC_TO_RDR_T0Apdu();
    RDR_to_PC_SlotStatus(errorCode);
    break;
  case PC_TO_RDR_MECHANICAL:
    errorCode = PC_TO_RDR_Mechanical();
    RDR_to_PC_SlotStatus(errorCode);
    break;   
  case PC_TO_RDR_SETDATARATEANDCLOCKFREQUENCY:
    errorCode = PC_TO_RDR_SetDataRateAndClockFrequency();
    RDR_to_PC_DataRateAndClockFrequency(errorCode);
    break;
  case PC_TO_RDR_SECURE:
    errorCode = PC_TO_RDR_Secure();
    RDR_to_PC_DataBlock(errorCode);
    break;
  default:
    RDR_to_PC_SlotStatus(SLOTERROR_CMD_NOT_SUPPORTED);
    break;
  }
  
     /********** Decide for all commands ***************/ 
  if (Ccid_BulkState == CCID_STATE_SEND_RESP)
  {
    CCID_Response_SendData(pdev, (uint8_t*)&Ccid_bulkin_data, 
                                  Ccid_bulkin_data.u16SizeToSend);
  }
}