hashicorp/packer · error

failed to describe plugin binary

Error message

failed to describe plugin binary %q: %s

What it means

checkVersion runs the freshly downloaded plugin binary with `describe` to read its self-reported version; if that command fails, this ContinuableInstallError is returned so InstallLatest skips to the next candidate version. The binary couldn't be executed or produced no usable describe output.

Solutions

  1. Try running the binary directly: <plugin-path> describe — the OS error names the real cause
  2. Check the binary architecture matches the host (file <plugin-path>) and re-init to re-download the right asset
  3. Remount or relocate the plugin directory if it's on a noexec filesystem
  4. Delete the plugin from ~/.packer.d/plugins and re-run `packer init` for a clean download
  5. Update to a packer/plugin release where assets are correctly labeled for your platform

Example fix

// before (noexec /tmp)
$ packer init .
Error: failed to describe plugin binary "/tmp/packer-plugin...": fork/exec ...: permission denied
// after
export PACKER_PLUGIN_PATH=$HOME/.packer.d  # on exec-mounted fs
packer init .
Defensive patterns

Strategy: validation

Validate before calling

// after a failure, validate the binary can execute at all
import "os/exec"
out, err := exec.Command(binPath, "describe").CombinedOutput()
if err != nil {
    // e.g. fork/exec: permission denied => noexec mount or missing exec bit
    // e.g. exec format error => wrong architecture
    return fmt.Errorf("plugin binary %s not runnable: %v: %s", binPath, err, out)
}

Prevention

When it happens

Trigger: GetPluginDescription(binPath) fails — binary not executable (download lost the exec bit / noexec mount), corrupted/truncated download, wrong architecture for the host, or the plugin crashes on `describe`.

Common situations: Downloading a darwin/windows binary on linux due to mislabeled release assets; /home or /tmp mounted noexec; partial download from a flaky network; malicious/corrupted binary that fails to start.

Related errors


AI-assisted analysis of hashicorp/packer@eb36e3c3e4 (2026-09-05). Data as JSON: /api/errors/905b4211360c1342. Report an issue: GitHub.

Appendix: source

Thrown at packer/plugin-getter/plugins.go:984

func GetPluginDescription(pluginPath string) (pluginsdk.SetDescription, error) {
	out, err := exec.Command(pluginPath, "describe").Output()
	if err != nil {
		return pluginsdk.SetDescription{}, err
	}

	desc := pluginsdk.SetDescription{}
	err = json.Unmarshal(out, &desc)

	return desc, err
}

// checkVersion checks the described version of a plugin binary against the requested version constriant.
// A ContinuableInstallError is returned upon a version mismatch to indicate that the caller should try the next
// available version. A PrereleaseInstallError is returned to indicate an unsupported version install.
func checkVersion(binPath string, identifier string, version *goversion.Version) error {
	desc, err := GetPluginDescription(binPath)
	if err != nil {
		err := fmt.Errorf("failed to describe plugin binary %q: %s", binPath, err)
		return &ContinuableInstallError{Err: err}
	}
	descVersion, err := goversion.NewSemver(desc.Version)
	if err != nil {
		err := fmt.Errorf("invalid self-reported version %q: %s", desc.Version, err)
		return &ContinuableInstallError{Err: err}
	}
	if descVersion.Core().Compare(version.Core()) != 0 {
		err := fmt.Errorf("binary reported version (%q) is different from the expected %q, skipping", desc.Version, version.String())
		return &ContinuableInstallError{Err: err}
	}
	if version.Prerelease() != "" {
		return &PrereleaseInstallError{
			PluginSrc: identifier,
			Err:       errors.New("binary reported a pre-release version of " + version.String()),
		}
	}
	// Since only final releases can be installed remotely, a non-empty prerelease version

View on GitHub (pinned to eb36e3c3e4)