解决keil单片编程ERROR L107: ADDRESS SPACE OVERFLOW问题及根源分析

1、将部分声明的不需要修改的变量声明为程序存储器变量,即在变量名前增加code关键字,如:

unsigned char code  led_mod[] = {0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};

当然,我们也可以使用关键字xdata将数据存储到片外存储器中去(如果我们不加任何关键字,就相当于默认使用了data关键字,也就是默认使用的是片内数据存储器)

2、修改存储器模式
对于代码行数比较多,程序运行空间需求大的程序,可能也会出现内存溢出的错误。但这个不是数据存储器的问题,而是程序存储器问题。程序存储器是用来供编译器控制指令small,compact和large指定编译时的存储器模式。

但是我自己测试 发现一个问题:

2.1如果把东西都放在PDATA

则不管是unsigned char 还是unsigned int全局变量,只要没有赋初值,大多都是默认为最大值,少量为随机数

2.2如果把东西都放在XDATA

总之就是可变的变量,不初始化放在PDATA或XDATA,则默认值都不正常(理论上应该全局变量不初始化,默认为0)。

3.放在data区

就正常了。

 

所以,我总结为,如果要改成XDATA,PDATA可变变量就都记得赋初值。
如果是DATA模式,则我们把不需要修改的变量声明为程序存储器变量(即在变量名前增加code关键字),以达到减少空间。如:

查看代码
code unsigned char led_mod[] = {0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};

code unsigned char mode1[] = {0X01,0X02,0X04,0X08,    0X10,0X20,0X40,0X80};    //L1-L8
code unsigned char mode2[] = {0X80,0X40,0X20,0X10,    0X08,0X04,0X02,0X01};    //L8-L1
code unsigned char mode3[] = {0X81,0X42,0X24,0X18};                                            //两边向中间
code unsigned char mode4[] = {0X18,0X24,0X42,0X81};

code的作用就是告诉单片机,定义的数据要放在ROM(程序存储区64KB)里面,写入后就不能再更改,因为C语言中没办法详细描述存入的是ROM还是RAM(寄存器),所以在软件中添加了这一个语句起到代替汇编指令的作用,对应的还有data(128B)是存入RAM的意思。

关键词的意思:

code :程序存储区(64KB),
data :可直接寻址的内部数据存储区(128B)
idata:间接寻址的内部数据存储区(256B),Indirect addressing
bdata:可位寻址内部数据存储区(16B),Bitable internal data
xdata:外部数据存储区(64KB),External data store
pdata:分页的外部数据存储区,Pagination addressing

 

Keil C51中code、data、bdata、idata、xdata、pdata的解释点击跳转

posted @ 2024-04-10 10:04  iZJ"Qq4577105  阅读(1924)  评论(1编辑  收藏  举报