Skip to content

Commit

Permalink
Merge pull request #1350 from bgilbert/userdata
Browse files Browse the repository at this point in the history
Delete userdata from VirtualBox/VMware after Ignition completes
  • Loading branch information
bgilbert authored May 3, 2022
2 parents fd557bb + b0562e3 commit 4b70b44
Show file tree
Hide file tree
Showing 27 changed files with 3,342 additions and 290 deletions.
3 changes: 3 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -23,8 +23,11 @@ install: all
install -m 0644 -D -t $(DESTDIR)/usr/lib/dracut/modules.d/$${bn} $$x/*; \
done
chmod a+x $(DESTDIR)/usr/lib/dracut/modules.d/*/*.sh $(DESTDIR)/usr/lib/dracut/modules.d/*/*-generator
install -m 0644 -D -t $(DESTDIR)/usr/lib/systemd/system systemd/ignition-delete-config.service
install -m 0755 -D -t $(DESTDIR)/usr/lib/dracut/modules.d/30ignition bin/$(GOARCH)/ignition
install -m 0755 -D -t $(DESTDIR)/usr/bin bin/$(GOARCH)/ignition-validate
install -m 0755 -d $(DESTDIR)/usr/libexec
ln -sf ../lib/dracut/modules.d/30ignition/ignition $(DESTDIR)/usr/libexec/ignition-rmcfg

.PHONY: vendor
vendor:
Expand Down
3 changes: 1 addition & 2 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -6,18 +6,17 @@ require (
cloud.google.com/go v0.58.0
cloud.google.com/go/storage v1.9.0
github.com/aws/aws-sdk-go v1.30.28
github.com/beevik/etree v1.1.1-0.20200718192613-4a2f8b9d084c
github.com/coreos/go-semver v0.3.0
github.com/coreos/go-systemd/v22 v22.0.0
github.com/coreos/vcontext v0.0.0-20211021162308-f1dbbca7bef4
github.com/google/renameio v0.1.0
github.com/google/uuid v1.1.1
github.com/pin/tftp v2.1.0+incompatible
github.com/smartystreets/goconvey v0.0.0-20190222223459-a17d461953aa // indirect
github.com/spf13/pflag v1.0.6-0.20210604193023-d5e0c0615ace
github.com/stretchr/testify v1.7.0
github.com/vincent-petithory/dataurl v1.0.0
github.com/vmware/vmw-guestinfo v0.0.0-20220317130741-510905f0efa3
github.com/vmware/vmw-ovflib v0.0.0-20170608004843-1f217b9dc714
go.opencensus.io v0.22.5 // indirect
golang.org/x/net v0.0.0-20200602114024-627f9648deb9
golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d
Expand Down
12 changes: 2 additions & 10 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,8 @@ github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03
github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo=
github.com/aws/aws-sdk-go v1.30.28 h1:SaPM7dlmp7h3Lj1nJ4jdzOkTdom08+g20k7AU5heZYg=
github.com/aws/aws-sdk-go v1.30.28/go.mod h1:5zCpMtNQVjRREroY7sYe8lOMRSxkhG6MZveU8YkpAk0=
github.com/beevik/etree v1.1.1-0.20200718192613-4a2f8b9d084c h1:uYq6BD31fkfeNKQmfLj7ODcEfkb5JLsKrXVSqgnfGg8=
github.com/beevik/etree v1.1.1-0.20200718192613-4a2f8b9d084c/go.mod h1:0yGO2rna3S9DkITDWHY1bMtcY4IJ4w+4S+EooZUR0bE=
github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU=
github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI=
github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI=
Expand Down Expand Up @@ -115,8 +117,6 @@ github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+
github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg=
github.com/googleapis/gax-go/v2 v2.0.5 h1:sjZBwGj9Jlw33ImPtvFviGYvseOtDM7hkSKB7+Tv3SM=
github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk=
github.com/gopherjs/gopherjs v0.0.0-20181017120253-0766667cb4d1 h1:EGx4pi6eqNxGaHF6qqu48+N2wcFQ5qg5FXgOdqsJ5d8=
github.com/gopherjs/gopherjs v0.0.0-20181017120253-0766667cb4d1/go.mod h1:wJfORRmW1u3UXTncJ5qlYoELFm8eSnnEO6hX4iZ3EWY=
github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
github.com/hashicorp/golang-lru v0.5.1/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
github.com/ianlancetaylor/demangle v0.0.0-20181102032728-5e5cf60278f6/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc=
Expand All @@ -125,8 +125,6 @@ github.com/jmespath/go-jmespath v0.3.0/go.mod h1:9QtRXoHjLGCJ5IBSaohpXITPlowMeeY
github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU=
github.com/jstemmer/go-junit-report v0.9.1 h1:6QPYqodiu3GuPL+7mfx+NwDdp2eTkp9IfEUpgAwUN0o=
github.com/jstemmer/go-junit-report v0.9.1/go.mod h1:Brl9GWCQeLvo8nXZwPNNblvFj/XSXhF0NWZEnDohbsk=
github.com/jtolds/gls v4.2.1+incompatible h1:fSuqC+Gmlu6l/ZYAoZzx2pyucC8Xza35fpRVWLVmUEE=
github.com/jtolds/gls v4.2.1+incompatible/go.mod h1:QJZ7F/aHp+rZTRtaJ1ow/lLfFfVYBRgL+9YlvaHOwJU=
github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI=
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
Expand All @@ -140,10 +138,6 @@ github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZb
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA=
github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
github.com/smartystreets/assertions v0.0.0-20180927180507-b2de0cb4f26d h1:zE9ykElWQ6/NYmHa3jpm/yHnI4xSofP+UP6SpjHcSeM=
github.com/smartystreets/assertions v0.0.0-20180927180507-b2de0cb4f26d/go.mod h1:OnSkiWE9lh6wB0YB77sQom3nweQdgAjqCqsofrRNTgc=
github.com/smartystreets/goconvey v0.0.0-20190222223459-a17d461953aa h1:E+gaaifzi2xF65PbDmuKI3PhLWY6G5opMLniFq8vmXA=
github.com/smartystreets/goconvey v0.0.0-20190222223459-a17d461953aa/go.mod h1:2RVY1rIf+2J2o/IM9+vPq9RzmHDSseB7FoXiSNIUsoU=
github.com/spf13/pflag v1.0.6-0.20210604193023-d5e0c0615ace h1:9PNP1jnUjRhfmGMlkXHjYPishpcw4jpSt/V/xYY3FMA=
github.com/spf13/pflag v1.0.6-0.20210604193023-d5e0c0615ace/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
Expand All @@ -155,8 +149,6 @@ github.com/vincent-petithory/dataurl v1.0.0 h1:cXw+kPto8NLuJtlMsI152irrVw9fRDX8A
github.com/vincent-petithory/dataurl v1.0.0/go.mod h1:FHafX5vmDzyP+1CQATJn7WFKc9CvnvxyvZy6I1MrG/U=
github.com/vmware/vmw-guestinfo v0.0.0-20220317130741-510905f0efa3 h1:v6jG/tdl4O07LNVp74Nt7/OyL+1JsIW1M2f/nSvQheY=
github.com/vmware/vmw-guestinfo v0.0.0-20220317130741-510905f0efa3/go.mod h1:CSBTxrhePCm0cmXNKDGeu+6bOQzpaEklfCqEpn89JWk=
github.com/vmware/vmw-ovflib v0.0.0-20170608004843-1f217b9dc714 h1:wJqF3m4Tj8I4beSi6vGxIyNtsq6wwGqhK3UnA99ltL4=
github.com/vmware/vmw-ovflib v0.0.0-20170608004843-1f217b9dc714/go.mod h1:jiPk45kn7klhByRvUq5i2vo1RtHKBHj+iWGFpxbXuuI=
github.com/yuin/goldmark v1.1.25/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
go.opencensus.io v0.21.0/go.mod h1:mSImk1erAIZhrmZN+AvHh14ztQfjbGwt4TtuofqLduU=
Expand Down
60 changes: 57 additions & 3 deletions internal/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,10 +41,13 @@ import (
)

func main() {
if filepath.Base(os.Args[0]) == "ignition-apply" {
switch filepath.Base(os.Args[0]) {
case "ignition-apply":
ignitionApplyMain()
} else {
// otherwise, assume regular Ignition
case "ignition-rmcfg":
ignitionRmCfgMain()
default:
// assume regular Ignition
ignitionMain()
}
}
Expand Down Expand Up @@ -187,3 +190,54 @@ func ignitionApplyMain() {
os.Exit(1)
}
}

func ignitionRmCfgMain() {
flags := struct {
logToStdout bool
platform string
version bool
}{}
pflag.StringVar(&flags.platform, "platform", "", fmt.Sprintf("current platform. %v", platform.Names()))
pflag.BoolVar(&flags.logToStdout, "log-to-stdout", false, "log to stdout instead of the system log")
pflag.BoolVar(&flags.version, "version", false, "print the version and exit")
pflag.Usage = func() {
fmt.Fprintf(pflag.CommandLine.Output(), "Usage: %s [options]\n", os.Args[0])
fmt.Fprintf(pflag.CommandLine.Output(), "Options:\n")
pflag.PrintDefaults()
}
pflag.Parse()

if flags.version {
fmt.Printf("%s\n", version.String)
return
}

if pflag.NArg() != 0 {
pflag.Usage()
os.Exit(2)
}

if flags.platform == "" {
fmt.Fprint(os.Stderr, "'--platform' must be provided\n")
os.Exit(2)
}

logger := log.New(flags.logToStdout)
defer logger.Close()

logger.Info(version.String)

platformConfig := platform.MustGet(flags.platform)
fetcher, err := platformConfig.NewFetcherFunc()(&logger)
if err != nil {
logger.Crit("failed to generate fetcher: %s", err)
os.Exit(3)
}

if err := platformConfig.DelConfig(&fetcher); err != nil {
logger.Crit("couldn't delete config: %s", err)
os.Exit(1)
}

logger.Info("Successfully deleted config")
}
24 changes: 20 additions & 4 deletions internal/platform/platform.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
package platform

import (
"errors"
"fmt"

"github.com/coreos/ignition/v2/internal/log"
Expand Down Expand Up @@ -44,13 +45,18 @@ import (
"github.com/coreos/ignition/v2/internal/resource"
)

var (
ErrCannotDelete = errors.New("cannot delete config on this platform")
)

// Config represents a set of options that map to a particular platform.
type Config struct {
name string
fetch providers.FuncFetchConfig
init providers.FuncInit
newFetcher providers.FuncNewFetcher
status providers.FuncPostStatus
delConfig providers.FuncDelConfig
}

func (c Config) Name() string {
Expand Down Expand Up @@ -93,6 +99,14 @@ func (c Config) Status(stageName string, f resource.Fetcher, statusErr error) er
return nil
}

func (c Config) DelConfig(f *resource.Fetcher) error {
if c.delConfig != nil {
return c.delConfig(f)
} else {
return ErrCannotDelete
}
}

var configs = registry.Create("platform configs")

func init() {
Expand Down Expand Up @@ -172,12 +186,14 @@ func init() {
fetch: qemu.FetchConfig,
})
configs.Register(Config{
name: "virtualbox",
fetch: virtualbox.FetchConfig,
name: "virtualbox",
fetch: virtualbox.FetchConfig,
delConfig: virtualbox.DelConfig,
})
configs.Register(Config{
name: "vmware",
fetch: vmware.FetchConfig,
name: "vmware",
fetch: vmware.FetchConfig,
delConfig: vmware.DelConfig,
})
configs.Register(Config{
name: "vultr",
Expand Down
1 change: 1 addition & 0 deletions internal/providers/providers.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,3 +32,4 @@ type FuncFetchConfig func(f *resource.Fetcher) (types.Config, report.Report, err
type FuncInit func(f *resource.Fetcher) error
type FuncNewFetcher func(logger *log.Logger) (resource.Fetcher, error)
type FuncPostStatus func(stageName string, f resource.Fetcher, e error) error
type FuncDelConfig func(f *resource.Fetcher) error
90 changes: 86 additions & 4 deletions internal/providers/virtualbox/virtualbox.c
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,10 @@
#include <errno.h>
#include "virtualbox.h"

// From virtualbox/include/VBox/HostServices/GuestPropertySvc.h
#define GUEST_PROP_FN_GET_PROP 1
#define GUEST_PROP_FN_DEL_PROP 4

static void _cleanup_close(int *fd) {
if (*fd != -1) {
close(*fd);
Expand Down Expand Up @@ -86,13 +90,16 @@ static int connect(int fd, uint32_t *client_id) {
}

static int get_prop(int fd, uint32_t client_id, const char *name, void **value, size_t *size) {
// xref VbglR3GuestPropRead() in
// virtualbox/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR3LibGuestProp.cpp

// init header
size_t msg_size = sizeof(struct vbg_ioctl_hgcm_call) + 4 * sizeof(struct vmmdev_hgcm_function_parameter64);
struct vbg_ioctl_hgcm_call _cleanup_free_ *msg = calloc(1, msg_size);
// init_header re-adds the size of msg->hdr
init_header(&msg->hdr, msg_size - sizeof(msg->hdr), msg_size - sizeof(msg->hdr));
msg->client_id = client_id;
msg->function = 1; // GUEST_PROP_FN_GET_PROP
msg->function = GUEST_PROP_FN_GET_PROP;
msg->timeout_ms = -1; // inf
msg->interruptible = 1;
msg->parm_count = 4;
Expand Down Expand Up @@ -147,6 +154,38 @@ static int get_prop(int fd, uint32_t client_id, const char *name, void **value,
}
}

static int del_prop(int fd, uint32_t client_id, const char *name) {
// xref VbglR3GuestPropDelete() in
// virtualbox/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR3LibGuestProp.cpp

// init header
size_t msg_size = sizeof(struct vbg_ioctl_hgcm_call) + sizeof(struct vmmdev_hgcm_function_parameter64);
struct vbg_ioctl_hgcm_call _cleanup_free_ *msg = calloc(1, msg_size);
// init_header re-adds the size of msg->hdr
init_header(&msg->hdr, msg_size - sizeof(msg->hdr), msg_size - sizeof(msg->hdr));
msg->client_id = client_id;
msg->function = GUEST_PROP_FN_DEL_PROP;
msg->timeout_ms = -1; // inf
msg->interruptible = 1;
msg->parm_count = 1;

// init arguments
struct vmmdev_hgcm_function_parameter64 *params = (void *) (msg + 1);
// property name (in)
params[0].type = VMMDEV_HGCM_PARM_TYPE_LINADDR_IN;
params[0].u.pointer.size = strlen(name) + 1;
params[0].u.pointer.u.linear_addr = (uintptr_t) name;

// delete value
if (ioctl(fd, VBG_IOCTL_HGCM_CALL_64(msg_size), msg)) {
return VERR_GENERAL_FAILURE;
}
if (msg->hdr.rc != VINF_SUCCESS) {
return msg->hdr.rc;
}
return VINF_SUCCESS;
}

static int disconnect(int fd, uint32_t client_id) {
struct vbg_ioctl_hgcm_disconnect msg = {
.u = {
Expand All @@ -162,7 +201,7 @@ static int disconnect(int fd, uint32_t client_id) {
return msg.hdr.rc;
}

int virtualbox_get_guest_property(char *name, void **value, size_t *size) {
static int start_connection(uint32_t *client_id) {
// clear any previous garbage in errno for error returns
errno = 0;

Expand All @@ -179,12 +218,26 @@ int virtualbox_get_guest_property(char *name, void **value, size_t *size) {
}

// connect to property service
uint32_t client_id;
ret = connect(fd, &client_id);
ret = connect(fd, client_id);
if (ret != VINF_SUCCESS) {
return ret;
}

// return fd
ret = fd;
fd = -1;
return ret;
}

int virtualbox_get_guest_property(char *name, void **value, size_t *size) {
// connect
uint32_t client_id;
int ret = start_connection(&client_id);
if (ret < 0) {
return ret;
}
int _cleanup_close_ fd = ret;

// get property
ret = get_prop(fd, client_id, name, value, size);
if (ret != VINF_SUCCESS) {
Expand All @@ -206,3 +259,32 @@ int virtualbox_get_guest_property(char *name, void **value, size_t *size) {
errno = 0;
return 0;
}

int virtualbox_delete_guest_property(char *name) {
// connect
uint32_t client_id;
int ret = start_connection(&client_id);
if (ret < 0) {
return ret;
}
int _cleanup_close_ fd = ret;

// delete property
ret = del_prop(fd, client_id, name);
if (ret != VINF_SUCCESS) {
disconnect(fd, client_id);
return ret;
}

// disconnect
ret = disconnect(fd, client_id);
if (ret != VINF_SUCCESS) {
// we could ignore the failure, but better to make sure bugs
// are noticed
return ret;
}

// for clarity, ensure the Go error return is nil
errno = 0;
return 0;
}
31 changes: 31 additions & 0 deletions internal/providers/virtualbox/virtualbox.go
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,19 @@ func FetchConfig(f *resource.Fetcher) (types.Config, report.Report, error) {
return util.ParseConfig(f.Logger, config)
}

func DelConfig(f *resource.Fetcher) error {
f.Logger.Info("deleting Ignition config from VirtualBox guest property")
err := deleteProperty(configEncodingProperty)
if err != nil {
return err
}
err = deleteProperty(configProperty)
if err != nil {
return err
}
return nil
}

func fetchProperty(name string) ([]byte, error) {
cName := C.CString(name)
defer C.free(unsafe.Pointer(cName))
Expand Down Expand Up @@ -96,3 +109,21 @@ func fetchProperty(name string) ([]byte, error) {
}
return s[0:len], nil
}

func deleteProperty(name string) error {
cName := C.CString(name)
defer C.free(unsafe.Pointer(cName))

ret, errno := C.virtualbox_delete_guest_property(cName)
if ret != C.VINF_SUCCESS {
if ret == C.VERR_GENERAL_FAILURE && errno != nil {
return fmt.Errorf("deleting VirtualBox guest property %q: %w", name, errno)
}
if ret == C.VERR_PERMISSION_DENIED {
return fmt.Errorf("deleting VirtualBox guest property %q: permission denied; is the property read-only?", name)
}
// see <linux/vbox_err.h>
return fmt.Errorf("deleting VirtualBox guest property %q: error %d", name, ret)
}
return nil
}
Loading

0 comments on commit 4b70b44

Please sign in to comment.