打印

菜鸟请教

[复制链接]
2788|22
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
ayb_ice|  楼主 | 2007-9-20 17:53 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
本人是FREESCALE菜鸟,请教CW6.0(HC08)C中怎样使用NOP指令...
还有0~255空间的变量效率较高,是否可以指定变量定位在0~255空间,怎样定位呢...
谢谢...

相关帖子

沙发
gxs64| | 2007-9-20 18:11 | 只看该作者

re

请教CW6.0(HC08)C中怎样使用NOP指令----    _asm nop;

使用特权

评论回复
板凳
ayb_ice|  楼主 | 2007-9-20 19:52 | 只看该作者

请教2楼

第二个问题呢...

使用特权

评论回复
地板
JerryBJ| | 2007-9-21 10:03 | 只看该作者

#pragma:

#pragma DATA_SEG MY_ZEROPAGE

unsigned char val1, val2, val3; 
//......       
#pragma DATA_SEG DEFAULT

使用特权

评论回复
5
yewuyi| | 2007-9-21 14:36 | 只看该作者

MY_ZEROPAGE的定义在哪里?

使用特权

评论回复
6
ayb_ice|  楼主 | 2007-9-21 14:59 | 只看该作者

谢谢,赶紧去试一下...

使用特权

评论回复
7
ayb_ice|  楼主 | 2007-9-21 16:40 | 只看该作者

再次请教...

用#pragma DATA_SEG MY_ZEROPAGE这种方法定位在了0页,但是
    if(i & 0x01){
        k++;
    }
这样的代码并没有被编译成位测试转移指令,怎样才能让它产生位测试转移指令...
看了一下反汇编,感觉CW远远没有KEIL产生的代码紧凑...
即可用位域的方式操作也没有产生位测试转移指令...

使用特权

评论回复
8
yewuyi| | 2007-9-21 17:38 | 只看该作者

是不是要开优化才会的把?

使用特权

评论回复
9
yewuyi| | 2007-9-21 17:39 | 只看该作者

汇编有没有位测试指令?

使用特权

评论回复
10
张明峰| | 2007-9-21 22:17 | 只看该作者

汇编有位测试指令

7楼的问题属于编译器的优化。并不是每个编译器都能将其译成对应的最精简位测试并跳转指令。

你可以将重要的位变量定义成“位域”形式再试试。或者将编译器的优化级别提到最高。

使用特权

评论回复
11
张明峰| | 2007-9-21 22:43 | 只看该作者

证明

编了一段小程序,证明如下:

#pragma DATA_SEG SHORT MY_ZEROPAGE
byte arg1;

#pragma DATA_SEG DEFAULT
byte a1;


    if (arg1 & 0x01) {
      a1++;
    }

翻译成汇编:
BRCLR 0, arg1, *+7
LDHX  #a1
INC   ,X

现在这里不能上传图片,不然可以给你看看截屏图片。

还是一句话:发现问题多找找自己的原因。


使用特权

评论回复
12
yewuyi| | 2007-9-22 08:37 | 只看该作者

请问张工MY_ZEROPAGE在哪里?

我怎么没找到饿?

使用特权

评论回复
13
张明峰| | 2007-9-22 09:13 | 只看该作者

看PRM文件

/* This is a linker parameter file for the JL8 */
NAMES END /* CodeWarrior will pass all the needed files to the linker by command line. But here you may add your own files too. */

SECTIONS /* here all RAM/ROM areas of the device are listed. Used in PLACEMENT below. */
  Z_RAM  = READ_WRITE 0x0060 TO 0x00FF; 
  RAM    = READ_WRITE 0x0100 TO 0x015F;
  ROM    = READ_ONLY  0xDC00 TO 0xFBFF;
END

PLACEMENT /* here all predefined and user segments are placed into the SECTIONS defined above. */
  DEFAULT_ROM                   INTO ROM;
  DEFAULT_RAM                   INTO RAM;
  _DATA_ZEROPAGE, MY_ZEROPAGE   INTO Z_RAM;
END

STACKSIZE 0x30

VECTOR 0 _Startup /* reset vector: this is the default entry point for a C/C++ application. */
//VECTOR 0 Entry  /* reset vector: this is the default entry point for a Assembly application. */
//INIT Entry      /* for assembly applications: that this is as well the initialisation entry point */


实际上这个名字在C语言文件中可以随便取,只要在PRM文件里写明对应的内存区即可。例如你可以写程序:
#pragma DATA_SEG SHORT YEWUYI_PAGE0
byte arg1;
然后修改PRM文件标明:
  _DATA_ZEROPAGE, MY_ZEROPAGE, YEWUYI_PAGE0   INTO Z_RAM;

使用特权

评论回复
14
yewuyi| | 2007-9-22 10:25 | 只看该作者

原来被看漏了

只是一个定义,肯定可以随便改名字了……

使用特权

