FreeCalypso > hg > fc-tourmaline
comparison src/cs/drivers/drv_core/abb/abb.c @ 0:4e78acac3d88
src/{condat,cs,gpf,nucleus}: import from Selenite
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Fri, 16 Oct 2020 06:23:26 +0000 |
parents | |
children | d00662aa64d8 |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:4e78acac3d88 |
---|---|
1 /**********************************************************************************/ | |
2 /* TEXAS INSTRUMENTS INCORPORATED PROPRIETARY INFORMATION */ | |
3 /* */ | |
4 /* Property of Texas Instruments -- For Unrestricted Internal Use Only */ | |
5 /* Unauthorized reproduction and/or distribution is strictly prohibited. This */ | |
6 /* product is protected under copyright law and trade secret law as an */ | |
7 /* unpublished work. Created 1987, (C) Copyright 1997 Texas Instruments. All */ | |
8 /* rights reserved. */ | |
9 /* */ | |
10 /* */ | |
11 /* Filename : abb.c */ | |
12 /* */ | |
13 /* Description : Functions to drive the ABB device. */ | |
14 /* The Serial Port Interface is used to connect the TI */ | |
15 /* Analog BaseBand (ABB). */ | |
16 /* It is assumed that the ABB is connected as the SPI */ | |
17 /* device 0. */ | |
18 /* */ | |
19 /* Author : Pascal PUEL */ | |
20 /* */ | |
21 /* Version number : 1.3 */ | |
22 /* */ | |
23 /* Date and time : 08/22/03 */ | |
24 /* */ | |
25 /* Previous delta : Creation */ | |
26 /* */ | |
27 /**********************************************************************************/ | |
28 | |
29 #include "l1sw.cfg" | |
30 | |
31 #include "chipset.cfg" | |
32 #include "board.cfg" | |
33 #include "rf.cfg" | |
34 #include "swconfig.cfg" | |
35 #include "sys.cfg" | |
36 #include "abb.h" | |
37 #include "l1_macro.h" | |
38 #include "l1_confg.h" | |
39 #include "clkm/clkm.h" // for wait_ARM_cycles function | |
40 #include "abb_inline.h" | |
41 #include "ulpd/ulpd.h" // for FRAME_STOP definition | |
42 #include "nucleus.h" // for NUCLEUS functions and types | |
43 #include "l1_types.h" | |
44 | |
45 #if (OP_L1_STANDALONE == 0) | |
46 #include "main/sys_types.h" | |
47 #include "rv/general.h" | |
48 #include "buzzer/buzzer.h" // for BZ_KeyBeep_OFF function | |
49 #else | |
50 #include "sys_types.h" | |
51 #endif | |
52 | |
53 #if (VCXO_ALGO == 1) | |
54 #include "l1_ctl.h" | |
55 #endif | |
56 | |
57 #if (RF_FAM == 35) | |
58 #include "l1_rf35.h" | |
59 #endif | |
60 | |
61 #if (RF_FAM == 12) | |
62 #include "tpudrv12.h" | |
63 #include "l1_rf12.h" | |
64 #endif | |
65 | |
66 #if (RF_FAM == 10) | |
67 #include "l1_rf10.h" | |
68 #endif | |
69 | |
70 #if (RF_FAM == 8) | |
71 #include "l1_rf8.h" | |
72 #endif | |
73 | |
74 #if (RF_FAM == 2) | |
75 #include "l1_rf2.h" | |
76 #endif | |
77 | |
78 /* | |
79 * The following conditional compilation control is a FreeCalypso addition. | |
80 * TI's original code always configured the BCICONF register with | |
81 * MESBB and BBCHGEN bits set, enabling both charging and the measurement | |
82 * resistive divider for the backup battery. However, on our primary | |
83 * hw targets (Openmoko GTA02 and our own FCDEV3B) Iota's VBACKUP pin | |
84 * is unconnected, whereas on Mot C139 and Pirelli DP-L10 "alien" hw | |
85 * the VBACKUP situation is unclear. But at least on our known hw | |
86 * with VBACKUP unconnected, it is better to leave backup battery charging | |
87 * and measurement OFF - TI's original config seems to be a drain on | |
88 * the main battery. Therefore, we are going to leave MESBB and BBCHGEN | |
89 * off until and unless we have a hw target where backup battery charging | |
90 * and measurement are appropriate. | |
91 */ | |
92 | |
93 #define ENABLE_BACKUP_BATTERY 0 | |
94 | |
95 /* | |
96 * The following ABB_sleep_allowed global variable is yet another FreeCalypso | |
97 * addition. Here is the issue: some handset boards have the controller/driver | |
98 * chip in the LCD powered from Iota VRIO, which is generally a very sensible | |
99 * arrangement. As one reference example, our 176x220 pixel TFT LCDs which | |
100 * we are considering for our own FC handset draw about 3 mA from their Vci | |
101 * supply which we connect to VRIO - perfectly fine when the regulators are | |
102 * in their normal Active mode. But what about sleep mode? Sleep mode VRIO | |
103 * current limit is only 1 mA, thus the combination of the LCD being on and | |
104 * drawing 3 mA with the ABB in sleep mode is invalid. TI's original code | |
105 * already had a check for VRPCSTS: PWON and RPWON need to be released and | |
106 * the charger needs to be unplugged in order to enter ABB superdeep sleep. | |
107 * We are extending this check with one more condition: ABB_sleep_allowed | |
108 * needs to be nonzero; the intent is that this variable will be set by the | |
109 * code responsible for putting the LCD into its own powerdown mode. | |
110 * This logic is included only for affected targets with LCDs. | |
111 */ | |
112 | |
113 #ifdef CONFIG_TARGET_LUNA | |
114 int ABB_sleep_allowed = 0; | |
115 #endif | |
116 | |
117 #if (ABB_SEMAPHORE_PROTECTION) | |
118 | |
119 static NU_SEMAPHORE abb_sem; | |
120 | |
121 /*-----------------------------------------------------------------------*/ | |
122 /* ABB_Sem_Create() */ | |
123 /* */ | |
124 /* This function creates the Nucleus semaphore to protect ABB accesses */ | |
125 /* against preemption. */ | |
126 /* No check on the result. */ | |
127 /* */ | |
128 /*-----------------------------------------------------------------------*/ | |
129 void ABB_Sem_Create(void) | |
130 { | |
131 // create a semaphore with an initial count of 1 and with FIFO type suspension. | |
132 NU_Create_Semaphore(&abb_sem, "ABB_SEM", 1, NU_FIFO); | |
133 } | |
134 | |
135 #endif // ABB_SEMAPHORE_PROTECTION | |
136 | |
137 /*-----------------------------------------------------------------------*/ | |
138 /* ABB_Wait_IBIC_Access() */ | |
139 /* */ | |
140 /* This function waits for the first IBIC access. */ | |
141 /* */ | |
142 /*-----------------------------------------------------------------------*/ | |
143 void ABB_Wait_IBIC_Access(void) | |
144 { | |
145 #if (ANLG_FAM ==1) | |
146 // Wait 6 OSCAS cycles (100 KHz) for first IBIC access | |
147 // (i.e wait 60us + 10% security marge = 66us) | |
148 wait_ARM_cycles(convert_nanosec_to_cycles(66000)); | |
149 #elif ((ANLG_FAM ==2) || (ANLG_FAM == 3)) | |
150 // Wait 6 x 32 KHz clock cycles for first IBIC access | |
151 // (i.e wait 187us + 10% security marge = 210us) | |
152 wait_ARM_cycles(convert_nanosec_to_cycles(210000)); | |
153 #endif | |
154 } | |
155 | |
156 | |
157 | |
158 /*-----------------------------------------------------------------------*/ | |
159 /* ABB_Write_Register_on_page() */ | |
160 /* */ | |
161 /* This function manages all the spi serial transfer to write to an */ | |
162 /* ABB register on a specified page. */ | |
163 /* */ | |
164 /*-----------------------------------------------------------------------*/ | |
165 void ABB_Write_Register_on_page(SYS_UWORD16 page, SYS_UWORD16 reg_id, SYS_UWORD16 value) | |
166 { | |
167 volatile SYS_UWORD16 status; | |
168 | |
169 // Start spi clock, mask IT for WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
170 SPI_Ready_for_WR | |
171 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
172 | |
173 #if ((ABB_SEMAPHORE_PROTECTION == 1) || (ABB_SEMAPHORE_PROTECTION == 2) || (ABB_SEMAPHORE_PROTECTION == 3)) | |
174 | |
175 // check if the semaphore has been correctly created and try to obtain it. | |
176 // if the semaphore cannot be obtained, the task is suspended and then resumed | |
177 // as soon as the semaphore is released. | |
178 if(&abb_sem != 0) | |
179 { | |
180 NU_Obtain_Semaphore(&abb_sem, NU_SUSPEND); | |
181 } | |
182 #endif // ABB_SEMAPHORE_PROTECTION | |
183 | |
184 // set the ABB page for register access | |
185 ABB_SetPage(page); | |
186 | |
187 // Write value in reg_id | |
188 ABB_WriteRegister(reg_id, value); | |
189 | |
190 // set the ABB page for register access at page 0 | |
191 ABB_SetPage(PAGE0); | |
192 | |
193 #if ((ABB_SEMAPHORE_PROTECTION == 1) || (ABB_SEMAPHORE_PROTECTION == 2) || (ABB_SEMAPHORE_PROTECTION == 3)) | |
194 // release the semaphore only if it has correctly been created. | |
195 if(&abb_sem != 0) | |
196 { | |
197 NU_Release_Semaphore(&abb_sem); | |
198 } | |
199 #endif // ABB_SEMAPHORE_PROTECTION | |
200 | |
201 // Stop the SPI clock | |
202 #ifdef SPI_CLK_LOW_POWER | |
203 SPI_CLK_DISABLE | |
204 #endif | |
205 } | |
206 | |
207 | |
208 /*-----------------------------------------------------------------------*/ | |
209 /* ABB_Read_Register_on_page() */ | |
210 /* */ | |
211 /* This function manages all the spi serial transfer to read one */ | |
212 /* ABB register on a specified page. */ | |
213 /* */ | |
214 /* Returns the real data value of the register. */ | |
215 /* */ | |
216 /*-----------------------------------------------------------------------*/ | |
217 SYS_UWORD16 ABB_Read_Register_on_page(SYS_UWORD16 page, SYS_UWORD16 reg_id) | |
218 { | |
219 volatile SYS_UWORD16 status; | |
220 SYS_UWORD16 reg_val; | |
221 | |
222 // Start spi clock, mask IT for RD and WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
223 SPI_Ready_for_RDWR | |
224 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
225 | |
226 #if ((ABB_SEMAPHORE_PROTECTION == 1) || (ABB_SEMAPHORE_PROTECTION == 2) || (ABB_SEMAPHORE_PROTECTION == 3)) | |
227 | |
228 // check if the semaphore has been correctly created and try to obtain it. | |
229 // if the semaphore cannot be obtained, the task is suspended and then resumed | |
230 // as soon as the semaphore is released. | |
231 if(&abb_sem != 0) | |
232 { | |
233 NU_Obtain_Semaphore(&abb_sem, NU_SUSPEND); | |
234 } | |
235 #endif // ABB_SEMAPHORE_PROTECTION | |
236 | |
237 /* set the ABB page for register access */ | |
238 ABB_SetPage(page); | |
239 | |
240 /* Read selected ABB register */ | |
241 reg_val = ABB_ReadRegister(reg_id); | |
242 | |
243 /* set the ABB page for register access at page 0 */ | |
244 ABB_SetPage(PAGE0); | |
245 | |
246 #if ((ABB_SEMAPHORE_PROTECTION == 1) || (ABB_SEMAPHORE_PROTECTION == 2) || (ABB_SEMAPHORE_PROTECTION == 3)) | |
247 // release the semaphore only if it has correctly been created. | |
248 if(&abb_sem != 0) | |
249 { | |
250 NU_Release_Semaphore(&abb_sem); | |
251 } | |
252 #endif // ABB_SEMAPHORE_PROTECTION | |
253 | |
254 // Stop the SPI clock | |
255 #ifdef SPI_CLK_LOW_POWER | |
256 SPI_CLK_DISABLE | |
257 #endif | |
258 | |
259 return (reg_val); // Return result | |
260 } | |
261 | |
262 /*------------------------------------------------------------------------*/ | |
263 /* ABB_free_13M() */ | |
264 /* */ | |
265 /* This function sets the 13M clock working in ABB. A wait loop */ | |
266 /* is required to allow first slow access to ABB clock register. */ | |
267 /* */ | |
268 /* WARNING !! : this function must not be protected by semaphore !! */ | |
269 /* */ | |
270 /*------------------------------------------------------------------------*/ | |
271 void ABB_free_13M(void) | |
272 { | |
273 volatile SYS_UWORD16 status; | |
274 | |
275 // Start spi clock, mask IT for WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
276 SPI_Ready_for_WR | |
277 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
278 | |
279 ABB_SetPage(PAGE0); | |
280 | |
281 // This transmission frees the CLK13 in ABB. | |
282 ABB_WriteRegister(TOGBR2, 0x08); | |
283 | |
284 // Wait for first IBIC access | |
285 ABB_Wait_IBIC_Access(); | |
286 | |
287 // SW Workaround : This transmission has to be done twice. | |
288 ABB_WriteRegister(TOGBR2, 0x08); | |
289 | |
290 // Wait for first IBIC access | |
291 ABB_Wait_IBIC_Access(); | |
292 | |
293 // Stop the SPI clock | |
294 #ifdef SPI_CLK_LOW_POWER | |
295 SPI_CLK_DISABLE | |
296 #endif | |
297 } | |
298 | |
299 | |
300 | |
301 /*------------------------------------------------------------------------*/ | |
302 /* ABB_stop_13M() */ | |
303 /* */ | |
304 /* This function stops the 13M clock in ABB. */ | |
305 /* */ | |
306 /*------------------------------------------------------------------------*/ | |
307 void ABB_stop_13M(void) | |
308 { | |
309 volatile SYS_UWORD16 status; | |
310 | |
311 // Start spi clock, mask IT for WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
312 SPI_Ready_for_WR | |
313 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
314 | |
315 ABB_SetPage(PAGE0); | |
316 | |
317 // Set ACTIVMCLK = 0. | |
318 ABB_WriteRegister(TOGBR2, 0x04); | |
319 | |
320 // Wait for first IBIC access | |
321 ABB_Wait_IBIC_Access(); | |
322 | |
323 // Stop the SPI clock | |
324 #ifdef SPI_CLK_LOW_POWER | |
325 SPI_CLK_DISABLE | |
326 #endif | |
327 } | |
328 | |
329 | |
330 | |
331 /*------------------------------------------------------------------------*/ | |
332 /* ABB_Read_Status() */ | |
333 /* */ | |
334 /* This function reads and returns the value of VRPCSTS ABB register. */ | |
335 /* */ | |
336 /*------------------------------------------------------------------------*/ | |
337 SYS_UWORD16 ABB_Read_Status(void) | |
338 { | |
339 volatile SYS_UWORD16 status; | |
340 SYS_UWORD16 reg_val; | |
341 | |
342 // Start spi clock, mask IT for WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
343 SPI_Ready_for_WR | |
344 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
345 | |
346 #if ((ABB_SEMAPHORE_PROTECTION == 2) || (ABB_SEMAPHORE_PROTECTION == 3)) | |
347 | |
348 // check if the semaphore has been correctly created and try to obtain it. | |
349 // if the semaphore cannot be obtained, the task is suspended and then resumed | |
350 // as soon as the semaphore is released. | |
351 if(&abb_sem != 0) | |
352 { | |
353 NU_Obtain_Semaphore(&abb_sem, NU_SUSPEND); | |
354 } | |
355 #endif // ABB_SEMAPHORE_PROTECTION | |
356 | |
357 ABB_SetPage(PAGE0); | |
358 | |
359 #if (ANLG_FAM == 1) || (ANLG_FAM == 2) | |
360 ABB_SetPage(PAGE0); | |
361 reg_val = ABB_ReadRegister(VRPCSTS); | |
362 #elif (ANLG_FAM == 3) | |
363 ABB_SetPage(PAGE1); | |
364 reg_val = ABB_ReadRegister(VRPCCFG); | |
365 #endif | |
366 | |
367 #if ((ABB_SEMAPHORE_PROTECTION == 2) || (ABB_SEMAPHORE_PROTECTION == 3)) | |
368 // release the semaphore only if it has correctly been created. | |
369 if(&abb_sem != 0) | |
370 { | |
371 NU_Release_Semaphore(&abb_sem); | |
372 } | |
373 #endif // ABB_SEMAPHORE_PROTECTION | |
374 | |
375 // Stop the SPI clock | |
376 #ifdef SPI_CLK_LOW_POWER | |
377 SPI_CLK_DISABLE | |
378 #endif | |
379 | |
380 return (reg_val); | |
381 } | |
382 | |
383 /*------------------------------------------------------------------------*/ | |
384 /* ABB_on() */ | |
385 /* */ | |
386 /* This function configures ABB registers to work in ON condition */ | |
387 /* */ | |
388 /*------------------------------------------------------------------------*/ | |
389 void ABB_on(SYS_UWORD16 modules, SYS_UWORD8 bRecoveryFlag) | |
390 { | |
391 volatile SYS_UWORD16 status; | |
392 #if ((ANLG_FAM ==2) || (ANLG_FAM == 3)) | |
393 SYS_UWORD32 reg; | |
394 #endif | |
395 | |
396 // a possible cause of the recovery is that ABB is on Oscas => switch from Oscas to CLK13 | |
397 if (bRecoveryFlag) | |
398 { | |
399 // RESTITUTE 13MHZ CLOCK TO ABB | |
400 //--------------------------------------------------- | |
401 ABB_free_13M(); | |
402 | |
403 // RESTITUTE 13MHZ CLOCK TO ABB AGAIN (C.F. BUG1719) | |
404 //--------------------------------------------------- | |
405 ABB_free_13M(); | |
406 } | |
407 | |
408 // Start spi clock, mask IT for RD and WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
409 SPI_Ready_for_RDWR | |
410 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
411 | |
412 #if (ABB_SEMAPHORE_PROTECTION == 3) | |
413 | |
414 // check if the semaphore has been correctly created and try to obtain it. | |
415 // if the semaphore cannot be obtained, the task is suspended and then resumed | |
416 // as soon as the semaphore is released. | |
417 if(&abb_sem != 0) | |
418 { | |
419 NU_Obtain_Semaphore(&abb_sem, NU_SUSPEND); | |
420 } | |
421 #endif // ABB_SEMAPHORE_PROTECTION | |
422 | |
423 ABB_SetPage(PAGE0); | |
424 | |
425 // This transmission disables MADC,AFC,VDL,VUL modules. | |
426 ABB_WriteRegister(TOGBR1, 0x0155); | |
427 | |
428 #if (ANLG_FAM == 1) | |
429 // This transmission disables Band gap fast mode Enable BB charge. | |
430 ABB_WriteRegister(VRPCCTL2, 0x1fc); | |
431 | |
432 /* *********** DC/DC enabling selection ************************************************************** */ | |
433 // This transmission changes the register page in OMEGA for usp to pg1. | |
434 ABB_SetPage(PAGE1); | |
435 | |
436 /* Insert here accesses to modify DC/DC parameters. Default is a switching frequency of 240 Khz */ | |
437 { | |
438 SYS_UWORD8 vrpcctrl3_data; | |
439 | |
440 #if (CHIPSET == 9) || (CHIPSET == 10) || (CHIPSET == 11) | |
441 vrpcctrl3_data = 0x007d; // core voltage 1.4V for C035 | |
442 #else | |
443 vrpcctrl3_data = 0x00bd; // core voltage 1.8V for C05 | |
444 #endif | |
445 | |
446 if(modules & DCDC) // check if the DCDC is enabled | |
447 { | |
448 vrpcctrl3_data |= 0x0002; // set DCDCEN | |
449 } | |
450 | |
451 // This access disables the DCDC. | |
452 ABB_WriteRegister(VRPCCTRL3, vrpcctrl3_data); | |
453 } | |
454 | |
455 /* ************************ SELECTION OF TEST MODE FOR ABB **************************************** */ | |
456 /* This test configuration allows visibility on BULENA,BULON,BDLON,BDLENA on test pins */ | |
457 /* ***************************************************************************************************/ | |
458 #if (BOARD==6)&& (ANLG_FAM==1) //BUG01967 to remove access to TAPCTRL (EVA4 board and Nausica) | |
459 // This transmission enables Omega test register. | |
460 ABB_WriteRegister(TAPCTRL, 0x01); | |
461 | |
462 // This transmission select Omega test instruction. | |
463 ABB_WriteRegister(TAPREG, TSPTEST1); | |
464 | |
465 // This transmission disables Omega test register. | |
466 ABB_WriteRegister(TAPCTRL, 0x00); | |
467 #endif | |
468 /* *************************************************************************************************** */ | |
469 | |
470 if (!bRecoveryFlag) // Check recovery status from L1, prevent G23 SIM issue | |
471 { | |
472 // This transmission changes SIM power supply to 3 volts. | |
473 ABB_WriteRegister(VRPCCTRL1, 0x45); | |
474 } | |
475 | |
476 ABB_SetPage(PAGE0); | |
477 | |
478 // This transmission enables selected OMEGA modules. | |
479 ABB_WriteRegister(TOGBR1, (modules & ~DCDC) >> 6); | |
480 | |
481 if(modules & MADC) // check if the ADC is enabled | |
482 { | |
483 // This transmission connects the resistive divider to MB and BB. | |
484 ABB_WriteRegister(BCICTL1, 0x0005); | |
485 } | |
486 #elif ((ANLG_FAM == 2) || (ANLG_FAM == 3)) | |
487 // Restore the ABB checks and debouncing if start on TESTRESETZ | |
488 | |
489 // This transmission changes the register page in the ABB for usp to pg1. | |
490 ABB_SetPage(PAGE1); | |
491 | |
492 // This transmission sets the AFCCK to CKIN/2. | |
493 ABB_WriteRegister(AFCCTLADD, 0x01); | |
494 | |
495 // This transmission enables the tapreg. | |
496 ABB_WriteRegister(TAPCTRL, 0x01); | |
497 | |
498 // This transmission enables access to page 2. | |
499 ABB_WriteRegister(TAPREG, 0x01b); | |
500 | |
501 // This transmission changes the register page in the ABB for usp to pg2. | |
502 ABB_SetPage(PAGE2); | |
503 | |
504 #if (ANLG_FAM == 2) | |
505 // Restore push button environment | |
506 ABB_WriteRegister(0x3C, 0x07); | |
507 | |
508 #elif (ANLG_FAM == 3) | |
509 | |
510 // Restore push button environment | |
511 ABB_WriteRegister(0x3C, 0xBF); | |
512 | |
513 /* ************************ SELECTION OF BBCFG CONFIG FOR ABB 3 PG1_0 *******************************/ | |
514 #if (ANLG_PG == S_PG_10) // SYREN PG1.0 ON ESAMPLE | |
515 ABB_WriteRegister(BBCFG, C_BBCFG); // Initialize transmit register | |
516 #endif | |
517 // This transmission enables access to page 0. | |
518 ABB_SetPage(PAGE0); | |
519 | |
520 // reset bit MSKINT1 , if set by TESTRESET | |
521 reg=ABB_ReadRegister(VRPCSTS) & 0xffe; | |
522 | |
523 ABB_WriteRegister(VRPCSTS, reg); | |
524 | |
525 ABB_SetPage(PAGE2); | |
526 | |
527 // Restore default for BG behavior in sleep mode | |
528 ABB_WriteRegister(VRPCAUX, 0xBF); | |
529 | |
530 // Restore default for deboucing length | |
531 ABB_WriteRegister(VRPCLDO, 0x00F); | |
532 | |
533 // Restore default for INT1 generation, wait time in switch on, checks in switch on | |
534 ABB_WriteRegister(VRPCABBTST, 0x0002); | |
535 | |
536 #endif | |
537 | |
538 // This transmission changes the register page in the ABB for usp to pg1. | |
539 ABB_SetPage(PAGE1); | |
540 | |
541 // This transmission sets tapinst to id code. | |
542 ABB_WriteRegister(TAPREG, 0x0001); | |
543 | |
544 // This transmission disables TAPREG access. | |
545 ABB_WriteRegister(TAPCTRL, 0x00); | |
546 | |
547 // enable BB battery charge BCICONF register, enable test mode to track BDLEN and BULEN windows | |
548 // This transmission enables BB charge and BB bridge connection for BB measurements. | |
549 #if ENABLE_BACKUP_BATTERY | |
550 ABB_WriteRegister(BCICONF, 0x060); | |
551 #else | |
552 ABB_WriteRegister(BCICONF, 0x000); | |
553 #endif | |
554 | |
555 /* ************************ SELECTION OF BBCFG CONFIG FOR ABB 3 PG2_0 *******************************/ | |
556 #if (ANLG_FAM == 3) | |
557 #if (ANLG_PG == S_PG_20) // SYREN PG2.0 ON EVACONSO | |
558 ABB_WriteRegister(BBCFG, C_BBCFG); // Initialize transmit register | |
559 #endif | |
560 #endif | |
561 | |
562 /* ************************ SELECTION OF TEST MODE FOR ABB ******************************************/ | |
563 /* This test configuration allows visibility on test pins TAPCTRL has not to be reset */ | |
564 /* ****************************************************************************************************/ | |
565 | |
566 // This transmission enables the tapreg. | |
567 ABB_WriteRegister(TAPCTRL, 0x01); | |
568 | |
569 // This transmission select ABB test instruction. | |
570 ABB_WriteRegister(TAPREG, TSPEN); | |
571 | |
572 // This transmission changes the register page in ABB for usp to pg0. | |
573 ABB_SetPage(PAGE0); | |
574 | |
575 // This transmission enables selected ABB modules. | |
576 ABB_WriteRegister(TOGBR1, modules >> 6); | |
577 | |
578 // enable MB & BB resistive bridges for measurements | |
579 if(modules & MADC) // check if the ADC is enabled | |
580 { | |
581 // This transmission connects the resistive divider to MB and BB. | |
582 ABB_WriteRegister(BCICTL1, 0x0001); | |
583 } | |
584 | |
585 /********* Sleep definition part ******************/ | |
586 // This transmission changes the register page in the ABB for usp to pg1. | |
587 #if (ANLG_FAM == 2) | |
588 ABB_SetPage(PAGE1); | |
589 | |
590 // update the Delay needed by the ABB before going in deep sleep, and clear previous delay value. | |
591 reg = ABB_ReadRegister(VRPCCFG) & 0x1e0; | |
592 | |
593 ABB_WriteRegister(VRPCCFG, (SLPDLY | reg)); | |
594 | |
595 // update the ABB mask sleep register (regulator disabled in deep sleep), and clear previous mask value. | |
596 reg = ABB_ReadRegister(VRPCMSK) & 0x1e0; | |
597 ABB_WriteRegister(VRPCMSK, (MASK_SLEEP_MODE | reg)); | |
598 #elif (ANLG_FAM == 3) | |
599 Syren_Sleep_Config(NORMAL_SLEEP,SLEEP_BG,SLPDLY); | |
600 #endif | |
601 // This transmission changes the register page in the ABB for usp to pg0. | |
602 ABB_SetPage(PAGE0); | |
603 #endif | |
604 | |
605 // SW workaround for initialization of the audio parts of the ABB to avoid white noise | |
606 // C.f. BUG1941 | |
607 // Set VDLR and VULR bits | |
608 // Write TOGBR1 register | |
609 // This transmission enables selected ABB modules. | |
610 ABB_WriteRegister(TOGBR1, 0x0A); | |
611 | |
612 // wait for 1 ms | |
613 wait_ARM_cycles(convert_nanosec_to_cycles(1000000)); | |
614 | |
615 // Reset VDLS and VULS bits | |
616 // Write TOGBR1 register | |
617 // This transmission enables selected ABB modules. | |
618 ABB_WriteRegister(TOGBR1, 0x05); | |
619 | |
620 #if (ABB_SEMAPHORE_PROTECTION == 3) | |
621 // release the semaphore only if it has correctly been created. | |
622 if(&abb_sem != 0) | |
623 { | |
624 NU_Release_Semaphore(&abb_sem); | |
625 } | |
626 #endif // ABB_SEMAPHORE_PROTECTION | |
627 | |
628 // Stop the SPI clock | |
629 #ifdef SPI_CLK_LOW_POWER | |
630 SPI_CLK_DISABLE | |
631 #endif | |
632 } | |
633 | |
634 | |
635 | |
636 /*-----------------------------------------------------------------------*/ | |
637 /* ABB_Read_ADC() */ | |
638 /* */ | |
639 /* This function manages all the spi serial transfer to read all the */ | |
640 /* ABB ADC conversion channels. */ | |
641 /* Stores the result in Buff parameter. */ | |
642 /* */ | |
643 /*-----------------------------------------------------------------------*/ | |
644 void ABB_Read_ADC(SYS_UWORD16 *Buff) | |
645 { | |
646 volatile SYS_UWORD16 status; | |
647 | |
648 // Start spi clock, mask IT for RD and WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
649 SPI_Ready_for_RDWR | |
650 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
651 | |
652 #if (ABB_SEMAPHORE_PROTECTION == 3) | |
653 | |
654 // check if the semaphore has been correctly created and try to obtain it. | |
655 // if the semaphore cannot be obtained, the task is suspended and then resumed | |
656 // as soon as the semaphore is released. | |
657 if(&abb_sem != 0) | |
658 { | |
659 NU_Obtain_Semaphore(&abb_sem, NU_SUSPEND); | |
660 } | |
661 #endif // ABB_SEMAPHORE_PROTECTION | |
662 | |
663 // This transmission changes the register page in the ABB for usp to pg0. | |
664 ABB_SetPage(PAGE0); | |
665 | |
666 /* Read all ABB ADC registers */ | |
667 *Buff++ = ABB_ReadRegister(VBATREG); | |
668 *Buff++ = ABB_ReadRegister(VCHGREG); | |
669 *Buff++ = ABB_ReadRegister(ICHGREG); | |
670 *Buff++ = ABB_ReadRegister(VBKPREG); | |
671 *Buff++ = ABB_ReadRegister(ADIN1REG); | |
672 *Buff++ = ABB_ReadRegister(ADIN2REG); | |
673 *Buff++ = ABB_ReadRegister(ADIN3REG); | |
674 | |
675 #if (ANLG_FAM ==1) | |
676 *Buff++ = ABB_ReadRegister(ADIN4XREG); | |
677 *Buff++ = ABB_ReadRegister(ADIN5YREG); | |
678 #elif (ANLG_FAM ==2) | |
679 *Buff++ = ABB_ReadRegister(ADIN4REG); | |
680 #elif (ANLG_FAM == 3) | |
681 *Buff++ = ABB_ReadRegister(ADIN4REG); | |
682 *Buff++ = ABB_ReadRegister(ADIN5REG); | |
683 #endif // ANLG_FAM | |
684 | |
685 #if (ABB_SEMAPHORE_PROTECTION == 3) | |
686 // release the semaphore only if it has correctly been created. | |
687 if(&abb_sem != 0) | |
688 { | |
689 NU_Release_Semaphore(&abb_sem); | |
690 } | |
691 #endif // ABB_SEMAPHORE_PROTECTION | |
692 | |
693 // Stop the SPI clock | |
694 #ifdef SPI_CLK_LOW_POWER | |
695 SPI_CLK_DISABLE | |
696 #endif | |
697 } | |
698 | |
699 | |
700 | |
701 /*-----------------------------------------------------------------------*/ | |
702 /* ABB_Conf_ADC() */ | |
703 /* */ | |
704 /* This function manages all the spi serial transfer to: */ | |
705 /* - select the ABB ADC channels to be converted */ | |
706 /* - enable/disable EOC interrupt */ | |
707 /* */ | |
708 /*-----------------------------------------------------------------------*/ | |
709 void ABB_Conf_ADC(SYS_UWORD16 Channels, SYS_UWORD16 ItVal) | |
710 { | |
711 volatile SYS_UWORD16 status; | |
712 SYS_UWORD16 reg_val; | |
713 | |
714 // Start spi clock, mask IT for RD and WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
715 SPI_Ready_for_RDWR | |
716 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
717 | |
718 #if (ABB_SEMAPHORE_PROTECTION == 3) | |
719 | |
720 // check if the semaphore has been correctly created and try to obtain it. | |
721 // if the semaphore cannot be obtained, the task is suspended and then resumed | |
722 // as soon as the semaphore is released. | |
723 if(&abb_sem != 0) | |
724 { | |
725 NU_Obtain_Semaphore(&abb_sem, NU_SUSPEND); | |
726 } | |
727 #endif // ABB_SEMAPHORE_PROTECTION | |
728 | |
729 // This transmission changes the register page in the ABB for usp to pg0. | |
730 ABB_SetPage(PAGE0); | |
731 | |
732 /* select ADC channels to be converted */ | |
733 #if (ANLG_FAM == 1) | |
734 ABB_WriteRegister(MADCCTRL1, Channels); | |
735 #elif ((ANLG_FAM == 2) || (ANLG_FAM == 3)) | |
736 ABB_WriteRegister(MADCCTRL, Channels); | |
737 #endif | |
738 | |
739 reg_val = ABB_ReadRegister(ITMASK); | |
740 | |
741 // This transmission configure the End Of Conversion IT without modifying other bits in the same register. | |
742 if(ItVal == EOC_INTENA) | |
743 ABB_WriteRegister(ITMASK, reg_val & EOC_INTENA); | |
744 else if(ItVal == EOC_INTMASK) | |
745 ABB_WriteRegister(ITMASK, reg_val | EOC_INTMASK); | |
746 | |
747 #if (ABB_SEMAPHORE_PROTECTION == 3) | |
748 // release the semaphore only if it has correctly been created. | |
749 if(&abb_sem != 0) | |
750 { | |
751 NU_Release_Semaphore(&abb_sem); | |
752 } | |
753 #endif // ABB_SEMAPHORE_PROTECTION | |
754 | |
755 // Stop the SPI clock | |
756 #ifdef SPI_CLK_LOW_POWER | |
757 SPI_CLK_DISABLE | |
758 #endif | |
759 } | |
760 | |
761 | |
762 | |
763 | |
764 /*------------------------------------------------------------------------*/ | |
765 /* ABB_sleep() */ | |
766 /* */ | |
767 /* This function disables the DCDC and returns to PAGE 0. It stops then */ | |
768 /* the 13MHz clock in ABB. A wait loop s required to allow */ | |
769 /* first slow access to ABB clock register. */ | |
770 /* */ | |
771 /* WARNING !! : this function must not be protected by semaphore !! */ | |
772 /* */ | |
773 /* Returns AFC value. */ | |
774 /* */ | |
775 /*------------------------------------------------------------------------*/ | |
776 SYS_UWORD32 ABB_sleep(SYS_UWORD8 sleep_performed, SYS_WORD16 afc) | |
777 { | |
778 volatile SYS_UWORD16 status; | |
779 SYS_UWORD32 afcout_index; | |
780 volatile SYS_UWORD16 nb_it; | |
781 SYS_UWORD16 reg_val; | |
782 | |
783 // table for AFC allowed values during Sleep mode. First 5th elements | |
784 // are related to positive AFC values, last 5th to negative ones. | |
785 SYS_UWORD32 Afcout_T[10]= {0x0f,0x1f,0x3f,0x7f,0xff,0x00,0x01,0x03,0x07,0x0f}; | |
786 | |
787 // Start spi clock, mask IT for RD and WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
788 SPI_Ready_for_RDWR | |
789 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
790 | |
791 // COMPUTATION AND PROGRAMMING OF AFC VALUE | |
792 //--------------------------------------------------- | |
793 if(afc & 0x1000) | |
794 afcout_index = ((afc + 512)>>10) + 1; | |
795 else | |
796 afcout_index = (afc + 512)>>10; | |
797 | |
798 if (sleep_performed == FRAME_STOP) // Big sleep | |
799 { | |
800 #if ((ANLG_FAM == 2) || (ANLG_FAM == 3)) | |
801 //////////// ADD HERE IOTA or SYREN CONFIGURATION FOR BIG SLEEP //////////////////////////// | |
802 #endif | |
803 | |
804 } | |
805 else // Deep sleep | |
806 { | |
807 #if(ANLG_FAM == 1) | |
808 // SELECTION OF AFC TEST MODE FOR OMEGA | |
809 //--------------------------------------------------- | |
810 // This test configuration allows access on the AFCOUT register | |
811 ABB_SetPage(PAGE1); | |
812 | |
813 // This transmission enables OMEGA test register. | |
814 ABB_WriteRegister(TAPCTRL, 0x01); | |
815 | |
816 // This transmission selects OMEGA test instruction. | |
817 ABB_WriteRegister(TAPREG, AFCTEST); | |
818 | |
819 // Set AFCOUT to 0. | |
820 ABB_WriteRegister(AFCOUT, 0x00 >> 6); | |
821 | |
822 ABB_SetPage(PAGE0); | |
823 | |
824 #elif (ANLG_FAM == 2) | |
825 // This configuration allows access on the AFCOUT register | |
826 ABB_SetPage(PAGE1); | |
827 | |
828 // Read AFCCTLADD value and enable USP access to AFCOUT register | |
829 reg_val = (ABB_ReadRegister(AFCCTLADD) | 0x04); | |
830 | |
831 ABB_WriteRegister(AFCCTLADD, reg_val); | |
832 | |
833 // Set AFCOUT to 0. | |
834 ABB_WriteRegister(AFCOUT, 0x00); | |
835 | |
836 #if ENABLE_BACKUP_BATTERY | |
837 // Read BCICONF value and cut the measurement bridge of BB cut the BB charge. | |
838 reg_val = ABB_ReadRegister(BCICONF) & 0x039f; | |
839 | |
840 ABB_WriteRegister(BCICONF, reg_val); | |
841 #endif | |
842 | |
843 // Disable the ABB test mode | |
844 ABB_WriteRegister(TAPCTRL, 0x00); | |
845 | |
846 ABB_SetPage(PAGE0); | |
847 | |
848 // Read BCICTL1 value and cut the measurement bridge of MB. | |
849 reg_val = ABB_ReadRegister(BCICTL1) & 0x03fe; | |
850 | |
851 ABB_WriteRegister(BCICTL1, reg_val); | |
852 #endif | |
853 | |
854 #if (ANLG_FAM == 3) // Nothing to be done as MB and BB measurement bridges are automatically disconnected | |
855 // in Syren during sleep mode. BB charge stays enabled | |
856 ABB_SetPage(PAGE1); // Initialize transmit reg_num. This transmission | |
857 // change the register page in IOTA for usp to pg1 | |
858 | |
859 ABB_WriteRegister(TAPCTRL, 0x00); // Disable Syren test mode | |
860 | |
861 ABB_SetPage(PAGE0); | |
862 #endif | |
863 | |
864 // switch off MADC, AFC, AUXDAC, VOICE. | |
865 ABB_WriteRegister(TOGBR1, 0x155); | |
866 | |
867 // Switch off Analog supply LDO | |
868 //----------------------------- | |
869 #if (ANLG_FAM == 1) | |
870 ABB_SetPage(PAGE1); | |
871 | |
872 // Read VRPCCTL3 register value and switch off VR3. | |
873 reg_val = ABB_ReadRegister(VRPCCTRL3) & 0x3df; | |
874 | |
875 ABB_WriteRegister(VRPCCTRL3, reg_val); | |
876 | |
877 #elif (ANLG_FAM == 2) | |
878 // Read VRPCSTS register value and extract status of meaningfull inputs. | |
879 reg_val = ABB_ReadRegister(VRPCSTS) & 0x0070; | |
880 | |
881 #ifdef CONFIG_TARGET_LUNA | |
882 if (reg_val == 0x30 && ABB_sleep_allowed) | |
883 #else | |
884 if (reg_val == 0x30) | |
885 #endif | |
886 { | |
887 // start the SLPDLY counter in order to switch the ABB in sleep mode. This transmission sets IOTA sleep bit. | |
888 ABB_WriteRegister(VRPCDEV, 0x02); | |
889 } | |
890 | |
891 // Dummy transmission to clean of ABB bus. This transmission accesses IOTA address 0 in "read". | |
892 ABB_WriteRegister(0x0000 | 0x0001, 0x0000); | |
893 | |
894 #elif (ANLG_FAM == 3) | |
895 // In Syren there is no need to check for VRPCCFG as wake up prioritys are changed | |
896 // start the SLPDLY counter in order to switch the ABB in sleep mode | |
897 ABB_WriteRegister(VRPCDEV,0x02); // Initialize transmit reg_num. This transmission | |
898 // set Syren sleep bit | |
899 /* | |
900 // Dummy transmission to clean of ABB bus. This transmission accesses SYREN address 0 in "read". | |
901 ABB_WriteRegister(0x0000 | 0x0001, 0x0000); | |
902 */ | |
903 #endif | |
904 | |
905 // Switch to low frequency clock | |
906 ABB_stop_13M(); | |
907 } | |
908 | |
909 // Stop the SPI clock | |
910 #ifdef SPI_CLK_LOW_POWER | |
911 SPI_CLK_DISABLE | |
912 #endif | |
913 | |
914 #if (OP_L1_STANDALONE == 1) | |
915 #if (CHIPSET == 12) | |
916 // GPIO_InitAllPull(ALL_ONE); // enable all GPIO internal pull | |
917 // workaround to set APLL_DIV_CLK( internal PU) at high level | |
918 // by default APLL_DIV_CLK is low pulling 80uA on VRIO | |
919 // *(SYS_UWORD16*) (0xFFFFFD90)= 0x01;//CNTL_APLL_DIV_CLK -> APLL_CLK_DIV != 0 | |
920 // *(SYS_UWORD16*) (0xFFFEF030)= 0x10;// DPLL mode | |
921 #endif | |
922 #endif | |
923 return(Afcout_T[afcout_index]); | |
924 } | |
925 | |
926 | |
927 /*------------------------------------------------------------------------*/ | |
928 /* ABB_wakeup() */ | |
929 /* */ | |
930 /* This function sets the 13MHz clock working in ABB. A wait loop */ | |
931 /* is required to allow first slow access to ABB clock register. */ | |
932 /* Then it re-enables DCDC and returns to PAGE 0. */ | |
933 /* */ | |
934 /* WARNING !! : this function must not be protected by semaphore !! */ | |
935 /* */ | |
936 /*------------------------------------------------------------------------*/ | |
937 void ABB_wakeup(SYS_UWORD8 sleep_performed, SYS_WORD16 afc) | |
938 { | |
939 volatile SYS_UWORD16 status; | |
940 SYS_UWORD16 reg_val; | |
941 | |
942 // Start spi clock, mask IT for RD and WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
943 SPI_Ready_for_RDWR | |
944 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
945 | |
946 if (sleep_performed == FRAME_STOP) // Big sleep | |
947 { | |
948 #if ((ANLG_FAM == 2) || (ANLG_FAM == 3)) | |
949 //////////// ADD HERE IOTA or SYREN CONFIGURATION FOR BIG SLEEP WAKEUP //////////////////////////// | |
950 #endif | |
951 } | |
952 else // Deep sleep | |
953 { | |
954 #if (OP_L1_STANDALONE == 1) | |
955 #if (CHIPSET == 12) | |
956 // restore context from | |
957 // workaround to set APLL_DIV_CLK( internal PU) at high level | |
958 // by default APLL_DIV_CLK is low pulling 80uA on VRIO | |
959 // *(SYS_UWORD16*) (0xFFFFFD90)= 0x00;//CNTL_APLL_DIV_CLK -> APLL_DIV_CLK != 0 | |
960 // *(SYS_UWORD16*) (0xFFFEF030)= 0x00;// DPLL mode | |
961 #endif | |
962 #endif | |
963 | |
964 // Restitutes 13MHZ Clock to ABB | |
965 ABB_free_13M(); | |
966 | |
967 // Switch ON Analog supply LDO | |
968 #if (ANLG_FAM == 1) | |
969 ABB_SetPage(PAGE1); | |
970 | |
971 // Read VRPCCTL3 register value and switch on VR3. | |
972 reg_val = ABB_ReadRegister(VRPCCTRL3) | 0x020; | |
973 | |
974 ABB_WriteRegister(VRPCCTRL3, reg_val); | |
975 ABB_SetPage(PAGE0); | |
976 #endif | |
977 | |
978 // This transmission switches on MADC, AFC. | |
979 ABB_WriteRegister(TOGBR1, 0x280); | |
980 | |
981 // This transmission sets the AUXAFC2. | |
982 ABB_WriteRegister(AUXAFC2, ((afc>>10) & 0x7)); | |
983 | |
984 // This transmission sets the AUXAFC1. | |
985 ABB_WriteRegister(AUXAFC1, (afc & 0x3ff)); | |
986 | |
987 #if (ANLG_FAM == 1) | |
988 // Remove AFC test mode | |
989 ABB_SetPage(PAGE1); | |
990 | |
991 // This transmission select Omega test instruction. | |
992 ABB_WriteRegister(TAPREG, TSPTEST1); | |
993 | |
994 // Disable test mode selection | |
995 // This transmission disables Omega test register. | |
996 ABB_WriteRegister(TAPCTRL, 0x00 >> 6); | |
997 | |
998 ABB_SetPage(PAGE0); | |
999 | |
1000 #elif (ANLG_FAM == 2) | |
1001 ABB_SetPage(PAGE1); | |
1002 | |
1003 // Read AFCCTLADD register value and disable USP access to AFCOUT register. | |
1004 reg_val = ABB_ReadRegister(AFCCTLADD) & ~0x04; | |
1005 | |
1006 ABB_WriteRegister(AFCCTLADD, reg_val); | |
1007 | |
1008 #if ENABLE_BACKUP_BATTERY | |
1009 // Read BCICONF register value and enable BB measurement bridge enable BB charge. | |
1010 reg_val = ABB_ReadRegister(BCICONF) | 0x0060; | |
1011 | |
1012 ABB_WriteRegister(BCICONF, reg_val); | |
1013 #endif | |
1014 | |
1015 | |
1016 /* *************************************************************************************************** */ | |
1017 // update the Delay needed by the ABB before going in deep sleep, and clear previous delay value. | |
1018 reg_val = ABB_ReadRegister(VRPCCFG) & 0x1e0; | |
1019 ABB_WriteRegister(VRPCCFG, (SLPDLY | reg_val)); | |
1020 | |
1021 // Enable the ABB test mode | |
1022 ABB_WriteRegister(TAPCTRL, 0x01); | |
1023 ABB_WriteRegister(TAPREG, TSPEN); | |
1024 ABB_SetPage(PAGE0); | |
1025 | |
1026 // Read BCICTL1 register value and enable MB measurement bridge and cut the measurement bridge of MB. | |
1027 reg_val = ABB_ReadRegister(BCICTL1) | 0x0001; | |
1028 | |
1029 ABB_WriteRegister(BCICTL1, reg_val); | |
1030 #endif | |
1031 | |
1032 #if (ANLG_FAM == 3) | |
1033 | |
1034 ABB_SetPage(PAGE1); | |
1035 | |
1036 /* *************************************************************************************************** */ | |
1037 // update the Delay needed by the ABB before going in deep sleep, and clear previous delay value. | |
1038 reg_val = ABB_ReadRegister(VRPCCFG) & 0x1e0; | |
1039 ABB_WriteRegister(VRPCCFG, (SLPDLY | reg_val)); | |
1040 | |
1041 /* ************************ SELECTION OF TEST MODE FOR ABB=3 *****************************************/ | |
1042 /* This test configuration allows visibility on test pins TAPCTRL has not to be reset */ | |
1043 /* ****************************************************************************************************/ | |
1044 | |
1045 ABB_WriteRegister(TAPCTRL, 0x01); // Initialize the transmit register | |
1046 // This transmission enables IOTA test register | |
1047 | |
1048 ABB_WriteRegister(TAPREG, TSPEN); | |
1049 // This transmission select IOTA test instruction | |
1050 // This transmission select IOTA test instruction | |
1051 /**************************************************************************************************** */ | |
1052 | |
1053 ABB_SetPage(PAGE0); // Initialize transmit reg_num. This transmission | |
1054 #endif | |
1055 } | |
1056 | |
1057 // Stop the SPI clock | |
1058 #ifdef SPI_CLK_LOW_POWER | |
1059 SPI_CLK_DISABLE | |
1060 #endif | |
1061 } | |
1062 | |
1063 /*------------------------------------------------------------------------*/ | |
1064 /* ABB_wa_VRPC() */ | |
1065 /* */ | |
1066 /* This function initializes the VRPCCTRL1 or VRPCSIM register */ | |
1067 /* according to the ABB used. */ | |
1068 /* */ | |
1069 /*------------------------------------------------------------------------*/ | |
1070 void ABB_wa_VRPC(SYS_UWORD16 value) | |
1071 { | |
1072 volatile SYS_UWORD16 status; | |
1073 | |
1074 // Start spi clock, mask IT for WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
1075 SPI_Ready_for_WR | |
1076 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
1077 | |
1078 #if ((ABB_SEMAPHORE_PROTECTION == 1) || (ABB_SEMAPHORE_PROTECTION == 2) || (ABB_SEMAPHORE_PROTECTION == 3)) | |
1079 | |
1080 // check if the semaphore has been correctly created and try to obtain it. | |
1081 // if the semaphore cannot be obtained, the task is suspended and then resumed | |
1082 // as soon as the semaphore is released. | |
1083 if(&abb_sem != 0) | |
1084 { | |
1085 NU_Obtain_Semaphore(&abb_sem, NU_SUSPEND); | |
1086 } | |
1087 #endif // ABB_SEMAPHORE_PROTECTION | |
1088 | |
1089 ABB_SetPage(PAGE1); | |
1090 | |
1091 #if (ANLG_FAM == 1) | |
1092 // This transmission initializes the VRPCCTL1 register. | |
1093 ABB_WriteRegister(VRPCCTRL1, value); | |
1094 | |
1095 #elif (ANLG_FAM == 2) | |
1096 // This transmission initializes the VRPCSIM register. | |
1097 ABB_WriteRegister(VRPCSIM, value); | |
1098 | |
1099 #elif (ANLG_FAM == 3) | |
1100 // This transmission initializes the VRPCSIMR register. | |
1101 ABB_WriteRegister(VRPCSIMR, value); | |
1102 | |
1103 #endif | |
1104 | |
1105 ABB_SetPage(PAGE0); | |
1106 | |
1107 #if ((ABB_SEMAPHORE_PROTECTION == 1) || (ABB_SEMAPHORE_PROTECTION == 2) || (ABB_SEMAPHORE_PROTECTION == 3)) | |
1108 // release the semaphore only if it has correctly been created. | |
1109 if(&abb_sem != 0) | |
1110 { | |
1111 NU_Release_Semaphore(&abb_sem); | |
1112 } | |
1113 #endif // ABB_SEMAPHORE_PROTECTION | |
1114 | |
1115 // Stop the SPI clock | |
1116 #ifdef SPI_CLK_LOW_POWER | |
1117 SPI_CLK_DISABLE | |
1118 #endif | |
1119 } | |
1120 | |
1121 | |
1122 /*-----------------------------------------------------------------------*/ | |
1123 /* ABB_Write_Uplink_Data() */ | |
1124 /* */ | |
1125 /* This function uses the SPI to write to ABB uplink buffer. */ | |
1126 /* */ | |
1127 /*-----------------------------------------------------------------------*/ | |
1128 void ABB_Write_Uplink_Data(SYS_UWORD16 *TM_ul_data) | |
1129 { | |
1130 SYS_UWORD8 i; | |
1131 volatile SYS_UWORD16 status; | |
1132 | |
1133 // Start spi clock, mask IT for WR and read SPI_REG_STATUS to reset the RE and WE flags. | |
1134 SPI_Ready_for_WR | |
1135 status = * (volatile SYS_UWORD16 *) SPI_REG_STATUS; | |
1136 | |
1137 // Select Page 0 for TOGBR2 | |
1138 ABB_SetPage(PAGE0); | |
1139 | |
1140 // Initialize pointer of burst buffer 1 : IBUFPTR is bit 10 of TOGBR2 | |
1141 ABB_WriteRegister(TOGBR2, 0x10); | |
1142 | |
1143 // Clear, assuming that it works like IBUFPTR of Vega | |
1144 ABB_WriteRegister(TOGBR2, 0x0); | |
1145 | |
1146 // Write the ramp data | |
1147 for (i=0;i<16;i++) | |
1148 ABB_WriteRegister(BULDATA1_2, TM_ul_data[i]>>6); | |
1149 | |
1150 // Stop the SPI clock | |
1151 #ifdef SPI_CLK_LOW_POWER | |
1152 SPI_CLK_DISABLE | |
1153 #endif | |
1154 } | |
1155 | |
1156 //////////////////////// IDEV-INLO integration of sleep mode for Syren /////////////////////////////////////// | |
1157 | |
1158 #if (ANLG_FAM == 3) | |
1159 | |
1160 // Syren Sleep configuration function -------------------------- | |
1161 void Syren_Sleep_Config(SYS_UWORD16 sleep_type,SYS_UWORD16 bg_select, SYS_UWORD16 sleep_delay) | |
1162 { | |
1163 volatile SYS_UWORD16 status,sl_ldo_stat; | |
1164 | |
1165 ABB_SetPage(PAGE1); // Initialize transmit register. This transmission | |
1166 // change the register page in ABB for usp to pg1 | |
1167 | |
1168 ABB_WriteRegister(VRPCCFG, sleep_delay); // write delay value | |
1169 | |
1170 sl_ldo_stat = ((sleep_type<<9|bg_select<<8) & 0x0374); | |
1171 | |
1172 ABB_WriteRegister(VRPCMSKSLP, sl_ldo_stat); // write sleep ldo configuration | |
1173 | |
1174 ABB_SetPage(PAGE0); // Initialize transmit register. This transmission | |
1175 // change the register page in ABB for usp to pg0 | |
1176 } | |
1177 #endif | |
1178 | |
1179 | |
1180 #if (OP_L1_STANDALONE == 0) | |
1181 /*-----------------------------------------------------------------------*/ | |
1182 /* ABB_Power_Off() */ | |
1183 /* */ | |
1184 /* This function uses the SPI to switch off the ABB. */ | |
1185 /* */ | |
1186 /*-----------------------------------------------------------------------*/ | |
1187 void ABB_Power_Off(void) | |
1188 { | |
1189 // Wait until all necessary actions are performed (write in FFS, etc...) to power-off the board (empirical value - 30 ticks). | |
1190 NU_Sleep (30); | |
1191 | |
1192 // Wait also until <ON/OFF> key is released. | |
1193 // This is needed to avoid, if the power key is pressed for a long time, to switch | |
1194 // ON-switch OFF the mobile, until the power key is released. | |
1195 #if((ANLG_FAM == 1) || (ANLG_FAM == 2)) | |
1196 while ((ABB_Read_Status() & ONREFLT) == PWR_OFF_KEY_PRESSED) { | |
1197 #elif(ANLG_FAM == 3) | |
1198 while ((ABB_Read_Register_on_page(PAGE1, VRPCCFG) & PWOND) == PWR_OFF_KEY_PRESSED) { | |
1199 #endif | |
1200 | |
1201 NU_Sleep (1); } | |
1202 | |
1203 BZ_KeyBeep_OFF(); | |
1204 | |
1205 #if(ANLG_FAM == 1) | |
1206 ABB_Write_Register_on_page(PAGE0, VRPCCTL2, 0x00EE); | |
1207 #elif((ANLG_FAM == 2) || (ANLG_FAM == 3)) | |
1208 ABB_Write_Register_on_page(PAGE0, VRPCDEV, 0x0001); | |
1209 #endif | |
1210 } | |
1211 #endif | |
1212 | |
1213 | |
1214 |