Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076 #include "chip.h"
00077
00078 #include <assert.h>
00079
00080
00081
00082
00083
00084 #define MASK_STATUS0 0xFFFFFFFC
00085 #define MASK_STATUS1 0xFFFFFFFF
00086
00087
00088
00089
00090
00091
00092
00093 static void _PMC_SwitchMck2PllaClock(void)
00094
00095 {
00096
00097 PMC->PMC_MCKR = (PMC->PMC_MCKR & ~PMC_MCKR_CSS_Msk) | PMC_MCKR_CSS_PLLA_CLK ;
00098
00099
00100 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00101 }
00102
00103
00104
00105
00106 static void _PMC_SwitchMck2MainClock(void)
00107 {
00108
00109 PMC->PMC_MCKR = (PMC->PMC_MCKR & ~PMC_MCKR_CSS_Msk) | PMC_MCKR_CSS_MAIN_CLK ;
00110
00111
00112 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00113 PMC->PMC_MCKR = PMC_MCKR_CSS_MAIN_CLK;
00114 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00115 }
00116
00117
00118
00119
00120 static void _PMC_SwitchMck2SlowClock(void)
00121 {
00122
00123 PMC->PMC_MCKR = (PMC->PMC_MCKR & ~PMC_MCKR_CSS_Msk) | PMC_MCKR_CSS_SLOW_CLK ;
00124
00125
00126 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00127 }
00128
00129
00130
00131
00132
00133
00134 static void _PMC_SetMckPrescaler(uint32_t prescaler)
00135 {
00136
00137 PMC->PMC_MCKR = (PMC->PMC_MCKR & ~PMC_MCKR_PRES_Msk) | prescaler;
00138
00139
00140 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00141 }
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154 void PMC_EnablePeripheral( uint32_t dwId )
00155 {
00156 assert( dwId < 63 ) ;
00157
00158 if ( dwId < 32 ) {
00159 if ( (PMC->PMC_PCSR0 & ((uint32_t)1 << dwId)) == ((uint32_t)1 << dwId) ) {
00160 TRACE_DEBUG( "PMC_EnablePeripheral: clock of peripheral" \
00161 " %u is already enabled\n\r", (unsigned int)dwId ) ;
00162 } else {
00163 PMC->PMC_PCER0 = 1 << dwId ;
00164 }
00165 } else {
00166 dwId -= 32;
00167 if ((PMC->PMC_PCSR1 & ((uint32_t)1 << dwId)) == ((uint32_t)1 << dwId)) {
00168 TRACE_DEBUG( "PMC_EnablePeripheral: clock of peripheral" \
00169 " %u is already enabled\n\r", (unsigned int)(dwId + 32) ) ;
00170 } else {
00171 PMC->PMC_PCER1 = 1 << dwId ;
00172 }
00173 }
00174 }
00175
00176
00177
00178
00179
00180
00181
00182
00183
00184 void PMC_DisablePeripheral( uint32_t dwId )
00185 {
00186 assert( dwId < 63 ) ;
00187
00188 if ( dwId < 32 ) {
00189 if ( (PMC->PMC_PCSR0 & ((uint32_t)1 << dwId)) != ((uint32_t)1 << dwId) ) {
00190 TRACE_DEBUG("PMC_DisablePeripheral: clock of peripheral" \
00191 " %u is not enabled\n\r", (unsigned int)dwId ) ;
00192 } else {
00193 PMC->PMC_PCDR0 = 1 << dwId ;
00194 }
00195 } else {
00196 dwId -= 32 ;
00197 if ( (PMC->PMC_PCSR1 & ((uint32_t)1 << dwId)) != ((uint32_t)1 << dwId) ) {
00198 TRACE_DEBUG( "PMC_DisablePeripheral: clock of peripheral"
00199 " %u is not enabled\n\r", (unsigned int)(dwId + 32) ) ;
00200 } else {
00201 PMC->PMC_PCDR1 = 1 << dwId ;
00202 }
00203 }
00204 }
00205
00206
00207
00208
00209 void PMC_EnableAllPeripherals( void )
00210 {
00211 PMC->PMC_PCER0 = MASK_STATUS0 ;
00212 while ( (PMC->PMC_PCSR0 & MASK_STATUS0) != MASK_STATUS0 ) ;
00213
00214 PMC->PMC_PCER1 = MASK_STATUS1 ;
00215 while ( (PMC->PMC_PCSR1 & MASK_STATUS1) != MASK_STATUS1 ) ;
00216
00217 TRACE_DEBUG( "Enable all periph clocks\n\r" ) ;
00218 }
00219
00220
00221
00222
00223 void PMC_DisableAllPeripherals( void )
00224 {
00225 PMC->PMC_PCDR0 = MASK_STATUS0 ;
00226 while ( (PMC->PMC_PCSR0 & MASK_STATUS0) != 0 ) ;
00227
00228 PMC->PMC_PCDR1 = MASK_STATUS1 ;
00229 while ( (PMC->PMC_PCSR1 & MASK_STATUS1) != 0 ) ;
00230
00231 TRACE_DEBUG( "Disable all periph clocks\n\r" ) ;
00232 }
00233
00234
00235
00236
00237
00238
00239 uint32_t PMC_IsPeriphEnabled( uint32_t dwId )
00240 {
00241 assert( dwId < ID_PERIPH_COUNT ) ;
00242
00243 if ( dwId < 32 ) {
00244 return ( PMC->PMC_PCSR0 & (1 << dwId) ) ;
00245 } else {
00246 return ( PMC->PMC_PCSR1 & (1 << (dwId - 32)) ) ;
00247 }
00248 }
00249
00250
00251
00252
00253
00254 void PMC_EnableExtOsc(void)
00255 {
00256 uint32_t read_MOR;
00257
00258
00259
00260
00261
00262 read_MOR = PMC->CKGR_MOR;
00263 read_MOR &= ~CKGR_MOR_MOSCRCF_Msk;
00264
00265 read_MOR |= (CKGR_MOR_KEY_PASSWD
00266 | CKGR_MOR_MOSCRCF_12_MHz
00267 | CKGR_MOR_MOSCXTEN
00268 | CKGR_MOR_MOSCRCEN
00269 | CKGR_MOR_MOSCXTST(DEFAUTL_MAIN_OSC_COUNT));
00270
00271
00272 PMC->CKGR_MOR = read_MOR;
00273
00274 while( !(PMC->PMC_SR & PMC_SR_MOSCRCS ) );
00275
00276 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00277
00278 read_MOR |= CKGR_MOR_MOSCSEL;
00279
00280
00281 PMC->CKGR_MOR = read_MOR;
00282
00283 while( !(PMC->PMC_SR & PMC_SR_MOSCSELS ) );
00284
00285 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00286 }
00287
00288
00289
00290
00291 void PMC_DisableExtOsc(void)
00292 {
00293 uint32_t read_MOR;
00294
00295 read_MOR = PMC->CKGR_MOR;
00296 read_MOR &= ~CKGR_MOR_MOSCXTEN;
00297 PMC->CKGR_MOR = CKGR_MOR_KEY_PASSWD | read_MOR;
00298 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00299 }
00300
00301
00302
00303
00304 void PMC_SelectExtOsc(void)
00305 {
00306
00307
00308 if ((PMC->CKGR_MOR & CKGR_MOR_MOSCSEL ) == CKGR_MOR_MOSCSEL) {
00309 PMC_DisableIntRC4_8_12MHz();
00310 return;
00311 }
00312
00313 PMC->CKGR_MOR |= CKGR_MOR_MOSCXTEN | CKGR_MOR_KEY_PASSWD;
00314
00315 while(!(PMC->CKGR_MCFR & CKGR_MCFR_MAINFRDY));
00316
00317 PMC->CKGR_MOR |= CKGR_MOR_MOSCSEL | CKGR_MOR_KEY_PASSWD;
00318
00319 while(!(PMC->PMC_SR & PMC_SR_MOSCSELS));
00320
00321 while(!(PMC->PMC_SR & PMC_SR_MCKRDY));
00322 PMC_DisableIntRC4_8_12MHz();
00323 }
00324
00325
00326
00327
00328
00329 void PMC_SelectExtBypassOsc(void)
00330 {
00331 volatile uint32_t timeout;
00332 if((PMC->CKGR_MOR & CKGR_MOR_MOSCXTBY) != CKGR_MOR_MOSCXTBY){
00333 PMC->CKGR_MOR = CKGR_MOR_KEY_PASSWD |
00334 CKGR_MOR_MOSCRCEN |
00335 CKGR_MOR_MOSCXTST(0xFF) |
00336 CKGR_MOR_MOSCXTBY;
00337 PMC->CKGR_MOR |= CKGR_MOR_KEY_PASSWD | CKGR_MOR_MOSCSEL;
00338
00339 while(!(PMC->PMC_SR & PMC_SR_MOSCSELS));
00340
00341 for(timeout = 0; timeout<0xffff;timeout++);
00342 while(!(PMC->CKGR_MCFR & CKGR_MCFR_MAINFRDY));
00343 }
00344 }
00345
00346
00347
00348
00349
00350
00351
00352 void PMC_EnableIntRC4_8_12MHz(uint32_t freqSelect)
00353 {
00354
00355 PMC->CKGR_MOR |= (CKGR_MOR_KEY_PASSWD | CKGR_MOR_MOSCRCEN);
00356
00357
00358 while (!(PMC->PMC_SR & PMC_SR_MOSCRCS));
00359
00360
00361 PMC->CKGR_MOR = (PMC->CKGR_MOR & ~CKGR_MOR_MOSCRCF_Msk) |
00362 CKGR_MOR_KEY_PASSWD | freqSelect;
00363
00364
00365 while (!(PMC->PMC_SR & PMC_SR_MOSCRCS));
00366
00367
00368 PMC->CKGR_MOR = (PMC->CKGR_MOR & ~CKGR_MOR_MOSCSEL) |
00369 CKGR_MOR_KEY_PASSWD;
00370
00371 while(!(PMC->PMC_SR & PMC_SR_MOSCSELS));
00372
00373
00374 while(!(PMC->PMC_SR & PMC_SR_MCKRDY));
00375
00376 }
00377
00378
00379
00380
00381 void PMC_DisableIntRC4_8_12MHz(void)
00382 {
00383 uint32_t read_MOR;
00384
00385 read_MOR = PMC->CKGR_MOR;
00386
00387 read_MOR &= ~CKGR_MOR_MOSCRCF_Msk;
00388 read_MOR &= ~CKGR_MOR_MOSCRCEN;
00389 PMC->CKGR_MOR = CKGR_MOR_KEY_PASSWD | read_MOR;
00390 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00391 }
00392
00393
00394
00395
00396
00397
00398
00399
00400 void PMC_SetPllaClock(uint32_t mul, uint32_t div)
00401 {
00402 if (mul != 0) {
00403
00404 PMC->CKGR_PLLAR = CKGR_PLLAR_ONE
00405 | CKGR_PLLAR_PLLACOUNT(DEFAUTL_PLLA_COUNT)
00406 | CKGR_PLLAR_MULA(mul - 1)
00407 | CKGR_PLLAR_DIVA(div);
00408
00409 while( !(PMC->PMC_SR & PMC_SR_LOCKA) );
00410 } else {
00411 PMC->CKGR_PLLAR = CKGR_PLLAR_ONE;
00412 }
00413 }
00414
00415
00416
00417
00418
00419
00420
00421
00422
00423
00424
00425 void PMC_SetMckSelection(uint32_t clockSource, uint32_t prescaler)
00426 {
00427 switch ( clockSource ) {
00428 case PMC_MCKR_CSS_SLOW_CLK :
00429 _PMC_SwitchMck2SlowClock();
00430 _PMC_SetMckPrescaler(prescaler);
00431 break;
00432
00433 case PMC_MCKR_CSS_MAIN_CLK :
00434 _PMC_SwitchMck2MainClock();
00435 _PMC_SetMckPrescaler(prescaler);
00436 break;
00437
00438 case PMC_MCKR_CSS_PLLA_CLK :
00439 _PMC_SetMckPrescaler(prescaler);
00440 _PMC_SwitchMck2PllaClock();
00441 break ;
00442 }
00443 }
00444
00445
00446
00447
00448 void PMC_DisableAllClocks(void)
00449 {
00450 uint32_t read_reg;
00451
00452 PMC->PMC_SCDR = PMC_SCDR_PCK0 | PMC_SCDR_PCK1 | PMC_SCDR_PCK2 | PMC_SCDR_PCK3 |
00453 PMC_SCDR_PCK4 | PMC_SCDR_PCK5 | PMC_SCDR_PCK6;
00454
00455 _PMC_SwitchMck2MainClock();
00456
00457 PMC->CKGR_PLLAR = PMC->CKGR_PLLAR & ~CKGR_PLLAR_MULA_Msk;
00458
00459 _PMC_SwitchMck2SlowClock();
00460
00461 read_reg = PMC->CKGR_MOR;
00462 read_reg = (read_reg & ~CKGR_MOR_MOSCRCEN) | CKGR_MOR_KEY_PASSWD;
00463
00464
00465 PMC->CKGR_MOR = read_reg;
00466
00467 PMC_DisableAllPeripherals();
00468 }
00469
00470
00471
00472
00473
00474
00475
00476
00477 void PMC_ConfigureMckWithPlla(uint32_t mul, uint32_t div, uint32_t prescaler)
00478 {
00479
00480 _PMC_SwitchMck2MainClock();
00481
00482
00483 PMC_SetPllaClock(mul, div);
00484
00485
00486
00487 while( !(PMC->PMC_SR & PMC_SR_MCKRDY) );
00488
00489
00490 PMC_SetMckSelection(PMC_MCKR_CSS_PLLA_CLK, prescaler);
00491 }
00492
00493
00494
00495
00496
00497
00498
00499
00500
00501 void PMC_EnableXT32KFME(void)
00502 {
00503
00504 uint32_t read_MOR;
00505
00506
00507
00508
00509
00510 read_MOR = PMC->CKGR_MOR;
00511
00512 read_MOR |= (CKGR_MOR_KEY_PASSWD |CKGR_MOR_XT32KFME);
00513
00514
00515 PMC->CKGR_MOR = read_MOR;
00516
00517 }
00518
00519
00520
00521
00522
00523
00524
00525
00526 void PMC_ConfigurePCK0(uint32_t MasterClk, uint32_t prescaler)
00527 {
00528 PMC->PMC_SCDR = PMC_SCDR_PCK0;
00529
00530 while((PMC->PMC_SCSR)& PMC_SCSR_PCK0);
00531 PMC->PMC_PCK[0] = MasterClk | prescaler;
00532 PMC->PMC_SCER = PMC_SCER_PCK0;
00533 while(!((PMC->PMC_SR) & PMC_SR_PCKRDY0));
00534
00535 }
00536
00537
00538
00539
00540
00541
00542
00543
00544
00545 void PMC_ConfigurePCK1(uint32_t MasterClk, uint32_t prescaler)
00546 {
00547 PMC->PMC_SCDR = PMC_SCDR_PCK1;
00548
00549 while((PMC->PMC_SCSR)& PMC_SCSR_PCK1);
00550 PMC->PMC_PCK[1] = MasterClk | prescaler;
00551 PMC->PMC_SCER = PMC_SCER_PCK1;
00552 while(!((PMC->PMC_SR) & PMC_SR_PCKRDY1));
00553
00554 }
00555
00556
00557
00558
00559
00560
00561
00562
00563 void PMC_ConfigurePCK2(uint32_t MasterClk, uint32_t prescaler)
00564 {
00565 PMC->PMC_SCDR = PMC_SCDR_PCK2;
00566
00567 while((PMC->PMC_SCSR)& PMC_SCSR_PCK2);
00568 PMC->PMC_PCK[2] = MasterClk | prescaler;
00569 PMC->PMC_SCER = PMC_SCER_PCK2;
00570 while(!((PMC->PMC_SR) & PMC_SR_PCKRDY2));
00571
00572 }