# Range Gate
This chip gets requests to verify that a number is in the range `[0, MAX)`.
In the trace, there is a counter column and a multiplicity column.
The counter column is generated using constraints (gates), as opposed to the [RangeCheckerChip](../range/README.md) which uses preprocessed trace.
The difference is that this chip does not use any preprocessed trace.
**Columns:**
- `counter`: Dynamically generated column containing sequential values from 0 to `range_max-1`
- `mult`: Multiplicity column tracking the number of range checks requested for each value
The `RangeCheckerGateAir` constrains that the `counter` column is increasing from 0 to `MAX - 1` and also leaves the `mult` column unconstrained.
**Constraints:**
```math
\begin{align}
\texttt{counter}_0 &= 0 & &\hspace{2em} (1)\\
\texttt{counter}_{i+1} - \texttt{counter}_i &= 1 & \forall\ 0 \leq i < H-1 &\hspace{2em} (2)\\
\texttt{counter}_{H-1} &= \texttt{range\_max} - 1 & &\hspace{2em} (3)
\end{align}
```
Constraint (1) ensures the counter starts at 0 on the first row.
Constraint (2) enforces that each subsequent row increments the counter by exactly 1.
Constraint (3) verifies that the last row contains the value `range_max-1`, ensuring the trace has the correct height.
The implementation of these constraints is shown below:
```rust
builder
.when_first_row()
.assert_eq(local.counter, AB::Expr::ZERO);
builder
.when_transition()
.assert_eq(local.counter + AB::Expr::ONE, next.counter);
builder.when_last_row().assert_eq(
local.counter,
AB::F::from_u32(self.bus.range_max - 1),
);
```
The trace is generated by accumulating the count of range checks requested for each value in the `mult` column, with each row's `counter` value representing the number being checked.
Other than that, the interaction constraints work similarly to the [RangeCheckerChip](../range/README.md).