Skip to content

Supplementary Report

(Thur Mar 19) After taking a rest, I have come to understand what “done” means for me, and with the one-week extension, I am continuing this journey.

1. Local Docker Setup

STEP 1. Install Docker and Start Docker Desktop

STEP 2. Clone or download the Repository Open your terminal. cd ~/Downloads/IIC-OSIC-TOOLS- then press tab on your keyboard to auto complete the folder name and press enter.

Step 3. Start the Container After in the folder. ./start_vnc.sh

But, IIC-OSIC-TOOLS did not start. Inquiry Via Mattermost app, The answer was “Do you have 25GB of space available on your MAC?”

2 . Generate GDS and review in Klayout

STEP 1. I decided to use Local VNC and restart the Container via Tools Dashboard (Not just quit & restart TigerVNC connect) –> Finally, I have understood the meaning of IIC-OSIC-TOOLS Running

STEP 2. Place lib/, flow/ , Makefile in /foss/designs/project/

STEP 3. Fix the code of Makefile and then Run.

Go to Session 6

3. Packaging and board design

Go to Session 7

4. My Presentation

Go to Session 8

5. Fix the code and then Upload the Final delivery

  • I fixed the code of hello_morse_tb.v , hello_morse.vvp, hello_morse_tb.vcd

  • My Final Code Set is here coloring_wing.zip

// ============================================================================
// Hello Morse Testbench
// ============================================================================
//
// This testbench verifies the Morse code beacon by:
//   1. Capturing the serial data transmitted to the WS2812 LED strip
//   2. Decoding the WS2812 waveform to recover LED color values
//   3. Detecting Morse dots, dashes, and inter-symbol / inter-character gaps
//   4. Monitoring the buzzer output to verify 600 Hz tone generation during Morse activity
//   5. Confirming synchronization between the LED indication and buzzer signal
//   6. Dumping simulation waveforms to a .vcd file for analysis in GTKWave
//
// MORSE TIMING RECAP:
//   - Dot  = 1 unit (LEDs on)
//   - Dash = 3 units (LEDs on)
//   - Gap between symbols = 1 unit (LEDs off)
//   - Gap between letters = 3 units (LEDs off)
//   - Gap between words   = 7 units (LEDs off)
//
// HOW TO RUN:
//   iverilog -g2012 -o hello_morse.vvp hello_morse.v hello_morse_tb.v debounce.v
//   vvp hello_morse.vvp
//   gtkwave hello_morse_tb.vcd
//
// ============================================================================

`timescale 1ns/1ps

module hello_morse_tb;

    // ========================================================================
    // Testbench Signals
    // ========================================================================

    reg  clk;
    reg  rst_n;
    reg  btn_color;
    wire led_data;
    wire buzzer_pwm;

    // ========================================================================
    // VCD Dump for GTKWave
    // ========================================================================

    initial begin
        $dumpfile("hello_morse_tb.vcd");
        $dumpvars(0, hello_morse_tb);
    end

    // ========================================================================
    // DUT Instantiation
    // ========================================================================
    //
    // We use 10 MHz clock for simulation.
    // At 10 MHz, clock period = 100 ns.
    // UNIT_TIME = 10_000_000 / 10 = 1,000,000 cycles = 100 ms per unit.

    hello_morse #(
        .CLK_FREQ(10_000_000),  // 10 MHz simulation clock
        .NUM_LEDS(8)
    ) dut (
        .clk        (clk),
        .rst_n      (rst_n),
        .btn_color  (btn_color),
        .led_data   (led_data),
        .buzzer_pwm (buzzer_pwm)
    );

    // ========================================================================
    // Clock Generation
    // ========================================================================

    initial begin
        clk = 1'b0;
        forever #50 clk = ~clk;   // 10 MHz clock
    end

    // ========================================================================
    // WS2812 Protocol Decoder
    // ========================================================================
    //
    // Decodes WS2812 serial data to extract LED colors.

    time rise_time;
    time fall_time;
    real high_time_us;

    reg [23:0] rx_data;
    reg [4:0]  rx_bit;
    integer    led_count;
    integer    frame_count;

    reg [23:0] last_color;

    initial begin
        rx_bit      = 0;
        rx_data     = 24'd0;
        led_count   = 0;
        frame_count = 0;
        rise_time   = 0;
        fall_time   = 0;
        high_time_us = 0.0;
        last_color  = 24'h000000;
    end

    // Record time on rising edge
    always @(posedge led_data) begin
        rise_time = $time;
    end

    // Decode each bit on falling edge
    always @(negedge led_data) begin
        fall_time    = $time;
        high_time_us = (fall_time - rise_time) / 1000.0;   // ns -> us

        if (high_time_us > 0.6)
            rx_data[23 - rx_bit] = 1'b1;
        else
            rx_data[23 - rx_bit] = 1'b0;

        rx_bit = rx_bit + 1;

        if (rx_bit >= 24) begin
            // First LED indicates whether Morse output is ON or OFF
            if (led_count == 0) begin
                if ((rx_data != 24'h000000) && (last_color == 24'h000000)) begin
                    $display("[%0t ns] LEDs ON  (G=%02h R=%02h B=%02h)",
                             $time, rx_data[23:16], rx_data[15:8], rx_data[7:0]);
                end
                else if ((rx_data == 24'h000000) && (last_color != 24'h000000)) begin
                    $display("[%0t ns] LEDs OFF", $time);
                end
                last_color = rx_data;
            end

            rx_bit = 0;
            led_count = led_count + 1;

            if (led_count >= 8) begin
                led_count = 0;
                frame_count = frame_count + 1;
            end
        end
    end

    // ========================================================================
    // Optional Buzzer Monitor
    // ========================================================================

    always @(posedge buzzer_pwm) begin
        $display("[%0t ns] Buzzer activity", $time);
    end

    // ========================================================================
    // Main Test Sequence
    // ========================================================================

    initial begin
        rst_n     = 1'b0;
        btn_color = 1'b0;

        $display("");
        $display("===========================================");
        $display("Hello Morse Testbench");
        $display("===========================================");
        $display("Message: HELLO");
        $display("Expected Morse: .... . .-.. .-.. ---");
        $display("");
        $display("Watching for LED on/off transitions...");
        $display("(At 10 MHz sim clock, 1 unit = 100 ms)");
        $display("");

        // Release reset
        #10_000;
        rst_n = 1'b1;

        // --------------------------------------------------------------------
        // Watch Morse Output
        // --------------------------------------------------------------------

        #500_000_000;   // 500 ms

        // --------------------------------------------------------------------
        // Test Color Change
        // --------------------------------------------------------------------

        $display("");
        $display("Pressing color button...");

        btn_color = 1'b1;
        #30_000_000;    // 30 ms press, long enough for debounce
        btn_color = 1'b0;

        // Wait for debounce and observe color change
        #200_000_000;

        // --------------------------------------------------------------------
        // Done
        // --------------------------------------------------------------------

        $display("");
        $display("===========================================");
        $display("Test complete!");
        $display("Frames captured: %0d", frame_count);
        $display("===========================================");
        $finish;
    end

endmodule

Go to Acknowlegements