Repository: moby/moby
File: daemon/command/daemon.go (Go)

Code before:

	return &daemonCLI{
		Config:       cfg,
		configFile:   &opts.configFile,
		flags:        opts.flags,
		apiShutdown:  make(chan struct{}),
		apiTLSConfig: tlsConfig,
	}, nil
}

func (cli *daemonCLI) start(ctx context.Context) (err error) {
	configureProxyEnv(ctx, cli.Config.Proxies)
	if err := configureDaemonLogs(ctx, cli.Config.DaemonLogConfig); err != nil {
		return fmt.Errorf("failed to configure daemon logging: %w", err)
	}

	log.G(ctx).Info("Starting up")

	if cli.Config.Debug {
		debug.Enable()
	}

	// Verify platform-specific requirements before proceeding with daemon initialization
	if err := daemon.CheckSystem(); err != nil {
		return fmt.Errorf("system requirements not met: %w", err)
	}

	if rootless.RunningWithRootlessKit() && !cli.Config.IsRootless() {
		return errors.New("rootless mode needs to be enabled for running with RootlessKit")
	}

	// return human-friendly error before creating files
	if runtime.GOOS == "linux" && os.Geteuid() != 0 {
		return errors.New("dockerd needs to be started with root privileges. To run dockerd in rootless mode as an unprivileged user, see https://docs.docker.com/go/rootless/")
	}

	if err := setDefaultUmask(); err != nil {
		return err
	}

	// Create the daemon root before we create ANY other files (PID, or migrate keys)
	// to ensure the appropriate ACL is set (particularly relevant on Windows)
	if err := daemon.CreateDaemonRoot(cli.Config); err != nil {
		return err
	}

	if err := os.MkdirAll(cli.Config.ExecRoot, 0o700); err != nil {
		return err
	}

	potentiallyUnderRuntimeDir := []string{cli.Config.ExecRoot}

Review comment (suggestion):
Wondering if we should put it even earlier, e.g. in `newDaemonCLI` https://github.com/moby/moby/blob/397c7d65ccaa12b5858d6cbffb419be646cb7c5c/daemon/command/daemon.go#L85-L96


If we would, then errors produced would also show when running `dockerd --validate`; https://github.com/moby/moby/blob/397c7d65ccaa12b5858d6cbffb419be646cb7c5c/daemon/command/docker.go#L35-L46


Code after:

	// Verify platform-specific requirements.
	// This is checked early so that `dockerd --validate` also validates system requirements.
	if err := daemon.CheckSystem(); err != nil {
		return nil, fmt.Errorf("system requirements not met: %w", err)
	}

	return &daemonCLI{
		Config:       cfg,
		configFile:   &opts.configFile,
		flags:        opts.flags,
		apiShutdown:  make(chan struct{}),
		apiTLSConfig: tlsConfig,
	}, nil
}

func (cli *daemonCLI) start(ctx context.Context) (err error) {
	configureProxyEnv(ctx, cli.Config.Proxies)
	if err := configureDaemonLogs(ctx, cli.Config.DaemonLogConfig); err != nil {
		return fmt.Errorf("failed to configure daemon logging: %w", err)
	}

	log.G(ctx).Info("Starting up")

	if cli.Config.Debug {
		debug.Enable()
	}

	if rootless.RunningWithRootlessKit() && !cli.Config.IsRootless() {
		return errors.New("rootless mode needs to be enabled for running with RootlessKit")
	}

	// return human-friendly error before creating files
	if runtime.GOOS == "linux" && os.Geteuid() != 0 {
		return errors.New("dockerd needs to be started with root privileges. To run dockerd in rootless mode as an unprivileged user, see https://docs.docker.com/go/rootless/")
	}

	if err := setDefaultUmask(); err != nil {
		return err
	}

	// Create the daemon root before we create ANY other files (PID, or migrate keys)
	// to ensure the appropriate ACL is set (particularly relevant on Windows)
	if err := daemon.CreateDaemonRoot(cli.Config); err != nil {
		return err
	}

	if err := os.MkdirAll(cli.Config.ExecRoot, 0o700); err != nil {
		return err
	}