打印

非常佩服匠人的bit真气**

[复制链接]
15849|113
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
ayb_ice|  楼主 | 2008-6-2 21:09 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
定义一个C宏,实现插入0~255个NOP指令。
几天后公布答案。
比如:_nopx(3);// 插入3个NOP

相关帖子

来自 2楼
程序匠人| | 2008-6-3 12:35 | 只看该作者

任务完成,匠人的答案如下:

//宏定义方法:
#define __NOP1__ asm("nop");
#define __NOP2__ __NOP1__ __NOP1__
#define __NOP4__ __NOP2__ __NOP2__
#define __NOP8__ __NOP4__ __NOP4__
#define __NOP16__ __NOP8__ __NOP8__
#define __NOP32__ __NOP16__ __NOP16__
#define __NOP64__ __NOP32__ __NOP32__
#define __NOP128__ __NOP64__ __NOP64__


#define __NOPX__(a)             
    if ((a)&(0x01))    {__NOP1__}                    
    if ((a)&(0x02))    {__NOP2__}                    
    if ((a)&(0x04))    {__NOP4__}                    
    if ((a)&(0x08))    {__NOP8__}                    
    if ((a)&(0x10))    {__NOP16__}                    
    if ((a)&(0x20))    {__NOP32__}                    
    if ((a)&(0x40))    {__NOP64__}                    
    if ((a)&(0x80))    {__NOP128__}                    

//宏引用方法(举例):

    __NOPX__(13)

//编译结果:
138:                   __NOPX__(13)
  051D    0000     NOP
  051E    0000     NOP
  051F    0000     NOP
  0520    0000     NOP
  0521    0000     NOP
  0522    0000     NOP
  0523    0000     NOP
  0524    0000     NOP
  0525    0000     NOP
  0526    0000     NOP
  0527    0000     NOP
  0528    0000     NOP
  0529    0000     NOP

//说明,此宏在PICC中编译通过
//程序匠人 于 2008-06-03

使用特权

评论回复
来自 3楼
ayb_ice|  楼主 | 2008-6-3 14:54 | 只看该作者

这是我的原文

extern void _nop_(void);
#define _nop1()   _nop_()
#define _nop2()   _nop_() ,_nop_()
#define _nop4()   _nop2() ,_nop2()
#define _nop8()   _nop4() ,_nop4()
#define _nop16()  _nop8() ,_nop8()
#define _nop32()  _nop16(),_nop16()
#define _nop64()  _nop32(),_nop32()
#define _nop128() _nop64(),_nop64()

#define _NOPX _nopx
#define _nopx(x)        
{                       
    if(x < 256){    
        if(x & 0x80){   
            _nop128();  
        }               
        if(x & 0x40){   
            _nop64();   
        }               
        if(x & 0x20){   
            _nop32();   
        }               
        if(x & 0x10){   
            _nop16();   
        }               
        if(x & 0x08){   
            _nop8();    
        }               
        if(x & 0x04){   
            _nop4();    
        }               
        if(x & 0x02){   
            _nop2();    
        }               
        if(x & 0x01){   
            _nop1();    
        }               
    }        
}

使用特权

评论回复
地板
dai_weis| | 2008-6-2 21:47 | 只看该作者

占个位置看看

使用特权

评论回复
5
谈的元| | 2008-6-2 21:57 | 只看该作者

C宏不会,汇编还可以

使用特权

评论回复
6
sz_kd| | 2008-6-2 22:00 | 只看该作者

路过

使用特权

评论回复
7
simon21ic| | 2008-6-3 06:54 | 只看该作者

请赐教,偶的方法太长了

偶只能想到(a是常量表达式):
#define NOPX(a)     
if((a)>0){asm("nop");}
if((a)-1>0){asm("nop");}
if((a)-2>0){asm("nop");}
if((a)-3>0){asm("nop");}
if((a)-4>0){asm("nop");}
if((a)-5>0){asm("nop");}
if((a)-6>0){asm("nop");}
if((a)-7>0){asm("nop");}
if((a)-8>0){asm("nop");}
if((a)-9>0){asm("nop");}
if((a)-10>0){asm("nop");}
if((a)-11>0){asm("nop");}
if((a)-12>0){asm("nop");}
if((a)-13>0){asm("nop");}
if((a)-14>0){asm("nop");}
if((a)-15>0){asm("nop");}
if((a)-16>0){asm("nop");}
......