评论回复
15
yewuyi| | 2007-9-22 10:26 | 只看该作者

谢了老张……

使用特权

评论回复
16
张明峰| | 2007-9-22 12:45 | 只看该作者

楼上不用客气

PRM文件在项目设计中有时非常重要,因为它定义和分配了所有片上内存的资源,包括RAM和Flash-ROM。通过自己改写分配特定的内存区域,你可以将特定的变量指定分配到特定的RAM区间,或者将特定的程序模块放到特殊的Flash空间,或者留出特定的Flash空间用以EEPROM模拟。举几个例子:

* 定义变量段使其在复位初始化时不被自动清零(C语言编程)
SECTIONS /* here all RAM/ROM areas of the device are listed. Used in PLACEMENT below. */
  Z_RAM  = READ_WRITE 0x0060 TO 0x00FF; 
  RAM_SV = NO_INIT    0x0100 TO 0x011F; /*非自动清零段*/
  RAM    = READ_WRITE 0x0120 TO 0x015F;
  ROM    = READ_ONLY  0xDC00 TO 0xFBFF;
END
在PLACEMENT声明中写
  RAM_KEEP INTO RAM_SV;
程序中定义:
#pragma DATA_SEG RAM_KEEP
byte arg1;

* 保留一段Flash作为EEPROM模拟
SECTIONS /* here all RAM/ROM areas of the device are listed. Used in PLACEMENT below. */
  Z_RAM  = READ_WRITE 0x0060 TO 0x00FF; 
  RAM    = READ_WRITE 0x0120 TO 0x015F;
  EEPROM = READ_ONLY  0xDC00 TO 0xDDFF; /*保留512字节做EEPROM模拟*/
  ROM    = READ_ONLY  0xDE00 TO 0xFBFF;
END
在PLACEMENT声明中写
  EE_DATA                       INTO EEPROM;
程序中定义数据并可以初始化
#pragma CONST_SEG EE_DATA
const byte str1[]="123456";

使用特权

评论回复
17
yewuyi| | 2007-9-22 13:18 | 只看该作者

难得教主今天有空讲课,多问点问题。



READ_WRITE 定义在哪里?
是编译器自己规定的关键字吗?

 RAM_KEEP INTO RAM_SV;
请问INTO的定义在哪里?

各个MCU的PRM文件中的关键字基本都一样的,但俺一直不是很明白,
俺很少改动PRM文件,印象总好象就是过去NEC的时候改过一次堆栈的大小(不够用了就改大点),基本都是用的default,用C语言,俺是个半吊子。

-Z(DATA)NEAR_I,NEAR_Z,NEAR_N,HEAP+_HEAP_SIZE=FE00-FE1F
-Z(DATA)CSTACK+_CSTACK_SIZE=FE40-FEFF
请问张工这两句怎么理解?
俺这么理解对不对?
1:-Z(DATA)CSTACK+_CSTACK_SIZE=FE40-FEFF
CSTACK地址:FE40
_CSTACK_SIZE长度=FEFF-FE40
-Z(DATA):初始化数据为0
2:-Z(DATA)NEAR_I,NEAR_Z,NEAR_N,HEAP+_HEAP_SIZE=FE00-FE1F
NEAR_I,NEAR_Z,NEAR_N,HEAP这4个区域地址分配在同一个地址段FE00-FE1F内

这是搞得IAR里面的一段。

使用特权

评论回复
18
张明峰| | 2007-9-22 20:18 | 只看该作者

IAR我没有用过

关于IAR的两个问题,看字面意思及其惯用的语法形式,你的理解应该是正确的。实际上有关连接定位的配置文件所含的内容描述,可以参考最后生成的MAP文件一起来理解。

关于PRM文件中的READ_WRITE、NO_INIT、READ_ONLY、INTO等都是约定的语法关键词,详细可以参考Codewarrior安装后的帮助文件"Build_Tools_Utilities.pdf"

使用特权

评论回复
19
ayb_ice|  楼主 | 2007-9-24 08:01 | 只看该作者

这个论坛还有点人气,看来FREESCALE还是不错...

使用特权

评论回复
20
ayb_ice|  楼主 | 2007-9-24 08:48 | 只看该作者

感谢张明峰...

原来是要加SHORT的缘故...
本人是FREESCALE的超级菜鸟,才接触几天而已,对KEIL C51较熟,最近对FREESCALE感兴趣,想学深点,想对汇编了解一下,想对编译器深入了解一下,所以有些问题比较菜,以后还会问些很菜的问题,希望高手不吝赐教...
在此先谢谢了...
不知张明峰是不是图示的那个张明峰...
对了要"只有本版版主或积分大于500的人才可以帖图哦!"
图贴不上来了...
就是那个写个PICC中文手册的上海的那个张明峰
不管是不是还是要谢谢你...

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

222

主题

15414

帖子

34

粉丝