将高级语言编译为机器代码

时间:2014-07-25 21:33:24

标签: c++ assembly compiler-construction machine-code

从网站上阅读了一些答案并查看了一些来源之后,我认为编译器将高级语言(例如C ++)转换为机器代码直接,因为计算机本身不需要将其转换为汇编,它只将其转换为程序集以供用户查看代码,并且可以根据需要对代码进行更多控制。

但是这可以在我的一个演讲表中找到,所以如果有人能够进一步解释并纠正我,如果我错了,或者下面的截图,我会感激。

Slide

3 个答案:

答案 0 :(得分:22)

你的幻灯片大多错了......

装配和机器代码之间存在一对一的映射。汇编是信息的文本表示,机器代码是二进制表示。

但是,某些机器支持其他汇编指令,但生成的汇编代码中包含的指令仍在编译时确定,而不是运行时。但一般来说,这取决于系统中的处理器(intel,amd,ti,nvidia等),而不是您从中购买整个系统的制造商。

答案 1 :(得分:6)

此幻灯片使字节码与文本汇编混淆。 汇编是字节码或机器码的人类可读版本。机器代码是硬件可以直接运行的。字节码进一步编译为机器码,它是低级的,但是通用的。

某些语言使用在运行时将字节代码转换为更低级别的机器代码。其中一个例子是java,其中类文件有时会被编译为机器代码作为运行时优化。另一个是cuda,其中每个nvidia gpu都有不同的指令集,但cuda编译器生成字节码,然后每个gpu的cuda驱动程序可以转换。

另一个选择是他正在谈论英特尔处理器如何在运行时将机器代码转换为内部微代码然后运行它,这对于软件来说是完全不可见的,包括操作系统。

答案 2 :(得分:4)

幻灯片在很多方面都是错误的。

幻灯片中给出的示例实际的大大简化版本 - 编译 C ++ - 将解释有四个阶段的编译要生成和执行源代码文件:

  1. 预处理
  2. 编译“正确”
  3. 装配
  4. 链接
  5. 预处理阶段,预处理程序指令(例如#include#define)已完全展开,预处理程序会删除注释,从而创建“postprocessed” C ++ 。幻灯片完全忽略了这一点。

    汇编“正确”阶段,编译器将上一阶段的后处理文本转换为汇编语言。不幸的是,我们使用相同的术语 - 编译 - 用于整个四步程序和这一步骤,但这就是它的方式。

    与幻灯片相反,汇编语言语句“可由OS读取”,也不会在运行时转换为机器代码。相反,它们可以被汇编程序读取,它在编译时完成它的工作(下一段)。

    程序集阶段,上一阶段的汇编语言语句将转换为目标代码(CPU理解的二进制机器代码指令,结合元数据,操作系统和链接器理解汇编程序。

    链接阶段,上一阶段的目标代码与其他目标代码文件和公共/系统库链接,形成可执行文件。

    在运行时,操作系统 - 特别是 loader - 将可执行文件读入内存并执行运行时链接,其中解析对公共/系统库的引用,并将这些库加载到内存中(如果他们还没有),那么你的可执行文件就可以使用它们。

    另一个错误是不同品牌的机器拥有“自己的机器代码”。决定机器理解机器代码的是CPU。如果两台机器具有相同的CPU(例如 Dell 笔记本电脑和具有相同 Intel i7-3610QM CPU的 Toshiba 笔记本电脑),那么他们就明白了相同的机器代码。此外,具有相同ISA(指令集架构)的两个CPU理解相同的机器代码。此外,较新的CPU通常向后兼容同一系列中较旧的CPU。例如,较新的 Intel i7 CPU了解较旧的 Intel Pentium 4 理解的所有说明,但反之亦然。

    希望我在简单性和正确性之间取得了比上面的幻灯片更好的平衡,上面的幻灯片惨遭失败。