新闻中心

EEPW首页 > 嵌入式系统 > 设计应用 > Cx51程序设计的堆栈空间计算方法

Cx51程序设计的堆栈空间计算方法

作者:时间:2010-12-09来源:网络收藏

引言

本文引用地址:http://www.eepw.com.cn/article/173073.htm

  用C语言进行MCS51系列单片机是单片机开发和应用的必然趋势。Keil公司的C51编译器支持经典8051和8051派生产品的版本,通称为。应该说,是C语言在MCS51单片机上的扩展,既有C语言的共性,又有它自己的特点。本文介绍的是

  1的溢出问题

  MCS51系列单片机将设置在片内RAM中,由于片内RAM资源有限,堆栈区的范围也是有限的。堆栈区留得太大,会减少其他数据的存放,留得太少则很容易溢出。所谓堆栈溢出,是指在堆栈区已经满了的时候还要进行新的压栈操作,这时只好将压栈的内容存放到非堆栈区的特殊功能寄存器(SFR)中或者堆栈外的数据区中。特殊功能寄存器的内容影响系统的状态,数据区的内容又很容易被程序修改,这样一来,之后进行出栈操作(如子程序返回)时内容已变样,程序也就乱套了。因此,堆栈区必须留够,宁可大一些。要在Cx51中防止堆栈的溢出,要解决两个问题:第一,精确系统分配给用户的堆栈大小,假设是M;第二,精确用户需要堆栈的大小,假设是N。要求M≥N,下面分别分析这两个问题。

  2计算系统

  分配给用户的堆栈大小Cx51程序设计中,因为动态局部变量是长驻内存中的,实际上相当于局部静态变量,即使在函数调用结束时也不释放(这一点不同于标准C语言)。Cx51编译器按照用户的设置,将所有的变量存放在片内和片外的RAM中。片内变量分配好后,将剩下的空间全部作为堆栈空间,这个空间是最大可能的堆栈空间。当然,因为Cx51是一种可以访问寄存器的C语言(特殊功能寄存器),因此可在程序中访问SP,将堆栈空间设置得小一点。不过,一般没有人这么做。本文只是讨论放在片内RAM的变量。我们把变量分为两种情况:

  ① 用作函数的参数和函数返回值的局部变量。这种变量尽量在寄存器组中存放。为了讨论方便,假设统一用寄存器组0,具体的地址为0x00~0x07。最多可以传递3个参数,如果参数的个数比较多,就将多余的参数放到内存(0x08以后的地址)中存放。这里,假设每个函数的参数都不大于3个。

  ② 我们在程序中定义的全局变量,以及不是用作函数的参数和函数返回值的局部变量。以上两种变量在内存中0x08地址以后存放,存放完毕后将堆栈指针SP指向分配了变量的片内RAM的最后一个字节。因为MCS51单片机的堆栈是一种满递增堆栈且堆栈的宽度为8位,所以在需要压栈操作时将堆栈指针先加1,后入栈有效内容。有了以上规则,就可以精确地计算出系统分配给用户的堆栈空间。以求两个数的最大公约数和最小公倍数的函数为例,代码如下:

  #include REG52.H>

  unsigned char max(unsigned char a, unsigned char b);

  unsigned char min(unsigned char a, unsigned char b);

  unsigned char M;

  void main (void) {

  unsigned char n;

  M = max(12, 9);

  n = min(12, 9);

  }

  unsigned char max(unsigned char a, unsigned char b){

  while(a != b) {

  if(a > b)

  a = a - b;

  else

  b = b - a;

  }

  return a;

  }

  unsigned char min(unsigned char a, unsigned char b){

  unsigned char k;

  k = a*b/M;

  return k;

  }


上一页 1 2 下一页

评论


相关推荐

技术专区

关闭