⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 pwmpdd.c

📁 Microsoft WinCE 6.0 BSP FINAL release source code for use with the i.MX27ADS TO2 WCE600_FINAL_MX27_S
💻 C
字号:
//------------------------------------------------------------------------------
//
//  Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
//  Use of this source code is subject to the terms of the Microsoft end-user
//  license agreement (EULA) under which you licensed this SOFTWARE PRODUCT.
//  If you did not accept the terms of the EULA, you are not authorized to use
//  this source code. For a copy of the EULA, please see the LICENSE.RTF on
//  your install media.
//
//------------------------------------------------------------------------------
//
//  Copyright (C) 2004, Motorola Inc. All Rights Reserved
//
//-----------------------------------------------------------------------------
//
//  Copyright (C) 2004-2006, Freescale Semiconductor, Inc. All Rights Reserved.
//  THIS SOURCE CODE, AND ITS USE AND DISTRIBUTION, IS SUBJECT TO THE TERMS
//  AND CONDITIONS OF THE APPLICABLE LICENSE AGREEMENT 
//
//-----------------------------------------------------------------------------
//
//  File:  pwmpdd.c
//
//  Implementation of PWM Driver Platform Device Driver
//
//  This file implements the device specific functions for PWM.
//
//------------------------------------------------------------------------------
#include <windows.h>
#include <nkintr.h>
#include <ceddk.h>
#include "csp.h"
#include "pwmdefs.h"

//------------------------------------------------------------------------------
// External Variables
//------------------------------------------------------------------------------
extern UINT32 BSPSetPWMClockSource(void);
extern void BSPPwmIomuxSetPin(void);
extern BOOL BSPPwmSetClockGatingMode(BOOL);

//------------------------------------------------------------------------------
// Defines
//------------------------------------------------------------------------------
#define PWMPRESCALER_VAL        0   // divide by 1
#define PWMWATERMARK_VAL        0   // FIFO empty flag is set when there are
                                    // more than or equal to 1 empty slots in FIFO
#define PWMOUTCONFIG_VAL        0   // output pin is set at rollover and cleared at comparsion
#define PWMSAMPLEREPEAT_VAL     0   // use each sample once
#define UPPER_LIMIT          65535  // upper limit of 16bits register
//------------------------------------------------------------------------------
// Types
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
// Global Variables
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
// Local Variables
//------------------------------------------------------------------------------
static PCSP_PWM_REG g_pPwm;
static CRITICAL_SECTION g_hPwmLock;
//------------------------------------------------------------------------------
// Local Functions
//------------------------------------------------------------------------------
static void Reset(void);
//------------------------------------------------------------------------------
//
// Function: PwmStart
//
// This function is used to start the Pwm. It will set the enable
// bit in pwm control register. This function should be called to
// enable the pwm after configuring the pwm.
//
// Parameters:
//      None
//
// Returns:
//      None
//
//------------------------------------------------------------------------------
void PwmStart(void)
{
     DEBUGMSG(ZONE_FUNCTION, (TEXT("++PwmStart\r\n")));

     // Enable the pwm
    INSREG32(&g_pPwm->PWM_CR, CSP_BITFMASK(PWM_CR_EN), CSP_BITFVAL(PWM_CR_EN, PWM_CR_EN_ENABLE));
    DEBUGMSG(ZONE_FUNCTION, (TEXT("--PwmStart\r\n")));
}


//------------------------------------------------------------------------------
//
// Function: PwmStop
//
// This function stops the Pwm. It will
// clear the enable bit in Pwm control register.
//
// Parameters:
//      None
//
// Returns:
//      None
//
//------------------------------------------------------------------------------
void PwmStop(void)
{
    DEBUGMSG(ZONE_FUNCTION, (TEXT("++PwmStop\r\n")));
    // Disable the pwm
   INSREG32(&g_pPwm->PWM_CR, CSP_BITFMASK(PWM_CR_EN),CSP_BITFVAL(PWM_CR_EN, PWM_CR_EN_DISABLE));
   DEBUGMSG(ZONE_FUNCTION, (TEXT("--PwmStop\r\n")));
}

