`timescale 1ns / 1ps ////////////////////////////////////////////////////////////////////////////////// // Company: // Engineer: // // Create Date: 02/16/2026 08:28:02 PM // Design Name: // Module Name: olla_testack // Project Name: // Target Devices: // Tool Versions: // Description: // // Dependencies: // // Revision: // Revision 0.01 - File Created // Additional Comments: // ////////////////////////////////////////////////////////////////////////////////// module autoack ( input logic CLK, input logic RST, input logic [8:0] OUTPUT_BITS_ONION_p, input logic [8:0] OUTPUT_BITS_ONION_n, output logic OUTPUT_BITS_ONION_A_AO ); //--------------------------------------------------------- // Local Parameters //--------------------------------------------------------- localparam int COUNTER_WIDTH = 27; // Örnek: CLK = 25 MHz ise 25,000,000 çevrim 1 saniyedir. // localparam int ONE_SEC_LIMIT = 25_000_000 - 1; localparam int ONE_SEC_LIMIT = 5 - 1; //--------------------------------------------------------- // Internal Signals //--------------------------------------------------------- // FSM State Definitions typedef enum logic [3:0] { S_WAIT_DATA_BLANK, // Faz 1: Veri hatlarının ve ACK'nin 0 olmasını bekle. S_DATA_LATCH, // Faz 2: Veri geldi, veriyi/adresi yakala. S_TIMER_START, // LED zamanlayıcısını başlat (Sayacı sıfırla). S_TIMER_WAIT, // LED açıkken 1 saniye bekle (ON Time). S_LED_BLANK_WAIT, // LED kapalıyken 1 saniye bekle (OFF Time). S_SEND_ACK, // Faz 3: ACK'yi '1' yap. S_WAIT_DATA_BLANK_LOW, // Faz 4: Göndericinin veri hatlarını '0' çekmesini bekle. S_ACK_LOW // Faz 5: ACK'yi '0' yap ve S_WAIT_DATA_BLANK'e dön. } state_t; state_t state, next_state; logic [COUNTER_WIDTH-1:0] counter_reg; //--------------------------------------------------------- // 1. Dual-Rail Veri Kontrolü //--------------------------------------------------------- // 'data_arrived' sinyali: Data hatlarından herhangi biri '1' ise veri gelmiştir. logic data_arrived; assign data_arrived = |OUTPUT_BITS_ONION_p | |OUTPUT_BITS_ONION_n; // 'data_is_blank' sinyali: Tüm data hatları '0' ise hat boş/temizdir. logic data_is_blank; assign data_is_blank = ~data_arrived; //--------------------------------------------------------- // 2. Sequential Logic: Counter Register //--------------------------------------------------------- always_ff @(posedge CLK) begin if (RST) begin counter_reg <= '0; end else begin // Counter Logic: Increments in S_TIMER_WAIT (LED ON time) // OR S_LED_BLANK_WAIT (LED OFF time) if (state == S_TIMER_WAIT || state == S_LED_BLANK_WAIT) begin if (counter_reg == ONE_SEC_LIMIT) counter_reg <= '0; else counter_reg <= counter_reg + 1; end // Reset counter when a new timer sequence starts else if (state == S_TIMER_START) counter_reg <= '0; // Reset counter in other states if it's not already 0 (safety) else if (counter_reg != '0 && state != S_TIMER_WAIT && state != S_LED_BLANK_WAIT) counter_reg <= '0; end end //--------------------------------------------------------- // 3. Sequential Logic: State Register //--------------------------------------------------------- always_ff @(posedge CLK) begin if (RST) state <= S_WAIT_DATA_BLANK; else state <= next_state; end //---------------------------------------------------------- // 4. Combinational Logic: Next State Determination (FSM) //---------------------------------------------------------- always_comb begin next_state = state; case (state) S_WAIT_DATA_BLANK: // Faz 1: Hatların boş olmasını bekle if (data_arrived) // Veri geldiğinde (Dual-rail sinyalleri 0'dan farklı) next_state = S_DATA_LATCH; S_DATA_LATCH: // Faz 2: Veri geldi, zamanlayıcıyı başlat next_state = S_TIMER_START; S_TIMER_START: // LED ON süresini başlatmak için sayacı sıfırla next_state = S_TIMER_WAIT; S_TIMER_WAIT: // LED açıkken 1 saniye bekle if (counter_reg == ONE_SEC_LIMIT) next_state = S_LED_BLANK_WAIT; // LED'i söndürme süresine geç S_LED_BLANK_WAIT: // LED kapalıyken 1 saniye bekle (Blink süresi) if (counter_reg == ONE_SEC_LIMIT) next_state = S_SEND_ACK; // ACK gönderme döngüsüne geç S_SEND_ACK: // Faz 3: ACK'yi '1' yap next_state = S_WAIT_DATA_BLANK_LOW; S_WAIT_DATA_BLANK_LOW: // Faz 4: Göndericinin veri hatlarını '0' çekmesini bekle if (data_is_blank) // Veri hatları boşaldı (tümü '0') next_state = S_ACK_LOW; S_ACK_LOW: // Faz 5: ACK'yi '0' yap next_state = S_WAIT_DATA_BLANK; default: next_state = S_WAIT_DATA_BLANK; endcase end //----------------------------------------------------------- // 5. Combinational Logic: Output Generation //----------------------------------------------------------- always_comb begin // Default değerler OUTPUT_BITS_ONION_A_AO = 1'b0; case (state) S_SEND_ACK, S_WAIT_DATA_BLANK_LOW: OUTPUT_BITS_ONION_A_AO = 1'b1; default: ; endcase end endmodule