This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

MSP430F247

Other Parts Discussed in Thread: MSP430F247

WDTCTL = WDTPW + WDTHOLD; // Stop Watchdog Timer
if (CALBC1_8MHZ==0xFF) // If calibration constant erased
{
while(1); // do not load, trap CPU!!
}
DCOCTL = 0; // Select lowest DCOx and MODx settings
BCSCTL1 = CALBC1_8MHZ; // Set DCO to 8MHz
DCOCTL = CALDCO_8MHZ;

一直在停在while(1); // do not load, trap CPU!! 

以前都是好的 版本为  E 和 F

新买的以MSP430F247 版本为D  就是通不过时钟校准,新买的怎么信息段被擦除了,

  • 楼主通过什么渠道购买的?一般批量购买,都是版本越来越大

  • CALBC1_8MHZ这个值应该是每个芯片都不一样的,用来做校准用的,你可以先都一下现在CALBC1_8MHZ中存的值是多少。

  • #include <msp430.h>

    #define DELTA_1MHZ 244 // 244 x 4096Hz = 999.4Hz
    #define DELTA_8MHZ 1953 // 1953 x 4096Hz = 7.99MHz
    #define DELTA_12MHZ 2930 // 2930 x 4096Hz = 12.00MHz
    #define DELTA_16MHZ 3906 // 3906 x 4096Hz = 15.99MHz

    unsigned char CAL_DATA[8]; // Temp. storage for constants
    volatile unsigned int i;
    int j;
    char *Flash_ptrA; // Segment A pointer
    void Set_DCO(unsigned int Delta);

    int main(void)
    {
    WDTCTL = WDTPW + WDTHOLD; // Stop WDT
    for (i = 0; i < 0xfffe; i++); // Delay for XTAL stabilization
    P1OUT = 0x00; // Clear P1 output latches
    P1DIR = 0x01; // P1.0 output
    P2SEL |= 0x02; // P2.1 SMCLK output
    P2DIR |= 0x02; // P2.1 output

    j = 0; // Reset pointer

    Set_DCO(DELTA_16MHZ); // Set DCO and obtain constants
    CAL_DATA[j++] = DCOCTL;
    CAL_DATA[j++] = BCSCTL1;

    Set_DCO(DELTA_12MHZ); // Set DCO and obtain constants
    CAL_DATA[j++] = DCOCTL;
    CAL_DATA[j++] = BCSCTL1;

    Set_DCO(DELTA_8MHZ); // Set DCO and obtain constants
    CAL_DATA[j++] = DCOCTL;
    CAL_DATA[j++] = BCSCTL1;

    Set_DCO(DELTA_1MHZ); // Set DCO and obtain constants
    CAL_DATA[j++] = DCOCTL;
    CAL_DATA[j++] = BCSCTL1;

    Flash_ptrA = (char *)0x10C0; // Point to beginning of seg A
    FCTL2 = FWKEY + FSSEL0 + FN1; // MCLK/3 for Flash Timing Generator
    FCTL1 = FWKEY + ERASE; // Set Erase bit
    FCTL3 = FWKEY + LOCKA; // Clear LOCK & LOCKA bits
    *Flash_ptrA = 0x00; // Dummy write to erase Flash seg A
    FCTL1 = FWKEY + WRT; // Set WRT bit for write operation
    Flash_ptrA = (char *)0x10F8; // Point to beginning of cal consts
    for (j = 0; j < 8; j++)
    *Flash_ptrA++ = CAL_DATA[j]; // re-flash DCO calibration data
    FCTL1 = FWKEY; // Clear WRT bit
    FCTL3 = FWKEY + LOCKA + LOCK; // Set LOCK & LOCKA bit

    while (1)
    {
    P1OUT ^= 0x01; // Toggle LED
    for (i = 0; i < 0x4000; i++); // SW Delay
    }
    }

    void Set_DCO(unsigned int Delta) // Set DCO to selected frequency
    {
    unsigned int Compare, Oldcapture = 0;
    BCSCTL3 |= XCAP_3; //内部驱动电容12.5P
    BCSCTL1 |= DIVA_3; // ACLK = LFXT1CLK/8
    TACCTL2 = CM_1 + CCIS_1 + CAP; // CAP, ACLK
    TACTL = TASSEL_2 + MC_2 + TACLR; // SMCLK, cont-mode, clear

    while (1)
    {
    while (!(CCIFG & TACCTL2)); // Wait until capture occured
    TACCTL2 &= ~CCIFG; // Capture occured, clear flag
    Compare = TACCR2; // Get current captured SMCLK
    Compare = Compare - Oldcapture; // SMCLK difference
    Oldcapture = TACCR2; // Save current captured SMCLK

    if (Delta == Compare)
    break; // If equal, leave "while(1)"
    else if (Delta < Compare)
    {
    DCOCTL--; // DCO is too fast, slow it down
    if (DCOCTL == 0xFF) // Did DCO roll under?
    if (BCSCTL1 & 0x0f)
    BCSCTL1--; // Select lower RSEL
    }
    else
    {
    DCOCTL++; // DCO is too slow, speed it up
    if (DCOCTL == 0x00) // Did DCO roll over?
    if ((BCSCTL1 & 0x0f) != 0x0f)
    BCSCTL1++; // Sel higher RSEL
    }
    }
    TACCTL2 = 0; // Stop TACCR2
    TACTL = 0; // Stop Timer_A
    BCSCTL1 &= ~DIVA_3; // ACLK = LFXT1CLK
    }

    通过校准后程序正常

    我板子上带有32.768  晶振,通过官方程序校准,但官方使用的是外部电容驱动,在此基础上增加了BCSCTL3 |= XCAP_3; 不知对匹配精度有没有影响,板载晶振匹配电容为12.5P。

  • 看Datasheet,推荐的电容是多少。一般板载和片内的电容选一个就好了