动态函数名称 - 无法解析外部符号

Dynamic Functionname - Cannot resolve extern symbol

提问人:Ferdinand Brunauer 提问时间:1/6/2017 更新时间:1/6/2017 访问量:157

问:

我正在尝试使用预处理器指令动态生成函数名称(添加可选前缀)。

生成工作,当 gcc 在预处理器 (gcc -E) 之后向我输出代码时,gcc 告诉我该函数具有正确的名称。

但是当我在代码中使用此函数时,gcc 会抛出一个错误,并带有未解析的外部符号?(链接2019 / 链接1120)

我不是 100% 确定链接器是如何工作的,但理论上 gcc 应该运行预处理器,构建所有库(更准确地说,首先是原型,然后是主要定义?)所以应该没有问题? 我必须添加一个特殊的编译器选项吗?一个链接?

我的主要:

#define _CRT_SECURE_NO_WARNINGS
#define STRING_FUNCTION_PREFIX my   // Defining a prefix for my string functions
#include <stdlib.h>
#include <stdio.h>
#include <string.h>                 // Original string functions
#include "string.h"                 // My string functions

#define ARRAY_SIZE 50
#define HALLO "HALLO"
#define WELT "WELT"

int main()
{
    char src1[ARRAY_SIZE], src2[ARRAY_SIZE], dst1[ARRAY_SIZE], dst2[ARRAY_SIZE];
    strcpy(src1, HALLO);
    strcpy(dst1, WELT);
    strcpy(src2, HALLO);
    strcpy(dst2, WELT);

    strcat(src1, dst1);
    mystrcat(src2, dst2);

    return 0;
}

我的字符串.h

#pragma once
#include <stdlib.h>

#if defined STRING_FUNCTION_PREFIX
#define FUNCTION_PASTER(ARG1,ARG2) ARG1 ## ARG2
#define FUNCTION_EVALUATER(ARG1,ARG2) FUNCTION_PASTER(ARG1, ARG2)
#define FUNCTION_NAME(FUNCTION) FUNCTION_EVALUATER(STRING_FUNCTION_PREFIX, FUNCTION)
#else
#define FUNCTION_NAME(FUNCTION) FUNCTION
#endif

/*
 * \brief: Adds the string from src to the destination string
 */
void FUNCTION_NAME(strcat)(char *dst, char *src);

我的字符串.c

#include "string.h"

void FUNCTION_NAME(strcat)(char *dst, char *src)
{
    int counter = 0, offset = 0;
    while (dst[offset] != '\0')
    {
        offset++;
    }

    dst[offset + counter] = src[counter];
}

使用 -E 编译时 string.h 的输出

1>  #line 11 "d:\\string.h"
1>
1>
1>
1>
1>  void mystrcat(char *dst, char *src);

感谢您的帮助!

GCC 链接器 C Unresolved-External

评论

0赞 jxh 1/6/2017
实际上,您没有生成动态函数名称。

答:

2赞 dbush 1/6/2017 #1

该指令在 main.c 中定义,但不在 string.c 中定义。因此,当编译 string.c 时,不会发生替换。如果你用 编译 string.c,你会看到这样做的效果。STRING_FUNCTION_PREFIXgcc -E

你需要放在 string.h 的顶部,而不是 main.c 中。这样,任何需要它的 .c 文件都已定义它,并且在所有位置都是一致的。#define STRING_FUNCTION_PREFIX my

1赞 jxh 1/6/2017 #2

您似乎正在尝试在 C 中创建模板模拟。如果是这种情况,您应该将 的内容视为头文件,需要由知道应该是什么值的人包含该文件。如果内容是头文件,请重命名它以使其清晰,例如 .string.cSTRING_FUNCTION_PREFIXstring.cstring_template.h

然后,您可以将文件实现为:mystring.c

#define STRING_FUNCTION_PREFIX my
#include "string_template.h"