Opened 4 months ago

Last modified 4 months ago

#69198 assigned defect

rust-bootstrap needs a lot of disk space to build

Reported by: ryandesign (Ryan Carsten Schmidt) Owned by: MarcusCalhoun-Lopez (Marcus Calhoun-Lopez)
Priority: Normal Milestone:
Component: ports Version: 2.9.0
Keywords: Cc:
Port: rust-bootstrap

Description

rust-bootstrap failed to build on a buildbot worker after consuming all 23GB of available disk space:

https://build.macports.org/builders/ports-10.12_x86_64-builder/builds/258909

LLVM ERROR: IO failure on output stream: No space left on device

Here is a build of rust-bootstrap-10.6 that finished with 4GB free after using 25GB of disk space:

https://build.macports.org/builders/ports-10.12_x86_64-builder/builds/258910

(so I'll retry the rust-bootstrap build since there's more free disk space now.)

Here is a build of rust-bootstrap-10.6 that barely succeeded with 2GB to spare after using 33GB of disk space:

https://build.macports.org/builders/ports-10.13_x86_64-builder/builds/219064

Is there any way to make these ports use less disk space while building? Are there any intermediate files that could be deleted partway through the build?

Change History (12)

comment:1 Changed 4 months ago by MarcusCalhoun-Lopez (Marcus Calhoun-Lopez)

I do not know of any way of minimizing disk space usage during the build.
One of the problems is probably LLVM.
It is built three different times, once for x86_64 and twice for i686 (since Rust considers this cross-compilation).
I can think of a few options.

  • Remove default_variants +universal. This is the easiest solution, but +universal is appropriate for those few of us who actually use the port.
  • Attempt to clean the directories after every architecture build. At least there would only be two builds of LLVM to deal with.
  • Try to create a separate LLVM port specifically for Rust. I do not know if this would make things easier or harder (more steps but more control over the LLVM build).
  • Restrict Rust support to x86_64 and arm64 on macOS >= 10.12. The sole reasons rust-bootstrap is to support older systems.

comment:2 Changed 4 months ago by jmroot (Joshua Root)

There's again probably not that much that can be done about it in the port, but it would also be nice if deleting the build directory for rust didn't take 30+ minutes.

comment:3 in reply to:  1 ; Changed 4 months ago by jmroot (Joshua Root)

Replying to MarcusCalhoun-Lopez:

  • Restrict Rust support to x86_64 and arm64 on macOS >= 10.12. The sole reasons rust-bootstrap is to support older systems.

This wouldn't reduce the disk space needed for builds, but could we at least reduce the number of builds by setting replaced_by on the platforms where each subport isn't needed? So for example rust-bootstrap-10.7 would do something like:

if {${os.major} == 9} {
    replaced_by rust-bootstrap-10.5
} elseif {${os.major} == 10} {
    replaced_by rust-bootstrap-10.6
} elseif {${os.major} >= 16} {
    replaced_by rust-bootstrap
}

comment:4 in reply to:  2 Changed 4 months ago by ryandesign (Ryan Carsten Schmidt)

Replying to jmroot:

it would also be nice if deleting the build directory for rust didn't take 30+ minutes.

Here I think you're talking about the macOS 13 and 14 x86_64 buildbot workers which are this slow because they boot from an external USB 3 hard drive and Apple has royally screwed the performance of hard drives (or maybe disks in general) in macOS 13. I mean it takes the machine 10–15 minutes just to boot up. It's a little better in macOS 14 but still inexcusable. The macOS 10.14, 10.11, and 10.8 workers are the other ones running on hard disks but they're internal. The macOS 10.14 builder "only" takes 12 minutes to clean up.

Last edited 4 months ago by ryandesign (Ryan Carsten Schmidt) (previous) (diff)

comment:5 in reply to:  1 ; Changed 4 months ago by ryandesign (Ryan Carsten Schmidt)

Replying to MarcusCalhoun-Lopez:

It is built three different times, once for x86_64 and twice for i686 (since Rust considers this cross-compilation).

Why twice for i386?

  • Attempt to clean the directories after every architecture build. At least there would only be two builds of LLVM to deal with.

This is the kind of thing I was talking about.

  • Try to create a separate LLVM port specifically for Rust. I do not know if this would make things easier or harder (more steps but more control over the LLVM build).

If rust is building its own private copy of llvm every time, yes, putting it in another port or subport could make a lot of sense. Maybe there are times when you are making a change to the port that only affects the private llvm, or only rust, so you could revbump just that subport and not have to rebuild the other part.

