|
- //-----------------------------------------------------------------------------
- // F41x_PCA0_8Bit_PWM_Output.c
- //-----------------------------------------------------------------------------
- // Copyright 2006 Silicon Laboratories, Inc.
- //
- // Program Description:
- //
- // This program sends a PWM waveform out of an I/O pin, using the PCA's
- // 8-bit PWM Output Mode. The duty cycle of the waveform is modified
- // periodically within the main loop.
- //
- // In this example, PCA Module 0 is used to generate the waveform, and the 模塊1
- // crossbar is configured to send the CEX0 pin out on P0.0. P0.0端口輸出PWM波
- //
- // How To Test:
- //
- // 1) Download code to a 'F41x device which has an oscilloscope monitoring P0.0
- // 2) Run the program - the waveform should be visible on the oscilloscope.
- // 3) Verify that the duty cycle of the waveform varies smoothly between
- // minimum and maximum values. 占空比在在最大值和最小值間平滑變化
- //
- //
- // FID: 41X000055
- // Target: C8051F41x
- // Tool chain: Keil C51 7.50 / Keil EVAL C51
- // Command Line: None
- //
- //
- // Release 1.0
- // -Initial Revision (BD)
- // -10 MAR 2006
- //
- //-----------------------------------------------------------------------------
- // Includes
- //-----------------------------------------------------------------------------
- #include <c8051f410.h> // SFR declarations 頭文件,單片機端口定義
- //-----------------------------------------------------------------------------
- // Global Constants
- //-----------------------------------------------------------------------------
- #define SYSCLK 24500000 // Internal oscillator frequency in Hz 單片機內部振蕩頻率
- //-----------------------------------------------------------------------------
- // Function Prototypes 振蕩器初始化,端口初始化, PCA定時器初始化
- //-----------------------------------------------------------------------------
- void OSCILLATOR_Init (void);
- void PORT_Init (void);
- void PCA0_Init (void);
- //-----------------------------------------------------------------------------
- // main() Routine 主函數
- //-----------------------------------------------------------------------------
- void main (void)
- {
- unsigned int delay_count; // Used to implement a delay 延時函數
- bit duty_direction = 0; // 0 = Decrease; 1 = Increase 定義占空比變化方向,0代表減小,1代表增大
- PCA0MD = 0x00; // Disable watchdog timer 關閉看門狗,選擇系統時鐘的12分頻作為時間基準
- PORT_Init (); // Initialize crossbar and GPIO 端口初始化
- OSCILLATOR_Init (); // Initialize oscillator 振蕩器初始化
- PCA0_Init (); // Initialize PCA0 PCA定時器初始化
- while (1)
- {
- // Wait a little while
- for (delay_count = 30000; delay_count > 0; delay_count--);
- if (duty_direction == 1) // Direction = Increase
- {
- // First, check the ECOM0 bit ECOM0位是PCA模塊的比較器功能的使能模塊,等于1時有比較器功能
- if ((PCA0CPM0 & 0x40) == 0x00) //與運算
- {
- PCA0CPM0 |= 0x40; // Set ECOM0 if it is '0' 如果ECOM0等于0則將其置位,b|=a等效于b=b|a,按位或,將ECOM0位置1
- }
- else // Increase duty cycle otherwise 否則增加占空比
- {
- PCA0CPH0--; // Increase duty cycle 增加占空比
- if (PCA0CPH0 == 0x00)
- {
- duty_direction = 0; // Change direction for next time 占空比變化反向
- }
- }
- }
- else // Direction = Decrease
- {
- if (PCA0CPH0 == 0xFF)
- {
- PCA0CPM0 &= ~0x40; // Clear ECOM0
- duty_direction = 1; // Change direction for next time
- }
- else
- {
- PCA0CPH0++; // Decrease duty cycle
- }
- }
- };
- }
- //-----------------------------------------------------------------------------
- // Initialization Subroutines
- //-----------------------------------------------------------------------------
- //-----------------------------------------------------------------------------
- // OSCILLATOR_Init 振蕩器時鐘初始化程序
- //-----------------------------------------------------------------------------
- //
- // Return Value : None
- // Parameters : None
- //
- // This function initializes the system clock to use the internal oscillator
- // at 24.5 MHz.
- //
- //-----------------------------------------------------------------------------
- void OSCILLATOR_Init (void)
- {
- OSCICN = 0x87; // Set internal oscillator to run OSCICN是內部振蕩器控制寄存器,將內部振蕩器設為最大振蕩頻率
- // at its maximum frequency
- CLKSEL = 0x00; // Select the internal osc. as CLKSEL是時鐘選擇寄存器,選擇內部振蕩器為系統時鐘源
- // the SYSCLK source
- }
- //-----------------------------------------------------------------------------
- // PORT_Init
- //-----------------------------------------------------------------------------
- //
- // Return Value : None
- // Parameters : None
- //
- // This function configures the crossbar and GPIO ports.
- //
- // P0.0 digital push-pull PCA0 CEX0 端口初始化程序
- //
- //-----------------------------------------------------------------------------
- void PORT_Init (void)
- {
- XBR0 = 0x00; //XBR0 端口I/O交叉控制開關0
- XBR1 = 0x41; // Route CEX0 to P0.0, 交叉使能開關必須使能
- // Enable crossbar and weak pull-ups 端口I/O交叉控制開關1,CEX0連接到端口引腳
- P0MDOUT |= 0x01; // Set CEX0 (P0.0) to push-pull 設置P0.0口為推挽式輸出,推挽式輸出有較大的驅動電流
- }
- //-----------------------------------------------------------------------------
- // PCA0_Init
- //-----------------------------------------------------------------------------
- //
- // Return Value : None
- // Parameters : None
- //
- // This function configures the PCA time base, and sets up 8-bit PWM output
- // mode for Module 0 (CEX0 pin).
- //
- // The frequency of the PWM signal generated at the CEX0 pin is equal to the
- // PCA main timebase frequency divided by 256.
- //
- // The PCA time base in this example is configured to use SYSCLK, and SYSCLK
- // is set up to use the internal oscillator running at 24.5 MHz. Therefore,
- // the frequency of the PWM signal will be 24.5 MHz / 256 = 95.7 kHz.
- // Using different PCA clock sources or a different processor clock will
- // result in a different frequency for the PWM signal.
- //
- // -------------------------------------------------------------------------
- // How "8-Bit PWM Mode" Works:
- //
- // The PCA's 8-bit PWM Mode works by setting an output pin low every
- // time the main PCA counter low byte (PCA0L) overflows, and then setting
- // the pin high whenever a specific match condition is met.
- //
- // Upon a PCA0L overflow (PCA0L incrementing from 0xFF to 0x00), two things
- // happen:
- //
- // 1) The CEXn pin will be set low.
- // 2) The contents of the PCA0CPHn register for the module are copied into
- // the PCA0CPLn register for the module.
- //
- // When the PCA0L register increments and matches the PCA0CPLn register for
- // the selected module, the CEXn pin will be set high, except when the
- // ECOMn bit in PCA0CPMn is cleared to '0'. By varying the value of the
- // PCA0CPHn register, the duty cycle of the waveform can also be varied.
- //
- // When ECOMn = '1', the duty cycle of the PWM waveform is:
- //
- // 8-bit PWM Duty Cycle = (256 - PCA0CPLn) / 256
- //
- // To set the duty cycle to 100%, a value of 0x00 should be loaded into the
- // PCA0CPHn register for the module being used (with ECOMn set to '1').
- // When the value of PCA0CPLn is equal to 0x00, the pin will never be
- // set low.
- //
- // To set the duty cycle to 0%, the ECOMn bit in the PCA0CPMn register
- // should be cleared to 0. This prevents the PCA0CPLn match from occuring,
- // which results in the pin never being set high.
- // -------------------------------------------------------------------------
- //
- //-----------------------------------------------------------------------------
- void PCA0_Init (void)
- {
- // Configure PCA time base; overflow interrupt disabled 配置PCA定時器時鐘基準,關閉溢出中斷
- PCA0CN = 0x00; // Stop counter; clear all flags 關閉PCA計數器,清除所有標志位
- PCA0MD = 0x08; // Use SYSCLK as time base 使用系統時鐘作為PCA定時器的時鐘源,關閉PCA定時器溢出中斷
- PCA0CPM0 = 0x42; // Module 0 = 8-bit PWM mode 設置為8位PWM輸出模式
- // Configure initial PWM duty cycle = 50%
- PCA0CPH0 = 256 - (256 * 0.5); 設置初始的占空比為50%
- // Start PCA counter 通過PCA0CN中的CR位打開PCA定時器
- CR = 1;
- }
- //-----------------------------------------------------------------------------
- // End Of File
- //-----------------------------------------------------------------------------
復制代碼
|
評分
-
查看全部評分
|