1ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#!/bin/sh
2ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
3ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# intgamma.sh
4ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
5ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# Last changed in libpng 1.6.0 [February 14, 2013]
6ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
7ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# COPYRIGHT: Written by John Cunningham Bowler, 2013.
8ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# To the extent possible under law, the author has waived all copyright and
9ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# related or neighboring rights to this work.  This work is published from:
10ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# United States.
11ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
12ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# Shell script to generate png.c 8-bit and 16-bit log tables (see the code in
13ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# png.c for details).
14ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
15ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# This script uses the "bc" arbitrary precision calculator to calculate 32-bit
16ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# fixed point values of logarithms appropriate to finding the log of an 8-bit
17ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# (0..255) value and a similar table for the exponent calculation.
18ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
19ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# "bc" must be on the path when the script is executed, and the math library
20ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# (-lm) must be available
21ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
22ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# function to print out a list of numbers as integers; the function truncates
23ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# the integers which must be one-per-line
24ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikfunction print(){
25ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   awk 'BEGIN{
26ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik      str = ""
27ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   }
28ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   {
29ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik      sub("\\.[0-9]*$", "")
30ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik      if ($0 == "")
31ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik         $0 = "0"
32ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik
33ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik      if (str == "")
34ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik         t = "   " $0 "U"
35ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik      else
36ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik         t = str ", " $0 "U"
37ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik
38ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik      if (length(t) >= 80) {
39ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik         print str ","
40ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik         str = "   " $0 "U"
41ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik      } else
42ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik         str = t
43ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   }
44ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   END{
45ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik      print str
46ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   }'
47ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik}
48ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
49ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# The logarithm table.
50ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikcat <<END
51ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik/* 8-bit log table: png_8bit_l2[128]
52ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * This is a table of -log(value/255)/log(2) for 'value' in the range 128 to
53ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * 255, so it's the base 2 logarithm of a normalized 8-bit floating point
54ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * mantissa.  The numbers are 32-bit fractions.
55ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik */
56ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikstatic const png_uint_32
57ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikpng_8bit_l2[128] =
58ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik{
59ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris CraikEND
60ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
61ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikbc -lqws <<END | print
62ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikf=65536*65536/l(2)
63ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikfor (i=128;i<256;++i) { .5 - l(i/255)*f; }
64ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris CraikEND
65ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikecho '};'
66ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikecho
67ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
68ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# The exponent table.
69ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikcat <<END
70ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik/* The 'exp()' case must invert the above, taking a 20-bit fixed point
71ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * logarithmic value and returning a 16 or 8-bit number as appropriate.  In
72ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * each case only the low 16 bits are relevant - the fraction - since the
73ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * integer bits (the top 4) simply determine a shift.
74ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik *
75ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * The worst case is the 16-bit distinction between 65535 and 65534; this
76ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * requires perhaps spurious accuracy in the decoding of the logarithm to
77ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * distinguish log2(65535/65534.5) - 10^-5 or 17 bits.  There is little chance
78ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * of getting this accuracy in practice.
79ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik *
80ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * To deal with this the following exp() function works out the exponent of the
81ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * frational part of the logarithm by using an accurate 32-bit value from the
82ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik * top four fractional bits then multiplying in the remaining bits.
83ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik */
84ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikstatic const png_uint_32
85ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikpng_32bit_exp[16] =
86ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik{
87ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris CraikEND
88ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
89ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikbc -lqws <<END | print
90ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikf=l(2)/16
91ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikfor (i=0;i<16;++i) {
92ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   x = .5 + e(-i*f)*2^32;
93ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   if (x >= 2^32) x = 2^32-1;
94ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   x;
95ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik}
96ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris CraikEND
97ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikecho '};'
98ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikecho
99ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#
100ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik# And the table of adjustment values.
101ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikcat <<END
102ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik/* Adjustment table; provided to explain the numbers in the code below. */
103ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik#if 0
104ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris CraikEND
105ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikbc -lqws <<END | awk '{ printf "%5d %s\n", 12-NR, $0 }'
106ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikfor (i=11;i>=0;--i){
107ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik   (1 - e(-(2^i)/65536*l(2))) * 2^(32-i)
108ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craik}
109ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris CraikEND
110ca2bf81b02c99afa2e76b3b2c6eb232c239221e0Chris Craikecho '#endif'
111