//------------------------------------------------------------------------------
//
// Function: PwmPlaySample
//
// This function is used to play the pwm sample
//
// Parameters:
//      SampleBuffer
//          [in] pwm sample conform to pwmSample_t structure
//
//      SampleSize
//          [in] Size of the pwmSample_t structure
// Returns:
//      TRUE - If success.
//
//      FALSE - If failed
//
//------------------------------------------------------------------------------
BOOL PwmPlaySample(LPCVOID SampleBuffer, int SampleSize )
{

       pPwmSample_t PwmSampleBuffer;
       DWORD dwStartTime, dwElapsedTime;
       DEBUGMSG(ZONE_FUNCTION, (TEXT("++PwmPlaySample\r\n")));

       PwmSampleBuffer = (pPwmSample_t)SampleBuffer;
       // check for the limits of the sample and period
       if(PwmSampleBuffer->sample > UPPER_LIMIT || PwmSampleBuffer->period > UPPER_LIMIT)
              return FALSE;
       if(SampleSize != sizeof(PwmSample_t))
              return FALSE;
       EnterCriticalSection(&g_hPwmLock);
       OUTREG32(&g_pPwm->PWM_SAR, PwmSampleBuffer->sample);
       OUTREG32(&g_pPwm->PWM_PR, PwmSampleBuffer->period);

       PwmStart();

       dwStartTime = GetTickCount();
       do{
             dwElapsedTime = GetTickCount() - dwStartTime;
       }while(dwElapsedTime < PwmSampleBuffer->duration);

       PwmStop();

       LeaveCriticalSection(&g_hPwmLock);
       DEBUGMSG(ZONE_FUNCTION, (TEXT("--PwmPlaySample\r\n")));
       return TRUE;
}

//------------------------------------------------------------------------------
//
// Function: PwmDeinit
//
// Frees up the register space and deletes critical
// section for deinitialization.
//
// Parameters:
//      None
//
// Returns:
//      None
//
//------------------------------------------------------------------------------
void PwmDeinit(void)
{
    DEBUGMSG(ZONE_FUNCTION, (TEXT("++PwmRelease\r\n")));;

    // free the virtual space allocated for PWM memory map
    if (g_pPwm != NULL)
    {
        VirtualFree((void *) g_pPwm, 0, MEM_RELEASE);
        g_pPwm = NULL;
    }

    // Delete the critical section
    DeleteCriticalSection(&g_hPwmLock);

    DEBUGMSG(ZONE_FUNCTION, (TEXT("--PwmRelease\r\n")));;
    return;
}

//------------------------------------------------------------------------------
//
// Function: PwmInitialize
//
// This function will allocate mapping for PWM registers, initialize critical section,
// reset the PWM, and initialize of PWM control register
//
// Parameters:
//      None
//
// Returns:
//      TRUE - If success
//
//      FALSE - If failure
//
//------------------------------------------------------------------------------
BOOL PwmInitialize(void)
{
    PHYSICAL_ADDRESS phyAddr;
    
    
    DEBUGMSG(ZONE_FUNCTION, (TEXT("++PwmInitialize\r\n")));;

    phyAddr.QuadPart = CSP_BASE_REG_PA_PWM;

    g_pPwm = (PCSP_PWM_REG) MmMapIoSpace(phyAddr, sizeof(CSP_PWM_REG), FALSE);

    // check if Map Virtual Address failed
    if (g_pPwm == NULL)
    {
        DEBUGMSG(ZONE_ERROR, (TEXT("PwmInitialize:  MmMapIoSpace failed!\r\n")));
        goto Error;
    }
      
    // Initialize PWM critical section
    InitializeCriticalSection(&g_hPwmLock);

	  BSPPwmIomuxSetPin();
	  BSPPwmSetClockGatingMode(TRUE);
    
    Reset();
    DEBUGMSG(ZONE_FUNCTION, (TEXT("--PwmInitialize\r\n")));;
    return TRUE;

Error:
       PwmDeinit();
      return FALSE;
}

//------------------------------------------------------------------------------
//
// Function: PwmReset
//
// This function will reset PWM.
//
// Parameters:
//      None
//
// Returns:
//      None
//
//------------------------------------------------------------------------------
void PwmReset(void)
{
       DEBUGMSG(ZONE_FUNCTION, (TEXT("++PwmReset\r\n")));

       EnterCriticalSection(&g_hPwmLock);
       Reset();
       LeaveCriticalSection(&g_hPwmLock);

       DEBUGMSG(ZONE_FUNCTION, (TEXT("--PwmReset\r\n")));
}

//------------------------------------------------------------------------------
//
// Function: PwmReadRegister
//
// This function is used to read the current values of all PWM registers
//
// Parameters:
//      readBuf
//          [in] pwm sample conform to pwmSample_t structure
//
//      Count
//      [in] number of uint32 to be read
//
// Returns:
//      TRUE - If success.
//
//      FALSE - If the Pwm is not allocated.
//
//------------------------------------------------------------------------------
BOOL PwmReadRegister(UINT32* readBuf, DWORD Count)
{
       DEBUGMSG(ZONE_FUNCTION, (TEXT("++PwmReadRegister\r\n")));

       EnterCriticalSection(&g_hPwmLock);
        
       if(Count < (6 * sizeof(UINT32))) 
              return FALSE;
       readBuf[0] = INREG32(&g_pPwm->PWM_CR);
       readBuf[1] = INREG32(&g_pPwm->PWM_SR);
       readBuf[2] = INREG32(&g_pPwm->PWM_IR);
       readBuf[3] = INREG32(&g_pPwm->PWM_SAR);
       readBuf[4] = INREG32(&g_pPwm->PWM_PR);
       readBuf[5] = INREG32(&g_pPwm->PWM_CNR);
       
       LeaveCriticalSection(&g_hPwmLock);
       DEBUGMSG(ZONE_FUNCTION, (TEXT("--PwmReadRegister\r\n")));
       return TRUE;

}

//------------------------------------------------------------------------------
//
// Function: Reset
//
// This function is used to trigger a reset in PWM Control Register,
// and load preset value in Control Register
//
// Parameters:
//      none.
//
// Returns:
//      none.
//
//------------------------------------------------------------------------------
static void Reset(void)
{
      UINT32 clkSrc;

       // Disable PWM and clear all configuration bits
      OUTREG32(&g_pPwm->PWM_CR, 0);
       // Assert software reset for the timer
      INSREG32BF(&g_pPwm->PWM_CR, PWM_CR_SWR, PWM_CR_SWR_RESET);
       // Wait for the software reset to complete
      while(EXTREG32BF(&g_pPwm->PWM_CR, PWM_CR_SWR));

     // Get BSP-specific clock source
     clkSrc = BSPSetPWMClockSource();

     OUTREG32(&g_pPwm->PWM_CR,
                        (CSP_BITFVAL(PWM_CR_EN, PWM_CR_EN_DISABLE)) |                        // disables the PWM
                        (CSP_BITFVAL(PWM_CR_REPEAT, PWMSAMPLEREPEAT_VAL)) |       // use sample with no repeat
                        (CSP_BITFVAL(PWM_CR_SWR, PWM_CR_SWR_NORESET)) |                // no SW reset
                        (CSP_BITFVAL(PWM_CR_PRESCALER, PWMPRESCALER_VAL)) |        // prescaler value of 1
                        (CSP_BITFVAL(PWM_CR_CLKSRC, clkSrc)) |                                             // bsp set clock source
                        (CSP_BITFVAL(PWM_CR_POUTC, PWMOUTCONFIG_VAL)) |                // PWM output configuration
                        (CSP_BITFVAL(PWM_CR_HCTR, PWM_CR_HCTR_DISABLE)) |             // no half-word data swap
                        (CSP_BITFVAL(PWM_CR_BCTR, PWM_CR_BCTR_DISABLE)) |              // no byte data swap
                        (CSP_BITFVAL(PWM_CR_DBGEN, PWM_CR_DBGEN_INACTIVE)) |      // pwm inactive in debug mode
                        (CSP_BITFVAL(PWM_CR_WAITEN, PWM_CR_WAITEN_INACTIVE)) |  // pwm inactive in wait mode
                        (CSP_BITFVAL(PWM_CR_DOZEN, PWM_CR_DOZEN_INACTIVE)) |      // pwm inactive in doze mode
                        (CSP_BITFVAL(PWM_CR_STOPEN, PWM_CR_STOPEN_INACTIVE)) |   // pwm inactive in stop mode
                        (CSP_BITFVAL(PWM_CR_FWM, PWMWATERMARK_VAL)));                 // FIFO empty flag set condition

   
       // disable all interrupts
       OUTREG32(&g_pPwm->PWM_IR,
                         (CSP_BITFVAL(PWM_IR_FIE, PWM_IR_FIE_DISABLE)) |
                         (CSP_BITFVAL(PWM_IR_RIE, PWM_IR_RIE_DISABLE)) |
                         (CSP_BITFVAL(PWM_IR_CIE, PWM_IR_CIE_DISABLE)));

       
       // Clear Interrupt Status Bits
       INSREG32(&g_pPwm->PWM_SR, CSP_BITFMASK(PWM_SR_CMP),        CSP_BITFVAL(PWM_SR_CMP, PWM_SR_CMP_STATUS_CLEAR));

}

//------------------------------------------------------------------------------
//
// Function: SetPwmPower
//
// This function is to initiailize the power management for PWM driver.
//
// Parameters:
//      power
//          [in] pointer to POWER_CAPABILITIES structure
//
// Returns:
//      none.
//
//------------------------------------------------------------------------------
void SetPwmPower(PPOWER_CAPABILITIES power)
{
       power->DeviceDx = 0x15;    // D0, D2 & D4

       // supported power & latency info
       power->Power[D0] = PwrDeviceUnspecified;     // mW  
       power->Power[D2] = PwrDeviceUnspecified;     // mW
       power->Power[D4] = PwrDeviceUnspecified;     // mW

       power->Latency[D0] = 0;   // mSec
       power->Latency[D2] = 0;   // mSec
       power->Latency[D4] = 0;   // mSec

       power->WakeFromDx = 0;    // no device wake
       power->InrushDx = 0;      // no inrush
       return;

}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -