Gray Code Converter

Convert between binary and Gray code, generate the full sequence table for small widths, and grab Verilog/VHDL bin2gray and gray2bin functions - the safe way to cross counters between clock domains.

Results

Binary in
10 (0b1010)
Gray out
15 (0b1111)

Full 4-bit table

DecimalBinaryGrayGray (dec)
0000000000
1000100011
2001000113
3001100102
4010001106
5010101117
6011001015
7011101004
81000110012
91001110113
101010111115
111011111014
121100101010
131101101111
14111010019
15111110008

Notes

Verilog functions
// Gray code conversion functions
// Generated by libfpga.com/tools/gray-code
function [W-1:0] bin2gray(input [W-1:0] b);
    bin2gray = b ^ (b >> 1);
endfunction

function [W-1:0] gray2bin(input [W-1:0] g);
    integer i;
    begin
        gray2bin[W-1] = g[W-1];
        for (i = W-2; i >= 0; i = i - 1)
            gray2bin[i] = gray2bin[i+1] ^ g[i];
    end
endfunction
VHDL functions
-- Gray code conversion functions
-- Generated by libfpga.com/tools/gray-code
function bin2gray(b : std_logic_vector) return std_logic_vector is
begin
    return b xor ('0' & b(b'high downto b'low + 1));
end function;

function gray2bin(g : std_logic_vector) return std_logic_vector is
    variable b : std_logic_vector(g'range);
begin
    b(g'high) := g(g'high);
    for i in g'high - 1 downto g'low loop
        b(i) := b(i + 1) xor g(i);
    end loop;
    return b;
end function;

This exact result is bookmarkable — the URL contains all your inputs. Need it in a script? Append &format=json (API docs).

About this tool

When a multi-bit counter crosses a clock domain, sampling it mid-transition can capture a mix of old and new bits — a binary counter going 7→8 flips four bits and can be read as anything. In Gray code, consecutive values differ in exactly one bit, so a mid-transition sample is at worst off by one count, never garbage. That property is the backbone of async FIFO pointers. This tool converts values both directions, prints the full sequence table for small widths, and provides the standard conversion functions (binary→Gray is one XOR; Gray→binary is a prefix XOR chain). Only counters that increment by one keep the property — don't Gray-code a value that jumps.

Related tools