Team Status Report for 04/04

This Sunday, the team finalized a functional interim-demo of the WaveShaper that involved end-to-end I/O functionality, oscillators, mixing, and integration with each feature’s component except for the MIDI keyboard which should be on the way soon.

Shayaan worked on the RTL for SVF filters, also wrestling with  the binary-offset encoding confusion in our IP-blocks. Jake worked on the synthesis of the ADSR envelope, ordering a keyboard, and the beginnings of the RTL for effects. Daniel successfully brought up MIDI parsing and system integration. His work result was a demonstration that could take a MIDI file from a host-machine, and play it back with saw-tooth oscillators, whilst showing the youngest notes requisite MIDI information on the DE-10’s seven-segment display in hex.

With the core elements of the subtraction synthesis pipeline at or near completion, what remains is the synthesis of filters, and adding of effects. This will transform the WaveShaper from a set of disconnected digital signal tools to a real interactive instrument.

There were a few setbacks encountered in unifying the pieces which we’re in the process of resolving. Not all components have been modified to support the binary-offset which the DAC requests in producing the output audio stream.

As the final product takes its shape, now is the time to consider both modular and integration tests. Diagnosing issues in each sub-system is much easier when direct focus is applied, and integration often comes with its own difficulties.

There are generally three types of bugs that we will be looking for in the Waveshaper hardware:

  1. Logical. (A fundamental flaw or oversight in the HDL algorithms and circuit designs which break the desired properties. Example: an error-prone frequency modulation algorithm which drifts non-linearly or jumps suddenly.)
  2. Implementation. (An issue in communication between components or hardware bottlenecks breaking system correctness or decreasing system performance. Example: A propagation delay in a MIDI stream reading system which results in lost bytes.)
  3. Subjective. (Something which breaks user expectations or lacks musicality despite technical correctness. Example: two frequencies within a reasonable margin of error of the target but sounding dissonant together due to a mismatch in their ratio.)

(Logic and Implementation may be ambiguous categories. Generally speaking, logic errors are discrepancies between the underlying mathematical functions which drive sound synthesis and the HDL specification. Implementation errors are hardware engineering oversights or mistakes which cause lack of coordination between the components as synthesized. An out-of-spec driver is considered an Implementation error.)

Logical errors for internal components will be caught and addressed by using HDL testbenches for simulation. The oscillators, ADSR envelopes, filters, and FX can all be implemented in MATLAB to provide a reference series of values in a controlled environment. MATLAB references are faster to implement at the cost of being slower to execute than the synthesized logic on an FPGA.

Logic errors for components may also be tested against pre-existing tools. For instance, the Linux command line utility amidi which comes with many distributions of ALSA (a long-standing backend for Linux audio) can be used to compare the parsing of our custom MIDI receiver with a battle-tested one.

Implementation errors will be diagnosed through measurement. There are oscilloscopes in the engineering labs which can measure the frequency of periodic signals and provide ratios between the peek-to-peek range in a signal with a (non-degenerate) envelope and its maximum. Such tests have already been fruitful in finding hardware artifacts in attempting to drive the speaker with discontinuous waves which can be eliminated with imperceptible interpolating stages.

Finally, subjective errors will be suggested by end users attempting to use the WaveShaper. These will be deliberated on, and minor changes to the specifications may be implemented.

Pitch and interval correctness, rhythmic consistency and responsiveness, lack of artifacts, and  waveform consistency are all technical factors which can be tested using an oscilloscope at the audio output. Ease-of-use can be tested in small groups of both experienced and inexperienced users of the WaveShaper.

The software will be tested with Rust unit tests. Importantly, the core library which communicates with the WaveShaper can be tested as a list of API calls.  The GUI interface software is likely too stateful to exhaustively test. As a result, in-the-field bug hunting will be done merely using the software, and an emphasis on robustness and being able to recover to states which are known to be well are critical.

Jake’s Status Report 4/4

This week was the WaveShaper interim demo. In trying to bring up the envelope onto the FPGA, I encountered unexpected issues with noise. The envelope successfully modulated the volume of the oscillator, moving through each respective phase, but something about the multiplication to scale the output is off. I tried things like synchronizing the inputs, or changing which clock modules made use of, I tried synchronizing the oscillator and envelope to only advance when the I2S ip-block moved to the left-sample-ready, sending zeros on the right. I tried explicitly setting a clock frequency on the FPGA, or driving the modules at 50Hz, with an added enable line to update the output samples in-respect to the audio-clock rate. Shayaan figured out that samples sent to the IP-blocks should actually be offset-K, which I intend to synthesize ASAP. The oscillators I was testing with were unsigned, and initially sounded better than did signed implementations. I also tried various things with the multiplication, such as “pipelining” it, in case it were somehow that  samples were  being dropped. What was working best was simply casting values to signed, but explicitly converting to offset-K is the correct behavior.

