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

📄 ffsport_spi.c

📁 The Fat Fs module is a middleware that written in ANSI C. There is no platform dependence, so long a
💻 C
字号:
/***********************************************************
*           MMC/SD-interface to SPI-slot of STR71x         *
*                                                          *
*          by  Frank Goetze  -  www.embedded-os.de         *
************************************************************
*                      FFSPort_MMC.c                       *
*                   MMC/SD TO SPI PORT                     *
************************************************************
*      - code generation            Frank Goetze   09/2007 *
***********************************************************/

/***********************************************************
*   !!! WARNING !!!                                        *
*         on STR71x you can not use the /SS pin of BSPIx   *
*         for manual /SS handling, you will get an BERR    *
*         (Bus Error) on next read-data after setting /SS  *
*         manually low.                                    *
*         using an other pin you have to set the unused    *
*         BSPIx /SS-pin to out-wp and driven high          *
***********************************************************/

#include "../../../inc/MMC/STR71x/FFSPort_SPI.h"

/****************** constant variables ********************/
#define CPU_CRISTAL_CLK  4000000UL                         // processor crystal-clock in Hz

/*
************************************************************
*          set max possible baudrate and return this
************************************************************
*/
U32 FFSPort_MMC_SetBR(U32 maxclk)
{
    U32 s_clksrc;
    U08 d;

    s_clksrc  = CPU_CRISTAL_CLK;                                       // set start-clk (cristal-clk)
    if(STR_PRCCU_CFR & STR_PRCCU_CFR_DIV2) s_clksrc /= 2U;             // is DIV2 active
    if(STR_PRCCU_CFR & STR_PRCCU_CFR_CSU_CKSEL) {                      // if PLL enabled
        while(!(STR_PRCCU_CFR & STR_PRCCU_CFR_LOCK));                  // be shure PLL is locked
        switch((STR_PRCCU_PLL1CR & STR_PRCCU_PLL1CR_MX_MASK) >> 4) {   // mul clk with PLL-multiplier  (defined at startup)
            case 0:  s_clksrc *= 20U; break;
            case 1:  s_clksrc *= 12U; break;
            case 2:  s_clksrc *= 24U; break;
            default:
            case 3:  s_clksrc *= 16U; break;
        }
        s_clksrc /= ((STR_PRCCU_PLL1CR & STR_PRCCU_PLL1CR_DX_MASK) + 1); // div clk with PLL-dividier  (defined at startup)
    } else {
        if(!(STR_PRCCU_CFR & STR_PRCCU_CFR_CK2_16)) {                  // if no PLL in use, check the CLK2/16 use
            s_clksrc /= 16U;
        }
    }
    s_clksrc /= (1U << (STR_PRCCU_PDIVR & STR_PRCCU_PDIVR_FACT1_MASK));  // PDIV for PCLK1 (APB1)
    d = 3;                                                             // div must be grater 5 and alltimes even, so we use d*2
    while((maxclk < (s_clksrc / (2 * d))) && (d < 0x7F)) d++;          // search lowest clk-div for SPI-speed (highest possible SPI-speed)
    STR_BSPI1_CLK = 2 * d;                                             // set SPI-div and return the used SPI-speed in Hz
    return(s_clksrc / (2 * d));                                        // !!! since STR_BSPIx_CLK must be an even-value greater 5...
}                                                                      // ... and the PCLK1 can not be greater than MCLK ...
                                                                       // ... you get not really the highest possible speed !!!
/*
************************************************************
*            write a char and read one back
************************************************************
*/
U08 FFSPort_MMC_Send(U08 w)
{
    while(!(STR_BSPI1_CSR2 & STR_BSPI1_CSR2_TFE));         // wait up to tx-empty
    STR_BSPI1_TXR = (U32)(w) << 8;                         // write char and send
    while(!(STR_BSPI1_CSR2 & STR_BSPI1_CSR2_RFNE));        // wait up to rx-not_empty (char received)
    return((U08)(STR_BSPI1_RXR >> 8));                     // return received char
}

/*
************************************************************
*              reinitialise the SPI-port
************************************************************
*/
U08 FFSPort_MMC_ReInit(void)
{
    STR_BSPI1_CLK    = 0x00FE;                             // master-clock dividier use at startup PCLK1 / 254
    STR_BSPI1_CSR2   = 0x0001;                             // TX-1word-FiFo & clear-FiFo
    STR_BSPI1_CSR1   = 0x0301;                             // RX-1word-FiFo & 8-bit & CPHA=1 & CPOL=1 & enable SPI1
    STR_BSPI1_CSR1  |= 0x0002;                             // and at last set master
    FFSPort_MMC_SetBR(400000);                             // set SPI-clk to max 400kHz as startup (should never be > 400kHz, says MMC)
    return(0);                                             // return actual alltimes ok.
}

/*
************************************************************
*              initialise the SPI-port
************************************************************
*/
U08 FFSPort_MMC_Init(void)
{
    STR_IOPORT0_PC0 |= 0x01F0;                             // P0.5, P0.6, alternate (SPI1) & P0.7, P0.8 manual output-pu & P0.4 as alt input-wp
    STR_IOPORT0_PC1  = (STR_IOPORT0_PC1 & ~0x0180) | 0x0070;
    STR_IOPORT0_PC2  = (STR_IOPORT0_PC2 & ~0x0010) | 0x01E0;
    STR_IOPORT0_PD  |= 0x0190;                             // set P0.4 (MISO-wp) & P0.8 (used /SS) & P.07 (org /SS) to high
    STR_IOPORT1_PC0 |= 0x8400;                             // P1.10, P1.15 manual input-wp (CMOS)
    STR_IOPORT1_PC1 |= 0x8400;
    STR_IOPORT1_PC2 &=~0x8400;
    STR_IOPORT1_PD  |= 0x8400;                             // set P1.10 (WP-wp) & P1.15 (CD-wp) to high
    return(FFSPort_MMC_ReInit());
}

⌨️ 快捷键说明

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