How do I use Digital I/O pins in Multi-instrument Mode
Using Moku:Go digital I/O with Multi-Instrument Mode and Moku Cloud Compile
-
Moku:Go
Moku:Go Arbitrary Waveform Generator Moku:Go Data Logger Moku:Go Frequency Response Analyzer Moku:Go Logic Analyzer & Pattern Generator Moku:Go Oscilloscope & Voltmeter Moku:Go PID Controller Moku:Go Spectrum Analyzer Moku:Go Waveform Generator Moku:Go Power Supplies Moku:Go Digital Filter Box Moku:Go FIR Filter Builder Moku:Go Lock-in Amplifier Moku:Go General Moku:Go Logic Analyzer/Pattern Generator Moku:Go Time & Frequency Analyzer Moku:Go Laser Lock Box Moku:Go Phasemeter
-
Moku:Lab
Moku:Lab General Moku:Lab Arbitrary Waveform Generator Moku:Lab Data Logger Moku:Lab Digital Filter Box Moku:Lab FIR Filter Builder Moku:Lab Frequency Response Analyzer Moku:Lab Laser Lock Box Moku:Lab Lock-in Amplifier Moku:Lab Oscilloscope Moku:Lab Phasemeter Moku:Lab PID Controller Moku:Lab Spectrum Analyzer Moku:Lab Waveform Generator Moku:Lab Time & Frequency Analyzer Moku:Lab Logic Analyzer/Pattern Generator
-
Moku:Pro
Moku:Pro Arbitrary Waveform Generator Moku:Pro Data Logger Moku:Pro Frequency Response Analyzer Moku:Pro Oscilloscope Moku:Pro PID Controller Moku:Pro Spectrum Analyzer Moku:Pro Waveform Generator Moku:Pro Lock-in Amplifier Moku:Pro Digital Filter Box Moku:Pro FIR Filter Builder Moku:Pro Phasemeter Moku:Pro Multi-instrument Mode Moku:Pro General Moku:Pro Logic Analyzer/Pattern Generator Moku:Pro Time & Frequency Analyzer
- Python API
- MATLAB API
- Arbitrary Waveform Generator
- Data Logger
- Digital Filter Box
- FIR Filter Builder
- Frequency Response Analyzer
- Laser Lock Box
- Lock-in Amplifier
- Oscilloscope
- Phasemeter
- PID Controller
- Spectrum Analyzer
- Time & Frequency Analyzer
- Waveform Generator
- Logic Analyzer & Pattern Generator
- Multi Instrument Mode
- Moku Cloud Compile
- Moku general
- LabVIEW
Moku:Go features 16 bi-directional pins, providing users the flexibility to utilize them either as 16 individual standalone signal pins or to combine them into a single 16 bit bus. This article will explain how to use Digital I/O pins in Multi-instrument Mode on Moku:Go.
1. Standalone digital pins
Each of the 16 pins on Moku:Go can be set as a digital input or output individually, and can be controlled by the integrated pattern generator in Logic Analyzer. Pins 1~8 were configured as output pins and Pins 9~16 were configured as input pins. Pins 1~8 were looped back to Pins 9~16 externally with jumper wires.
In this setup, the Logic Analyzer/Pattern Generator can both read signals from certain digital pins and output signals to other digital pins concurrently. As illustrated in the figure below, the Logic Analyzer accurately captures the signal generated by Pattern Generator 1 through DIO and jump wires. Please note that the Bits are 0-based while Pins are 1-based.
2. Combined as 16 bit bus
The digital pins can be mapped to a 16 bit signal bus, ranking from the least significant bit (LSB) to the most significant bit (MSB). For instance, Pin 1 corresponds to Bit 0 (LSB) in the 16 bit signal bus, while Pin 16 aligns with Bit 15 (MSB). In the depicted configuration shown in the screenshot below, the Waveform Generator produces a 16-bit ramp wave through the DIO; and simultaneously, Logic Analyzer visualizes the output waveforms on the 16 pins.
The ramp waveform is set as 100 Hz repetition rate and 10 Vpp amplitude. Waveforms on Logic Analyzer indicate that the higher-order bits experience fewer transitions, whereas the lower-order bits exhibit more transitions. This observation aligns with the anticipated behavior since the most significant bit (MSB) changes only twice within each cycle, while the least significant bit (LSB) changes with nearly every update of the waveform.
3. Moku Cloud Compile
Through Moku Cloud Compile (MCC), there's a broader scope for creating adaptable and tailored algorithms using DIO. You have the capability to craft your digital signal generator and transmit the signal through DIO. For instance, consider this MCC custom function: it reads a trigger signal from Pin 1 and generates three digital triggers on Pins 6 through 8. Subsequently, Pins 6 through 8 are looped back to Pins 2 through 4 and can be observed using the Logic Analyzer.
For example, the attached MCC code generates three trigger signals with a 10-clock-cycle gap between each adjacent trigger upon receiving an input trigger signal. The following figure displays both non-triggered (left) and triggered (right) output results. The 320 ns (10 * 1/31.25 MHz) delay between the trigger signals is observable in the triggered figure.
The VHDL code for this custom trigger function is provided below and can be synthesized and deployed to a Moku:Go. To generate the bitstream, please follow this link: Moku Cloud Compile - A getting started guide
LIBRARY IEEE;
USE IEEE.std_logic_1164.ALL;
USE IEEE.numeric_std.ALL;
-- InputA(0): trigger input
-- OutputA(5): regenerated trigger0 output
-- OutputA(6): regenerated trigger1 output
-- OutputA(7): regenerated trigger2 output
architecture TopWrapper of CustomWrapper is
type t_state is (Waiting, Running);
signal state, state_next : t_state;
signal prevTriggerIn : std_logic;
signal count, count_next : unsigned(15 downto 0);
begin
State_Machine: process (prevTriggerIn, InputA(0), count, state)
begin
case state is
when Waiting =>
if(prevTriggerIn /= '1' and InputA(0) = '1') then
state_next <= Running;
else
state_next <= Waiting;
end if;
when Running =>
if(count /= to_unsigned(31,count'length)) then
count_next <= count + to_unsigned(1,count'length);
state_next <= Running;
else
count_next <= to_unsigned(0,count'length);
state_next <= Waiting;
end if;
end case;
end process;
Trigger_Gen: process(clk) is
begin
if reset = '1' then
state <= Waiting;
prevTriggerIn <= '0';
count <= to_unsigned(0,count'length);
OutputA(5) <= '0';
OutputA(6) <= '0';
OutputA(7) <= '0';
elsif rising_edge(Clk) then
prevTriggerIn <= InputA(0);
state <= state_next;
count <= count_next;
case state is
when Waiting =>
OutputA(5) <= '0';
OutputA(6) <= '0';
OutputA(7) <= '0';
when Running =>
if (count = to_unsigned(10,count'length)) then
OutputA(5) <= '1';
OutputA(6) <= '0';
OutputA(7) <= '0';
elsif (count = to_unsigned(20,count'length)) then
OutputA(5) <= '0';
OutputA(6) <= '1';
OutputA(7) <= '0';
elsif (count = to_unsigned(30,count'length)) then
OutputA(5) <= '0';
OutputA(6) <= '0';
OutputA(7) <= '1';
else
OutputA(5) <= '0';
OutputA(6) <= '0';
OutputA(7) <= '0';
end if;
end case;
end if;
end process;
end architecture;