~ubuntu-branches/ubuntu/natty/mesa/natty-proposed

« back to all changes in this revision

Viewing changes to src/gallium/auxiliary/gallivm/lp_bld_pack.c

  • Committer: Bazaar Package Importer
  • Author(s): Robert Hooker, Robert Hooker, Christopher James Halse Rogers
  • Date: 2010-09-14 08:55:40 UTC
  • mfrom: (1.2.28 upstream)
  • Revision ID: james.westby@ubuntu.com-20100914085540-m4fpl0hdjlfd4jgz
Tags: 7.9~git20100909-0ubuntu1
[ Robert Hooker ]
* New upstream git snapshot up to commit 94118fe2d4b1e5 (LP: #631413)
* New features include ATI HD5xxx series support in r600, and a vastly
  improved glsl compiler.
* Remove pre-generated .pc's, use the ones generated at build time
  instead.
* Remove all references to mesa-utils now that its no longer shipped
  with the mesa source.
* Disable the experimental ARB_fragment_shader option by default on
  i915, it exposes incomplete functionality that breaks KDE compositing
  among other things. It can be enabled via driconf still. (LP: #628930).

[ Christopher James Halse Rogers ]
* debian/patches/04_osmesa_version.diff:
  - Refresh for new upstream
* Bugs fixed in this release:
  - Fixes severe rendering corruption in Unity on radeon (LP: #628727,
    LP: #596292, LP: #599741, LP: #630315, LP: #613694, LP: #599741).
  - Also fixes rendering in gnome-shell (LP: #578619).
  - Flickering in OpenGL apps on radeon (LP: #626943, LP: #610541).
  - Provides preliminary support for new intel chips (LP: #601052).
* debian/rules:
  - Update configure flags to match upstream reshuffling.
  - Explicitly remove gallium DRI drivers that we don't want to ship.
* Update debian/gbp.conf for this Maverick-specific packaging
* libegl1-mesa-dri-x11,kms: There are no longer separate kms or x11 drivers
  for EGL, libegl1-mesa-drivers now contains a single driver that provides
  both backends.

Show diffs side-by-side

added added

removed removed

Lines of Context:
164
164
 
165
165
   if(dst_type.sign && src_type.sign) {
166
166
      /* Replicate the sign bit in the most significant bits */
167
 
      msb = LLVMBuildAShr(builder, src, lp_build_int_const_scalar(src_type, src_type.width - 1), "");
 
167
      msb = LLVMBuildAShr(builder, src, lp_build_const_int_vec(src_type, src_type.width - 1), "");
168
168
   }
169
169
   else
170
170
      /* Most significant bits always zero */
171
171
      msb = lp_build_zero(src_type);
172
172
 
173
173
   /* Interleave bits */
174
 
   if(util_cpu_caps.little_endian) {
 
174
#ifdef PIPE_ARCH_LITTLE_ENDIAN
175
175
      *dst_lo = lp_build_interleave2(builder, src_type, src, msb, 0);
176
176
      *dst_hi = lp_build_interleave2(builder, src_type, src, msb, 1);
177
 
   }
178
 
   else {
 
177
#else
179
178
      *dst_lo = lp_build_interleave2(builder, src_type, msb, src, 0);
180
179
      *dst_hi = lp_build_interleave2(builder, src_type, msb, src, 1);
181
 
   }
 
180
#endif
182
181
 
183
182
   /* Cast the result into the new type (twice as wide) */
184
183
 
256
255
               LLVMValueRef lo,
257
256
               LLVMValueRef hi)
258
257
{
 
258
#if HAVE_LLVM < 0x0207
259
259
   LLVMTypeRef src_vec_type = lp_build_vec_type(src_type);
 
260
#endif
260
261
   LLVMTypeRef dst_vec_type = lp_build_vec_type(dst_type);
261
262
   LLVMValueRef shuffle;
262
 
   LLVMValueRef res;
263
 
 
264
 
   dst_vec_type = lp_build_vec_type(dst_type);
 
263
   LLVMValueRef res = NULL;
265
264
 
266
265
   assert(!src_type.floating);
267
266
   assert(!dst_type.floating);
268
267
   assert(src_type.width == dst_type.width * 2);
269
268
   assert(src_type.length * 2 == dst_type.length);
270
269
 
 
270
   /* Check for special cases first */
271
271
   if(util_cpu_caps.has_sse2 && src_type.width * src_type.length == 128) {
272
272
      switch(src_type.width) {
273
273
      case 32:
274
274
         if(dst_type.sign) {
 
275
#if HAVE_LLVM >= 0x0207
 
276
            res = lp_build_intrinsic_binary(builder, "llvm.x86.sse2.packssdw.128", dst_vec_type, lo, hi);
 
277
#else
275
278
            res = lp_build_intrinsic_binary(builder, "llvm.x86.sse2.packssdw.128", src_vec_type, lo, hi);
 
279
#endif
276
280
         }
277
281
         else {
278
282
            if (util_cpu_caps.has_sse4_1) {
279
 
               /* PACKUSDW is the only instrinsic with a consistent signature */
280
283
               return lp_build_intrinsic_binary(builder, "llvm.x86.sse41.packusdw", dst_vec_type, lo, hi);
281
284
            }
282
285
            else {
283
 
               assert(0);
284
 
               return LLVMGetUndef(dst_vec_type);
 
286
               /* use generic shuffle below */
 
287
               res = NULL;
285
288
            }
286
289
         }
287
290
         break;
288
291
 
289
292
      case 16:
290
293
         if(dst_type.sign)
 
294
#if HAVE_LLVM >= 0x0207
 
295
            res = lp_build_intrinsic_binary(builder, "llvm.x86.sse2.packsswb.128", dst_vec_type, lo, hi);
 
296
#else
291
297
            res = lp_build_intrinsic_binary(builder, "llvm.x86.sse2.packsswb.128", src_vec_type, lo, hi);
 
298
#endif
292
299
         else
 
300
#if HAVE_LLVM >= 0x0207
 
301
            res = lp_build_intrinsic_binary(builder, "llvm.x86.sse2.packuswb.128", dst_vec_type, lo, hi);
 
302
#else
293
303
            res = lp_build_intrinsic_binary(builder, "llvm.x86.sse2.packuswb.128", src_vec_type, lo, hi);
 
304
#endif
294
305
         break;
295
306
 
296
307
      default:
299
310
         break;
300
311
      }
301
312
 
302
 
      res = LLVMBuildBitCast(builder, res, dst_vec_type, "");
303
 
      return res;
 
313
      if (res) {
 
314
         res = LLVMBuildBitCast(builder, res, dst_vec_type, "");
 
315
         return res;
 
316
      }
304
317
   }
305
318
 
 
319
   /* generic shuffle */
306
320
   lo = LLVMBuildBitCast(builder, lo, dst_vec_type, "");
307
321
   hi = LLVMBuildBitCast(builder, hi, dst_vec_type, "");
308
322
 
348
362
   if(clamp) {
349
363
      struct lp_build_context bld;
350
364
      unsigned dst_bits = dst_type.sign ? dst_type.width - 1 : dst_type.width;
351
 
      LLVMValueRef dst_max = lp_build_int_const_scalar(src_type, ((unsigned long long)1 << dst_bits) - 1);
 
365
      LLVMValueRef dst_max = lp_build_const_int_vec(src_type, ((unsigned long long)1 << dst_bits) - 1);
352
366
      lp_build_context_init(&bld, builder, src_type);
353
367
      lo = lp_build_min(&bld, lo, dst_max);
354
368
      hi = lp_build_min(&bld, hi, dst_max);
416
430
 
417
431
   return tmp[0];
418
432
}
 
433
 
 
434
 
 
435
/**
 
436
 * Truncate or expand the bitwidth.
 
437
 *
 
438
 * NOTE: Getting the right sign flags is crucial here, as we employ some
 
439
 * intrinsics that do saturation.
 
440
 */
 
441
void
 
442
lp_build_resize(LLVMBuilderRef builder,
 
443
                struct lp_type src_type,
 
444
                struct lp_type dst_type,
 
445
                const LLVMValueRef *src, unsigned num_srcs,
 
446
                LLVMValueRef *dst, unsigned num_dsts)
 
447
{
 
448
   LLVMValueRef tmp[LP_MAX_VECTOR_LENGTH];
 
449
   unsigned i;
 
450
 
 
451
   /*
 
452
    * We don't support float <-> int conversion here. That must be done
 
453
    * before/after calling this function.
 
454
    */
 
455
   assert(src_type.floating == dst_type.floating);
 
456
 
 
457
   /*
 
458
    * We don't support double <-> float conversion yet, although it could be
 
459
    * added with little effort.
 
460
    */
 
461
   assert((!src_type.floating && !dst_type.floating) ||
 
462
          src_type.width == dst_type.width);
 
463
 
 
464
   /* We must not loose or gain channels. Only precision */
 
465
   assert(src_type.length * num_srcs == dst_type.length * num_dsts);
 
466
 
 
467
   /* We don't support M:N conversion, only 1:N, M:1, or 1:1 */
 
468
   assert(num_srcs == 1 || num_dsts == 1);
 
469
 
 
470
   assert(src_type.length <= LP_MAX_VECTOR_LENGTH);
 
471
   assert(dst_type.length <= LP_MAX_VECTOR_LENGTH);
 
472
   assert(num_srcs <= LP_MAX_VECTOR_LENGTH);
 
473
   assert(num_dsts <= LP_MAX_VECTOR_LENGTH);
 
474
 
 
475
   if (src_type.width > dst_type.width) {
 
476
      /*
 
477
       * Truncate bit width.
 
478
       */
 
479
 
 
480
      assert(num_dsts == 1);
 
481
 
 
482
      if (src_type.width * src_type.length == dst_type.width * dst_type.length) {
 
483
        /*
 
484
         * Register width remains constant -- use vector packing intrinsics
 
485
         */
 
486
 
 
487
         tmp[0] = lp_build_pack(builder, src_type, dst_type, TRUE, src, num_srcs);
 
488
      }
 
489
      else {
 
490
         /*
 
491
          * Do it element-wise.
 
492
          */
 
493
 
 
494
         assert(src_type.length == dst_type.length);
 
495
         tmp[0] = lp_build_undef(dst_type);
 
496
         for (i = 0; i < dst_type.length; ++i) {
 
497
            LLVMValueRef index = LLVMConstInt(LLVMInt32Type(), i, 0);
 
498
            LLVMValueRef val = LLVMBuildExtractElement(builder, src[0], index, "");
 
499
            val = LLVMBuildTrunc(builder, val, lp_build_elem_type(dst_type), "");
 
500
            tmp[0] = LLVMBuildInsertElement(builder, tmp[0], val, index, "");
 
501
         }
 
502
      }
 
503
   }
 
504
   else if (src_type.width < dst_type.width) {
 
505
      /*
 
506
       * Expand bit width.
 
507
       */
 
508
 
 
509
      assert(num_srcs == 1);
 
510
 
 
511
      if (src_type.width * src_type.length == dst_type.width * dst_type.length) {
 
512
         /*
 
513
          * Register width remains constant -- use vector unpack intrinsics
 
514
          */
 
515
         lp_build_unpack(builder, src_type, dst_type, src[0], tmp, num_dsts);
 
516
      }
 
517
      else {
 
518
         /*
 
519
          * Do it element-wise.
 
520
          */
 
521
 
 
522
         assert(src_type.length == dst_type.length);
 
523
         tmp[0] = lp_build_undef(dst_type);
 
524
         for (i = 0; i < dst_type.length; ++i) {
 
525
            LLVMValueRef index = LLVMConstInt(LLVMInt32Type(), i, 0);
 
526
            LLVMValueRef val = LLVMBuildExtractElement(builder, src[0], index, "");
 
527
 
 
528
            if (src_type.sign && dst_type.sign) {
 
529
               val = LLVMBuildSExt(builder, val, lp_build_elem_type(dst_type), "");
 
530
            } else {
 
531
               val = LLVMBuildZExt(builder, val, lp_build_elem_type(dst_type), "");
 
532
            }
 
533
            tmp[0] = LLVMBuildInsertElement(builder, tmp[0], val, index, "");
 
534
         }
 
535
      }
 
536
   }
 
537
   else {
 
538
      /*
 
539
       * No-op
 
540
       */
 
541
 
 
542
      assert(num_srcs == 1);
 
543
      assert(num_dsts == 1);
 
544
 
 
545
      tmp[0] = src[0];
 
546
   }
 
547
 
 
548
   for(i = 0; i < num_dsts; ++i)
 
549
      dst[i] = tmp[i];
 
550
}
 
551
 
 
552