@@ -21,6 +21,7 @@ import (
2121 "bufio"
2222 "flag"
2323 "fmt"
24+ "io"
2425 "os"
2526 "os/exec"
2627 "path/filepath"
@@ -168,6 +169,7 @@ func (l *Ldconfig) UpdateLDCache() error {
168169 return fmt .Errorf ("failed to write %s drop-in: %w" , ldsoconfdFilenamePattern , err )
169170 }
170171
172+ systemSearchPaths := l .getSystemSearchPaths ()
171173 // In most cases, the hook will be executing a host ldconfig that may be configured widely
172174 // differently from what the container image expects.
173175 // The common case is Debian-like (e.g. Debian, Ubuntu) vs non-Debian-like (e.g. RHEL, Fedora).
@@ -176,10 +178,15 @@ func (l *Ldconfig) UpdateLDCache() error {
176178 // paths to a drop-in conf file that is likely to be last in lexicographic order. Entries in the
177179 // top-level ld.so.conf file may be processed after this drop-in, but this hook does not modify
178180 // the top-level file if it exists.
179- if err := createLdsoconfdFile (defaultLdsoconfdDir , ldsoconfdSystemDirsFilenamePattern , l . getSystemSearchPaths () ... ); err != nil {
181+ if err := createLdsoconfdFile (defaultLdsoconfdDir , ldsoconfdSystemDirsFilenamePattern , systemSearchPaths ... ); err != nil {
180182 return fmt .Errorf ("failed to write %s drop-in: %w" , ldsoconfdSystemDirsFilenamePattern , err )
181183 }
182184
185+ // Also output the folders to the alpine .path file as required.
186+ if err := createAlpinePathFileIfRequired (append (filteredDirectories , systemSearchPaths ... )... ); err != nil {
187+ return err
188+ }
189+
183190 return SafeExec (ldconfigPath , args , nil )
184191}
185192
@@ -246,23 +253,30 @@ func createLdsoconfdFile(ldsoconfdDir, pattern string, dirs ...string) error {
246253 _ = configFile .Close ()
247254 }()
248255
256+ if err := outputListToFile (configFile , dirs ... ); err != nil {
257+ return err
258+ }
259+
260+ // The created file needs to be world readable for the cases where the container is run as a non-root user.
261+ if err := configFile .Chmod (0644 ); err != nil {
262+ return fmt .Errorf ("failed to chmod config file: %w" , err )
263+ }
264+
265+ return nil
266+ }
267+
268+ func outputListToFile (w io.Writer , dirs ... string ) error {
249269 added := make (map [string ]bool )
250270 for _ , dir := range dirs {
251271 if added [dir ] {
252272 continue
253273 }
254- _ , err := fmt .Fprintf (configFile , "%s\n " , dir )
274+ _ , err := fmt .Fprintf (w , "%s\n " , dir )
255275 if err != nil {
256276 return fmt .Errorf ("failed to update config file: %w" , err )
257277 }
258278 added [dir ] = true
259279 }
260-
261- // The created file needs to be world readable for the cases where the container is run as a non-root user.
262- if err := configFile .Chmod (0644 ); err != nil {
263- return fmt .Errorf ("failed to chmod config file: %w" , err )
264- }
265-
266280 return nil
267281}
268282
@@ -360,6 +374,38 @@ func processLdsoconfFile(ldsoconfFilename string) ([]string, []string, error) {
360374 return directories , includedFilenames , nil
361375}
362376
377+ func createAlpinePathFileIfRequired (dirs ... string ) error {
378+ if ! isAlpine () {
379+ return nil
380+ }
381+
382+ var pathFileName string
383+ switch runtime .GOARCH {
384+ case "amd64" :
385+ pathFileName = "/etc/ld-musl-x86_64.path"
386+ case "arm64" :
387+ pathFileName = "/etc/ld-musl-aarch64.path"
388+ }
389+
390+ pathFile , err := os .OpenFile (pathFileName , os .O_CREATE | os .O_APPEND | os .O_RDWR , 0644 )
391+ if err != nil {
392+ return fmt .Errorf ("could not open .path file: %w" , err )
393+ }
394+ defer func () {
395+ _ = pathFile .Close ()
396+ }()
397+
398+ return outputListToFile (pathFile , dirs ... )
399+ }
400+
401+ func isAlpine () bool {
402+ info , err := os .Stat ("/etc/alpine-release" )
403+ if err != nil {
404+ return false
405+ }
406+ return ! info .IsDir ()
407+ }
408+
363409// isDebianLike returns true if a Debian-like distribution is detected.
364410// Debian-like distributions include Debian and Ubuntu, whereas non-Debian-like
365411// distributions include RHEL and Fedora.
0 commit comments