Skip to content

Commit 5a47c5e

Browse files
committed
Add lib support as an option
Some images like `criu` will have extra libs that it requires. This adds lib support via LD_LIBRARY_PATH and InstallOpts Signed-off-by: Michael Crosby <[email protected]>
1 parent 1537f31 commit 5a47c5e

9 files changed

Lines changed: 101 additions & 11 deletions

File tree

archive/tar.go

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -158,7 +158,11 @@ func applyNaive(ctx context.Context, root string, tr *tar.Reader, options ApplyO
158158
// Normalize name, for safety and for a simple is-root check
159159
hdr.Name = filepath.Clean(hdr.Name)
160160

161-
if !options.Filter(hdr) {
161+
accept, err := options.Filter(hdr)
162+
if err != nil {
163+
return 0, err
164+
}
165+
if !accept {
162166
continue
163167
}
164168

archive/tar_opts.go

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,11 +22,11 @@ import "archive/tar"
2222
type ApplyOpt func(options *ApplyOptions) error
2323

2424
// Filter specific files from the archive
25-
type Filter func(*tar.Header) bool
25+
type Filter func(*tar.Header) (bool, error)
2626

2727
// all allows all files
28-
func all(_ *tar.Header) bool {
29-
return true
28+
func all(_ *tar.Header) (bool, error) {
29+
return true, nil
3030
}
3131

3232
// WithFilter uses the filter to select which files are to be extracted.

cmd/ctr/commands/install/install.go

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
package install
1818

1919
import (
20+
"github.com/containerd/containerd"
2021
"github.com/containerd/containerd/cmd/ctr/commands"
2122
"github.com/urfave/cli"
2223
)
@@ -27,6 +28,16 @@ var Command = cli.Command{
2728
Usage: "install a new package",
2829
ArgsUsage: "<ref>",
2930
Description: "install a new package",
31+
Flags: []cli.Flag{
32+
cli.BoolFlag{
33+
Name: "libs,l",
34+
Usage: "install libs from the image",
35+
},
36+
cli.BoolFlag{
37+
Name: "replace,r",
38+
Usage: "replace any binaries or libs in the opt directory",
39+
},
40+
},
3041
Action: func(context *cli.Context) error {
3142
client, ctx, cancel, err := commands.NewClient(context)
3243
if err != nil {
@@ -38,6 +49,13 @@ var Command = cli.Command{
3849
if err != nil {
3950
return err
4051
}
41-
return client.Install(ctx, image)
52+
var opts []containerd.InstallOpts
53+
if context.Bool("libs") {
54+
opts = append(opts, containerd.WithInstallLibs)
55+
}
56+
if context.Bool("replace") {
57+
opts = append(opts, containerd.WithInstallReplace)
58+
}
59+
return client.Install(ctx, image, opts...)
4260
},
4361
}

install.go

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ package containerd
1919
import (
2020
"archive/tar"
2121
"context"
22-
"errors"
22+
"os"
2323
"path/filepath"
2424

2525
introspectionapi "github.com/containerd/containerd/api/services/introspection/v1"
@@ -28,10 +28,11 @@ import (
2828
"github.com/containerd/containerd/content"
2929
"github.com/containerd/containerd/images"
3030
"github.com/containerd/containerd/platforms"
31+
"github.com/pkg/errors"
3132
)
3233

3334
// Install a binary image into the opt service
34-
func (c *Client) Install(ctx context.Context, image Image) error {
35+
func (c *Client) Install(ctx context.Context, image Image, opts ...InstallOpts) error {
3536
resp, err := c.IntrospectionService().Plugins(ctx, &introspectionapi.PluginsRequest{
3637
Filters: []string{
3738
"id==opt",
@@ -47,6 +48,10 @@ func (c *Client) Install(ctx context.Context, image Image) error {
4748
if path == "" {
4849
return errors.New("opt path not exported")
4950
}
51+
var config InstallConfig
52+
for _, o := range opts {
53+
o(&config)
54+
}
5055
var (
5156
cs = image.ContentStore()
5257
platform = platforms.Default()
@@ -66,8 +71,18 @@ func (c *Client) Install(ctx context.Context, image Image) error {
6671
return err
6772
}
6873
defer r.Close()
69-
if _, err := archive.Apply(ctx, path, r, archive.WithFilter(func(hdr *tar.Header) bool {
70-
return filepath.Dir(hdr.Name) == "bin"
74+
if _, err := archive.Apply(ctx, path, r, archive.WithFilter(func(hdr *tar.Header) (bool, error) {
75+
d := filepath.Dir(hdr.Name)
76+
result := d == "bin"
77+
if config.Libs {
78+
result = result || d == "lib"
79+
}
80+
if result && !config.Replace {
81+
if _, err := os.Lstat(filepath.Join(path, hdr.Name)); err == nil {
82+
return false, errors.Errorf("cannot replace %s in %s", hdr.Name, path)
83+
}
84+
}
85+
return result, nil
7186
})); err != nil {
7287
return err
7388
}

install_opts.go

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
/*
2+
Copyright The containerd Authors.
3+
4+
Licensed under the Apache License, Version 2.0 (the "License");
5+
you may not use this file except in compliance with the License.
6+
You may obtain a copy of the License at
7+
8+
http://www.apache.org/licenses/LICENSE-2.0
9+
10+
Unless required by applicable law or agreed to in writing, software
11+
distributed under the License is distributed on an "AS IS" BASIS,
12+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
See the License for the specific language governing permissions and
14+
limitations under the License.
15+
*/
16+
17+
package containerd
18+
19+
// InstallOpts configures binary installs
20+
type InstallOpts func(*InstallConfig)
21+
22+
// InstallConfig sets the binary install configuration
23+
type InstallConfig struct {
24+
// Libs installs libs from the image
25+
Libs bool
26+
// Replace will overwrite existing binaries or libs in the opt directory
27+
Replace bool
28+
}
29+
30+
// WithInstallLibs installs libs from the image
31+
func WithInstallLibs(c *InstallConfig) {
32+
c.Libs = true
33+
}
34+
35+
// WithInstallReplace will replace existing files
36+
func WithInstallReplace(c *InstallConfig) {
37+
c.Replace = true
38+
}

services/opt/service.go

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ import (
2020
"fmt"
2121
"os"
2222
"path/filepath"
23+
"runtime"
2324

2425
"github.com/containerd/containerd/plugin"
2526
"github.com/pkg/errors"
@@ -49,6 +50,15 @@ func init() {
4950
if err := os.Setenv("PATH", fmt.Sprintf("%s:%s", bin, os.Getenv("PATH"))); err != nil {
5051
return nil, errors.Wrapf(err, "set binary image directory in path %s", bin)
5152
}
53+
if runtime.GOOS != "windows" {
54+
lib := filepath.Join(path, "lib")
55+
if err := os.MkdirAll(lib, 0711); err != nil {
56+
return nil, err
57+
}
58+
if err := os.Setenv("LD_LIBRARY_PATH", fmt.Sprintf("%s:%s", os.Getenv("LD_LIBRARY_PATH"), lib)); err != nil {
59+
return nil, errors.Wrapf(err, "set binary lib directory in path %s", lib)
60+
}
61+
}
5262
return &manager{}, nil
5363
},
5464
})

vendor.conf

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
github.com/containerd/go-runc 14606eb66abd9e834e3bd22a4f5f46a3aad54c54
1+
github.com/containerd/go-runc edcf3de1f4971445c42d61f20d506b30612aa031
22
github.com/containerd/console 4d8a41f4ce5b9bae77c41786ea2458330f43f081
33
github.com/containerd/cgroups 5e610833b72089b37d0e615de9a92dfc043757c2
44
github.com/containerd/typeurl a93fcdb778cd272c6e9b3028b2f42d813e785d40

vendor/github.com/containerd/go-runc/command_linux.go

Lines changed: 2 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

vendor/github.com/containerd/go-runc/command_other.go

Lines changed: 4 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)