Tizen 2.0 Release
[profile/ivi/osmesa.git] / src / gallium / auxiliary / gallivm / lp_bld_sample.h
1 /**************************************************************************
2  *
3  * Copyright 2009 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  * @file
30  * Texture sampling.
31  *
32  * @author Jose Fonseca <jfonseca@vmware.com>
33  */
34
35 #ifndef LP_BLD_SAMPLE_H
36 #define LP_BLD_SAMPLE_H
37
38
39 #include "pipe/p_format.h"
40 #include "util/u_debug.h"
41 #include "gallivm/lp_bld.h"
42 #include "gallivm/lp_bld_type.h"
43 #include "gallivm/lp_bld_swizzle.h"
44
45
46 struct pipe_resource;
47 struct pipe_sampler_view;
48 struct pipe_sampler_state;
49 struct util_format_description;
50 struct lp_type;
51 struct lp_build_context;
52
53
54 /**
55  * Sampler static state.
56  *
57  * These are the bits of state from pipe_resource and pipe_sampler_state that
58  * are embedded in the generated code.
59  */
60 struct lp_sampler_static_state
61 {
62    /* pipe_sampler_view's state */
63    enum pipe_format format;
64    unsigned swizzle_r:3;     /**< PIPE_SWIZZLE_* */
65    unsigned swizzle_g:3;
66    unsigned swizzle_b:3;
67    unsigned swizzle_a:3;
68
69    /* pipe_texture's state */
70    unsigned target:3;        /**< PIPE_TEXTURE_* */
71    unsigned pot_width:1;     /**< is the width a power of two? */
72    unsigned pot_height:1;
73    unsigned pot_depth:1;
74
75    /* pipe_sampler_state's state */
76    unsigned wrap_s:3;
77    unsigned wrap_t:3;
78    unsigned wrap_r:3;
79    unsigned min_img_filter:2;
80    unsigned min_mip_filter:2;
81    unsigned mag_img_filter:2;
82    unsigned compare_mode:1;
83    unsigned compare_func:3;
84    unsigned normalized_coords:1;
85    unsigned min_max_lod_equal:1;  /**< min_lod == max_lod ? */
86    unsigned lod_bias_non_zero:1;
87    unsigned apply_min_lod:1;  /**< min_lod > 0 ? */
88    unsigned apply_max_lod:1;  /**< max_lod < last_level ? */
89 };
90
91
92 /**
93  * Sampler dynamic state.
94  *
95  * These are the bits of state from pipe_resource and pipe_sampler_state that
96  * are computed in runtime.
97  *
98  * There are obtained through callbacks, as we don't want to tie the texture
99  * sampling code generation logic to any particular texture layout or pipe
100  * driver.
101  */
102 struct lp_sampler_dynamic_state
103 {
104
105    /** Obtain the base texture width (returns int32) */
106    LLVMValueRef
107    (*width)( const struct lp_sampler_dynamic_state *state,
108              struct gallivm_state *gallivm,
109              unsigned unit);
110
111    /** Obtain the base texture height (returns int32) */
112    LLVMValueRef
113    (*height)( const struct lp_sampler_dynamic_state *state,
114               struct gallivm_state *gallivm,
115               unsigned unit);
116
117    /** Obtain the base texture depth (returns int32) */
118    LLVMValueRef
119    (*depth)( const struct lp_sampler_dynamic_state *state,
120              struct gallivm_state *gallivm,
121              unsigned unit);
122
123    /** Obtain the first mipmap level (base level) (returns int32) */
124    LLVMValueRef
125    (*first_level)( const struct lp_sampler_dynamic_state *state,
126                    struct gallivm_state *gallivm,
127                    unsigned unit);
128
129    /** Obtain the number of mipmap levels minus one (returns int32) */
130    LLVMValueRef
131    (*last_level)( const struct lp_sampler_dynamic_state *state,
132                   struct gallivm_state *gallivm,
133                   unsigned unit);
134
135    /** Obtain stride in bytes between image rows/blocks (returns int32) */
136    LLVMValueRef
137    (*row_stride)( const struct lp_sampler_dynamic_state *state,
138                   struct gallivm_state *gallivm,
139                   unsigned unit);
140
141    /** Obtain stride in bytes between image slices (returns int32) */
142    LLVMValueRef
143    (*img_stride)( const struct lp_sampler_dynamic_state *state,
144                   struct gallivm_state *gallivm,
145                   unsigned unit);
146
147    /** Obtain pointer to array of pointers to mimpap levels */
148    LLVMValueRef
149    (*data_ptr)( const struct lp_sampler_dynamic_state *state,
150                 struct gallivm_state *gallivm,
151                 unsigned unit);
152
153    /** Obtain texture min lod (returns float) */
154    LLVMValueRef
155    (*min_lod)(const struct lp_sampler_dynamic_state *state,
156               struct gallivm_state *gallivm, unsigned unit);
157
158    /** Obtain texture max lod (returns float) */
159    LLVMValueRef
160    (*max_lod)(const struct lp_sampler_dynamic_state *state,
161               struct gallivm_state *gallivm, unsigned unit);
162
163    /** Obtain texture lod bias (returns float) */
164    LLVMValueRef
165    (*lod_bias)(const struct lp_sampler_dynamic_state *state,
166                struct gallivm_state *gallivm, unsigned unit);
167
168    /** Obtain texture border color (returns ptr to float[4]) */
169    LLVMValueRef
170    (*border_color)(const struct lp_sampler_dynamic_state *state,
171                    struct gallivm_state *gallivm, unsigned unit);
172 };
173
174
175 /**
176  * Keep all information for sampling code generation in a single place.
177  */
178 struct lp_build_sample_context
179 {
180    struct gallivm_state *gallivm;
181
182    const struct lp_sampler_static_state *static_state;
183
184    struct lp_sampler_dynamic_state *dynamic_state;
185
186    const struct util_format_description *format_desc;
187
188    /* See texture_dims() */
189    unsigned dims;
190
191    /** regular scalar float type */
192    struct lp_type float_type;
193    struct lp_build_context float_bld;
194
195    /** float vector type */
196    struct lp_build_context float_vec_bld;
197
198    /** regular scalar float type */
199    struct lp_type int_type;
200    struct lp_build_context int_bld;
201
202    /** Incoming coordinates type and build context */
203    struct lp_type coord_type;
204    struct lp_build_context coord_bld;
205
206    /** Signed integer coordinates */
207    struct lp_type int_coord_type;
208    struct lp_build_context int_coord_bld;
209
210    /** Unsigned integer texture size */
211    struct lp_type int_size_type;
212    struct lp_build_context int_size_bld;
213
214    /** Unsigned integer texture size */
215    struct lp_type float_size_type;
216    struct lp_build_context float_size_bld;
217
218    /** Output texels type and build context */
219    struct lp_type texel_type;
220    struct lp_build_context texel_bld;
221
222    /* Common dynamic state values */
223    LLVMValueRef width;
224    LLVMValueRef height;
225    LLVMValueRef depth;
226    LLVMValueRef row_stride_array;
227    LLVMValueRef img_stride_array;
228    LLVMValueRef data_array;
229
230    /** Integer vector with texture width, height, depth */
231    LLVMValueRef int_size;
232 };
233
234
235
236 /**
237  * We only support a few wrap modes in lp_build_sample_wrap_linear_int() at
238  * this time.  Return whether the given mode is supported by that function.
239  */
240 static INLINE boolean
241 lp_is_simple_wrap_mode(unsigned mode)
242 {
243    switch (mode) {
244    case PIPE_TEX_WRAP_REPEAT:
245    case PIPE_TEX_WRAP_CLAMP_TO_EDGE:
246       return TRUE;
247    default:
248       return FALSE;
249    }
250 }
251
252
253 static INLINE void
254 apply_sampler_swizzle(struct lp_build_sample_context *bld,
255                       LLVMValueRef *texel)
256 {
257    unsigned char swizzles[4];
258
259    swizzles[0] = bld->static_state->swizzle_r;
260    swizzles[1] = bld->static_state->swizzle_g;
261    swizzles[2] = bld->static_state->swizzle_b;
262    swizzles[3] = bld->static_state->swizzle_a;
263
264    lp_build_swizzle_soa_inplace(&bld->texel_bld, texel, swizzles);
265 }
266
267
268 static INLINE unsigned
269 texture_dims(enum pipe_texture_target tex)
270 {
271    switch (tex) {
272    case PIPE_TEXTURE_1D:
273       return 1;
274    case PIPE_TEXTURE_2D:
275    case PIPE_TEXTURE_RECT:
276    case PIPE_TEXTURE_CUBE:
277       return 2;
278    case PIPE_TEXTURE_3D:
279       return 3;
280    default:
281       assert(0 && "bad texture target in texture_dims()");
282       return 2;
283    }
284 }
285
286
287 boolean
288 lp_sampler_wrap_mode_uses_border_color(unsigned mode,
289                                        unsigned min_img_filter,
290                                        unsigned mag_img_filter);
291
292 /**
293  * Derive the sampler static state.
294  */
295 void
296 lp_sampler_static_state(struct lp_sampler_static_state *state,
297                         const struct pipe_sampler_view *view,
298                         const struct pipe_sampler_state *sampler);
299
300
301 void
302 lp_build_lod_selector(struct lp_build_sample_context *bld,
303                       unsigned unit,
304                       const LLVMValueRef ddx[4],
305                       const LLVMValueRef ddy[4],
306                       LLVMValueRef lod_bias, /* optional */
307                       LLVMValueRef explicit_lod, /* optional */
308                       unsigned mip_filter,
309                       LLVMValueRef *out_lod_ipart,
310                       LLVMValueRef *out_lod_fpart);
311
312 void
313 lp_build_nearest_mip_level(struct lp_build_sample_context *bld,
314                            unsigned unit,
315                            LLVMValueRef lod,
316                            LLVMValueRef *level_out);
317
318 void
319 lp_build_linear_mip_levels(struct lp_build_sample_context *bld,
320                            unsigned unit,
321                            LLVMValueRef lod_ipart,
322                            LLVMValueRef *lod_fpart_inout,
323                            LLVMValueRef *level0_out,
324                            LLVMValueRef *level1_out);
325
326 LLVMValueRef
327 lp_build_get_mipmap_level(struct lp_build_sample_context *bld,
328                           LLVMValueRef level);
329
330 LLVMValueRef
331 lp_build_get_const_mipmap_level(struct lp_build_sample_context *bld,
332                                 int level);
333
334
335 void
336 lp_build_mipmap_level_sizes(struct lp_build_sample_context *bld,
337                             LLVMValueRef ilevel,
338                             LLVMValueRef *out_size_vec,
339                             LLVMValueRef *row_stride_vec,
340                             LLVMValueRef *img_stride_vec);
341
342
343 void
344 lp_build_extract_image_sizes(struct lp_build_sample_context *bld,
345                              struct lp_type size_type,
346                              struct lp_type coord_type,
347                              LLVMValueRef size,
348                              LLVMValueRef *out_width,
349                              LLVMValueRef *out_height,
350                              LLVMValueRef *out_depth);
351
352
353 void
354 lp_build_unnormalized_coords(struct lp_build_sample_context *bld,
355                              LLVMValueRef flt_size,
356                              LLVMValueRef *s,
357                              LLVMValueRef *t,
358                              LLVMValueRef *r);
359
360
361 void
362 lp_build_cube_lookup(struct lp_build_sample_context *bld,
363                      LLVMValueRef s,
364                      LLVMValueRef t,
365                      LLVMValueRef r,
366                      LLVMValueRef *face,
367                      LLVMValueRef *face_s,
368                      LLVMValueRef *face_t);
369
370
371 void
372 lp_build_sample_partial_offset(struct lp_build_context *bld,
373                                unsigned block_length,
374                                LLVMValueRef coord,
375                                LLVMValueRef stride,
376                                LLVMValueRef *out_offset,
377                                LLVMValueRef *out_i);
378
379
380 void
381 lp_build_sample_offset(struct lp_build_context *bld,
382                        const struct util_format_description *format_desc,
383                        LLVMValueRef x,
384                        LLVMValueRef y,
385                        LLVMValueRef z,
386                        LLVMValueRef y_stride,
387                        LLVMValueRef z_stride,
388                        LLVMValueRef *out_offset,
389                        LLVMValueRef *out_i,
390                        LLVMValueRef *out_j);
391
392
393 void
394 lp_build_sample_soa(struct gallivm_state *gallivm,
395                     const struct lp_sampler_static_state *static_state,
396                     struct lp_sampler_dynamic_state *dynamic_state,
397                     struct lp_type fp_type,
398                     unsigned unit,
399                     unsigned num_coords,
400                     const LLVMValueRef *coords,
401                     const LLVMValueRef *ddx,
402                     const LLVMValueRef *ddy,
403                     LLVMValueRef lod_bias,
404                     LLVMValueRef explicit_lod,
405                     LLVMValueRef texel_out[4]);
406
407 void
408 lp_build_sample_nop(struct gallivm_state *gallivm, struct lp_type type,
409                     LLVMValueRef texel_out[4]);
410
411
412 #endif /* LP_BLD_SAMPLE_H */