1384 lines
51 KiB
C
1384 lines
51 KiB
C
/*
|
|
* Copyright (C) 2010 NXP Semiconductors
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
/*!
|
|
* =========================================================================== *
|
|
* *
|
|
* *
|
|
* \file phHciNfc_Emulation.c *
|
|
* \brief HCI Emulation management routines. *
|
|
* *
|
|
* *
|
|
* Project: NFC-FRI-1.1 *
|
|
* *
|
|
* $Date: Tue Jun 8 09:30:37 2010 $ *
|
|
* $Author: ing04880 $ *
|
|
* $Revision: 1.52 $ *
|
|
* $Aliases: NFC_FRI1.1_WK1023_R35_1 $
|
|
* *
|
|
* =========================================================================== *
|
|
*/
|
|
|
|
/*
|
|
***************************** Header File Inclusion ****************************
|
|
*/
|
|
#include <phNfcConfig.h>
|
|
#include <phNfcCompId.h>
|
|
#include <phNfcHalTypes.h>
|
|
#include <phHciNfc_Pipe.h>
|
|
#include <phHciNfc_Emulation.h>
|
|
#include <phHciNfc_WI.h>
|
|
#include <phHciNfc_SWP.h>
|
|
#ifdef ENABLE_P2P
|
|
#include <phHciNfc_NfcIPMgmt.h>
|
|
#endif
|
|
#ifdef HOST_EMULATION
|
|
#include <phHciNfc_CE_A.h>
|
|
#include <phHciNfc_CE_B.h>
|
|
#endif
|
|
#include <phOsalNfc.h>
|
|
/*
|
|
****************************** Macro Definitions *******************************
|
|
*/
|
|
|
|
|
|
|
|
/*
|
|
*************************** Structure and Enumeration ***************************
|
|
*/
|
|
|
|
/** \defgroup grp_hci_nfc HCI Emulation Management Component
|
|
*
|
|
*
|
|
*/
|
|
|
|
typedef enum phHciNfc_EmulationMgmt_Seq{
|
|
NFCIP_TARGET_PIPE_OPEN = 0x00U,
|
|
NFCIP_TARGET_MODE_CONFIG,
|
|
NFCIP_TARGET_MERGE_SAK,
|
|
NFCIP_TARGET_PIPE_CLOSE,
|
|
|
|
HOST_CE_A_INIT,
|
|
HOST_CE_A_RELEASE,
|
|
|
|
HOST_CE_B_INIT,
|
|
HOST_CE_B_RELEASE,
|
|
|
|
WI_PIPE_OPEN,
|
|
WI_ENABLE_EMULATION,
|
|
WI_DEFAULT_EMULATION,
|
|
WI_DISABLE_EMULATION,
|
|
|
|
WI_ENABLE_NOTIFICATION,
|
|
WI_DISABLE_NOTIFICATION,
|
|
|
|
WI_SWITCH_WIRED_MODE,
|
|
WI_SWITCH_DEFAULT_MODE,
|
|
|
|
WI_PIPE_CLOSE,
|
|
|
|
SWP_PIPE_OPEN,
|
|
SWP_ENABLE_EMULATION,
|
|
SWP_DEFAULT_EMULATION,
|
|
SWP_DETECTION,
|
|
SWP_DISABLE_EMULATION,
|
|
SWP_GET_BIT_RATE,
|
|
SWP_PIPE_CLOSE,
|
|
|
|
CONFIG_DEFAULT_EMULATION,
|
|
|
|
END_EMULATION_SEQ
|
|
} phHciNfc_EmulationMgmt_Seq_t;
|
|
|
|
typedef struct phHciNfc_EmulationMgmt_Info{
|
|
phHal_eEmulationType_t se_default;
|
|
uint8_t smx_powerless;
|
|
uint8_t uicc_enable;
|
|
uint8_t uicc_powerless;
|
|
uint8_t uicc_id;
|
|
/* Application ID of the UICC Transaction performed */
|
|
uint8_t uicc_aid[MAX_AID_LEN];
|
|
uint8_t uicc_param[MAX_UICC_PARAM_LEN];
|
|
uint8_t uicc_param_len;
|
|
phHciNfc_Pipe_Info_t *p_uicc_pipe_info;
|
|
phHciNfc_EmulationMgmt_Seq_t emulation_cur_seq;
|
|
phHciNfc_EmulationMgmt_Seq_t emulation_next_seq;
|
|
|
|
|
|
} phHciNfc_EmulationMgmt_Info_t;
|
|
|
|
|
|
/*
|
|
*************************** Static Function Declaration **************************
|
|
*/
|
|
|
|
static
|
|
NFCSTATUS
|
|
phHciNfc_Recv_Uicc_Cmd (
|
|
void *psContext,
|
|
void *pHwRef,
|
|
uint8_t *pCmd,
|
|
#ifdef ONE_BYTE_LEN
|
|
uint8_t length
|
|
#else
|
|
uint16_t length
|
|
#endif
|
|
);
|
|
|
|
static
|
|
NFCSTATUS
|
|
phHciNfc_Recv_Uicc_Event (
|
|
void *psContext,
|
|
void *pHwRef,
|
|
uint8_t *pEvent,
|
|
#ifdef ONE_BYTE_LEN
|
|
uint8_t length
|
|
#else
|
|
uint16_t length
|
|
#endif
|
|
);
|
|
|
|
|
|
/*
|
|
*************************** Function Definitions ***************************
|
|
*/
|
|
|
|
void
|
|
phHciNfc_Uicc_Connectivity(
|
|
phHciNfc_sContext_t *psHciContext,
|
|
void *pHwRef
|
|
)
|
|
{
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
phHciNfc_Pipe_Info_t *pPipeInfo = NULL;
|
|
phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info = NULL;
|
|
|
|
if( NULL != psHciContext->p_emulation_mgmt_info )
|
|
{
|
|
p_emulation_mgmt_info = (phHciNfc_EmulationMgmt_Info_t *)
|
|
psHciContext->p_emulation_mgmt_info ;
|
|
pPipeInfo = psHciContext->p_pipe_list[NXP_PIPE_CONNECTIVITY];
|
|
if( (TRUE == ((phHal_sHwReference_t *)pHwRef)->uicc_connected)
|
|
&& (NULL == pPipeInfo))
|
|
{
|
|
status = phHciNfc_Allocate_Resource((void **)&pPipeInfo,
|
|
sizeof(phHciNfc_Pipe_Info_t));
|
|
if((NULL != pPipeInfo)
|
|
&& (NFCSTATUS_SUCCESS == status))
|
|
{
|
|
/* The Source Host is the UICC Host */
|
|
pPipeInfo->pipe.source.host_id =
|
|
(uint8_t) phHciNfc_UICCHostID;
|
|
/* The Source Gate is same as the Destination Gate */
|
|
pPipeInfo->pipe.source.gate_id =
|
|
(uint8_t) phHciNfc_ConnectivityGate;
|
|
/* The Destination Host is the Terminal Host */
|
|
pPipeInfo->pipe.dest.host_id =
|
|
(uint8_t) phHciNfc_TerminalHostID;
|
|
/* The Source Gate is same as the Destination Gate */
|
|
pPipeInfo->pipe.dest.gate_id =
|
|
(uint8_t) phHciNfc_ConnectivityGate;
|
|
/* The Pipe ID is Hardcoded to Connectivity */
|
|
pPipeInfo->pipe.pipe_id = (uint8_t) NXP_PIPE_CONNECTIVITY;
|
|
|
|
|
|
status = phHciNfc_Uicc_Update_PipeInfo(psHciContext,
|
|
NXP_PIPE_CONNECTIVITY, pPipeInfo);
|
|
if (NFCSTATUS_SUCCESS == status)
|
|
{
|
|
psHciContext->p_pipe_list[NXP_PIPE_CONNECTIVITY] = pPipeInfo;
|
|
p_emulation_mgmt_info->uicc_enable = TRUE;
|
|
}
|
|
else
|
|
{
|
|
(void)phOsalNfc_FreeMemory(pPipeInfo);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
return;
|
|
}
|
|
|
|
/*!
|
|
* \brief Get the pipe_id of Connectivity Managment Gate.
|
|
*
|
|
* This function Get the pipe_id of Connectivity Managment Gate.
|
|
*
|
|
*/
|
|
|
|
|
|
NFCSTATUS
|
|
phHciNfc_Uicc_Get_PipeID(
|
|
phHciNfc_sContext_t *psHciContext,
|
|
uint8_t *ppipe_id
|
|
)
|
|
{
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info = NULL;
|
|
if( (NULL != psHciContext)
|
|
&& ( NULL != ppipe_id )
|
|
&& ( NULL != psHciContext->p_emulation_mgmt_info )
|
|
)
|
|
{
|
|
p_emulation_mgmt_info = (phHciNfc_EmulationMgmt_Info_t *)
|
|
psHciContext->p_emulation_mgmt_info ;
|
|
*ppipe_id = p_emulation_mgmt_info->uicc_id ;
|
|
}
|
|
else
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_PARAMETER);
|
|
}
|
|
return status;
|
|
}
|
|
|
|
|
|
/* Function to Update the Pipe Information */
|
|
NFCSTATUS
|
|
phHciNfc_Uicc_Update_PipeInfo(
|
|
phHciNfc_sContext_t *psHciContext,
|
|
uint8_t pipe_id,
|
|
phHciNfc_Pipe_Info_t *pPipeInfo
|
|
)
|
|
{
|
|
phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info=NULL;
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
|
|
if( NULL == psHciContext )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_PARAMETER);
|
|
}
|
|
else if ( NULL == psHciContext->p_emulation_mgmt_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
p_emulation_mgmt_info = (phHciNfc_EmulationMgmt_Info_t *)
|
|
psHciContext->p_emulation_mgmt_info ;
|
|
/* Update the pipe_id of the Connectivity Gate
|
|
* obtained from the HCI Response */
|
|
p_emulation_mgmt_info->uicc_id = pipe_id;
|
|
p_emulation_mgmt_info->p_uicc_pipe_info = pPipeInfo;
|
|
if ( NULL != pPipeInfo)
|
|
{
|
|
/* Update the Response Receive routine of the Connectivity Gate */
|
|
/* pPipeInfo->recv_resp = phHciNfc_Recv_Uicc_Response; */
|
|
pPipeInfo->recv_cmd = &phHciNfc_Recv_Uicc_Cmd;
|
|
pPipeInfo->recv_event = &phHciNfc_Recv_Uicc_Event;
|
|
}
|
|
}
|
|
|
|
return status;
|
|
}
|
|
|
|
|
|
/*!
|
|
* \brief Updates the Sequence of Emulation Managment Gate.
|
|
*
|
|
* This function Resets/Updates the sequence of the Emulation Management
|
|
* gate.
|
|
*
|
|
*/
|
|
|
|
|
|
NFCSTATUS
|
|
phHciNfc_EmuMgmt_Update_Seq(
|
|
phHciNfc_sContext_t *psHciContext,
|
|
phHciNfc_eSeqType_t seq_type
|
|
)
|
|
{
|
|
phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info=NULL;
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
if( NULL == psHciContext )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_PARAMETER);
|
|
}
|
|
else
|
|
{
|
|
if( NULL == psHciContext->p_emulation_mgmt_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
p_emulation_mgmt_info = (phHciNfc_EmulationMgmt_Info_t *)
|
|
psHciContext->p_emulation_mgmt_info ;
|
|
switch(seq_type)
|
|
{
|
|
case RESET_SEQ:
|
|
case INIT_SEQ:
|
|
{
|
|
#ifdef ENABLE_P2P
|
|
p_emulation_mgmt_info->emulation_cur_seq = NFCIP_TARGET_PIPE_OPEN;
|
|
#else
|
|
p_emulation_mgmt_info->emulation_cur_seq = WI_PIPE_OPEN;
|
|
#endif
|
|
p_emulation_mgmt_info->emulation_next_seq = END_EMULATION_SEQ ;
|
|
break;
|
|
}
|
|
case UPDATE_SEQ:
|
|
{
|
|
p_emulation_mgmt_info->emulation_cur_seq =
|
|
p_emulation_mgmt_info->emulation_next_seq;
|
|
break;
|
|
}
|
|
case INFO_SEQ:
|
|
{
|
|
p_emulation_mgmt_info->emulation_cur_seq = SWP_ENABLE_EMULATION;
|
|
p_emulation_mgmt_info->emulation_next_seq = END_EMULATION_SEQ ;
|
|
break;
|
|
}
|
|
case REL_SEQ:
|
|
{
|
|
p_emulation_mgmt_info->emulation_cur_seq = WI_DISABLE_EMULATION;
|
|
p_emulation_mgmt_info->emulation_next_seq = END_EMULATION_SEQ ;
|
|
break;
|
|
}
|
|
default:
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
return status;
|
|
}
|
|
|
|
|
|
/*!
|
|
* \brief Initialisation of RF Emulation Gates.
|
|
*
|
|
* This function initialses the RF Emulation Management and
|
|
* populates the Reader Management Information Structure
|
|
*
|
|
*/
|
|
|
|
|
|
NFCSTATUS
|
|
phHciNfc_EmuMgmt_Initialise(
|
|
phHciNfc_sContext_t *psHciContext,
|
|
void *pHwRef
|
|
)
|
|
{
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
phHciNfc_Pipe_Info_t *p_pipe_info = NULL;
|
|
phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info=NULL;
|
|
|
|
if( NULL == psHciContext )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_PARAMETER);
|
|
}
|
|
else
|
|
{
|
|
|
|
if( ( NULL == psHciContext->p_emulation_mgmt_info )
|
|
&& (phHciNfc_Allocate_Resource((void **)(&p_emulation_mgmt_info),
|
|
sizeof(phHciNfc_EmulationMgmt_Info_t))== NFCSTATUS_SUCCESS)
|
|
)
|
|
{
|
|
psHciContext->p_emulation_mgmt_info = p_emulation_mgmt_info;
|
|
#ifdef ENABLE_P2P
|
|
p_emulation_mgmt_info->emulation_cur_seq = NFCIP_TARGET_PIPE_OPEN;
|
|
#else
|
|
p_emulation_mgmt_info->emulation_cur_seq = WI_PIPE_OPEN;
|
|
#endif
|
|
p_emulation_mgmt_info->emulation_next_seq = END_EMULATION_SEQ;
|
|
p_emulation_mgmt_info->uicc_id = (uint8_t)HCI_UNKNOWN_PIPE_ID;
|
|
}
|
|
else
|
|
{
|
|
p_emulation_mgmt_info = (phHciNfc_EmulationMgmt_Info_t *)
|
|
psHciContext->p_emulation_mgmt_info ;
|
|
}
|
|
|
|
if( NULL == psHciContext->p_emulation_mgmt_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INSUFFICIENT_RESOURCES);
|
|
}
|
|
#ifdef ESTABLISH_SESSION
|
|
else if(( hciMode_Session == psHciContext->hci_mode )
|
|
&& (NFCIP_TARGET_PIPE_OPEN == p_emulation_mgmt_info->emulation_cur_seq )
|
|
)
|
|
{
|
|
status = NFCSTATUS_SUCCESS;
|
|
}
|
|
#endif
|
|
else
|
|
{
|
|
switch(p_emulation_mgmt_info->emulation_cur_seq )
|
|
{
|
|
#ifdef ENABLE_P2P
|
|
/* NFCIP Target Open sequence */
|
|
case NFCIP_TARGET_PIPE_OPEN:
|
|
{
|
|
p_pipe_info = ((phHciNfc_NfcIP_Info_t *)
|
|
psHciContext->p_nfcip_info)->p_tgt_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_Open_Pipe( psHciContext,
|
|
pHwRef, p_pipe_info );
|
|
if(status == NFCSTATUS_SUCCESS)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
NFCIP_TARGET_MODE_CONFIG;
|
|
status = NFCSTATUS_PENDING;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* NFCIP Target Mode Config sequence */
|
|
case NFCIP_TARGET_MODE_CONFIG:
|
|
{
|
|
#define NFCIP_ACTIVE_SHIFT 0x03U
|
|
#define NFCIP_PASSIVE_MASK 0x07U
|
|
uint8_t mode = ( NXP_NFCIP_ACTIVE_DEFAULT << NFCIP_ACTIVE_SHIFT ) |
|
|
( DEFAULT_NFCIP_TARGET_MODE_SUPPORT & NFCIP_PASSIVE_MASK );
|
|
status = phHciNfc_NfcIP_SetMode( psHciContext, pHwRef,
|
|
NFCIP_TARGET, mode);
|
|
if(status == NFCSTATUS_PENDING )
|
|
{
|
|
#ifdef TGT_MERGE_SAK
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
NFCIP_TARGET_MERGE_SAK;
|
|
#else
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
WI_PIPE_OPEN;
|
|
#endif /* #ifdef TGT_MERGE_SAK */
|
|
/* status = NFCSTATUS_SUCCESS; */
|
|
}
|
|
break;
|
|
}
|
|
#ifdef TGT_MERGE_SAK
|
|
/* NFCIP Target SAK Merge sequence */
|
|
case NFCIP_TARGET_MERGE_SAK:
|
|
{
|
|
status = phHciNfc_NfcIP_SetMergeSak( psHciContext, pHwRef,
|
|
TRUE );
|
|
if(status == NFCSTATUS_PENDING )
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
WI_PIPE_OPEN;
|
|
/* status = NFCSTATUS_SUCCESS; */
|
|
}
|
|
break;
|
|
}
|
|
#endif /* #ifdef TGT_MERGE_SAK */
|
|
#endif /* #ifdef ENABLE_P2P */
|
|
/* Secure Element WI pipe open sequence */
|
|
case WI_PIPE_OPEN:
|
|
{
|
|
p_pipe_info = ((phHciNfc_WI_Info_t *)
|
|
psHciContext->p_wi_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_Open_Pipe( psHciContext,
|
|
pHwRef, p_pipe_info );
|
|
if(status == NFCSTATUS_SUCCESS)
|
|
{
|
|
#ifdef DISABLE_WI_NOTIFICATION
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_PIPE_OPEN;
|
|
#else
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
WI_ENABLE_NOTIFICATION;
|
|
#endif
|
|
status = NFCSTATUS_PENDING;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* Enable the SmartMx Notifications through WI */
|
|
case WI_ENABLE_NOTIFICATION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_WI_Info_t *)
|
|
psHciContext->p_wi_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_WI_Configure_Notifications(
|
|
psHciContext, pHwRef, eEnableEvents );
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_PIPE_OPEN;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* Enable the SmartMx Emulation by Default through WI */
|
|
case WI_ENABLE_EMULATION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_WI_Info_t *)
|
|
psHciContext->p_wi_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_WI_Configure_Default( psHciContext,
|
|
pHwRef, TRUE );
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_PIPE_OPEN;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* SWP pipe open sequence */
|
|
case SWP_PIPE_OPEN:
|
|
{
|
|
p_pipe_info = ((phHciNfc_SWP_Info_t *)
|
|
psHciContext->p_swp_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_Open_Pipe( psHciContext,
|
|
pHwRef, p_pipe_info );
|
|
if(status == NFCSTATUS_SUCCESS)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_ENABLE_EMULATION;
|
|
#ifndef ESTABLISH_SESSION
|
|
status = NFCSTATUS_PENDING;
|
|
#endif
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* Enable the UICC Emulation through SWP */
|
|
case SWP_ENABLE_EMULATION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_SWP_Info_t *)
|
|
psHciContext->p_swp_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
#ifdef SWP_EVENT_USAGE
|
|
status = phHciNfc_SWP_Configure_Mode( psHciContext, pHwRef,
|
|
UICC_SWITCH_MODE_ON );
|
|
/* UICC_SWITCH_MODE_DEFAULT */
|
|
#else
|
|
status = phHciNfc_SWP_Configure_Default( psHciContext,
|
|
pHwRef, TRUE );
|
|
#endif
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_DETECTION;
|
|
/* status = NFCSTATUS_SUCCESS; */
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* Disable the UICC Emulation through SWP */
|
|
case SWP_DETECTION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_SWP_Info_t *)
|
|
psHciContext->p_swp_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
break;
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_Uicc_Connect_Status(
|
|
psHciContext, pHwRef );
|
|
if(status == NFCSTATUS_SUCCESS)
|
|
{
|
|
uint8_t uicc_connect = ((phHciNfc_SWP_Info_t *)
|
|
psHciContext->p_swp_info)->uicc_status;
|
|
if(UICC_CONNECTED == uicc_connect)
|
|
{
|
|
#ifdef SWP_EVENT_USAGE
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_DISABLE_EMULATION;
|
|
#else
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
WI_DISABLE_EMULATION;
|
|
#endif
|
|
((phHal_sHwReference_t *)
|
|
pHwRef)->uicc_connected = TRUE;
|
|
status = NFCSTATUS_PENDING;
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_SWP_Configure_Mode( psHciContext,
|
|
pHwRef, UICC_SWITCH_MODE_DEFAULT );
|
|
(NFCSTATUS_PENDING == status)?
|
|
(p_emulation_mgmt_info->emulation_next_seq =
|
|
WI_DISABLE_EMULATION):
|
|
(p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_DETECTION);
|
|
break;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
/* fall through */
|
|
/* Disable the SmartMx Emulation through WI */
|
|
case WI_DISABLE_EMULATION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_WI_Info_t *)
|
|
psHciContext->p_wi_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_WI_Configure_Mode( psHciContext,
|
|
pHwRef, eSmartMx_Default );
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_DISABLE_EMULATION;
|
|
status = NFCSTATUS_SUCCESS;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
#ifndef SWP_EVENT_USAGE
|
|
/* fall through */
|
|
/* Get the UICC Baud Rate Status */
|
|
case SWP_GET_BIT_RATE:
|
|
{
|
|
p_pipe_info = ((phHciNfc_SWP_Info_t *)
|
|
psHciContext->p_swp_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_SWP_Get_Bitrate(
|
|
psHciContext, pHwRef );
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_DISABLE_EMULATION;
|
|
status = NFCSTATUS_SUCCESS;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
#endif
|
|
/* fall through */
|
|
/* Disable the UICC Emulation through SWP */
|
|
case SWP_DISABLE_EMULATION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_SWP_Info_t *)
|
|
psHciContext->p_swp_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_SWP_Configure_Mode( psHciContext,
|
|
pHwRef, UICC_SWITCH_MODE_DEFAULT );
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
WI_DISABLE_EMULATION;
|
|
/* Disable WI Emulation for Previous Wired
|
|
* Mode Set */
|
|
/* status = NFCSTATUS_SUCCESS; */
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
default:
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_HCI_SEQUENCE);
|
|
break;
|
|
}
|
|
|
|
}/* End of the Sequence Switch */
|
|
|
|
}/* End of the Reader Info Memory Check */
|
|
|
|
} /* End of Null Context Check */
|
|
|
|
return status;
|
|
}
|
|
|
|
/*!
|
|
* \brief Connection Routine for the Uicc.
|
|
*
|
|
* This function tries to enable and initialise the UICC connected
|
|
* through SWP.
|
|
*
|
|
*/
|
|
|
|
|
|
NFCSTATUS
|
|
phHciNfc_Uicc_Connect_Status(
|
|
phHciNfc_sContext_t *psHciContext,
|
|
void *pHwRef
|
|
)
|
|
{
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
/* phHciNfc_Pipe_Info_t *p_pipe_info = NULL; */
|
|
/* phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info=NULL; */
|
|
static uint32_t uicc_connection_retry = 0;
|
|
|
|
if( NULL == psHciContext )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_PARAMETER);
|
|
}
|
|
else
|
|
{
|
|
phHciNfc_SWP_Status_t uicc_status =
|
|
((phHciNfc_SWP_Info_t *)
|
|
psHciContext->p_swp_info)->uicc_status;
|
|
if(uicc_connection_retry == 0)
|
|
{
|
|
#ifdef UICC_STATUS_DELAY
|
|
for( ;uicc_connection_retry < UICC_STATUS_DELAY_COUNT;
|
|
uicc_connection_retry ++ );
|
|
uicc_connection_retry = 0;
|
|
#endif
|
|
status = phHciNfc_SWP_Get_Status(
|
|
psHciContext, pHwRef );
|
|
if (NFCSTATUS_PENDING == status)
|
|
{
|
|
uicc_connection_retry++;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
switch(uicc_status)
|
|
{
|
|
case UICC_CONNECTION_ONGOING:
|
|
case UICC_DISCONNECTION_ONGOING:
|
|
case UICC_NOT_CONNECTED:
|
|
{
|
|
if(uicc_connection_retry <
|
|
UICC_MAX_CONNECT_RETRY)
|
|
{
|
|
status = phHciNfc_SWP_Get_Status(
|
|
psHciContext, pHwRef );
|
|
if (NFCSTATUS_PENDING == status)
|
|
{
|
|
uicc_connection_retry++;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
case UICC_CONNECTED:
|
|
{
|
|
break;
|
|
}
|
|
case UICC_CONNECTION_LOST:
|
|
case UICC_CONNECTION_FAILED:
|
|
default:
|
|
{
|
|
uicc_connection_retry = 0;
|
|
break;
|
|
}
|
|
} /* End of the Status Switch */
|
|
}
|
|
|
|
if( NFCSTATUS_PENDING != status )
|
|
{
|
|
uicc_connection_retry = 0;
|
|
/* Error Scenario due to SWP Disable Config */
|
|
}
|
|
|
|
} /* End of Null Context Check */
|
|
|
|
return status;
|
|
}
|
|
|
|
/*!
|
|
* \brief Release of RF Emulation Gate Configuration.
|
|
*
|
|
* This function initialses the RF Emulation Management and
|
|
* populates the Reader Management Information Structure
|
|
*
|
|
*/
|
|
|
|
|
|
NFCSTATUS
|
|
phHciNfc_EmuMgmt_Release(
|
|
phHciNfc_sContext_t *psHciContext,
|
|
void *pHwRef
|
|
)
|
|
{
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
phHciNfc_Pipe_Info_t *p_pipe_info = NULL;
|
|
phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info=NULL;
|
|
|
|
if( NULL == psHciContext )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_PARAMETER);
|
|
}
|
|
else
|
|
{
|
|
|
|
p_emulation_mgmt_info = (phHciNfc_EmulationMgmt_Info_t *)
|
|
psHciContext->p_emulation_mgmt_info ;
|
|
|
|
if( NULL == psHciContext->p_emulation_mgmt_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INSUFFICIENT_RESOURCES);
|
|
}
|
|
else
|
|
{
|
|
switch(p_emulation_mgmt_info->emulation_cur_seq )
|
|
{
|
|
/* Enable/Disable the SmartMx Emulation through WI
|
|
* After the power down
|
|
*/
|
|
/* Enable the SmartMx Emulation by Default through WI */
|
|
case WI_DEFAULT_EMULATION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_WI_Info_t *)
|
|
psHciContext->p_wi_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_WI_Configure_Default( psHciContext,
|
|
pHwRef, p_emulation_mgmt_info->smx_powerless );
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
WI_DISABLE_EMULATION;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* SmartMx In Default Mode */
|
|
case WI_DISABLE_EMULATION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_WI_Info_t *)
|
|
psHciContext->p_wi_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_WI_Configure_Mode( psHciContext,
|
|
pHwRef, eSmartMx_Default );
|
|
if(status == NFCSTATUS_SUCCESS )
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_DISABLE_EMULATION;
|
|
status = phHciNfc_EmuMgmt_Update_Seq(psHciContext,
|
|
UPDATE_SEQ);
|
|
/* status = NFCSTATUS_PENDING; */
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* Enable/Disable the UICC Emulation through SWP
|
|
* After the power down
|
|
*/
|
|
/* Enable the UICC Emulation by Default through SWP */
|
|
case SWP_DEFAULT_EMULATION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_SWP_Info_t *)
|
|
psHciContext->p_swp_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_SWP_Configure_Default( psHciContext,
|
|
pHwRef, p_emulation_mgmt_info->uicc_powerless );
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
SWP_DISABLE_EMULATION;
|
|
/* status = NFCSTATUS_SUCCESS; */
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* Disable the UICC Emulation through SWP */
|
|
case SWP_DISABLE_EMULATION:
|
|
{
|
|
p_pipe_info = ((phHciNfc_SWP_Info_t *)
|
|
psHciContext->p_swp_info)->p_pipe_info;
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_SWP_Configure_Mode( psHciContext,
|
|
pHwRef, UICC_SWITCH_MODE_DEFAULT );
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
CONFIG_DEFAULT_EMULATION;
|
|
status = phHciNfc_EmuMgmt_Update_Seq(psHciContext,
|
|
UPDATE_SEQ);
|
|
status = NFCSTATUS_SUCCESS;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
/* Configure the Default Secure Element Emulation */
|
|
case CONFIG_DEFAULT_EMULATION:
|
|
{
|
|
#if 0
|
|
if(NULL == p_pipe_info )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI,
|
|
NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
/* status = phHciNfc_DevMgmt_Configure( psHciContext,
|
|
pHwRef, , ); */
|
|
if(status == NFCSTATUS_PENDING)
|
|
{
|
|
p_emulation_mgmt_info->emulation_next_seq =
|
|
END_EMULATION_SEQ;
|
|
status = phHciNfc_EmuMgmt_Update_Seq(psHciContext,
|
|
UPDATE_SEQ);
|
|
status = NFCSTATUS_SUCCESS;
|
|
}
|
|
}
|
|
#endif
|
|
break;
|
|
}
|
|
default:
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_HCI_SEQUENCE);
|
|
break;
|
|
}
|
|
|
|
}/* End of the Sequence Switch */
|
|
|
|
}/* End of the Reader Info Memory Check */
|
|
|
|
} /* End of Null Context Check */
|
|
|
|
return status;
|
|
}
|
|
|
|
#if 0
|
|
NFCSTATUS
|
|
phHciNfc_Emulation_Start (
|
|
phHciNfc_sContext_t *psHciContext,
|
|
void *pHwRef
|
|
)
|
|
{
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
|
|
return status;
|
|
}
|
|
#endif
|
|
|
|
NFCSTATUS
|
|
phHciNfc_Emulation_Cfg (
|
|
phHciNfc_sContext_t *psHciContext,
|
|
void *pHwRef,
|
|
phHciNfc_eConfigType_t cfg_type
|
|
)
|
|
{
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info=NULL;
|
|
phHal_sEmulationCfg_t *p_emulation_cfg = NULL;
|
|
|
|
if( (NULL == psHciContext) || (NULL == pHwRef) )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_PARAMETER);
|
|
}
|
|
else if ( ( NULL == psHciContext->p_emulation_mgmt_info )
|
|
|| ( NULL == psHciContext->p_config_params ) )
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
}
|
|
else
|
|
{
|
|
p_emulation_mgmt_info = (phHciNfc_EmulationMgmt_Info_t *)
|
|
psHciContext->p_emulation_mgmt_info ;
|
|
p_emulation_cfg = psHciContext->p_config_params;
|
|
switch(cfg_type)
|
|
{
|
|
case SMX_WI_CFG:
|
|
{
|
|
phHal_sSmartMX_Cfg_t *smx_config =
|
|
&p_emulation_cfg->config.smartMxCfg;
|
|
p_emulation_mgmt_info->smx_powerless =
|
|
(uint8_t)(FALSE != smx_config->lowPowerMode );
|
|
status = phHciNfc_WI_Configure_Default( psHciContext, pHwRef,
|
|
smx_config->enableEmulation );
|
|
break;
|
|
}
|
|
case UICC_SWP_CFG:
|
|
{
|
|
#ifdef SWP_CFG_SEQ
|
|
phHal_sUiccEmuCfg_t *uicc_config =
|
|
&p_emulation_cfg->config.uiccEmuCfg;
|
|
p_emulation_mgmt_info->uicc_powerless =
|
|
(uint8_t)(FALSE != uicc_config->lowPowerMode );
|
|
{
|
|
#ifdef SWP_EVENT_USAGE
|
|
status = phHciNfc_SWP_Configure_Mode( psHciContext, pHwRef,
|
|
((TRUE == uicc_config->enableUicc)? /* UICC_SWITCH_MODE_DEFAULT */
|
|
UICC_SWITCH_MODE_ON :UICC_SWITCH_MODE_OFF));
|
|
#else
|
|
status = phHciNfc_SWP_Configure_Default( psHciContext, pHwRef,
|
|
uicc_config->enableUicc );
|
|
#endif
|
|
}
|
|
#else
|
|
status = phHciNfc_SWP_Config_Sequence( psHciContext,
|
|
pHwRef, p_emulation_cfg);
|
|
#endif
|
|
break;
|
|
}
|
|
case SWP_EVT_CFG:
|
|
{
|
|
phHal_sUiccEmuCfg_t *uicc_config =
|
|
&p_emulation_cfg->config.uiccEmuCfg;
|
|
p_emulation_mgmt_info->uicc_powerless =
|
|
(uint8_t)(FALSE != uicc_config->lowPowerMode );
|
|
{
|
|
status = phHciNfc_SWP_Configure_Mode( psHciContext, pHwRef,
|
|
((TRUE == uicc_config->enableUicc)? /* UICC_SWITCH_MODE_DEFAULT */
|
|
UICC_SWITCH_MODE_ON :UICC_SWITCH_MODE_DEFAULT));
|
|
}
|
|
break;
|
|
}
|
|
#ifdef HOST_EMULATION
|
|
case NFC_CE_A_CFG:
|
|
{
|
|
phHal_sHostEmuCfg_A_t *host_ce_a_cfg =
|
|
&p_emulation_cfg->config.hostEmuCfg_A;
|
|
if(host_ce_a_cfg->enableEmulation == TRUE )
|
|
{
|
|
status = phHciNfc_CE_A_Initialise( psHciContext, pHwRef);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_CE_A_Release( psHciContext, pHwRef);
|
|
}
|
|
break;
|
|
}
|
|
case NFC_CE_B_CFG:
|
|
{
|
|
phHal_sHostEmuCfg_B_t *host_ce_b_cfg =
|
|
&p_emulation_cfg->config.hostEmuCfg_B;
|
|
if(host_ce_b_cfg->enableEmulation == TRUE )
|
|
{
|
|
status = phHciNfc_CE_B_Initialise( psHciContext, pHwRef);
|
|
}
|
|
else
|
|
{
|
|
status = phHciNfc_CE_B_Release( psHciContext, pHwRef);
|
|
}
|
|
break;
|
|
}
|
|
#endif
|
|
/* case INVALID_CFG:
|
|
case POLL_LOOP_CFG: */
|
|
default:
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_HCI_INFORMATION);
|
|
break;
|
|
}
|
|
|
|
} /* End of the Configuration Switch */
|
|
}
|
|
|
|
return status;
|
|
}
|
|
|
|
|
|
static
|
|
NFCSTATUS
|
|
phHciNfc_Recv_Uicc_Cmd (
|
|
void *psContext,
|
|
void *pHwRef,
|
|
uint8_t *pCmd,
|
|
#ifdef ONE_BYTE_LEN
|
|
uint8_t length
|
|
#else
|
|
uint16_t length
|
|
#endif
|
|
)
|
|
{
|
|
uint8_t pipe_id = (uint8_t) HCI_UNKNOWN_PIPE_ID;
|
|
uint8_t cmd = (uint8_t) HCP_MSG_INSTRUCTION_INVALID;
|
|
uint8_t response = (uint8_t) ANY_OK;
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
phHciNfc_sContext_t *psHciContext =
|
|
(phHciNfc_sContext_t *)psContext ;
|
|
phHciNfc_HCP_Packet_t *hcp_packet = NULL;
|
|
phHciNfc_HCP_Message_t *hcp_message = NULL;
|
|
phHciNfc_Pipe_Info_t *p_pipe_info = NULL;
|
|
phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info=NULL;
|
|
|
|
if( (NULL == psHciContext)
|
|
|| (NULL == pHwRef)
|
|
|| (HCP_HEADER_LEN > length )
|
|
)
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_PARAMETER);
|
|
}
|
|
else
|
|
{
|
|
hcp_packet = (phHciNfc_HCP_Packet_t *)pCmd;
|
|
hcp_message = &hcp_packet->msg.message;
|
|
p_emulation_mgmt_info = psHciContext->p_emulation_mgmt_info;
|
|
|
|
/* Get the Command instruction bits from the Message Header */
|
|
cmd = (uint8_t) GET_BITS8( hcp_message->msg_header,
|
|
HCP_MSG_INSTRUCTION_OFFSET, HCP_MSG_INSTRUCTION_LEN);
|
|
pipe_id = p_emulation_mgmt_info->uicc_id;
|
|
p_pipe_info = psHciContext->p_pipe_list[pipe_id];
|
|
|
|
switch( cmd )
|
|
{
|
|
/* These are Commands are sent from the UICC Controller */
|
|
case ANY_OPEN_PIPE:
|
|
{
|
|
p_emulation_mgmt_info->uicc_enable = TRUE ;
|
|
break;
|
|
}
|
|
case ANY_CLOSE_PIPE:
|
|
{
|
|
if(TRUE != p_emulation_mgmt_info->uicc_enable)
|
|
{
|
|
response = ANY_E_PIPE_NOT_OPENED;
|
|
/* status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_FAILED); */
|
|
}
|
|
else
|
|
{
|
|
p_emulation_mgmt_info->uicc_enable = FALSE;
|
|
}
|
|
break;
|
|
}
|
|
case ANY_SET_PARAMETER:
|
|
case ANY_GET_PARAMETER:
|
|
case PRO_HOST_REQUEST:
|
|
{
|
|
response = ANY_E_CMD_NOT_SUPPORTED;
|
|
/* status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_COMMAND_NOT_SUPPORTED);*/
|
|
break;
|
|
}
|
|
default:
|
|
{
|
|
response = ANY_E_NOK;
|
|
/* status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_INVALID_HCI_COMMAND); */
|
|
break;
|
|
}
|
|
}
|
|
hcp_packet = (phHciNfc_HCP_Packet_t *) psHciContext->send_buffer;
|
|
phHciNfc_Build_HCPFrame(hcp_packet,HCP_CHAINBIT_DEFAULT,
|
|
pipe_id, HCP_MSG_TYPE_RESPONSE, response );
|
|
psHciContext->tx_total = HCP_HEADER_LEN;
|
|
status = phHciNfc_Send_HCP( (void *)psHciContext, (void *)pHwRef );
|
|
|
|
p_pipe_info->recv_msg_type = HCP_MSG_TYPE_COMMAND;
|
|
p_pipe_info->sent_msg_type = HCP_MSG_TYPE_RESPONSE;
|
|
p_pipe_info->prev_msg = response ;
|
|
p_pipe_info->prev_status = status;
|
|
status = NFCSTATUS_SUCCESS;
|
|
|
|
}
|
|
return status;
|
|
}
|
|
|
|
static
|
|
NFCSTATUS
|
|
phHciNfc_Recv_Uicc_Event (
|
|
void *psContext,
|
|
void *pHwRef,
|
|
uint8_t *pEvent,
|
|
#ifdef ONE_BYTE_LEN
|
|
uint8_t length
|
|
#else
|
|
uint16_t length
|
|
#endif
|
|
)
|
|
{
|
|
uint8_t event = (uint8_t) HCP_MSG_INSTRUCTION_INVALID;
|
|
uint32_t i = 0;
|
|
NFCSTATUS status = NFCSTATUS_SUCCESS;
|
|
phHciNfc_sContext_t *psHciContext =
|
|
(phHciNfc_sContext_t *)psContext ;
|
|
phHciNfc_HCP_Packet_t *hcp_packet = NULL;
|
|
phHciNfc_HCP_Message_t *hcp_message = NULL;
|
|
phHal_sEventInfo_t event_info;
|
|
phHciNfc_EmulationMgmt_Info_t *p_emulation_mgmt_info =
|
|
psHciContext->p_emulation_mgmt_info ;
|
|
|
|
|
|
if( (NULL == p_emulation_mgmt_info)
|
|
|| ( TRUE != p_emulation_mgmt_info->uicc_enable)
|
|
)
|
|
{
|
|
status = PHNFCSTVAL(CID_NFC_HCI, NFCSTATUS_FEATURE_NOT_SUPPORTED);
|
|
}
|
|
else
|
|
{
|
|
hcp_packet = (phHciNfc_HCP_Packet_t *)pEvent;
|
|
hcp_message = &hcp_packet->msg.message;
|
|
|
|
/* Get the Event instruction bits from the Message Header */
|
|
event = (uint8_t) GET_BITS8( hcp_message->msg_header,
|
|
HCP_MSG_INSTRUCTION_OFFSET, HCP_MSG_INSTRUCTION_LEN);
|
|
event_info.eventHost = phHal_eUICCHost ;
|
|
event_info.eventSource = phHal_ePICC_DevType ;
|
|
|
|
switch( event )
|
|
{
|
|
case EVT_END_OF_TRANSACTION:
|
|
{
|
|
event_info.eventType = NFC_EVT_END_OF_TRANSACTION;
|
|
break;
|
|
}
|
|
case EVT_TRANSACTION:
|
|
{
|
|
if(length > HCP_HEADER_LEN + TRANSACTION_MIN_LEN)
|
|
{
|
|
event_info.eventType = NFC_EVT_TRANSACTION;
|
|
|
|
for(;i<(length-HCP_HEADER_LEN);)
|
|
{
|
|
switch (hcp_message->payload[i])
|
|
{
|
|
case TRANSACTION_AID:
|
|
{
|
|
/* AID LENGTH INDEX */
|
|
i++;
|
|
/* Fill the event_info.eventInfo.aid
|
|
* Structure with the Received Transaction AID.
|
|
*/
|
|
event_info.eventInfo.aid.length =
|
|
hcp_message->payload[i++];
|
|
(void) memcpy((void *)p_emulation_mgmt_info->uicc_aid,
|
|
&(hcp_message->payload[i]),
|
|
event_info.eventInfo.aid.length );
|
|
event_info.eventInfo.aid.buffer = (uint8_t *)
|
|
p_emulation_mgmt_info->uicc_aid;
|
|
i = i + event_info.eventInfo.aid.length;
|
|
break;
|
|
}
|
|
case TRANSACTION_PARAM:
|
|
{
|
|
/* Parameter Length Index */
|
|
i++;
|
|
/* Fill the event_info.eventInfo.param
|
|
* Structure with the Received Parameter.
|
|
*/
|
|
p_emulation_mgmt_info->uicc_param_len =
|
|
hcp_message->payload[i++];
|
|
(void) memcpy((void *)p_emulation_mgmt_info->uicc_param,
|
|
&(hcp_message->payload[i]),
|
|
p_emulation_mgmt_info->uicc_param_len );
|
|
event_info.eventInfo.uicc_info.param.length =
|
|
p_emulation_mgmt_info->uicc_param_len;
|
|
event_info.eventInfo.uicc_info.param.buffer = (uint8_t *)
|
|
p_emulation_mgmt_info->uicc_param;
|
|
i = i + event_info.eventInfo.uicc_info.param.length;
|
|
break;
|
|
}
|
|
default:
|
|
{
|
|
|
|
status = PHNFCSTVAL( CID_NFC_HCI,
|
|
NFCSTATUS_FEATURE_NOT_SUPPORTED );
|
|
i = length;
|
|
HCI_DEBUG("%s: Statement Should Not Occur \n",
|
|
"phHciNfc_Recv_Uicc_Event");
|
|
break;
|
|
}
|
|
} /* End of Transaction Switch */
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
case EVT_CONNECTIVITY:
|
|
{
|
|
event_info.eventType = NFC_EVT_CONNECTIVITY;
|
|
break;
|
|
}
|
|
case EVT_OPERATION_ENDED:
|
|
{
|
|
event_info.eventType = NFC_EVT_OPERATION_ENDED;
|
|
break;
|
|
}
|
|
default:
|
|
{
|
|
status = PHNFCSTVAL( CID_NFC_HCI, NFCSTATUS_FEATURE_NOT_SUPPORTED );
|
|
HCI_DEBUG("%s: Statement Should Not Occur \n","phHciNfc_Recv_Uicc_Event");
|
|
break;
|
|
}
|
|
}
|
|
if ( NFCSTATUS_SUCCESS == status )
|
|
{
|
|
phHciNfc_Notify_Event( psHciContext, pHwRef,
|
|
NFC_NOTIFY_EVENT, (void *)&event_info );
|
|
}
|
|
}
|
|
return status;
|
|
}
|
|
|
|
|