working code for Mozzi output via MCP4811/MCP4801/MCP4821 DACs (and probably MCP4901/4911/4921 series too)

2,230 views
Skip to first unread message

fakeb...@gmail.com

unread,
Feb 18, 2014, 11:32:51 AM2/18/14
to mozzi...@googlegroups.com
Sorry if this is fairly widely known, I couldn't find all the info together in one place - basically I've got this working by connecting the DAC (a 10bit MCP4811 in my case) via the same pins used for the Arduino-based Bleep Drum:

(the pin numbers are for the ATMega328 rather than the Arduino pins but they're easily translatable via the charts at http://forum.arduino.cc/index.php/topic,146315.0.html )

The 4801 series DACs have SHDN on pin 6 rather than REFA but seem to work OK if you leave it disconnected, plus handily you can then run the Bleep Drum sketch on the same setup.

Then in MozziGuts.cpp you need to include the SPI library at the start (mine seems to need the full path probably due to me not understanding .h files properly)
#include "C:\Documents and Settings\DGreen\My Documents\arduino-1.0.3\libraries\SPI\SPI.h">

...and in ISR(TIMER1_OVF_vect, ISR_BLOCK), just after output_buffer_tail++; comment out the Mozzi audio output...

// AUDIO_CHANNEL_1_OUTPUT_REGISTER = output_buffer[(unsigned char)output_buffer_tail & (unsigned char)(BUFFER_NUM_CELLS-1)]; // 1us, 2.5us with longs

...and paste in the following (you can theoretically leave the previous line in and take output from either PWM pin 9 or the DAC, though I think there's a performance hit for doing so)
 
    uint16_t dac_out = ( 0b0111000000000000 | ( (output_buffer[(unsigned char)output_buffer_tail & (unsigned char)(BUFFER_NUM_CELLS-1)])<<1 )); 
    PORTB &= 0b11111011; //faster digitalWrite(10,LOW);
    SPI.transfer(dac_out>>8);
    SPI.transfer(dac_out & 255);
    PORTB |= 0b00000100; // faster digitalWrite(10,HIGH);

(the <<1 in the first line is like a software volume control depending how many bits you have available; <<2 or <<3 probably double the volume each time)

...then finally add these two SPI controls to startMozzi(int control_rate_hz)

void startMozzi(int control_rate_hz)
{
    SPI.begin(); 
    SPI.setBitOrder(MSBFIRST);

(I also have to #include "SPI.h" at the start of my main Mozzi sketches but there are probably ways around that - I started out incorporating the SPI.transfers into my updateAudio() functions where they kind of worked but are prone to timing irregularities that the excellent buffering in MozziGuts.cpp avoids)

anyway, hope this is some use - get in touch here or twitter.com/fakedavegreen for any feedback/clarifications!


scuttie

unread,
Mar 7, 2014, 3:31:22 PM3/7/14
to mozzi...@googlegroups.com
Hi and good work in getting Mozzi to work on the MCP4xxx chips! :)
I've changed the code as you suggested and can confirm that I've got Mozzi working with an MCP4922 dual DAC (only through 1 channel yet though.)
I've not tried all of the examples only a few but it works fine.
Thanks again!
Steve Scutt.

scuttie

unread,
Mar 9, 2014, 12:09:54 PM3/9/14
to mozzi...@googlegroups.com
UPDATE: Also, with the dual DACs you control which channel the signal comes out of on bit 15 of the register. So if this line is changed in Mozziguts.h:

uint16_t dac_out = ( 0b0111000000000000 | ( (output_buffer[(unsigned char)output_buffer_tail & (unsigned char)(BUFFER_NUM_CELLS-1)])<<3 )); 

so that  the leftmost bit is a 1 (i.e.:  0b1111000000000000 ),  
the signal comes out of channel 2 instead of 1!
So the next question is:  How to make Mozzi Stereo. ??

Mr Sensorium

unread,
Mar 9, 2014, 8:39:39 PM3/9/14
to mozzi...@googlegroups.com
Hi,
this thread has a hack and example which does stereo, using 2 output buffers:
https://groups.google.com/d/msg/mozzi-users/YmmnCsKL6GA/tOpwumr8LMQJ
It's out of date, but that makes it easier to read, since Mozziguts was a lot simpler with less conditional compilation etc. back then..

Tim

Fakebit Polytechnic

unread,
Mar 10, 2014, 1:53:48 PM3/10/14
to mozzi...@googlegroups.com
No worries, hope it's useful - Bleep Drum (and of course Mozzi) had done all the difficult stuff already..!

I've also put a possibly more straightforward diagram on my Mozzi synth pages (link below) for anyone potentially put off by having to decode the ATmega328 pinouts : )



--
You received this message because you are subscribed to a topic in the Google Groups "Mozzi-users" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/mozzi-users/mQr4T45Kteg/unsubscribe.
To unsubscribe from this group and all its topics, send an email to mozzi-users...@googlegroups.com.
To post to this group, send email to mozzi...@googlegroups.com.
To view this discussion on the web, visit https://groups.google.com/d/msgid/mozzi-users/545e1627-49a9-48ed-8124-92ab9bdca2d9%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Jean-Luc Deladrière

unread,
Mar 13, 2015, 3:18:28 AM3/13/15
to mozzi...@googlegroups.com
Hi 
Can you post your modified  MozziGuts.cpp
I 'am trying your modifications with an MCP4822  but without success
thanks

marcelo malmierca

unread,
Jun 24, 2015, 11:08:49 AM6/24/15
to mozzi...@googlegroups.com

Can you post your modified MozziGuts.cpp ?

Thanks in advance !

Marcelo

frost...@gmail.com

unread,
Feb 22, 2016, 7:58:15 PM2/22/16
to Mozzi-users
Hi Everyone,

I've had some success using an external DAC with mozzi, using Fakebit Polytechnic's circuit diagram from his website (http://www.fakebitpolytechnic.com/cheapsynth-external-module/#DAC).

However, some things have changed about MozziGuts.cpp since Fakebit Polytechnic posted his code above, so you can't just copy and paste anymore.

This is what I had to do to get it to work with the current version of Mozzi (1.0.2):

-------------------------------------
Edit MozziGuts.cpp:
-------------------------------------


1) Near the top of the file, along with the other includes, add:

#include "SPI.h"


(I didn't need to supply the full path the "SPI.h", but if you have an error when compiling sketches maybe you will need the full path - see Fakebit's original post)


2) Find the line, "AUDIO_CHANNEL_1_OUTPUT_REGISTER = output_buffer.read();" and comment it out with two "/" slashes (turning off the PWM output):

// AUDIO_CHANNEL_1_OUTPUT_REGISTER = output_buffer.read();


3) Under the line you just commented out, add the following to turn on the DAC output:

uint16_t dac_out = ( 0b0111000000000000 | (output_buffer.read()<<3 ));
    PORTB &= 0b11111011; //faster digitalWrite(10,LOW);
    SPI.transfer(dac_out>>8);
    SPI.transfer(dac_out & 255);
    PORTB |= 0b00000100; // faster digitalWrite(10,HIGH);



4) Under "void startMozzi(int control_rate_hz)" add the following (after the curly braces):

    SPI.begin(); 
    SPI.setBitOrder(MSBFIRST);

