今天编译kvm upstream时,发现如下的错误,是一个struct里面的union的初始化时的语法错误,所以简单总结了一下。本博客中提及的对C的编译,默认情况下,使用的是GCC作为编译器(gcc version >= 4.4.0)。
arch/x86/kvm/pmu.c: In function 'reprogram_counter':
arch/x86/kvm/pmu.c:173: error: unknown field 'sample_period' specified in initializer
我写了一个patch去fix这个问题,发到kvm mailing list中,redhat的人告诉说已经在kvm next tree中fix过了;不过我只改了两行的patch如下。
diff --git a/arch/x86/kvm/pmu.c b/arch/x86/kvm/pmu.c
index 061a03f..8f142bf 100644
--- a/arch/x86/kvm/pmu.c
+++ b/arch/x86/kvm/pmu.c
@@ -170,9 +170,9 @@ static void reprogram_counter(struct kvm_pmc *pmc, u32 type,
.exclude_host = 1,
.exclude_user = exclude_user,
.exclude_kernel = exclude_kernel,
- .sample_period = (-pmc->counter) & pmc_bitmask(pmc),
.config = config,
};
+ attr.sample_period = (-pmc->counter) & pmc_bitmask(pmc),
event = perf_event_create_kernel_counter(&attr, -1, current,
intr ? kvm_perf_overflow_intr :
这个问题就在于union中的成员(这个union在一个struct中),不能在结构体初始化时,直接地同结构体的普通成员一样初始化。当然如果定义结构体时顺便定义其中的联合体,那么是可以在结构体初始化时,就一起初始化联合体里面的成员。说的很绕,可能没表达的很清楚,还是看下面的代码吧。
/*
* This sample shows definition and initiation of a struct and a union in a struct.
* using GCC to compile this C file
* Author: Jay Ren
*/
#include
int main(int argc, char *argv[])
{
struct my_struct1 {
int num1;
union {
int num2;
char ch;
};
};
struct my_struct1 my_st1 = {
.num1 = 111,
/* the following commented line will cause a syntax error. */
/* .num2 = 123456,*/
};
/* num2 or ch in the union of the struct can't be initiated before. */
my_st1.num2 = 123456;
printf("my_st1.num1 = %d\n", my_st1.num1);
printf("my_st1.num2 = %d\n", my_st1.num2);
struct my_struct2 {
int num1;
union my_union {
int num2;
char ch;
} my_u;
};
struct my_struct2 my_st2 = {
.num1 = 222,
/* the following line for initiating num2 works fine. */
.my_u.num2 = 123456,
};
printf("my_st2.num1 = %d\n", my_st2.num1);
printf("my_st2.num2 = %d\n", my_st2.my_u.num2);
return 0;
}