module ultrasonic_fpga #( parameter integer CLK_FREQ = 27_000_000 // Fréquence d'horloge en Hz )( input wire clk, input wire rst, input wire start, inout wire sig, // Broche bidirectionnelle vers le capteur output reg [15:0] distance_cm // Distance mesurée en cm ); reg [2:0] state; reg [15:0] trig_counter; reg [31:0] echo_counter; reg sig_out; reg sig_dir; // 1: output, 0: input assign sig = sig_dir ? sig_out : 1'bz; wire sig_in = sig; localparam IDLE = 3'd0, TRIG_HIGH = 3'd1, TRIG_LOW = 3'd2, WAIT_ECHO = 3'd3, MEASURE_ECHO = 3'd4, DONE = 3'd5; localparam integer TRIG_PULSE_CYCLES = CLK_FREQ / 100_000; // 10us pulse localparam integer DIST_DIVISOR = (58 * CLK_FREQ) / 1_000_000; // pour conversion us -> cm always @(posedge clk or posedge rst) begin if (rst) begin state <= IDLE; trig_counter <= 0; echo_counter <= 0; sig_out <= 0; sig_dir <= 0; distance_cm <= 0; end else begin case (state) IDLE: begin sig_out <= 0; sig_dir <= 1; if (start) begin state <= TRIG_HIGH; trig_counter <= 0; end end TRIG_HIGH: begin sig_out <= 1; sig_dir <= 1; if (trig_counter < TRIG_PULSE_CYCLES) begin trig_counter <= trig_counter + 1; end else begin trig_counter <= 0; state <= TRIG_LOW; end end TRIG_LOW: begin sig_out <= 0; sig_dir <= 0; // Mettre en entrée state <= WAIT_ECHO; end WAIT_ECHO: begin if (sig_in) begin echo_counter <= 0; state <= MEASURE_ECHO; end end MEASURE_ECHO: begin if (sig_in) begin echo_counter <= echo_counter + 1; end else begin distance_cm <= (echo_counter * 1000) / DIST_DIVISOR; state <= DONE; end end DONE: begin state <= IDLE; end endcase end end endmodule