Skip to content

Instantly share code, notes, and snippets.

@luctrudeau
Created June 16, 2016 13:30
Show Gist options
  • Save luctrudeau/66d32cc3ed979e2ab4cc69efe53de75e to your computer and use it in GitHub Desktop.
Save luctrudeau/66d32cc3ed979e2ab4cc69efe53de75e to your computer and use it in GitHub Desktop.
Daala Log2 Int Approx
clc; clear; clf;
% Base-2 logarithm approximation (log2(x)). (Q14 input, Q10 output)
qI = 14;
q14_one = bitshift(1,qI);
% Range from 0 to 1
x = bitshift(1,qI-1):q14_one-1;
% Output
qO = 13;
qO_one = bitshift(1,qO);
% Ground truth
y = qO_one * log2(x ./ q14_one);
d = 4;
[fit,~,mu] = polyfit(x,y,d);
y = int32(y);
y2 = polyval(fit, x, [], mu);
diff = int32(y) - int32(y2);
fprintf('Matlab Max Abs Diff = %f RSAD = %f\n', max(diff), sum((diff ./ y).^2));
plot(x,y);
hold all
% Increase Q (*4 is Q+2)
q15_x = int32(x*4);
% - 1.5
q15_one = bitshift(1,15);
q15_x = q15_x - q15_one-q14_one; %Q4 is half Q15
% Coefficients
shift = bitshift(1,13 - qO);
C = int32([-6801 + shift, 15746, -5217, 2545, -1401]);
%y1 = -0.41445418 + x1.*(0.95909232 + x1.*(-0.33951290 + x1.*0.16541097));
y1 = mul16_16_q15(q15_x,C(5));
y1 = y1 + C(4);
y1 = mul16_16_q15(q15_x,y1);
y1 = y1 + C(3);
y1 = mul16_16_q15(q15_x,y1);
y1 = y1 + C(2);
y1 = mul16_16_q15(q15_x,y1);
y1 = y1 + C(1);
y1 = bitshift(y1, qO - qI);
plot(x, y1)
diff = int32(y) - int32(y1);
fprintf('Float Max Abs Diff = %f RSAD = %f\n', max(diff), sum((diff ./ y).^2));
legend({'Log2', 'float celt\_log2'})
%assert(max(abs(int32(y) - y1)) == 1);
hold off
hist(double(diff))
function [ result ] = mul16_16_q15( a, b )
result = bitshift(a .* b, -15);
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment