Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/144.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ C++;程序从“导入文件”;。a「;文件,但您可以';“t反向”;。a「;你自己归档?_C++ - Fatal编程技术网

C++ C++;程序从“导入文件”;。a「;文件,但您可以';“t反向”;。a「;你自己归档?

C++ C++;程序从“导入文件”;。a「;文件,但您可以';“t反向”;。a「;你自己归档?,c++,C++,如果包含打包为“.a”的文件,则可以导入其中的文件并调用其方法。但是,据我所知,您无法从“.a”文件检索源代码。程序怎么可能知道并可以使用源代码,但没有程序以人类可读的形式生成源代码?编译器将源代码转换为二进制文件,称为对象文件,可直接链接或存储在存档(.a、.lib等)中. 链接器将对象文件(可以是实际文件或存档内容)组合到可执行文件中。档案文件中没有魔法;链接器不会将二进制文件转换回源代码 至于将目标文件转换回源文件,有一些工具可以做到这一点;它们被称为反编译器,但它们工作得不太好,因为根本

如果包含打包为“.a”的文件,则可以导入其中的文件并调用其方法。但是,据我所知,您无法从“.a”文件检索源代码。程序怎么可能知道并可以使用源代码,但没有程序以人类可读的形式生成源代码?

编译器将源代码转换为二进制文件,称为对象文件,可直接链接或存储在存档(.a、.lib等)中. 链接器将对象文件(可以是实际文件或存档内容)组合到可执行文件中。档案文件中没有魔法;链接器不会将二进制文件转换回源代码


至于将目标文件转换回源文件,有一些工具可以做到这一点;它们被称为反编译器,但它们工作得不太好,因为根本没有足够的信息来重构源代码。制作香肠后,你无法回到猪的身边。

编译器将源代码转换为二进制文件,称为对象文件,可以直接链接或存储在存档(.a、.lib等)中。链接器将对象文件(可以是实际文件或存档内容)组合到可执行文件中。档案文件中没有魔法;链接器不会将二进制文件转换回源代码


至于将目标文件转换回源文件,有一些工具可以做到这一点;它们被称为反编译器,但它们工作得不太好,因为根本没有足够的信息来重构源代码。在你做了香肠之后,你不能回到猪的身边。

好吧,即使有关于链接器的所有解释,你仍然感到困惑

简单地说,CPU理解并执行的代码不是您在
C++
中编写的代码。它做同样的事情,但它不一样

汇编是介于
C++
(和其他高级语言)和机器代码(CPU执行的代码)之间的一种语言,人眼仍然可以理解,因此我将在这里使用汇编。让我们看两个
C++
函数,并查看它们的程序集(通过启用优化的叮当声生成):

第一个功能: 第二条: 使用它生成的程序集:

foo(int, int, int):                              # @foo(int, int, int)
        cmpl    %edx, %edi
        cmovlel %edi, %edx
        cmpl    %esi, %edi
        cmovll  %esi, %edx
        movl    %edx, %eax
        retq
clamp(int, int, int):                            # @clamp(int, int, int)
        cmpl    %edi, %edx
        cmovlel %edx, %edi
        cmpl    %esi, %edi
        cmovll  %esi, %edi
        movl    %edi, %eax
        retq
我们可以观察到:
  • 这两个
    c++
    函数的作用完全相同
  • 组件丢失了很多信息:
    • 参数的原始名称
    • 即使是函数中有多少变量的信息也会丢失
    • 函数具有什么样的指令流
    • C++
      代码有什么指令
    • 第二个函数实际上调用了其他函数
    • 除非明确指定(
      -g
      ),否则即使函数名也会在最终的对象文件中丢失
    • 等等等等
  • <> L>强的>非常不同的< /强>(在实现中)C++函数生成<强>相同的<强> >(几乎,取“五月”字,它只是不同的测试顺序)

因此,您可以看到,没有可靠的方法可以从程序集中获取原始的
C++
代码(从对象文件中更是如此)。

好的,即使对链接器进行了所有说明,您仍然感到困惑

简单地说,CPU理解并执行的代码不是您在
C++
中编写的代码。它做同样的事情,但它不一样

汇编是介于
C++
(和其他高级语言)和机器代码(CPU执行的代码)之间的一种语言,人眼仍然可以理解,因此我将在这里使用汇编。让我们看两个
C++
函数,并查看它们的程序集(通过启用优化的叮当声生成):

第一个功能: 第二条: 使用它生成的程序集:

foo(int, int, int):                              # @foo(int, int, int)
        cmpl    %edx, %edi
        cmovlel %edi, %edx
        cmpl    %esi, %edi
        cmovll  %esi, %edx
        movl    %edx, %eax
        retq
clamp(int, int, int):                            # @clamp(int, int, int)
        cmpl    %edi, %edx
        cmovlel %edx, %edi
        cmpl    %esi, %edi
        cmovll  %esi, %edi
        movl    %edi, %eax
        retq
我们可以观察到:
  • 这两个
    c++
    函数的作用完全相同
  • 组件丢失了很多信息:
    • 参数的原始名称
    • 即使是函数中有多少变量的信息也会丢失
    • 函数具有什么样的指令流
    • C++
      代码有什么指令
    • 第二个函数实际上调用了其他函数
    • 除非明确指定(
      -g
      ),否则即使函数名也会在最终的对象文件中丢失
    • 等等等等
  • <> L>强的>非常不同的< /强>(在实现中)C++函数生成<强>相同的<强> >(几乎,取“五月”字,它只是不同的测试顺序)
因此,您可以看到,没有可靠的方法可以从程序集中获取原始的
C++
代码(从对象文件中更是如此)。

负责组合多个文件的“程序”。一个文件称为链接器。它无法访问.a中的源代码(并且.a甚至不包含源代码)。它只知道函数的机器代码,以及其中一些函数的入口点,以便其他链接代码可以调用它们

to.a文件的示例:

  • file1.a在某个地方调用了一个函数foo(),该函数未在文件中定义。编译器当时知道调用此函数的方法将在以后定义,他让调用“挂起”在.a中
  • file2.a具有函数foo()的编译机器代码和一个包含调用foo所需信息的符号表
链接器合并这两个文件的机器代码,并填充未定义的fu