So it should read:


void startMozzi(int control_rate_hz)
{
  SPI.begin(); 
  SPI.setBitOrder(MSBFIRST);
    setupMozziADC(); // you can use setupFastAnalogRead() ...
.... and so on....


5) You also need to include "SPI.h" at the top of your mozzi sketches:

#include "SPI.h"


Hopefully this works for people - let me know!

frost...@gmail.com

unread,
Feb 22, 2016, 8:21:10 PM2/22/16
to Mozzi-users
Oh - there is one hitch with what I've posted above, and I'm not sure how to fix it:

When the waveform output from all my mozzi sketches (including the basic sine demo) is only half the available voltage swing out of the DAC (MCP4811) - it should be 2v peak to peak, but I'm only getting 1v p-p.

So I'm loosing some bit depth I assume... Is there anything people can think of that would be causing this?

I'm not a programmer - I just dabble in the dark arts of copy and paste :) ....so my understanding of bit manipulation etc is pretty much non-existent I'm afraid.

I've tried changing the value of the "<<3" in the line:


uint16_t dac_out = ( 0b0111000000000000 | (output_buffer.read()<<3 ))


If i decrease this value to <<1 or <<2 the output waveform is quieter.  If I increase it to <<4 then the sinewave is clipped and then the peaks are folded back on itself... but the clipping point is 2v peak to peak, so I know it is capable of the full voltage swing.

I've also tested the arduino - DAC setup with some other, non mozzi sketches, and I can get the full 2v p-p out.

One example that works with full voltage swing is on Moosteria's blog: http://moosteria.blogspot.com.au/2015/02/dacs-part-2.html


Any thoughts?

Jean-Luc Deladrière

unread,
Feb 23, 2016, 1:27:17 AM2/23/16
to Mozzi-users
I also played with the MCP4811 and had seen that too
I changed the bias :
#define AUDIO_BIAS ((unsigned int) 0x2000) (line 31 in AudioConfigHiSpeed14bitPwm.h)
to : #define AUDIO_BIAS ((unsigned int) 0x0770)
Can you give a try ?

