Opened 3 months ago
Last modified 3 months ago
#70539 new defect
base: failure for building some ports (depending on conditions) when Macports is installed at deeper directory hierarchy with "--prefix" option
Reported by: | nanigashi-uji (Nanigashi Uji) | Owned by: | |
---|---|---|---|
Priority: | Normal | Milestone: | |
Component: | base | Version: | 2.10.0 |
Keywords: | Cc: | ||
Port: |
Description
I have installed Macports as follows
% tar xvf MacPorts-2.9.3.tar.bz2 % cd MacPorts-2.9.3 % ./configure --prefix=${HOME}/Documents/workspace/opr/depot/macports-2.9.3.arm64 \ --with-no-root-privileges --enable-readline \ --enable-shared --without-startupitems \ --with-applications-dir=${HOME}/Documents/workspace/opr/depot/macports-2.9.3.arm64/Applications \ --with-frameworks-dir=${HOME}/Documents/workspace/opr/depot/macports-2.9.3.arm64/Library/Frameworks % make && make install && ${HOME}/Documents/workspace/opr/depot/macports-2.9.3.arm64/bin/port -v selfupdate
Then we can basically use port command with out trouble, but sometimes we fail to build some ports almost randomly. The reason why some ports are failed to be build is intermediate file name become longer than the FILENAME_MAX or PATH_MAX of macOS. One of the reason of the too long intermediate filename is that "${portbuildpath}" is generated based on the full path of Portfile like "${prefix}/var/macports/build/_Users_{username}_Documents_workspace_opr_depot_macports-2.9.3.arm64_var_macports_sources_rsync.macports.org_macports_release_tarballs_ports_{category}_{portname}" in the example above.
So, I propose to modify "macports.tcl" as follows to reduce the possibility the probability of the error due to too long filename during the build.
diff -rupN MacPorts-2.10.0.orig/src/macports1.0/macports.tcl MacPorts-2.10.0/src/macports1.0/macports.tcl --- MacPorts-2.10.0.orig/src/macports1.0/macports.tcl 2024-08-07 23:17:43 +++ MacPorts-2.10.0/src/macports1.0/macports.tcl 2024-08-13 20:25:36 @@ -3028,16 +3028,29 @@ proc _source_is_obsolete_svn_repo {source_dir} { return 0 } +proc macports::trim_prefix {fullpath prefix} { + set fullpath [file normalize $fullpath] + set prefix [file normalize $prefix] + if {[string first $prefix $fullpath] != 0} { + return $fullpath + } + set relative_path [string range $fullpath [string length $prefix] end] + set relative_path [string trimleft $relative_path "/\\"] + return $relative_path +} + proc macports::getportbuildpath {id {portname {}}} { variable portdbpath - regsub {://} $id {.} port_path + set s_id [macports::trim_prefix $id [file join $portdbpath sources]] + regsub {://} $s_id {.} port_path regsub -all {/} $port_path {_} port_path return [file join $portdbpath build $port_path $portname] } proc macports::getportlogpath {id {portname {}}} { variable portdbpath - regsub {://} $id {.} port_path + set s_id [macports::trim_prefix $id [file join $portdbpath sources]] + regsub {://} $s_id {.} port_path regsub -all {/} $port_path {_} port_path return [file join $portdbpath logs $port_path $portname] } diff -rupN MacPorts-2.10.0.orig/src/port1.0/tests/portutil.test MacPorts-2.10.0/src/port1.0/tests/portutil.test --- MacPorts-2.10.0.orig/src/port1.0/tests/portutil.test 2024-08-07 23:17:43 +++ MacPorts-2.10.0/src/port1.0/tests/portutil.test 2024-08-13 20:25:56 @@ -52,9 +52,21 @@ proc init_eval_targets {} { set mport [mportopen file://.] + proc trim_prefix {fullpath prefix} { + set fullpath [file normalize $fullpath] + set prefix [file normalize $prefix] + if {[string first $prefix $fullpath] != 0} { + return $fullpath + } + set relative_path [string range $fullpath [string length $prefix] end] + set relative_path [string trimleft $relative_path "/\\"] + return $relative_path + } + proc getportbuildpath {id {portname ""}} { global portdbpath - regsub {://} $id {.} port_path + set s_id [trim_prefix $id [file join $portdbpath sources]] + regsub {://} $s_id {.} port_patha regsub -all {/} $port_path {_} port_path return [file join $portdbpath build $port_path $portname] }
Attachments (2)
Change History (9)
Changed 3 months ago by nanigashi-uji (Nanigashi Uji)
Attachment: | MacPorts-2.10.0.diff added |
---|
Changed 3 months ago by nanigashi-uji (Nanigashi Uji)
Attachment: | macports-1.0-buildpath-truncate.patch added |
---|
comment:1 Changed 3 months ago by ryandesign (Ryan Carsten Schmidt)
comment:2 Changed 3 months ago by nanigashi-uji (Nanigashi Uji)
The build/log path become as follows:
${prefix}/var/macports/build/rsync.macports.org_macports_release_tarballs_ports_{category}_{portname}
and
${prefix}/var/macports/logs/rsync.macports.org_macports_release_tarballs_ports_{category}_{portname}
comment:3 Changed 3 months ago by ryandesign (Ryan Carsten Schmidt)
That seems like an improvement. It is of course possible to build ports that are not in one of the configured ports trees. I assume in that case the full path will still be used as before.
comment:4 follow-up: 6 Changed 3 months ago by jmroot (Joshua Root)
If we abbreviate the path at all, we need to handle collisions, maybe by storing the full path in a file. And if we're doing that, maybe we might as well abandon any attempt at human-readability and just use something like a short checksum of the path. Most of the time you're going to be using command like port work
to find the path anyway, and if you have to look in there manually, the next subdir down still has the subport name.
comment:5 Changed 3 months ago by jmroot (Joshua Root)
There will also need to be a script that moves existing old-style paths to their new-style equivalent when upgrading.
comment:6 Changed 3 months ago by ryandesign (Ryan Carsten Schmidt)
comment:7 Changed 3 months ago by nanigashi-uji (Nanigashi Uji)
The above patch keeps the paths for each port under "${prefix}/var/macports/sources", so there is no problem in terms of avoiding conflicts between ports, and the full path can be reproduced by adding "${portdbpath}/sources" at the beginning. On the other hand, in the original code, if "${prefix}" contains "_", the name conversion is not one-to-one mapping, so this is not the best method, I think.
I've also encountered some build failures due to too-long paths.
I haven't tried your code… could you give an example of what the build/log path would be after your changes?