1 /* 2 * Copyright (C) 2010 NXP Semiconductors 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 /*! 17 * \file phHal4Nfc_Emulation.c 18 * \brief Hal4 Emulation source. 19 * 20 * Project: NFC-FRI 1.1 21 * 22 * $Date: Wed May 26 18:03:59 2010 $ 23 * $Author: ing07385 $ 24 * $Revision: 1.35 $ 25 * $Aliases: NFC_FRI1.1_WK1023_R35_1 $ 26 * 27 */ 28 29 /* ---------------------------Include files ------------------------------------*/ 30 #include <phHciNfc.h> 31 #include <phHal4Nfc.h> 32 #include <phHal4Nfc_Internal.h> 33 #include <phOsalNfc.h> 34 35 /* ------------------------------- Macros ------------------------------------*/ 36 37 /* Note : Macros required and used only in this module to be declared here*/ 38 39 40 /* --------------------Structures and enumerations --------------------------*/ 41 42 43 /*Event Notification handler for emulation*/ 44 void phHal4Nfc_HandleEmulationEvent( 45 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt, 46 void *pInfo 47 ) 48 { 49 phNfc_sNotificationInfo_t *psNotificationInfo = (phNfc_sNotificationInfo_t *) 50 pInfo; 51 phHal4Nfc_NotificationInfo_t uNotificationInfo = {NULL}; 52 /*Pass on Event notification info from Hci to Upper layer*/ 53 uNotificationInfo.psEventInfo = psNotificationInfo->info; 54 if(NULL != Hal4Ctxt->sUpperLayerInfo.pEventNotification) 55 { 56 Hal4Ctxt->sUpperLayerInfo.pEventNotification( 57 Hal4Ctxt->sUpperLayerInfo.EventNotificationCtxt, 58 psNotificationInfo->type, 59 uNotificationInfo, 60 NFCSTATUS_SUCCESS 61 ); 62 } 63 else/*No Event notification handler registered*/ 64 { 65 /*Use default handler to notify to the upper layer*/ 66 if(NULL != Hal4Ctxt->sUpperLayerInfo.pDefaultEventHandler) 67 { 68 Hal4Ctxt->sUpperLayerInfo.pDefaultEventHandler( 69 Hal4Ctxt->sUpperLayerInfo.DefaultListenerCtxt, 70 psNotificationInfo->type, 71 uNotificationInfo, 72 NFCSTATUS_SUCCESS 73 ); 74 } 75 } 76 return; 77 } 78 79 /* Switch mode from Virtual to Wired or Vice Versa for SMX. 80 */ 81 NFCSTATUS phHal4Nfc_Switch_SMX_Mode( 82 phHal_sHwReference_t *psHwReference, 83 phHal_eSmartMX_Mode_t smx_mode, 84 pphHal4Nfc_GenCallback_t pSwitchModecb, 85 void *pContext 86 ) 87 { 88 NFCSTATUS CfgStatus = NFCSTATUS_PENDING; 89 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt = NULL; 90 static phHal_sADD_Cfg_t sSmxCfg; 91 92 /*NULL checks*/ 93 if((NULL == psHwReference) || (NULL == pSwitchModecb)) 94 { 95 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1); 96 CfgStatus = PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_INVALID_PARAMETER); 97 } 98 /*Check Initialised state*/ 99 else if((NULL == psHwReference->hal_context) 100 || (((phHal4Nfc_Hal4Ctxt_t *) 101 psHwReference->hal_context)->Hal4CurrentState 102 < eHal4StateOpenAndReady) 103 || (((phHal4Nfc_Hal4Ctxt_t *) 104 psHwReference->hal_context)->Hal4NextState 105 == eHal4StateClosed)) 106 { 107 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1); 108 CfgStatus = PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_NOT_INITIALISED); 109 } 110 else 111 { 112 Hal4Ctxt = psHwReference->hal_context; 113 /*Previous POLL Config has not completed or device is connected, 114 do not allow poll*/ 115 if(Hal4Ctxt->Hal4NextState == eHal4StateConfiguring) 116 { 117 PHDBG_INFO("Hal4:Configuration in progress.Returning status Busy"); 118 CfgStatus= PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_BUSY); 119 } 120 else if(Hal4Ctxt->Hal4CurrentState >= eHal4StateOpenAndReady) 121 { 122 /**If config discovery has not been called prior to this ,allocate 123 ADD Context here*/ 124 if (NULL == Hal4Ctxt->psADDCtxtInfo) 125 { 126 Hal4Ctxt->psADDCtxtInfo= (pphHal4Nfc_ADDCtxtInfo_t) 127 phOsalNfc_GetMemory((uint32_t) 128 (sizeof(phHal4Nfc_ADDCtxtInfo_t))); 129 if(NULL != Hal4Ctxt->psADDCtxtInfo) 130 { 131 (void)memset(Hal4Ctxt->psADDCtxtInfo, 132 0,sizeof(phHal4Nfc_ADDCtxtInfo_t)); 133 } 134 } 135 if(NULL == Hal4Ctxt->psADDCtxtInfo) 136 { 137 phOsalNfc_RaiseException(phOsalNfc_e_NoMemory,0); 138 CfgStatus= PHNFCSTVAL(CID_NFC_HAL , 139 NFCSTATUS_INSUFFICIENT_RESOURCES); 140 } 141 else 142 { 143 /* Switch request to Wired mode */ 144 if(eSmartMx_Wired == smx_mode) 145 { 146 if(Hal4Ctxt->Hal4CurrentState 147 == eHal4StateTargetConnected) 148 { 149 PHDBG_INFO("Hal4:In Connected state.Returning Busy"); 150 CfgStatus= PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_BUSY); 151 } 152 /*It is Mandatory to register a listener before switching 153 to wired mode*/ 154 else if(NULL == 155 Hal4Ctxt->sUpperLayerInfo.pTagDiscoveryNotification) 156 { 157 CfgStatus = PHNFCSTVAL(CID_NFC_HAL , 158 NFCSTATUS_FAILED); 159 } 160 else 161 { 162 Hal4Ctxt->psADDCtxtInfo->nbr_of_devices = 0; 163 Hal4Ctxt->psADDCtxtInfo->smx_discovery = TRUE; 164 sSmxCfg.PollDevInfo.PollCfgInfo.EnableIso14443A = TRUE; 165 sSmxCfg.PollDevInfo.PollCfgInfo.DisableCardEmulation = TRUE; 166 /*Switch mode to wired*/ 167 CfgStatus = phHciNfc_Switch_SmxMode ( 168 Hal4Ctxt->psHciHandle, 169 psHwReference, 170 smx_mode, 171 &sSmxCfg 172 ); 173 } 174 } 175 else 176 { 177 Hal4Ctxt->psADDCtxtInfo->smx_discovery = FALSE; 178 /*Switch mode to virtual or off*/ 179 CfgStatus = phHciNfc_Switch_SmxMode ( 180 Hal4Ctxt->psHciHandle, 181 psHwReference, 182 smx_mode, 183 &(Hal4Ctxt->psADDCtxtInfo->sADDCfg) 184 ); 185 } 186 187 /* Change the State of the HAL only if Switch mode Returns 188 Success*/ 189 if ( NFCSTATUS_PENDING == CfgStatus ) 190 { 191 Hal4Ctxt->Hal4NextState = eHal4StateConfiguring; 192 Hal4Ctxt->sUpperLayerInfo.pConfigCallback 193 = pSwitchModecb; 194 } 195 } 196 } 197 else/*Return Status not initialised*/ 198 { 199 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1); 200 CfgStatus= PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_NOT_INITIALISED); 201 } 202 } 203 return CfgStatus; 204 } 205 206 207 208 /* Switch mode for Swp.*/ 209 NFCSTATUS phHal4Nfc_Switch_Swp_Mode( 210 phHal_sHwReference_t *psHwReference, 211 phHal_eSWP_Mode_t swp_mode, 212 pphHal4Nfc_GenCallback_t pSwitchModecb, 213 void *pContext 214 ) 215 { 216 NFCSTATUS CfgStatus = NFCSTATUS_PENDING; 217 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt = NULL; 218 /*NULL checks*/ 219 if(NULL == psHwReference 220 || NULL == pSwitchModecb 221 ) 222 { 223 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1); 224 CfgStatus = PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_INVALID_PARAMETER); 225 } 226 /*Check Initialised state*/ 227 else if((NULL == psHwReference->hal_context) 228 || (((phHal4Nfc_Hal4Ctxt_t *) 229 psHwReference->hal_context)->Hal4CurrentState 230 < eHal4StateOpenAndReady) 231 || (((phHal4Nfc_Hal4Ctxt_t *) 232 psHwReference->hal_context)->Hal4NextState 233 == eHal4StateClosed)) 234 { 235 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1); 236 CfgStatus = PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_NOT_INITIALISED); 237 } 238 else 239 { 240 Hal4Ctxt = psHwReference->hal_context; 241 /*Previous POLL CFG has not completed or device is connected, 242 do not allow poll*/ 243 if(Hal4Ctxt->Hal4NextState == eHal4StateConfiguring) 244 { 245 PHDBG_INFO("Hal4:Configuration in progress.Returning status Busy"); 246 CfgStatus= PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_BUSY); 247 } 248 else if(Hal4Ctxt->Hal4CurrentState >= eHal4StateOpenAndReady) 249 { 250 /**If config discovery has not been called prior to this ,allocate 251 ADD Context here*/ 252 if (NULL == Hal4Ctxt->psADDCtxtInfo) 253 { 254 Hal4Ctxt->psADDCtxtInfo= (pphHal4Nfc_ADDCtxtInfo_t) 255 phOsalNfc_GetMemory((uint32_t) 256 (sizeof(phHal4Nfc_ADDCtxtInfo_t))); 257 if(NULL != Hal4Ctxt->psADDCtxtInfo) 258 { 259 (void)memset(Hal4Ctxt->psADDCtxtInfo, 260 0,sizeof(phHal4Nfc_ADDCtxtInfo_t)); 261 } 262 } 263 if(NULL == Hal4Ctxt->psADDCtxtInfo) 264 { 265 phOsalNfc_RaiseException(phOsalNfc_e_NoMemory,0); 266 CfgStatus= PHNFCSTVAL(CID_NFC_HAL , 267 NFCSTATUS_INSUFFICIENT_RESOURCES); 268 } 269 else 270 { 271 /*Switch mode to On or off*/ 272 CfgStatus = phHciNfc_Switch_SwpMode( 273 Hal4Ctxt->psHciHandle, 274 psHwReference, 275 swp_mode 276 ); 277 278 /* Change the State of the HAL only if Switch mode Returns 279 Success*/ 280 if ( NFCSTATUS_PENDING == CfgStatus ) 281 { 282 Hal4Ctxt->Hal4NextState = eHal4StateConfiguring; 283 Hal4Ctxt->sUpperLayerInfo.pConfigCallback 284 = pSwitchModecb; 285 } 286 } 287 } 288 else/*Return Status not initialised*/ 289 { 290 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1); 291 CfgStatus= PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_NOT_INITIALISED); 292 } 293 } 294 return CfgStatus; 295 } 296 297 #ifdef FULL_HAL4_EMULATION_ENABLE 298 /* Switch Emulation mode ON or OFF.*/ 299 NFCSTATUS phHal4Nfc_Host_Emulation_Mode( 300 phHal_sHwReference_t *psHwReference, 301 phNfc_eModeType_t eModeType, 302 pphHal4Nfc_GenCallback_t pEmulationModecb, 303 void *pContext 304 ) 305 { 306 NFCSTATUS RetStatus = NFCSTATUS_PENDING; 307 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt = NULL; 308 /*NULL checks*/ 309 if(NULL == psHwReference 310 || NULL == pEmulationModecb 311 ) 312 { 313 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1); 314 RetStatus = PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_INVALID_PARAMETER); 315 } 316 /*Check Initialised state*/ 317 else if((NULL == psHwReference->hal_context) 318 || (((phHal4Nfc_Hal4Ctxt_t *) 319 psHwReference->hal_context)->Hal4CurrentState 320 < eHal4StateOpenAndReady) 321 || (((phHal4Nfc_Hal4Ctxt_t *) 322 psHwReference->hal_context)->Hal4NextState 323 == eHal4StateClosed)) 324 { 325 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1); 326 RetStatus = PHNFCSTVAL(CID_NFC_HAL , NFCSTATUS_NOT_INITIALISED); 327 } 328 else 329 { 330 331 } 332 return NFCSTATUS_PENDING; 333 } 334 #endif /*FULL_HAL4_EMULATION_ENABLE*/ 335