source: svn/trunk/newcon3bcm2_21bu/magnum/portinginterface/gio/7552/bgio_priv.c

Last change on this file was 2, checked in by jglee, 11 years ago

first commit

  • Property svn:executable set to *
File size: 15.3 KB
Line 
1/***************************************************************************
2 *     Copyright (c) 2003-2012, Broadcom Corporation
3 *     All Rights Reserved
4 *     Confidential Property of Broadcom Corporation
5 *
6 *  THIS SOFTWARE MAY ONLY BE USED SUBJECT TO AN EXECUTED SOFTWARE LICENSE
7 *  AGREEMENT  BETWEEN THE USER AND BROADCOM.  YOU HAVE NO RIGHT TO USE OR
8 *  EXPLOIT THIS MATERIAL EXCEPT SUBJECT TO THE TERMS OF SUCH AN AGREEMENT.
9 *
10 * $brcm_Workfile: bgio_priv.c $
11 * $brcm_Revision: Hydra_Software_Devel/50 $
12 * $brcm_Date: 4/24/12 3:02p $
13 *
14 * Module Description:
15 *
16 *
17 * Revision History:
18 * $brcm_Log: /magnum/portinginterface/gio/7435/bgio_priv.c $
19 *
20 * Hydra_Software_Devel/50   4/24/12 3:02p tdo
21 * SW7584-10: Add PI/gio support for 7584
22 *
23 * Hydra_Software_Devel/49   6/16/11 5:59p tdo
24 * SWDTV-7592: add BDBG_OBJECT_ASSERT for BGIO.
25 *
26 * Hydra_Software_Devel/48   6/16/11 11:26a tdo
27 * SWDTV-7292: Re-org GIO code
28 *
29 * Hydra_Software_Devel/47   6/7/11 1:22p tdo
30 * SWDTV-7292: Add Magnum PI GIO to 35233
31 *
32 * Hydra_Software_Devel/SWDTV-7288/1   5/26/11 5:16p franli
33 * SWDTV-7288:Correct the GPIO control set for 35233 chip
34 *
35 * Hydra_Software_Devel/46   5/11/11 11:20a tdo
36 * SW7231-139: [BGIO] It is not possible to control GPIO[149:122]
37 *
38 * Hydra_Software_Devel/45   4/8/11 9:40a tdo
39 * SWBLURAY-23686: Add GIO PortingInterface support for Blast (7640) chip
40 *
41 * Hydra_Software_Devel/44   3/21/11 3:47p jhaberf
42 * SW35330-13: Added support for 35233 DTV chip
43 *
44 * Hydra_Software_Devel/43   12/6/10 4:09p jhaberf
45 * SW35230-1: Added 35125 to the build
46 *
47 * Hydra_Software_Devel/42   12/2/10 2:38p tdo
48 * SWBLURAY-23686: Add GIO PortingInterface support for Blast (7640) chip
49 *
50 * Hydra_Software_Devel/41   11/17/10 9:03a tdo
51 * SW7231-11: Add GIO PI support for 7231/7344/7346
52 *
53 * Hydra_Software_Devel/40   11/1/10 5:01p xhuang
54 * SW7552-4: Add 7552 support
55 *
56 * Hydra_Software_Devel/39   8/30/10 3:18p tdo
57 * SW7425-22: Add GIO PI support for 7425
58 *
59 * Hydra_Software_Devel/38   8/12/10 1:00p tdo
60 * SW7358-6: Add support for 7358
61 *
62 * Hydra_Software_Devel/SW7358-6/1   8/12/10 2:48p xhuang
63 * SW7358-6: Add support for 7358 in gio
64 *
65 * Hydra_Software_Devel/37   6/22/10 11:40a vanessah
66 * SW7422-12:  To support appframework. Missing files added:
67 * magnum\portinginterface\pwr rockford\appframework\src\board\97422  To
68 * do list: 1. in framework_board.c, more initialization to be done.  2.
69 * More registers mapping, like clock generation as well as
70 * BCHP_SUN_TOP_CTRL_PIN_MUX_CTRL etc
71 *
72 * Hydra_Software_Devel/36   1/5/10 1:02p jhaberf
73 * SW35230-1: Check in of file on behalf of Srinivasa M.P. Reddy in order
74 * to get 35230 RAP PI compiling
75 *
76 * Hydra_Software_Devel/35   11/19/09 11:14a tdo
77 * SW7468-23: Create GIO PI for 7468
78 *
79 * Hydra_Software_Devel/34   11/18/09 11:36p tdo
80 * SW7408-22: Add GIO PI support for 7408
81 *
82 * Hydra_Software_Devel/33   9/1/09 2:37p yuxiaz
83 * SW7550-28: Add GIO pinmux support for 7125.
84 *
85 * Hydra_Software_Devel/32   9/1/09 11:11a tdo
86 * SW7550-28: Add GIO pinmux support for 7550
87 *
88 * Hydra_Software_Devel/31   8/27/09 6:30p tdo
89 * SW7630-15: Bringup of portinginterface "gio" for Grain (7630) and 7342
90 *
91 * Hydra_Software_Devel/30   6/11/09 9:30p tdo
92 * PR55763: Port Magnum gio module to 97340 chipset
93 *
94 * Hydra_Software_Devel/29   4/27/09 11:07a jhaberf
95 * PR53796: Updating gio build to support BCM35130 DTV chip.
96 *
97 * Hydra_Software_Devel/28   3/23/09 10:01p tdo
98 * PR52975: BGIO PI support for 7635 "Dune" chip
99 *
100 * Hydra_Software_Devel/27   1/27/09 8:37p tdo
101 * PR51627: add VDC 7336 PI support
102 *
103 * Hydra_Software_Devel/26   12/3/08 11:01a tdo
104 * PR49907: incorrect pin mux setting for 7601 GIO
105 *
106 * Hydra_Software_Devel/25   9/16/08 12:15p tdo
107 * PR46945: Fix bug to program sgpio pin when there is no Ext gio pins
108 *
109 * Hydra_Software_Devel/24   9/11/08 11:27a tdo
110 * PR36114: Fix Ext Hi pin to unused for 7325
111 *
112 * Hydra_Software_Devel/23   9/10/08 7:50p tdo
113 * PR46763: Add GIO PI support for 7420
114 *
115 * Hydra_Software_Devel/22   9/10/08 3:46p tdo
116 * PR41941: Basic GIO PI support for 7335B0
117 *
118 * Hydra_Software_Devel/21   7/7/08 6:06p tdo
119 * PR44530: BGIO support for 7601
120 *
121 * Hydra_Software_Devel/20   4/8/08 5:48p tdo
122 * PR41205: Add _isr functions to avoid deadlock
123 *
124 * Hydra_Software_Devel/19   3/5/08 12:32p tdo
125 * PR39459: Basic GIO PI support for 3556
126 *
127 * Hydra_Software_Devel/18   2/27/08 11:55a tdo
128 * PR34956: Re-organize GPIO pin  mux and add 3548 support.
129 *
130 * Hydra_Software_Devel/17   2/14/08 6:25p pntruong
131 * PR34956: Added stub to compile for 3548.
132 *
133 * Hydra_Software_Devel/16   11/20/07 10:53p tdo
134 * PR36883: Add gio PI suppport for 7335
135 *
136 * Hydra_Software_Devel/15   10/15/07 2:29p yuxiaz
137 * PR36114: Added GIO support for 7325.
138 *
139 * Hydra_Software_Devel/14   9/13/07 4:12p syang
140 * PR 30391, PR 32351: clean up OpenDrain pin data set records when it is
141 * destroied or changed to diff type
142 *
143 * Hydra_Software_Devel/13   9/12/07 6:34p syang
144 * PR 30391, PR 32351: guard reg read and modify by kni critical section
145 *
146 * Hydra_Software_Devel/12   9/12/07 5:59p syang
147 * PR 30391, PR 32351: BGIO only init for the pin created by BGIO to avoid
148 * overriding configures by other sw entity; BGIO read from HW reg (no more
149 * sw buffering);
150 *
151 * Hydra_Software_Devel/11   5/18/07 3:20p syang
152 * PR 31356: add gpio PI support for 7440 B0
153 *
154 * Hydra_Software_Devel/10   5/18/07 10:48a yuxiaz
155 * PR30839: Added 7405 support in GIO.
156 *
157 * Hydra_Software_Devel/9   12/29/06 11:31a syang
158 * PR 25750: add 7403 and 7400 B0 support
159 *
160 * Hydra_Software_Devel/8   7/21/06 11:25a syang
161 * PR 22789: added support for gio control set *_EXT_HI and more pins with
162 * control set *_EXT, added suuport for 7118, 3563 and 7440
163 *
164 * Hydra_Software_Devel/7   3/23/06 2:27p syang
165 * PR 19670: added support for 7438 A0
166 *
167 * Hydra_Software_Devel/6   4/20/05 12:56p syang
168 * PR 14421: be able to compile for 3560 now
169 *
170 * Hydra_Software_Devel/5   5/24/04 5:07p jasonh
171 * PR 11189: Merge down from B0 to main-line
172 *
173 * Hydra_Software_Devel/Refsw_Devel_7038_B0/1   5/7/04 5:02p syang
174 * PR 10097: added RST register setting to block interrupt firing when it
175 * is meant to be disabled
176 *
177 * Hydra_Software_Devel/4   4/12/04 5:21p syang
178 * PR 10564: multiply BGIO_P_NUM_LOW_REGS by 4 in BGIO_P_CalcPinRegAndBit
179 *
180 * Hydra_Software_Devel/3   3/15/04 6:29p syang
181 * PR 10097: fixed a problems related to reg index and offset
182 *
183 * Hydra_Software_Devel/2   2/24/04 7:20p syang
184 * PR 9785: more api function implementations are added
185 *
186 * Hydra_Software_Devel/1   2/20/04 11:23a syang
187 * PR 9785: init version
188 *
189 ***************************************************************************/
190
191#include "bgio_priv.h"
192#include "bchp_gio.h"
193#include "bkni.h"
194
195BDBG_MODULE(BGIO);
196
197
198/***************************************************************************
199 *
200 * Utility functions
201 *
202 ***************************************************************************/
203/*--------------------------------------------------------------------------
204 * To be called by BGIO_P_WritePinRegBit and BGIO_P_ReadPinRegBit to calculate the
205 * register offset relative to BGIO_P_REG_BASE and the bit offset
206 * relative to bit 0, based on pin ID.
207 */
208BERR_Code BGIO_P_CalcPinRegAndBit(
209        BGIO_PinId            ePinId,
210        uint32_t              ulRegLow,        /* corresponding reg_low */
211        uint32_t *            pulRegOffset,
212        uint32_t *            pulBitOffset )
213{
214        const BGIO_P_PinSet  *pGioPinSet = BGIO_P_GetPinMapping();
215
216        /* assert para from our private code */
217        BDBG_ASSERT( NULL != pGioPinSet );
218        BDBG_ASSERT( BGIO_PinId_eInvalid > ePinId );
219        BDBG_ASSERT( (BGIO_P_REG_BASE <= ulRegLow) &&
220                                 (ulRegLow <= BGIO_P_REG_LOW_TOP ) );
221        BDBG_ASSERT( NULL != pulRegOffset );
222        BDBG_ASSERT( NULL != pulBitOffset );
223
224        /* calc register and bit offset */
225        if(pGioPinSet->eSetLo != BGIO_PinId_eInvalid &&
226           ePinId < pGioPinSet->eSetHi && ePinId < BGIO_PinId_eSgpio00)
227        {
228                /* _LO */
229                *pulRegOffset = ulRegLow - BGIO_P_REG_BASE;
230                *pulBitOffset = ePinId - pGioPinSet->eSetLo;
231                if(pGioPinSet->ulSetSgio == 0)
232                        *pulBitOffset += pGioPinSet->ulSetSgioShift;
233        }
234        else if(pGioPinSet->eSetHi != BGIO_PinId_eInvalid &&
235                ePinId < pGioPinSet->eSetExt && ePinId < BGIO_PinId_eSgpio00)
236        {
237                /* _HI */
238                *pulRegOffset = (BGIO_P_NUM_LOW_REGS * 4 * 1 + ulRegLow) - BGIO_P_REG_BASE;
239                *pulBitOffset = ePinId - pGioPinSet->eSetHi;
240                if(pGioPinSet->ulSetSgio == 1)
241                        *pulBitOffset += pGioPinSet->ulSetSgioShift;
242        }
243        else if(pGioPinSet->eSetExt != BGIO_PinId_eInvalid &&
244                ePinId < pGioPinSet->eSetExtHi && ePinId < BGIO_PinId_eSgpio00)
245        {
246                /* _EXT */
247                *pulRegOffset = (BGIO_P_NUM_LOW_REGS * 4 * 2 + ulRegLow) - BGIO_P_REG_BASE;
248                *pulBitOffset = (ePinId - pGioPinSet->eSetExt);
249                if(pGioPinSet->ulSetSgio == 2)
250                        *pulBitOffset += pGioPinSet->ulSetSgioShift;
251        }
252        else if(pGioPinSet->eSetExtHi != BGIO_PinId_eInvalid &&
253                ePinId < pGioPinSet->eSetExt2 && ePinId < BGIO_PinId_eSgpio00)
254        {
255                /* _EXT_HI */
256                *pulRegOffset = (BGIO_P_NUM_LOW_REGS * 4 * 3 + ulRegLow) - BGIO_P_REG_BASE;
257                *pulBitOffset = ePinId - pGioPinSet->eSetExtHi;
258                if(pGioPinSet->ulSetSgio == 3)
259                        *pulBitOffset += pGioPinSet->ulSetSgioShift;
260        }
261        else if(pGioPinSet->eSetExt2 != BGIO_PinId_eInvalid && ePinId < BGIO_PinId_eSgpio00)
262        {
263                /* _EXT2 */
264                *pulRegOffset = (BGIO_P_NUM_LOW_REGS * 4 * 4 + ulRegLow) - BGIO_P_REG_BASE;
265                *pulBitOffset = ePinId - pGioPinSet->eSetExt2;
266                if(pGioPinSet->ulSetSgio == 4)
267                        *pulBitOffset += pGioPinSet->ulSetSgioShift;
268        }
269        else if(ePinId < BGIO_PinId_eAgpio00)
270        {
271                /* special gpio pins */
272                *pulRegOffset = (BGIO_P_NUM_LOW_REGS * 4 * pGioPinSet->ulSetSgio + ulRegLow) - BGIO_P_REG_BASE;
273                *pulBitOffset = ePinId - BGIO_PinId_eSgpio00;
274        }
275        else if(ePinId < BGIO_PinId_eAsgpio00)
276        {
277                /* Aon GPIO */
278                *pulRegOffset = ulRegLow - BGIO_P_REG_BASE;
279                *pulBitOffset = ePinId - BGIO_PinId_eAgpio00;
280        }
281        else
282        {
283                /* Aon SGPIO */
284                *pulRegOffset = (BGIO_P_NUM_LOW_REGS * 4 * 1 + ulRegLow) - BGIO_P_REG_BASE;
285                *pulBitOffset = ePinId - BGIO_PinId_eAsgpio00;
286        }
287
288        return BERR_SUCCESS;
289}
290
291/*--------------------------------------------------------------------------
292 * To be called to write the GPIO pin's bit into one register
293 */
294BERR_Code BGIO_P_WritePinRegBit(
295        BGIO_Handle           hGpio,
296        BGIO_PinId            ePinId,
297        BGIO_PinType          ePinType,
298        uint32_t              ulRegLow,
299        BGIO_PinValue         ePinValue,
300        bool                  bInIsr )
301{
302        BERR_Code eResult = BERR_SUCCESS;
303        uint32_t  ulRegOffset, ulBitOffset;
304        uint32_t  ulRegValue;
305        uint32_t  ulRegIndex = 0;
306        uint32_t  ulOpenDrainSet = 0;
307        uint32_t  ulRegBase = (ePinId < BGIO_PinId_eAgpio00) ? BGIO_P_REG_BASE : BGIO_P_AON_BASE;
308
309        /* check input para */
310        BDBG_OBJECT_ASSERT(hGpio, BGIO);
311        BDBG_ASSERT( BGIO_PinId_eInvalid > ePinId );
312        BDBG_ASSERT( (BGIO_P_REG_BASE <= ulRegLow) &&
313                                 (ulRegLow <= BGIO_P_REG_LOW_TOP ) );
314        BDBG_ASSERT( BGIO_PinValue_eInvalid > ePinValue );
315
316        /* read the HW register and modify it for this setting */
317        eResult = BGIO_P_CalcPinRegAndBit( ePinId, ulRegLow,
318                                                                           &ulRegOffset, &ulBitOffset );
319        BDBG_ASSERT( BERR_SUCCESS == eResult );
320        if(!bInIsr)
321        {
322                BKNI_EnterCriticalSection();
323        }
324        ulRegValue = BREG_Read32( hGpio->hRegister, ulRegBase + ulRegOffset );
325
326        /* for the data of other pins of open drain type, we can not write 0 only if HW
327         * reading returns 0, since it might be due to that some other device is pulling
328         * down the bus */
329        if (BCHP_GIO_DATA_LO == ulRegLow)
330        {
331                ulRegIndex = ulRegOffset / 4;
332                ulOpenDrainSet = hGpio->aulOpenDrainSet[ulRegIndex];
333                ulRegValue = ulRegValue | ulOpenDrainSet;
334        }
335
336        /* set new value to the bit */
337        ulRegValue = ulRegValue & (~ BGIO_P_BIT_MASK(ulBitOffset));
338        ulRegValue = (ePinValue << ulBitOffset) | ulRegValue;
339
340        /* write to HW */
341        BREG_Write32( hGpio->hRegister, ulRegBase + ulRegOffset, ulRegValue );
342        if(!bInIsr)
343        {
344                BKNI_LeaveCriticalSection();
345        }
346
347        BDBG_MSG(("Write: RegAddr=0x%08x, RegValue=0x%08x", ulRegBase + ulRegOffset, ulRegValue));
348
349        /* record open drain pin data set for future modification to this register by some other pin */
350        if ((BCHP_GIO_DATA_LO == ulRegLow) && (BGIO_PinType_eOpenDrain == ePinType))
351        {
352                hGpio->aulOpenDrainSet[ulRegIndex] =
353                        (ulOpenDrainSet & (~ BGIO_P_BIT_MASK(ulBitOffset))) | (ePinValue << ulBitOffset);
354        }
355
356        return BERR_TRACE(eResult);
357}
358
359/*--------------------------------------------------------------------------
360 * To be called to write the GPIO pin's bit into one register
361 */
362BERR_Code BGIO_P_ReadPinRegBit(
363        BGIO_Handle           hGpio,
364        BGIO_PinId            ePinId,
365        uint32_t              ulRegLow,
366        BGIO_PinValue *       pePinValue )
367{
368        BERR_Code eResult = BERR_SUCCESS;
369        uint32_t  ulRegOffset, ulBitOffset;
370        uint32_t  ulRegValue;
371        BGIO_PinValue  ePinValue;
372        uint32_t  ulRegBase = (ePinId < BGIO_PinId_eAgpio00) ? BGIO_P_REG_BASE : BGIO_P_AON_BASE;
373
374        /* check input para */
375        BDBG_OBJECT_ASSERT(hGpio, BGIO);
376        BDBG_ASSERT( BGIO_PinId_eInvalid > ePinId );
377        BDBG_ASSERT( (BGIO_P_REG_BASE <= ulRegLow) &&
378                                 (ulRegLow <= BGIO_P_REG_LOW_TOP ) );
379        BDBG_ASSERT( NULL != pePinValue );
380
381        /* read the HW reg
382         * note: should not modify pGpio's records for this register based on the
383         * reading from HW, since it might be diff from user's last setting, such
384         * in as open dran case, and pGpio's records for this register will be
385         * used in BGIO_P_WritePinRegBit */
386        eResult = BGIO_P_CalcPinRegAndBit( ePinId, ulRegLow,
387                                                                           &ulRegOffset, &ulBitOffset );
388        BDBG_ASSERT( BERR_SUCCESS == eResult );
389        ulRegValue = BREG_Read32( hGpio->hRegister, ulRegBase + ulRegOffset );
390        ePinValue = (ulRegValue & BGIO_P_BIT_MASK(ulBitOffset)) >> ulBitOffset;
391
392        BDBG_MSG(("Read: RegAddr=0x%08x, RegValue=0x%08x", ulRegBase + ulRegOffset, ulRegValue));
393
394        *pePinValue = ePinValue;
395        return BERR_TRACE(eResult);
396}
397
398/***************************************************************************
399 * To be called to add a pin handle into the pin list in BGIO's main
400 * context
401 */
402BERR_Code BGIO_P_AddPinToList(
403        BGIO_Handle           hGpio,
404        BGIO_Pin_Handle       hPin )
405{
406
407        BDBG_OBJECT_ASSERT(hGpio, BGIO);
408        BDBG_OBJECT_ASSERT(hPin, BGIO_PIN);
409
410        /* add to the head */
411        BLST_D_INSERT_HEAD(&hGpio->PinHead , hPin, Link);
412        return BERR_SUCCESS;
413}
414
415/***************************************************************************
416 * To be called to remove a pin handle from the pin list in BGIO's main
417 * context
418 */
419BERR_Code BGIO_P_RemovePinFromList(
420        BGIO_Handle           hGpio,
421        BGIO_Pin_Handle       hPin )
422{
423        BDBG_OBJECT_ASSERT(hGpio, BGIO);
424        BDBG_OBJECT_ASSERT(hPin, BGIO_PIN);
425        BDBG_ASSERT( BGIO_P_GetPinHandle(hGpio, hPin->ePinId) );
426
427        BLST_D_REMOVE(&hGpio->PinHead, hPin, Link);
428        return BERR_SUCCESS;
429}
430
431/*--------------------------------------------------------------------------
432 * To be called to get the pin handle for a PinId from the pin list in
433 * BGIO's main context. NULL returned if it does not exist.
434 */
435BGIO_Pin_Handle BGIO_P_GetPinHandle(
436        BGIO_Handle           hGpio,
437        BGIO_PinId            ePinId )
438{
439        BGIO_P_Pin_Context *  pPin;
440
441        BDBG_OBJECT_ASSERT(hGpio, BGIO);
442        BDBG_ASSERT( BGIO_PinId_eInvalid > ePinId );
443
444        /* check whether the pin is already being in use */
445        pPin = BLST_D_FIRST(&hGpio->PinHead);
446        while ( NULL != pPin )
447        {
448                if ( pPin->ePinId == ePinId )
449                {
450                        return pPin;
451                }
452                pPin = BLST_D_NEXT(pPin, Link);
453        }
454
455        /* not found */
456        return NULL;
457}
458
459/***************************************************************************
460 * To be called to get the register handle
461 */
462BREG_Handle BGIO_P_GetRegisterHandle(
463        BGIO_Handle           hGpio )
464{
465
466        BDBG_OBJECT_ASSERT(hGpio, BGIO);
467        return hGpio->hRegister;
468}
469
470/* End of File */
471
Note: See TracBrowser for help on using the repository browser.