神秘的case常量定义了多次错误

神秘的case常量定义了多次错误,c,embedded,c-preprocessor,C,Embedded,C Preprocessor,我正在使用C语言商用RTOS的socket库开发一个嵌入式项目。出于保密的原因,我将对周围的一些细节非常含糊,但我只知道其中涉及到完整的产品和RTOS堆栈 在我正在研究的部分中,我有一个相当大但简单的switch语句,它检查一个宏值并设置另一个宏值。案例值是RTOS标头中的套接字选项标志。当我用这个switch语句编译文件时,我得到一个错误,它说“case constant defined over-one次”,指的是其中的五种情况 以下是一些细节,让这一切变得神秘: 所有标题都用#ifndef

我正在使用C语言商用RTOS的socket库开发一个嵌入式项目。出于保密的原因,我将对周围的一些细节非常含糊,但我只知道其中涉及到完整的产品和RTOS堆栈

在我正在研究的部分中,我有一个相当大但简单的switch语句,它检查一个宏值并设置另一个宏值。案例值是RTOS标头中的套接字选项标志。当我用这个switch语句编译文件时,我得到一个错误,它说“case constant defined over-one次”,指的是其中的五种情况

以下是一些细节,让这一切变得神秘:

  • 所有标题都用
    #ifndef标题
    包装,以避免多个包含内容
  • 宏值来自多个不同的标题,但案例是否产生此错误与原始标题之间没有明显的相关性
  • 如果我注释掉单个定义或不显式地包含该头,我会得到“未定义的标识符”,因此它显然与该文件和定义相关联
  • 如果我在Eclipse中对宏进行“C/C++”搜索,它会列出定义的两个实例,但都引用同一文件中的同一点
  • 我已经运行了一个高级开发人员在这里,他和我一样困惑。有谁知道C语言解释的一个怪癖可能导致这种情况,或者任何地雷可能忽略了


    谢谢

    该错误意味着两个或多个宏的替换值相同,即使宏本身是不同的

    下面是重现此错误的简单方法:

    #define ONE 42
    #define TWO 42
    
    int main(int argc, char* argv[]) {
        int k = atoi(argv[1]);
        switch (k) {
            case ONE:
                printf("ONE\n");
                break;
            case TWO:
                printf("TWO\n");
                break;
            default:
                printf("NONE\n");
                break;
        }
        return 0;
    }
    

    尽管宏被称为
    ONE
    TWO
    ,但它们的值都是42,这导致了错误。

    所有对宏和头的引用(几乎)都是除此之外的一点:
    case常量被多次定义
    意味着您的
    case
    语句中有多个计算为相同的值,因此,编译器无法区分要选择的大小写


    尝试打印案例标签的实际值(它们都应计算为整数,这样您就可以使用
    %d
    格式
    printf
    打印它们),看看是否可以找出某些宏具有重叠值的原因。

    这意味着在宏替换和扩展之后,存在具有相同整数值的大小写标签。识别案例标签冲突,并了解宏是如何展开的。如果不发布代码和相关宏,我们无法提供比我更大的帮助。保密原因无关紧要-如果没有一个标签,除了猜测之外,你不太可能得到太多帮助。出于保密原因,你是含糊不清的。问题是,这使得你的问题如此模糊,以至于没有人能明智地帮助你。试着创建一个与你实际的“机密”代码无关,但显示出同样问题的代码。尽管它令人尴尬,但我认为@PaulOgilvie解决了它。事实证明,RTO的设计者并不太担心他们的参数被一起使用。