intgamma.sh 2.9 KB

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