调用了这个函数之后整个系统复位之后就起不来了

[复制链接]
2827|25
 楼主| dengdc 发表于 2014-7-10 19:31 | 显示全部楼层 |阅读模式
我想用软件的方法复位,阅读固件手册,发现SysCtlReset();该函数可以解决问题。
但是我在调用了这个函数之后,整个系统复位之后就起不来了。
shimx 发表于 2014-7-10 19:31 | 显示全部楼层
为什么判断说已经复位了
 楼主| dengdc 发表于 2014-7-10 19:33 | 显示全部楼层
因为我在这个函数之前有个串口发送数据,结果发到一半就停了
午夜粪车 发表于 2014-7-10 19:34 | 显示全部楼层
感觉这个复位函数已经起作用了
 楼主| dengdc 发表于 2014-7-10 19:37 | 显示全部楼层
是啊,谁有经验,传授一下,除了看门狗,还有什么软件复位的办法
spark周 发表于 2014-7-10 19:38 | 显示全部楼层
最好把相关代码贴出来分析下。
 楼主| dengdc 发表于 2014-7-10 19:39 | 显示全部楼层

代码很简单,就是一个调用SysCtlReset();函数
 楼主| dengdc 发表于 2014-7-10 19:39 | 显示全部楼层
void end2cmd(unsigned char Ch)
{
         PROG_MODE = 0;
         CopyPrint(pagetop_msg_tab[PRGPAGE.top_no]);
         PRGPAGE.top_no = 0;
         PRGPAGE.progmode = 1;
         mac_save_flag = 0;
         FlashInit();
         SysCtlReset();
}
spark周 发表于 2014-7-10 19:41 | 显示全部楼层
按照逻辑复位后应该到main函数,主函数部分是什么个情况?
liliang9554 发表于 2014-7-10 19:41 | 显示全部楼层
记得好像复位后要人为将某位清零。
spark周 发表于 2014-7-10 19:44 | 显示全部楼层

    基于《Stellaris外设驱动库》的SysCtl例程:软件复位示例

    掌握库函数SysCtlReset()的用法。

    程序运行后,LED1和LED2交替闪烁数次,以表明正常工作了。稍后,由于执行函数SysCtlReset()而导致芯片复位重来,LED1和LED2又会交替闪烁数次。如此反复。

    主函数:

    // 包含必要的头文件

    #include "LED.H"

    #include <hw_types.h>

    #include <hw_memmap.h>

    #include <hw_sysctl.h>

    #include <hw_gpio.h>

    #include <sysctl.h>

    #include <gpio.h>


    // 将较长的标识符定义成较短的形式

    #define SysCtlPeriEnable SysCtlPeripheralEnable

    #define SysCtlPeriDisable SysCtlPeripheralDisable

    #define GPIOPinTypeIn GPIOPinTypeGPIOInput

    #define GPIOPinTypeOut GPIOPinTypeGPIOOutput

    #define GPIOPinTypeOD GPIOPinTypeGPIOOutputOD


    // 定义KEY

    #define KEY_PERIPH SYSCTL_PERIPH_GPIOG

    #define KEY_PORT GPIO_PORTG_BASE

    #define KEY_PIN GPIO_PIN_5


    // 防止JTAG失效

    void JTAG_Wait(void)

    {

    SysCtlPeriEnable(KEY_PERIPH); // 使能KEY所在的GPIO端口

    GPIOPinTypeIn(KEY_PORT , KEY_PIN); // 设置KEY所在管脚为输入

    if ( GPIOPinRead(KEY_PORT , KEY_PIN) == 0x00 ) // 如果复位时按下KEY,则进入

    {

    for (;;); // 死循环,以等待JTAG连接

    }

    SysCtlPeriDisable(KEY_PERIPH); // 禁止KEY所在的GPIO端口

    }


    // 定义全局的系统时钟变量

    unsigned long TheSysClock = 12000000UL;


    // 延时

    void Delay(unsigned long ulVal)

    {

    while ( --ulVal != 0 );

    }


    // 主函数(程序入口)

    int main(void)

    {

    int i;

    JTAG_Wait(); // 防止JTAG失效,重要!

    LED_Init(LED1 | LED2); // 初始化LED1和LED2

    LED_On(LED1); // 点亮LED1

    LED_Off(LED2); // 熄灭LED2

    for ( i = 0; i < 6; i++ ) // 使LED闪烁数次,表明已复位

    {

    LED_Toggle(LED1 | LED2);

    Delay(200 * (TheSysClock / 4000));

    }

    LED_Off(LED1 | LED2); // 熄灭LED

    Delay(3500 * (TheSysClock / 4000)); // 延迟一段时间

    SysCtlReset(); // 软件复位

    for (;;) // 不会执行到这里

    {

    }

    }

 楼主| dengdc 发表于 2014-7-10 19:44 | 显示全部楼层
主函数比较麻烦,在0-1000H单元里是我的BOOT程序,判断按键情况跳转到1000H起始的应用程序main函数。
void
SysCtlReset(void)
{
     //
     // Perform a software reset request.  This request causes the device to
     // reset, no further code is executed.
     //
     HWREG(NVIC_APINT) = NVIC_APINT_VECTKEY | NVIC_APINT_SYSRESETREQ;

    //
     // The device should have reset, so this should never be reached.  Just in
     // case, loop forever.
     //
     while(1)
     {
     }
}
我看这个函数的意思是,往NVIC_APINT这个寄存器里写数,就可以复位了,之后程序就不往下继续走了,如何清零啊
zhaoxqi 发表于 2014-7-10 19:45 | 显示全部楼层
串口发送数据到一半就停了,这个感觉和复位没关系吧,至少发完才开始复位才对
 楼主| dengdc 发表于 2014-7-10 19:46 | 显示全部楼层
你的例子我感觉和我的使用应该是一样的,串口数据放入发送的FIFO中,然后程序就从发送程序中退出了,执行其他的部分,这个时候调用的复位函数,应该就会出现我说的这种发送了一半的情况。
huangchui 发表于 2014-7-10 19:48 | 显示全部楼层
是不是boot程序对于复位有影响
 楼主| dengdc 发表于 2014-7-10 19:48 | 显示全部楼层
啊,我也这么想,我得再试试。
spark周 发表于 2014-7-10 20:38 | 显示全部楼层
试试主函数里判断RESC寄存器中的SW位,如为1,则清零。
 楼主| dengdc 发表于 2014-7-10 20:38 | 显示全部楼层
靠,仿真器DOWN不了程序了,老出这个问题
shimx 发表于 2014-7-10 20:40 | 显示全部楼层
把串口给拔了
jiajs 发表于 2014-7-10 20:41 | 显示全部楼层
对,我的两个串口和电脑的串口助手软件连接,此时使用仿真器的时候,老是提示can not connect to target,后来把串口给拔了,就好用了。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

892

主题

13885

帖子

7

粉丝
快速回复 在线客服 返回列表 返回顶部