为什么我的程序一开始就跑到PC0x621处呢?

2019-03-25 18:45发布

今天用maplab仿真一个DS1302的程序,复位后点开始单步运行,结果点了三下,PC值就跳到0X621处,不是PC值0x3,这是怎么回事?是不是哪里设置有问题?芯片是PIC16F877A
程序如下:

#include<pic.h>
__CONFIG(0xff32);
//芯片配置字,看门狗关,上电延时开,掉电检测关,低压编程关,加密,4M晶体HS振荡
#define uchar unsigned char
#define uint unsigned int
#define rst RC2
#define clk RC3
#define sda RC4
#define write_second 0x80 //秒的写寄存器地址
#define write_minute 0x82 //分的写寄存器地址
#define write_hour 0x84  //时的写寄存器地址
#define read_second 0x81 //秒的读寄存器地址
#define read_minute 0x83 //分的读寄存器地址
#define read_hour 0x85  //时的读寄存器地址
#define write_protect 0x8e //写保护寄存器地址
void delayms(uint x);
void delayus(uint x);
void port_init();
void ds1302_init();
void write_byte(uchar data);
void write_ds1302(uchar addr,uchar data);
void disp();
void get_time();
uchar read_ds1302(uchar addr);
uchar read_byte();
uchar hour,min,sec;
uchar num[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,
                     0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};

///////////////////主程序///////////////////
void main()
{
port_init();
ds1302_init();
while(1)
{
  get_time();
  disp();
}
}
//////////////////ms级延时函数///////////////
void delayms(uint x)
{
uint i,j;
for(i=x;i>0;i--)
for(j=78;j>0;j--);
}
//////////////////////us级延时函数//////////////////
void delayus(uint x)
{
uint i;
for(i=x;i>0;i--);
}
//////////////////IO口初始化///////////////////
void port_init()
{
TRISD=0;
TRISA=0;
TRISC=0;
PORTD=0;
PORTA=0;
PORTC=0;
}
//////////////////////DS1302初始化////////////////////
void ds1302_init()
{
write_ds1302(write_protect,0x00);
write_ds1302(write_second,0x12);
write_ds1302(write_minute,0x12);
write_ds1302(write_hour,0x12);
}
/////////////////////往1302里写一个字节////////////////////
void write_byte(uchar data)
{
uint i;
for(i=0;i<8;i++)
{
  clk=0;
  sda=data&(0x01);
  data=data>>1;
  clk=1;
}
clk=0;
}
////////////////////从1302中读一个字节/////////////////////////
uchar read_byte()
{
uchar data;
uint i;
TRISC4=1;
for(i=0;i<8;i++)
{
  clk=0;
  data=data>>1;
  if(sda==1)
  {
   data=data|0x80;
  }
  clk=0;
}
clk=0;
TRISC4=0;
return data;
}
////////////往1302中写地址和数据;先写地址,后写数据/////////
void write_ds1302(uchar addr,uchar data)
{
rst=0;
rst=1;
write_byte(addr);
write_byte(data);
rst=0;
}
////////////从1302中读出指定地址中的数据/////////////////
uchar read_ds1302(uchar addr)
{
uchar data;
rst=0;
rst=1;
write_byte(addr);
data=read_byte();
rst=0;
return data;
}
/////////////从1302中读出时,分,秒////////////////
void get_time()
{
hour=read_ds1302(read_hour);
min=read_ds1302(read_minute);
sec=read_ds1302(read_second);
}
/////////////////////显示////////////////////////
void disp()
{
uchar hour1,hour0,min1,min0,sec1,sec0;    //定义查表变量

hour0=hour&0x0f;              //求时的个位
hour1=hour>>4;
PORTD=num[hour0]|0x80;          //送D口显示,并加上小数点(与80相或,就等于加了一个小数点)
PORTA = 0x10;                    //点亮时的个位
delayms(2);                       //延时一定时间,保证亮度
PORTD=num[hour1];          //送D口显示
PORTA = 0x20;                    //点亮时的十位
delayms(2);                       //延长一段时间,保证亮度

min0=min&0x0f;              //求时的个位
min1=min>>4;
PORTD=num[min0]|0x80;          //送D口显示,并加上小数点(与80相或,就等于加了一个小数点)
PORTA = 0x04;                    //点亮时的个位
delayms(2);                       //延时一定时间,保证亮度
PORTD=num[min1];          //送D口显示
PORTA = 0x08;                    //点亮时的十位
delayms(2);                      //延长一段时间,保证亮度
sec0=sec&0x0f;              //求时的个位
sec1=sec>>4;

PORTD=num[sec0]|0x80;          //送D口显示,并加上小数点(与80相或,就等于加了一个小数点)
PORTA = 0x01;                    //点亮时的个位
delayms(2);                       //延时一定时间,保证亮度
PORTD=num[sec1];          //送D口显示
PORTA = 0x02;                    //点亮时的十位
delayms(2);                      //延长一段时间,保证亮度
}

此帖出自小平头技术问答
友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。
该问题目前已经被作者或者管理员关闭, 无法添加新回复
7条回答
dingzy_2002
1楼-- · 2019-03-26 14:56
yealien 发表于 2018-7-8 11:49
最大地址和最小地址有什么关系?不好意思,我是刚学,不懂这些,麻烦了。

这个应该是编译器设置造成的
具体功能,我也在参考
可以找下PICC的参考手册看下,如何设置
我记得877这类的芯片是不从首地址编译的.

一周热门 更多>