- 1、本文档共8页,可阅读全部内容。
- 2、有哪些信誉好的足球投注网站(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。
- 3、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载。
- 4、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
查看更多
volitale的使用
volatile的使用2007-11-16 23:43:00
0
推荐
普通变量的定义和访问同标准C语言,在HCS08 C语言中我们主要要解决映像寄存器变量和某些特殊变量的定位问题,即把这些变量存放在RAM中指定的位置。
1映像寄存器定位
映像寄存器单片机中跟硬件有关的寄存器,它们都有各自固定RAM地址,其定位有3种方法
1)宏定义
例如:#define PortA ( * ( volatile unsigned char * )? 0x0000 )
这样 PortA 成为一个地址在0x0000的unsigned char类型变量。这个定义看起来很复杂,其实它也可以分解成几个很简单的部分来看。 ( volatile unsigned char * )是C语言中的强制类型转换,它的作用是把0x0000这个纯粹的十六进制数转换成为一个(地址)指针,其中volatile并不是必要的,它只是告诉编译器,这个值与外界环境有关,不要对它优化接下来在外面又加了一个*号,就表示0x0000内存单元中的内容了。经过这个宏定义之后,PortA就被可以做为一个普通的变量来操作,所有出现PortA的地方编译的时候都被替换成( * ( volatile unsigned char * )? 0x0000 ),外面一层括号是为了保证里面的操作不会因为运算符优先级或者其它不可预测的原因被改变而无法得到预期的结果。
这种定义方法适合所有的C编译器,可移植性好,但PortA并不是一个真正的变量,只是一个宏名,当你调试一个程序的时候,无法在调试窗口观察它的值。另外连接器也失去了灵活性,它得防止其它变量跟此变量冲突。
2)使用@关键字
例如: volatile unsigned char PortA?????? @0x0000;
@是编译器扩展的一个特殊修饰符,其它编译器很可能并不认识。这种定义具有很好的可读性,失去了可移植性。
3)使用段定义
这种方法分为2个步骤
首先把变量定义在段中,其次在连接参数文件(*.prm)中把段定位在一个合适的位置
例如:第1步:在源程序文件中
#pragma DATA_SEG PORTB_SEG
volatile unsigned char PortA;
#pragma DATA_SEG DEFAULT
这样变量 PortA 定义在段 PORTB_SEG 中
第2步:在 prm 文件中
SECTIONS
PORTB_SEG = READ_WRITE 0x0000 SIZE 1;
这样段 PORTB_SEG 定位在地址0x0000上。
这种方法可移植性也很差,如果你要把它移植在别的编译器上,你不得不修改源程序。
2变量定义修饰符
变量定义有三个修饰符值得注意,虽然它们与标准C是相同的,但是在嵌入式C语言中又有不同的含义。
1) static
在子函数中static用声明的变量是局部变量,但是退出这个子函数后其值不消失。下一次调用这个函数时仍可以访问到原来的值。注意,在子函数中声明的static变量只对声明他的函数可见,别的函数是不可以使用的。如果static变量是在模块中声明的,那么只有本模块的函数可以使用它,别的模块中的函数是不能访问的。
void MyFunction (void)
{?
? static char myVar = 0; ?//用 static声明的局部变量
? myVar = myVar + 1;
}
void main (void)
{
?? MyFunction();????? //调用之前myVar = 0,调用之后myVar = 1
?? MyFunction();????? //调用之前myVar = 1,调用之后myVar = 2
}
?
2) volatile
如果一个变量的值可能会被程序操作之外的其它操作所改变,那么你必需用volatile 声明。在嵌入式系统中其它操作是:中断服务程序的操作、硬件动作的操作。
用volatile声明的变量是不会被编译器优化掉的,如:
volatile unsigned char PortA?????? @0x0000;
PORTA做为一个输入端口,其值是由外部设备决定的,由于外部设备的变化是随机的,因此第一次读取的值和第二次读取的值很可能不同,所以我们把它声明为volatile变量。
a = PORTA;??
a = PORTA;
由于PORTA是用volatile声明的变量,编译器不会把它优化成一句,而如果不是volatile声明的编译器就会将第二句优化掉,从而程序将会忽略输入端口的变化。
通常把嵌入式设备的所有外围器件寄存器都声明为volatile 的。
?
3) const
修饰符 const 可以用在任何变量之前, 告诉编译器把此变量存储在ROM
文档评论(0)