在AVRGCC测试通过

使用特权

评论回复
8
xwj| | 2008-6-3 07:42 | 只看该作者

嗯,我也暂时只能想到这个笨办法

使用特权

评论回复
9
dld2| | 2008-6-3 08:09 | 只看该作者

不懂。不会。

使用特权

评论回复
10
wxj1952| | 2008-6-3 08:22 | 只看该作者

太简单了。

先看看别人的。不过至少应有2种方法,我一种,看看有没有不同的。要是和别人想的一样可太没劲了。

使用特权

评论回复
11
xwj| | 2008-6-3 08:33 | 只看该作者

LS,每次都是这样,你除了嚷嚷还会什么???

使用特权

评论回复
12
yewuyi| | 2008-6-3 08:42 | 只看该作者

swtich case

使用特权

评论回复
13
simon21ic| | 2008-6-3 08:50 | 只看该作者

switch case本质上是一样的

实现起来都需要长长的代码
如果LZ是说0~8的话,我也相信就是正解了
但0~255的话,不知道LZ有什么招,好奇杀死猫啊

使用特权

评论回复
14
xwj| | 2008-6-3 08:53 | 只看该作者

宏好像不支持swtich case哦

使用特权

评论回复
15
程序匠人| | 2008-6-3 08:55 | 只看该作者

别忘了宏是可以嵌套的。

simon21ic的方法是比较直接的办法。就是有点长,不过也无所谓,又不必真的行一行地输。如果想精简,可以用宏嵌套。

使用特权

评论回复
16
dld2| | 2008-6-3 08:56 | 只看该作者

我咋没明白为什么不能用循环

for、while之类?
为什么呀?

使用特权

评论回复
17
simon21ic| | 2008-6-3 08:57 | 只看该作者

宏为什么不支持switch case?

#define NOPX(a)    
switch(a)
{
......
case 9:asm("nop");
case 8:asm("nop");
case 7:asm("nop");
case 6:asm("nop");
case 5:asm("nop");
case 4:asm("nop");
case 3:asm("nop");
case 2:asm("nop");
case 1:asm("nop");
}

使用特权

评论回复
18
simon21ic| | 2008-6-3 08:58 | 只看该作者

to 13楼

宏是不可以嵌套的,不然就不用那么麻烦了
难道有什么高招?

#define NOPX(a)  if(a){asm("nop");if(a>1)NOPX(a-1);}
是不行的

使用特权

评论回复
19
wxj1952| | 2008-6-3 09:03 | 只看该作者

回9楼

我现在就写答案,是不是太不给你留面子了?过2天吧。

使用特权

评论回复
20
程序匠人| | 2008-6-3 09:06 | 只看该作者

这是匠人N年前做过的一个汇编的例子

功能和搂主要求有点类似。估计C里面也可以实现,并且可以做得更好:


;=================
;软件陷阱
;=================
JLOOP    MACRO        ;8
    NOP
    NOP
    NOP
    NOP
    NOP
    PAGE    0
    JMP    START1
ENDM

JLOOP1    MACRO        ;8*8=64
    JLOOP
    JLOOP
    JLOOP
    JLOOP
    JLOOP
    JLOOP
    JLOOP
    JLOOP
ENDM

JLOOP2    MACRO        ;64*8=512
    JLOOP1
    JLOOP1
    JLOOP1
    JLOOP1
    JLOOP1
    JLOOP1
    JLOOP1
    JLOOP1
ENDM

JLOOP3    MACRO        ;512*2=1K
    JLOOP2
    JLOOP2
ENDM

使用特权

评论回复
21
xwj| | 2008-6-3 09:07 | 只看该作者

宏是可以嵌套,但嵌套层数有限

纯粹嵌套出255个的话肯定是不行的

而且,LZ为什么是0~255个呢???
应该是他的方法造成的
还真是好奇心杀死猫啊....


Re 14楼:
我咋没明白为什么不能用循环

呵呵,我也不明白,只能说LZ是吃饱了撑的,想出来炫耀一下...

呵呵^_^




使用特权

评论回复
22
simon21ic| | 2008-6-3 09:11 | 只看该作者

关键是

宏是根据参数来确定多少个nop的

使用特权

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

本版积分规则

222

主题

15445

帖子

34

粉丝