如何在低 RAM 下编译 Android SDK?

问题描述 投票:0回答:1

我正在尝试通过 docker 脚本编译 Android SDK(版本 11),网址为 gitlab.com/android-rebuilds/auto。 由于各种原因,我必须使用具有 8 GB RAM 的设备。储物空间很大。

脚本已被修改为可以工作(SSH问题),并且我还添加了大量交换内存(当前为 315 GB)。 我还添加了zram内存。

我在 build.shbuild-sys-img.sh 脚本中添加了值, 导出 JAVA_TOOL_OPTIONS、JAVA_OPTIONS 和 _JAVA_OPTION = "-Xmx270g" 将大部分交换空间分配给编译器。

我还使用了 make -j1 而不是

make $(nproc)

尽管完成了所有步骤,我仍然遇到错误,例如 Java 堆空间。 错误偶尔会有所不同,但一般模式如下:

Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
    at java.base/java.util.Arrays.copyOfRange(Arrays.java:4030)
    at java.base/java.lang.StringLatin1.newString(StringLatin1.java:715)
    at java.base/java.lang.String.substring(String.java:1879)
    at java.base/java.lang.String.subSequence(String.java:1913)
    at com.intellij.lang.impl.PsiBuilderImpl$RelativeTokenTextView.get(PsiBuilderImpl.java:1161)
    at com.intellij.lang.java.parser.JavaParserUtil$TrailingWhitespacesAndCommentsBinder.getEdgePosition(JavaParserUtil.java:88)
    at com.intellij.lang.impl.PsiBuilderImpl.balanceWhiteSpaces(PsiBuilderImpl.java:1116)
    at com.intellij.lang.impl.PsiBuilderImpl.prepareLightTree(PsiBuilderImpl.java:1017)
    at com.intellij.lang.impl.PsiBuilderImpl.buildTree(PsiBuilderImpl.java:910)
    at com.intellij.lang.impl.PsiBuilderImpl.getTreeBuilt(PsiBuilderImpl.java:905)
    at com.intellij.psi.impl.source.tree.JavaElementType$ICodeBlockElementType.parseContents(JavaElementType.java:156)
    at com.intellij.psi.impl.source.tree.LazyParseableElement.lambda$ensureParsed$0(LazyParseableElement.java:206)
    at com.intellij.psi.impl.source.tree.LazyParseableElement$$Lambda$213/0x00000001004e5440.run(Unknown Source)
    at com.intellij.psi.impl.DebugUtil.performPsiModification(DebugUtil.java:553)
    at com.intellij.psi.impl.source.tree.LazyParseableElement.ensureParsed(LazyParseableElement.java:205)
    at com.intellij.psi.impl.source.tree.LazyParseableElement.getFirstChildNode(LazyParseableElement.java:254)
    at com.intellij.psi.impl.source.tree.LazyParseablePsiElement.getFirstChild(LazyParseablePsiElement.java:90)
    at com.intellij.psi.impl.source.tree.LazyParseablePsiElement.acceptChildren(LazyParseablePsiElement.java:104)
    at com.intellij.psi.JavaRecursiveElementVisitor.visitElement(JavaRecursiveElementVisitor.java:43)
    at com.intellij.psi.JavaElementVisitor.visitCodeBlock(JavaElementVisitor.java:52)
    at com.intellij.psi.impl.source.tree.java.PsiCodeBlockImpl.accept(PsiCodeBlockImpl.java:212)
    at com.intellij.psi.impl.source.tree.CompositePsiElement.acceptChildren(CompositePsiElement.java:81)
    at com.intellij.psi.JavaRecursiveElementVisitor.visitElement(JavaRecursiveElementVisitor.java:43)
    at com.intellij.psi.JavaElementVisitor.visitStatement(JavaElementVisitor.java:259)
    at com.intellij.psi.JavaElementVisitor.visitBlockStatement(JavaElementVisitor.java:32)
    at com.intellij.psi.impl.source.tree.java.PsiBlockStatementImpl.accept(PsiBlockStatementImpl.java:67)
    at com.intellij.psi.impl.source.tree.LazyParseablePsiElement.acceptChildren(LazyParseablePsiElement.java:106)
    at com.intellij.psi.JavaRecursiveElementVisitor.visitElement(JavaRecursiveElementVisitor.java:43)
    at com.intellij.psi.JavaElementVisitor.visitCodeBlock(JavaElementVisitor.java:52)
    at com.intellij.psi.impl.source.tree.java.PsiCodeBlockImpl.accept(PsiCodeBlockImpl.java:212)
    at com.intellij.psi.impl.source.tree.CompositePsiElement.acceptChildren(CompositePsiElement.java:81)
    at com.intellij.psi.JavaRecursiveElementVisitor.visitElement(JavaRecursiveElementVisitor.java:43)
