1 /* 2 * Mesa 3-D graphics library 3 * 4 * Copyright (C) 2012-2013 LunarG, Inc. 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining a 7 * copy of this software and associated documentation files (the "Software"), 8 * to deal in the Software without restriction, including without limitation 9 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 10 * and/or sell copies of the Software, and to permit persons to whom the 11 * Software is furnished to do so, subject to the following conditions: 12 * 13 * The above copyright notice and this permission notice shall be included 14 * in all copies or substantial portions of the Software. 15 * 16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 21 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 22 * DEALINGS IN THE SOFTWARE. 23 * 24 * Authors: 25 * Chia-I Wu <olv (at) lunarg.com> 26 */ 27 28 #ifndef ILO_RENDER_GEN_H 29 #define ILO_RENDER_GEN_H 30 31 #include "core/ilo_builder.h" 32 #include "core/ilo_builder_3d.h" 33 #include "core/ilo_builder_render.h" 34 #include "core/ilo_state_raster.h" 35 36 #include "ilo_common.h" 37 #include "ilo_state.h" 38 #include "ilo_render.h" 39 40 struct ilo_bo; 41 struct ilo_blitter; 42 struct ilo_render; 43 struct ilo_state_vector; 44 45 /** 46 * Render Engine. 47 */ 48 struct ilo_render { 49 const struct ilo_dev *dev; 50 struct ilo_builder *builder; 51 52 struct intel_bo *workaround_bo; 53 54 struct ilo_render_scratch_space { 55 struct intel_bo *bo; 56 int size; 57 } vs_scratch, gs_scratch, fs_scratch; 58 59 struct ilo_state_sample_pattern sample_pattern; 60 61 bool hw_ctx_changed; 62 63 /* 64 * Any state that involves resources needs to be re-emitted when the 65 * batch bo changed. This is because we do not pin the resources and 66 * their offsets (or existence) may change between batch buffers. 67 */ 68 bool batch_bo_changed; 69 bool state_bo_changed; 70 bool instruction_bo_changed; 71 72 /** 73 * HW states. 74 */ 75 struct ilo_render_state { 76 /* 77 * When a WA is needed before some command, we always emit the WA right 78 * before the command. Knowing what have already been done since last 79 * 3DPRIMITIVE allows us to skip some WAs. 80 */ 81 uint32_t current_pipe_control_dw1; 82 83 /* 84 * When a WA is needed after some command, we may have the WA follow the 85 * command immediately or defer it. If this is non-zero, a PIPE_CONTROL 86 * will be emitted before 3DPRIMITIVE. 87 */ 88 uint32_t deferred_pipe_control_dw1; 89 90 int reduced_prim; 91 int so_max_vertices; 92 93 struct ilo_state_urb urb; 94 struct ilo_state_raster rs; 95 struct ilo_state_cc cc; 96 97 uint32_t SF_VIEWPORT; 98 uint32_t CLIP_VIEWPORT; 99 uint32_t SF_CLIP_VIEWPORT; /* GEN7+ */ 100 uint32_t CC_VIEWPORT; 101 102 uint32_t COLOR_CALC_STATE; 103 uint32_t BLEND_STATE; 104 uint32_t DEPTH_STENCIL_STATE; 105 106 uint32_t SCISSOR_RECT; 107 108 struct { 109 uint32_t BINDING_TABLE_STATE; 110 uint32_t SURFACE_STATE[ILO_MAX_SURFACES]; 111 uint32_t SAMPLER_STATE; 112 uint32_t SAMPLER_BORDER_COLOR_STATE[ILO_MAX_SAMPLERS]; 113 uint32_t PUSH_CONSTANT_BUFFER; 114 int PUSH_CONSTANT_BUFFER_size; 115 } vs; 116 117 struct { 118 uint32_t BINDING_TABLE_STATE; 119 uint32_t SURFACE_STATE[ILO_MAX_SURFACES]; 120 bool active; 121 } gs; 122 123 struct { 124 uint32_t BINDING_TABLE_STATE; 125 uint32_t SURFACE_STATE[ILO_MAX_SURFACES]; 126 uint32_t SAMPLER_STATE; 127 uint32_t SAMPLER_BORDER_COLOR_STATE[ILO_MAX_SAMPLERS]; 128 uint32_t PUSH_CONSTANT_BUFFER; 129 int PUSH_CONSTANT_BUFFER_size; 130 } wm; 131 132 struct { 133 uint32_t BINDING_TABLE_STATE; 134 uint32_t SURFACE_STATE[ILO_MAX_SURFACES]; 135 uint32_t SAMPLER_STATE; 136 uint32_t SAMPLER_BORDER_COLOR_STATE[ILO_MAX_SAMPLERS]; 137 uint32_t PUSH_CONSTANT_BUFFER; 138 int PUSH_CONSTANT_BUFFER_size; 139 } cs; 140 } state; 141 }; 142 143 struct ilo_render_draw_session { 144 uint32_t pipe_dirty; 145 146 /* commands */ 147 int reduced_prim; 148 149 bool prim_changed; 150 151 struct ilo_state_urb_delta urb_delta; 152 struct ilo_state_vf_delta vf_delta; 153 struct ilo_state_raster_delta rs_delta; 154 struct ilo_state_viewport_delta vp_delta; 155 struct ilo_state_cc_delta cc_delta; 156 157 /* dynamic states */ 158 bool viewport_changed; 159 bool scissor_changed; 160 161 bool cc_changed; 162 bool dsa_changed; 163 bool blend_changed; 164 165 bool sampler_vs_changed; 166 bool sampler_gs_changed; 167 bool sampler_fs_changed; 168 169 bool pcb_vs_changed; 170 bool pcb_gs_changed; 171 bool pcb_fs_changed; 172 173 /* surface states */ 174 bool binding_table_vs_changed; 175 bool binding_table_gs_changed; 176 bool binding_table_fs_changed; 177 }; 178 179 struct ilo_render_rectlist_session { 180 uint32_t vb_start; 181 uint32_t vb_end; 182 }; 183 184 struct ilo_render_launch_grid_session { 185 const unsigned *thread_group_offset; 186 const unsigned *thread_group_dim; 187 unsigned thread_group_size; 188 const struct pipe_constant_buffer *input; 189 uint32_t pc; 190 191 uint32_t idrt; 192 int idrt_size; 193 194 uint32_t compute_data[6]; 195 struct ilo_state_compute compute; 196 }; 197 198 int 199 ilo_render_get_draw_commands_len_gen6(const struct ilo_render *render, 200 const struct ilo_state_vector *vec); 201 202 int 203 ilo_render_get_draw_commands_len_gen7(const struct ilo_render *render, 204 const struct ilo_state_vector *vec); 205 206 int 207 ilo_render_get_draw_commands_len_gen8(const struct ilo_render *render, 208 const struct ilo_state_vector *vec); 209 210 static inline int 211 ilo_render_get_draw_commands_len(const struct ilo_render *render, 212 const struct ilo_state_vector *vec) 213 { 214 if (ilo_dev_gen(render->dev) >= ILO_GEN(8)) 215 return ilo_render_get_draw_commands_len_gen8(render, vec); 216 else if (ilo_dev_gen(render->dev) >= ILO_GEN(7)) 217 return ilo_render_get_draw_commands_len_gen7(render, vec); 218 else 219 return ilo_render_get_draw_commands_len_gen6(render, vec); 220 } 221 222 void 223 ilo_render_emit_draw_commands_gen6(struct ilo_render *render, 224 const struct ilo_state_vector *vec, 225 struct ilo_render_draw_session *session); 226 227 void 228 ilo_render_emit_draw_commands_gen7(struct ilo_render *render, 229 const struct ilo_state_vector *vec, 230 struct ilo_render_draw_session *session); 231 232 void 233 ilo_render_emit_draw_commands_gen8(struct ilo_render *render, 234 const struct ilo_state_vector *vec, 235 struct ilo_render_draw_session *session); 236 237 static inline void 238 ilo_render_emit_draw_commands(struct ilo_render *render, 239 const struct ilo_state_vector *vec, 240 struct ilo_render_draw_session *session) 241 { 242 const unsigned batch_used = ilo_builder_batch_used(render->builder); 243 244 if (ilo_dev_gen(render->dev) >= ILO_GEN(8)) 245 ilo_render_emit_draw_commands_gen8(render, vec, session); 246 else if (ilo_dev_gen(render->dev) >= ILO_GEN(7)) 247 ilo_render_emit_draw_commands_gen7(render, vec, session); 248 else 249 ilo_render_emit_draw_commands_gen6(render, vec, session); 250 251 assert(ilo_builder_batch_used(render->builder) <= batch_used + 252 ilo_render_get_draw_commands_len(render, vec)); 253 } 254 255 int 256 ilo_render_get_rectlist_commands_len_gen6(const struct ilo_render *render, 257 const struct ilo_blitter *blitter); 258 259 int 260 ilo_render_get_rectlist_commands_len_gen8(const struct ilo_render *render, 261 const struct ilo_blitter *blitter); 262 263 static inline int 264 ilo_render_get_rectlist_commands_len(const struct ilo_render *render, 265 const struct ilo_blitter *blitter) 266 { 267 if (ilo_dev_gen(render->dev) >= ILO_GEN(8)) 268 return ilo_render_get_rectlist_commands_len_gen8(render, blitter); 269 else 270 return ilo_render_get_rectlist_commands_len_gen6(render, blitter); 271 } 272 273 void 274 ilo_render_emit_rectlist_commands_gen6(struct ilo_render *r, 275 const struct ilo_blitter *blitter, 276 const struct ilo_render_rectlist_session *session); 277 278 void 279 ilo_render_emit_rectlist_commands_gen7(struct ilo_render *r, 280 const struct ilo_blitter *blitter, 281 const struct ilo_render_rectlist_session *session); 282 283 void 284 ilo_render_emit_rectlist_commands_gen8(struct ilo_render *r, 285 const struct ilo_blitter *blitter, 286 const struct ilo_render_rectlist_session *session); 287 288 static inline void 289 ilo_render_emit_rectlist_commands(struct ilo_render *render, 290 const struct ilo_blitter *blitter, 291 const struct ilo_render_rectlist_session *session) 292 { 293 const unsigned batch_used = ilo_builder_batch_used(render->builder); 294 295 if (ilo_dev_gen(render->dev) >= ILO_GEN(8)) 296 ilo_render_emit_rectlist_commands_gen8(render, blitter, session); 297 else if (ilo_dev_gen(render->dev) >= ILO_GEN(7)) 298 ilo_render_emit_rectlist_commands_gen7(render, blitter, session); 299 else 300 ilo_render_emit_rectlist_commands_gen6(render, blitter, session); 301 302 assert(ilo_builder_batch_used(render->builder) <= batch_used + 303 ilo_render_get_rectlist_commands_len(render, blitter)); 304 } 305 306 int 307 ilo_render_get_launch_grid_commands_len(const struct ilo_render *render, 308 const struct ilo_state_vector *vec); 309 310 void 311 ilo_render_emit_launch_grid_commands(struct ilo_render *render, 312 const struct ilo_state_vector *vec, 313 const struct ilo_render_launch_grid_session *session); 314 315 int 316 ilo_render_get_draw_dynamic_states_len(const struct ilo_render *render, 317 const struct ilo_state_vector *vec); 318 319 void 320 ilo_render_emit_draw_dynamic_states(struct ilo_render *render, 321 const struct ilo_state_vector *vec, 322 struct ilo_render_draw_session *session); 323 324 int 325 ilo_render_get_rectlist_dynamic_states_len(const struct ilo_render *render, 326 const struct ilo_blitter *blitter); 327 328 void 329 ilo_render_emit_rectlist_dynamic_states(struct ilo_render *render, 330 const struct ilo_blitter *blitter, 331 struct ilo_render_rectlist_session *session); 332 333 int 334 ilo_render_get_launch_grid_dynamic_states_len(const struct ilo_render *render, 335 const struct ilo_state_vector *vec); 336 337 void 338 ilo_render_emit_launch_grid_dynamic_states(struct ilo_render *render, 339 const struct ilo_state_vector *vec, 340 struct ilo_render_launch_grid_session *session); 341 342 int 343 ilo_render_get_draw_surface_states_len(const struct ilo_render *render, 344 const struct ilo_state_vector *vec); 345 346 void 347 ilo_render_emit_draw_surface_states(struct ilo_render *render, 348 const struct ilo_state_vector *vec, 349 struct ilo_render_draw_session *session); 350 351 int 352 ilo_render_get_launch_grid_surface_states_len(const struct ilo_render *render, 353 const struct ilo_state_vector *vec); 354 355 void 356 ilo_render_emit_launch_grid_surface_states(struct ilo_render *render, 357 const struct ilo_state_vector *vec, 358 struct ilo_render_launch_grid_session *session); 359 360 /** 361 * A convenient wrapper for gen6_PIPE_CONTROL(). This should be enough for 362 * our needs everywhere except for queries. 363 */ 364 static inline void 365 ilo_render_pipe_control(struct ilo_render *r, uint32_t dw1) 366 { 367 const uint32_t write_mask = (dw1 & GEN6_PIPE_CONTROL_WRITE__MASK); 368 struct intel_bo *bo = (write_mask) ? r->workaround_bo : NULL; 369 370 ILO_DEV_ASSERT(r->dev, 6, 8); 371 372 if (write_mask) 373 assert(write_mask == GEN6_PIPE_CONTROL_WRITE_IMM); 374 375 if (dw1 & GEN6_PIPE_CONTROL_CS_STALL) { 376 /* CS stall cannot be set alone */ 377 const uint32_t mask = GEN6_PIPE_CONTROL_RENDER_CACHE_FLUSH | 378 GEN6_PIPE_CONTROL_DEPTH_CACHE_FLUSH | 379 GEN6_PIPE_CONTROL_PIXEL_SCOREBOARD_STALL | 380 GEN6_PIPE_CONTROL_DEPTH_STALL | 381 GEN6_PIPE_CONTROL_WRITE__MASK; 382 if (!(dw1 & mask)) 383 dw1 |= GEN6_PIPE_CONTROL_PIXEL_SCOREBOARD_STALL; 384 } 385 386 gen6_PIPE_CONTROL(r->builder, dw1, bo, 0, 0); 387 388 r->state.current_pipe_control_dw1 |= dw1; 389 r->state.deferred_pipe_control_dw1 &= ~dw1; 390 } 391 392 /** 393 * A convenient wrapper for gen{6,7}_3DPRIMITIVE(). 394 */ 395 static inline void 396 ilo_render_3dprimitive(struct ilo_render *r, 397 const struct gen6_3dprimitive_info *info) 398 { 399 ILO_DEV_ASSERT(r->dev, 6, 8); 400 401 if (r->state.deferred_pipe_control_dw1) 402 ilo_render_pipe_control(r, r->state.deferred_pipe_control_dw1); 403 404 /* 3DPRIMITIVE */ 405 if (ilo_dev_gen(r->dev) >= ILO_GEN(7)) 406 gen7_3DPRIMITIVE(r->builder, info); 407 else 408 gen6_3DPRIMITIVE(r->builder, info); 409 410 r->state.current_pipe_control_dw1 = 0; 411 assert(!r->state.deferred_pipe_control_dw1); 412 } 413 414 void 415 gen6_wa_pre_pipe_control(struct ilo_render *r, uint32_t dw1); 416 417 void 418 gen6_draw_common_select(struct ilo_render *r, 419 const struct ilo_state_vector *ilo, 420 struct ilo_render_draw_session *session); 421 422 void 423 gen6_draw_common_sip(struct ilo_render *r, 424 const struct ilo_state_vector *ilo, 425 struct ilo_render_draw_session *session); 426 427 void 428 gen6_draw_common_base_address(struct ilo_render *r, 429 const struct ilo_state_vector *ilo, 430 struct ilo_render_draw_session *session); 431 432 void 433 gen6_draw_vf(struct ilo_render *r, 434 const struct ilo_state_vector *ilo, 435 struct ilo_render_draw_session *session); 436 437 void 438 gen6_draw_vf_statistics(struct ilo_render *r, 439 const struct ilo_state_vector *ilo, 440 struct ilo_render_draw_session *session); 441 442 void 443 gen6_draw_vs(struct ilo_render *r, 444 const struct ilo_state_vector *ilo, 445 struct ilo_render_draw_session *session); 446 447 void 448 gen6_draw_clip(struct ilo_render *r, 449 const struct ilo_state_vector *ilo, 450 struct ilo_render_draw_session *session); 451 452 void 453 gen6_draw_sf_rect(struct ilo_render *r, 454 const struct ilo_state_vector *ilo, 455 struct ilo_render_draw_session *session); 456 457 void 458 gen6_draw_wm_raster(struct ilo_render *r, 459 const struct ilo_state_vector *ilo, 460 struct ilo_render_draw_session *session); 461 462 void 463 gen7_draw_common_pcb_alloc(struct ilo_render *r, 464 const struct ilo_state_vector *vec, 465 struct ilo_render_draw_session *session); 466 467 void 468 gen7_draw_common_pointers_1(struct ilo_render *r, 469 const struct ilo_state_vector *vec, 470 struct ilo_render_draw_session *session); 471 472 void 473 gen7_draw_common_urb(struct ilo_render *r, 474 const struct ilo_state_vector *vec, 475 struct ilo_render_draw_session *session); 476 477 void 478 gen7_draw_common_pointers_2(struct ilo_render *r, 479 const struct ilo_state_vector *vec, 480 struct ilo_render_draw_session *session); 481 482 void 483 gen7_draw_vs(struct ilo_render *r, 484 const struct ilo_state_vector *vec, 485 struct ilo_render_draw_session *session); 486 487 void 488 gen7_draw_ds(struct ilo_render *r, 489 const struct ilo_state_vector *vec, 490 struct ilo_render_draw_session *session); 491 492 void 493 gen7_draw_te(struct ilo_render *r, 494 const struct ilo_state_vector *vec, 495 struct ilo_render_draw_session *session); 496 497 void 498 gen7_draw_hs(struct ilo_render *r, 499 const struct ilo_state_vector *vec, 500 struct ilo_render_draw_session *session); 501 502 void 503 gen7_draw_gs(struct ilo_render *r, 504 const struct ilo_state_vector *vec, 505 struct ilo_render_draw_session *session); 506 507 void 508 gen7_draw_sol(struct ilo_render *r, 509 const struct ilo_state_vector *vec, 510 struct ilo_render_draw_session *session); 511 512 #endif /* ILO_RENDER_GEN_H */ 513