#define相关查询

时间:2012-03-12 14:36:36

标签: c c-preprocessor

我正在进行从Linux到Windows的代码移植。我正在使用Visual Studio环境。我遇到了一个问题。

在Windows中有一个带有2个参数的函数调用,用于获取和释放信号量。 Linux代码有一个参数
视窗:

KeInitializeSpinLock(spinlock,oldIRQL);

Linux的

spin_lock_init(spinlock);

我有通用电话,我必须使用:

Get_Lock(spinlock);

如何在不更改Get_Lock原型的情况下为Windows执行此操作?

我尝试了以下内容:

#define Get_Lock(lock) \

KIRQL  oldIrql;\

KeAcquireSpinLock(&(lock),&oldIrql);

#define Release_Lock(sync) KeReleaseSpinLock(&(sync),oldIrql)

但编译器发出错误。基本上我想保留oldIrql的值,因为KeReleaseSpinLock需要该值

错误

error C2275: 'KIRQL' : illegal use of this type as an expression
error C2146: syntax error : missing ';' before identifier 'oldIrql'
error C2065: 'oldIrql' : undeclared identifier
error C2065: 'oldIrql' : undeclared identifier
error C2065: 'oldIrql' : undeclared identifier

KIRQL定义为

typedef UCHAR KIRQL

我在这里做错了什么?或者是否有其他方法可以在不更改Get_LockRelease_Lock原型的情况下使用?

2 个答案:

答案 0 :(得分:1)

问题是由于Microsoft编译器仅支持C89标准,它不允许混合代码和声明。 Get_Lock()是在一行代码(我怀疑)之后被调用的,它引入了oldIrql的声明。

如果是在同一范围内获取和释放锁的情况,则可能的修复(hack)是在KIRQL oldIrql;和{{范围的顶部声明Get_Lock()。调用1}},并从Release_Lock()删除声明。

更整洁的解决方案是消除宏并引入一个定义锁的新Get_Lock()。例如:

struct

答案 1 :(得分:0)

我也怀疑hmjd发布的原因。但是,在我看来,解决方案可以如下:

#define Get_Lock(lock)  { KIRQL  oldIrql;  KeAcquireSpinLock(&(lock),&oldIrql);  
#define Release_Lock(sync) KeReleaseSpinLock(&(sync),oldIrql) }

但是,你需要确保Get_Lock&根据您的意见,Release_Lock与您保证的范围相同。

这个想法与pthread_cleanup_push & pthread_cleanup_pop的想法大致相同。您也可以参考相同的内容。