From ab4ad2a3d12c60e71f5e3eb3e2dc4fe9c4ae8d4f Mon Sep 17 00:00:00 2001 From: Alberto Carretero Date: Tue, 21 Jan 2025 18:33:34 +0100 Subject: [PATCH] some ideas --- internal/deb/extract.go | 12 +++++++++--- internal/fsutil/create.go | 19 +++++++++++++++++++ 2 files changed, 28 insertions(+), 3 deletions(-) diff --git a/internal/deb/extract.go b/internal/deb/extract.go index e7429c16..b7670b33 100644 --- a/internal/deb/extract.go +++ b/internal/deb/extract.go @@ -213,7 +213,8 @@ func extractData(pkgReader io.ReadSeeker, options *ExtractOptions) error { delete(tarDirMode, path) createOptions := &fsutil.CreateOptions{ - Path: filepath.Join(options.TargetDir, path), + Root: options.TargetDir, + Path: path, Mode: mode, MakeParents: true, } @@ -237,7 +238,8 @@ func extractData(pkgReader io.ReadSeeker, options *ExtractOptions) error { // Create the entry itself. createOptions := &fsutil.CreateOptions{ - Path: filepath.Join(options.TargetDir, targetPath), + Root: options.TargetDir, + Path: targetPath, Mode: tarHeader.FileInfo().Mode(), Data: pathReader, Link: link, @@ -342,7 +344,8 @@ func extractHardLinks(pkgReader io.ReadSeeker, opts *extractHardLinkOptions) err absLink := filepath.Join(opts.TargetDir, links[0].path) // Extract the content to the first hard link path. createOptions := &fsutil.CreateOptions{ - Path: absLink, + Root: opts.TargetDir, + Path: links[0].path, Mode: tarHeader.FileInfo().Mode(), Data: tarReader, } @@ -354,6 +357,9 @@ func extractHardLinks(pkgReader io.ReadSeeker, opts *extractHardLinkOptions) err // Create the remaining hard links. for _, link := range links[1:] { createOptions := &fsutil.CreateOptions{ + // TODO should Root also be taken into account for Link? How do + // we create relative symlinks then. We can validate that it is + // inside though and preserve Link. Path: filepath.Join(opts.TargetDir, link.path), Mode: tarHeader.FileInfo().Mode(), // Link to the first file extracted for the hard links. diff --git a/internal/fsutil/create.go b/internal/fsutil/create.go index 92b1592f..87f31af4 100644 --- a/internal/fsutil/create.go +++ b/internal/fsutil/create.go @@ -9,9 +9,13 @@ import ( "io/fs" "os" "path/filepath" + "strings" ) type CreateOptions struct { + // Root defaults to "/" if empty. + Root string + // Path is relative to Root. Path string Mode fs.FileMode Data io.Reader @@ -45,6 +49,21 @@ func Create(options *CreateOptions) (*Entry, error) { optsCopy.Data = rp o := &optsCopy + if o.Root == "" { + o.Root = "/" + } + o.Path = filepath.Clean(filepath.Join(o.Root, o.Path)) + if !strings.HasPrefix(o.Path, o.Root) { + return nil, fmt.Errorf("TODO") + } + o.Link = filepath.Clean(o.Link) + if filepath.IsAbs(o.Link) { + if !strings.HasPrefix(o.Link) { + return nil, fmt.Errorf("TODO") + } + } + // TODO check for relative? + var err error var hash string if o.MakeParents {