【问题标题】:Is i686 32 bit? Why does my gcc/g++ fail compiling .cpp and .c files?i686 是 32 位的吗?为什么我的 gcc/g++ 无法编译 .cpp 和 .c 文件?
【发布时间】:2015-10-22 05:51:39
【问题描述】:

我正在尝试编译一个 helloworld.c 代码

#include<stdio.h>
 int main(){
 printf("Hello World");
 return 0;
 }

在 Linux 机器上。下面是机器的 unname-a 结果,表明机器是 64 位的。

uname-a : Linux pascal 2.6.32-358.23.2.el6.x86_64 #1 SMP Sat Sep 14 05:32:37 EDT 2013 x86_64 x86_64 x86_64 GNU/Linux

运行 gcc 命令时出现以下错误:

 [pascal]/user/gasharma/workspaceC++:/>gcc -c helloworld.c

 /tmp/ccpg1Atk.s: Assembler messages:
 /tmp/ccpg1Atk.s:11: Error: suffix or operands invalid for `push'
 /tmp/ccpg1Atk.s:12: Error: suffix or operands invalid for `push'
 /tmp/ccpg1Atk.s:14: Error: suffix or operands invalid for `push'
 /tmp/ccpg1Atk.s:20: Error: suffix or operands invalid for `pop'
 /tmp/ccpg1Atk.s:21: Error: suffix or operands invalid for `pop'

这是 gcc -v 的输出:

 [pascal]/user/gasharma/workspaceC++:/>gcc -v
 Using built-in specs.
 Target: i686-pc-linux-gnu
 Configured with: ../gcc-4.2.4/configure --prefix=/usr/local --with-gmp=/usr/local --with-mpfr=/usr/local
 Thread model: posix
 gcc version 4.2.4

仔细检查上述内容,我确实看到目标是 i686(我不确定是 32 位还是 64 位)。我强烈的猜测是它是 32 位的。我用谷歌搜索了一段时间,结果表明问题可能出在 64 位机器上的 32 位编译器上。但是,一些结果也表明使用 -m32 和 -m64 选项来执行成功的编译运行。

我使用 -m64 运行了 gcc,结果出现以下错误。

 [pascal]/user/gasharma/workspaceC++:/>gcc -c -m64 helloworld.c
 helloworld.c:1: sorry, unimplemented: 64-bit mode not compiled in

这里有六个问题:

1) 目标中的 i686 代表 32 位还是 64 位机器?我怎样才能做出这种区分?一般 i386 指的是 32 位,x86_64 指的是 64 位。

2) 我该如何运行一个简单的 helloworld.c?何时、为什么以及如何使用 -m32 和 -64 选项?

3) 这与汇编器或编译器有关吗?

4) “抱歉,未实现:未编译的 64 位模式”是什么意思?

5) "Configured with: ../gcc-4.2.4/configure --prefix=/usr/local --with-gmp=/usr/local --with-mpfr=/usr 是什么意思/本地”?

6) 为什么我在运行64位机时目标机不是gcc下的x86_64?

我非常感谢有人花时间回答我的上述问题。提前致谢!

【问题讨论】:

  • i686、i386、i586、x86 等都是 32 位的。 x86_64 是 64 位
  • 了解@AmalGJose
  • 尝试which gcc 并验证您是否正在从您的发行版包中运行gcc。您看到的错误是因为gcc 正在生成 32 位代码,即使它不应该生成,并且汇编程序正确地期望 64 位。但是gcc -m32 应该可以工作,因为这也应该在 32 位模式下调用汇编程序(但显然会创建 32 位输出)。还将-v 选项添加到gcc 以查看它如何调用工具。
  • @Jester:我确实确认发行版是正确的。我不确定为什么 -m32 不在 32 位模式下调用汇编程序。我在一台权限有限的 Linux 机器上。您认为这可能是汇编程序不切换模式的原因吗?感谢您的帮助!

标签: c gcc assembly 64-bit 32-bit


【解决方案1】:
  1. i686 是对用于 Pentium Pro 和 Pentium II 处理器的 Intel CPU 架构的引用。这也意味着目标是 32 位 x86 代码而不是 64 位 x86 代码。

  2. 您需要修复您的安装,因为安装的编译器与安装的汇编器不兼容。您不需要使用 -m32 或 -m64 选项来编译 hello world 程序。

  3. 问题是您的编译器与您的汇编器不兼容。您的编译器只能生成 32 位代码,但您的汇编器默认采用 64 位代码。您的编译器错误地假定您的汇编器默认为 32 位,因此没有传递允许汇编器使用 32 位代码的必要选项。

  4. 这意味着您的编译器无法生成 64 位代码。

  5. 构建您正在使用的编译器 GCC 的第一步是运行源代码中包含的配置脚本。这一行显示了配置脚本是如何运行的,包括使用了哪些参数。

  6. 因为您计算机上安装的 GCC 版本仅针对 32 位。它将在 x86_64 CPU 上以 32 位模式运行,并且通过兼容的汇编程序,它可以生成将在 x86_64 CPU 上以 32 位模式运行的代码。

我不知道为什么您的编译器和/或汇编器安装不正确或如何修复它。

【讨论】:

  • 即使我也不知道为什么要这样安装编译器和汇编器。最简单的方法是重新安装 64 位的 gcc。但是,我真的很想知道机制。再问一个问题,configure脚本一般是在安装的时候设置的吧?程序员可以调整它吗?有什么使用例子吗?
  • @GauravSharma 更改配置脚本或它生成的文件不会改变您机器上已编译和安装的 GCC 版本的行为。您可以创建或编辑一个 .specs 文件,以便编译器将正确的选项传递给汇编器,但最好安装一个完全工作的编译器。
猜你喜欢
  • 1970-01-01
  • 2011-04-23
  • 1970-01-01
  • 2011-05-12
  • 2011-10-01
  • 1970-01-01
  • 1970-01-01
  • 2015-01-05
  • 2014-10-03
相关资源
最近更新 更多