Table of Contents
dsPIC/PIC32 tone generator
This is a project for the dsPIC33FJ128GP802 or PIC32MX150F128B acting as a tone generator connected to a Raspberry Pi.
Four separate tones may be generated simultaneously from five different waves and each tone can be any audible frequency.
A tone may also be triggered and it has a standard four stage envelope (ADSR).
This project is under development and certain aspects may change and features added or removed at any time.
Waves
There are standard wave types supported for generating tones.
A noise generator is also available which operates at the current frequency.
Schematic
This is the bare minimum layout required for this project using the dsPIC with integrated audio DAC. We use a RPi for communication and ICSP.
For PIC32 an external audio DAC is required. Only the CS4334K and PT8211 are supported at present and are selected at compile time. Connection to either device is as follows.
CS4334K WITH Vcc = 5V. PIC32MX150 CS4334K COMMENT ---------- ------- ------- PIN 15 RPB6 PIN 4 MCLK 128X OVERSAMPLING CLOCK PIN 16 RPB7 PIN 3 LRCK SAMPLE RATE LEFT/RIGHT CLOCK PIN 17 RPB8 PIN 1 SDATA SERIAL DATA INPUT PIN 18 RPB9 PIN 2 DEM/SCLK DE-EMPHASIS FILTER OFF/ON PIN 25 SCK1 UNUSED |
PT8211 WITH Vdd = 5V. PIC32MX150 PT8211 COMMENT ---------- ------- ------- PIN 15 RPB6 UNUSED PIN 16 RPB7 PIN 2 WS SAMPLE RATE LEFT/RIGHT CLOCK PIN 17 RPB8 PIN 3 SDATA SERIAL DATA INPUT PIN 18 RPB9 UNUSED PIN 25 SCK1 PIN 1 BCK SERIAL BIT CLOCK |
The CS4334K is a far superior device, but the PT8211 is incredibly cheap (15p each).
Firmware
For dSPIC First install a working XC16 compiler, for PIC32, install XC32.
Now build the dsPIC/PIC32 applications.
hg clone http://hg.kewl.org/pub/generator cd generator/src make
Pickle must be installed and configured and when ready we can write the firmware.
Eg.
p24 lvp program dspic.hex
Usage
Controlling the tone generator is accomplished via the RPi UART at 115200 baud.
When connected a prompt is displayed which contains the currently selected voice. If no prompt is seen, pressing enter will bring it up.
Commands are entered following a parameter entry. Parameter entry is done via a 32-bit accumulator. As each nibble of a hexadecimal value is entered the current accumulator value is shifted left 4 bits and the new value added. To clear the accumulator, enter eight noughts in succession or a full-stop.
Once the accumulator has been set, and a single character command may be entered. The command operates on the current accumulator value.
Commands
Here is the command table, most commands operate on the current accumulated value described in usage above.
Command | Description |
---|---|
. | The accumulator is reset |
+ | The accumulator is incremented |
- | The accumulator is decremented |
~ | The accumulator low nibble is transferred to the voice function selection byte |
= | The accumulator is transferred to the voice control word |
/ | The accumulator low word is transferred to the voice volume word |
% | The accumulator low word is transferred to the voice square wave duty word |
@ | The accumulater low word is transferred to the voice ADSR envelope generator |
! | Trigger the voice ADSR envelope |
> | The accumulator low nibble is transferred to the voice selection byte |
\ | The accumulator low word is transferred to the master volume word |
# | The accumulator low byte is evaluated as a midi note and used to update the voice control word |
< | The accumulator is evaluated as a frequency and used to update the voice control word |
$ | The accumulator is evaluated as SID HI/LO registers and used to update the voice control word |
If updating the voice control word directly using '=' (rather than using a midi note, frequency or SID value) the following formula must be used.
CONTROL WORD = 2^32 / 78000 * FREQUENCY
Using GNU bc from the shell we can calculate the above for 440 Hz like this.
printf "%08X=\n" `echo "scale=10; 2^32 / 78000 * 440" | bc` 0171B0B4=
Examples
Here are some examples showing the parameter entry followed by a command and the function performed.
Entry | Function |
---|---|
1~ | Select sine waveform |
2~ | Select triangle waveform |
3~ | Select saw-tooth waveform |
4~ | Select square waveform |
5~ | Select noise |
0~ | Select nothing (OFF) |
7FFF/ | Set max volume |
8000% | Set 50% duty cycle |
AAAA@ | Set ADSR |
! | Trigger ADSR |