frost...@gmail.com

unread,
Feb 23, 2016, 2:49:34 AM2/23/16
to Mozzi-users
Thanks Jean - I gave that a go, tried that, didn't make any difference to the output for me...

Maybe I'm not using "AudioConfigHiSpeed14bitPwm.h"?

I think the way I've modified MozziGuts.cpp I'm just using "standard mode" rather than the 14bit mode?

To be clear - the problem I'm having is the amplitude of the DAC output - the offset seems ok... seems to be centered in the range of voltage swing the DAC is capable of...

Cheers though!

Jean-Luc Deladrière

unread,
Feb 23, 2016, 3:20:38 AM2/23/16
to Mozzi-users
I was using HIFI
Here are the file I modified ...
Note that I used pin 8 for CS  instead of 10  (I have disassembled the hardware so I can't test it today)
I renamed the Mozzi folder to MozziGuts_DAC to separate from a normal setup
MozziGuts_DAC.cpp
dac.h
mozzi_config.h

frost...@gmail.com

unread,
Feb 23, 2016, 6:08:14 AM2/23/16
to Mozzi-users
Thanks so much Jean! I'll give these files a go tomorrow.

Is it built on top of Mozzi-1.0.2?

I notice at the top of MozziGuts_DAC.cpp there's a line: #include "MozziGuts_DAC.h"

Is that the file called "dac.h" attached above? do I just need to rename it?

Thanks so much again!

Jean-Luc Deladrière

unread,
Feb 23, 2016, 6:22:37 AM2/23/16
to Mozzi-users
oops Yes.. I guess (sorry I made this a year ago)

frost...@gmail.com

unread,
Feb 25, 2016, 8:35:29 AM2/25/16
to Mozzi-users
Hi Jean,

I'm getting an error "error: MozziGuts_DAC.h: No such file or directory" when I try to compile - Do I need "MozziGuts_DAC.h" from you?

Thanks! Sorry to bug you :)

Jean-Luc Deladrière

unread,
Feb 25, 2016, 8:48:40 AM2/25/16
to Mozzi-users
Yes you need the dac.h file I uploaded before
rename the dac.h I uploaded  or change the error line  to refer to dac.h

frost...@gmail.com

unread,
Feb 25, 2016, 3:46:22 PM2/25/16
to Mozzi-users
Hi Jean,

Your MozziGuts_DAC.cpp has #includes for both dac.h and MozziGuts_DAC.h

If I comment out the include for MozziGuts_DAC.h I still get lots of errors when compiling.

Are you sure there isn't an additional file called "MozziGuts_DAC.h" that I need?

Sorry to bug you!

Thanks for bearing with me!

Jean-Luc Deladrière

unread,
Feb 26, 2016, 1:36:59 AM2/26/16
to Mozzi-users
Really sorry  : I should rebuild one (I will soon do) to make sure about what I say
In the mean time can you try to copy these files and overwrite the other
mozzi_config.h
Oscil.h
MozziGuts.cpp
AudioConfigHiSpeed14bitPwm.h
dac.h

frost...@gmail.com

unread,
Feb 26, 2016, 9:24:58 PM2/26/16
to Mozzi-users
Thanks!

I'll give it a go and report back :)

frost...@gmail.com

unread,
Feb 26, 2016, 11:30:44 PM2/26/16
to Mozzi-users
Ok, it now compiles without error (as long as I include "SPI.h" at the top of my sketches).

Now I just need to build the circuit to test!

Thanks Jean :)

frost...@gmail.com

unread,
Mar 1, 2016, 11:00:24 PM3/1/16
to Mozzi-users
Hi Jean,

Do you remember what pin CS is on in your files - Was it 8 or 10?

Is it easy to change?

I already have some circuit boards soldered up on veroboard that uses pin 10 for CS... I can change them but surely it's easy to change in software, I just couldn't see where...

Thanks man!

Jean-Luc Deladrière

unread,
Mar 5, 2016, 3:55:47 AM3/5/16
to Mozzi-users
To get pin 10 working you need to change the dac code to toggle the pin 10 like :
void setOutput(unsigned int val)
{
   
  byte lowByte = val & 0xff;
  
  byte highByte = ((val >> 8) & 0xff) | 0x10;

  // Set CS PIN LOW
  PORTB &= 0xfb; //pin10
  // PORTB &= 0xfe; // pin8
 

  SPI.transfer(highByte);
  SPI.transfer(lowByte);

   // Set CS PIN HIGH
  PORTB |= 0x4; // pin10  
  // PORTB |= 0x1; // pin 8
}

I have a DAC installed on pin 10 but I started checking the modified code I gave you but ... I can't get it to work anymore  :-(
I guess I will have to retrace my steps back from the beginning. Really sorry

