xref: /utopia/UTPA2-700.0.x/modules/dscmb/drv/nds/nds_sc.c (revision 53ee8cc121a030b8d368113ac3e966b4705770ef)
1*53ee8cc1Swenshuai.xi //<MStar Software>
2*53ee8cc1Swenshuai.xi //******************************************************************************
3*53ee8cc1Swenshuai.xi // MStar Software
4*53ee8cc1Swenshuai.xi // Copyright (c) 2010 - 2012 MStar Semiconductor, Inc. All rights reserved.
5*53ee8cc1Swenshuai.xi // All software, firmware and related documentation herein ("MStar Software") are
6*53ee8cc1Swenshuai.xi // intellectual property of MStar Semiconductor, Inc. ("MStar") and protected by
7*53ee8cc1Swenshuai.xi // law, including, but not limited to, copyright law and international treaties.
8*53ee8cc1Swenshuai.xi // Any use, modification, reproduction, retransmission, or republication of all
9*53ee8cc1Swenshuai.xi // or part of MStar Software is expressly prohibited, unless prior written
10*53ee8cc1Swenshuai.xi // permission has been granted by MStar.
11*53ee8cc1Swenshuai.xi //
12*53ee8cc1Swenshuai.xi // By accessing, browsing and/or using MStar Software, you acknowledge that you
13*53ee8cc1Swenshuai.xi // have read, understood, and agree, to be bound by below terms ("Terms") and to
14*53ee8cc1Swenshuai.xi // comply with all applicable laws and regulations:
15*53ee8cc1Swenshuai.xi //
16*53ee8cc1Swenshuai.xi // 1. MStar shall retain any and all right, ownership and interest to MStar
17*53ee8cc1Swenshuai.xi //    Software and any modification/derivatives thereof.
18*53ee8cc1Swenshuai.xi //    No right, ownership, or interest to MStar Software and any
19*53ee8cc1Swenshuai.xi //    modification/derivatives thereof is transferred to you under Terms.
20*53ee8cc1Swenshuai.xi //
21*53ee8cc1Swenshuai.xi // 2. You understand that MStar Software might include, incorporate or be
22*53ee8cc1Swenshuai.xi //    supplied together with third party`s software and the use of MStar
23*53ee8cc1Swenshuai.xi //    Software may require additional licenses from third parties.
24*53ee8cc1Swenshuai.xi //    Therefore, you hereby agree it is your sole responsibility to separately
25*53ee8cc1Swenshuai.xi //    obtain any and all third party right and license necessary for your use of
26*53ee8cc1Swenshuai.xi //    such third party`s software.
27*53ee8cc1Swenshuai.xi //
28*53ee8cc1Swenshuai.xi // 3. MStar Software and any modification/derivatives thereof shall be deemed as
29*53ee8cc1Swenshuai.xi //    MStar`s confidential information and you agree to keep MStar`s
30*53ee8cc1Swenshuai.xi //    confidential information in strictest confidence and not disclose to any
31*53ee8cc1Swenshuai.xi //    third party.
32*53ee8cc1Swenshuai.xi //
33*53ee8cc1Swenshuai.xi // 4. MStar Software is provided on an "AS IS" basis without warranties of any
34*53ee8cc1Swenshuai.xi //    kind. Any warranties are hereby expressly disclaimed by MStar, including
35*53ee8cc1Swenshuai.xi //    without limitation, any warranties of merchantability, non-infringement of
36*53ee8cc1Swenshuai.xi //    intellectual property rights, fitness for a particular purpose, error free
37*53ee8cc1Swenshuai.xi //    and in conformity with any international standard.  You agree to waive any
38*53ee8cc1Swenshuai.xi //    claim against MStar for any loss, damage, cost or expense that you may
39*53ee8cc1Swenshuai.xi //    incur related to your use of MStar Software.
40*53ee8cc1Swenshuai.xi //    In no event shall MStar be liable for any direct, indirect, incidental or
41*53ee8cc1Swenshuai.xi //    consequential damages, including without limitation, lost of profit or
42*53ee8cc1Swenshuai.xi //    revenues, lost or damage of data, and unauthorized system use.
43*53ee8cc1Swenshuai.xi //    You agree that this Section 4 shall still apply without being affected
44*53ee8cc1Swenshuai.xi //    even if MStar Software has been modified by MStar in accordance with your
45*53ee8cc1Swenshuai.xi //    request or instruction for your use, except otherwise agreed by both
46*53ee8cc1Swenshuai.xi //    parties in writing.
47*53ee8cc1Swenshuai.xi //
48*53ee8cc1Swenshuai.xi // 5. If requested, MStar may from time to time provide technical supports or
49*53ee8cc1Swenshuai.xi //    services in relation with MStar Software to you for your use of
50*53ee8cc1Swenshuai.xi //    MStar Software in conjunction with your or your customer`s product
51*53ee8cc1Swenshuai.xi //    ("Services").
52*53ee8cc1Swenshuai.xi //    You understand and agree that, except otherwise agreed by both parties in
53*53ee8cc1Swenshuai.xi //    writing, Services are provided on an "AS IS" basis and the warranty
54*53ee8cc1Swenshuai.xi //    disclaimer set forth in Section 4 above shall apply.
55*53ee8cc1Swenshuai.xi //
56*53ee8cc1Swenshuai.xi // 6. Nothing contained herein shall be construed as by implication, estoppels
57*53ee8cc1Swenshuai.xi //    or otherwise:
58*53ee8cc1Swenshuai.xi //    (a) conferring any license or right to use MStar name, trademark, service
59*53ee8cc1Swenshuai.xi //        mark, symbol or any other identification;
60*53ee8cc1Swenshuai.xi //    (b) obligating MStar or any of its affiliates to furnish any person,
61*53ee8cc1Swenshuai.xi //        including without limitation, you and your customers, any assistance
62*53ee8cc1Swenshuai.xi //        of any kind whatsoever, or any information; or
63*53ee8cc1Swenshuai.xi //    (c) conferring any license or right under any intellectual property right.
64*53ee8cc1Swenshuai.xi //
65*53ee8cc1Swenshuai.xi // 7. These terms shall be governed by and construed in accordance with the laws
66*53ee8cc1Swenshuai.xi //    of Taiwan, R.O.C., excluding its conflict of law rules.
67*53ee8cc1Swenshuai.xi //    Any and all dispute arising out hereof or related hereto shall be finally
68*53ee8cc1Swenshuai.xi //    settled by arbitration referred to the Chinese Arbitration Association,
69*53ee8cc1Swenshuai.xi //    Taipei in accordance with the ROC Arbitration Law and the Arbitration
70*53ee8cc1Swenshuai.xi //    Rules of the Association by three (3) arbitrators appointed in accordance
71*53ee8cc1Swenshuai.xi //    with the said Rules.
72*53ee8cc1Swenshuai.xi //    The place of arbitration shall be in Taipei, Taiwan and the language shall
73*53ee8cc1Swenshuai.xi //    be English.
74*53ee8cc1Swenshuai.xi //    The arbitration award shall be final and binding to both parties.
75*53ee8cc1Swenshuai.xi //
76*53ee8cc1Swenshuai.xi //******************************************************************************
77*53ee8cc1Swenshuai.xi //<MStar Software>
78*53ee8cc1Swenshuai.xi ////////////////////////////////////////////////////////////////////////////////
79*53ee8cc1Swenshuai.xi //
80*53ee8cc1Swenshuai.xi // Copyright (c) 2008-2009 MStar Semiconductor, Inc.
81*53ee8cc1Swenshuai.xi // All rights reserved.
82*53ee8cc1Swenshuai.xi //
83*53ee8cc1Swenshuai.xi // Unless otherwise stipulated in writing, any and all information contained
84*53ee8cc1Swenshuai.xi // herein regardless in any format shall remain the sole proprietary of
85*53ee8cc1Swenshuai.xi // MStar Semiconductor Inc. and be kept in strict confidence
86*53ee8cc1Swenshuai.xi // ("MStar Confidential Information") by the recipient.
87*53ee8cc1Swenshuai.xi // Any unauthorized act including without limitation unauthorized disclosure,
88*53ee8cc1Swenshuai.xi // copying, use, reproduction, sale, distribution, modification, disassembling,
89*53ee8cc1Swenshuai.xi // reverse engineering and compiling of the contents of MStar Confidential
90*53ee8cc1Swenshuai.xi // Information is unlawful and strictly prohibited. MStar hereby reserves the
91*53ee8cc1Swenshuai.xi // rights to any and all damages, losses, costs and expenses resulting therefrom.
92*53ee8cc1Swenshuai.xi //
93*53ee8cc1Swenshuai.xi ////////////////////////////////////////////////////////////////////////////////
94*53ee8cc1Swenshuai.xi 
95*53ee8cc1Swenshuai.xi ///////////////////////////////////////////////////////////////////////////////////////////////////
96*53ee8cc1Swenshuai.xi ///
97*53ee8cc1Swenshuai.xi /// file    drvNDS.c
98*53ee8cc1Swenshuai.xi /// @brief  NDS Driver Interface
99*53ee8cc1Swenshuai.xi /// @author MStar Semiconductor Inc.
100*53ee8cc1Swenshuai.xi ///////////////////////////////////////////////////////////////////////////////////////////////////
101*53ee8cc1Swenshuai.xi 
102*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
103*53ee8cc1Swenshuai.xi //  Include Files
104*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
105*53ee8cc1Swenshuai.xi #include "MsCommon.h"
106*53ee8cc1Swenshuai.xi 
107*53ee8cc1Swenshuai.xi #include "asmCPU.h"
108*53ee8cc1Swenshuai.xi #include "regNDS.h"
109*53ee8cc1Swenshuai.xi #include "drvNDS.h"
110*53ee8cc1Swenshuai.xi #include "halNDS.h"
111*53ee8cc1Swenshuai.xi 
112*53ee8cc1Swenshuai.xi #include "ddiNDS_HDI.h"
113*53ee8cc1Swenshuai.xi 
114*53ee8cc1Swenshuai.xi #include "nds.h"
115*53ee8cc1Swenshuai.xi 
116*53ee8cc1Swenshuai.xi #ifdef MSOS_TYPE_LINUX_KERNEL
117*53ee8cc1Swenshuai.xi #include <linux/delay.h>
118*53ee8cc1Swenshuai.xi #endif
119*53ee8cc1Swenshuai.xi 
120*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
121*53ee8cc1Swenshuai.xi //  Driver Compiler Options
122*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
123*53ee8cc1Swenshuai.xi 
124*53ee8cc1Swenshuai.xi 
125*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
126*53ee8cc1Swenshuai.xi //  Local Defines
127*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
128*53ee8cc1Swenshuai.xi #define NDS_SC_FIFO_SIZE                (256 + 64)                      // Rx/Tx fifo size
129*53ee8cc1Swenshuai.xi #define NDS_SC_RX_REQ_MAX               32
130*53ee8cc1Swenshuai.xi #define NDS_SC_RX_TIMEOUT               1500//1600// 1000ms
131*53ee8cc1Swenshuai.xi #define NDS_SC_VCC_DELAY                10
132*53ee8cc1Swenshuai.xi 
133*53ee8cc1Swenshuai.xi #define NDS_SC_CHK_TIMER                500
134*53ee8cc1Swenshuai.xi 
135*53ee8cc1Swenshuai.xi #define NDS_SC_EVENT_CARD               0x00000001      // 0x00000010-0x00000019
136*53ee8cc1Swenshuai.xi #define NDS_SC_EVENT_RX                 0x00000010
137*53ee8cc1Swenshuai.xi #define NDS_SC_EVENT_RX_OVERFLOW        0x00000020
138*53ee8cc1Swenshuai.xi #define NDS_SC_EVENT_RX_ERROR           0x00000040
139*53ee8cc1Swenshuai.xi 
140*53ee8cc1Swenshuai.xi #define NDS_SC_OS_AttachInterrupt(isr)  MsOS_AttachInterrupt(NDS_INT_UART_CA, isr)
141*53ee8cc1Swenshuai.xi #define NDS_SC_OS_EnableInterrupt()     MsOS_EnableInterrupt(NDS_INT_UART_CA);
142*53ee8cc1Swenshuai.xi #define NDS_SC_OS_DisableInterrupt()    MsOS_DisableInterrupt(NDS_INT_UART_CA);
143*53ee8cc1Swenshuai.xi #define NDS_SC_OS_DetachInterrupt()     MsOS_DetachInterrupt(NDS_INT_UART_CA);
144*53ee8cc1Swenshuai.xi 
145*53ee8cc1Swenshuai.xi #define NDS_SC_LOCK()                   { MsOS_ObtainMutex(_nds_sc_dev.s32Mutex, MSOS_WAIT_FOREVER); }
146*53ee8cc1Swenshuai.xi #define NDS_SC_UNLOCK()                 { MsOS_ReleaseMutex(_nds_sc_dev.s32Mutex); }
147*53ee8cc1Swenshuai.xi #define NDS_SC_ENTRY()                  { }
148*53ee8cc1Swenshuai.xi #define NDS_SC_RETURN(_ret)             { return _ret; }
149*53ee8cc1Swenshuai.xi #define NDS_SC_RXQ_LOCK()                { MsOS_ObtainMutex(_nds_sc_dev.s32MutexIdRx, MSOS_WAIT_FOREVER); }
150*53ee8cc1Swenshuai.xi #define NDS_SC_RXQ_UNLOCK()              { MsOS_ReleaseMutex(_nds_sc_dev.s32MutexIdRx); }
151*53ee8cc1Swenshuai.xi 
152*53ee8cc1Swenshuai.xi #define SC_RX_TIMEOUT_ENABLE            0
153*53ee8cc1Swenshuai.xi #define SC_FLOWCTRL_ENABLE              1
154*53ee8cc1Swenshuai.xi 
155*53ee8cc1Swenshuai.xi #if 1 //defined(MS_DEBUG)
156*53ee8cc1Swenshuai.xi #define NDS_SC_DBG(_fmt, _args...)      printf(_fmt, ##_args)
157*53ee8cc1Swenshuai.xi #else
158*53ee8cc1Swenshuai.xi #define NDS_SC_DBG(_fmt, _args...)      { }
159*53ee8cc1Swenshuai.xi #endif
160*53ee8cc1Swenshuai.xi 
161*53ee8cc1Swenshuai.xi 
162*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
163*53ee8cc1Swenshuai.xi //  Local Structurs
164*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
165*53ee8cc1Swenshuai.xi typedef struct _NDS_SC_Dev
166*53ee8cc1Swenshuai.xi {
167*53ee8cc1Swenshuai.xi     // device info
168*53ee8cc1Swenshuai.xi 
169*53ee8cc1Swenshuai.xi     // device identification
170*53ee8cc1Swenshuai.xi 
171*53ee8cc1Swenshuai.xi     // device context
172*53ee8cc1Swenshuai.xi     MS_BOOL                         bOpened;
173*53ee8cc1Swenshuai.xi     MS_BOOL                         bCardRdy;                           // since Vcc is controlled by user
174*53ee8cc1Swenshuai.xi     MS_BOOL                         bAborting;
175*53ee8cc1Swenshuai.xi 
176*53ee8cc1Swenshuai.xi     MS_U8                           Rxfifo[NDS_SC_FIFO_SIZE];
177*53ee8cc1Swenshuai.xi     MS_U8                           Txfifo[NDS_SC_FIFO_SIZE];
178*53ee8cc1Swenshuai.xi     MS_U16                          Rxfifo_r;
179*53ee8cc1Swenshuai.xi     MS_U16                          Rxfifo_w;
180*53ee8cc1Swenshuai.xi     MS_U16                          Txfifo_r;
181*53ee8cc1Swenshuai.xi     MS_U16                          Txfifo_w;
182*53ee8cc1Swenshuai.xi 
183*53ee8cc1Swenshuai.xi     // system specified
184*53ee8cc1Swenshuai.xi     MS_S32                          s32DevEventId;
185*53ee8cc1Swenshuai.xi     MS_S32                          s32TaskId;
186*53ee8cc1Swenshuai.xi     MS_S32                          s32Mutex;
187*53ee8cc1Swenshuai.xi     MS_S32                          s32MutexIdRx;
188*53ee8cc1Swenshuai.xi 
189*53ee8cc1Swenshuai.xi     NDS_SC_Clk                      clk;
190*53ee8cc1Swenshuai.xi     NDS_SC_Param                    param;
191*53ee8cc1Swenshuai.xi 
192*53ee8cc1Swenshuai.xi } NDS_SC_Dev;
193*53ee8cc1Swenshuai.xi 
194*53ee8cc1Swenshuai.xi 
195*53ee8cc1Swenshuai.xi typedef struct _NDS_SC_Rx
196*53ee8cc1Swenshuai.xi {
197*53ee8cc1Swenshuai.xi     // system specified
198*53ee8cc1Swenshuai.xi     MS_BOOL                         bUse;
199*53ee8cc1Swenshuai.xi     MS_S32                          s32Len;
200*53ee8cc1Swenshuai.xi     MS_S32                          s32Num;
201*53ee8cc1Swenshuai.xi     MS_BOOL                         bNullFilter;
202*53ee8cc1Swenshuai.xi     MS_BOOL                         bFlowCtrl;
203*53ee8cc1Swenshuai.xi     MS_U8                           *pAddr;
204*53ee8cc1Swenshuai.xi     MS_U32                          u32Timeout;
205*53ee8cc1Swenshuai.xi } NDS_SC_Rx;
206*53ee8cc1Swenshuai.xi 
207*53ee8cc1Swenshuai.xi 
208*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
209*53ee8cc1Swenshuai.xi //  Global Variables
210*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
211*53ee8cc1Swenshuai.xi 
212*53ee8cc1Swenshuai.xi #if 1 //[VERIFIER]
213*53ee8cc1Swenshuai.xi //TODO: remove it
214*53ee8cc1Swenshuai.xi extern MS_BOOL bEmmOverflow;
215*53ee8cc1Swenshuai.xi extern MS_U32 emm_overflow_time;
216*53ee8cc1Swenshuai.xi #endif
217*53ee8cc1Swenshuai.xi 
218*53ee8cc1Swenshuai.xi 
219*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
220*53ee8cc1Swenshuai.xi //  Local Variables
221*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
222*53ee8cc1Swenshuai.xi static MS_U32                       _nds_sc_stack[4096/4];
223*53ee8cc1Swenshuai.xi 
224*53ee8cc1Swenshuai.xi // Rx Request Queue
225*53ee8cc1Swenshuai.xi static NDS_SC_Rx                    _nds_sc_rxq[NDS_SC_RX_REQ_MAX];
226*53ee8cc1Swenshuai.xi static MS_U8                        _nds_sc_rxq_read        = 0;    // User read queue (HDI)
227*53ee8cc1Swenshuai.xi static MS_U8                        _nds_sc_rxq_cur         = 0;    // Current active queue (ISR)
228*53ee8cc1Swenshuai.xi static MS_U8                        _nds_sc_rxq_next        = 0;    // The next non-used queue for request (HDI)
229*53ee8cc1Swenshuai.xi 
230*53ee8cc1Swenshuai.xi static NDS_SC_Dev                   _nds_sc_dev = {
231*53ee8cc1Swenshuai.xi                                         .bOpened            = FALSE,
232*53ee8cc1Swenshuai.xi                                         .bCardRdy           = FALSE,
233*53ee8cc1Swenshuai.xi                                         .bAborting          = FALSE,
234*53ee8cc1Swenshuai.xi                                         .clk                = E_NDS_SC_CLK_27M_D6,
235*53ee8cc1Swenshuai.xi                                         .param.cbSetVcc     = NULL,
236*53ee8cc1Swenshuai.xi                                         .param.cbEvent      = NULL,
237*53ee8cc1Swenshuai.xi                                         .param.bCommDump    = FALSE,
238*53ee8cc1Swenshuai.xi                                     };
239*53ee8cc1Swenshuai.xi 
240*53ee8cc1Swenshuai.xi static MS_BOOL                      _nds_sc_cardin          = FALSE;
241*53ee8cc1Swenshuai.xi static MS_BOOL                      _nds_sc_last_cardin     = 2;    // other than TRUE / FALSE
242*53ee8cc1Swenshuai.xi static MS_U16                       _nds_sc_rx_cnt          = 0;    // for flow control
243*53ee8cc1Swenshuai.xi static MS_U8                        _nds_sc_reg_ctrl        = 0;
244*53ee8cc1Swenshuai.xi 
245*53ee8cc1Swenshuai.xi 
246*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
247*53ee8cc1Swenshuai.xi //  Debug Functions
248*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
249*53ee8cc1Swenshuai.xi 
250*53ee8cc1Swenshuai.xi 
251*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
252*53ee8cc1Swenshuai.xi //  Local Functions
253*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
254*53ee8cc1Swenshuai.xi 
NDS_SC_DBG_PrintData(MS_U8 * pu8Data,MS_U16 u16DataLen)255*53ee8cc1Swenshuai.xi void NDS_SC_DBG_PrintData(MS_U8 *pu8Data, MS_U16 u16DataLen)
256*53ee8cc1Swenshuai.xi {
257*53ee8cc1Swenshuai.xi     int                 i;
258*53ee8cc1Swenshuai.xi     //printf("(%d)>>", u16DataLen);
259*53ee8cc1Swenshuai.xi     for (i = 0; i < u16DataLen; i++)
260*53ee8cc1Swenshuai.xi     {
261*53ee8cc1Swenshuai.xi         if ((i % 16) == 0)
262*53ee8cc1Swenshuai.xi         {
263*53ee8cc1Swenshuai.xi             NDS_SC_DBG("\n    ");
264*53ee8cc1Swenshuai.xi         }
265*53ee8cc1Swenshuai.xi         NDS_SC_DBG(" %02X ", pu8Data[i]);
266*53ee8cc1Swenshuai.xi     }
267*53ee8cc1Swenshuai.xi     NDS_SC_DBG("\n");
268*53ee8cc1Swenshuai.xi }
269*53ee8cc1Swenshuai.xi 
270*53ee8cc1Swenshuai.xi 
_NDS_SC_SET_CTRL(MS_U8 bits)271*53ee8cc1Swenshuai.xi void _NDS_SC_SET_CTRL(MS_U8 bits)
272*53ee8cc1Swenshuai.xi {
273*53ee8cc1Swenshuai.xi //try
274*53ee8cc1Swenshuai.xi     MS_U8 dbg;
275*53ee8cc1Swenshuai.xi     dbg = _nds_sc_reg_ctrl | bits;
276*53ee8cc1Swenshuai.xi     MS_U32 old_int = MsOS_DisableAllInterrupts();
277*53ee8cc1Swenshuai.xi //try
278*53ee8cc1Swenshuai.xi 
279*53ee8cc1Swenshuai.xi     NDS_SC_OS_DisableInterrupt();
280*53ee8cc1Swenshuai.xi     NDS_SC_LOCK();
281*53ee8cc1Swenshuai.xi     _nds_sc_reg_ctrl |= bits;
282*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
283*53ee8cc1Swenshuai.xi     NDS_SC_UNLOCK();
284*53ee8cc1Swenshuai.xi     NDS_SC_OS_EnableInterrupt();
285*53ee8cc1Swenshuai.xi 
286*53ee8cc1Swenshuai.xi //try
287*53ee8cc1Swenshuai.xi     old_int = MsOS_RestoreAllInterrupts(old_int);
288*53ee8cc1Swenshuai.xi     if (dbg != _nds_sc_reg_ctrl)
289*53ee8cc1Swenshuai.xi     {
290*53ee8cc1Swenshuai.xi         while (1);
291*53ee8cc1Swenshuai.xi     }
292*53ee8cc1Swenshuai.xi //try
293*53ee8cc1Swenshuai.xi }
294*53ee8cc1Swenshuai.xi 
_NDS_SC_CLR_CTRL(MS_U8 bits)295*53ee8cc1Swenshuai.xi void _NDS_SC_CLR_CTRL(MS_U8 bits)
296*53ee8cc1Swenshuai.xi {
297*53ee8cc1Swenshuai.xi //try
298*53ee8cc1Swenshuai.xi     MS_U8 dbg;
299*53ee8cc1Swenshuai.xi     dbg = _nds_sc_reg_ctrl & ~bits;
300*53ee8cc1Swenshuai.xi     MS_U32 old_int = MsOS_DisableAllInterrupts();
301*53ee8cc1Swenshuai.xi //try
302*53ee8cc1Swenshuai.xi 
303*53ee8cc1Swenshuai.xi     NDS_SC_OS_DisableInterrupt();
304*53ee8cc1Swenshuai.xi     NDS_SC_LOCK();
305*53ee8cc1Swenshuai.xi     _nds_sc_reg_ctrl &= ~(bits);
306*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
307*53ee8cc1Swenshuai.xi     NDS_SC_UNLOCK();
308*53ee8cc1Swenshuai.xi     NDS_SC_OS_EnableInterrupt();
309*53ee8cc1Swenshuai.xi 
310*53ee8cc1Swenshuai.xi //tt
311*53ee8cc1Swenshuai.xi     old_int = MsOS_RestoreAllInterrupts(old_int);
312*53ee8cc1Swenshuai.xi     if (dbg != _nds_sc_reg_ctrl)
313*53ee8cc1Swenshuai.xi     {
314*53ee8cc1Swenshuai.xi         while (1);
315*53ee8cc1Swenshuai.xi     }
316*53ee8cc1Swenshuai.xi //tt
317*53ee8cc1Swenshuai.xi }
318*53ee8cc1Swenshuai.xi 
319*53ee8cc1Swenshuai.xi 
_NDS_SC_ResetRxIdx(void)320*53ee8cc1Swenshuai.xi static void _NDS_SC_ResetRxIdx(void)
321*53ee8cc1Swenshuai.xi {
322*53ee8cc1Swenshuai.xi     MS_U32              i = 0;
323*53ee8cc1Swenshuai.xi     for (i = 0; i < NDS_SC_RX_REQ_MAX; i++)
324*53ee8cc1Swenshuai.xi     {
325*53ee8cc1Swenshuai.xi         _nds_sc_rxq[i].bUse = FALSE;
326*53ee8cc1Swenshuai.xi         //_smart_rx[i].pAddr = NULL;
327*53ee8cc1Swenshuai.xi         _nds_sc_rxq[i].s32Num = 0;
328*53ee8cc1Swenshuai.xi         _nds_sc_rxq[i].u32Timeout = 0;
329*53ee8cc1Swenshuai.xi         _nds_sc_rxq[i].bFlowCtrl = 0;
330*53ee8cc1Swenshuai.xi         _nds_sc_rxq[i].bNullFilter = 0;
331*53ee8cc1Swenshuai.xi         _nds_sc_rxq[i].s32Len = 0;
332*53ee8cc1Swenshuai.xi     }
333*53ee8cc1Swenshuai.xi     _nds_sc_rxq_read     = 0;
334*53ee8cc1Swenshuai.xi     _nds_sc_rxq_cur      = 0;
335*53ee8cc1Swenshuai.xi     _nds_sc_rxq_next     = 0;
336*53ee8cc1Swenshuai.xi     _nds_sc_rx_cnt  = 0;
337*53ee8cc1Swenshuai.xi }
338*53ee8cc1Swenshuai.xi 
339*53ee8cc1Swenshuai.xi 
_NDS_SC_Isr(InterruptNum eIntNum)340*53ee8cc1Swenshuai.xi static void _NDS_SC_Isr(InterruptNum eIntNum)
341*53ee8cc1Swenshuai.xi {
342*53ee8cc1Swenshuai.xi     MS_U32              events = 0;
343*53ee8cc1Swenshuai.xi     MS_U16              u16RegRead = 0, u16RegCtrl = 0;
344*53ee8cc1Swenshuai.xi     MS_U8               u8Char;
345*53ee8cc1Swenshuai.xi 
346*53ee8cc1Swenshuai.xi //    NDS_SC_OS_DisableInterrupt(); // @FIXME: why?
347*53ee8cc1Swenshuai.xi 
348*53ee8cc1Swenshuai.xi     // Recieve all data in fifo
349*53ee8cc1Swenshuai.xi     u16RegRead = CAM_REG(REG_CAM_UART_INT);
350*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_INT) = (CAM_UART_INT_MASK_RESET | u16RegRead); // clear interrupt
351*53ee8cc1Swenshuai.xi 
352*53ee8cc1Swenshuai.xi     if (u16RegRead & CAM_UART_INT_CD)
353*53ee8cc1Swenshuai.xi     {
354*53ee8cc1Swenshuai.xi         _nds_sc_dev.bCardRdy = FALSE;
355*53ee8cc1Swenshuai.xi 
356*53ee8cc1Swenshuai.xi         // [NOTE] ICAM2 certification needs the Vcc to be OFF after removal.
357*53ee8cc1Swenshuai.xi         _nds_sc_reg_ctrl &= ~(CAM_UART_CTRL_VCC_ACTIVE);
358*53ee8cc1Swenshuai.xi         CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
359*53ee8cc1Swenshuai.xi 
360*53ee8cc1Swenshuai.xi         u16RegRead &= ~(CAM_UART_INT_CD);
361*53ee8cc1Swenshuai.xi         MsOS_SetEvent(_nds_sc_dev.s32DevEventId, NDS_SC_EVENT_CARD);// Notify ISR event
362*53ee8cc1Swenshuai.xi     }
363*53ee8cc1Swenshuai.xi 
364*53ee8cc1Swenshuai.xi     // recv ALL bytes if avaiable
365*53ee8cc1Swenshuai.xi     if (u16RegRead & (CAM_UART_INT_RX | CAM_UART_INT_RX_OVERFLOW | CAM_UART_INT_PARITY_ERR_RX))
366*53ee8cc1Swenshuai.xi     {
367*53ee8cc1Swenshuai.xi         if (u16RegRead & CAM_UART_INT_RX)
368*53ee8cc1Swenshuai.xi         {
369*53ee8cc1Swenshuai.xi             if (u16RegRead & CAM_UART_INT_RX_OVERFLOW)
370*53ee8cc1Swenshuai.xi             {
371*53ee8cc1Swenshuai.xi                 events |= NDS_SC_EVENT_RX_OVERFLOW;
372*53ee8cc1Swenshuai.xi             }
373*53ee8cc1Swenshuai.xi             else if (u16RegRead & CAM_UART_INT_PARITY_ERR_RX)
374*53ee8cc1Swenshuai.xi             {
375*53ee8cc1Swenshuai.xi                 events |= NDS_SC_EVENT_RX_ERROR;
376*53ee8cc1Swenshuai.xi             }
377*53ee8cc1Swenshuai.xi 
378*53ee8cc1Swenshuai.xi             while (1) // read all Rx data received regardless of any software status, e.g. bCardIn
379*53ee8cc1Swenshuai.xi             {
380*53ee8cc1Swenshuai.xi                 u16RegCtrl = CAM_REG(REG_CAM_UART_CTRL);
381*53ee8cc1Swenshuai.xi                 if ((u16RegCtrl & CAM_UART_STAT_RX_RDY) /* && (_nds_sc_dev.bCardIn)*/)
382*53ee8cc1Swenshuai.xi                 {
383*53ee8cc1Swenshuai.xi                     MS_U32  u32tmp;
384*53ee8cc1Swenshuai.xi 
385*53ee8cc1Swenshuai.xi                     u8Char = CAM_REG(REG_CAM_UART_DATA);
386*53ee8cc1Swenshuai.xi                     _nds_sc_dev.Rxfifo[_nds_sc_dev.Rxfifo_w] = u8Char;
387*53ee8cc1Swenshuai.xi                     u32tmp = _nds_sc_dev.Rxfifo_w + 1;
388*53ee8cc1Swenshuai.xi #if 0
389*53ee8cc1Swenshuai.xi                     if ( (NDS_SC_FIFO_SIZE == u32tmp) && (_nds_sc_dev.Rxfifo_r != 0))
390*53ee8cc1Swenshuai.xi                     {
391*53ee8cc1Swenshuai.xi                         // Not overflow but wrap
392*53ee8cc1Swenshuai.xi                         _nds_sc_dev.Rxfifo_w = 0;
393*53ee8cc1Swenshuai.xi                     }
394*53ee8cc1Swenshuai.xi                     else if ( u32tmp != _nds_sc_dev.Rxfifo_r )
395*53ee8cc1Swenshuai.xi                     {
396*53ee8cc1Swenshuai.xi                         // Not overflow
397*53ee8cc1Swenshuai.xi                         _nds_sc_dev.Rxfifo_w = u32tmp;
398*53ee8cc1Swenshuai.xi                     }
399*53ee8cc1Swenshuai.xi                     else
400*53ee8cc1Swenshuai.xi                     {
401*53ee8cc1Swenshuai.xi                         break; //overflow
402*53ee8cc1Swenshuai.xi                         //_NDS_ASSERT_();
403*53ee8cc1Swenshuai.xi                     }
404*53ee8cc1Swenshuai.xi #else
405*53ee8cc1Swenshuai.xi                     if (u32tmp >= NDS_SC_FIFO_SIZE)
406*53ee8cc1Swenshuai.xi                     {
407*53ee8cc1Swenshuai.xi                         u32tmp = 0;
408*53ee8cc1Swenshuai.xi                     }
409*53ee8cc1Swenshuai.xi 
410*53ee8cc1Swenshuai.xi                     if (u32tmp != _nds_sc_dev.Rxfifo_r)
411*53ee8cc1Swenshuai.xi                     {
412*53ee8cc1Swenshuai.xi                         // Not overflow
413*53ee8cc1Swenshuai.xi                         _nds_sc_dev.Rxfifo_w = u32tmp;
414*53ee8cc1Swenshuai.xi                     }
415*53ee8cc1Swenshuai.xi                     else
416*53ee8cc1Swenshuai.xi                     {
417*53ee8cc1Swenshuai.xi                         MAsm_CPU_SwDbgBp();
418*53ee8cc1Swenshuai.xi                         break; // overflow
419*53ee8cc1Swenshuai.xi                     }
420*53ee8cc1Swenshuai.xi #endif
421*53ee8cc1Swenshuai.xi 
422*53ee8cc1Swenshuai.xi                     _nds_sc_rx_cnt--; // _nds_sc_rx_cnt > 0
423*53ee8cc1Swenshuai.xi 
424*53ee8cc1Swenshuai.xi #if SC_FLOWCTRL_ENABLE
425*53ee8cc1Swenshuai.xi                     // Do flow control by current rxq
426*53ee8cc1Swenshuai.xi                     // _nds_sc_rx_cur could be 2 over than _nds_sc_rx_read
427*53ee8cc1Swenshuai.xi                     if ( (_nds_sc_rx_cnt == 0) && (_nds_sc_rxq_cur != _nds_sc_rxq_next) )
428*53ee8cc1Swenshuai.xi                     {
429*53ee8cc1Swenshuai.xi                         // switch to next rxq
430*53ee8cc1Swenshuai.xi                         _nds_sc_rxq_cur++;
431*53ee8cc1Swenshuai.xi                         if (_nds_sc_rxq_cur >= (NDS_SC_RX_REQ_MAX-2))
432*53ee8cc1Swenshuai.xi                         {
433*53ee8cc1Swenshuai.xi                             _nds_sc_rxq_cur = 0;
434*53ee8cc1Swenshuai.xi                         }
435*53ee8cc1Swenshuai.xi                         if (_nds_sc_rxq_cur != _nds_sc_rxq_next)
436*53ee8cc1Swenshuai.xi                         {
437*53ee8cc1Swenshuai.xi                             _nds_sc_rx_cnt = _nds_sc_rxq[_nds_sc_rxq_cur].s32Len;
438*53ee8cc1Swenshuai.xi                         }
439*53ee8cc1Swenshuai.xi                     }
440*53ee8cc1Swenshuai.xi 
441*53ee8cc1Swenshuai.xi                     if (_nds_sc_rx_cnt != 0)
442*53ee8cc1Swenshuai.xi                     {
443*53ee8cc1Swenshuai.xi                         _nds_sc_reg_ctrl &= ~(CAM_UART_CTRL_FLOWCTRL); // open (high)
444*53ee8cc1Swenshuai.xi                         CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
445*53ee8cc1Swenshuai.xi                         if (_nds_sc_rxq[_nds_sc_rxq_cur].bFlowCtrl)
446*53ee8cc1Swenshuai.xi                         {
447*53ee8cc1Swenshuai.xi                             _nds_sc_reg_ctrl |= (CAM_UART_CTRL_FLOWCTRL); // close (low)
448*53ee8cc1Swenshuai.xi                             CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
449*53ee8cc1Swenshuai.xi                         }
450*53ee8cc1Swenshuai.xi                     }
451*53ee8cc1Swenshuai.xi                     else
452*53ee8cc1Swenshuai.xi                     {
453*53ee8cc1Swenshuai.xi                         // do nothing, flow control is be defined by the last byte
454*53ee8cc1Swenshuai.xi                     }
455*53ee8cc1Swenshuai.xi 
456*53ee8cc1Swenshuai.xi #else
457*53ee8cc1Swenshuai.xi                     if ((_nds_sc_rx_cnt != 0) && (_nds_sc_rxq[_nds_sc_rxq_read].bFlowCtrl))
458*53ee8cc1Swenshuai.xi                     {
459*53ee8cc1Swenshuai.xi                         _nds_sc_reg_ctrl &= ~(CAM_UART_CTRL_FLOWCTRL); // open (high)
460*53ee8cc1Swenshuai.xi                         CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
461*53ee8cc1Swenshuai.xi                         //__asm__ __volatile__("nop;");
462*53ee8cc1Swenshuai.xi                         _nds_sc_reg_ctrl |= (CAM_UART_CTRL_FLOWCTRL); // close (low)
463*53ee8cc1Swenshuai.xi                         CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
464*53ee8cc1Swenshuai.xi                     }
465*53ee8cc1Swenshuai.xi                     else
466*53ee8cc1Swenshuai.xi                     {
467*53ee8cc1Swenshuai.xi                         _nds_sc_rx_cnt = 0;
468*53ee8cc1Swenshuai.xi                         break;
469*53ee8cc1Swenshuai.xi                     }
470*53ee8cc1Swenshuai.xi #endif
471*53ee8cc1Swenshuai.xi                 }
472*53ee8cc1Swenshuai.xi                 else
473*53ee8cc1Swenshuai.xi                 {
474*53ee8cc1Swenshuai.xi                     break;
475*53ee8cc1Swenshuai.xi                     //_NDS_ASSERT_();
476*53ee8cc1Swenshuai.xi                 }
477*53ee8cc1Swenshuai.xi             }
478*53ee8cc1Swenshuai.xi             events |= NDS_SC_EVENT_RX;
479*53ee8cc1Swenshuai.xi         }
480*53ee8cc1Swenshuai.xi 
481*53ee8cc1Swenshuai.xi         MsOS_SetEvent(_nds_sc_dev.s32DevEventId, events);
482*53ee8cc1Swenshuai.xi         u16RegRead &= ~(CAM_UART_INT_RX | CAM_UART_INT_RX_OVERFLOW | CAM_UART_INT_PARITY_ERR_RX);
483*53ee8cc1Swenshuai.xi     }
484*53ee8cc1Swenshuai.xi 
485*53ee8cc1Swenshuai.xi     // send ONE byte if avaiable
486*53ee8cc1Swenshuai.xi     if (u16RegRead & (CAM_UART_INT_TX | CAM_UART_INT_PARITY_ERR_TX))
487*53ee8cc1Swenshuai.xi     {
488*53ee8cc1Swenshuai.xi         if (u16RegRead & CAM_UART_INT_PARITY_ERR_TX)
489*53ee8cc1Swenshuai.xi         {
490*53ee8cc1Swenshuai.xi             NDS_ASSERT(FALSE, , "NDS_ASSERT [%s]-[%d]\n", __FUNCTION__, __LINE__);
491*53ee8cc1Swenshuai.xi         }
492*53ee8cc1Swenshuai.xi         else
493*53ee8cc1Swenshuai.xi         {
494*53ee8cc1Swenshuai.xi             u16RegCtrl = CAM_REG(REG_CAM_UART_CTRL);
495*53ee8cc1Swenshuai.xi             if (u16RegCtrl & CAM_UART_STAT_TX_RDY)
496*53ee8cc1Swenshuai.xi             {
497*53ee8cc1Swenshuai.xi                 if(_nds_sc_dev.Txfifo_r != _nds_sc_dev.Txfifo_w)
498*53ee8cc1Swenshuai.xi                 {
499*53ee8cc1Swenshuai.xi                     CAM_REG(REG_CAM_UART_DATA) = _nds_sc_dev.Txfifo[_nds_sc_dev.Txfifo_r];
500*53ee8cc1Swenshuai.xi                     _nds_sc_dev.Txfifo[_nds_sc_dev.Txfifo_r] = 0xff;
501*53ee8cc1Swenshuai.xi                     _nds_sc_dev.Txfifo_r++;
502*53ee8cc1Swenshuai.xi                     if (NDS_SC_FIFO_SIZE == _nds_sc_dev.Txfifo_r)
503*53ee8cc1Swenshuai.xi                     {
504*53ee8cc1Swenshuai.xi                         _nds_sc_dev.Txfifo_r = 0;
505*53ee8cc1Swenshuai.xi                     }
506*53ee8cc1Swenshuai.xi                 }
507*53ee8cc1Swenshuai.xi             }
508*53ee8cc1Swenshuai.xi         }
509*53ee8cc1Swenshuai.xi         u16RegRead &= ~(CAM_UART_INT_TX | CAM_UART_INT_PARITY_ERR_TX);
510*53ee8cc1Swenshuai.xi     }
511*53ee8cc1Swenshuai.xi 
512*53ee8cc1Swenshuai.xi     // for debugging
513*53ee8cc1Swenshuai.xi     if (u16RegRead)
514*53ee8cc1Swenshuai.xi     {
515*53ee8cc1Swenshuai.xi         NDS_ASSERT(FALSE, , "NDS_ASSERT [%s]-[%d]\n", __FUNCTION__, __LINE__);
516*53ee8cc1Swenshuai.xi     }
517*53ee8cc1Swenshuai.xi 
518*53ee8cc1Swenshuai.xi     // IRQ handled
519*53ee8cc1Swenshuai.xi     NDS_SC_OS_EnableInterrupt();
520*53ee8cc1Swenshuai.xi }
521*53ee8cc1Swenshuai.xi 
522*53ee8cc1Swenshuai.xi 
_NDS_SC_IsrTask(void)523*53ee8cc1Swenshuai.xi static void _NDS_SC_IsrTask(void)
524*53ee8cc1Swenshuai.xi {
525*53ee8cc1Swenshuai.xi     MS_U8               u8Reg;
526*53ee8cc1Swenshuai.xi     MS_U32              u32Events, u32Timer;
527*53ee8cc1Swenshuai.xi 
528*53ee8cc1Swenshuai.xi     NDS_DBG("%s\n", __FUNCTION__);
529*53ee8cc1Swenshuai.xi 
530*53ee8cc1Swenshuai.xi     while(1)
531*53ee8cc1Swenshuai.xi     {
532*53ee8cc1Swenshuai.xi         u32Events = 0;
533*53ee8cc1Swenshuai.xi 
534*53ee8cc1Swenshuai.xi #if SC_RX_TIMEOUT_ENABLE
535*53ee8cc1Swenshuai.xi         MsOS_WaitEvent(_nds_sc_dev.s32DevEventId, 0xFFFF, &u32Events, E_OR_CLEAR, NDS_SC_CHK_TIMER);
536*53ee8cc1Swenshuai.xi #else
537*53ee8cc1Swenshuai.xi         MsOS_WaitEvent(_nds_sc_dev.s32DevEventId, 0xFFFF, &u32Events, E_OR_CLEAR, MSOS_WAIT_FOREVER);
538*53ee8cc1Swenshuai.xi #endif
539*53ee8cc1Swenshuai.xi 
540*53ee8cc1Swenshuai.xi         if (u32Events & NDS_SC_EVENT_CARD)
541*53ee8cc1Swenshuai.xi         {
542*53ee8cc1Swenshuai.xi             MsOS_DelayTask(10); // skip glitch
543*53ee8cc1Swenshuai.xi 
544*53ee8cc1Swenshuai.xi             // event notification
545*53ee8cc1Swenshuai.xi             u8Reg = CAM_REG(REG_CAM_UART_CTRL);
546*53ee8cc1Swenshuai.xi             if (u8Reg & CAM_UART_STAT_DETECT)
547*53ee8cc1Swenshuai.xi             {
548*53ee8cc1Swenshuai.xi                 _nds_sc_cardin = TRUE;
549*53ee8cc1Swenshuai.xi             }
550*53ee8cc1Swenshuai.xi             else
551*53ee8cc1Swenshuai.xi             {
552*53ee8cc1Swenshuai.xi                 _nds_sc_cardin = FALSE;
553*53ee8cc1Swenshuai.xi             }
554*53ee8cc1Swenshuai.xi             if (_nds_sc_cardin)
555*53ee8cc1Swenshuai.xi             {
556*53ee8cc1Swenshuai.xi                 if (_nds_sc_last_cardin == _nds_sc_cardin)
557*53ee8cc1Swenshuai.xi                 {   //[NOTE] Since reset is control by upper level, the REMOVE event can never be LOST!!
558*53ee8cc1Swenshuai.xi                     // -- Jerry
559*53ee8cc1Swenshuai.xi //printf("ISR_SC_REMOVED_2\n");
560*53ee8cc1Swenshuai.xi                     CORECA_SmartCardComm(SC_REMOVED);
561*53ee8cc1Swenshuai.xi                     if (_nds_sc_dev.param.cbEvent)
562*53ee8cc1Swenshuai.xi                     {
563*53ee8cc1Swenshuai.xi                         _nds_sc_dev.param.cbEvent(E_NDS_SC_EVENT_CARD_REMOVED);
564*53ee8cc1Swenshuai.xi                     }
565*53ee8cc1Swenshuai.xi //                    MsOS_DelayTask(100);
566*53ee8cc1Swenshuai.xi                 }
567*53ee8cc1Swenshuai.xi //printf("ISR_SC_REMOVED\n");
568*53ee8cc1Swenshuai.xi                 CORECA_SmartCardComm(SC_INSERTED);
569*53ee8cc1Swenshuai.xi                 if (_nds_sc_dev.param.cbEvent)
570*53ee8cc1Swenshuai.xi                 {
571*53ee8cc1Swenshuai.xi                     _nds_sc_dev.param.cbEvent(E_NDS_SC_EVENT_CARD_INSERTED);
572*53ee8cc1Swenshuai.xi                 }
573*53ee8cc1Swenshuai.xi             }
574*53ee8cc1Swenshuai.xi             else
575*53ee8cc1Swenshuai.xi             {
576*53ee8cc1Swenshuai.xi //printf("ISR_SC_REMOVED_1\n");
577*53ee8cc1Swenshuai.xi                 if (_nds_sc_last_cardin != _nds_sc_cardin)
578*53ee8cc1Swenshuai.xi                 {
579*53ee8cc1Swenshuai.xi                     CORECA_SmartCardComm(SC_REMOVED);
580*53ee8cc1Swenshuai.xi                     if (_nds_sc_dev.param.cbEvent)
581*53ee8cc1Swenshuai.xi                     {
582*53ee8cc1Swenshuai.xi                         _nds_sc_dev.param.cbEvent(E_NDS_SC_EVENT_CARD_REMOVED);
583*53ee8cc1Swenshuai.xi                     }
584*53ee8cc1Swenshuai.xi                 }
585*53ee8cc1Swenshuai.xi             }
586*53ee8cc1Swenshuai.xi             _nds_sc_last_cardin = _nds_sc_cardin;
587*53ee8cc1Swenshuai.xi 
588*53ee8cc1Swenshuai.xi         } // NDS_SC_EVENT_CARD
589*53ee8cc1Swenshuai.xi 
590*53ee8cc1Swenshuai.xi         if (u32Events & NDS_SC_EVENT_RX)
591*53ee8cc1Swenshuai.xi         {
592*53ee8cc1Swenshuai.xi             if ( (u32Events == (NDS_SC_EVENT_RX | NDS_SC_EVENT_RX_OVERFLOW))
593*53ee8cc1Swenshuai.xi                  && (_nds_sc_dev.bAborting != TRUE) )
594*53ee8cc1Swenshuai.xi             {
595*53ee8cc1Swenshuai.xi                 printf("SC_COMM_OVERFLOW[%d]\n", __LINE__);
596*53ee8cc1Swenshuai.xi                 CORECA_SmartCardComm(SC_COMM_OVERFLOW);
597*53ee8cc1Swenshuai.xi             }
598*53ee8cc1Swenshuai.xi             if ( (u32Events == (NDS_SC_EVENT_RX | NDS_SC_EVENT_RX_ERROR))
599*53ee8cc1Swenshuai.xi                  && (_nds_sc_dev.bAborting != TRUE) )
600*53ee8cc1Swenshuai.xi             {
601*53ee8cc1Swenshuai.xi                 printf("SC_PARITY[%d]\n", __LINE__);
602*53ee8cc1Swenshuai.xi                 CORECA_SmartCardComm(SC_PARITY);
603*53ee8cc1Swenshuai.xi             }
604*53ee8cc1Swenshuai.xi 
605*53ee8cc1Swenshuai.xi             if ( (_nds_sc_rxq_read != _nds_sc_rxq_next) && (_nds_sc_dev.bCardRdy) ) // incompleted Rx queue
606*53ee8cc1Swenshuai.xi             {
607*53ee8cc1Swenshuai.xi                 while(1)
608*53ee8cc1Swenshuai.xi                 {
609*53ee8cc1Swenshuai.xi                     if (_nds_sc_dev.Rxfifo_w != _nds_sc_dev.Rxfifo_r) // data in fifo
610*53ee8cc1Swenshuai.xi                     {
611*53ee8cc1Swenshuai.xi                         u32Timer = 0;
612*53ee8cc1Swenshuai.xi 
613*53ee8cc1Swenshuai.xi                         if (_nds_sc_rxq[_nds_sc_rxq_read].bUse)
614*53ee8cc1Swenshuai.xi                         {
615*53ee8cc1Swenshuai.xi                             if (_nds_sc_dev.bCardRdy != TRUE)
616*53ee8cc1Swenshuai.xi                             {
617*53ee8cc1Swenshuai.xi                                 break;
618*53ee8cc1Swenshuai.xi                             }
619*53ee8cc1Swenshuai.xi 
620*53ee8cc1Swenshuai.xi                             NDS_SC_RXQ_LOCK();
621*53ee8cc1Swenshuai.xi                             if ( (_nds_sc_rxq[_nds_sc_rxq_read].s32Len == 1)
622*53ee8cc1Swenshuai.xi                                  && (_nds_sc_rxq[_nds_sc_rxq_read].bNullFilter == TRUE)
623*53ee8cc1Swenshuai.xi                                  && (_nds_sc_dev.Rxfifo[_nds_sc_dev.Rxfifo_r] == 0x60) )
624*53ee8cc1Swenshuai.xi                             {
625*53ee8cc1Swenshuai.xi                                 //NOTE:
626*53ee8cc1Swenshuai.xi                                 // Will NULL only comes when the s32Len == 1?
627*53ee8cc1Swenshuai.xi                                 // - jerry
628*53ee8cc1Swenshuai.xi                                 _nds_sc_dev.Rxfifo_r++;
629*53ee8cc1Swenshuai.xi 
630*53ee8cc1Swenshuai.xi                                 if (_nds_sc_dev.param.bCommDump)
631*53ee8cc1Swenshuai.xi                                 {
632*53ee8cc1Swenshuai.xi                                     NDS_SC_DBG("NULL(0x60)\n");
633*53ee8cc1Swenshuai.xi                                 }
634*53ee8cc1Swenshuai.xi                             }
635*53ee8cc1Swenshuai.xi                             else
636*53ee8cc1Swenshuai.xi                             {
637*53ee8cc1Swenshuai.xi                                 if (_nds_sc_rxq[_nds_sc_rxq_read].s32Num > 0)
638*53ee8cc1Swenshuai.xi                                 {
639*53ee8cc1Swenshuai.xi                                     // receive one byte from Rx FIFO
640*53ee8cc1Swenshuai.xi                                     *(MS_U8 *)_nds_sc_rxq[_nds_sc_rxq_read].pAddr = _nds_sc_dev.Rxfifo[_nds_sc_dev.Rxfifo_r++];
641*53ee8cc1Swenshuai.xi                                     _nds_sc_rxq[_nds_sc_rxq_read].s32Num--;
642*53ee8cc1Swenshuai.xi                                     _nds_sc_rxq[_nds_sc_rxq_read].pAddr++;
643*53ee8cc1Swenshuai.xi                                 }
644*53ee8cc1Swenshuai.xi 
645*53ee8cc1Swenshuai.xi                                 // check Rx queue completion
646*53ee8cc1Swenshuai.xi                                 if (_nds_sc_rxq[_nds_sc_rxq_read].s32Num <= 0)
647*53ee8cc1Swenshuai.xi                                 {
648*53ee8cc1Swenshuai.xi                                     // Dump communcation for NDS tests
649*53ee8cc1Swenshuai.xi                                     if (_nds_sc_dev.param.bCommDump)
650*53ee8cc1Swenshuai.xi                                     {
651*53ee8cc1Swenshuai.xi                                         NDS_SC_DBG("RX= ");
652*53ee8cc1Swenshuai.xi                                         NDS_SC_DBG_PrintData( (_nds_sc_rxq[_nds_sc_rxq_read].pAddr - _nds_sc_rxq[_nds_sc_rxq_read].s32Len),
653*53ee8cc1Swenshuai.xi                                                           _nds_sc_rxq[_nds_sc_rxq_read].s32Len);
654*53ee8cc1Swenshuai.xi                                     }
655*53ee8cc1Swenshuai.xi 
656*53ee8cc1Swenshuai.xi                                     // reset queue
657*53ee8cc1Swenshuai.xi                                     _nds_sc_rxq[_nds_sc_rxq_read].bUse = FALSE;
658*53ee8cc1Swenshuai.xi                                     _nds_sc_rxq[_nds_sc_rxq_read].s32Num = 0;
659*53ee8cc1Swenshuai.xi                                     // next queue
660*53ee8cc1Swenshuai.xi                                     _nds_sc_rxq_read++;
661*53ee8cc1Swenshuai.xi                                     if (_nds_sc_rxq_read >= (NDS_SC_RX_REQ_MAX-2))
662*53ee8cc1Swenshuai.xi                                     {
663*53ee8cc1Swenshuai.xi                                         _nds_sc_rxq_read = 0;
664*53ee8cc1Swenshuai.xi                                     }
665*53ee8cc1Swenshuai.xi 
666*53ee8cc1Swenshuai.xi                                     if (_nds_sc_dev.bAborting == FALSE)
667*53ee8cc1Swenshuai.xi                                     {
668*53ee8cc1Swenshuai.xi                                         if (_nds_sc_dev.bCardRdy == TRUE)
669*53ee8cc1Swenshuai.xi                                         {
670*53ee8cc1Swenshuai.xi //                                            printf("SC_COMM_OK\n");
671*53ee8cc1Swenshuai.xi                                             CORECA_SmartCardComm(SC_COMM_OK);
672*53ee8cc1Swenshuai.xi                                         }
673*53ee8cc1Swenshuai.xi                                     }
674*53ee8cc1Swenshuai.xi                                 }
675*53ee8cc1Swenshuai.xi                             }
676*53ee8cc1Swenshuai.xi                             // wrap FIFO
677*53ee8cc1Swenshuai.xi                             if (_nds_sc_dev.Rxfifo_r >= NDS_SC_FIFO_SIZE)
678*53ee8cc1Swenshuai.xi                             {
679*53ee8cc1Swenshuai.xi                                 _nds_sc_dev.Rxfifo_r = 0;
680*53ee8cc1Swenshuai.xi                             }
681*53ee8cc1Swenshuai.xi                             NDS_SC_RXQ_UNLOCK();
682*53ee8cc1Swenshuai.xi 
683*53ee8cc1Swenshuai.xi                         }
684*53ee8cc1Swenshuai.xi                         else // not bUsed
685*53ee8cc1Swenshuai.xi                         {
686*53ee8cc1Swenshuai.xi                             //_NDS_ASSERT_();
687*53ee8cc1Swenshuai.xi                         }
688*53ee8cc1Swenshuai.xi                     }
689*53ee8cc1Swenshuai.xi                     else
690*53ee8cc1Swenshuai.xi                     {
691*53ee8cc1Swenshuai.xi #if 1 //[VERIFIER] try '50' for verifier overnight instead of '1'
692*53ee8cc1Swenshuai.xi //TODO: more overnight & smartcard single test for verification
693*53ee8cc1Swenshuai.xi                         NDS_DELAY(1);
694*53ee8cc1Swenshuai.xi #endif
695*53ee8cc1Swenshuai.xi                     }
696*53ee8cc1Swenshuai.xi 
697*53ee8cc1Swenshuai.xi                     if ( (!_nds_sc_dev.bCardRdy) || (!_nds_sc_rxq[_nds_sc_rxq_read].bUse) )
698*53ee8cc1Swenshuai.xi                     {
699*53ee8cc1Swenshuai.xi                         break;
700*53ee8cc1Swenshuai.xi                     }
701*53ee8cc1Swenshuai.xi                 }
702*53ee8cc1Swenshuai.xi             }
703*53ee8cc1Swenshuai.xi         }
704*53ee8cc1Swenshuai.xi 
705*53ee8cc1Swenshuai.xi #if SC_RX_TIMEOUT_ENABLE // WaitEvent should have timer to support timeout
706*53ee8cc1Swenshuai.xi         //---- Time Out ------
707*53ee8cc1Swenshuai.xi         // @TODO reset the new u32Timeout for next queued read request
708*53ee8cc1Swenshuai.xi         if (_nds_sc_rxq[_nds_sc_rxq_read].bUse == TRUE)
709*53ee8cc1Swenshuai.xi         {
710*53ee8cc1Swenshuai.xi             if (u32Timer > _nds_sc_rxq[_nds_sc_rxq_read].u32Timeout)
711*53ee8cc1Swenshuai.xi             {
712*53ee8cc1Swenshuai.xi                 u32Timer = 0; // reset timer
713*53ee8cc1Swenshuai.xi 
714*53ee8cc1Swenshuai.xi                 NDS_SC_RXQ_LOCK();
715*53ee8cc1Swenshuai.xi 
716*53ee8cc1Swenshuai.xi                 // Dump communcation for NDS tests
717*53ee8cc1Swenshuai.xi                 if (_nds_sc_dev.param.bCommDump)
718*53ee8cc1Swenshuai.xi                 {
719*53ee8cc1Swenshuai.xi                     NDS_SC_DBG("RX= ");
720*53ee8cc1Swenshuai.xi                     NDS_SC_DBG_PrintData( (_nds_sc_rxq[_nds_sc_rxq_read].pAddr - (_nds_sc_rxq[_nds_sc_rxq_read].s32Len-_nds_sc_rxq[_nds_sc_rxq_read].s32Num)),
721*53ee8cc1Swenshuai.xi                                        (_nds_sc_rxq[_nds_sc_rxq_read].s32Len-_nds_sc_rxq[_nds_sc_rxq_read].s32Num));
722*53ee8cc1Swenshuai.xi                 }
723*53ee8cc1Swenshuai.xi 
724*53ee8cc1Swenshuai.xi                 // reset queue
725*53ee8cc1Swenshuai.xi                 _nds_sc_rxq[_nds_sc_rxq_read].bUse = FALSE;
726*53ee8cc1Swenshuai.xi                 _nds_sc_rxq[_nds_sc_rxq_read].s32Num = 0;
727*53ee8cc1Swenshuai.xi                 // next queue
728*53ee8cc1Swenshuai.xi                 _nds_sc_rxq_read++;
729*53ee8cc1Swenshuai.xi                 if (_nds_sc_rxq_read >= (NDS_SC_RX_REQ_MAX-2))
730*53ee8cc1Swenshuai.xi                 {
731*53ee8cc1Swenshuai.xi                     _nds_sc_rxq_read = 0;
732*53ee8cc1Swenshuai.xi                 }
733*53ee8cc1Swenshuai.xi                 NDS_SC_RXQ_UNLOCK();
734*53ee8cc1Swenshuai.xi 
735*53ee8cc1Swenshuai.xi                 if ( (_nds_sc_dev.bAborting == FALSE)
736*53ee8cc1Swenshuai.xi                      && (_nds_sc_dev.bCardIn)
737*53ee8cc1Swenshuai.xi                      && (CAM_REG(REG_CAM_UART_CTRL) & CAM_UART_STAT_DETECT))
738*53ee8cc1Swenshuai.xi                 {
739*53ee8cc1Swenshuai.xi                     printf("SC_ERROR line %d\n", __LINE__);
740*53ee8cc1Swenshuai.xi                     CORECA_SmartCardComm(SC_ERROR); // time out
741*53ee8cc1Swenshuai.xi                 }
742*53ee8cc1Swenshuai.xi 
743*53ee8cc1Swenshuai.xi #if 0 // Only send one SC_ERROR and clear all the rest. But it may also resolved by AbortCommSession
744*53ee8cc1Swenshuai.xi                 NDS_SC_RXQ_LOCK();
745*53ee8cc1Swenshuai.xi                 while (_nds_sc_rxq[_nds_sc_rxq_read].bUse)
746*53ee8cc1Swenshuai.xi                 {
747*53ee8cc1Swenshuai.xi                     // reset queue
748*53ee8cc1Swenshuai.xi                     _nds_sc_rxq[_nds_sc_rxq_read].bUse = FALSE;
749*53ee8cc1Swenshuai.xi                     _nds_sc_rxq[_nds_sc_rxq_read].s32Num = 0;
750*53ee8cc1Swenshuai.xi                     // next queue
751*53ee8cc1Swenshuai.xi                     _nds_sc_rxq_read++;
752*53ee8cc1Swenshuai.xi                     if (_nds_sc_rxq_read >= (NDS_SC_RX_REQ_MAX-2))
753*53ee8cc1Swenshuai.xi                     {
754*53ee8cc1Swenshuai.xi                         _nds_sc_rxq_read = 0;
755*53ee8cc1Swenshuai.xi                     }
756*53ee8cc1Swenshuai.xi                 }
757*53ee8cc1Swenshuai.xi                 NDS_SC_RXQ_UNLOCK();
758*53ee8cc1Swenshuai.xi #endif
759*53ee8cc1Swenshuai.xi             }
760*53ee8cc1Swenshuai.xi             u32Timer += NDS_SC_CHK_TIMER;
761*53ee8cc1Swenshuai.xi         }
762*53ee8cc1Swenshuai.xi #endif
763*53ee8cc1Swenshuai.xi     }
764*53ee8cc1Swenshuai.xi }
765*53ee8cc1Swenshuai.xi 
766*53ee8cc1Swenshuai.xi 
767*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
768*53ee8cc1Swenshuai.xi //  Global Functions
769*53ee8cc1Swenshuai.xi //-------------------------------------------------------------------------------------------------
770*53ee8cc1Swenshuai.xi 
_NDS_SC_ResetFifo(void)771*53ee8cc1Swenshuai.xi void _NDS_SC_ResetFifo(void)
772*53ee8cc1Swenshuai.xi {
773*53ee8cc1Swenshuai.xi     //printf("--- SmartNDS_ResetFifo ---\n");
774*53ee8cc1Swenshuai.xi     NDS_SC_OS_DisableInterrupt();
775*53ee8cc1Swenshuai.xi 
776*53ee8cc1Swenshuai.xi     // @TODO: is it possible to lost card detection interrupt becuase clear it?
777*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_INT) = (CAM_UART_INT_MASK_RESET | CAM_UART_INT_ALL);
778*53ee8cc1Swenshuai.xi 
779*53ee8cc1Swenshuai.xi     NDS_SC_RXQ_LOCK();
780*53ee8cc1Swenshuai.xi     _nds_sc_dev.Rxfifo_r = 0;
781*53ee8cc1Swenshuai.xi     _nds_sc_dev.Rxfifo_w = 0;
782*53ee8cc1Swenshuai.xi     _NDS_SC_ResetRxIdx();
783*53ee8cc1Swenshuai.xi     NDS_SC_RXQ_UNLOCK();
784*53ee8cc1Swenshuai.xi 
785*53ee8cc1Swenshuai.xi     _nds_sc_dev.Txfifo_r = 0;
786*53ee8cc1Swenshuai.xi     _nds_sc_dev.Txfifo_w = 0;
787*53ee8cc1Swenshuai.xi     NDS_SC_OS_EnableInterrupt();
788*53ee8cc1Swenshuai.xi }
789*53ee8cc1Swenshuai.xi 
790*53ee8cc1Swenshuai.xi 
_NDS_SC_Write(MS_U8 * buf,MS_U32 len,MS_BOOL nfc)791*53ee8cc1Swenshuai.xi int _NDS_SC_Write(MS_U8 *buf, MS_U32 len, MS_BOOL nfc)
792*53ee8cc1Swenshuai.xi {
793*53ee8cc1Swenshuai.xi     int                 i, retry;
794*53ee8cc1Swenshuai.xi 
795*53ee8cc1Swenshuai.xi     NDS_SC_ENTRY();
796*53ee8cc1Swenshuai.xi 
797*53ee8cc1Swenshuai.xi     if ( (len <= 0) || (_nds_sc_dev.bCardRdy != TRUE) )
798*53ee8cc1Swenshuai.xi     {
799*53ee8cc1Swenshuai.xi         NDS_SC_RETURN(0);
800*53ee8cc1Swenshuai.xi     }
801*53ee8cc1Swenshuai.xi 
802*53ee8cc1Swenshuai.xi     NDS_SC_OS_DisableInterrupt();
803*53ee8cc1Swenshuai.xi     for (i = 1; i < len; i++)
804*53ee8cc1Swenshuai.xi     {
805*53ee8cc1Swenshuai.xi         if (_nds_sc_dev.bCardRdy != TRUE)
806*53ee8cc1Swenshuai.xi         {
807*53ee8cc1Swenshuai.xi             break;
808*53ee8cc1Swenshuai.xi         }
809*53ee8cc1Swenshuai.xi         _nds_sc_dev.Txfifo[_nds_sc_dev.Txfifo_w++] = buf[i];
810*53ee8cc1Swenshuai.xi         if (_nds_sc_dev.Txfifo_w >= NDS_SC_FIFO_SIZE)
811*53ee8cc1Swenshuai.xi         {
812*53ee8cc1Swenshuai.xi             _nds_sc_dev.Txfifo_w = 0;
813*53ee8cc1Swenshuai.xi         }
814*53ee8cc1Swenshuai.xi 
815*53ee8cc1Swenshuai.xi         if (i >= len)
816*53ee8cc1Swenshuai.xi         {
817*53ee8cc1Swenshuai.xi             break;
818*53ee8cc1Swenshuai.xi         }
819*53ee8cc1Swenshuai.xi     }
820*53ee8cc1Swenshuai.xi     NDS_SC_OS_EnableInterrupt();
821*53ee8cc1Swenshuai.xi 
822*53ee8cc1Swenshuai.xi     // Flow Control
823*53ee8cc1Swenshuai.xi     retry = 0;
824*53ee8cc1Swenshuai.xi     while (!(CAM_REG(REG_CAM_UART_CTRL)&CAM_UART_STAT_TX_RDY))
825*53ee8cc1Swenshuai.xi     {
826*53ee8cc1Swenshuai.xi         if ( ((retry++) > 10) || (_nds_sc_dev.bCardRdy != TRUE) )
827*53ee8cc1Swenshuai.xi         {
828*53ee8cc1Swenshuai.xi             NDS_SC_OS_DisableInterrupt();
829*53ee8cc1Swenshuai.xi             _nds_sc_dev.Txfifo_w = _nds_sc_dev.Txfifo_r;
830*53ee8cc1Swenshuai.xi             NDS_SC_OS_EnableInterrupt();
831*53ee8cc1Swenshuai.xi 
832*53ee8cc1Swenshuai.xi             NDS_SC_RETURN(0);
833*53ee8cc1Swenshuai.xi         }
834*53ee8cc1Swenshuai.xi         NDS_DELAY(1);
835*53ee8cc1Swenshuai.xi     }
836*53ee8cc1Swenshuai.xi     //printf("MStar. SC TX ing..\n");
837*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_DATA) = buf[0];
838*53ee8cc1Swenshuai.xi 
839*53ee8cc1Swenshuai.xi     NDS_SC_RETURN(i);
840*53ee8cc1Swenshuai.xi 
841*53ee8cc1Swenshuai.xi }
842*53ee8cc1Swenshuai.xi 
843*53ee8cc1Swenshuai.xi 
_NDS_SC_Read(MS_U8 * buf,MS_U32 len,MS_BOOL bnf,MS_BOOL bfc,MS_U32 timeout)844*53ee8cc1Swenshuai.xi int _NDS_SC_Read(MS_U8 *buf, MS_U32 len, MS_BOOL bnf, MS_BOOL bfc, MS_U32 timeout)
845*53ee8cc1Swenshuai.xi {
846*53ee8cc1Swenshuai.xi     NDS_SC_ENTRY();
847*53ee8cc1Swenshuai.xi 
848*53ee8cc1Swenshuai.xi     if ( (len > 255) || (len == 0) || (_nds_sc_dev.bCardRdy != TRUE) )
849*53ee8cc1Swenshuai.xi     {
850*53ee8cc1Swenshuai.xi         NDS_SC_RETURN(0);
851*53ee8cc1Swenshuai.xi     }
852*53ee8cc1Swenshuai.xi 
853*53ee8cc1Swenshuai.xi     NDS_SC_RXQ_LOCK();
854*53ee8cc1Swenshuai.xi     if ( (_nds_sc_rxq[_nds_sc_rxq_next].bUse) || (buf == NULL) )
855*53ee8cc1Swenshuai.xi     {
856*53ee8cc1Swenshuai.xi         NDS_SC_RXQ_UNLOCK();
857*53ee8cc1Swenshuai.xi         //_NDS_ASSERT_();
858*53ee8cc1Swenshuai.xi         //GEN_EXCEP;
859*53ee8cc1Swenshuai.xi         NDS_SC_RETURN(0);
860*53ee8cc1Swenshuai.xi     }
861*53ee8cc1Swenshuai.xi 
862*53ee8cc1Swenshuai.xi     _nds_sc_rxq[_nds_sc_rxq_next].pAddr = buf;
863*53ee8cc1Swenshuai.xi     _nds_sc_rxq[_nds_sc_rxq_next].s32Num = len;
864*53ee8cc1Swenshuai.xi     _nds_sc_rxq[_nds_sc_rxq_next].s32Len = len;
865*53ee8cc1Swenshuai.xi     _nds_sc_rxq[_nds_sc_rxq_next].u32Timeout = timeout;
866*53ee8cc1Swenshuai.xi     _nds_sc_rxq[_nds_sc_rxq_next].bNullFilter = bnf;
867*53ee8cc1Swenshuai.xi     _nds_sc_rxq[_nds_sc_rxq_next].bFlowCtrl = bfc;
868*53ee8cc1Swenshuai.xi 
869*53ee8cc1Swenshuai.xi     // Flow control
870*53ee8cc1Swenshuai.xi #if SC_FLOWCTRL_ENABLE
871*53ee8cc1Swenshuai.xi 
872*53ee8cc1Swenshuai.xi     _nds_sc_rxq[_nds_sc_rxq_next].bUse = TRUE;
873*53ee8cc1Swenshuai.xi 
874*53ee8cc1Swenshuai.xi     NDS_SC_OS_DisableInterrupt();
875*53ee8cc1Swenshuai.xi     _nds_sc_rxq_next++;
876*53ee8cc1Swenshuai.xi     if (_nds_sc_rxq_next >= (NDS_SC_RX_REQ_MAX-2))
877*53ee8cc1Swenshuai.xi     {
878*53ee8cc1Swenshuai.xi         _nds_sc_rxq_next = 0;
879*53ee8cc1Swenshuai.xi     }
880*53ee8cc1Swenshuai.xi     NDS_SC_OS_EnableInterrupt();
881*53ee8cc1Swenshuai.xi 
882*53ee8cc1Swenshuai.xi     // @TODO: check read request queue overflow
883*53ee8cc1Swenshuai.xi     {
884*53ee8cc1Swenshuai.xi         //NDS_SC_OS_DisableInterrupt();
885*53ee8cc1Swenshuai.xi         // read is protected by RXQ_LOCK, but cur is touched at ISR
886*53ee8cc1Swenshuai.xi         if (_nds_sc_rxq_next == _nds_sc_rxq_read)
887*53ee8cc1Swenshuai.xi         {
888*53ee8cc1Swenshuai.xi             NDS_ERR("[%s]-[%d] -- sc_rxq vverflow\n", __FUNCTION__, __LINE__);
889*53ee8cc1Swenshuai.xi             while(1);
890*53ee8cc1Swenshuai.xi         }
891*53ee8cc1Swenshuai.xi         //NDS_SC_OS_EnableInterrupt();
892*53ee8cc1Swenshuai.xi     }
893*53ee8cc1Swenshuai.xi 
894*53ee8cc1Swenshuai.xi     if (_nds_sc_rx_cnt == 0) // cur == next
895*53ee8cc1Swenshuai.xi     {
896*53ee8cc1Swenshuai.xi //printf("DEBUG:rx_cnt==0\n");
897*53ee8cc1Swenshuai.xi         //NOTE:
898*53ee8cc1Swenshuai.xi         // rx_cnt == 0 iff cur == next
899*53ee8cc1Swenshuai.xi         // there is no race condition between USER function and ISR
900*53ee8cc1Swenshuai.xi         // -- jerry
901*53ee8cc1Swenshuai.xi         _nds_sc_rx_cnt = len;
902*53ee8cc1Swenshuai.xi 
903*53ee8cc1Swenshuai.xi         NDS_SC_OS_DisableInterrupt();
904*53ee8cc1Swenshuai.xi         NDS_SC_LOCK();
905*53ee8cc1Swenshuai.xi         _nds_sc_reg_ctrl &= ~(CAM_UART_CTRL_FLOWCTRL); // open (high)
906*53ee8cc1Swenshuai.xi         CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
907*53ee8cc1Swenshuai.xi         if (bfc)
908*53ee8cc1Swenshuai.xi         {
909*53ee8cc1Swenshuai.xi             _nds_sc_reg_ctrl |= (CAM_UART_CTRL_FLOWCTRL); // close (low)
910*53ee8cc1Swenshuai.xi             CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
911*53ee8cc1Swenshuai.xi         }
912*53ee8cc1Swenshuai.xi         NDS_SC_UNLOCK();
913*53ee8cc1Swenshuai.xi         NDS_SC_OS_EnableInterrupt();
914*53ee8cc1Swenshuai.xi     }
915*53ee8cc1Swenshuai.xi 
916*53ee8cc1Swenshuai.xi #else
917*53ee8cc1Swenshuai.xi     _nds_sc_rx_cnt = len;
918*53ee8cc1Swenshuai.xi     _nds_sc_rxq_next++;
919*53ee8cc1Swenshuai.xi     if (_nds_sc_rxq_next >= (NDS_SC_RX_REQ_MAX-2))
920*53ee8cc1Swenshuai.xi     {
921*53ee8cc1Swenshuai.xi         _nds_sc_rxq_next = 0;
922*53ee8cc1Swenshuai.xi     }
923*53ee8cc1Swenshuai.xi #endif
924*53ee8cc1Swenshuai.xi     NDS_SC_RXQ_UNLOCK();
925*53ee8cc1Swenshuai.xi 
926*53ee8cc1Swenshuai.xi     if (_nds_sc_dev.bCardRdy != TRUE)
927*53ee8cc1Swenshuai.xi     {
928*53ee8cc1Swenshuai.xi         NDS_SC_RETURN(0);
929*53ee8cc1Swenshuai.xi     }
930*53ee8cc1Swenshuai.xi 
931*53ee8cc1Swenshuai.xi     NDS_SC_RETURN(len);
932*53ee8cc1Swenshuai.xi }
933*53ee8cc1Swenshuai.xi 
934*53ee8cc1Swenshuai.xi 
NDS_SC_Open(void)935*53ee8cc1Swenshuai.xi NDS_Result NDS_SC_Open(void)
936*53ee8cc1Swenshuai.xi {
937*53ee8cc1Swenshuai.xi     if (CAM_REG(REG_CAM_UART_CTRL) & CAM_UART_STAT_DETECT)
938*53ee8cc1Swenshuai.xi     {
939*53ee8cc1Swenshuai.xi         _nds_sc_cardin = TRUE;
940*53ee8cc1Swenshuai.xi     }
941*53ee8cc1Swenshuai.xi     else
942*53ee8cc1Swenshuai.xi     {
943*53ee8cc1Swenshuai.xi         _nds_sc_cardin = FALSE;
944*53ee8cc1Swenshuai.xi     }
945*53ee8cc1Swenshuai.xi 
946*53ee8cc1Swenshuai.xi     // register interrupt handler//enable interrupt for Icam-2
947*53ee8cc1Swenshuai.xi     NDS_SC_OS_AttachInterrupt(_NDS_SC_Isr);
948*53ee8cc1Swenshuai.xi     NDS_SC_OS_EnableInterrupt();
949*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_INT) = CAM_UART_INT_ALL;//(CAM_UART_INT_TX|CAM_UART_INT_RX|CAM_UART_INT_CD|CAM_UART_INT_RX_OVERFLOW);//0x3F;
950*53ee8cc1Swenshuai.xi 
951*53ee8cc1Swenshuai.xi     //MsOS_SetEvent(_smart_dev.s32DevEventId, 0x0001);
952*53ee8cc1Swenshuai.xi     _nds_sc_dev.bOpened = TRUE;
953*53ee8cc1Swenshuai.xi     return E_NDS_OK;
954*53ee8cc1Swenshuai.xi }
955*53ee8cc1Swenshuai.xi 
956*53ee8cc1Swenshuai.xi 
NDS_SC_Close(void)957*53ee8cc1Swenshuai.xi NDS_Result NDS_SC_Close(void)
958*53ee8cc1Swenshuai.xi {
959*53ee8cc1Swenshuai.xi     NDS_SC_OS_DisableInterrupt();
960*53ee8cc1Swenshuai.xi     NDS_SC_OS_DetachInterrupt();
961*53ee8cc1Swenshuai.xi 
962*53ee8cc1Swenshuai.xi     // clear interrupt
963*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_INT) = (CAM_UART_INT_MASK_RESET | CAM_UART_INT_ALL);
964*53ee8cc1Swenshuai.xi 
965*53ee8cc1Swenshuai.xi     _nds_sc_dev.bOpened = FALSE;
966*53ee8cc1Swenshuai.xi     return E_NDS_OK;
967*53ee8cc1Swenshuai.xi }
968*53ee8cc1Swenshuai.xi 
969*53ee8cc1Swenshuai.xi 
NDS_SC_Init(NDS_SC_Param * param)970*53ee8cc1Swenshuai.xi NDS_Result NDS_SC_Init(NDS_SC_Param *param)
971*53ee8cc1Swenshuai.xi {
972*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] cbSetVcc:0x%08lX, cbEvent:0x%08lX\n", __FUNCTION__, __LINE__, (MS_U32)param->cbSetVcc, (MS_U32)param->cbEvent);
973*53ee8cc1Swenshuai.xi 
974*53ee8cc1Swenshuai.xi     _nds_sc_reg_ctrl = 0;
975*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_CTRL) = _nds_sc_reg_ctrl;
976*53ee8cc1Swenshuai.xi 
977*53ee8cc1Swenshuai.xi     _nds_sc_dev.param.cbSetVcc  = param->cbSetVcc;
978*53ee8cc1Swenshuai.xi     _nds_sc_dev.param.cbEvent   = param->cbEvent;
979*53ee8cc1Swenshuai.xi     _nds_sc_dev.param.bCommDump = param->bCommDump;
980*53ee8cc1Swenshuai.xi     HAL_NDS_SC_Init(param);
981*53ee8cc1Swenshuai.xi 
982*53ee8cc1Swenshuai.xi     _NDS_SC_ResetFifo();
983*53ee8cc1Swenshuai.xi     //SmartNDS_ResetRxIdx();
984*53ee8cc1Swenshuai.xi     //NDS_SC_OS_DisableInterrupt();
985*53ee8cc1Swenshuai.xi     //NDS_SC_OS_DetachInterrupt();
986*53ee8cc1Swenshuai.xi 
987*53ee8cc1Swenshuai.xi 
988*53ee8cc1Swenshuai.xi     // Initialize inter-process variable --------------------------------------
989*53ee8cc1Swenshuai.xi     _nds_sc_dev.s32DevEventId = MsOS_CreateEventGroup("DevSmart_Event");
990*53ee8cc1Swenshuai.xi     if (_nds_sc_dev.s32DevEventId < 0)
991*53ee8cc1Swenshuai.xi     {
992*53ee8cc1Swenshuai.xi         MsOS_DeleteTask(_nds_sc_dev.s32TaskId);
993*53ee8cc1Swenshuai.xi         return E_NDS_FAIL;
994*53ee8cc1Swenshuai.xi     }
995*53ee8cc1Swenshuai.xi 
996*53ee8cc1Swenshuai.xi     _nds_sc_dev.s32Mutex = MsOS_CreateMutex(E_MSOS_FIFO, "NDS_SC_MutexRx", MSOS_PROCESS_SHARED);
997*53ee8cc1Swenshuai.xi     if (_nds_sc_dev.s32Mutex < 0)
998*53ee8cc1Swenshuai.xi     {
999*53ee8cc1Swenshuai.xi         MsOS_DeleteEventGroup(_nds_sc_dev.s32DevEventId);
1000*53ee8cc1Swenshuai.xi         MsOS_DeleteTask(_nds_sc_dev.s32TaskId);
1001*53ee8cc1Swenshuai.xi         return E_NDS_FAIL;
1002*53ee8cc1Swenshuai.xi     }
1003*53ee8cc1Swenshuai.xi 
1004*53ee8cc1Swenshuai.xi     _nds_sc_dev.s32MutexIdRx = MsOS_CreateMutex(E_MSOS_FIFO, "NDS_SC_MutexRx", MSOS_PROCESS_SHARED);
1005*53ee8cc1Swenshuai.xi     if (_nds_sc_dev.s32MutexIdRx < 0)
1006*53ee8cc1Swenshuai.xi     {
1007*53ee8cc1Swenshuai.xi         MsOS_DeleteMutex(_nds_sc_dev.s32Mutex);
1008*53ee8cc1Swenshuai.xi         MsOS_DeleteEventGroup(_nds_sc_dev.s32DevEventId);
1009*53ee8cc1Swenshuai.xi         MsOS_DeleteTask(_nds_sc_dev.s32TaskId);
1010*53ee8cc1Swenshuai.xi         return E_NDS_FAIL;
1011*53ee8cc1Swenshuai.xi     }
1012*53ee8cc1Swenshuai.xi 
1013*53ee8cc1Swenshuai.xi     _nds_sc_dev.s32TaskId = MsOS_CreateTask( (TaskEntry) _NDS_SC_IsrTask,
1014*53ee8cc1Swenshuai.xi                                              NULL,
1015*53ee8cc1Swenshuai.xi #if 1 //[VERIFIER]
1016*53ee8cc1Swenshuai.xi //TODO: try to be lower-priority for system banlance and smartcard single test for verification
1017*53ee8cc1Swenshuai.xi                                              (TaskPriority) (E_TASK_PRI_SYS+2),
1018*53ee8cc1Swenshuai.xi #else
1019*53ee8cc1Swenshuai.xi                                              (TaskPriority) (E_TASK_PRI_SYS),
1020*53ee8cc1Swenshuai.xi #endif
1021*53ee8cc1Swenshuai.xi                                              TRUE,
1022*53ee8cc1Swenshuai.xi                                              _nds_sc_stack,
1023*53ee8cc1Swenshuai.xi                                              4096,
1024*53ee8cc1Swenshuai.xi                                              "NDS_SC_IsrTask");
1025*53ee8cc1Swenshuai.xi 
1026*53ee8cc1Swenshuai.xi     return E_NDS_OK;
1027*53ee8cc1Swenshuai.xi }
1028*53ee8cc1Swenshuai.xi 
1029*53ee8cc1Swenshuai.xi 
NDS_SC_Exit(void)1030*53ee8cc1Swenshuai.xi NDS_Result NDS_SC_Exit(void)
1031*53ee8cc1Swenshuai.xi {
1032*53ee8cc1Swenshuai.xi     MsOS_DeleteTask(_nds_sc_dev.s32TaskId);
1033*53ee8cc1Swenshuai.xi     MsOS_DeleteMutex(_nds_sc_dev.s32MutexIdRx);
1034*53ee8cc1Swenshuai.xi     MsOS_DeleteMutex(_nds_sc_dev.s32Mutex);
1035*53ee8cc1Swenshuai.xi     MsOS_DeleteEventGroup(_nds_sc_dev.s32DevEventId);
1036*53ee8cc1Swenshuai.xi 
1037*53ee8cc1Swenshuai.xi     HAL_NDS_SC_Exit();
1038*53ee8cc1Swenshuai.xi 
1039*53ee8cc1Swenshuai.xi     return E_NDS_FAIL;
1040*53ee8cc1Swenshuai.xi }
1041*53ee8cc1Swenshuai.xi 
1042*53ee8cc1Swenshuai.xi 
1043*53ee8cc1Swenshuai.xi // 6.3.3
HDICA_SetCardClockDivisor(NDS_BYTE clock_divisor)1044*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_SetCardClockDivisor(NDS_BYTE clock_divisor)
1045*53ee8cc1Swenshuai.xi {
1046*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] -- clock_divisor[%d]\n", __FUNCTION__, __LINE__, clock_divisor);
1047*53ee8cc1Swenshuai.xi 
1048*53ee8cc1Swenshuai.xi     // ND-T189
1049*53ee8cc1Swenshuai.xi     switch (clock_divisor)
1050*53ee8cc1Swenshuai.xi     {
1051*53ee8cc1Swenshuai.xi     case HIGHEST_CLOCK : // 13.5 MHz
1052*53ee8cc1Swenshuai.xi         _nds_sc_dev.clk = E_NDS_SC_CLK_27M_D2;
1053*53ee8cc1Swenshuai.xi         break;
1054*53ee8cc1Swenshuai.xi     case MEDIUM_CLOCK : // 6.75 MHz
1055*53ee8cc1Swenshuai.xi         _nds_sc_dev.clk = E_NDS_SC_CLK_27M_D4;
1056*53ee8cc1Swenshuai.xi         break;
1057*53ee8cc1Swenshuai.xi     case LOWEST_CLOCK : // 4.5 MHz
1058*53ee8cc1Swenshuai.xi         _nds_sc_dev.clk = E_NDS_SC_CLK_27M_D6;
1059*53ee8cc1Swenshuai.xi         break;
1060*53ee8cc1Swenshuai.xi     default:
1061*53ee8cc1Swenshuai.xi         NDS_DBG("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1062*53ee8cc1Swenshuai.xi         return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1063*53ee8cc1Swenshuai.xi     }
1064*53ee8cc1Swenshuai.xi 
1065*53ee8cc1Swenshuai.xi     if (!HAL_NDS_SC_SetClockDivisor(_nds_sc_dev.clk))
1066*53ee8cc1Swenshuai.xi     {
1067*53ee8cc1Swenshuai.xi         NDS_DBG("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1068*53ee8cc1Swenshuai.xi         return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1069*53ee8cc1Swenshuai.xi     }
1070*53ee8cc1Swenshuai.xi 
1071*53ee8cc1Swenshuai.xi     MsOS_DelayTask(10);
1072*53ee8cc1Swenshuai.xi 
1073*53ee8cc1Swenshuai.xi     return CA_OK;
1074*53ee8cc1Swenshuai.xi }
1075*53ee8cc1Swenshuai.xi 
1076*53ee8cc1Swenshuai.xi 
1077*53ee8cc1Swenshuai.xi // 6.3.4
HDICA_SetConvention(NDS_BYTE convention)1078*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_SetConvention (NDS_BYTE convention)
1079*53ee8cc1Swenshuai.xi {
1080*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] -- convention[%d] \n", __FUNCTION__, __LINE__, convention);
1081*53ee8cc1Swenshuai.xi 
1082*53ee8cc1Swenshuai.xi     switch (convention)
1083*53ee8cc1Swenshuai.xi     {
1084*53ee8cc1Swenshuai.xi     case HDICA_CONVENTION_INVERSE:
1085*53ee8cc1Swenshuai.xi         _NDS_SC_CLR_CTRL(CAM_UART_CTRL_CONV_DIRECT);
1086*53ee8cc1Swenshuai.xi         break;
1087*53ee8cc1Swenshuai.xi     case HDICA_CONVENTION_DIRECT:
1088*53ee8cc1Swenshuai.xi         _NDS_SC_SET_CTRL(CAM_UART_CTRL_CONV_DIRECT);
1089*53ee8cc1Swenshuai.xi         break;
1090*53ee8cc1Swenshuai.xi     default:
1091*53ee8cc1Swenshuai.xi         NDS_DBG("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1092*53ee8cc1Swenshuai.xi         return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1093*53ee8cc1Swenshuai.xi     }
1094*53ee8cc1Swenshuai.xi 
1095*53ee8cc1Swenshuai.xi     return CA_OK;
1096*53ee8cc1Swenshuai.xi }
1097*53ee8cc1Swenshuai.xi 
1098*53ee8cc1Swenshuai.xi 
1099*53ee8cc1Swenshuai.xi // 6.3.5
HDICA_SetUartBaudRate(NDS_BYTE baud_rate)1100*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_SetUartBaudRate (NDS_BYTE baud_rate)
1101*53ee8cc1Swenshuai.xi {
1102*53ee8cc1Swenshuai.xi     MS_U16              n;
1103*53ee8cc1Swenshuai.xi     MS_U32              br, div;
1104*53ee8cc1Swenshuai.xi 
1105*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] -- baud_rate[%d]\n", __FUNCTION__, __LINE__, baud_rate);
1106*53ee8cc1Swenshuai.xi 
1107*53ee8cc1Swenshuai.xi     // Real baudrate (BR) for ICAM2_clk = 50 MHz, SM_clk = 27MHz/6 = 4.5 MHz
1108*53ee8cc1Swenshuai.xi 
1109*53ee8cc1Swenshuai.xi     br = 580645; // Nominal BAUD_RATE (153600) for HIGH_CLOCK (13.5 MHz) : 13.5 * 153600 / 3.5712
1110*53ee8cc1Swenshuai.xi     div = 1;
1111*53ee8cc1Swenshuai.xi     switch (_nds_sc_dev.clk)
1112*53ee8cc1Swenshuai.xi     {
1113*53ee8cc1Swenshuai.xi     case E_NDS_SC_CLK_27M_D2:
1114*53ee8cc1Swenshuai.xi         // do nothing
1115*53ee8cc1Swenshuai.xi         break;
1116*53ee8cc1Swenshuai.xi     case E_NDS_SC_CLK_27M_D4:
1117*53ee8cc1Swenshuai.xi         div = 2;
1118*53ee8cc1Swenshuai.xi         break;
1119*53ee8cc1Swenshuai.xi     case E_NDS_SC_CLK_27M_D6:
1120*53ee8cc1Swenshuai.xi     default:
1121*53ee8cc1Swenshuai.xi         div = 3;
1122*53ee8cc1Swenshuai.xi         break;
1123*53ee8cc1Swenshuai.xi     }
1124*53ee8cc1Swenshuai.xi 
1125*53ee8cc1Swenshuai.xi     switch (baud_rate)
1126*53ee8cc1Swenshuai.xi     {
1127*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_9600:
1128*53ee8cc1Swenshuai.xi         div = div << 1;
1129*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_19200:
1130*53ee8cc1Swenshuai.xi         div = div << 1;
1131*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_38400:
1132*53ee8cc1Swenshuai.xi         div = div << 1;
1133*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_76800:
1134*53ee8cc1Swenshuai.xi         div = div << 1;
1135*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_153600:
1136*53ee8cc1Swenshuai.xi         // do nothing
1137*53ee8cc1Swenshuai.xi         break;
1138*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_223200:
1139*53ee8cc1Swenshuai.xi     default:
1140*53ee8cc1Swenshuai.xi         NDS_DBG("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1141*53ee8cc1Swenshuai.xi         return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1142*53ee8cc1Swenshuai.xi     }
1143*53ee8cc1Swenshuai.xi 
1144*53ee8cc1Swenshuai.xi     n = NDS_CAM_CLK / br * div; // clk / (br / div)
1145*53ee8cc1Swenshuai.xi /*
1146*53ee8cc1Swenshuai.xi     switch(_nds_sc_dev.clk)
1147*53ee8cc1Swenshuai.xi     {
1148*53ee8cc1Swenshuai.xi     case E_NDS_SC_CLK_27M_D2:
1149*53ee8cc1Swenshuai.xi         clkdiv = 72580; // 72580.5
1150*53ee8cc1Swenshuai.xi         break;
1151*53ee8cc1Swenshuai.xi     case E_NDS_SC_CLK_27M_D4:
1152*53ee8cc1Swenshuai.xi         clkdiv = 36290; // 36290.25
1153*53ee8cc1Swenshuai.xi         break;
1154*53ee8cc1Swenshuai.xi     case E_NDS_SC_CLK_27M_D6:
1155*53ee8cc1Swenshuai.xi     default:
1156*53ee8cc1Swenshuai.xi         clkdiv = 24193; // 24193.5 (BR) for
1157*53ee8cc1Swenshuai.xi         break;
1158*53ee8cc1Swenshuai.xi     }
1159*53ee8cc1Swenshuai.xi 
1160*53ee8cc1Swenshuai.xi     // N = MCLK / BReal
1161*53ee8cc1Swenshuai.xi     switch (baud_rate)
1162*53ee8cc1Swenshuai.xi     {
1163*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_153600:
1164*53ee8cc1Swenshuai.xi         //div = (div>>1) + (div&0x1);
1165*53ee8cc1Swenshuai.xi         n = (clk/193548)-2 ;
1166*53ee8cc1Swenshuai.xi         break;
1167*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_76800:
1168*53ee8cc1Swenshuai.xi         //div = (div>>1) + (div&0x1);
1169*53ee8cc1Swenshuai.xi         n = (clk/96774)-2 ;
1170*53ee8cc1Swenshuai.xi         break;
1171*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_38400:
1172*53ee8cc1Swenshuai.xi         //div = (div>>1) + (div&0x1);
1173*53ee8cc1Swenshuai.xi         n = (clk/48387)-2 ;
1174*53ee8cc1Swenshuai.xi         break;
1175*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_19200:
1176*53ee8cc1Swenshuai.xi         //div = (div>>1) + (div&0x1);
1177*53ee8cc1Swenshuai.xi         n = (clk/clkdiv)-2 ;
1178*53ee8cc1Swenshuai.xi         break;
1179*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_9600:
1180*53ee8cc1Swenshuai.xi         n = (clk/12096)-2 ;
1181*53ee8cc1Swenshuai.xi         break;
1182*53ee8cc1Swenshuai.xi     case HDICA_BAUD_RATE_223200:
1183*53ee8cc1Swenshuai.xi     default:
1184*53ee8cc1Swenshuai.xi         NDS_DBG("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1185*53ee8cc1Swenshuai.xi         return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1186*53ee8cc1Swenshuai.xi     }
1187*53ee8cc1Swenshuai.xi */
1188*53ee8cc1Swenshuai.xi 
1189*53ee8cc1Swenshuai.xi     n = n - 2;
1190*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_BDRT_L) = n & 0xFF;
1191*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_BDRT_H) = n >> 8;
1192*53ee8cc1Swenshuai.xi 
1193*53ee8cc1Swenshuai.xi     return CA_OK;
1194*53ee8cc1Swenshuai.xi }
1195*53ee8cc1Swenshuai.xi 
1196*53ee8cc1Swenshuai.xi 
1197*53ee8cc1Swenshuai.xi // 6.3.6
HDICA_SetVccLevel(NDS_BYTE vcc_level)1198*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_SetVccLevel(NDS_BYTE vcc_level)
1199*53ee8cc1Swenshuai.xi {
1200*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] -- vcc_level[%d]\n", __FUNCTION__, __LINE__, vcc_level);
1201*53ee8cc1Swenshuai.xi 
1202*53ee8cc1Swenshuai.xi     if (!_nds_sc_dev.param.cbSetVcc)
1203*53ee8cc1Swenshuai.xi     {
1204*53ee8cc1Swenshuai.xi         NDS_DBG("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1205*53ee8cc1Swenshuai.xi         return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1206*53ee8cc1Swenshuai.xi     }
1207*53ee8cc1Swenshuai.xi 
1208*53ee8cc1Swenshuai.xi     switch (vcc_level)
1209*53ee8cc1Swenshuai.xi     {
1210*53ee8cc1Swenshuai.xi     case HDICA_VCC_3V:
1211*53ee8cc1Swenshuai.xi         if (FALSE == _nds_sc_dev.param.cbSetVcc(FALSE))
1212*53ee8cc1Swenshuai.xi         {
1213*53ee8cc1Swenshuai.xi             return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1214*53ee8cc1Swenshuai.xi         }
1215*53ee8cc1Swenshuai.xi         break;
1216*53ee8cc1Swenshuai.xi     case HDICA_VCC_5V:
1217*53ee8cc1Swenshuai.xi         if (FALSE == _nds_sc_dev.param.cbSetVcc(TRUE))
1218*53ee8cc1Swenshuai.xi         {
1219*53ee8cc1Swenshuai.xi             return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1220*53ee8cc1Swenshuai.xi         }
1221*53ee8cc1Swenshuai.xi         break;
1222*53ee8cc1Swenshuai.xi     }
1223*53ee8cc1Swenshuai.xi 
1224*53ee8cc1Swenshuai.xi     return CA_OK;
1225*53ee8cc1Swenshuai.xi 
1226*53ee8cc1Swenshuai.xi     /*
1227*53ee8cc1Swenshuai.xi     switch (vcc_level)
1228*53ee8cc1Swenshuai.xi     {
1229*53ee8cc1Swenshuai.xi     case HDICA_VCC_3V:
1230*53ee8cc1Swenshuai.xi         *((volatile unsigned int*)0xBF203CC0) = 0x0B00;//TODO:: GPIO_OEN pad enable
1231*53ee8cc1Swenshuai.xi         *((volatile unsigned int*)0xBF203CC0) |= 0xB000;//TODO:: GPIO
1232*53ee8cc1Swenshuai.xi         break;
1233*53ee8cc1Swenshuai.xi     case HDICA_VCC_5V:
1234*53ee8cc1Swenshuai.xi 
1235*53ee8cc1Swenshuai.xi         *((volatile unsigned int*)0xBF203CC0) = 0x4F00;//TODO:: GPIO_OEN pad enable
1236*53ee8cc1Swenshuai.xi         *((volatile unsigned int*)0xBF203CC0) &= ~0xB000;//TODO:: GPIO
1237*53ee8cc1Swenshuai.xi         break;
1238*53ee8cc1Swenshuai.xi     default:
1239*53ee8cc1Swenshuai.xi     }
1240*53ee8cc1Swenshuai.xi     */
1241*53ee8cc1Swenshuai.xi 
1242*53ee8cc1Swenshuai.xi     return CA_OK;
1243*53ee8cc1Swenshuai.xi }
1244*53ee8cc1Swenshuai.xi 
1245*53ee8cc1Swenshuai.xi // 6.3.7
HDICA_SetVcc(NDS_BYTE vcc_switch)1246*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_SetVcc (NDS_BYTE vcc_switch)
1247*53ee8cc1Swenshuai.xi {
1248*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] -- vcc_switch[%d]\n", __FUNCTION__, __LINE__, vcc_switch);
1249*53ee8cc1Swenshuai.xi 
1250*53ee8cc1Swenshuai.xi     if (_nds_sc_dev.bOpened)
1251*53ee8cc1Swenshuai.xi     {
1252*53ee8cc1Swenshuai.xi         NDS_SC_RXQ_LOCK(); // for SetVcc, bCardIn
1253*53ee8cc1Swenshuai.xi         {
1254*53ee8cc1Swenshuai.xi             if (vcc_switch == HDICA_VCC_ON) //(HDICA_VCC_ON)
1255*53ee8cc1Swenshuai.xi             {
1256*53ee8cc1Swenshuai.xi //                NDS_DBG("HDICA_VCC_ON\n");
1257*53ee8cc1Swenshuai.xi 
1258*53ee8cc1Swenshuai.xi                 //[NOTE]
1259*53ee8cc1Swenshuai.xi                 // When ACTIVE, only remove could be detected.
1260*53ee8cc1Swenshuai.xi                 // When DEACTIVE, both remove & insert could be detected.
1261*53ee8cc1Swenshuai.xi                 // If the card is removed and Vcc is ON, the DETECT will never work
1262*53ee8cc1Swenshuai.xi                 // -- Jerry
1263*53ee8cc1Swenshuai.xi                 _NDS_SC_SET_CTRL(CAM_UART_CTRL_VCC_ACTIVE);
1264*53ee8cc1Swenshuai.xi                 if ( !(CAM_REG(REG_CAM_UART_CTRL) & CAM_UART_STAT_DETECT) )
1265*53ee8cc1Swenshuai.xi                 {
1266*53ee8cc1Swenshuai.xi //                    NDS_DBG("HDICA_VCC_ON[FAIL]\n");
1267*53ee8cc1Swenshuai.xi                     _NDS_SC_CLR_CTRL(CAM_UART_CTRL_VCC_ACTIVE);
1268*53ee8cc1Swenshuai.xi                     NDS_SC_RXQ_UNLOCK(); // for SetVcc, bCardIn
1269*53ee8cc1Swenshuai.xi                     return CA_DRIVER_CAN_NOT_PERFORM_FUNCTION_NOW;
1270*53ee8cc1Swenshuai.xi                 }
1271*53ee8cc1Swenshuai.xi #ifdef MSOS_TYPE_LINUX_KERNEL
1272*53ee8cc1Swenshuai.xi                 mdelay(NDS_SC_VCC_DELAY);
1273*53ee8cc1Swenshuai.xi #else
1274*53ee8cc1Swenshuai.xi                 MsOS_DelayTask(NDS_SC_VCC_DELAY);
1275*53ee8cc1Swenshuai.xi #endif
1276*53ee8cc1Swenshuai.xi 
1277*53ee8cc1Swenshuai.xi                 _nds_sc_dev.bAborting = FALSE;
1278*53ee8cc1Swenshuai.xi                 _nds_sc_dev.bCardRdy = TRUE;
1279*53ee8cc1Swenshuai.xi             }
1280*53ee8cc1Swenshuai.xi             else
1281*53ee8cc1Swenshuai.xi             {
1282*53ee8cc1Swenshuai.xi //                NDS_DBG("HDICA_VCC_OFF\n");
1283*53ee8cc1Swenshuai.xi                 _NDS_SC_CLR_CTRL(CAM_UART_CTRL_VCC_ACTIVE);
1284*53ee8cc1Swenshuai.xi 
1285*53ee8cc1Swenshuai.xi #ifdef MSOS_TYPE_LINUX_KERNEL
1286*53ee8cc1Swenshuai.xi                 mdelay(10);
1287*53ee8cc1Swenshuai.xi #else
1288*53ee8cc1Swenshuai.xi                 MsOS_DelayTask(10);
1289*53ee8cc1Swenshuai.xi #endif
1290*53ee8cc1Swenshuai.xi             }
1291*53ee8cc1Swenshuai.xi         }
1292*53ee8cc1Swenshuai.xi         NDS_SC_RXQ_UNLOCK(); // for SetVcc, bCardIn
1293*53ee8cc1Swenshuai.xi 
1294*53ee8cc1Swenshuai.xi         _NDS_SC_ResetFifo();
1295*53ee8cc1Swenshuai.xi     }
1296*53ee8cc1Swenshuai.xi 
1297*53ee8cc1Swenshuai.xi     return CA_OK;
1298*53ee8cc1Swenshuai.xi }
1299*53ee8cc1Swenshuai.xi 
1300*53ee8cc1Swenshuai.xi 
1301*53ee8cc1Swenshuai.xi // 6.3.8
HDICA_SetVpp(NDS_BYTE vpp_switch)1302*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_SetVpp (NDS_BYTE vpp_switch)
1303*53ee8cc1Swenshuai.xi {
1304*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s][%d]\n", __FUNCTION__, __LINE__);
1305*53ee8cc1Swenshuai.xi 
1306*53ee8cc1Swenshuai.xi     if (vpp_switch == HDICA_VCC_ON)
1307*53ee8cc1Swenshuai.xi     {
1308*53ee8cc1Swenshuai.xi         _NDS_SC_SET_CTRL(CAM_UART_CTRL_VPP_ACTIVE);
1309*53ee8cc1Swenshuai.xi     }
1310*53ee8cc1Swenshuai.xi     else
1311*53ee8cc1Swenshuai.xi     {
1312*53ee8cc1Swenshuai.xi         _NDS_SC_CLR_CTRL(CAM_UART_CTRL_VPP_ACTIVE);
1313*53ee8cc1Swenshuai.xi     }
1314*53ee8cc1Swenshuai.xi 
1315*53ee8cc1Swenshuai.xi     return CA_OK;
1316*53ee8cc1Swenshuai.xi }
1317*53ee8cc1Swenshuai.xi 
1318*53ee8cc1Swenshuai.xi 
1319*53ee8cc1Swenshuai.xi // 6.3.9
HDICA_SetGuardTime(NDS_BYTE guard_time)1320*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_SetGuardTime (NDS_BYTE guard_time)
1321*53ee8cc1Swenshuai.xi {
1322*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] -- guard_time[%d]\n", __FUNCTION__, __LINE__, guard_time);
1323*53ee8cc1Swenshuai.xi 
1324*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_GUARD) = guard_time;
1325*53ee8cc1Swenshuai.xi 
1326*53ee8cc1Swenshuai.xi     return CA_OK;
1327*53ee8cc1Swenshuai.xi }
1328*53ee8cc1Swenshuai.xi 
1329*53ee8cc1Swenshuai.xi 
1330*53ee8cc1Swenshuai.xi // 6.3.10
HDICA_GetInputByte(NDS_BYTE * input_byte)1331*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_GetInputByte (NDS_BYTE *input_byte)
1332*53ee8cc1Swenshuai.xi {
1333*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1334*53ee8cc1Swenshuai.xi 
1335*53ee8cc1Swenshuai.xi     return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1336*53ee8cc1Swenshuai.xi }
1337*53ee8cc1Swenshuai.xi 
1338*53ee8cc1Swenshuai.xi 
1339*53ee8cc1Swenshuai.xi // 6.3.11
HDICA_PutOutputByte(NDS_BYTE output_byte)1340*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_PutOutputByte (NDS_BYTE output_byte)
1341*53ee8cc1Swenshuai.xi {
1342*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1343*53ee8cc1Swenshuai.xi 
1344*53ee8cc1Swenshuai.xi     return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1345*53ee8cc1Swenshuai.xi }
1346*53ee8cc1Swenshuai.xi 
1347*53ee8cc1Swenshuai.xi 
1348*53ee8cc1Swenshuai.xi MS_U32 sc_poll_time = 0;
1349*53ee8cc1Swenshuai.xi 
1350*53ee8cc1Swenshuai.xi // 6.3.12
HDICA_ResetCard(NDS_BYTE reset_switch)1351*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_ResetCard (NDS_BYTE reset_switch)
1352*53ee8cc1Swenshuai.xi {
1353*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] -- reset_switch[%d]\n", __FUNCTION__, __LINE__, reset_switch);
1354*53ee8cc1Swenshuai.xi 
1355*53ee8cc1Swenshuai.xi #if 0 //[VERIFIER]
1356*53ee8cc1Swenshuai.xi     // Debug Only
1357*53ee8cc1Swenshuai.xi     MS_U32 time = MsOS_GetSystemTime();
1358*53ee8cc1Swenshuai.xi     printf("HDICA_ResetCard %ld poll:%ld overflow:%ld\n", time, time-sc_poll_time, time-emm_overflow_time);
1359*53ee8cc1Swenshuai.xi #else
1360*53ee8cc1Swenshuai.xi     printf("HDICA_ResetCard %ld\n", MsOS_GetSystemTime());
1361*53ee8cc1Swenshuai.xi #endif
1362*53ee8cc1Swenshuai.xi 
1363*53ee8cc1Swenshuai.xi     switch (reset_switch)
1364*53ee8cc1Swenshuai.xi     {
1365*53ee8cc1Swenshuai.xi     case ACTIVE:
1366*53ee8cc1Swenshuai.xi         _NDS_SC_SET_CTRL(CAM_UART_CTRL_RST);
1367*53ee8cc1Swenshuai.xi         break;
1368*53ee8cc1Swenshuai.xi 
1369*53ee8cc1Swenshuai.xi     case INACTIVE:
1370*53ee8cc1Swenshuai.xi         _NDS_SC_CLR_CTRL(CAM_UART_CTRL_RST);
1371*53ee8cc1Swenshuai.xi         break;
1372*53ee8cc1Swenshuai.xi 
1373*53ee8cc1Swenshuai.xi     case RESET_CYCLE:
1374*53ee8cc1Swenshuai.xi         MsOS_DelayTask(10); /* Delay for Vcc to rise */
1375*53ee8cc1Swenshuai.xi         _NDS_SC_CLR_CTRL(CAM_UART_CTRL_RST);
1376*53ee8cc1Swenshuai.xi         MsOS_DelayTask(5);
1377*53ee8cc1Swenshuai.xi         _NDS_SC_SET_CTRL(CAM_UART_CTRL_RST);
1378*53ee8cc1Swenshuai.xi         MsOS_DelayTask(5);
1379*53ee8cc1Swenshuai.xi         //CAM_REG(REG_CAM_UART_CTRL) = 0;//_NDS_SC_Ctrl_Reg;
1380*53ee8cc1Swenshuai.xi         //MsOS_DelayTask(2); /* should be 10 msec - Zvika */
1381*53ee8cc1Swenshuai.xi 
1382*53ee8cc1Swenshuai.xi         /* perform card reset cycle */
1383*53ee8cc1Swenshuai.xi         /* enable RX interrupts (should already be enabled!) */
1384*53ee8cc1Swenshuai.xi         //ICAM_RegisterWrite(SmartCardICAM, ICAM_UART_INT, IC_UI_DETECT_INT + IC_UI_RX_INT + IC_UI_RX_OV_INT);
1385*53ee8cc1Swenshuai.xi         CAM_REG(REG_CAM_UART_INT) = CAM_UART_INT_ALL; //enable (CAM_UART_INT_TX|CAM_UART_INT_RX|CAM_UART_INT_CD|CAM_UART_INT_RX_OVERFLOW);
1386*53ee8cc1Swenshuai.xi 
1387*53ee8cc1Swenshuai.xi         _NDS_SC_CLR_CTRL(CAM_UART_CTRL_RST);
1388*53ee8cc1Swenshuai.xi 
1389*53ee8cc1Swenshuai.xi         //printf("================>   RESET VAR:[%02X]\n", _nds_sc_reg_ctrl);
1390*53ee8cc1Swenshuai.xi         break;
1391*53ee8cc1Swenshuai.xi 
1392*53ee8cc1Swenshuai.xi     default:
1393*53ee8cc1Swenshuai.xi         NDS_DBG("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1394*53ee8cc1Swenshuai.xi         return CA_REQUEST_NOT_SUPPORTED_BY_DRIVER;
1395*53ee8cc1Swenshuai.xi     }
1396*53ee8cc1Swenshuai.xi 
1397*53ee8cc1Swenshuai.xi     return CA_OK;
1398*53ee8cc1Swenshuai.xi }
1399*53ee8cc1Swenshuai.xi 
1400*53ee8cc1Swenshuai.xi 
1401*53ee8cc1Swenshuai.xi // 6.3.13
HDICA_GetUartStatus(NDS_BYTE * uart_status)1402*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_GetUartStatus (NDS_BYTE *uart_status)
1403*53ee8cc1Swenshuai.xi {
1404*53ee8cc1Swenshuai.xi     *uart_status = 0;
1405*53ee8cc1Swenshuai.xi 
1406*53ee8cc1Swenshuai.xi     if (CAM_REG(REG_CAM_UART_CTRL) & CAM_UART_STAT_TX_RDY)
1407*53ee8cc1Swenshuai.xi     {
1408*53ee8cc1Swenshuai.xi         *uart_status |= HDICA_UART_STATUS_TX_IS_READY;                  /* Bit 0 */
1409*53ee8cc1Swenshuai.xi     }
1410*53ee8cc1Swenshuai.xi 
1411*53ee8cc1Swenshuai.xi     if (CAM_REG(REG_CAM_UART_CTRL) & CAM_UART_STAT_RX_RDY)
1412*53ee8cc1Swenshuai.xi     {
1413*53ee8cc1Swenshuai.xi         *uart_status |= HDICA_UART_STATUS_RX_IS_READY;                  /* Bit 1 */
1414*53ee8cc1Swenshuai.xi     }
1415*53ee8cc1Swenshuai.xi 
1416*53ee8cc1Swenshuai.xi     if (CAM_REG(REG_CAM_UART_INT) & CAM_UART_INT_PARITY_ERR_RX)
1417*53ee8cc1Swenshuai.xi     {
1418*53ee8cc1Swenshuai.xi         *uart_status |= HDICA_UART_STATUS_RCV_PARITY_ERROR;             /* Bit 2 */
1419*53ee8cc1Swenshuai.xi     }
1420*53ee8cc1Swenshuai.xi 
1421*53ee8cc1Swenshuai.xi     if (CAM_REG(REG_CAM_UART_INT) & CAM_UART_INT_RX_OVERFLOW)
1422*53ee8cc1Swenshuai.xi     {
1423*53ee8cc1Swenshuai.xi         *uart_status |= HDICA_UART_STATUS_OVERFLOW;                     /* Bit 3 */
1424*53ee8cc1Swenshuai.xi     }
1425*53ee8cc1Swenshuai.xi 
1426*53ee8cc1Swenshuai.xi     if (CAM_REG(REG_CAM_UART_INT) & CAM_UART_INT_PARITY_ERR_TX)
1427*53ee8cc1Swenshuai.xi     {
1428*53ee8cc1Swenshuai.xi         *uart_status |= HDICA_UART_STATUS_TX_PARITY_ERROR;              /* Bit 4 */
1429*53ee8cc1Swenshuai.xi     }
1430*53ee8cc1Swenshuai.xi 
1431*53ee8cc1Swenshuai.xi     if (_nds_sc_reg_ctrl & CAM_UART_CTRL_CONV_DIRECT)
1432*53ee8cc1Swenshuai.xi     {
1433*53ee8cc1Swenshuai.xi         *uart_status |= HDICA_UART_STATUS_CONVENTION_DIRECT;            /* Bit 5 */
1434*53ee8cc1Swenshuai.xi     }
1435*53ee8cc1Swenshuai.xi 
1436*53ee8cc1Swenshuai.xi     if (CAM_REG(REG_CAM_UART_CTRL) & CAM_UART_STAT_INT_PEND)
1437*53ee8cc1Swenshuai.xi     {
1438*53ee8cc1Swenshuai.xi         *uart_status |= HDICA_UART_STATUS_INTERRUPT_PENDING;            /* Bit 6 */
1439*53ee8cc1Swenshuai.xi     }
1440*53ee8cc1Swenshuai.xi 
1441*53ee8cc1Swenshuai.xi     if (CAM_REG(REG_CAM_UART_CTRL) & CAM_UART_STAT_DETECT)
1442*53ee8cc1Swenshuai.xi     {
1443*53ee8cc1Swenshuai.xi         *uart_status |= HDICA_UART_STATUS_CARD_INSERTED;                /* Bit 7 */
1444*53ee8cc1Swenshuai.xi     }
1445*53ee8cc1Swenshuai.xi 
1446*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] -- status[0x%x]\n", __FUNCTION__, __LINE__, *uart_status);
1447*53ee8cc1Swenshuai.xi 
1448*53ee8cc1Swenshuai.xi     return CA_OK;
1449*53ee8cc1Swenshuai.xi }
1450*53ee8cc1Swenshuai.xi 
1451*53ee8cc1Swenshuai.xi 
1452*53ee8cc1Swenshuai.xi // 6.3.14
HDICA_SetUartCommand(NDS_BYTE pin_mask)1453*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_SetUartCommand (NDS_BYTE pin_mask)
1454*53ee8cc1Swenshuai.xi {
1455*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d]\n", __FUNCTION__, __LINE__);
1456*53ee8cc1Swenshuai.xi 
1457*53ee8cc1Swenshuai.xi     CAM_REG(REG_CAM_UART_COM) = pin_mask;
1458*53ee8cc1Swenshuai.xi 
1459*53ee8cc1Swenshuai.xi     if (pin_mask & (CAM_UART_COM_C4 | CAM_UART_COM_C8))
1460*53ee8cc1Swenshuai.xi     {
1461*53ee8cc1Swenshuai.xi         HAL_NDS_SC_SetUartC48(TRUE);
1462*53ee8cc1Swenshuai.xi     }
1463*53ee8cc1Swenshuai.xi     else
1464*53ee8cc1Swenshuai.xi     {
1465*53ee8cc1Swenshuai.xi         HAL_NDS_SC_SetUartC48(FALSE);
1466*53ee8cc1Swenshuai.xi     }
1467*53ee8cc1Swenshuai.xi 
1468*53ee8cc1Swenshuai.xi     return CA_OK;
1469*53ee8cc1Swenshuai.xi }
1470*53ee8cc1Swenshuai.xi 
1471*53ee8cc1Swenshuai.xi 
1472*53ee8cc1Swenshuai.xi // 6.3.15
HDICA_SendAndReceiveBytesSession(NDS_BYTE * xmt_ptr,NDS_BYTE xmit_length,CAHDI_BOOLEAN null_filter,CAHDI_BOOLEAN use_flow_control,NDS_BYTE * rcv_ptr,NDS_BYTE rcv_length)1473*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_SendAndReceiveBytesSession (NDS_BYTE       *xmt_ptr,
1474*53ee8cc1Swenshuai.xi                                              NDS_BYTE       xmit_length,
1475*53ee8cc1Swenshuai.xi                                              CAHDI_BOOLEAN  null_filter,
1476*53ee8cc1Swenshuai.xi                                              CAHDI_BOOLEAN  use_flow_control,
1477*53ee8cc1Swenshuai.xi                                              NDS_BYTE       *rcv_ptr,
1478*53ee8cc1Swenshuai.xi                                              NDS_BYTE       rcv_length)
1479*53ee8cc1Swenshuai.xi {
1480*53ee8cc1Swenshuai.xi     MS_U32  len;
1481*53ee8cc1Swenshuai.xi 
1482*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] -- xmit[%d], rcv[%d]\n", __FUNCTION__, __LINE__, xmit_length, rcv_length);
1483*53ee8cc1Swenshuai.xi 
1484*53ee8cc1Swenshuai.xi     // check busy
1485*53ee8cc1Swenshuai.xi     if (_nds_sc_dev.bAborting)
1486*53ee8cc1Swenshuai.xi     {
1487*53ee8cc1Swenshuai.xi         return CA_DRIVER_CAN_NOT_PERFORM_FUNCTION_NOW;
1488*53ee8cc1Swenshuai.xi     }
1489*53ee8cc1Swenshuai.xi 
1490*53ee8cc1Swenshuai.xi     // Dump communcation for NDS tests
1491*53ee8cc1Swenshuai.xi     if (_nds_sc_dev.param.bCommDump)
1492*53ee8cc1Swenshuai.xi     {
1493*53ee8cc1Swenshuai.xi         NDS_SC_DBG("TX= ");
1494*53ee8cc1Swenshuai.xi         NDS_SC_DBG_PrintData(xmt_ptr, xmit_length);
1495*53ee8cc1Swenshuai.xi     }
1496*53ee8cc1Swenshuai.xi 
1497*53ee8cc1Swenshuai.xi #if 1 // debug
1498*53ee8cc1Swenshuai.xi     if (xmt_ptr[0] == 0x48) // 0x40, 0x54, 0x5c
1499*53ee8cc1Swenshuai.xi     {
1500*53ee8cc1Swenshuai.xi         switch (xmt_ptr[1])
1501*53ee8cc1Swenshuai.xi         {
1502*53ee8cc1Swenshuai.xi         case 0x5C:
1503*53ee8cc1Swenshuai.xi             //sc_poll_time = MsOS_GetSystemTime();
1504*53ee8cc1Swenshuai.xi             printf("NDS_POLL(%02X)\n", xmt_ptr[1]);
1505*53ee8cc1Swenshuai.xi             break;
1506*53ee8cc1Swenshuai.xi         default:
1507*53ee8cc1Swenshuai.xi             break;
1508*53ee8cc1Swenshuai.xi         }
1509*53ee8cc1Swenshuai.xi     }
1510*53ee8cc1Swenshuai.xi #endif // debug
1511*53ee8cc1Swenshuai.xi 
1512*53ee8cc1Swenshuai.xi     // Rx
1513*53ee8cc1Swenshuai.xi     len = _NDS_SC_Read(rcv_ptr, rcv_length, null_filter, use_flow_control, NDS_SC_RX_TIMEOUT);
1514*53ee8cc1Swenshuai.xi     if (len != rcv_length)
1515*53ee8cc1Swenshuai.xi     {
1516*53ee8cc1Swenshuai.xi         return CA_DRIVER_CAN_NOT_PERFORM_FUNCTION_NOW;
1517*53ee8cc1Swenshuai.xi     }
1518*53ee8cc1Swenshuai.xi 
1519*53ee8cc1Swenshuai.xi     // Tx
1520*53ee8cc1Swenshuai.xi     if ( (_NDS_SC_Write(xmt_ptr, xmit_length, use_flow_control) <= 0) ||
1521*53ee8cc1Swenshuai.xi          (_nds_sc_dev.bAborting) )
1522*53ee8cc1Swenshuai.xi     {
1523*53ee8cc1Swenshuai.xi         return CA_DRIVER_CAN_NOT_PERFORM_FUNCTION_NOW;
1524*53ee8cc1Swenshuai.xi     }
1525*53ee8cc1Swenshuai.xi 
1526*53ee8cc1Swenshuai.xi #if 1 //[VERIFIER]
1527*53ee8cc1Swenshuai.xi //TODO: check if delay necessary and smartcard single test
1528*53ee8cc1Swenshuai.xi     MsOS_DelayTask(5); // yield for ISR_Task
1529*53ee8cc1Swenshuai.xi #endif
1530*53ee8cc1Swenshuai.xi 
1531*53ee8cc1Swenshuai.xi     return CA_OK;
1532*53ee8cc1Swenshuai.xi }
1533*53ee8cc1Swenshuai.xi 
1534*53ee8cc1Swenshuai.xi 
HDICA_ReceiveBytesSession(CAHDI_BOOLEAN null_filter,CAHDI_BOOLEAN use_flow_control,NDS_BYTE * rcv_ptr,NDS_BYTE rcv_length)1535*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_ReceiveBytesSession (CAHDI_BOOLEAN null_filter,
1536*53ee8cc1Swenshuai.xi                                       CAHDI_BOOLEAN use_flow_control,
1537*53ee8cc1Swenshuai.xi                                       NDS_BYTE      *rcv_ptr,
1538*53ee8cc1Swenshuai.xi                                       NDS_BYTE      rcv_length)
1539*53ee8cc1Swenshuai.xi {
1540*53ee8cc1Swenshuai.xi     MS_U32  len;
1541*53ee8cc1Swenshuai.xi 
1542*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] rcv[%d]\n", __FUNCTION__, __LINE__, rcv_length);
1543*53ee8cc1Swenshuai.xi 
1544*53ee8cc1Swenshuai.xi     // check busy
1545*53ee8cc1Swenshuai.xi     if (_nds_sc_dev.bAborting)
1546*53ee8cc1Swenshuai.xi     {
1547*53ee8cc1Swenshuai.xi         return CA_DRIVER_CAN_NOT_PERFORM_FUNCTION_NOW;
1548*53ee8cc1Swenshuai.xi     }
1549*53ee8cc1Swenshuai.xi 
1550*53ee8cc1Swenshuai.xi     // Flow control
1551*53ee8cc1Swenshuai.xi #if SC_FLOWCTRL_ENABLE
1552*53ee8cc1Swenshuai.xi #else
1553*53ee8cc1Swenshuai.xi     _NDS_SC_CLR_CTRL(CAM_UART_CTRL_FLOWCTRL); // open (high)
1554*53ee8cc1Swenshuai.xi     if (bfc)
1555*53ee8cc1Swenshuai.xi     {
1556*53ee8cc1Swenshuai.xi         _NDS_SC_SET_CTRL(CAM_UART_CTRL_FLOWCTRL); // close (low)
1557*53ee8cc1Swenshuai.xi     }
1558*53ee8cc1Swenshuai.xi #endif
1559*53ee8cc1Swenshuai.xi 
1560*53ee8cc1Swenshuai.xi     // Rx
1561*53ee8cc1Swenshuai.xi     len = _NDS_SC_Read(rcv_ptr, rcv_length, null_filter, use_flow_control, NDS_SC_RX_TIMEOUT);
1562*53ee8cc1Swenshuai.xi     if (len != rcv_length)
1563*53ee8cc1Swenshuai.xi     {
1564*53ee8cc1Swenshuai.xi         return CA_DRIVER_CAN_NOT_PERFORM_FUNCTION_NOW;
1565*53ee8cc1Swenshuai.xi     }
1566*53ee8cc1Swenshuai.xi 
1567*53ee8cc1Swenshuai.xi #if 1 //[VERIFIER]
1568*53ee8cc1Swenshuai.xi //TODO: check if delay necessary and smartcard single test
1569*53ee8cc1Swenshuai.xi     MsOS_DelayTask(5); // yield for ISR_Task
1570*53ee8cc1Swenshuai.xi #endif
1571*53ee8cc1Swenshuai.xi 
1572*53ee8cc1Swenshuai.xi     return CA_OK;
1573*53ee8cc1Swenshuai.xi }
1574*53ee8cc1Swenshuai.xi 
1575*53ee8cc1Swenshuai.xi 
HDICA_AbortSmartCardCommSession(void)1576*53ee8cc1Swenshuai.xi NDS_STATUS HDICA_AbortSmartCardCommSession (void)
1577*53ee8cc1Swenshuai.xi {
1578*53ee8cc1Swenshuai.xi     NDS_FUNC("[%s]-[%d] \n", __FUNCTION__, __LINE__);
1579*53ee8cc1Swenshuai.xi 
1580*53ee8cc1Swenshuai.xi     printf("HDICA_AbortSmartCardCommSession\n");
1581*53ee8cc1Swenshuai.xi 
1582*53ee8cc1Swenshuai.xi     _nds_sc_dev.bAborting = TRUE;
1583*53ee8cc1Swenshuai.xi //tt
1584*53ee8cc1Swenshuai.xi     // disable flow control
1585*53ee8cc1Swenshuai.xi     _NDS_SC_CLR_CTRL(CAM_UART_CTRL_FLOWCTRL); // open (high)
1586*53ee8cc1Swenshuai.xi //tt
1587*53ee8cc1Swenshuai.xi 
1588*53ee8cc1Swenshuai.xi     _NDS_SC_ResetFifo();
1589*53ee8cc1Swenshuai.xi 
1590*53ee8cc1Swenshuai.xi     _nds_sc_dev.bAborting = FALSE;
1591*53ee8cc1Swenshuai.xi 
1592*53ee8cc1Swenshuai.xi     return CA_OK;
1593*53ee8cc1Swenshuai.xi }
1594*53ee8cc1Swenshuai.xi 
1595*53ee8cc1Swenshuai.xi 
1596