How to modify zeros and poles in a delta-sigma modulator loop?

In this specific case, I am modeling a delta-sigma analog-to-digital converter with a basic loop in which the output $$V$$ is fed back with unity gain to be subtracted from the previously sampled input $$U$$ (discrete time) and this difference is fed to an integrator modeled with the transfer function:

$$G(z) = \frac{z^{-1}}{1- z^{-1}}$$

Quantization noise is added in form of error $$E$$ to the output of the integrator, giving the output $$V$$. It follows:

$$V(z)=\frac{G(z)}{1+G(z)}U(z)+\frac{1}{1+G(z)}E(z)$$

The complete model, however, should be a third-order system in which the output $$V$$ is fed back with unity gain twice more so that it is once subtracted from the sampled input in the outer loop, this difference is then integrated and fed to the next loop, in which the fed-back output is subtracted again. This new delta enters the second integrator and the same process repeats once more in the inner loop, where the quantization error is added as described in the first lines above. In total there will be 2 identical outer loops and a third inner loop where the quantization is added. In total there will be 3 integrators with transfer function $$G$$.

the minus sign is missing in the second picture for all three summation nodes. it was a mistake. the feedbacks should be indeed negative

Now I'm interested in the Noise Transfer Function: NTF = $$V / E$$. According to my computations:

NTF with gain unity in all three feedback paths (alpha, beta and gamma are 1) should be equal to:

$$\text{NTF}(z)=\frac{V(z)}{E(z)}=\frac{1}{G(z)^3+3G(z)^2+3G(z)+1}$$

It follows:

$$\text{NTF}(z)=\frac{(z-1)^3}{(z-1)^3+3(z-1)^2+3(z-1)+1}$$

From here, I would like to do two things:

• Replace the poles $$z1 = 1$$, $$z2 = 1$$ and $$z3 = 1$$ of the NTF with different values. In order to do so, I simply introduced a gain factor in the feedback path of each of the three loops (alpha, beta and gamma as above). This will add three coefficients in the denominator that I can play with.

However:

• I would also like to replace two of the zeros of the NTF, which are now all equal to 1, with a pair of complex conjugate zeros. This should provide "lower noise around the zeros, at the expense of a less effective shaping at $$z = 1$$, thus increasing the usable frequency range".

If I understand correctly, the numerator $$N(z)$$ of the NTF should be something like this in the end:

$$N(z)=(z-1)(z-e^{jω})(z-e^{-jω})$$

My question is: how do I achieve this? What should I add in the model to shift the zeros slightly away from DC?

Just for information: once I have also obtained a pair of complex conjugate zeros, I should solve an optimization problem to find the optimal position of poles and zeros in the NTF for a determinate quantization noise power. So my humble guess is that ideally I should add something as simple as a gain in the model for the zeros, too, so that can adjust the numerator of the NTF, too, and solve for the optimal zeros within certain boundaries.

• This is a question of substance. – robert bristow-johnson Oct 9 '20 at 2:11
• well, before i really jump into this, since you're saying that this is sigma-delta (or "delta-sigma"), does that mean that the output of the quantizer is binary? That is $$v[n] = \pm 1$$ in some given units? If that is the case, you have an issue about the "gain of the quantizer" or the "gain of the comparator" and that gain is not necessarily equal to $1$. And there is necessarily a delay of one sample upon feedback. There must be a $z^{-1}$ in the feedback path. – robert bristow-johnson Oct 9 '20 at 2:17
• @robertbristow-johnson Thank you for your interest in the question. In our exercise the assumption is exactly that of a 1-bit quantizer, however we're not simulating any conversion to and from binary, the quantizer is represented by an approximating function with a specific step size. I hope that makes sense. The delay you're taking about is included in the filter transfer function G, I think. – Andrea Toffanin Oct 9 '20 at 13:35
• Well, Andrea, your professor might be missing something. There is a paper by John Paulos from 1986 where this gain of the comparator is discussed. I have some math for it. I also have a MATLAB file for demonstration. Do you want it? – robert bristow-johnson Oct 9 '20 at 14:43

