您可以动态编译和链接/加载 C 代码到 C 程序中吗?

标签 c jit

我读到了eval in C ,如果你编写一个 C 字符串解析器/求值器,你可以将它映射到你的主 C 程序中的特定函数,这是有道理的。但据我所知,它实际上并没有将其放入可执行内存中,例如 JIT compiler似乎可以。我不完全理解 JIT 编译器(我从来没有做过),但我明白了要点。

所以我想知道的是,您是否可以在 C 中创建一种 JIT 编译器,而无需做太多的解析 C 字符串和转换为 AST 之类的工作。基本上,您可以像在 JavaScript 中那样动态地创建一个函数(在 C 中),使得该函数与任何其他 C 函数完全相同(即,它在程序的可执行部分中直接编译成可执行机器代码事物)。

如果无法做到这一点,第二种方法是动态加载 C 导入/文件/模块。因此,您分离出一个告诉 clang 编译器编译一些库函数的进程,完成后,无需停止当前程序,它将新程序库链接/附加到自身,因此可以以这种方式执行代码.

如果这不可能,也许一个选项是简单地在后台重新编译程序,然后将当前程序与从头启动的新程序交换。不过,那将是非常原始的。

试图弄清楚您在 C 中是否有一些用于您自己的自定义函数数据类型的结构,然后如何以最优化的方式在 C 中执行该函数。

最佳答案

在 POSIX 系统(Linix、Mac、UNIX)上,您有 dlopendlsym您可以使用的功能。这些函数可用于在运行时加载共享库并从中执行函数。

至于创建库,最简单的做法是将相关源代码写入文件,在单独的进程中运行 gcc 进行编译,然后使用 dlopen/dlsym运行它包含的功能。

例如:

#include <stdio.h>
#include <stdlib.h>
#include <dlfcn.h>

const char *libsrc =
"#include <stdio.h>\n"
"\n"
"void f1()\n"
"{\n"
"  printf(\"in f1\\n\");\n"
"}\n"
"\n"
"int add(int a, int b)\n"
"{\n"
"  return a+b;\n"
"}\n";

int main()
{
    FILE *libfile = fopen("mylib.c", "w");
    fputs(libsrc, libfile);
    fclose(libfile);
    system("gcc -fPIC -shared -g -Wall -Wextra -o libmylib.so mylib.c");

    void *lib = dlopen("libmylib.so", RTLD_NOW);
    if (!lib) {
        printf("dlopen failed: %s\n", dlerror());
        return 1;
    }

    void (*f)() = dlsym(lib, "f1");
    if (f) {
        f();
    } else {
        printf("dlsym for f1 failed: %s\n", dlerror());
    }

    int (*a)(int, int) = dlsym(lib, "add");
    if (a) {
        int x = a(2,3);
        printf("x=%d\n", x);
    } else {
        printf("dlsym for add failed: %s\n", dlerror());
    }

    dlclose(lib);
    return 0;
}

关于您可以动态编译和链接/加载 C 代码到 C 程序中吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56829292/

相关文章:

c - 来自 fgets 的段错误

ios - MonoTouch 链接器无法解析 System.Void System.Console::set_ForegroundColor(System.ConsoleColor)

python - 使用 jit nopython 了解 Numba TypingError

python - 在 Python 中快速执行动态代码的可能性

c - 无法理解linux的 "Kill"程序

c - 非本地跳转是否存在性能问题?

c - 未使用 open 系统调用正确设置文件权限

c - c中的字符串读取

java - Java 如何让低效代码运行得比高效代码更快?

.net - 为什么 .NET 开发人员提供 32 位/64 位版本的 .NET 程序集?