gfx/qcms/qcmsint.h

Tue, 06 Jan 2015 21:39:09 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Tue, 06 Jan 2015 21:39:09 +0100
branch
TOR_BUG_9701
changeset 8
97036ab72558
permissions
-rw-r--r--

Conditionally force memory storage according to privacy.thirdparty.isolate;
This solves Tor bug #9701, complying with disk avoidance documented in
https://www.torproject.org/projects/torbrowser/design/#disk-avoidance.

michael@0 1 /* vim: set ts=8 sw=8 noexpandtab: */
michael@0 2 #include "qcms.h"
michael@0 3 #include "qcmstypes.h"
michael@0 4
michael@0 5 /* used as a lookup table for the output transformation.
michael@0 6 * we refcount them so we only need to have one around per output
michael@0 7 * profile, instead of duplicating them per transform */
michael@0 8 struct precache_output
michael@0 9 {
michael@0 10 int ref_count;
michael@0 11 /* We previously used a count of 65536 here but that seems like more
michael@0 12 * precision than we actually need. By reducing the size we can
michael@0 13 * improve startup performance and reduce memory usage. ColorSync on
michael@0 14 * 10.5 uses 4097 which is perhaps because they use a fixed point
michael@0 15 * representation where 1. is represented by 0x1000. */
michael@0 16 #define PRECACHE_OUTPUT_SIZE 8192
michael@0 17 #define PRECACHE_OUTPUT_MAX (PRECACHE_OUTPUT_SIZE-1)
michael@0 18 uint8_t data[PRECACHE_OUTPUT_SIZE];
michael@0 19 };
michael@0 20
michael@0 21 #ifdef _MSC_VER
michael@0 22 #define ALIGN __declspec(align(16))
michael@0 23 #else
michael@0 24 #define ALIGN __attribute__(( aligned (16) ))
michael@0 25 #endif
michael@0 26
michael@0 27 struct _qcms_transform {
michael@0 28 float ALIGN matrix[3][4];
michael@0 29 float *input_gamma_table_r;
michael@0 30 float *input_gamma_table_g;
michael@0 31 float *input_gamma_table_b;
michael@0 32
michael@0 33 float *input_clut_table_r;
michael@0 34 float *input_clut_table_g;
michael@0 35 float *input_clut_table_b;
michael@0 36 uint16_t input_clut_table_length;
michael@0 37 float *r_clut;
michael@0 38 float *g_clut;
michael@0 39 float *b_clut;
michael@0 40 uint16_t grid_size;
michael@0 41 float *output_clut_table_r;
michael@0 42 float *output_clut_table_g;
michael@0 43 float *output_clut_table_b;
michael@0 44 uint16_t output_clut_table_length;
michael@0 45
michael@0 46 float *input_gamma_table_gray;
michael@0 47
michael@0 48 float out_gamma_r;
michael@0 49 float out_gamma_g;
michael@0 50 float out_gamma_b;
michael@0 51
michael@0 52 float out_gamma_gray;
michael@0 53
michael@0 54 uint16_t *output_gamma_lut_r;
michael@0 55 uint16_t *output_gamma_lut_g;
michael@0 56 uint16_t *output_gamma_lut_b;
michael@0 57
michael@0 58 uint16_t *output_gamma_lut_gray;
michael@0 59
michael@0 60 size_t output_gamma_lut_r_length;
michael@0 61 size_t output_gamma_lut_g_length;
michael@0 62 size_t output_gamma_lut_b_length;
michael@0 63
michael@0 64 size_t output_gamma_lut_gray_length;
michael@0 65
michael@0 66 struct precache_output *output_table_r;
michael@0 67 struct precache_output *output_table_g;
michael@0 68 struct precache_output *output_table_b;
michael@0 69
michael@0 70 void (*transform_fn)(struct _qcms_transform *transform, unsigned char *src, unsigned char *dest, size_t length);
michael@0 71 };
michael@0 72
michael@0 73 struct matrix {
michael@0 74 float m[3][3];
michael@0 75 bool invalid;
michael@0 76 };
michael@0 77
michael@0 78 struct qcms_modular_transform;
michael@0 79
michael@0 80 typedef void (*transform_module_fn_t)(struct qcms_modular_transform *transform, float *src, float *dest, size_t length);
michael@0 81
michael@0 82 struct qcms_modular_transform {
michael@0 83 struct matrix matrix;
michael@0 84 float tx, ty, tz;
michael@0 85
michael@0 86 float *input_clut_table_r;
michael@0 87 float *input_clut_table_g;
michael@0 88 float *input_clut_table_b;
michael@0 89 uint16_t input_clut_table_length;
michael@0 90 float *r_clut;
michael@0 91 float *g_clut;
michael@0 92 float *b_clut;
michael@0 93 uint16_t grid_size;
michael@0 94 float *output_clut_table_r;
michael@0 95 float *output_clut_table_g;
michael@0 96 float *output_clut_table_b;
michael@0 97 uint16_t output_clut_table_length;
michael@0 98
michael@0 99 uint16_t *output_gamma_lut_r;
michael@0 100 uint16_t *output_gamma_lut_g;
michael@0 101 uint16_t *output_gamma_lut_b;
michael@0 102
michael@0 103 size_t output_gamma_lut_r_length;
michael@0 104 size_t output_gamma_lut_g_length;
michael@0 105 size_t output_gamma_lut_b_length;
michael@0 106
michael@0 107 transform_module_fn_t transform_module_fn;
michael@0 108 struct qcms_modular_transform *next_transform;
michael@0 109 };
michael@0 110
michael@0 111 typedef int32_t s15Fixed16Number;
michael@0 112 typedef uint16_t uInt16Number;
michael@0 113 typedef uint8_t uInt8Number;
michael@0 114
michael@0 115 struct XYZNumber {
michael@0 116 s15Fixed16Number X;
michael@0 117 s15Fixed16Number Y;
michael@0 118 s15Fixed16Number Z;
michael@0 119 };
michael@0 120
michael@0 121 struct curveType {
michael@0 122 uint32_t type;
michael@0 123 uint32_t count;
michael@0 124 float parameter[7];
michael@0 125 uInt16Number data[];
michael@0 126 };
michael@0 127
michael@0 128 struct lutmABType {
michael@0 129 uint8_t num_in_channels;
michael@0 130 uint8_t num_out_channels;
michael@0 131 // 16 is the upperbound, actual is 0..num_in_channels.
michael@0 132 uint8_t num_grid_points[16];
michael@0 133
michael@0 134 s15Fixed16Number e00;
michael@0 135 s15Fixed16Number e01;
michael@0 136 s15Fixed16Number e02;
michael@0 137 s15Fixed16Number e03;
michael@0 138 s15Fixed16Number e10;
michael@0 139 s15Fixed16Number e11;
michael@0 140 s15Fixed16Number e12;
michael@0 141 s15Fixed16Number e13;
michael@0 142 s15Fixed16Number e20;
michael@0 143 s15Fixed16Number e21;
michael@0 144 s15Fixed16Number e22;
michael@0 145 s15Fixed16Number e23;
michael@0 146
michael@0 147 // reversed elements (for mBA)
michael@0 148 bool reversed;
michael@0 149
michael@0 150 float *clut_table;
michael@0 151 struct curveType *a_curves[10];
michael@0 152 struct curveType *b_curves[10];
michael@0 153 struct curveType *m_curves[10];
michael@0 154 float clut_table_data[];
michael@0 155 };
michael@0 156
michael@0 157 /* should lut8Type and lut16Type be different types? */
michael@0 158 struct lutType { // used by lut8Type/lut16Type (mft2) only
michael@0 159 uint8_t num_input_channels;
michael@0 160 uint8_t num_output_channels;
michael@0 161 uint8_t num_clut_grid_points;
michael@0 162
michael@0 163 s15Fixed16Number e00;
michael@0 164 s15Fixed16Number e01;
michael@0 165 s15Fixed16Number e02;
michael@0 166 s15Fixed16Number e10;
michael@0 167 s15Fixed16Number e11;
michael@0 168 s15Fixed16Number e12;
michael@0 169 s15Fixed16Number e20;
michael@0 170 s15Fixed16Number e21;
michael@0 171 s15Fixed16Number e22;
michael@0 172
michael@0 173 uint16_t num_input_table_entries;
michael@0 174 uint16_t num_output_table_entries;
michael@0 175
michael@0 176 float *input_table;
michael@0 177 float *clut_table;
michael@0 178 float *output_table;
michael@0 179
michael@0 180 float table_data[];
michael@0 181 };
michael@0 182 #if 0
michael@0 183 /* this is from an intial idea of having the struct correspond to the data in
michael@0 184 * the file. I decided that it wasn't a good idea.
michael@0 185 */
michael@0 186 struct tag_value {
michael@0 187 uint32_t type;
michael@0 188 union {
michael@0 189 struct {
michael@0 190 uint32_t reserved;
michael@0 191 struct {
michael@0 192 s15Fixed16Number X;
michael@0 193 s15Fixed16Number Y;
michael@0 194 s15Fixed16Number Z;
michael@0 195 } XYZNumber;
michael@0 196 } XYZType;
michael@0 197 };
michael@0 198 }; // I guess we need to pack this?
michael@0 199 #endif
michael@0 200
michael@0 201 #define RGB_SIGNATURE 0x52474220
michael@0 202 #define GRAY_SIGNATURE 0x47524159
michael@0 203 #define XYZ_SIGNATURE 0x58595A20
michael@0 204 #define LAB_SIGNATURE 0x4C616220
michael@0 205
michael@0 206 struct _qcms_profile {
michael@0 207 uint32_t class;
michael@0 208 uint32_t color_space;
michael@0 209 uint32_t pcs;
michael@0 210 qcms_intent rendering_intent;
michael@0 211 struct XYZNumber redColorant;
michael@0 212 struct XYZNumber blueColorant;
michael@0 213 struct XYZNumber greenColorant;
michael@0 214 struct curveType *redTRC;
michael@0 215 struct curveType *blueTRC;
michael@0 216 struct curveType *greenTRC;
michael@0 217 struct curveType *grayTRC;
michael@0 218 struct lutType *A2B0;
michael@0 219 struct lutType *B2A0;
michael@0 220 struct lutmABType *mAB;
michael@0 221 struct lutmABType *mBA;
michael@0 222 struct matrix chromaticAdaption;
michael@0 223
michael@0 224 struct precache_output *output_table_r;
michael@0 225 struct precache_output *output_table_g;
michael@0 226 struct precache_output *output_table_b;
michael@0 227 };
michael@0 228
michael@0 229 #ifdef _MSC_VER
michael@0 230 #define inline _inline
michael@0 231 #endif
michael@0 232
michael@0 233 /* produces the nearest float to 'a' with a maximum error
michael@0 234 * of 1/1024 which happens for large values like 0x40000040 */
michael@0 235 static inline float s15Fixed16Number_to_float(s15Fixed16Number a)
michael@0 236 {
michael@0 237 return ((int32_t)a)/65536.f;
michael@0 238 }
michael@0 239
michael@0 240 static inline s15Fixed16Number double_to_s15Fixed16Number(double v)
michael@0 241 {
michael@0 242 return (int32_t)(v*65536);
michael@0 243 }
michael@0 244
michael@0 245 static inline float uInt8Number_to_float(uInt8Number a)
michael@0 246 {
michael@0 247 return ((int32_t)a)/255.f;
michael@0 248 }
michael@0 249
michael@0 250 static inline float uInt16Number_to_float(uInt16Number a)
michael@0 251 {
michael@0 252 return ((int32_t)a)/65535.f;
michael@0 253 }
michael@0 254
michael@0 255
michael@0 256 void precache_release(struct precache_output *p);
michael@0 257 qcms_bool set_rgb_colorants(qcms_profile *profile, qcms_CIE_xyY white_point, qcms_CIE_xyYTRIPLE primaries);
michael@0 258 qcms_bool get_rgb_colorants(struct matrix *colorants, qcms_CIE_xyY white_point, qcms_CIE_xyYTRIPLE primaries);
michael@0 259
michael@0 260 void qcms_transform_data_rgb_out_lut_sse2(qcms_transform *transform,
michael@0 261 unsigned char *src,
michael@0 262 unsigned char *dest,
michael@0 263 size_t length);
michael@0 264 void qcms_transform_data_rgba_out_lut_sse2(qcms_transform *transform,
michael@0 265 unsigned char *src,
michael@0 266 unsigned char *dest,
michael@0 267 size_t length);
michael@0 268 void qcms_transform_data_rgb_out_lut_sse1(qcms_transform *transform,
michael@0 269 unsigned char *src,
michael@0 270 unsigned char *dest,
michael@0 271 size_t length);
michael@0 272 void qcms_transform_data_rgba_out_lut_sse1(qcms_transform *transform,
michael@0 273 unsigned char *src,
michael@0 274 unsigned char *dest,
michael@0 275 size_t length);
michael@0 276
michael@0 277 void qcms_transform_data_rgb_out_lut_altivec(qcms_transform *transform,
michael@0 278 unsigned char *src,
michael@0 279 unsigned char *dest,
michael@0 280 size_t length);
michael@0 281 void qcms_transform_data_rgba_out_lut_altivec(qcms_transform *transform,
michael@0 282 unsigned char *src,
michael@0 283 unsigned char *dest,
michael@0 284 size_t length);
michael@0 285
michael@0 286 extern qcms_bool qcms_supports_iccv4;
michael@0 287
michael@0 288 #ifdef _MSC_VER
michael@0 289
michael@0 290 long __cdecl _InterlockedIncrement(long volatile *);
michael@0 291 long __cdecl _InterlockedDecrement(long volatile *);
michael@0 292 #pragma intrinsic(_InterlockedIncrement)
michael@0 293 #pragma intrinsic(_InterlockedDecrement)
michael@0 294
michael@0 295 #define qcms_atomic_increment(x) _InterlockedIncrement((long volatile *)&x)
michael@0 296 #define qcms_atomic_decrement(x) _InterlockedDecrement((long volatile*)&x)
michael@0 297
michael@0 298 #else
michael@0 299
michael@0 300 #define qcms_atomic_increment(x) __sync_add_and_fetch(&x, 1)
michael@0 301 #define qcms_atomic_decrement(x) __sync_sub_and_fetch(&x, 1)
michael@0 302
michael@0 303 #endif
michael@0 304
michael@0 305
michael@0 306 #ifdef NATIVE_OUTPUT
michael@0 307 # define RGB_OUTPUT_COMPONENTS 4
michael@0 308 # define RGBA_OUTPUT_COMPONENTS 4
michael@0 309 # ifdef IS_LITTLE_ENDIAN
michael@0 310 # define OUTPUT_A_INDEX 3
michael@0 311 # define OUTPUT_R_INDEX 2
michael@0 312 # define OUTPUT_G_INDEX 1
michael@0 313 # define OUTPUT_B_INDEX 0
michael@0 314 # else
michael@0 315 # define OUTPUT_A_INDEX 0
michael@0 316 # define OUTPUT_R_INDEX 1
michael@0 317 # define OUTPUT_G_INDEX 2
michael@0 318 # define OUTPUT_B_INDEX 3
michael@0 319 # endif
michael@0 320 #else
michael@0 321 # define RGB_OUTPUT_COMPONENTS 3
michael@0 322 # define RGBA_OUTPUT_COMPONENTS 4
michael@0 323 # define OUTPUT_R_INDEX 0
michael@0 324 # define OUTPUT_G_INDEX 1
michael@0 325 # define OUTPUT_B_INDEX 2
michael@0 326 # define OUTPUT_A_INDEX 3
michael@0 327 #endif

mercurial