【发布时间】:2018-08-08 16:59:45
【问题描述】:
Minecraft Modding 的世界让我对 Java 和 C/C++ 库之间的机制差异感到好奇,以允许在外部调用库中的方法/函数。
我的理解是,Minecraft Modding 的出现是由于能够对 Java 进行反编译/反射,以便对可以从库中调用的类和方法进行逆向工程。我相信 Java 类规范包含大量关于类结构的元数据,允许以非预期方式使用代码。
有一些混淆工具试图让 Java 逆向工程变得更加困难,但总体而言,这似乎很难防止。
我没有 C/C++ 方面的知识深度,不知道在那里可以做到什么程度。
对于 C/C++ 代码,提前本地编译。最终结果是特定于该平台的机器代码组合。 C/C++ 具有外部化函数的概念,以便它们可以从库或可执行文件外部公开。一些库也有入口点。
通常在连接到外部函数时,会有一个头文件列出库中可用于编写代码的函数。
我认为需要一种机制将公开的函数映射到库/可执行机器代码程序集中的地址,以便在正确的位置进行函数调用。
通常将函数调用与地址连接在一起是链接器的工作。链接器仍然需要以某种方式知道在哪里可以找到这些函数。
这让我想知道是否从根本上可以调用非导出函数。如果是这样,这是否需要能够定位它们的地址并理解它们的参数格式?
据我了解,C/C++ 中的函数调用通常是通过将参数分配给简单函数的寄存器或更复杂函数的参数数组来完成的。
我不知道在本机代码中调用非公共 API 的做法是否普遍 或者如果这样做的固有困难使本机代码在这种使用中非常安全。
【问题讨论】:
-
请注意,没有“C/C++”之类的语言。虽然存在两种 非常 不同的语言 C 和 C++。
-
这是对的,但 C++ 以 C 为基础构建的方式旨在允许它仍然与它互操作并保持兼容性级别。 C++ 运行时建立在 C 功能之上,例如在使用“new”创建对象或删除它们时会在后台调用 alloc 和 free。
-
@CarlJokl,您的假设非常简单。 C++ 允许运算符和函数重载,例如,你要避免的东西,而且根本不明显......只是举一个例子说明它们是多么不同的语言。
-
语言的差异并不是重点。 C++ 可以直接调用 C 函数,而无需通过兼容层。例如,C++ 程序可以使用普通 C 中公开的 OpenGL 函数。C 程序可以调用以 C++ 实现的 Direct3D(尽管更混乱)。这些都不需要像 JNI 或 PInvoke 这样的本机 ABI 翻译层。 Objective-C 也可以直接调用 C,但是是一种非常不同的语言风格。所以我说的是语言的直接互操作性,而不是特定的语法。
-
等价的分组可能是 Java、Scala、Groovy、Clojure 等,它们的语法非常不同,但由于在 Java 虚拟机上运行,它们能够相互调用。等价物也将是 .Net 系列,其中 C# .net 和 VB .net 可以调用公共库,即使语法非常不同,它在 CLR 上运行并且具有公共语言接口,因此语言可以相对直接地相互调用。跨度>
标签: java c++ c reverse-engineering libraries