DrKLO/Telegram · warning

Error: encoder doesn't match decoder\n

Error message

Error: encoder doesn't match decoder\n

What it means

Only emitted under #if !(FIXED_POINT && !CUSTOM_MODES) && defined(RESYNTH): after the full encode/decode round trip, the computed RMS difference between input and output samples (rmsd) is > 0, meaning the encoder/decoder pair is not perfectly reconstructive for this input. The message is a self-test failure indicating the Opus build is numerically inconsistent.

Source

Thrown at TMessagesProj/jni/opus/celt/opus_custom_demo.c:201

#endif
      count++;
      fwrite(out+skip*channels, sizeof(short), (ret-skip)*channels, fout);
      skip = 0;
   }
   PRINT_MIPS(stderr);

   opus_custom_encoder_destroy(enc);
   opus_custom_decoder_destroy(dec);
   fclose(fin);
   fclose(fout);
   opus_custom_mode_destroy(mode);
   free(in);
   free(out);
#if !(defined (FIXED_POINT) && !defined(CUSTOM_MODES)) && defined(RESYNTH)
   if (rmsd > 0)
   {
      rmsd = sqrt(rmsd/(1.0*frame_size*channels*count));
      fprintf (stderr, "Error: encoder doesn't match decoder\n");
      fprintf (stderr, "RMS mismatch is %f\n", rmsd);
      return 1;
   } else {
      fprintf (stderr, "Encoder matches decoder!!\n");
   }
#endif
   return 0;
}

View on GitHub (pinned to 45ab8f4308)

Solutions

  1. Confirm whether RESYNTH divergence is expected for your bitrate — increase bytes_per_packet and re-test.
  2. Disable the bit-error / packet-loss simulation (use 9-arg form without a high loss rate) to isolate codec behavior.
  3. Rebuild opus cleanly with consistent FIXED_POINT/FLOAT settings across all translation units.
  4. If divergence is expected lossy behavior, treat this message as informational rather than a failure.

Example fix

// before (lossy: small bytes_per_packet causes expected divergence)
./test_opus_custom 48000 1 480 20 input.sw output.sw

// after (transparent at higher bitrate; divergence ~0)
./test_opus_custom 48000 1 480 120 input.sw output.sw
Defensive patterns

Strategy: validation

Validate before calling

// Confirm divergence is expected for the bitrate before treating as failure.
if (rmsd > RMSD_TOLERANCE) {
    fprintf(stderr, "RMS mismatch %f exceeds tolerance for bitrate\n", rmsd);
    return 1;
}

Prevention

When it happens

Trigger: rmsd = sqrt(sum((in[i]-out[i])^2) / (frame_size*channels*count)) > 0. This requires RESYNTH to be defined at compile time. Any non-zero divergence between encode-then-decode samples triggers it. Expected in lossy modes; suspicious for a build intended to be transparent at the given bitrate.

Common situations: Running the demo on a build with RESYNTH enabled (a developer/QA build, not a release build); low bytes_per_packet causing lossy quantization; a buggy or mis-compiled opus (e.g. mixed fixed/float objects); bit-error or packet-loss simulation introducing divergence.

Related errors


AI-assisted analysis of DrKLO/Telegram@45ab8f4308 (2026-08-14). Data as JSON: /api/errors/4d0697a603fe4d98. Report an issue: GitHub.