And, why can't they use our existing llvm ports like everyone else?

comment:6 Changed 4 months ago by mascguy (Christopher Nielsen)

Cc: mascguy added

comment:7 in reply to:  3 Changed 4 months ago by MarcusCalhoun-Lopez (Marcus Calhoun-Lopez)

Cc: mascguy removed

Replying to jmroot:

This wouldn't reduce the disk space needed for builds, but could we at least reduce the number of builds by setting replaced_by on the platforms where each subport isn't needed? So for example rust-bootstrap-10.7 would do something like:

if {${os.major} == 9} {
    replaced_by rust-bootstrap-10.5
} elseif {${os.major} == 10} {
    replaced_by rust-bootstrap-10.6
} elseif {${os.major} >= 16} {
    replaced_by rust-bootstrap
}

Please forgive me if I am not understanding your suggestion, but rust-bootstrap-10.5 isn't meant to be built on 10.5, it is meant to be built for 10.5.
None of the rust-bootstrap subports build on machines prior to 10.12 because the upstream provided Rust compiler does not run on them.

comment:8 Changed 4 months ago by jmroot (Joshua Root)

Ah, I see. In that case, they should produce a binary with no material differences regardless of which OS version they are built on, and could set platforms {darwin any >= 16}?

comment:9 in reply to:  5 ; Changed 4 months ago by MarcusCalhoun-Lopez (Marcus Calhoun-Lopez)

Replying to ryandesign:

Why twice for i386?

My understanding is that the x86_64 upstream stage0 compiler builds an x86_64 stage1 compiler which in turn builds an i386 stage2 compiler.

If rust is building its own private copy of llvm every time, yes, putting it in another port or subport could make a lot of sense. Maybe there are times when you are making a change to the port that only affects the private llvm, or only rust, so you could revbump just that subport and not have to rebuild the other part.

And, why can't they use our existing llvm ports like everyone else?

There was a time when Rust used the MacPorts LLVM.
However the consensus was that it was too difficult to keep track of Rust's LLVM fork.

Last edited 4 months ago by ryandesign (Ryan Carsten Schmidt) (previous) (diff)

comment:10 in reply to:  8 Changed 4 months ago by MarcusCalhoun-Lopez (Marcus Calhoun-Lopez)

Replying to jmroot:

Ah, I see. In that case, they should produce a binary with no material differences regardless of which OS version they are built on, and could set platforms {darwin any >= 16}?

rust-bootstrap already has platforms {darwin >= 16}
Are you suggesting that platforms {darwin any >= 16} is better?

comment:11 Changed 4 months ago by ryandesign (Ryan Carsten Schmidt)

{darwin >= 16} means it can be built on darwin 16 and later and that it builds differently on each darwin version. For example, usually the deployment target matches the OS version.

{darwin any >= 16} would mean it can be built on darwin 16 and later and that it builds essentially identically on each darwin version. For example, a port that installs only documentation, or game assets, or a precompiled binary downloaded from the developer's site would be identical on any OS version. any changes the archive filename so that it ends with .darwin_any.tbz2 instead of e.g. .darwin_16.tbz2. It means MacPorts on any user's system, regardless of OS version, will download the same archive. It means we only need to store one file on the packages server instead of one file per OS version. It also means that only one buildbot worker needs to build that archive. In practice, it isn't quite as efficient as that: if the buildbot was idle when a commit came through, all wokers will get notified to start their jobs at about the same time. They'll all check if the archive already exists on the server, which it doesn't, so they'll all do the build. But if the workers are busy when the commit comes through, maybe only the first worker to become available needs to build it because maybe by the time the second worker becomes available, the first one has already finished and uploaded the archive to the server.

So if it is true that rust-bootstrap builds essentially identically regardless of the OS version (e.g. it forces the same deployment target and it does nothing else that varies by OS version) then adding any would be correct and would save build time and server space.

comment:12 in reply to:  9 Changed 4 months ago by ryandesign (Ryan Carsten Schmidt)

Replying to MarcusCalhoun-Lopez:

However the consensus was that it was too difficult to keep track of Rust's LLVM fork.

Right, I assumed they had a fork. The question was why they need that. For example, if they're fixing bugs in llvm, maybe we'd like to have those bugfixes in the main llvm ports so that everyone could benefit, not just rust.

Note: See TracTickets for help on using tickets.