1 /************************************************************************** 2 * 3 * Copyright 2007 VMware, Inc. 4 * All Rights Reserved. 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining a 7 * copy of this software and associated documentation files (the 8 * "Software"), to deal in the Software without restriction, including 9 * without limitation the rights to use, copy, modify, merge, publish, 10 * distribute, sub license, and/or sell copies of the Software, and to 11 * permit persons to whom the Software is furnished to do so, subject to 12 * the following conditions: 13 * 14 * The above copyright notice and this permission notice (including the 15 * next paragraph) shall be included in all copies or substantial portions 16 * of the Software. 17 * 18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 19 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 20 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. 21 * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR 22 * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 23 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 24 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 25 * 26 **************************************************************************/ 27 28 /* 29 * Authors: 30 * Keith Whitwell <keithw (at) vmware.com> 31 */ 32 33 #include "util/u_memory.h" 34 #include "util/u_format.h" 35 #include "util/u_half.h" 36 #include "util/u_math.h" 37 #include "pipe/p_state.h" 38 #include "translate.h" 39 40 41 #define DRAW_DBG 0 42 43 typedef void (*fetch_func)(void *dst, 44 const uint8_t *src, 45 unsigned i, unsigned j); 46 typedef void (*emit_func)(const void *attrib, void *ptr); 47 48 49 50 struct translate_generic { 51 struct translate translate; 52 53 struct { 54 enum translate_element_type type; 55 56 fetch_func fetch; 57 unsigned buffer; 58 unsigned input_offset; 59 unsigned instance_divisor; 60 61 emit_func emit; 62 unsigned output_offset; 63 64 const uint8_t *input_ptr; 65 unsigned input_stride; 66 unsigned max_index; 67 68 /* this value is set to -1 if this is a normal element with 69 * output_format != input_format: in this case, u_format is used 70 * to do a full conversion 71 * 72 * this value is set to the format size in bytes if 73 * output_format == input_format or for 32-bit instance ids: 74 * in this case, memcpy is used to copy this amount of bytes 75 */ 76 int copy_size; 77 78 } attrib[TRANSLATE_MAX_ATTRIBS]; 79 80 unsigned nr_attrib; 81 }; 82 83 84 static struct translate_generic * 85 translate_generic(struct translate *translate) 86 { 87 return (struct translate_generic *)translate; 88 } 89 90 91 /** 92 * Fetch a dword[4] vertex attribute from memory, doing format/type 93 * conversion as needed. 94 * 95 * This is probably needed/dupliocated elsewhere, eg format 96 * conversion, texture sampling etc. 97 */ 98 #define ATTRIB(NAME, SZ, SRCTYPE, DSTTYPE, TO) \ 99 static void \ 100 emit_##NAME(const void *attrib, void *ptr) \ 101 { \ 102 unsigned i; \ 103 SRCTYPE *in = (SRCTYPE *)attrib; \ 104 DSTTYPE *out = (DSTTYPE *)ptr; \ 105 \ 106 for (i = 0; i < SZ; i++) { \ 107 out[i] = TO(in[i]); \ 108 } \ 109 } 110 111 112 #define TO_64_FLOAT(x) ((double) x) 113 #define TO_32_FLOAT(x) (x) 114 #define TO_16_FLOAT(x) util_float_to_half(x) 115 116 #define TO_8_USCALED(x) ((unsigned char) x) 117 #define TO_16_USCALED(x) ((unsigned short) x) 118 #define TO_32_USCALED(x) ((unsigned int) x) 119 120 #define TO_8_SSCALED(x) ((char) x) 121 #define TO_16_SSCALED(x) ((short) x) 122 #define TO_32_SSCALED(x) ((int) x) 123 124 #define TO_8_UNORM(x) ((unsigned char) (x * 255.0f)) 125 #define TO_16_UNORM(x) ((unsigned short) (x * 65535.0f)) 126 #define TO_32_UNORM(x) ((unsigned int) (x * 4294967295.0f)) 127 128 #define TO_8_SNORM(x) ((char) (x * 127.0f)) 129 #define TO_16_SNORM(x) ((short) (x * 32767.0f)) 130 #define TO_32_SNORM(x) ((int) (x * 2147483647.0f)) 131 132 #define TO_32_FIXED(x) ((int) (x * 65536.0f)) 133 134 #define TO_INT(x) (x) 135 136 137 ATTRIB(R64G64B64A64_FLOAT, 4, float, double, TO_64_FLOAT) 138 ATTRIB(R64G64B64_FLOAT, 3, float, double, TO_64_FLOAT) 139 ATTRIB(R64G64_FLOAT, 2, float, double, TO_64_FLOAT) 140 ATTRIB(R64_FLOAT, 1, float, double, TO_64_FLOAT) 141 142 ATTRIB(R32G32B32A32_FLOAT, 4, float, float, TO_32_FLOAT) 143 ATTRIB(R32G32B32_FLOAT, 3, float, float, TO_32_FLOAT) 144 ATTRIB(R32G32_FLOAT, 2, float, float, TO_32_FLOAT) 145 ATTRIB(R32_FLOAT, 1, float, float, TO_32_FLOAT) 146 147 ATTRIB(R16G16B16A16_FLOAT, 4, float, ushort, TO_16_FLOAT) 148 ATTRIB(R16G16B16_FLOAT, 3, float, ushort, TO_16_FLOAT) 149 ATTRIB(R16G16_FLOAT, 2, float, ushort, TO_16_FLOAT) 150 ATTRIB(R16_FLOAT, 1, float, ushort, TO_16_FLOAT) 151 152 ATTRIB(R32G32B32A32_USCALED, 4, float, unsigned, TO_32_USCALED) 153 ATTRIB(R32G32B32_USCALED, 3, float, unsigned, TO_32_USCALED) 154 ATTRIB(R32G32_USCALED, 2, float, unsigned, TO_32_USCALED) 155 ATTRIB(R32_USCALED, 1, float, unsigned, TO_32_USCALED) 156 157 ATTRIB(R32G32B32A32_SSCALED, 4, float, int, TO_32_SSCALED) 158 ATTRIB(R32G32B32_SSCALED, 3, float, int, TO_32_SSCALED) 159 ATTRIB(R32G32_SSCALED, 2, float, int, TO_32_SSCALED) 160 ATTRIB(R32_SSCALED, 1, float, int, TO_32_SSCALED) 161 162 ATTRIB(R32G32B32A32_UNORM, 4, float, unsigned, TO_32_UNORM) 163 ATTRIB(R32G32B32_UNORM, 3, float, unsigned, TO_32_UNORM) 164 ATTRIB(R32G32_UNORM, 2, float, unsigned, TO_32_UNORM) 165 ATTRIB(R32_UNORM, 1, float, unsigned, TO_32_UNORM) 166 167 ATTRIB(R32G32B32A32_SNORM, 4, float, int, TO_32_SNORM) 168 ATTRIB(R32G32B32_SNORM, 3, float, int, TO_32_SNORM) 169 ATTRIB(R32G32_SNORM, 2, float, int, TO_32_SNORM) 170 ATTRIB(R32_SNORM, 1, float, int, TO_32_SNORM) 171 172 ATTRIB(R16G16B16A16_USCALED, 4, float, ushort, TO_16_USCALED) 173 ATTRIB(R16G16B16_USCALED, 3, float, ushort, TO_16_USCALED) 174 ATTRIB(R16G16_USCALED, 2, float, ushort, TO_16_USCALED) 175 ATTRIB(R16_USCALED, 1, float, ushort, TO_16_USCALED) 176 177 ATTRIB(R16G16B16A16_SSCALED, 4, float, short, TO_16_SSCALED) 178 ATTRIB(R16G16B16_SSCALED, 3, float, short, TO_16_SSCALED) 179 ATTRIB(R16G16_SSCALED, 2, float, short, TO_16_SSCALED) 180 ATTRIB(R16_SSCALED, 1, float, short, TO_16_SSCALED) 181 182 ATTRIB(R16G16B16A16_UNORM, 4, float, ushort, TO_16_UNORM) 183 ATTRIB(R16G16B16_UNORM, 3, float, ushort, TO_16_UNORM) 184 ATTRIB(R16G16_UNORM, 2, float, ushort, TO_16_UNORM) 185 ATTRIB(R16_UNORM, 1, float, ushort, TO_16_UNORM) 186 187 ATTRIB(R16G16B16A16_SNORM, 4, float, short, TO_16_SNORM) 188 ATTRIB(R16G16B16_SNORM, 3, float, short, TO_16_SNORM) 189 ATTRIB(R16G16_SNORM, 2, float, short, TO_16_SNORM) 190 ATTRIB(R16_SNORM, 1, float, short, TO_16_SNORM) 191 192 ATTRIB(R8G8B8A8_USCALED, 4, float, ubyte, TO_8_USCALED) 193 ATTRIB(R8G8B8_USCALED, 3, float, ubyte, TO_8_USCALED) 194 ATTRIB(R8G8_USCALED, 2, float, ubyte, TO_8_USCALED) 195 ATTRIB(R8_USCALED, 1, float, ubyte, TO_8_USCALED) 196 197 ATTRIB(R8G8B8A8_SSCALED, 4, float, char, TO_8_SSCALED) 198 ATTRIB(R8G8B8_SSCALED, 3, float, char, TO_8_SSCALED) 199 ATTRIB(R8G8_SSCALED, 2, float, char, TO_8_SSCALED) 200 ATTRIB(R8_SSCALED, 1, float, char, TO_8_SSCALED) 201 202 ATTRIB(R8G8B8A8_UNORM, 4, float, ubyte, TO_8_UNORM) 203 ATTRIB(R8G8B8_UNORM, 3, float, ubyte, TO_8_UNORM) 204 ATTRIB(R8G8_UNORM, 2, float, ubyte, TO_8_UNORM) 205 ATTRIB(R8_UNORM, 1, float, ubyte, TO_8_UNORM) 206 207 ATTRIB(R8G8B8A8_SNORM, 4, float, char, TO_8_SNORM) 208 ATTRIB(R8G8B8_SNORM, 3, float, char, TO_8_SNORM) 209 ATTRIB(R8G8_SNORM, 2, float, char, TO_8_SNORM) 210 ATTRIB(R8_SNORM, 1, float, char, TO_8_SNORM) 211 212 ATTRIB(R32G32B32A32_UINT, 4, uint32_t, unsigned, TO_INT) 213 ATTRIB(R32G32B32_UINT, 3, uint32_t, unsigned, TO_INT) 214 ATTRIB(R32G32_UINT, 2, uint32_t, unsigned, TO_INT) 215 ATTRIB(R32_UINT, 1, uint32_t, unsigned, TO_INT) 216 217 ATTRIB(R16G16B16A16_UINT, 4, uint32_t, ushort, TO_INT) 218 ATTRIB(R16G16B16_UINT, 3, uint32_t, ushort, TO_INT) 219 ATTRIB(R16G16_UINT, 2, uint32_t, ushort, TO_INT) 220 ATTRIB(R16_UINT, 1, uint32_t, ushort, TO_INT) 221 222 ATTRIB(R8G8B8A8_UINT, 4, uint32_t, ubyte, TO_INT) 223 ATTRIB(R8G8B8_UINT, 3, uint32_t, ubyte, TO_INT) 224 ATTRIB(R8G8_UINT, 2, uint32_t, ubyte, TO_INT) 225 ATTRIB(R8_UINT, 1, uint32_t, ubyte, TO_INT) 226 227 ATTRIB(R32G32B32A32_SINT, 4, int32_t, int, TO_INT) 228 ATTRIB(R32G32B32_SINT, 3, int32_t, int, TO_INT) 229 ATTRIB(R32G32_SINT, 2, int32_t, int, TO_INT) 230 ATTRIB(R32_SINT, 1, int32_t, int, TO_INT) 231 232 ATTRIB(R16G16B16A16_SINT, 4, int32_t, short, TO_INT) 233 ATTRIB(R16G16B16_SINT, 3, int32_t, short, TO_INT) 234 ATTRIB(R16G16_SINT, 2, int32_t, short, TO_INT) 235 ATTRIB(R16_SINT, 1, int32_t, short, TO_INT) 236 237 ATTRIB(R8G8B8A8_SINT, 4, int32_t, char, TO_INT) 238 ATTRIB(R8G8B8_SINT, 3, int32_t, char, TO_INT) 239 ATTRIB(R8G8_SINT, 2, int32_t, char, TO_INT) 240 ATTRIB(R8_SINT, 1, int32_t, char, TO_INT) 241 242 static void 243 emit_A8R8G8B8_UNORM(const void *attrib, void *ptr) 244 { 245 float *in = (float *)attrib; 246 ubyte *out = (ubyte *)ptr; 247 out[0] = TO_8_UNORM(in[3]); 248 out[1] = TO_8_UNORM(in[0]); 249 out[2] = TO_8_UNORM(in[1]); 250 out[3] = TO_8_UNORM(in[2]); 251 } 252 253 static void 254 emit_B8G8R8A8_UNORM(const void *attrib, void *ptr) 255 { 256 float *in = (float *)attrib; 257 ubyte *out = (ubyte *)ptr; 258 out[2] = TO_8_UNORM(in[0]); 259 out[1] = TO_8_UNORM(in[1]); 260 out[0] = TO_8_UNORM(in[2]); 261 out[3] = TO_8_UNORM(in[3]); 262 } 263 264 static void 265 emit_B10G10R10A2_UNORM(const void *attrib, void *ptr) 266 { 267 float *src = (float *)ptr; 268 uint32_t value = 0; 269 value |= ((uint32_t)(CLAMP(src[2], 0, 1) * 0x3ff)) & 0x3ff; 270 value |= (((uint32_t)(CLAMP(src[1], 0, 1) * 0x3ff)) & 0x3ff) << 10; 271 value |= (((uint32_t)(CLAMP(src[0], 0, 1) * 0x3ff)) & 0x3ff) << 20; 272 value |= ((uint32_t)(CLAMP(src[3], 0, 1) * 0x3)) << 30; 273 *(uint32_t *)attrib = util_le32_to_cpu(value); 274 } 275 276 static void 277 emit_B10G10R10A2_USCALED(const void *attrib, void *ptr) 278 { 279 float *src = (float *)ptr; 280 uint32_t value = 0; 281 value |= ((uint32_t)CLAMP(src[2], 0, 1023)) & 0x3ff; 282 value |= (((uint32_t)CLAMP(src[1], 0, 1023)) & 0x3ff) << 10; 283 value |= (((uint32_t)CLAMP(src[0], 0, 1023)) & 0x3ff) << 20; 284 value |= ((uint32_t)CLAMP(src[3], 0, 3)) << 30; 285 *(uint32_t *)attrib = util_le32_to_cpu(value); 286 } 287 288 static void 289 emit_B10G10R10A2_SNORM(const void *attrib, void *ptr) 290 { 291 float *src = (float *)ptr; 292 uint32_t value = 0; 293 value |= (uint32_t)(((uint32_t)(CLAMP(src[2], -1, 1) * 0x1ff)) & 0x3ff) ; 294 value |= (uint32_t)((((uint32_t)(CLAMP(src[1], -1, 1) * 0x1ff)) & 0x3ff) << 10) ; 295 value |= (uint32_t)((((uint32_t)(CLAMP(src[0], -1, 1) * 0x1ff)) & 0x3ff) << 20) ; 296 value |= (uint32_t)(((uint32_t)(CLAMP(src[3], -1, 1) * 0x1)) << 30) ; 297 *(uint32_t *)attrib = util_le32_to_cpu(value); 298 } 299 300 static void 301 emit_B10G10R10A2_SSCALED(const void *attrib, void *ptr) 302 { 303 float *src = (float *)ptr; 304 uint32_t value = 0; 305 value |= (uint32_t)(((uint32_t)CLAMP(src[2], -512, 511)) & 0x3ff) ; 306 value |= (uint32_t)((((uint32_t)CLAMP(src[1], -512, 511)) & 0x3ff) << 10) ; 307 value |= (uint32_t)((((uint32_t)CLAMP(src[0], -512, 511)) & 0x3ff) << 20) ; 308 value |= (uint32_t)(((uint32_t)CLAMP(src[3], -2, 1)) << 30) ; 309 *(uint32_t *)attrib = util_le32_to_cpu(value); 310 } 311 312 static void 313 emit_R10G10B10A2_UNORM(const void *attrib, void *ptr) 314 { 315 float *src = (float *)ptr; 316 uint32_t value = 0; 317 value |= ((uint32_t)(CLAMP(src[0], 0, 1) * 0x3ff)) & 0x3ff; 318 value |= (((uint32_t)(CLAMP(src[1], 0, 1) * 0x3ff)) & 0x3ff) << 10; 319 value |= (((uint32_t)(CLAMP(src[2], 0, 1) * 0x3ff)) & 0x3ff) << 20; 320 value |= ((uint32_t)(CLAMP(src[3], 0, 1) * 0x3)) << 30; 321 *(uint32_t *)attrib = util_le32_to_cpu(value); 322 } 323 324 static void 325 emit_R10G10B10A2_USCALED(const void *attrib, void *ptr) 326 { 327 float *src = (float *)ptr; 328 uint32_t value = 0; 329 value |= ((uint32_t)CLAMP(src[0], 0, 1023)) & 0x3ff; 330 value |= (((uint32_t)CLAMP(src[1], 0, 1023)) & 0x3ff) << 10; 331 value |= (((uint32_t)CLAMP(src[2], 0, 1023)) & 0x3ff) << 20; 332 value |= ((uint32_t)CLAMP(src[3], 0, 3)) << 30; 333 *(uint32_t *)attrib = util_le32_to_cpu(value); 334 } 335 336 static void 337 emit_R10G10B10A2_SNORM(const void *attrib, void *ptr) 338 { 339 float *src = (float *)ptr; 340 uint32_t value = 0; 341 value |= (uint32_t)(((uint32_t)(CLAMP(src[0], -1, 1) * 0x1ff)) & 0x3ff) ; 342 value |= (uint32_t)((((uint32_t)(CLAMP(src[1], -1, 1) * 0x1ff)) & 0x3ff) << 10) ; 343 value |= (uint32_t)((((uint32_t)(CLAMP(src[2], -1, 1) * 0x1ff)) & 0x3ff) << 20) ; 344 value |= (uint32_t)(((uint32_t)(CLAMP(src[3], -1, 1) * 0x1)) << 30) ; 345 *(uint32_t *)attrib = util_le32_to_cpu(value); 346 } 347 348 static void 349 emit_R10G10B10A2_SSCALED(const void *attrib, void *ptr) 350 { 351 float *src = (float *)ptr; 352 uint32_t value = 0; 353 value |= (uint32_t)(((uint32_t)CLAMP(src[0], -512, 511)) & 0x3ff) ; 354 value |= (uint32_t)((((uint32_t)CLAMP(src[1], -512, 511)) & 0x3ff) << 10) ; 355 value |= (uint32_t)((((uint32_t)CLAMP(src[2], -512, 511)) & 0x3ff) << 20) ; 356 value |= (uint32_t)(((uint32_t)CLAMP(src[3], -2, 1)) << 30) ; 357 *(uint32_t *)attrib = util_le32_to_cpu(value); 358 } 359 360 static void 361 emit_NULL(const void *attrib, void *ptr) 362 { 363 /* do nothing is the only sensible option */ 364 } 365 366 static emit_func 367 get_emit_func(enum pipe_format format) 368 { 369 switch (format) { 370 case PIPE_FORMAT_R64_FLOAT: 371 return &emit_R64_FLOAT; 372 case PIPE_FORMAT_R64G64_FLOAT: 373 return &emit_R64G64_FLOAT; 374 case PIPE_FORMAT_R64G64B64_FLOAT: 375 return &emit_R64G64B64_FLOAT; 376 case PIPE_FORMAT_R64G64B64A64_FLOAT: 377 return &emit_R64G64B64A64_FLOAT; 378 379 case PIPE_FORMAT_R32_FLOAT: 380 return &emit_R32_FLOAT; 381 case PIPE_FORMAT_R32G32_FLOAT: 382 return &emit_R32G32_FLOAT; 383 case PIPE_FORMAT_R32G32B32_FLOAT: 384 return &emit_R32G32B32_FLOAT; 385 case PIPE_FORMAT_R32G32B32A32_FLOAT: 386 return &emit_R32G32B32A32_FLOAT; 387 388 case PIPE_FORMAT_R16_FLOAT: 389 return &emit_R16_FLOAT; 390 case PIPE_FORMAT_R16G16_FLOAT: 391 return &emit_R16G16_FLOAT; 392 case PIPE_FORMAT_R16G16B16_FLOAT: 393 return &emit_R16G16B16_FLOAT; 394 case PIPE_FORMAT_R16G16B16A16_FLOAT: 395 return &emit_R16G16B16A16_FLOAT; 396 397 case PIPE_FORMAT_R32_UNORM: 398 return &emit_R32_UNORM; 399 case PIPE_FORMAT_R32G32_UNORM: 400 return &emit_R32G32_UNORM; 401 case PIPE_FORMAT_R32G32B32_UNORM: 402 return &emit_R32G32B32_UNORM; 403 case PIPE_FORMAT_R32G32B32A32_UNORM: 404 return &emit_R32G32B32A32_UNORM; 405 406 case PIPE_FORMAT_R32_USCALED: 407 return &emit_R32_USCALED; 408 case PIPE_FORMAT_R32G32_USCALED: 409 return &emit_R32G32_USCALED; 410 case PIPE_FORMAT_R32G32B32_USCALED: 411 return &emit_R32G32B32_USCALED; 412 case PIPE_FORMAT_R32G32B32A32_USCALED: 413 return &emit_R32G32B32A32_USCALED; 414 415 case PIPE_FORMAT_R32_SNORM: 416 return &emit_R32_SNORM; 417 case PIPE_FORMAT_R32G32_SNORM: 418 return &emit_R32G32_SNORM; 419 case PIPE_FORMAT_R32G32B32_SNORM: 420 return &emit_R32G32B32_SNORM; 421 case PIPE_FORMAT_R32G32B32A32_SNORM: 422 return &emit_R32G32B32A32_SNORM; 423 424 case PIPE_FORMAT_R32_SSCALED: 425 return &emit_R32_SSCALED; 426 case PIPE_FORMAT_R32G32_SSCALED: 427 return &emit_R32G32_SSCALED; 428 case PIPE_FORMAT_R32G32B32_SSCALED: 429 return &emit_R32G32B32_SSCALED; 430 case PIPE_FORMAT_R32G32B32A32_SSCALED: 431 return &emit_R32G32B32A32_SSCALED; 432 433 case PIPE_FORMAT_R16_UNORM: 434 return &emit_R16_UNORM; 435 case PIPE_FORMAT_R16G16_UNORM: 436 return &emit_R16G16_UNORM; 437 case PIPE_FORMAT_R16G16B16_UNORM: 438 return &emit_R16G16B16_UNORM; 439 case PIPE_FORMAT_R16G16B16A16_UNORM: 440 return &emit_R16G16B16A16_UNORM; 441 442 case PIPE_FORMAT_R16_USCALED: 443 return &emit_R16_USCALED; 444 case PIPE_FORMAT_R16G16_USCALED: 445 return &emit_R16G16_USCALED; 446 case PIPE_FORMAT_R16G16B16_USCALED: 447 return &emit_R16G16B16_USCALED; 448 case PIPE_FORMAT_R16G16B16A16_USCALED: 449 return &emit_R16G16B16A16_USCALED; 450 451 case PIPE_FORMAT_R16_SNORM: 452 return &emit_R16_SNORM; 453 case PIPE_FORMAT_R16G16_SNORM: 454 return &emit_R16G16_SNORM; 455 case PIPE_FORMAT_R16G16B16_SNORM: 456 return &emit_R16G16B16_SNORM; 457 case PIPE_FORMAT_R16G16B16A16_SNORM: 458 return &emit_R16G16B16A16_SNORM; 459 460 case PIPE_FORMAT_R16_SSCALED: 461 return &emit_R16_SSCALED; 462 case PIPE_FORMAT_R16G16_SSCALED: 463 return &emit_R16G16_SSCALED; 464 case PIPE_FORMAT_R16G16B16_SSCALED: 465 return &emit_R16G16B16_SSCALED; 466 case PIPE_FORMAT_R16G16B16A16_SSCALED: 467 return &emit_R16G16B16A16_SSCALED; 468 469 case PIPE_FORMAT_R8_UNORM: 470 return &emit_R8_UNORM; 471 case PIPE_FORMAT_R8G8_UNORM: 472 return &emit_R8G8_UNORM; 473 case PIPE_FORMAT_R8G8B8_UNORM: 474 return &emit_R8G8B8_UNORM; 475 case PIPE_FORMAT_R8G8B8A8_UNORM: 476 return &emit_R8G8B8A8_UNORM; 477 478 case PIPE_FORMAT_R8_USCALED: 479 return &emit_R8_USCALED; 480 case PIPE_FORMAT_R8G8_USCALED: 481 return &emit_R8G8_USCALED; 482 case PIPE_FORMAT_R8G8B8_USCALED: 483 return &emit_R8G8B8_USCALED; 484 case PIPE_FORMAT_R8G8B8A8_USCALED: 485 return &emit_R8G8B8A8_USCALED; 486 487 case PIPE_FORMAT_R8_SNORM: 488 return &emit_R8_SNORM; 489 case PIPE_FORMAT_R8G8_SNORM: 490 return &emit_R8G8_SNORM; 491 case PIPE_FORMAT_R8G8B8_SNORM: 492 return &emit_R8G8B8_SNORM; 493 case PIPE_FORMAT_R8G8B8A8_SNORM: 494 return &emit_R8G8B8A8_SNORM; 495 496 case PIPE_FORMAT_R8_SSCALED: 497 return &emit_R8_SSCALED; 498 case PIPE_FORMAT_R8G8_SSCALED: 499 return &emit_R8G8_SSCALED; 500 case PIPE_FORMAT_R8G8B8_SSCALED: 501 return &emit_R8G8B8_SSCALED; 502 case PIPE_FORMAT_R8G8B8A8_SSCALED: 503 return &emit_R8G8B8A8_SSCALED; 504 505 case PIPE_FORMAT_B8G8R8A8_UNORM: 506 return &emit_B8G8R8A8_UNORM; 507 508 case PIPE_FORMAT_A8R8G8B8_UNORM: 509 return &emit_A8R8G8B8_UNORM; 510 511 case PIPE_FORMAT_R32_UINT: 512 return &emit_R32_UINT; 513 case PIPE_FORMAT_R32G32_UINT: 514 return &emit_R32G32_UINT; 515 case PIPE_FORMAT_R32G32B32_UINT: 516 return &emit_R32G32B32_UINT; 517 case PIPE_FORMAT_R32G32B32A32_UINT: 518 return &emit_R32G32B32A32_UINT; 519 520 case PIPE_FORMAT_R16_UINT: 521 return &emit_R16_UINT; 522 case PIPE_FORMAT_R16G16_UINT: 523 return &emit_R16G16_UINT; 524 case PIPE_FORMAT_R16G16B16_UINT: 525 return &emit_R16G16B16_UINT; 526 case PIPE_FORMAT_R16G16B16A16_UINT: 527 return &emit_R16G16B16A16_UINT; 528 529 case PIPE_FORMAT_R8_UINT: 530 return &emit_R8_UINT; 531 case PIPE_FORMAT_R8G8_UINT: 532 return &emit_R8G8_UINT; 533 case PIPE_FORMAT_R8G8B8_UINT: 534 return &emit_R8G8B8_UINT; 535 case PIPE_FORMAT_R8G8B8A8_UINT: 536 return &emit_R8G8B8A8_UINT; 537 538 case PIPE_FORMAT_R32_SINT: 539 return &emit_R32_SINT; 540 case PIPE_FORMAT_R32G32_SINT: 541 return &emit_R32G32_SINT; 542 case PIPE_FORMAT_R32G32B32_SINT: 543 return &emit_R32G32B32_SINT; 544 case PIPE_FORMAT_R32G32B32A32_SINT: 545 return &emit_R32G32B32A32_SINT; 546 547 case PIPE_FORMAT_R16_SINT: 548 return &emit_R16_SINT; 549 case PIPE_FORMAT_R16G16_SINT: 550 return &emit_R16G16_SINT; 551 case PIPE_FORMAT_R16G16B16_SINT: 552 return &emit_R16G16B16_SINT; 553 case PIPE_FORMAT_R16G16B16A16_SINT: 554 return &emit_R16G16B16A16_SINT; 555 556 case PIPE_FORMAT_R8_SINT: 557 return &emit_R8_SINT; 558 case PIPE_FORMAT_R8G8_SINT: 559 return &emit_R8G8_SINT; 560 case PIPE_FORMAT_R8G8B8_SINT: 561 return &emit_R8G8B8_SINT; 562 case PIPE_FORMAT_R8G8B8A8_SINT: 563 return &emit_R8G8B8A8_SINT; 564 565 case PIPE_FORMAT_B10G10R10A2_UNORM: 566 return &emit_B10G10R10A2_UNORM; 567 case PIPE_FORMAT_B10G10R10A2_USCALED: 568 return &emit_B10G10R10A2_USCALED; 569 case PIPE_FORMAT_B10G10R10A2_SNORM: 570 return &emit_B10G10R10A2_SNORM; 571 case PIPE_FORMAT_B10G10R10A2_SSCALED: 572 return &emit_B10G10R10A2_SSCALED; 573 574 case PIPE_FORMAT_R10G10B10A2_UNORM: 575 return &emit_R10G10B10A2_UNORM; 576 case PIPE_FORMAT_R10G10B10A2_USCALED: 577 return &emit_R10G10B10A2_USCALED; 578 case PIPE_FORMAT_R10G10B10A2_SNORM: 579 return &emit_R10G10B10A2_SNORM; 580 case PIPE_FORMAT_R10G10B10A2_SSCALED: 581 return &emit_R10G10B10A2_SSCALED; 582 583 default: 584 assert(0); 585 return &emit_NULL; 586 } 587 } 588 589 static ALWAYS_INLINE void PIPE_CDECL 590 generic_run_one(struct translate_generic *tg, 591 unsigned elt, 592 unsigned start_instance, 593 unsigned instance_id, 594 void *vert) 595 { 596 unsigned nr_attrs = tg->nr_attrib; 597 unsigned attr; 598 599 for (attr = 0; attr < nr_attrs; attr++) { 600 float data[4]; 601 uint8_t *dst = (uint8_t *)vert + tg->attrib[attr].output_offset; 602 603 if (tg->attrib[attr].type == TRANSLATE_ELEMENT_NORMAL) { 604 const uint8_t *src; 605 unsigned index; 606 int copy_size; 607 608 if (tg->attrib[attr].instance_divisor) { 609 index = start_instance; 610 index += (instance_id / tg->attrib[attr].instance_divisor); 611 /* XXX we need to clamp the index here too, but to a 612 * per-array max value, not the draw->pt.max_index value 613 * that's being given to us via translate->set_buffer(). 614 */ 615 } 616 else { 617 index = elt; 618 /* clamp to avoid going out of bounds */ 619 index = MIN2(index, tg->attrib[attr].max_index); 620 } 621 622 src = tg->attrib[attr].input_ptr + 623 (ptrdiff_t)tg->attrib[attr].input_stride * index; 624 625 copy_size = tg->attrib[attr].copy_size; 626 if (likely(copy_size >= 0)) { 627 memcpy(dst, src, copy_size); 628 } else { 629 tg->attrib[attr].fetch(data, src, 0, 0); 630 631 if (0) 632 debug_printf("Fetch linear attr %d from %p stride %d index %d: " 633 " %f, %f, %f, %f \n", 634 attr, 635 tg->attrib[attr].input_ptr, 636 tg->attrib[attr].input_stride, 637 index, 638 data[0], data[1],data[2], data[3]); 639 640 tg->attrib[attr].emit(data, dst); 641 } 642 } else { 643 if (likely(tg->attrib[attr].copy_size >= 0)) { 644 memcpy(data, &instance_id, 4); 645 } else { 646 data[0] = (float)instance_id; 647 tg->attrib[attr].emit(data, dst); 648 } 649 } 650 } 651 } 652 653 /** 654 * Fetch vertex attributes for 'count' vertices. 655 */ 656 static void PIPE_CDECL 657 generic_run_elts(struct translate *translate, 658 const unsigned *elts, 659 unsigned count, 660 unsigned start_instance, 661 unsigned instance_id, 662 void *output_buffer) 663 { 664 struct translate_generic *tg = translate_generic(translate); 665 char *vert = output_buffer; 666 unsigned i; 667 668 for (i = 0; i < count; i++) { 669 generic_run_one(tg, *elts++, start_instance, instance_id, vert); 670 vert += tg->translate.key.output_stride; 671 } 672 } 673 674 static void PIPE_CDECL 675 generic_run_elts16(struct translate *translate, 676 const uint16_t *elts, 677 unsigned count, 678 unsigned start_instance, 679 unsigned instance_id, 680 void *output_buffer) 681 { 682 struct translate_generic *tg = translate_generic(translate); 683 char *vert = output_buffer; 684 unsigned i; 685 686 for (i = 0; i < count; i++) { 687 generic_run_one(tg, *elts++, start_instance, instance_id, vert); 688 vert += tg->translate.key.output_stride; 689 } 690 } 691 692 static void PIPE_CDECL 693 generic_run_elts8(struct translate *translate, 694 const uint8_t *elts, 695 unsigned count, 696 unsigned start_instance, 697 unsigned instance_id, 698 void *output_buffer) 699 { 700 struct translate_generic *tg = translate_generic(translate); 701 char *vert = output_buffer; 702 unsigned i; 703 704 for (i = 0; i < count; i++) { 705 generic_run_one(tg, *elts++, start_instance, instance_id, vert); 706 vert += tg->translate.key.output_stride; 707 } 708 } 709 710 static void PIPE_CDECL 711 generic_run(struct translate *translate, 712 unsigned start, 713 unsigned count, 714 unsigned start_instance, 715 unsigned instance_id, 716 void *output_buffer) 717 { 718 struct translate_generic *tg = translate_generic(translate); 719 char *vert = output_buffer; 720 unsigned i; 721 722 for (i = 0; i < count; i++) { 723 generic_run_one(tg, start + i, start_instance, instance_id, vert); 724 vert += tg->translate.key.output_stride; 725 } 726 } 727 728 729 730 static void 731 generic_set_buffer(struct translate *translate, 732 unsigned buf, 733 const void *ptr, 734 unsigned stride, 735 unsigned max_index) 736 { 737 struct translate_generic *tg = translate_generic(translate); 738 unsigned i; 739 740 for (i = 0; i < tg->nr_attrib; i++) { 741 if (tg->attrib[i].buffer == buf) { 742 tg->attrib[i].input_ptr = ((const uint8_t *)ptr + 743 tg->attrib[i].input_offset); 744 tg->attrib[i].input_stride = stride; 745 tg->attrib[i].max_index = max_index; 746 } 747 } 748 } 749 750 751 static void 752 generic_release(struct translate *translate) 753 { 754 /* Refcount? 755 */ 756 FREE(translate); 757 } 758 759 static boolean 760 is_legal_int_format_combo(const struct util_format_description *src, 761 const struct util_format_description *dst) 762 { 763 unsigned i; 764 unsigned nr = MIN2(src->nr_channels, dst->nr_channels); 765 766 for (i = 0; i < nr; i++) { 767 /* The signs must match. */ 768 if (src->channel[i].type != dst->channel[i].type) { 769 return FALSE; 770 } 771 772 /* Integers must not lose precision at any point in the pipeline. */ 773 if (src->channel[i].size > dst->channel[i].size) { 774 return FALSE; 775 } 776 } 777 return TRUE; 778 } 779 780 struct translate * 781 translate_generic_create(const struct translate_key *key) 782 { 783 struct translate_generic *tg = CALLOC_STRUCT(translate_generic); 784 unsigned i; 785 786 if (!tg) 787 return NULL; 788 789 assert(key->nr_elements <= TRANSLATE_MAX_ATTRIBS); 790 791 tg->translate.key = *key; 792 tg->translate.release = generic_release; 793 tg->translate.set_buffer = generic_set_buffer; 794 tg->translate.run_elts = generic_run_elts; 795 tg->translate.run_elts16 = generic_run_elts16; 796 tg->translate.run_elts8 = generic_run_elts8; 797 tg->translate.run = generic_run; 798 799 for (i = 0; i < key->nr_elements; i++) { 800 const struct util_format_description *format_desc = 801 util_format_description(key->element[i].input_format); 802 803 assert(format_desc); 804 805 tg->attrib[i].type = key->element[i].type; 806 807 if (format_desc->channel[0].pure_integer) { 808 const struct util_format_description *out_format_desc = 809 util_format_description(key->element[i].output_format); 810 811 if (!is_legal_int_format_combo(format_desc, out_format_desc)) { 812 FREE(tg); 813 return NULL; 814 } 815 816 if (format_desc->channel[0].type == UTIL_FORMAT_TYPE_SIGNED) { 817 assert(format_desc->fetch_rgba_sint); 818 tg->attrib[i].fetch = (fetch_func)format_desc->fetch_rgba_sint; 819 } else { 820 assert(format_desc->fetch_rgba_uint); 821 tg->attrib[i].fetch = (fetch_func)format_desc->fetch_rgba_uint; 822 } 823 } else { 824 assert(format_desc->fetch_rgba_float); 825 tg->attrib[i].fetch = (fetch_func)format_desc->fetch_rgba_float; 826 } 827 828 tg->attrib[i].buffer = key->element[i].input_buffer; 829 tg->attrib[i].input_offset = key->element[i].input_offset; 830 tg->attrib[i].instance_divisor = key->element[i].instance_divisor; 831 832 tg->attrib[i].output_offset = key->element[i].output_offset; 833 834 tg->attrib[i].copy_size = -1; 835 if (tg->attrib[i].type == TRANSLATE_ELEMENT_INSTANCE_ID) { 836 if (key->element[i].output_format == PIPE_FORMAT_R32_USCALED 837 || key->element[i].output_format == PIPE_FORMAT_R32_SSCALED) 838 tg->attrib[i].copy_size = 4; 839 } else { 840 if (key->element[i].input_format == key->element[i].output_format 841 && format_desc->block.width == 1 842 && format_desc->block.height == 1 843 && !(format_desc->block.bits & 7)) 844 tg->attrib[i].copy_size = format_desc->block.bits >> 3; 845 } 846 847 if (tg->attrib[i].copy_size < 0) 848 tg->attrib[i].emit = get_emit_func(key->element[i].output_format); 849 else 850 tg->attrib[i].emit = NULL; 851 } 852 853 tg->nr_attrib = key->nr_elements; 854 855 return &tg->translate; 856 } 857 858 boolean 859 translate_generic_is_output_format_supported(enum pipe_format format) 860 { 861 switch(format) { 862 case PIPE_FORMAT_R64G64B64A64_FLOAT: return TRUE; 863 case PIPE_FORMAT_R64G64B64_FLOAT: return TRUE; 864 case PIPE_FORMAT_R64G64_FLOAT: return TRUE; 865 case PIPE_FORMAT_R64_FLOAT: return TRUE; 866 867 case PIPE_FORMAT_R32G32B32A32_FLOAT: return TRUE; 868 case PIPE_FORMAT_R32G32B32_FLOAT: return TRUE; 869 case PIPE_FORMAT_R32G32_FLOAT: return TRUE; 870 case PIPE_FORMAT_R32_FLOAT: return TRUE; 871 872 case PIPE_FORMAT_R16G16B16A16_FLOAT: return TRUE; 873 case PIPE_FORMAT_R16G16B16_FLOAT: return TRUE; 874 case PIPE_FORMAT_R16G16_FLOAT: return TRUE; 875 case PIPE_FORMAT_R16_FLOAT: return TRUE; 876 877 case PIPE_FORMAT_R32G32B32A32_USCALED: return TRUE; 878 case PIPE_FORMAT_R32G32B32_USCALED: return TRUE; 879 case PIPE_FORMAT_R32G32_USCALED: return TRUE; 880 case PIPE_FORMAT_R32_USCALED: return TRUE; 881 882 case PIPE_FORMAT_R32G32B32A32_SSCALED: return TRUE; 883 case PIPE_FORMAT_R32G32B32_SSCALED: return TRUE; 884 case PIPE_FORMAT_R32G32_SSCALED: return TRUE; 885 case PIPE_FORMAT_R32_SSCALED: return TRUE; 886 887 case PIPE_FORMAT_R32G32B32A32_UNORM: return TRUE; 888 case PIPE_FORMAT_R32G32B32_UNORM: return TRUE; 889 case PIPE_FORMAT_R32G32_UNORM: return TRUE; 890 case PIPE_FORMAT_R32_UNORM: return TRUE; 891 892 case PIPE_FORMAT_R32G32B32A32_SNORM: return TRUE; 893 case PIPE_FORMAT_R32G32B32_SNORM: return TRUE; 894 case PIPE_FORMAT_R32G32_SNORM: return TRUE; 895 case PIPE_FORMAT_R32_SNORM: return TRUE; 896 897 case PIPE_FORMAT_R16G16B16A16_USCALED: return TRUE; 898 case PIPE_FORMAT_R16G16B16_USCALED: return TRUE; 899 case PIPE_FORMAT_R16G16_USCALED: return TRUE; 900 case PIPE_FORMAT_R16_USCALED: return TRUE; 901 902 case PIPE_FORMAT_R16G16B16A16_SSCALED: return TRUE; 903 case PIPE_FORMAT_R16G16B16_SSCALED: return TRUE; 904 case PIPE_FORMAT_R16G16_SSCALED: return TRUE; 905 case PIPE_FORMAT_R16_SSCALED: return TRUE; 906 907 case PIPE_FORMAT_R16G16B16A16_UNORM: return TRUE; 908 case PIPE_FORMAT_R16G16B16_UNORM: return TRUE; 909 case PIPE_FORMAT_R16G16_UNORM: return TRUE; 910 case PIPE_FORMAT_R16_UNORM: return TRUE; 911 912 case PIPE_FORMAT_R16G16B16A16_SNORM: return TRUE; 913 case PIPE_FORMAT_R16G16B16_SNORM: return TRUE; 914 case PIPE_FORMAT_R16G16_SNORM: return TRUE; 915 case PIPE_FORMAT_R16_SNORM: return TRUE; 916 917 case PIPE_FORMAT_R8G8B8A8_USCALED: return TRUE; 918 case PIPE_FORMAT_R8G8B8_USCALED: return TRUE; 919 case PIPE_FORMAT_R8G8_USCALED: return TRUE; 920 case PIPE_FORMAT_R8_USCALED: return TRUE; 921 922 case PIPE_FORMAT_R8G8B8A8_SSCALED: return TRUE; 923 case PIPE_FORMAT_R8G8B8_SSCALED: return TRUE; 924 case PIPE_FORMAT_R8G8_SSCALED: return TRUE; 925 case PIPE_FORMAT_R8_SSCALED: return TRUE; 926 927 case PIPE_FORMAT_R8G8B8A8_UNORM: return TRUE; 928 case PIPE_FORMAT_R8G8B8_UNORM: return TRUE; 929 case PIPE_FORMAT_R8G8_UNORM: return TRUE; 930 case PIPE_FORMAT_R8_UNORM: return TRUE; 931 932 case PIPE_FORMAT_R8G8B8A8_SNORM: return TRUE; 933 case PIPE_FORMAT_R8G8B8_SNORM: return TRUE; 934 case PIPE_FORMAT_R8G8_SNORM: return TRUE; 935 case PIPE_FORMAT_R8_SNORM: return TRUE; 936 937 case PIPE_FORMAT_A8R8G8B8_UNORM: return TRUE; 938 case PIPE_FORMAT_B8G8R8A8_UNORM: return TRUE; 939 940 case PIPE_FORMAT_R32G32B32A32_UINT: return TRUE; 941 case PIPE_FORMAT_R32G32B32_UINT: return TRUE; 942 case PIPE_FORMAT_R32G32_UINT: return TRUE; 943 case PIPE_FORMAT_R32_UINT: return TRUE; 944 945 case PIPE_FORMAT_R16G16B16A16_UINT: return TRUE; 946 case PIPE_FORMAT_R16G16B16_UINT: return TRUE; 947 case PIPE_FORMAT_R16G16_UINT: return TRUE; 948 case PIPE_FORMAT_R16_UINT: return TRUE; 949 950 case PIPE_FORMAT_R8G8B8A8_UINT: return TRUE; 951 case PIPE_FORMAT_R8G8B8_UINT: return TRUE; 952 case PIPE_FORMAT_R8G8_UINT: return TRUE; 953 case PIPE_FORMAT_R8_UINT: return TRUE; 954 955 case PIPE_FORMAT_R32G32B32A32_SINT: return TRUE; 956 case PIPE_FORMAT_R32G32B32_SINT: return TRUE; 957 case PIPE_FORMAT_R32G32_SINT: return TRUE; 958 case PIPE_FORMAT_R32_SINT: return TRUE; 959 960 case PIPE_FORMAT_R16G16B16A16_SINT: return TRUE; 961 case PIPE_FORMAT_R16G16B16_SINT: return TRUE; 962 case PIPE_FORMAT_R16G16_SINT: return TRUE; 963 case PIPE_FORMAT_R16_SINT: return TRUE; 964 965 case PIPE_FORMAT_R8G8B8A8_SINT: return TRUE; 966 case PIPE_FORMAT_R8G8B8_SINT: return TRUE; 967 case PIPE_FORMAT_R8G8_SINT: return TRUE; 968 case PIPE_FORMAT_R8_SINT: return TRUE; 969 970 case PIPE_FORMAT_B10G10R10A2_UNORM: return TRUE; 971 case PIPE_FORMAT_B10G10R10A2_USCALED: return TRUE; 972 case PIPE_FORMAT_B10G10R10A2_SNORM: return TRUE; 973 case PIPE_FORMAT_B10G10R10A2_SSCALED: return TRUE; 974 975 case PIPE_FORMAT_R10G10B10A2_UNORM: return TRUE; 976 case PIPE_FORMAT_R10G10B10A2_USCALED: return TRUE; 977 case PIPE_FORMAT_R10G10B10A2_SNORM: return TRUE; 978 case PIPE_FORMAT_R10G10B10A2_SSCALED: return TRUE; 979 980 default: return FALSE; 981 } 982 } 983