i dunno, i might have posted this before. but here is a 2nd-order sigma-delta quantizer that operates not as an oversampled rate. so you can hear the quantization noise, but you can also hear the music beneath it. and the output is binary: $$y[n] = \pm A$$.

your professor is mistaken if he/she thinks they can model this without the $$z^{-1}$$ in the feedback path nor leave out the gain of the comparator.

%
%
%
%
%
%
%   simulated 1 bit sigma-delta converter:
%
%
%            x(n)-y(n-1)    w(n)                v(n)                 ( mean(y^2) = A^2 )
%
%   x ---->(+)--->[1/(z-1)]--->(+)--->[1/(z-1)]--->[Quantizer]----.---> y = +/- A = quantized value
%           ^                   ^                                 |
%           |                   |                                 |
%           |                   '----[-fbg]<----.                 |
%           |                                   |                 |
%           '------[-1]<------------------------'------[1/z]<-----'
%
%
%
%
%
%   "linearized" model:
%                                                          .---- q = quantization noise  ( mean(q) = 0 )
%                                                          |
%                                                          |
%            x - y/z        w                   v          |         ( mean(y^2) = G^2*mean(v^2) + mean(q^2) )
%                                                          v
%   x ---->(+)--->[1/(z-1)]--->(+)--->[1/(z-1)]--->[G]--->(+)-----.---> y = G*v + q
%           ^                   ^                                 |
%           |                   |                                 |
%           |                   '----[-fbg]<----.                 |
%           |                                   |                 |
%           '------[-1]<------------------------'------[1/z]<-----'
%
%
%
%
%
%
%
%
%           W = 1/(z-1)*(X - Y/z)
%
%
%           V = 1/(z-1)*(W - fbg*Y/z)
%
%             = (X - Y/z - fbg*Y*(z-1)/z)/(z-1)^2
%
%             = (X*z - Y*(1+fbg*(z-1))) / (z*(z-1)^2)
%
%
%           Y = G*V + Q = G*(X*z - Y*(1+fbg*(z-1)))/(z*(z-1)^2) + Q
%
%             = G*X/(z-1)^2 - G*Y*(1+fbg*(z-1))/(z*(z-1)^2) + Q
%
%
%           Y + G*Y*(1-fbg + fbg*z)/(z*(z-1)^2) = G*X/(z-1)^2 + Q
%
%
%           Y = (G*X/(z-1)^2 + Q)/(1 + G*(1-fbg + fbg*z)/(z*(z-1)^2))
%
%             = (G*X/(z-1)^2 + Q)*(z*(z-1)^2)/((z*(z-1)^2) + G*(1-fbg + fbg*z))
%
%             = z*(G*X + Q*(z-1)^2)/(z^3 - 2*z^2 + (G*fbg+1)*z + G*(1-fbg))
%
%             = z*(G*X + Q*(z-1)^2)/(z*(z-1)^2 + G*fbg*z + G*(1-fbga))
%
%
%    as z -> 1  (DC)
%
%           Y  ->  z*X/(fbg*z + (1-fbg)) =  X/(fbg + (1-fbg)/z)  -->  X
%
%

if ~exist('mean_vv', 'var')
linearized_model = 0                % run this with 0 the first time to define G and mean(q^2)
end

if ~exist('A', 'var')
A = 1.0                             % comparator output magnitude
end

if ~exist('fbg', 'var')
fbg = 2.0                           % feedback gain to internal integrator
end

%
%   if there is an input soundfile specified, use it.  else, create a sin wave
%

if exist('inputFile', 'var')

fileSize = length(inputBuffer);

numSamples = 2.^(ceil(log2(fileSize(1))));  % round up to nearest power of 2

x = zeros(numSamples, 1);                   % zero pad if necessary

x(1:fileSize) = inputBuffer(:,1);           % if multi-channel, use left channel only

clear inputBuffer;                          % free this memory
clear fileSize;

t = linspace(0.0, (numSamples-1)/Fs, numSamples);   % time

else

