1 #ifndef IMDI_GEN_H 2 #define IMDI_GEN_H 3 4 /* Integer Multi-Dimensional Interpolation */ 5 6 /* 7 * Copyright 2000 - 2007 Graeme W. Gill 8 * All rights reserved. 9 * 10 * This material is licenced under the GNU AFFERO GENERAL PUBLIC LICENSE Version 3 :- 11 * see the License.txt file for licencing details. 12 */ 13 14 /* 15 * Pixel code generation definitions. 16 * 17 * This defines a particular combination of pixel layout, 18 * number of channels, and other runtime requestable features. 19 * This is used by the code generation to setup anticipated 20 * support for these requests, used by the runtime to request 21 * the features, and by the runtime to identify the correct 22 * generated module to use. 23 * 24 */ 25 26 27 /* -------------------------------------------------- */ 28 /* High level kernel generation description */ 29 30 31 /* This is a high level macro desciption of the pixel layout. */ 32 /* It can be expanded by adding a new enumeration, and then */ 33 /* implementing the code in imdi_gen to translate the enumeration */ 34 /* into the exact pixlayout structure details. */ 35 36 typedef enum { 37 invalid_rep = 0x00, 38 pixint8 = 0x01, /* 8 Bits per value, pixel interleaved, no padding */ 39 planeint8 = 0x02, /* 8 bits per value, plane interleaved */ 40 pixint16 = 0x03, /* 16 Bits per value, pixel interleaved, no padding */ 41 planeint16 = 0x04 /* 16 bits per value, plane interleaved */ 42 } imdi_pixrep; 43 44 /* The internal processing precision */ 45 typedef enum { 46 prec_min = 0, /* Minimum of input and output precision */ 47 prec_max = 1, /* Maximum of input and output precision */ 48 prec_in = 2, /* Same as input */ 49 prec_out = 3, /* Same as output */ 50 prec_p8 = 4, /* 8 Bits precision */ 51 prec_p16 = 5 /* 16 Bits precision */ 52 } imdi_iprec; 53 54 /* Output per channel processing options. For the compiled */ 55 /* kernels, this is indexed by physical output channel, */ 56 /* (not to be confused with the runtime oopt which is indexed */ 57 /* by callback channel). */ 58 /* - shift left by channel no * 2 to access option. */ 59 /* Note that oopts_skip valid only for plane interleaved, */ 60 /* and doesn't change the number output channels looked up, */ 61 /* it changes the number of output channels written, hence */ 62 /* must be matched by the arguments to interp() (number of */ 63 /* output pointers, stride etc.) */ 64 typedef enum { 65 oopts_none = 0x0, /* No extra options */ 66 oopts_check = 0x1, /* Test channel value against trigger */ 67 oopts_skip = 0x2, /* Don't write channel value */ 68 oopts_chskp = 0x3 /* oopts_check + oopts_skip */ 69 } imdi_ooptions; 70 71 /* Macro to create an instance of imdi_ooptions for a particular channel */ 72 #define OOPT(flag,chan) ((flag) << (chan * 2)) 73 74 /* Macro to extract the flags particular channel */ 75 #define OOPTX(val,chan) (0x3 & ((val) >> (chan * 2))) 76 77 /* Value of no oopt flags set */ 78 #define OOPTS_NONE 0x00000000 79 80 /* Mask to detect any oopts_check flags that are set */ 81 #define OOPTS_CHECK 0x55555555 82 83 /* Mask to ignore any oopts_check flags that are set */ 84 #define OOPTS_NOT_CHECK 0xAAAAAAAA 85 86 /* Mask to detect any oopts_skip flags that are set */ 87 #define OOPTS_SKIP 0xAAAAAAAA 88 89 /* Mask to ignore any oopts_skip flags that are set */ 90 #define OOPTS_NOT_SKIP 0x55555555 91 92 /* Processing options */ 93 /* Note that there will be a choice between simplex lookup or sort algoritm for */ 94 /* only a subset of kernels (8 bits processing precision, <= 4 input channels) */ 95 typedef enum { 96 opts_none = 0x00, /* Forward direction, no stride */ 97 opts_fwd = 0x01, /* Forwards direction (default is gen fwd/run don't care) */ 98 opts_bwd = 0x02, /* Backwards direction (default is gen fwd/run don't care) */ 99 opts_istride = 0x04, /* Stride on input */ 100 opts_ostride = 0x08, /* Stride on output */ 101 102 opts_splx_sort = 0x10, /* Prefer simplex over sort algorithm (generate both) */ 103 opts_sort_splx = 0x20, /* Force sort algorithm, rather than simplex table (generate both) */ 104 opts_splx = 0x40, /* Generate simplex only (when possible), default is sort only. */ 105 106 opts_end = 0x80 /* End marker */ 107 } imdi_options; 108 109 /* This sructure allows a series of related kernels to be generated */ 110 #define MX_GDCS 20 111 /* * means multiplies combination */ 112 /* + means lockstep with previous line */ 113 typedef struct { 114 int idcombs[MX_GDCS]; /* * Input dimension combinations (0 at end) */ 115 int itres[MX_GDCS]; /* + Interpolation table resolutions for */ 116 int stres[MX_GDCS]; /* + Simplex table resolutions */ 117 118 int odcombs[MX_GDCS]; /* * Output dimensions combinations (0 at end) */ 119 imdi_ooptions ooptcombs[MX_GDCS]; /* + output per channel options */ 120 121 imdi_pixrep incombs[MX_GDCS]; /* * Input pixel representation */ 122 imdi_iprec iprecs[MX_GDCS]; /* + Internal precision */ 123 imdi_pixrep outcombs[MX_GDCS]; /* + Output pixel representation */ 124 125 imdi_options optcombs[MX_GDCS]; /* * Direction and stride options */ 126 } gendesc; 127 128 /* -------------------------------------------------- */ 129 /* Detailed level of generation specification */ 130 131 /* Pixel layout: */ 132 /* Each channel value is assumed to be read with a */ 133 /* native machine single read of size bpch, */ 134 /* and bov and bpv being bit indexes into that value. */ 135 /* */ 136 /* If pint == 0, then each read will be of size bpch[], and will */ 137 /* have its own pointer, will be incremented by chi[]. */ 138 /* If pint != 0, then the reads will be size bpch[0], from successive */ 139 /* locations, chi[] apart. */ 140 /* */ 141 /* If packed == 0, then separate reads are needed for each input */ 142 /* channel. */ 143 /* If packed != 0, then the channel values will be extracted */ 144 /* from a single read of size bpch[0] */ 145 /* */ 146 /* Note that at all times the bit offset and size values */ 147 /* will be obeyed for each input value. */ 148 149 /* NOTE :- if you change this, you need to change the code in cgen.c */ 150 /* labeled !genspec and tabspec delta code! */ 151 typedef struct { 152 int bpch[IXDIDO]; /* Bits per channel read (must be divisible by 8) */ 153 int chi[IXDIDO]; /* channel increment in multiples of bpch[] (0 == dimensionality) */ 154 int bov[IXDIDO]; /* Bit offset to value within channel */ 155 int bpv[IXDIDO]; /* Bits per value within channel */ 156 int pint; /* Flag - nonz if pixel interleaved (ie. reads from successice locations) */ 157 int packed; /* Flag - nonz if all channels are packed into a single read */ 158 } pixlayout; 159 160 /* Structure that specifies the configuration of a generated interpolation kernel. */ 161 /* NOTE :- if you change this, you need to change the code in cgen.c */ 162 /* labeled !genspec and tabspec delta code! */ 163 typedef struct { 164 /* Input to code generator */ 165 int prec; /* Internal precision:- either 8 or 16 bits */ 166 int id; /* Number of input dimensions used for interpolation */ 167 int od; /* Number of output dimensions created by interpolation */ 168 imdi_pixrep irep; /* High level input pixel representation */ 169 imdi_pixrep orep; /* High level output pixel representation */ 170 int in_signed; /* Bit flag per channel, NZ if treat as signed (runtime setup) */ 171 int out_signed; /* Bit flag per channel, NZ if treat as signed (runtime setup) */ 172 pixlayout in; /* Input pixel layout */ 173 pixlayout out; /* Output pixel layout */ 174 imdi_ooptions oopt; /* output per channel options */ 175 imdi_options opt; /* Direction and stride options */ 176 int itres; /* Interpolation table resolution */ 177 int stres; /* Simplex table resolution */ 178 179 /* Returned value */ 180 char kkeys[100]; /* Kernel keys */ 181 char kdesc[100]; /* At genspec time */ 182 char kname[100]; /* At generation time */ 183 } genspec; 184 185 /* - - - - - - - - - - - - - - - - - - - - - - - */ 186 187 /* Translate between high level and low level generation specification */ 188 int set_genspec(genspec *gs, gendesc *gd, int comb, mach_arch *a); 189 190 /* - - - - - - - - - - - - - - - - - - - - - - - */ 191 /* Convert the input and output pixel representation and the internal */ 192 /* precision choice into a precision in bits */ 193 /* (Used at code gen and code execution, hence defined as a macro) */ 194 #define COMPUTE_IPREC(PRECOUT, INREP, IPREC, OUTREP) \ 195 { \ 196 int _iprec, _oprec; \ 197 \ 198 switch (INREP) { \ 199 default: \ 200 case pixint8: \ 201 case planeint8: \ 202 _iprec = 8; \ 203 break; \ 204 case pixint16: \ 205 case planeint16: \ 206 _iprec = 16; \ 207 break; \ 208 } \ 209 switch (OUTREP) { \ 210 default: \ 211 case pixint8: \ 212 case planeint8: \ 213 _oprec = 8; \ 214 break; \ 215 case pixint16: \ 216 case planeint16: \ 217 _oprec = 16; \ 218 break; \ 219 } \ 220 switch (IPREC) { \ 221 default: \ 222 case prec_min: \ 223 PRECOUT = _iprec < _oprec ? _iprec : _oprec; \ 224 break; \ 225 case prec_max: \ 226 PRECOUT = _iprec > _oprec ? _iprec : _oprec; \ 227 break; \ 228 case prec_in: \ 229 PRECOUT = _iprec; \ 230 break; \ 231 case prec_out: \ 232 PRECOUT = _oprec; \ 233 break; \ 234 case prec_p8: \ 235 PRECOUT = 8; \ 236 break; \ 237 case prec_p16: \ 238 PRECOUT = 16; \ 239 break; \ 240 } \ 241 } \ 242 243 244 /* - - - - - - - - - - - - - - - - - - - - - - - */ 245 246 struct _tabspec; 247 248 /* Supported code generators: */ 249 250 /* The 'C' code generator */ 251 /* Generate a source file to implement the specified */ 252 /* interpolation kernel. Fill in return values and return 0 if OK. */ 253 /* Return 1 if this kernel should be skipped (ie. force sort and sort not forced) */ 254 /* and some other anon-zero on error. */ 255 int gen_c_kernel(genspec *g, struct _tabspec *t, mach_arch *a, 256 FILE *fp, int index, genspec *og, struct _tabspec *ot); 257 258 /* asm, MMX, etc. generators declarations go here ! */ 259 260 #endif /* IMDI_GEN_H */ 261 262 263 264 265 266 267 268 269 270 271 272