This is an old revision of the document!
dsPIC tone generator
This is a project for the dsPIC33FJ128GP802 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 still under development and certain aspects may change or features added or removed at any time.
Waves
These are standard wave types supported for generating tones.
A noise generator is also available which operates at the current frequency.
Install
First install a working XC16 compiler.
Now build the dsPIC application.
hg clone http://hg.kewl.org/pub/generator cd generator make
This is the bare minimum layout required for this project. We will use a RPi for communication with the dsPIC and for ICSP.
Pickle must be installed and configured and when ready we can write the firmware.
p24 lvp program dac/dac.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 accumulated is evaluated as the voice ADSR envelope |
! | 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 |