Verilog case statements


Sigasi Studio has a number of checks on Verilog case statements.

Case statement does not cover all cases

A case statement should cover all options, either enumerating all options explicitly or with a default clause (rule 8). This rule is checked for enum types only, not for scalar or vector types.

module badcode(input clk);
    typedef enum {INIT, IDLE, START, READY} t_state;
    t_state state;

    always @(posedge clk) begin
        case (state)                      // Error: case `INIT` is missing
            IDLE    : state = START;
            START   : state = READY;
            READY   : state = IDLE ;
        endcase
    end
endmodule

module bettercode(input clk);
    typedef enum {INIT, IDLE, START, READY} t_state;
    t_state state;

    always @(posedge clk) begin
        case (state)
            INIT    : state = IDLE ;
            IDLE    : state = START;
            START   : state = READY;
            READY   : state = IDLE ;
        endcase
    end
endmodule

Note that Sigasi Studio also warns for case statements without a default clause

Default clause has to be the last item in a case statement

The default clause should be at the end, after all other options (rule 15). Sigasi Studio flags a warning if that is not the case.

module badcode(input clk);
    typedef enum {INIT, IDLE, START, READY} t_state;
    t_state state;

    always @(posedge clk) begin
        case (state)
            IDLE    : state = START;
            START   : state = READY;
            default : state = IDLE ;      // The `default` clause must be at the end
            READY   : state = IDLE ;
        endcase
    end
endmodule

module goodcode(input clk);
    typedef enum {INIT, IDLE, START, READY} t_state;
    t_state state;

    always @(posedge clk) begin
        case (state)
            IDLE    : state = START;
            START   : state = READY;
            READY   : state = IDLE ;
            default : state = IDLE ;
        endcase
    end
endmodule

Case statement can only have one default clause

A case statement can only have one default clause (rule 16). An error is flagged if more than one default clause is present.

module badcode(input clk);
    typedef enum {INIT, IDLE, START, READY} t_state;
    t_state state;

    always @(posedge clk) begin
        case (state)
            IDLE    : state = START;
            START   : state = READY;
            READY   : state = IDLE ;
            default : state = IDLE ;      // Error: two `default` clauses
            default : state = START;
        endcase
    end
endmodule

module goodcode(input clk);
    typedef enum {INIT, IDLE, START, READY} t_state;
    t_state state;

    always @(posedge clk) begin
        case (state)
            IDLE    : state = START;
            START   : state = READY;
            READY   : state = IDLE ;
            default : state = IDLE ;
        endcase
    end
endmodule

Default clause missing from case statement

Sigasi Studio flags a warning for case statements without a default clause (rule 40). While a case statement without a default branch is syntactically correct, many guidelines recommend to attach default branch, even if the case statement is completely defined. This ensures no latch would be inferred during synthesis, if case is incomplete (sometimes difficult to judge, esp with casex/casez semantics or larger widths).

module rather_ok_code(input clk);
    typedef enum {INIT, IDLE, START, READY} t_state;
    t_state state;

    always @(posedge clk) begin
        case (state)
            INIT    : state = IDLE ;
            IDLE    : state = START;
            START   : state = READY;
            READY   : state = IDLE ;
            // no default branch
        endcase
    end
endmodule

module goodcode(input clk);
    typedef enum {INIT, IDLE, START, READY} t_state;
    t_state state;

    always @(posedge clk) begin
        case (state)
            INIT    : state = IDLE ;
            IDLE    : state = START;
            START   : state = READY;
            READY   : state = IDLE ;
            default : state = IDLE ;
        endcase
    end
endmodule

Project specific setting of these rules

These rules can be disabled for your project, or its severity can be modified in the project linting settings.

Manual configuration in ${project location}/.settings/com.sigasi.hdt.verilog.linting.prefs:

8/severity/<project>=IGNORE

15/severity/<project>=IGNORE

16/severity/<project>=IGNORE

40/severity/<project>=IGNORE