sensorium / Mozzi

sound synthesis library for Arduino
https://sensorium.github.io/Mozzi/
GNU Lesser General Public License v2.1
1.05k stars 184 forks source link

AVR PWM range is not actually 0-488 ("8.5 bit"), but effectively 0-400 #223

Closed eclab closed 5 months ago

eclab commented 6 months ago

The title is just an estimate, don't take it as precise.

I have been doing experiments controlling pitch CV with Mozzi's PWM on AE Modular "GRAINS" module, which is essentially a Nano. I've found:

It is possible that these results are due to the output circuitry on the GRAINS, but I don't think so. What it means is that the more or less linear portion of the AVR PWM appears to about 0-400, that is, -244 to +156.

The table below was developed to provide AVR PWM values per semitone. As you can see, there are only 42 of them, not 60.


{  
   0,   13,  23,  32,  41,  50,  59,  68,  78,  87,  96,  106,  // by 9.3, except first which jumps by 13
   116, 125, 135, 144, 154, 163, 173, 182, 192, 202, 212, 222,  // by 9.666
   232, 242, 251, 261, 271, 281, 291, 300, 310, 320, 330, 339,  // by 9.75
   349, 358, 368, 377, 386, 397     // by 9.25, except last which jumps by 11.  One more pitch is exists but is highly nonlinear    
};```
tfry-git commented 6 months ago

I'll second-check this, but my pocket scope died the other day, and it's hard to arrive at a definite diagnosis, without that.

I have to admit, though, that for the time being, I'm inclined to attribute your findings, and esp. any non-linearity to the rest of the circuitry (output, input, ADC conversion). On the MCU end, this is just counting digital clock cycles, after all.

eclab commented 6 months ago

It is possible! I'm unable to determine if it's the GRAINS circuitry or Mozzi proper. :-( I have also posted this bug in the GRAINS groups.

What I'm seeing is this: There's a slight sub-linearity from 0 to about 13, then approximately linear from 13 to about 400, rising about 9.5 or so per semitone if we're v/oct. Near 400 it's slightly sub-linear, then beyond 400 it goes very sublinear to the point where the upper values have little effect.

Sean

On Jan 7, 2024, at 8:54 PM, Thomas Friedrichsmeier @.***> wrote:

I'll second-check this, but my pocket scope died the other day, and it's hard to arrive at a definite diagnosis, without that.

I have to admit, though, that for the time being, I'm inclined to attribute your findings, and esp. any non-linearity to the rest of the circuitry (output, input, ADC conversion). On the MCU end, this is just counting digital clock cycles, after all.

— Reply to this email directly, view it on GitHub, or unsubscribe. You are receiving this because you authored the thread.

tomcombriat commented 6 months ago

I can try to test here with my scope, it is an analog one but that's a starter.

To be sure we are on the same page (I was initially confused with the mention of "frequency" drop), all of this boils down to: Is the PWM linear or not in the full range? Of course, to input into a CV, the PWM needs to be filtered (as, as a baseline it is only 0 and 5V in different time mixture). Do you have the parameters of this filter?

Edit: just discovered that Mozzi is actually mentioned on the website selling the module (tangible waves), fun!

eclab commented 6 months ago

On Jan 7, 2024, at 11:56 PM, Thomas Combriat @.***> wrote:

To be sure we are on the same page (I was initially confused with the mention of "frequency" drop), all of this boils down to: Is the PWM linear or not in the full range? Of course, to input into a CV, the PWM needs to be filtered (as, as a baseline it is only 0 and 5V in different time mixture). Do you have the parameters of this filter?

There are two issues: they may be related. In issue #219, I am using Mozzi to generate an audio-rate wave in the range -128 to 127. The wave is generated by taking a saw, square, or tri wave and pushing it through a filter. But if I change the gain on the wave so it is outside this range, it gets louder as expected, but the apparent frequency of the wave drops.

In issue #223, I am using Mozzi to generate a CV signal. I'm simply setting the value myself and, for values -244 through about 156 I'm getting pretty linearly increasing and reasonably stable output. Notionally this value should be -244 to +244. But beyond about 156 or so the actual CV value starts changing sublinearly with increases in PWM.

These may be related, or they may not.

In both cases I am using an AE Modular GRAINS with filtered PWM. It's basically a Nano, a clone of the original Eurorack GRAINS with a switch to use Mozzi's pinout instead. I do not have the specs on the filter being used, nor the op-amp but it is has been sufficient to produce 8-bit audio output with reasonable quality. Again, this may entirely be due to the GRAINS: or it may not. :-(

tomcombriat commented 6 months ago

Okay, these issues are a bit mixed, both of them about the two problems.

For #219, we can continue the discussion there but so far there is not enough information to reproduce this frequency drop:

tfry-git commented 5 months ago

So I got myself a new digital (cheap pocket) scope, and gave the matter a test by generating a slow triangle waveform between -244 and 243 on a Nano clone. Looking at the raw PWM, the duty cycle shifts smoothly between both ends. It does appear that on both ends the output pin will change state for one clock cycle, suggesting that a tiny micro-optimization might still be possible (ideally, at -244 and 243, the pin would remain permanently low/high), but there is no sign of non-linearity.

I then attached a simple RC-filter and obtained a very linear swing with no signs of flattening at either end.

Closing this report. If you can reproduce it in a setup without additional hardware stages involved, feel free to reopen. Also, we'll be happy to assist in your bug-hunt (here or in the forum), but you will have to answer @tomcombriat 's questions on the details.