commaai/openpilot · error

clip encoding failed: %s

Error message

clip encoding failed: %s

What it means

Printed by encoderd's --clip error handler when any exception escapes clip setup or encode_clip(): std::stoi/std::stod conversion failures ("stod"), the explicit invalid_argument messages from the option parser ('missing clip option value', 'unknown clip option: X', 'missing clip input'), or errors raised inside encode_clip itself. It prints e.what() and exits 1.

Source

Thrown at openpilot/system/loggerd/encoderd.cc:207

      int bitrate = 5'000'000;
      int speedup = 1;
      std::string metadata;
      int input_arg = 5;
      while (input_arg < argc && std::string(argv[input_arg]).rfind("--", 0) == 0) {
        const std::string option = argv[input_arg++];
        if (option == "--") break;
        if (input_arg == argc) throw std::invalid_argument("missing clip option value");
        if (option == "--bitrate") bitrate = std::stoi(argv[input_arg++]);
        else if (option == "--speedup") speedup = std::stoi(argv[input_arg++]);
        else if (option == "--metadata") metadata = argv[input_arg++];
        else throw std::invalid_argument("unknown clip option: " + option);
      }
      if (input_arg == argc) throw std::invalid_argument("missing clip input");
      std::vector<std::string> inputs(argv + input_arg, argv + argc);
      return encode_clip(inputs, argv[2], std::stod(argv[3]), std::stod(argv[4]),
                         bitrate, speedup, metadata);
    } catch (const std::exception &e) {
      fprintf(stderr, "clip encoding failed: %s\n", e.what());
      return 1;
    }
  }
#endif
  if (!Hardware::PC()) {
    int ret;
    ret = util::set_realtime_priority(52);
    assert(ret == 0);
    ret = util::set_core_affinity({3});
    assert(ret == 0);
  }
  if (argc > 1) {
    std::string arg1(argv[1]);
    if (arg1 == "--stream") {
      encoderd_thread(stream_cameras_logged);
    } else {
      LOGE("Argument '%s' is not supported", arg1.c_str());
    }

View on GitHub (pinned to 516ec1e682)

Solutions

  1. Read e.what() in the printed message — it names the exact failing part ('stod', 'unknown clip option: --fps', etc.).
  2. Quote and check your script variables: empty or non-numeric START/DURATION/bitrate are the most common cause.
  3. Verify the segment numbers you passed exist in the route directory before invoking.
  4. Spell options exactly --bitrate, --speedup, --metadata (unsigned values with no '=').

Example fix

# before
encoderd --clip out.mp4 "$START" 10 5 --bitrate 4M   # stod('') / stoi('4M') throw

# after
encoderd --clip out.mp4 30 10 5 --bitrate 4000000
Defensive patterns

Strategy: validation

Validate before calling

def is_num(s):
    try:
        float(s); return True
    except ValueError:
        return False

for v in (start, duration):
    assert is_num(v), f'{v!r} must be numeric seconds'
assert str(bitrate).isdigit(), 'bitrate must be integer bps'
subprocess.run(['encoderd', '--clip', out, start, duration, *segments, '--bitrate', str(bitrate)], check=True)

Prevention

When it happens

Trigger: Passing a non-numeric value to --bitrate/--speedup or START/DURATION (std::stoi/stod throw), a flag like --bitrate as the last argument with no value, an unknown option (e.g. --fps), no segment numbers at all, or encode_clip failing on missing/corrupt input segments.

Common situations: Shell scripts passing empty variables ("$START" unset -> stod('') throws), decimal locale differences, typos like --speed=2, or referencing a segment number that doesn't exist in the route so encode_clip cannot open the logs.

Related errors


AI-assisted analysis of commaai/openpilot@516ec1e682 (2026-08-15). Data as JSON: /api/errors/be0d5069942ce877. Report an issue: GitHub.