## Expo Converters / DACs

**Moderators:** Kent, luketeaford, Joe.

### Expo Converters / DACs

Hello!

I'm quite new to all of this but there ist something that quite bothers me and that I don't understand.

I started learning everything about analog synthesizer and how each circuit works. Now I'm stuck with understanding the exponential vs. linear, expo converters... thing.

My question would be: (And its most probably full of mistakes and wrong ideas but I'm happy to learn!)

Why don't use persice DACs to output CV in a logarithmic scale to control VCO/VCFs frequency WITHOUT an Expo Converter as this is the troublemaker that makes everything unstable?

I understand that the DACs then would have to produce higher voltages but would that really be a problem?

I'm quite new to all of this but there ist something that quite bothers me and that I don't understand.

I started learning everything about analog synthesizer and how each circuit works. Now I'm stuck with understanding the exponential vs. linear, expo converters... thing.

My question would be: (And its most probably full of mistakes and wrong ideas but I'm happy to learn!)

Why don't use persice DACs to output CV in a logarithmic scale to control VCO/VCFs frequency WITHOUT an Expo Converter as this is the troublemaker that makes everything unstable?

I understand that the DACs then would have to produce higher voltages but would that really be a problem?

### Re: Expo Converters / DACs

this can be done, but it depends upon the range you want, and what you want to use that exponential voltage for. the most restrictive example is a VCO. lets say you want 20Hz to 20kHz of range, and this is now mapped linearly to a DAC produced voltage that maxes out at 5V, you now have a 5mV to 5V CV being produced which needs to be accurately converted into a current to charge a capacitor. at 5V, this is not a problem, but at 5mV a lot of little errors can cause a much bigger change in current. lets just take the offset voltage of the opamp used to convert voltage to current. each cent is 0.06% of your CV value, so down at 5mV, a drift of 3uV will be 1 cent. lets say we can handle 5 cents of drift, thats 15uV that you need to keep the offset voltage from drifting. you can do this, but it usually requires a chopper stabilized opamp. you also need a DAC that is low drift down to that level as well. and, if you want a few cents of resolution on the DAC, thats 100cents x 10octaves x 12notes = 12000 values or 14b for 1 cent, or 12b for 4 cent. so you need a decent DAC. these start to get expensive. you can add up 2 or more lower resolution DACs, but then they need to precisely calibrated to each other. and all of this requires a microcontroller. but, once you have a microcontroller, now you can start doing auto calibration, etc, and make up for some of the limitations. so it can be done, and there are definitely applications for this, but its a bit more complicated and costly. some synths do do this, but a decent temperature stable expo converter isnt too hard to come by, and can be quite cheap. if its of any help, here are some ways of doing it in analog and their relative tradeoffs:

http://www.openmusiclabs.com/files/expotemp.pdf

also, this is by no means an attempt to discourage you from using a DAC, there are things you can do with digital control that are very difficult in analog.

http://www.openmusiclabs.com/files/expotemp.pdf

also, this is by no means an attempt to discourage you from using a DAC, there are things you can do with digital control that are very difficult in analog.

openmusiclabs.com

### Re: Expo Converters / DACs

Driving precisely tunable low frequency notes from a linear DAC also requires very high resolution. 1 cent for any given frequency is 1.005777895... times it (resulting in 1200 multiplying steps per octave, 1.005777895^1200 = 2). A step 1 cent up from 20.00Hz goes to about 20.01 Hz, about 1/100 Hz, and with a linear DAC you have this resolution across the full range. For 20 kHz at this resolution, you will need 20000 * 100 = 20 Million steps, which is just above 2^24 = 16.7 Million. Therefore, by sacrificing a bit (literally, as in "binary digit") of precision at the low end, you can specify a 24 bit DAC.

Short of exotic precision metrology equipment, such a DAC doesn't exist in the "classic" form we're mainly interested in. Audio codecs with that nominal resolution resort to "Sigma-Delta" 1-bit conversion, which is one way to do Pulse Density Modulation (PDM). I haven't got the exact math ready, but an interesting bit about 1-bit conversion is that the precision is higher around the center (a 1010101010...) pattern. This is just what we need for the low frequencies. So if you manage to create such a PDM output, and map the center to 0V, your only remaining task is to either keep drift in the single microvolt range as guest wrote, or correct for it in software (in which case you could just as well correct an expo converter).

Don't be scared, though. I've seen an old Yamaha mono which uses Hz/V (linear CV) internally being switched on and played (no very low notes, I guess...). Instantly in tune, no drift over time. It is well feasible.

Short of exotic precision metrology equipment, such a DAC doesn't exist in the "classic" form we're mainly interested in. Audio codecs with that nominal resolution resort to "Sigma-Delta" 1-bit conversion, which is one way to do Pulse Density Modulation (PDM). I haven't got the exact math ready, but an interesting bit about 1-bit conversion is that the precision is higher around the center (a 1010101010...) pattern. This is just what we need for the low frequencies. So if you manage to create such a PDM output, and map the center to 0V, your only remaining task is to either keep drift in the single microvolt range as guest wrote, or correct for it in software (in which case you could just as well correct an expo converter).

Don't be scared, though. I've seen an old Yamaha mono which uses Hz/V (linear CV) internally being switched on and played (no very low notes, I guess...). Instantly in tune, no drift over time. It is well feasible.

### Re: Expo Converters / DACs

thanks for the correction on my DAC resolution calculation, that 14b number seemed way too low!

i spent a bunch of time looking at various DAC to CV options, and just thumbed through my notebook for anything that might be of use. heres some findings:

1. dual or triple PWM circuits are limited to around 18b or so due to resistor limitations (20b max). if you dont need the full 10 octaves or 1cent resolution, this might be good enough. dual DACs can improve performance a bit over PWM.

2. a DAC to an expo converter can by quite accurate and cheap. one trick is to use an DAC with external reference (or if PWM the logic level) and drive the reference with a Vt generator. this eliminates the multiplier in Vt mulitplier circuits, which are some of the best thermal compensation techniques.

3. you can also drive an MDAC with another DAC to get a larger range. or, have a 2b or 3b code select various mixing resistors into the voltage to current converter. if you imagine having a 3b code selecting one of eight octaves, then a 12b DAC will give 1 cent resolution.

4. audio codecs are a decent solution. they are cheap and high resolution. but, most datasheets dont list temperature drift. some of the cirrus chips do, and maybe akm, and the numbers ive seen are pretty good. i tested out an audio DAC driving a VCO and my notes say: 0.1Hz short term jitter, 0.3Hz long term jitter; noise floor around 16b, although responds to bits down to 24b; usable down to 20Hz, but pertty poor until 200Hz. a better DAC with a better layout would help the situation a lot. this was with an old wolfson codec that had 16b noise floor on a good day, with an arduino powering it, so whatever the onboard 3.3V regulator produced was the noise i had to deal with.

i spent a bunch of time looking at various DAC to CV options, and just thumbed through my notebook for anything that might be of use. heres some findings:

1. dual or triple PWM circuits are limited to around 18b or so due to resistor limitations (20b max). if you dont need the full 10 octaves or 1cent resolution, this might be good enough. dual DACs can improve performance a bit over PWM.

2. a DAC to an expo converter can by quite accurate and cheap. one trick is to use an DAC with external reference (or if PWM the logic level) and drive the reference with a Vt generator. this eliminates the multiplier in Vt mulitplier circuits, which are some of the best thermal compensation techniques.

3. you can also drive an MDAC with another DAC to get a larger range. or, have a 2b or 3b code select various mixing resistors into the voltage to current converter. if you imagine having a 3b code selecting one of eight octaves, then a 12b DAC will give 1 cent resolution.

4. audio codecs are a decent solution. they are cheap and high resolution. but, most datasheets dont list temperature drift. some of the cirrus chips do, and maybe akm, and the numbers ive seen are pretty good. i tested out an audio DAC driving a VCO and my notes say: 0.1Hz short term jitter, 0.3Hz long term jitter; noise floor around 16b, although responds to bits down to 24b; usable down to 20Hz, but pertty poor until 200Hz. a better DAC with a better layout would help the situation a lot. this was with an old wolfson codec that had 16b noise floor on a good day, with an arduino powering it, so whatever the onboard 3.3V regulator produced was the noise i had to deal with.

openmusiclabs.com

### Re: Expo Converters / DACs

Thank you for your responses! I see this goes way beyond my current knowledge... but I understand the main issues.

What got me thinking was

a. Old Yamaha and Korg synths that were hz/V and worked very well. (I got a Yamaha CS20M myself)

b. All analog polys get their CV from Dacs (correct me if I’m wrong)

The Prophet 5 OSC B has also a LFO Mode.

What got me thinking was

a. Old Yamaha and Korg synths that were hz/V and worked very well. (I got a Yamaha CS20M myself)

b. All analog polys get their CV from Dacs (correct me if I’m wrong)

The Prophet 5 OSC B has also a LFO Mode.

### Re: Expo Converters / DACs

a lot of the analog polys had expo converters, so the DAC was just driving the expo. and on a keyboard, the top note is 4kHz, so the range isnt as drastic. you could probably get away with an 18b converter and still have ~1cent resolution.

openmusiclabs.com

### Re: Expo Converters / DACs

guest:

Heh, I thought you were just doing the calculation for the expo variant with the 14 bit. Interesting results with the audio DACs, I always asked myself whether these are suitable for "ordinary" DC drive applications. Low-pass filtering might help getting smoother results with them?!

Anyway, I was thinking more of primitive solutions for the PDM output, like a microcontroller that outputs a continuous SPI stream at, say 64kHz ("64x oversampling" in CD player lingo) that is entirely done in software. It would be followed up by a four-pole low pass at 1kHz that lowers the sample rate by 6 octaves * 24dB = 144 dB. But reading over your calculations for the microvolt range, I think such a setup would probably introduce too many errors.

ArthurTsz:

b. yes, and the LFO mode of a VCO can simply be done by linearly reducing the CV voltage by a few volts to drop the frequency by a few octaves. This is usually an extra switch in hardware, so the DACs don't have to cover the whole spectrum.

Btw, one "halfway" solution to getting around expo converters is to move it to the DAC and distribute exponential voltage from there. The Poly 61 does this for the CV (but it doesn't have to be precise, because it has DCOs).

I suspect the expo temperature compensation on "modern" polys is almost entirely in software, made from a combination of some temperature measurement (ideally some expo-like transistor Vbe close to the expo(s), but using some on-controller sensing is cheaper), and autotune results.

Heh, I thought you were just doing the calculation for the expo variant with the 14 bit. Interesting results with the audio DACs, I always asked myself whether these are suitable for "ordinary" DC drive applications. Low-pass filtering might help getting smoother results with them?!

Anyway, I was thinking more of primitive solutions for the PDM output, like a microcontroller that outputs a continuous SPI stream at, say 64kHz ("64x oversampling" in CD player lingo) that is entirely done in software. It would be followed up by a four-pole low pass at 1kHz that lowers the sample rate by 6 octaves * 24dB = 144 dB. But reading over your calculations for the microvolt range, I think such a setup would probably introduce too many errors.

ArthurTsz:

b. yes, and the LFO mode of a VCO can simply be done by linearly reducing the CV voltage by a few volts to drop the frequency by a few octaves. This is usually an extra switch in hardware, so the DACs don't have to cover the whole spectrum.

Btw, one "halfway" solution to getting around expo converters is to move it to the DAC and distribute exponential voltage from there. The Poly 61 does this for the CV (but it doesn't have to be precise, because it has DCOs).

I suspect the expo temperature compensation on "modern" polys is almost entirely in software, made from a combination of some temperature measurement (ideally some expo-like transistor Vbe close to the expo(s), but using some on-controller sensing is cheaper), and autotune results.

### Re: Expo Converters / DACs

ive wondered about using an SPI for PDM, but it seemed like it would be a lot of processing overhead (at least for audio rate). but maybe with an ARM processor thats not such a concern. some of the PICs have an NCO on them, which i think can be used to do PDM. you just load your value into the NCO, and set it to produce a pulse on every overflow. the larger the count, the more it will overflow.

openmusiclabs.com

### Re: Expo Converters / DACs

For audio, PDM is a science in itself. I haven't done the math, but as I understood it, in layman's terms, you can end up with a repeating cycle in the audio spectrum, therefore the bitstream needs to undergo further processing. I think a crude approach to solving that could be to add a slight bit of high frequency noise to spread this aliasing (it could even be summed up, so the integrated S-D value stays correct). Computing power is not a big deal if the desired result is a CV up to a kHz, and you can feed 8 bits every 125ms (which even an AVR could do) and filter out the high frequency components. Variants could include using sample/hold logic as integrator (with tri-state input while holding). I guess a few advantages over trivial PWM could be found, but I haven't made any hands-on experiments yet.

### Re: Expo Converters / DACs

there are a lot of things i get hung up on when i start thinking it through. i dont know if you have any of the answers to this, but:

1. what do you do for low values? is it limited the same way PWM is limited, where min_value = min_freq/clock_freq. for example, you have 1MHz clock, and you want 1kHz as your lowest frequency, therefore you have 1000 spots you can fill with pulses, so smallest value is 1/1000? or do you not use the lowest values and just subtract some offset off? im beginning to wonder if this accounts for some of the low frequency issues i was having with the audio codec VCO.

2. is max_freq = clock_freq/2? do you have to skip every other slot so that you have identical pulse widths? i know there are issues of having varying pulse widths, as rise and fall times integrate differently than just a high or low level signal. so if you keep pulse widths the same, each pulse integrates an equal amount, whereas a longer pulse width will integrate to a slightly higher value due to having less rise and fall time as a precentage of its full length.

3. with DMA i can imagine a pretty efficient system, but is there some trick to get SPI to reload on the 8b machines? or is there a lot of interrupt overhead to just load a new value?

4. would you use a SD algorithm or NCO or something else for doing the actual pulse generation? lookup tables (this value = this pulse stream, etc)?

1. what do you do for low values? is it limited the same way PWM is limited, where min_value = min_freq/clock_freq. for example, you have 1MHz clock, and you want 1kHz as your lowest frequency, therefore you have 1000 spots you can fill with pulses, so smallest value is 1/1000? or do you not use the lowest values and just subtract some offset off? im beginning to wonder if this accounts for some of the low frequency issues i was having with the audio codec VCO.

2. is max_freq = clock_freq/2? do you have to skip every other slot so that you have identical pulse widths? i know there are issues of having varying pulse widths, as rise and fall times integrate differently than just a high or low level signal. so if you keep pulse widths the same, each pulse integrates an equal amount, whereas a longer pulse width will integrate to a slightly higher value due to having less rise and fall time as a precentage of its full length.

3. with DMA i can imagine a pretty efficient system, but is there some trick to get SPI to reload on the 8b machines? or is there a lot of interrupt overhead to just load a new value?

4. would you use a SD algorithm or NCO or something else for doing the actual pulse generation? lookup tables (this value = this pulse stream, etc)?

openmusiclabs.com

### Re: Expo Converters / DACs

Back in the day, there were companding DACs, with a piecewise-linear exponential output (plus a sign bit). I used one to build a companding ADC, combined with a successive approximation register. However, these were not high enough resolution to suffice for pitch control.

It might be feasible to make a discrete version - I think the circuitry is fairly simple. If you do that, you could make a higher-resolution version.

http://www.electrongate.com/dmxfiles/images/am6070.pdf

It might be feasible to make a discrete version - I think the circuitry is fairly simple. If you do that, you could make a higher-resolution version.

http://www.electrongate.com/dmxfiles/images/am6070.pdf

### Re: Expo Converters / DACs

guest:

1. The zero value is the center (10101010... pattern), the low values are around it. As you noted, it becomes difficult to get decent resolution near the edges. Accuracy decreases towards highter values. I remember reading around 60% of the switching voltage is the reasonable maximum.

2. I was assuming instant rise/fall in my ballpark calculations. But you could compensate for rise/fall by measuring the real-world difference to the ideal and calculate that into your sigma for any given bit pattern.

3. I took 8 kHz * 8 bit as an example, because in my "commercial" project, I drive DACs in an 8kHz interrupt on an AVR. Nothing that you would want to do under an Arduino runtime, but the hardware can deliver it. Once you use more modern hardware (which I did not, on purpose), you could also run DMA, but for low latency with the updates, I'd still update on the fly in the IRQ. I'd say from STM32 up you don't even have to look for performance tweaks. The computation has to be done anyway, and unless you want to save your IRQ latency for something else, why not use what the controller can do. It's not that you have a timeshare system where you have to be considerate with other users.

4. I'd use an SD algorithm. (I'm an old Woz school disciple and like using software for most things I can get away with to save hardware...)

jorg:

I've been asking myself how precise a successive-approximation DAC could be. In theory, there are no limits, you sample the reference voltage, halve it for every bit, and if it's a one, it goes to the integrator for a bit period. I assume it's rather difficult to be precise enough (i.e. R2R is better and simpler in all ways), or we'd see that in the wild.

1. The zero value is the center (10101010... pattern), the low values are around it. As you noted, it becomes difficult to get decent resolution near the edges. Accuracy decreases towards highter values. I remember reading around 60% of the switching voltage is the reasonable maximum.

2. I was assuming instant rise/fall in my ballpark calculations. But you could compensate for rise/fall by measuring the real-world difference to the ideal and calculate that into your sigma for any given bit pattern.

3. I took 8 kHz * 8 bit as an example, because in my "commercial" project, I drive DACs in an 8kHz interrupt on an AVR. Nothing that you would want to do under an Arduino runtime, but the hardware can deliver it. Once you use more modern hardware (which I did not, on purpose), you could also run DMA, but for low latency with the updates, I'd still update on the fly in the IRQ. I'd say from STM32 up you don't even have to look for performance tweaks. The computation has to be done anyway, and unless you want to save your IRQ latency for something else, why not use what the controller can do. It's not that you have a timeshare system where you have to be considerate with other users.

4. I'd use an SD algorithm. (I'm an old Woz school disciple and like using software for most things I can get away with to save hardware...)

jorg:

I've been asking myself how precise a successive-approximation DAC could be. In theory, there are no limits, you sample the reference voltage, halve it for every bit, and if it's a one, it goes to the integrator for a bit period. I assume it's rather difficult to be precise enough (i.e. R2R is better and simpler in all ways), or we'd see that in the wild.

### Re: Expo Converters / DACs

Here's an 11-bit COMDAC I've whipped up. It's a fairly "conceptual" design. "CPU" is anything outputting an 11-bit word. The DAC shown here is actually a serial (SPI) part from TI, but Tina (conveniently for simulation) shows it as a parallel word input. You could pop in a DAC0808 or something similar. The output is shown as an inverted exponential voltage; in real life you'd likely want a current, to charge a VCO capacitor. For that, replace the output op amp circuit (which is shown as a current-to-voltage converter with a bit of lowpass filtering) with your integrator/reset of choice. There's a bit of glitch at the "octave" transitions, when the DAC output suddenly changes, and the gain (CD4051 circuit) also changes, but not exactly simultaneous. To deal with this, you can use a lowpass, or a sample and hold, or some clever circuit of your choosing. There are a number of opportunities to tweak and improve accuracy. Pay close attention to resistor tolerances, choice of precision op amp (I picked fairly randomly), and possibly a trimmer or two is needed.

This circuit covers 8 octaves of current output, with 256 steps per octave (about 5 cents per step). You could add a couple more octaves (i.e. use a 4-bit multiplexer instead of 3-bits, and add a couple more resistors - maybe a 5k and a 2.56M).

The companding ADC I made in the 1980s was just for basic audio; I wasn't attempting to do any better than the COMDACs of the era (which were built for telephone applications). I think it came pretty close to exploiting the COMDAC's full pseudo-13 bit capability.

The circuit below is (for pitch CV purposes) roughly equivalent to a 16-bit DAC, but needs only 11 bits. Would I personally use it? Probably not - it'd be cheaper to just buy a 16-bit DAC, and simpler too.

This circuit covers 8 octaves of current output, with 256 steps per octave (about 5 cents per step). You could add a couple more octaves (i.e. use a 4-bit multiplexer instead of 3-bits, and add a couple more resistors - maybe a 5k and a 2.56M).

The companding ADC I made in the 1980s was just for basic audio; I wasn't attempting to do any better than the COMDACs of the era (which were built for telephone applications). I think it came pretty close to exploiting the COMDAC's full pseudo-13 bit capability.

The circuit below is (for pitch CV purposes) roughly equivalent to a 16-bit DAC, but needs only 11 bits. Would I personally use it? Probably not - it'd be cheaper to just buy a 16-bit DAC, and simpler too.

### Re: Expo Converters / DACs

On a related note, here's some code to convert linear to expo. It works on pretty much any CPU with floating-point, but doesn't use the very costly library functions to take the exponent.

#include <math.h>

#include <stdio.h>

#include <stdlib.h>

#define LOG2_TO_LN 0.693147180559945f

#define LOG2_TO_LOG10 0.301029995663981f

#define EXP2_TO_EXP 1.442695040888963f

#define EXP2_TO_EXP10 3.321928094887362f

inline float log2f (float arg)

// frexp is a macro, supported in FP hardware, which basically takes a "binary logarithm" of a floating point number.

// Use MS Excel to compute a trendline approximation (4th order polynomial) then manually tilt it so the ends have zero error (at 0.5 and 1.0).

// Manual tilt increases peak error but makes the output seamless and monotonic.

// return (-1.3063652f*x*x*x*x + 5.1500062f*x*x*x - 8.456181f*x*x + 8.1212785f*x - 3.508697f + (float)exp); // Peak Error ~ 0.00025

// Use https://www.wolframalpha.com/calculator ... alculator/ to reduce the number of multiplies by factoring the above polynomial:

// Math is reduced from 11 multiplies and 5 adds to 4 multiplies and 5 adds.

// For a fair comparison, standard "CSE" compiler optimization would give 9 multiplies and 5 adds.

{

float x;

int exp;

x = frexpf(arg, &exp);

return (-1.30637f*(x - 1.81165f)*(x - 0.999971f)*(x*(x - 1.13062f) + 1.48259f)) + (float)exp;

}

inline float exp2f (float arg)

// ldexp is a macro, supported in FP hardware, which basically takes a "binary exponentiation" of a floating point number.

// Use MS Excel to compute a trendline approximation (4th order polynomial) then manually tilt it so the ends have zero error (at 0.0 and 1.0).

// Manual tilt increases peak error but makes the output seamless and monotonic.

// y = 0.0068396f*x*x*x*x + 0.0531991f*x*x*x + 0.2394017f*x*x + 0.6930421f*x + 0.9999999f; // Error ~ 0.0009%

// Use https://www.wolframalpha.com/calculator ... alculator/ to reduce the number of multiplies by factoring the above polynomial:

// Math is reduced from 11 multiplies and 5 adds to 4 multiplies and 4 adds.

// For a fair comparison, standard "CSE" compiler optimization would give 9 multiplies and 5 adds.

{

float x,y,result;

int exp;

exp = (int)(arg)+(arg>0.0f);

x = arg-exp;

y = 0.0068396f*(x*(x + 1.76767f) + 13.726f)*(x*(x + 6.01044f) + 10.6519f);

return ldexpf(y,exp);

}

inline float logfq (float arg) // natural logarithm, scaled from log base 2

{

return LOG2_TO_LN * log2f (arg);

}

inline float log10fq (float arg) // logarithm base 10, scaled from log base 2

{

return LOG2_TO_LOG10 * log2f (arg);

}

inline float expfq (float arg) // e^x, scaled from exp2

{

return exp2f (EXP2_TO_EXP * arg);

}

inline float exp10fq (float arg) // 10^x, scaled from exp2

{

return exp2f (EXP2_TO_EXP10 * arg);

}

int main ()

{

float x, y, z, ygood, p=69, f=440, _l2;

int exp;

printf ("z, exp2(z), experr\n");

for(z=-2.002; z<=3.0; z+=0.002)

{

y=exp2f(z), ygood=pow(2.0,z);

printf ("%.6f, %.6f, %.6g\n",z,y,(y-ygood)/ygood);

}

printf ("x, log2(x), err, z, exp\n");

_l2=1.0/log(2.0);

for(x=0.24; x<=16.2; x*=1.05)

{

y=log2f(x), ygood=log(x)*_l2;

z = frexpf(x, &exp);

printf ("%.6f, %.6f, %.6g, %.6g, %d\n",x,y, y-ygood, z, exp);

}

return 0;

}

#include <math.h>

#include <stdio.h>

#include <stdlib.h>

#define LOG2_TO_LN 0.693147180559945f

#define LOG2_TO_LOG10 0.301029995663981f

#define EXP2_TO_EXP 1.442695040888963f

#define EXP2_TO_EXP10 3.321928094887362f

inline float log2f (float arg)

// frexp is a macro, supported in FP hardware, which basically takes a "binary logarithm" of a floating point number.

// Use MS Excel to compute a trendline approximation (4th order polynomial) then manually tilt it so the ends have zero error (at 0.5 and 1.0).

// Manual tilt increases peak error but makes the output seamless and monotonic.

// return (-1.3063652f*x*x*x*x + 5.1500062f*x*x*x - 8.456181f*x*x + 8.1212785f*x - 3.508697f + (float)exp); // Peak Error ~ 0.00025

// Use https://www.wolframalpha.com/calculator ... alculator/ to reduce the number of multiplies by factoring the above polynomial:

// Math is reduced from 11 multiplies and 5 adds to 4 multiplies and 5 adds.

// For a fair comparison, standard "CSE" compiler optimization would give 9 multiplies and 5 adds.

{

float x;

int exp;

x = frexpf(arg, &exp);

return (-1.30637f*(x - 1.81165f)*(x - 0.999971f)*(x*(x - 1.13062f) + 1.48259f)) + (float)exp;

}

inline float exp2f (float arg)

// ldexp is a macro, supported in FP hardware, which basically takes a "binary exponentiation" of a floating point number.

// Use MS Excel to compute a trendline approximation (4th order polynomial) then manually tilt it so the ends have zero error (at 0.0 and 1.0).

// Manual tilt increases peak error but makes the output seamless and monotonic.

// y = 0.0068396f*x*x*x*x + 0.0531991f*x*x*x + 0.2394017f*x*x + 0.6930421f*x + 0.9999999f; // Error ~ 0.0009%

// Use https://www.wolframalpha.com/calculator ... alculator/ to reduce the number of multiplies by factoring the above polynomial:

// Math is reduced from 11 multiplies and 5 adds to 4 multiplies and 4 adds.

// For a fair comparison, standard "CSE" compiler optimization would give 9 multiplies and 5 adds.

{

float x,y,result;

int exp;

exp = (int)(arg)+(arg>0.0f);

x = arg-exp;

y = 0.0068396f*(x*(x + 1.76767f) + 13.726f)*(x*(x + 6.01044f) + 10.6519f);

return ldexpf(y,exp);

}

inline float logfq (float arg) // natural logarithm, scaled from log base 2

{

return LOG2_TO_LN * log2f (arg);

}

inline float log10fq (float arg) // logarithm base 10, scaled from log base 2

{

return LOG2_TO_LOG10 * log2f (arg);

}

inline float expfq (float arg) // e^x, scaled from exp2

{

return exp2f (EXP2_TO_EXP * arg);

}

inline float exp10fq (float arg) // 10^x, scaled from exp2

{

return exp2f (EXP2_TO_EXP10 * arg);

}

int main ()

{

float x, y, z, ygood, p=69, f=440, _l2;

int exp;

printf ("z, exp2(z), experr\n");

for(z=-2.002; z<=3.0; z+=0.002)

{

y=exp2f(z), ygood=pow(2.0,z);

printf ("%.6f, %.6f, %.6g\n",z,y,(y-ygood)/ygood);

}

printf ("x, log2(x), err, z, exp\n");

_l2=1.0/log(2.0);

for(x=0.24; x<=16.2; x*=1.05)

{

y=log2f(x), ygood=log(x)*_l2;

z = frexpf(x, &exp);

printf ("%.6f, %.6f, %.6g, %.6g, %d\n",x,y, y-ygood, z, exp);

}

return 0;

}

### Re: Expo Converters / DACs

i wonder what the limit of the companding DAC is. for 1c resolution, youd need ~12b, but you could probably get away with 10b, which is what youd get with 0.1% resistors anyways. but, you have 100ohm of on resistance in the switches. that can be calibrated out, but there is also 0.5ohm/C drift, so you might see 20 ohms of drift, which is pushing the limit down on the 10k level. there is the treade-off with Ron errors versus leakge errors up on the 1M. 1nA of leakage is 1mV, although the virtual ground summing juntion helps keep those leakage currents to a minimum (10pA at 25C).

i wonder if a variant using PWM to an 8ch digital DMUX would be more accurate. the Ron values are lower, the drift is lower, and all off channels are tied to ground, eliminating leakage. although at that rate, i wonder if its much different than a dual PWM.

i wonder if a variant using PWM to an 8ch digital DMUX would be more accurate. the Ron values are lower, the drift is lower, and all off channels are tied to ground, eliminating leakage. although at that rate, i wonder if its much different than a dual PWM.

openmusiclabs.com

### Re: Expo Converters / DACs

Quite the interesting conversation here.

+/- a cent or 2 is practically realisable for this sort of application (+/-10V swing full range, through zero drive) but its going to need some pretty sophisticated hardware to be stable and switching rate 200x or higher than the desired modulation bandwidth.

All ideas (plenty of them above) going to range switching offloads the precision to those switched components (try making a VCO with octave switching by changing the capacitors!) which is why the extreme linearity of PDM is so attractive. Also why exponential and log analog functions are still a thing in 2020.

This is very dependent on the specific hardware doing the switching (how its non-ideal) and also the modulation method. Its entirely possible to get the same resolution/precision all the way to the rails. Where it becomes even more complex is these things all have bandwidth tradeoffs, so is ideally designed to match the output filter.rich_de wrote: ↑Fri Apr 09, 2021 1:18 pm1. The zero value is the center (10101010... pattern), the low values are around it. As you noted, it becomes difficult to get decent resolution near the edges. Accuracy decreases towards highter values. I remember reading around 60% of the switching voltage is the reasonable maximum.

+/- a cent or 2 is practically realisable for this sort of application (+/-10V swing full range, through zero drive) but its going to need some pretty sophisticated hardware to be stable and switching rate 200x or higher than the desired modulation bandwidth.

All ideas (plenty of them above) going to range switching offloads the precision to those switched components (try making a VCO with octave switching by changing the capacitors!) which is why the extreme linearity of PDM is so attractive. Also why exponential and log analog functions are still a thing in 2020.

### Re: Expo Converters / DACs

i took a look at the resolution and possible error sources for dual PWM versus switched ranging, and i think the dual PWM is slightly better, and mungo brings up some good points along those lines. the resolution of a 10b DAC going to a 3b swiched resistor network is 18b. this is slightly different than a normal 18b, as the frequency resolution changes with range. but, at the low end, for a 20Hz bottom frequency, you get 1.5c resolution (0.02Hz). this is the same as you would get with a normal 18b converter down at the low end, but then you would continue to get that same Hz resolution as compared to the switched range version which gives you the same cent resolution as you go up in range. so, all things being equal, you get finer control with a straight 18b converter as compared to a switched range version.

with both dual PWM and switched range you have the issue of resistor size to contend with. too large and leakage errors are a problem, too small and stray resistance issues are a problem, but with the dual PWM you only have to match 2 resistors, not 8, so calibration is a lot easier. and, if you want, you could go to 20b with dual PWM quite easily, although im not sure you would ever see more than 18b accuracy. perhaps with a daul 10b external DAC you could get near there.

i might try setting up my codec-vco again and run at a lower clock speed and smaller part of the range and see if that helps any. one nice thing about all of these setups is that, as long as the DAC is linear, the errors will most likely be offset issues, so you can easily recalibrate and add an offset back in to compensate.

with both dual PWM and switched range you have the issue of resistor size to contend with. too large and leakage errors are a problem, too small and stray resistance issues are a problem, but with the dual PWM you only have to match 2 resistors, not 8, so calibration is a lot easier. and, if you want, you could go to 20b with dual PWM quite easily, although im not sure you would ever see more than 18b accuracy. perhaps with a daul 10b external DAC you could get near there.

i might try setting up my codec-vco again and run at a lower clock speed and smaller part of the range and see if that helps any. one nice thing about all of these setups is that, as long as the DAC is linear, the errors will most likely be offset issues, so you can easily recalibrate and add an offset back in to compensate.

openmusiclabs.com

### Re: Expo Converters / DACs

If you start considering precision ways to deliver known quanta, it ends up back with charge pumps and Jim Williams' AN14. Then the VCO is just a fancy filter smoothing out the "DACs" output pulses.

### Re: Expo Converters / DACs

the feedback charge balance oscillators pretty much are just sigma delta converters, especially if you consider the syncrhonous ones. so this sort of flips that around a bit, and does the sigma delta in digital.

ive been thinking a bit more about doing sigma delta on a microcontroller, and i think i have myself convinced that the basic, 1b sigma delta is the same as an NCO. youre pretty much adding the input value plus a feedback value on every count. that feedback value is either the min or max value of the range, and this all goes to an accumulator. if that accumulator were only the size of min/max, then the min/max additions would just roll over, and youd only be summing the input value into the accumulator. ive gone through a few examples, and they all produce the same pulse stream regardless of nco or basic 1b sigma delta algorithm. considering an nco is way, way fewer clock cycles, that seems the way to go (0 clock cycles on the PICs that have a hardware version).

the thing im still hung up on, though, is the frequency response. if i want 20b resolution, it seems like there is no way to get around that their need to be enough slots in the pulse sequence to accomodate that level of charge manipulation, so if you have a 10MHz clock, you would still have max frequency response of 10Hz. i feel like the case for AC might be different, but for DC wouldnt you need the 1,000,000 time slots to get 20b? or is it just the case that you can set your filter to whatever you want, and you dont get the full 20b until the 10Hz settling time, but can get faster signals at lower resolution in the meantime? i seem to recall that being the case for the audio rate sigma delta converters ive made in the past. i got really good SNR at low frequencies, and at higher frequencies i still got signal but it got noisier. i suppose thats what the higher order sigma deltas help with - pushing all that noise out of the frequencies of interest.

ive been thinking a bit more about doing sigma delta on a microcontroller, and i think i have myself convinced that the basic, 1b sigma delta is the same as an NCO. youre pretty much adding the input value plus a feedback value on every count. that feedback value is either the min or max value of the range, and this all goes to an accumulator. if that accumulator were only the size of min/max, then the min/max additions would just roll over, and youd only be summing the input value into the accumulator. ive gone through a few examples, and they all produce the same pulse stream regardless of nco or basic 1b sigma delta algorithm. considering an nco is way, way fewer clock cycles, that seems the way to go (0 clock cycles on the PICs that have a hardware version).

the thing im still hung up on, though, is the frequency response. if i want 20b resolution, it seems like there is no way to get around that their need to be enough slots in the pulse sequence to accomodate that level of charge manipulation, so if you have a 10MHz clock, you would still have max frequency response of 10Hz. i feel like the case for AC might be different, but for DC wouldnt you need the 1,000,000 time slots to get 20b? or is it just the case that you can set your filter to whatever you want, and you dont get the full 20b until the 10Hz settling time, but can get faster signals at lower resolution in the meantime? i seem to recall that being the case for the audio rate sigma delta converters ive made in the past. i got really good SNR at low frequencies, and at higher frequencies i still got signal but it got noisier. i suppose thats what the higher order sigma deltas help with - pushing all that noise out of the frequencies of interest.

openmusiclabs.com

### Re: Expo Converters / DACs

Isn't the assumption that you need a 1,000,000 bit long sequence based on just averaging the number of ones in the sequence to get 20 bit resolution? I'm not convinced this is correct and think it also depends on the sequence of ones. For instance, if we integrate the bits +1, +1, -1, -1 we get the output sequence +1, +2, +1, 0 with an average of +1 while the sequence +1, -1, +1, -1 generates the output +1, 0, +1, 0 with an average of +0.5 even if it has the same number of +1 as the previous case.

A sigma-delta modulator uses both oversampling and noiseshaping to achieve a high dynamic range. Every time the oversampling ratio is doubled, the output noise is spread over twice the bandwidth so the noise density is reduced by 3dB. Thanks to the high gain in the integrator at low frequencies, the noise is pushed up to higher frequencies above the baseband where the gain is lower. The high frequency noise is then filtered out when the sampling frequency is reduced down to the final frequency. For a first order sigma-delta converter, the slope is +6dB/octave and +12dB/octave for a second order system. So we gain a total of +9dB (1.5 bit) SNR for a first order and +15dB (2.5 bit) for a second order modulator when doubling the oversampling ratio. So a second order modulator would theoretically(!) only need a 256x oversampling ratio for 20 bits. In practice, many S-D audio DACs only reach 17-18 bits SNR with a 256x (or higher) ratio.

A sigma-delta modulator uses both oversampling and noiseshaping to achieve a high dynamic range. Every time the oversampling ratio is doubled, the output noise is spread over twice the bandwidth so the noise density is reduced by 3dB. Thanks to the high gain in the integrator at low frequencies, the noise is pushed up to higher frequencies above the baseband where the gain is lower. The high frequency noise is then filtered out when the sampling frequency is reduced down to the final frequency. For a first order sigma-delta converter, the slope is +6dB/octave and +12dB/octave for a second order system. So we gain a total of +9dB (1.5 bit) SNR for a first order and +15dB (2.5 bit) for a second order modulator when doubling the oversampling ratio. So a second order modulator would theoretically(!) only need a 256x oversampling ratio for 20 bits. In practice, many S-D audio DACs only reach 17-18 bits SNR with a 256x (or higher) ratio.

### Re: Expo Converters / DACs

... then you'll need a clock source and reference voltage and switching system all with sub PPM drift/variation. Thats much harder than the modulation.