This week we also ordered the MIDI controller for use in the final demo. Users will be able to send at-once four voices. Arbitration will hold 4 voices in play, but drop a key in release if a new one is pressed. I chose the NEKTAR IMPACT LX49 for the controller explicitly to make Daniel’s life easier with the MIDI-CC features. It has 8 dials, and 9 sliders with a bank. The bank is desirable because the keyboard will manage a “page-toggle” control feature without us having to handle arbitration on the limited FPGA fabric. If we have more user-tunable parameters than are dials on the keyboard, this internal bank will allow the user to shift through the set of parameters the hardware buttons control, and the keyboard will do this for us by sending different MIDI identifiers.

Verification here is more than technical, as a lot of the tuning of parameters need to make sense from a user’s perspective. The first step in verification is through inspection through VCS. A more rigorous verification will involve comparing this sample-by-sample to the MATLAB pipeline equivalent, but should be functionally the same. The MATLAB comparison will become especially important as we test the effects, and summed waveforms. The MATLAB comparisons will also be important as we combine elements, as we should get the same stream out, bit-by-bit if the same elements are staged the same way. The last piece is the subjective, focusing on my own parts, the part to be verified is the playability. The last piece isn’t rigorous so much as: “are the options presented meaningful?”. When the WaveShapers various parts are all finally assembled, “Can I forget the instrument is there and just play?”.

Daniel’s Status Report for 04/04

This week, I brought up the HPS, HPS-FPGA communication over AXI, and implemented a MIDI state machine in SystemVerilog which can parse a stream of bytes.

These system integration tasks tied together all the work in the synthesizer core that the team has done so far into a platform ready for a polyphonic music demo which could play public domain MIDI tracks that other people have written.

Notably, the MIDI track was from a live input as though it were coming in from a MIDI controller like a keyboard. I was able to stream MIDI from my personal laptop and hear the synthesized output from the speakers. I only used command line tools that came with my system’s default package manager which aligns with the goal of the WaveShaper to be compatible with already existing technologies.

This is a first step in driving the synthesizer modules that we have designed outside of testbench environments. This coming week, the same will be done for the ADSR envelope and the filters in a custom CLI representing the software core.

As you’ve designed, implemented and debugged your project, what new tools or new knowledge did you find it necessary to learn to be able to accomplish these tasks?

I had to learn Quartus II’s Platform Manager and U-Boot.

What learning strategies did you use to acquire this new knowledge?

I usually read documentation, but many of the linked documents provided by Quartus 404’d. I had to filter through old university course labs to try and guess how to write up the IP blocks internally in Quartus correctly.

Shayaan Status Report 4/4

This week, we successfully synthesized the oscillators on the FPGA. One of the primary issues we encountered involved the DAC logic: although the documentation indicated a two’s complement input, the DAC is wrapped in Intel IP that requires Offset Binary logic. Once we adjusted for this, we were able to produce clean sawtooth, square, and triangle waveforms. We also discovered that the DAC cannot handle a square wave that swings rail-to-rail, as it requires additional headroom to account for higher-order harmonics.

I am still troubleshooting the sine wave generation via a Lookup Table (LUT). I loaded a ROM with a sine .mif file and confirmed that the system is reading the values correctly by verifying them on the Hex display. However, the resulting output is very noisy; while it retains a sinusoidal shape, the source of the noise remains unclear.

Additionally, I synthesized a Chamberlin State Variable Filter (SVF), which features integrated LPF, HPF, and BPF outputs. I have verified the filter’s mathematical correctness through our MATLAB pipeline and completed the SystemVerilog implementation. Despite this, the filter is not yet behaving as expected when running on the FPGA.

Verification is an important step that I take before synthesis on the FPGA and is the reason we have implement a MATLAB pipeline. To use the MATLAB pipeline, I generate a .hex file with our theoretical values. This .hex file in then read in a SystemVerilog testbench and I check after each timestep whether my SystemVerilog output is the same as the hex. This has been very useful in debugging and verifying the filter.

Jake’s Status Report 3/28

This week we spent some time in Quartus bringing up the device. We all raced to get a top module with working audio output, which Daniel figured out first.

