pyRound function

int pyRound(
  1. double x
)

Rounding helpers that match the semantics of Python's built-in round, which the Falcon reference relies on inside ffnp, reduce and the pre-image sampler.

Python rounds half-to-even ("banker's rounding"): round(2.5) == 2, round(3.5) == 4, round(-0.5) == 0. Dart's double.round() instead rounds half away from zero, so we cannot use it if we want bit-for-bit reproducibility with the reference (and with cross-verified signatures).

Implementation

int pyRound(double x) {
  final floor = x.floorToDouble();
  final diff = x - floor;
  if (diff < 0.5) return floor.toInt();
  if (diff > 0.5) return floor.toInt() + 1;
  // Exactly halfway: round to the even neighbour.
  final low = floor.toInt();
  return (low.isEven) ? low : low + 1;
}