Anyway if you want to check your DAC on pin 10 ; try this


#include <SPI.h>

// basic DAC SPI test 
//                  +---\/---+
//   +5V     VDD  1 |  MCP   | 8 VOUTA  out
//   ss 10   /CS  2 |  4822  | 7 VSS    Gnd
//   sck 13  SCK  3 |        | 6 VOUTB
//  mosi 11  SDI  4 +---\/---+ 5 /LDAC  Gnd
//        

 
void setup()
{
  pinMode(10, OUTPUT);
  SPI.begin();  
  SPI.setClockDivider(SPI_CLOCK_DIV2);
}
 
//assuming single channel, gain=2
void setOutput(unsigned int val)
{
   
  byte lowByte = val & 0xff;
  
  byte highByte = ((val >> 8) & 0xff) | 0x10;

  // Set CS PIN LOW
  PORTB &= 0xfb; //pin10
  // PORTB &= 0xfe; // pin8
 

  SPI.transfer(highByte);
  SPI.transfer(lowByte);

   // Set CS PIN HIGH
  PORTB |= 0x4; // pin10  
  // PORTB |= 0x1; // pin 8
}
  
void loop()
{
 //high-res triangular wave
 for (int i=0; i < 4096; i+=1)   
 {
  
  setOutput(i);
 }
}

Louis Croisez

unread,
May 14, 2016, 1:00:15 PM5/14/16
to Mozzi-users
I have a DAC MCP4822 working well now with Mozzi_1.0.2.
I really would like to upgrade to stereo, because the 4822 has this capability, but also because playing with Mozzi in Stereo is way more interresting.

I have problems with the polyphony patched files using 2 output buffers (see https://groups.google.com/d/msg/mozzi-users/YmmnCsKL6GA/tOpwumr8LMQJ).
MozziGuts.cpp and MozziGuts.h from this zip file are not compatible with Mozzi_1.0.2, nor with Mozzi_1.0.0.
And also, there is no ref inside the zip to know from which release it was coming.

Does someone has done a working "polyphony patch" for Mozzi_1.0.2 already?
Thanks.

Tim Barrass

unread,
May 14, 2016, 10:14:37 PM5/14/16
to mozzi...@googlegroups.com
Hi Louis,
here are some files from my unpublished version of Mozzi, with a STEREO_HACK option in mozzi_config.h.  I should get around to testing it properly and making it available, when I have time...
I hope it works for you..

TIm

--
You received this message because you are subscribed to the Google Groups "Mozzi-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mozzi-users...@googlegroups.com.

To post to this group, send email to mozzi...@googlegroups.com.
mozzi_config.h
MozziGuts.cpp
MozziGuts.h
Stereo_Hack.ino

Louis Croisez

unread,
May 16, 2016, 11:20:12 AM5/16/16
to Mozzi-users
Hello, thank you for giving me your code.
Thanks to you, I got Mozzi-1.0.2 working with MCP4822 in stereo.

I had initialy started playing with a Nano clone, and I just switched to Teensy3.1 (which I did'nt used for a long time because it was 3.3V only, and some of my sensors required 5V). 
With Teensy, I get more cpu speed, and more freedom in playing with stereo hacks ;)

BTW, I added following 3 lines to MozziGuts.h file:
#if defined(__MK20DX128__) || defined(__MK20DX256__)
#include <ADC.h>
#endif
This avoids to decomment //#include <DAC.h> at beginning of all example sketches, when using a Teensy.

I attached you a zip with a working sketch (the phasemod_envelop demo + a pan left/right using a knob on analog0 input).

LOUIS
Mozzi-1.0.2-louis-stereodac.zip

Tim Barrass

unread,
May 16, 2016, 7:43:25 PM5/16/16
to mozzi...@googlegroups.com
Great, thanks Louis, I'll add your modification (with credit)  in the next release.
Tim

--
You received this message because you are subscribed to the Google Groups "Mozzi-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mozzi-users...@googlegroups.com.
To post to this group, send email to mozzi...@googlegroups.com.

Louis Croisez

unread,
May 18, 2016, 1:27:59 AM5/18/16
to Mozzi-users
I think there is a lot of open improvements considering the stereo issue. I think about modifying the reverb tank, to make it reverb in stereo.

Tim Barrass

unread,
May 18, 2016, 11:36:04 PM5/18/16
to mozzi...@googlegroups.com
Go for it Louis - please feel free to create a fork of Mozzi on github to develop your ideas...

Louis Croisez

unread,
May 24, 2016, 3:09:30 AM5/24/16
to Mozzi-users
Reply all
Reply to author
Forward
0 new messages