ninja: build stopped: subcommand failed.
09:03:17 ninja failed with: exit status 1

此外,我在此页面上附加了一个更大的错误包:https://pastebin.com/YNN0fAp2

我该如何修复它?

java android-source
1个回答
-2
投票

使用有限的 RAM 编译 Android SDK 可能是一项具有挑战性的任务,因为 Android 的构建过程可能会占用大量资源。但是,如果您的系统 RAM 较低,则可以采用一些策略来使该过程更易于管理。请记住,Android SDK 是工具、库和 API 的集合,您通常不需要自己编译整个 SDK。您可能正在考虑从 Android 开源项目 (AOSP) 编译 Android,这是一个不同的且更耗费资源的过程。

如果您正在使用 AOSP 或其他需要编译的 Android 项目,这里有一些提示可以帮助您在有限的 RAM 下完成此操作:

  1. 增加交换空间:

    • 弥补 RAM 不足的一种方法是增加系统的交换空间。这允许您的系统在 RAM 不足时使用硬盘驱动器的一部分作为虚拟内存。但要小心,因为使用大量交换空间会显着减慢构建过程。
  2. 使用轻量级桌面环境:

    • 运行轻量级桌面环境或根本不运行桌面环境可以为构建过程释放更多 RAM。命令行界面 (CLI) 或 Openbox 等轻量级窗口管理器可以提供帮助。
  3. 优化您的构建环境:

    • 禁用任何不必要的后台进程或服务以释放 RAM。您还应该关闭任何其他应用程序以尽量减少内存使用。
  4. 交叉编译:

    • 如果你有能力更强的机器,可以考虑交叉编译。交叉编译涉及在功能更强大的系统上编译 Android,然后将编译后的二进制文件传输到低 RAM 计算机。这可能是一种更有效的方法。
  5. 使用CCache:

    • CCache 是一个编译器缓存,可以通过重用以前编译的对象来帮助加快重建速度。它可以节省时间并减少构建 Android 的内存需求。要启用 CCache,请遵循 AOSP 文档。
  6. 调整编译标志:

    • 运行
      -j
      时使用
      make
      标志来限制并行作业的数量。例如,
      make -j4
      将运行最多四个并行构建作业。根据您的可用 RAM 调整此数字;使用太多并行作业可能会导致内存使用过多。
  7. 限制您构建的内容:

    • 您不需要构建整个 AOSP 或 Android SDK。您可以使用相关构建目标或 make 命令指定要构建的特定模块或组件。这样,您可以通过仅构建您需要的内容来节省内存和时间。
  8. 分阶段构建:

    • 将构建过程分为几个阶段,一次构建一个部分。这有助于减少构建期间的内存使用。例如,与系统映像分开构建内核。
  9. 使用内存优化内核:

    • 一些自定义内核和配置可以针对低 RAM 使用进行优化。寻找优先考虑内存效率的内核配置。

请记住,使用低 RAM 构建 Android 可能会更慢,并且可能需要更多时间和耐心。监视系统资源并确保在编译过程中不会耗尽磁盘空间也是一个很好的做法。根据您的项目和可用资源,考虑使用基于云的服务或更强大的硬件来执行 AOSP 编译等资源密集型任务。

© www.soinside.com 2019 - 2024. All rights reserved.