gallivm: Allow to force nearest filtering on a per-axis basis.
authorJosé Fonseca <jfonseca@vmware.com>
Fri, 13 Jul 2012 17:27:43 +0000 (18:27 +0100)
committerJosé Fonseca <jfonseca@vmware.com>
Tue, 17 Jul 2012 12:42:39 +0000 (13:42 +0100)
Experimental code, not really used yet.

src/gallium/auxiliary/gallivm/lp_bld_sample.h
src/gallium/auxiliary/gallivm/lp_bld_sample_aos.c

index 8ccba2ca09ebffdb23ae2c0d8ab6d8e56f93683b..dad138abee00a0c1a483b487d6e444d669d6d83f 100644 (file)
@@ -86,6 +86,10 @@ struct lp_sampler_static_state
    unsigned lod_bias_non_zero:1;
    unsigned apply_min_lod:1;  /**< min_lod > 0 ? */
    unsigned apply_max_lod:1;  /**< max_lod < last_level ? */
+
+   /* Hacks */
+   unsigned force_nearest_s:1;
+   unsigned force_nearest_t:1;
 };
 
 
index 423f290e04b3e20e05311224a334c86444adb48f..74858bc9718b19c5c2ca440fb1ae1d863466a0e0 100644 (file)
@@ -498,8 +498,10 @@ lp_build_sample_image_linear(struct lp_build_sample_context *bld,
 
    /* subtract 0.5 (add -128) */
    i32_c128 = lp_build_const_int_vec(bld->gallivm, i32.type, -128);
-   s = LLVMBuildAdd(builder, s, i32_c128, "");
-   if (dims >= 2) {
+   if (!bld->static_state->force_nearest_s) {
+      s = LLVMBuildAdd(builder, s, i32_c128, "");
+   }
+   if (dims >= 2 && !bld->static_state->force_nearest_t) {
       t = LLVMBuildAdd(builder, t, i32_c128, "");
    }
    if (dims >= 3) {
@@ -716,56 +718,82 @@ lp_build_sample_image_linear(struct lp_build_sample_context *bld,
    /*
     * Linear interpolation with 8.8 fixed point.
     */
-   if (dims == 1) {
-      /* 1-D lerp */
+   if (bld->static_state->force_nearest_s) {
+      /* special case 1-D lerp */
       packed_lo = lp_build_lerp(&h16,
-                               s_fpart_lo,
-                               neighbors_lo[0][0][0],
-                               neighbors_lo[0][0][1]);
+                                t_fpart_lo,
+                                neighbors_lo[0][0][0],
+                                neighbors_lo[0][0][1]);
 
       packed_hi = lp_build_lerp(&h16,
-                               s_fpart_hi,
-                               neighbors_hi[0][0][0],
-                               neighbors_hi[0][0][1]);
+                                t_fpart_hi,
+                                neighbors_hi[0][1][0],
+                                neighbors_hi[0][1][0]);
    }
-   else {
-      /* 2-D lerp */
-      packed_lo = lp_build_lerp_2d(&h16,
-                                  s_fpart_lo, t_fpart_lo,
-                                  neighbors_lo[0][0][0],
-                                  neighbors_lo[0][0][1],
-                                  neighbors_lo[0][1][0],
-                                  neighbors_lo[0][1][1]);
-
-      packed_hi = lp_build_lerp_2d(&h16,
-                                  s_fpart_hi, t_fpart_hi,
-                                  neighbors_hi[0][0][0],
-                                  neighbors_hi[0][0][1],
-                                  neighbors_hi[0][1][0],
-                                  neighbors_hi[0][1][1]);
+   else if (bld->static_state->force_nearest_t) {
+      /* special case 1-D lerp */
+      packed_lo = lp_build_lerp(&h16,
+                                s_fpart_lo,
+                                neighbors_lo[0][0][0],
+                                neighbors_lo[0][0][1]);
 
-      if (dims >= 3) {
-        LLVMValueRef packed_lo2, packed_hi2;
-
-        /* lerp in the second z slice */
-        packed_lo2 = lp_build_lerp_2d(&h16,
-                                      s_fpart_lo, t_fpart_lo,
-                                      neighbors_lo[1][0][0],
-                                      neighbors_lo[1][0][1],
-                                      neighbors_lo[1][1][0],
-                                      neighbors_lo[1][1][1]);
-
-        packed_hi2 = lp_build_lerp_2d(&h16,
-                                      s_fpart_hi, t_fpart_hi,
-                                      neighbors_hi[1][0][0],
-                                      neighbors_hi[1][0][1],
-                                      neighbors_hi[1][1][0],
-                                      neighbors_hi[1][1][1]);
-        /* interp between two z slices */
-        packed_lo = lp_build_lerp(&h16, r_fpart_lo,
-                                  packed_lo, packed_lo2);
-        packed_hi = lp_build_lerp(&h16, r_fpart_hi,
-                                  packed_hi, packed_hi2);
+      packed_hi = lp_build_lerp(&h16,
+                                s_fpart_hi,
+                                neighbors_hi[0][0][0],
+                                neighbors_hi[0][0][1]);
+   }
+   else {
+      /* general 1/2/3-D lerping */
+      if (dims == 1) {
+         packed_lo = lp_build_lerp(&h16,
+                                   s_fpart_lo,
+                                   neighbors_lo[0][0][0],
+                                   neighbors_lo[0][0][1]);
+
+         packed_hi = lp_build_lerp(&h16,
+                                   s_fpart_hi,
+                                   neighbors_hi[0][0][0],
+                                   neighbors_hi[0][0][1]);
+      }
+      else {
+         /* 2-D lerp */
+         packed_lo = lp_build_lerp_2d(&h16,
+                                      s_fpart_lo, t_fpart_lo,
+                                      neighbors_lo[0][0][0],
+                                      neighbors_lo[0][0][1],
+                                      neighbors_lo[0][1][0],
+                                      neighbors_lo[0][1][1]);
+
+         packed_hi = lp_build_lerp_2d(&h16,
+                                      s_fpart_hi, t_fpart_hi,
+                                      neighbors_hi[0][0][0],
+                                      neighbors_hi[0][0][1],
+                                      neighbors_hi[0][1][0],
+                                      neighbors_hi[0][1][1]);
+
+         if (dims >= 3) {
+            LLVMValueRef packed_lo2, packed_hi2;
+
+            /* lerp in the second z slice */
+            packed_lo2 = lp_build_lerp_2d(&h16,
+                                          s_fpart_lo, t_fpart_lo,
+                                          neighbors_lo[1][0][0],
+                                          neighbors_lo[1][0][1],
+                                          neighbors_lo[1][1][0],
+                                          neighbors_lo[1][1][1]);
+
+            packed_hi2 = lp_build_lerp_2d(&h16,
+                                          s_fpart_hi, t_fpart_hi,
+                                          neighbors_hi[1][0][0],
+                                          neighbors_hi[1][0][1],
+                                          neighbors_hi[1][1][0],
+                                          neighbors_hi[1][1][1]);
+            /* interp between two z slices */
+            packed_lo = lp_build_lerp(&h16, r_fpart_lo,
+                                      packed_lo, packed_lo2);
+            packed_hi = lp_build_lerp(&h16, r_fpart_hi,
+                                      packed_hi, packed_hi2);
+         }
       }
    }