C 如何在不编写完整解析器的情况下将部分源程序转换为库调用?
举个例子: 假设我有一个非常简单的库,它允许从另一种语言L调用C代码 为了使用L中的C代码,您需要更改C代码中的某些结构,例如将函数类型更改为void、将函数参数替换为单个库类型等。因此,您的C代码可能会更改如下内容:C 如何在不编写完整解析器的情况下将部分源程序转换为库调用?,c,parsing,translation,C,Parsing,Translation,举个例子: 假设我有一个非常简单的库,它允许从另一种语言L调用C代码 为了使用L中的C代码,您需要更改C代码中的某些结构,例如将函数类型更改为void、将函数参数替换为单个库类型等。因此,您的C代码可能会更改如下内容: double foo(double bar, double baz) { return bar + baz; } 对这样的事情: void foo(LibraryArgs args) { double bar = args.get(1); double baz =
double foo(double bar, double baz) {
return bar + baz;
}
对这样的事情:
void foo(LibraryArgs args) {
double bar = args.get(1);
double baz = args.get(2);
setReturn(baz + bar);
}
现在你的函数可以从L调用
我正在尝试编写一个程序,当它看到一个带有某种注释的函数时,它会自动进行这种转换,可能类似于:
@MakeCallableFromL
double foo(double bar, double baz) {
return bar + baz;
}
但是,除了为C编写一个近乎完整的解析器之外,我似乎找不到一个解决方案。有没有更简单的方法来解决这类问题呢?有很多解析包装生成器,其中最主要的是SWIG(这非常棒,同时也非常糟糕) 如果无法使用SWIG或类似现有解析器的内容: 我会完全避免更改原始代码——无论如何,C函数必须是外部可见的,因此只获取完成的共享对象,从中提取符号,从头开始生成包装器代码要容易得多 根据您的框架,有不同的选项可供选择。对于
gcc
,nm
将是首选工具,或objdump-t
或objdump-t
因为你要求的是开销:它可以忽略不计;编译器会自动优化掉大部分不必要的事情。能够生成多种语言的绑定。可能有一种方法可以使用SWIG的基础结构为L生成绑定。。。包装纸<代码>void wrap_foo(LibraryArgs args){setReturn(foo(arg1+arg2);}。也许最好也看看这个软件包:。C最常见、最简单的子集实际上并不难解析或编写简单的编译器。但是,您可能想看看,例如,您可以使用哪一个已完成的解析器,并将生成的树转换为您想要的任何形式。@hustmphrr,我喜欢t他的方法,但由于我绝不是一个C专家,我不得不问,是否值得花时间担心额外调用1个函数(包装器->原始函数)所增加的开销vs直接调用原始函数。这是我可以忽略的开销吗?@kjh您可以忽略。除了添加额外的函数调用包装器之外,还有太多其他东西会损害您的性能。在设计方面,如果您以这种形式修改所有代码,您可能会遇到麻烦。增强开发总是更好、更安全的保证。你是说我应该编译原始源代码,并使用
extern
创建函数,将原始调用封装在L兼容的代码中,类似于@hustmphrr建议的那样?