I finished the envelope-generator, handling the edge cases. You’re now able to interrupt a release with another key-press, jumping to the beginning of the attack, which seemed initially unnecessary as I thought another voice would eliminate the need to handle this case. However, this logic handles another key being pressed whilst the bank of voices is all in use. Inside the bank we can have an arbitration that “evicts” a voice inside of the “retrigger window” while a note is being released. Whilst this case may not arise in the use of a portamento, our current implementation doesn’t have this feature. The net effect is that when more keys are pressed than are voices, and held down, the oldest are held. But any key which happens to be in release will be replaced.

Team Status Report for 03/28

This week, the team has been trying to clean up the SystemVerilog HDL for the WaveShaper core and implement it on the FPGA to demonstrate what it can do.

Shayaan has been working on the filtering and regularizing the oscillators for making all the tones sound more similar. Jake has been adjusting the ADSR envelope, adding additional logic and safeguards to prevent glitching. Daniel has been working on setting up end-to-end I/O on the DE-10 Standard FPGA development board.

This coming week, we hope to have a scaffolding of the WaveShaper to then fill in during the month of April as the period to work on the project comes to a close.

Daniel’s Status Report for 03/28

This week, I got audio output to work. Now, we have an easy-to-use streaming interface and can focus on the rest of the WaveShaper core. While it was mostly just pruning small errors in the protocol, it was fairly time consuming.

I have moved onto serial communications, attempting to get a structure up before the interim demo such that we can stream live music to show off the WaveShaper’s unique sound.

Progress is going slightly slower than I like, it has again been a bit of a struggle with an unfamiliar tool to bridge the HPS ARM-core with the FPGA fabric using AXI. Seeing as the deadline approaches, I am looking into using the Avalon-MM interface instead.

I am aiming to have an end-to-end music playing device by Sunday evening by integrating the SystemVerilog which we have so far been simulating on actual hardware.

This week, I also spent some time on a MIDI parsing state machine which is as of now just on paper.

Shayaan’s Status Report 3/28

This week, we worked on synthesizing the oscillators on the FPGA to produce a real audio output signal. This required correctly driving the DAC and initializing I2C communication with it. Ultimately, we were successful in driving the DAC using our previously developed oscillators. However, we noticed some issues with the periodicity of certain waveforms, as well as with the sine wave lookup table (LUT).

While working on fixing the oscillators and synthesizing a filter onto the FPGA, I encountered an issue accessing my account on the HH machines. Whenever I try to log in, I am redirected back to the username page. This has prevented me from synthesizing additional modules on the FPGA and continuing my work.

The next steps are to determine why I cannot access my account on the HH machines and then resume synthesizing modules such as filters and envelopes so we can move on to implementing effects.

Jake’s Status Report

This week I added a counter-based clock-divider to produce an audio clock from the onboard 50MHz main. This approach won’t be final, as we’ll need to generate the audio clock higher in the system-hierarchy when the entire project goes onto the FPGA, but it was an effective workaround this week. 

Testbenching the envelope generator is producing coherent shapes, but adjusting ADSR values while the “key-press” signal is active affects the way the current voice moves through the stages. I am not confident on what “correct behavior” looks like here, and will need to do some exploring to decide what the design should do when we do things like shorten the attack in the middle of a really long attack-phase gradually rising in.

The majority of time this week was spent with Daniel working on synthesis. We developed a top-module to wrap The Waveshaper System-Verilog thus far, and connected Intel IP blocks to initialize the Wolfson Codec and drive the DAC line-out.  However, somewhere in the path we’ve got a bug, which I believe pertains to the I2C used to set up the DAC, as we’re using IP blocks to do this now. 

Additional time was spent resolving Quartus environment issues, which delayed synthesis and debugging. The next steps are to address the I2C configuration issues I suspect are present, validate with audio out, and to resolve the ADSR tests.

Daniel’s Status Update for 03/21

This week, I started my implementation of the driving HDL for the WaveShaper’s audio output with Jake. This involved reading the documentation and datasheets for several different IP blocks and most importantly filtering out which ones not to use.

 

By the end of the week, we were able to get a noisy signal coming out of the hardware in a manner that is distinct from both environment noise and the state when the hardware for driving the speaker is not initialized. While this is a far cry from the desired result, I feel confident that my SystemVerilog is directly driving the output signal, so it is merely a matter of detecting whichever bug or oversight is throwing a wrench in the works.

 

This also marked the beginnings of a top-level module which has kick-started the iterative design process of architecting the HDL and interconnecting the modules that we have thus far.

 

I was not able to attend last week’s lab session and aim to better touch base with my teammates in preparation for the interim demo on Monday.