ARM 交叉编译时如何选择要链接的静态库?

2024-11-06 08:34:00
admin
原创
210
摘要:问题描述:我在 Ubuntu 中有一个 ARM 交叉编译器(arm-linux-gnueabi-gcc),默认架构是 ARMv7。但是,我想编译 ARMv5 二进制文件。我通过为编译器提供选项来实现这一点-march=armv5te。到目前为止一切顺利。由于我的 ARM 系统使用 BusyBox,因此我必须以...

问题描述:

我在 Ubuntu 中有一个 ARM 交叉编译器(arm-linux-gnueabi-gcc),默认架构是 ARMv7。但是,我想编译 ARMv5 二进制文件。我通过为编译器提供选项来实现这一点-march=armv5te

到目前为止一切顺利。由于我的 ARM 系统使用 BusyBox,因此我必须以静态链接方式编译二进制文件。因此我给了 gcc 这个-static选项。

但是,链接器链接到我的 ARMv5 二进制文件的libc.a存在问题。此文件使用 ARMv7 架构选项进行编译。因此,即使我将 ARM 二进制文件与 ARMv5 进行交叉编译,也无法在基于 BusyBox 的 ARMv5 机器上运行它。

  1. 我该如何解决这个问题?

  2. 在哪里可以获得 ARMv5 libc.a静态库,以及如何链接它?

先感谢您。


解决方案 1:

你有两个选择,

  1. 获取正确的编译器。

  2. 编写您自己的“C”库。

获取正确的编译器。

让编译器与您的系统匹配总是最安全的。这适用于 x86 Linux 和各种发行版。如果不同的编译器可以工作,您就很幸运了。交叉编译时会更加困难,因为编译器通常不会自动同步。尝试在 2014 年的 Ubuntu 系统上运行在 1999 年 x86 Mandrake Linux 上编译的程序。

除了指令兼容性(您已确定)之外,还有 ABI 和 OS 依赖关系。具体来说,armv7最有可能是硬浮点(具有浮点 FPU和寄存器调用约定),而您需要软浮点(模拟 FPU)。特定的glibc(或ucLibc)具有 Linux OS 的特定调用和期望。例如,线程的工作方式随着时间的推移而发生了变化。

编写自己的

您始终可以使用-fno-builtin-ffreestanding以及-static。然后您不能使用任何libc函数,但您可以自己对它们进行编程。

有外部源代码,如Mark Martinec 的 snprintfwrite()和易于实现的构建块,

#define _SYS_IOCTL_H 1
#include <linux/unistd.h>
#include <linux/ioctl.h>
static inline int write(int fd, void *buf, int len)
{
    int rval;
        asm volatile ("mov      r0, %1
    "
                "mov    r1, %2
    "
                "mov    r2, %3
    "
                "mov    r7, %4
    "
                "swi    #0
    "
                "mov    %0, r0
    "
                : "=r" (rval)
                : "r" (fd),
                  "r" (buf),
                  "r" (len),
                  "Ir" (__NR_write)
                : "r0", "r1", "r2", "r7");
    return rval;
}

static inline void exit(int status)
{
        asm volatile ("mov      r0, %0
    "
                "mov    r7, %1
    "
                "swi    #0
    "
                : : "r" (status),
                  "Ir" (__NR_exit)
                : "r0", "r7");
}

你必须添加你自己的启动机制,由“C”库来负责,

/* Called from assembler startup. */
int main (int argc, char*argv[])
{
    write(STDOUT, "Hello world
", sizeof("Hello world
"));
    return 0;
}

/* Wrapper for main return code. */
void __attribute__ ((unused)) estart (int argc, char*argv[])
{
    int rval = main(argc,argv);
    exit(rval);
}

/* Setup arguments for estart [like main()]. */
void __attribute__ ((naked)) _start (void)
{
    asm(" sub     lr, lr, lr
"   /* Clear the link register. */
        " ldr     r0, [sp]
"     /* Get argc... */
        " add     r1, sp, #4
"   /* ... and argv ... */
        " b       estart
"       /* Let's go! */
        );
}

如果这太令人生畏,因为您需要实现很多功能,那么您可以尝试获取各种库源并用它们重建-fno-builtin,并确保这些库不会与不兼容的 Ubuntu 库链接。

像crosstool-ng这样的项目可以让你构建一个适合armv5系统的正确编译器(可能具有更高级的代码生成功能)。这似乎很麻烦,但上述替代方案也不容易。

相关推荐
  为什么项目管理通常仍然耗时且低效?您是否还在反复更新电子表格、淹没在便利贴中并参加每周更新会议?这确实是耗费时间和精力。借助软件工具的帮助,您可以一目了然地全面了解您的项目。如今,国内外有足够多优秀的项目管理软件可以帮助您掌控每个项目。什么是项目管理软件?项目管理软件是广泛行业用于项目规划、资源分配和调度的软件。它使项...
项目管理软件   1136  
  IPD(Integrated Product Development,集成产品开发)流程是一种广泛应用于高科技和制造业的产品开发方法论。它通过跨职能团队的紧密协作,将产品开发周期缩短,同时提高产品质量和市场成功率。在IPD流程中,CDCP(Concept Decision Checkpoint,概念决策检查点)是一个关...
IPD培训课程   90  
  研发IPD(集成产品开发)流程作为一种系统化的产品开发方法,已经在许多行业中得到广泛应用。它不仅能够提升产品开发的效率和质量,还能够通过优化流程和资源分配,显著提高客户满意度。客户满意度是企业长期成功的关键因素之一,而IPD流程通过其独特的结构和机制,能够确保产品从概念到市场交付的每个环节都围绕客户需求展开。本文将深入...
IPD流程   84  
  IPD(Integrated Product Development,集成产品开发)流程是一种以跨职能团队协作为核心的产品开发方法,旨在通过优化资源分配、提高沟通效率以及减少返工,从而缩短项目周期并提升产品质量。随着企业对产品上市速度的要求越来越高,IPD流程的应用价值愈发凸显。通过整合产品开发过程中的各个环节,IPD...
IPD项目管理咨询   92  
  跨部门沟通是企业运营中不可或缺的一环,尤其在复杂的产品开发过程中,不同部门之间的协作效率直接影响项目的成败。集成产品开发(IPD)作为一种系统化的项目管理方法,旨在通过优化流程和增强团队协作来提升产品开发的效率和质量。然而,跨部门沟通的复杂性往往成为IPD实施中的一大挑战。部门之间的目标差异、信息不对称以及沟通渠道不畅...
IPD是什么意思   89  
热门文章
项目管理软件有哪些?
云禅道AD
禅道项目管理软件

云端的项目管理软件

尊享禅道项目软件收费版功能

无需维护,随时随地协同办公

内置subversion和git源码管理

每天备份,随时转为私有部署

免费试用