if ~exist('numSamples', 'var')
numSamples = 65536                              % number of samples in simulation
end

if ~exist('Fs', 'var')
Fs = 44100                                      % (oversampled) sample rate
end

if ~exist('f0', 'var')
f0 = 261.6255653                                % input freq (middle C)
end

if ~exist('Amplitude', 'var')
Amplitude = 0.25                                % input amplitude
end

t = linspace(0.0, (numSamples-1)/Fs, numSamples);   % time
x = Amplitude*cos(2*pi*f0*t);                       % the input

end

sound(x, Fs);                                   % listen to input sound
pause;

y = zeros(1, numSamples);                       % the output (created and initialized for speed later)

if linearized_model
% artificial quantization noise for linearized model
% mean(q) = 0, var(q) = mean(q^2) = mean(y^2) - G^2*mean(v^2)
% does not have to be uniform or triangle p.d.f.
q = sqrt(6.0*(A^2 - G^2*mean_vv))*( rand(1, numSamples) - rand(1, numSamples) );
else
q = zeros(1, numSamples);
end

sum_yv = 0.0;
sum_vv = 0.0;

w = 0;
v = 0;
for n = 1:numSamples

if linearized_model

y(n) = G*v + q(n);                      % here the comparator is modelled as a little gain with additive noise

else

if (v >= 0)                             % the comparator
y(n) = +A;
else
y(n) = -A;
end

q(n) = y(n) - (sum_vv+1e-20)/(sum_yv+1e-20)*v;

end

sum_yv = sum_yv + y(n)*v;                   % collect some statistics on v
sum_vv = sum_vv +    v*v;

v = v + w  - fbg*y(n);                      % second integrator
w = w + x(n) - y(n);                        % first integrator

end

if ~linearized_model                            % don't recalculate this if using the linearized model
mean_yv = sum_yv/numSamples;
mean_vv = sum_vv/numSamples;
G = mean_yv/mean_vv;                        % the apparent comparator gain (assuming stationary input)
end

%
%
%
%     Y = ((G*z)*X + (z^3 - 2*z^2 + z)*Q) / (z^3 - 2*z^2 + (G*a+1)*z + G*(1-a))
%
%
%
Hx = freqz([0  0 G 0], [1 -2 G*fbg+1 G*(1-fbg)], numSamples/2);
Hq = freqz([1 -2 1 0], [1 -2 G*fbg+1 G*(1-fbg)], numSamples/2);

plot(t, y, 'b');
sound(y, Fs);                                   % this could sound pretty bad
pause;

Y = fft(fftshift(y .* kaiser(numSamples, 5.0)'));
Q = fft(fftshift(q .* kaiser(numSamples, 5.0)'));

f = linspace(0.0, (numSamples/2-1)/numSamples*Fs, numSamples/2);

plot(f, 20*log10(abs(Y(1:numSamples/2)) + 1e-10), 'b');
hold on;
plot(f, 20*log10(abs(Q(1:numSamples/2)) + 1e-10), 'r');
plot(f, 20*log10(abs(Hq) + 1e-10), 'g');
axis([0 Fs/2 -50 100]);
hold off;
pause;

semilogx(f(2:numSamples/2), 20*log10(abs(Y(2:numSamples/2)) + 1e-10), 'b');
hold on;
semilogx(f(2:numSamples/2), 20*log10(abs(Q(2:numSamples/2)) + 1e-10), 'r');
semilogx(f(2:numSamples/2), 20*log10(abs(Hq(2:numSamples/2)) + 1e-10), 'g');
axis([Fs/numSamples Fs/2 -50 100]);
hold off;
pause;

semilogx(f(2:numSamples/2), 20*log10(abs(Y(2:numSamples/2)) + 1e-10), 'b');
hold on;
semilogx(f(2:numSamples/2), 20*log10(abs(Hq(2:numSamples/2)) + 1e-10), 'r');
semilogx(f(2:numSamples/2), 20*log10(abs(Hx(2:numSamples/2)) + 1e-10), 'g');
axis([Fs/numSamples Fs/2 -50 110]);
hold off;