14a49301eSmrg/********************************************************** 24a49301eSmrg * Copyright 2008-2009 VMware, Inc. All rights reserved. 34a49301eSmrg * 44a49301eSmrg * Permission is hereby granted, free of charge, to any person 54a49301eSmrg * obtaining a copy of this software and associated documentation 64a49301eSmrg * files (the "Software"), to deal in the Software without 74a49301eSmrg * restriction, including without limitation the rights to use, copy, 84a49301eSmrg * modify, merge, publish, distribute, sublicense, and/or sell copies 94a49301eSmrg * of the Software, and to permit persons to whom the Software is 104a49301eSmrg * furnished to do so, subject to the following conditions: 114a49301eSmrg * 124a49301eSmrg * The above copyright notice and this permission notice shall be 134a49301eSmrg * included in all copies or substantial portions of the Software. 144a49301eSmrg * 154a49301eSmrg * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 164a49301eSmrg * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 174a49301eSmrg * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 184a49301eSmrg * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS 194a49301eSmrg * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN 204a49301eSmrg * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 214a49301eSmrg * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 224a49301eSmrg * SOFTWARE. 234a49301eSmrg * 244a49301eSmrg **********************************************************/ 254a49301eSmrg 264a49301eSmrg#include "svga_cmd.h" 274a49301eSmrg 284a49301eSmrg#include "pipe/p_defines.h" 29cdc920a0Smrg#include "util/u_inlines.h" 304a49301eSmrg#include "pipe/p_screen.h" 314a49301eSmrg#include "util/u_memory.h" 324a49301eSmrg#include "util/u_bitmask.h" 3301e04c3fSmrg#include "util/u_upload_mgr.h" 344a49301eSmrg 354a49301eSmrg#include "svga_context.h" 364a49301eSmrg#include "svga_screen.h" 373464ebd5Sriastradh#include "svga_surface.h" 383464ebd5Sriastradh#include "svga_resource_texture.h" 393464ebd5Sriastradh#include "svga_resource_buffer.h" 403464ebd5Sriastradh#include "svga_resource.h" 414a49301eSmrg#include "svga_winsys.h" 424a49301eSmrg#include "svga_swtnl.h" 434a49301eSmrg#include "svga_draw.h" 444a49301eSmrg#include "svga_debug.h" 454a49301eSmrg#include "svga_state.h" 4601e04c3fSmrg#include "svga_winsys.h" 477ec681f3Smrg#include "svga_streamout.h" 4801e04c3fSmrg 4901e04c3fSmrg#define CONST0_UPLOAD_DEFAULT_SIZE 65536 504a49301eSmrg 513464ebd5SriastradhDEBUG_GET_ONCE_BOOL_OPTION(no_swtnl, "SVGA_NO_SWTNL", FALSE) 523464ebd5SriastradhDEBUG_GET_ONCE_BOOL_OPTION(force_swtnl, "SVGA_FORCE_SWTNL", FALSE); 533464ebd5SriastradhDEBUG_GET_ONCE_BOOL_OPTION(use_min_mipmap, "SVGA_USE_MIN_MIPMAP", FALSE); 543464ebd5SriastradhDEBUG_GET_ONCE_BOOL_OPTION(no_line_width, "SVGA_NO_LINE_WIDTH", FALSE); 553464ebd5SriastradhDEBUG_GET_ONCE_BOOL_OPTION(force_hw_line_stipple, "SVGA_FORCE_HW_LINE_STIPPLE", FALSE); 564a49301eSmrg 5701e04c3fSmrg 5801e04c3fSmrgstatic void 5901e04c3fSmrgsvga_destroy(struct pipe_context *pipe) 604a49301eSmrg{ 6101e04c3fSmrg struct svga_context *svga = svga_context(pipe); 6201e04c3fSmrg unsigned shader, i; 6301e04c3fSmrg 6401e04c3fSmrg /* free any alternate rasterizer states used for point sprite */ 6501e04c3fSmrg for (i = 0; i < ARRAY_SIZE(svga->rasterizer_no_cull); i++) { 6601e04c3fSmrg if (svga->rasterizer_no_cull[i]) { 6701e04c3fSmrg pipe->delete_rasterizer_state(pipe, svga->rasterizer_no_cull[i]); 6801e04c3fSmrg } 6901e04c3fSmrg } 704a49301eSmrg 7101e04c3fSmrg /* free depthstencil_disable state */ 7201e04c3fSmrg if (svga->depthstencil_disable) { 7301e04c3fSmrg pipe->delete_depth_stencil_alpha_state(pipe, svga->depthstencil_disable); 7401e04c3fSmrg } 7501e04c3fSmrg 7601e04c3fSmrg /* free HW constant buffers */ 7701e04c3fSmrg for (shader = 0; shader < ARRAY_SIZE(svga->state.hw_draw.constbuf); shader++) { 787ec681f3Smrg for (i = 0; i < ARRAY_SIZE(svga->state.hw_draw.constbuf[0]); i++) { 797ec681f3Smrg pipe_resource_reference(&svga->state.hw_draw.constbuf[shader][i], NULL); 807ec681f3Smrg } 8101e04c3fSmrg } 82af69d88dSmrg 8301e04c3fSmrg pipe->delete_blend_state(pipe, svga->noop_blend); 844a49301eSmrg 857ec681f3Smrg /* destroy stream output statistics queries */ 867ec681f3Smrg svga_destroy_stream_output_queries(svga); 877ec681f3Smrg 8801e04c3fSmrg /* free query gb object */ 8901e04c3fSmrg if (svga->gb_query) { 9001e04c3fSmrg pipe->destroy_query(pipe, NULL); 9101e04c3fSmrg svga->gb_query = NULL; 9201e04c3fSmrg } 9301e04c3fSmrg 9401e04c3fSmrg util_blitter_destroy(svga->blitter); 954a49301eSmrg 9601e04c3fSmrg svga_cleanup_sampler_state(svga); 9701e04c3fSmrg svga_cleanup_framebuffer(svga); 9801e04c3fSmrg svga_cleanup_tss_binding(svga); 994a49301eSmrg svga_cleanup_vertex_state(svga); 1007ec681f3Smrg svga_cleanup_tcs_state(svga); 1014a49301eSmrg 10201e04c3fSmrg svga_destroy_swtnl(svga); 10301e04c3fSmrg svga_hwtnl_destroy(svga->hwtnl); 10401e04c3fSmrg 10501e04c3fSmrg svga->swc->destroy(svga->swc); 1064a49301eSmrg 10701e04c3fSmrg util_bitmask_destroy(svga->blend_object_id_bm); 10801e04c3fSmrg util_bitmask_destroy(svga->ds_object_id_bm); 10901e04c3fSmrg util_bitmask_destroy(svga->input_element_object_id_bm); 11001e04c3fSmrg util_bitmask_destroy(svga->rast_object_id_bm); 11101e04c3fSmrg util_bitmask_destroy(svga->sampler_object_id_bm); 11201e04c3fSmrg util_bitmask_destroy(svga->sampler_view_id_bm); 11301e04c3fSmrg util_bitmask_destroy(svga->shader_id_bm); 11401e04c3fSmrg util_bitmask_destroy(svga->surface_view_id_bm); 11501e04c3fSmrg util_bitmask_destroy(svga->stream_output_id_bm); 11601e04c3fSmrg util_bitmask_destroy(svga->query_id_bm); 11701e04c3fSmrg u_upload_destroy(svga->const0_upload); 11801e04c3fSmrg u_upload_destroy(svga->pipe.stream_uploader); 11901e04c3fSmrg u_upload_destroy(svga->pipe.const_uploader); 12001e04c3fSmrg svga_texture_transfer_map_upload_destroy(svga); 12101e04c3fSmrg 12201e04c3fSmrg /* free user's constant buffers */ 123af69d88dSmrg for (shader = 0; shader < PIPE_SHADER_TYPES; ++shader) { 12401e04c3fSmrg for (i = 0; i < ARRAY_SIZE(svga->curr.constbufs[shader]); ++i) { 12501e04c3fSmrg pipe_resource_reference(&svga->curr.constbufs[shader][i].buffer, NULL); 12601e04c3fSmrg } 127af69d88dSmrg } 1284a49301eSmrg 12901e04c3fSmrg FREE(svga); 1304a49301eSmrg} 1314a49301eSmrg 1324a49301eSmrg 13301e04c3fSmrgstruct pipe_context * 13401e04c3fSmrgsvga_context_create(struct pipe_screen *screen, void *priv, unsigned flags) 1354a49301eSmrg{ 1364a49301eSmrg struct svga_screen *svgascreen = svga_screen(screen); 1374a49301eSmrg struct svga_context *svga = NULL; 1384a49301eSmrg enum pipe_error ret; 1394a49301eSmrg 14001e04c3fSmrg SVGA_STATS_TIME_PUSH(svgascreen->sws, SVGA_STATS_TIME_CREATECONTEXT); 14101e04c3fSmrg 1424a49301eSmrg svga = CALLOC_STRUCT(svga_context); 14301e04c3fSmrg if (!svga) 14401e04c3fSmrg goto done; 1454a49301eSmrg 1467ec681f3Smrg list_inithead(&svga->dirty_buffers); 147af69d88dSmrg 1484a49301eSmrg svga->pipe.screen = screen; 149cdc920a0Smrg svga->pipe.priv = priv; 1504a49301eSmrg svga->pipe.destroy = svga_destroy; 15101e04c3fSmrg svga->pipe.stream_uploader = u_upload_create(&svga->pipe, 1024 * 1024, 15201e04c3fSmrg PIPE_BIND_VERTEX_BUFFER | 15301e04c3fSmrg PIPE_BIND_INDEX_BUFFER, 15401e04c3fSmrg PIPE_USAGE_STREAM, 0); 15501e04c3fSmrg if (!svga->pipe.stream_uploader) 15601e04c3fSmrg goto cleanup; 15701e04c3fSmrg 1587ec681f3Smrg u_upload_disable_persistent(svga->pipe.stream_uploader); 1597ec681f3Smrg 16001e04c3fSmrg svga->pipe.const_uploader = u_upload_create(&svga->pipe, 128 * 1024, 16101e04c3fSmrg PIPE_BIND_CONSTANT_BUFFER, 16201e04c3fSmrg PIPE_USAGE_STREAM, 0); 16301e04c3fSmrg if (!svga->pipe.const_uploader) 16401e04c3fSmrg goto cleanup; 1654a49301eSmrg 1667ec681f3Smrg u_upload_disable_persistent(svga->pipe.const_uploader); 1677ec681f3Smrg 1684a49301eSmrg svga->swc = svgascreen->sws->context_create(svgascreen->sws); 16901e04c3fSmrg if (!svga->swc) 17001e04c3fSmrg goto cleanup; 1714a49301eSmrg 1723464ebd5Sriastradh svga_init_resource_functions(svga); 1734a49301eSmrg svga_init_blend_functions(svga); 1744a49301eSmrg svga_init_blit_functions(svga); 1754a49301eSmrg svga_init_depth_stencil_functions(svga); 1764a49301eSmrg svga_init_draw_functions(svga); 1774a49301eSmrg svga_init_flush_functions(svga); 1784a49301eSmrg svga_init_misc_functions(svga); 1794a49301eSmrg svga_init_rasterizer_functions(svga); 1804a49301eSmrg svga_init_sampler_functions(svga); 1814a49301eSmrg svga_init_fs_functions(svga); 1824a49301eSmrg svga_init_vs_functions(svga); 18301e04c3fSmrg svga_init_gs_functions(svga); 1847ec681f3Smrg svga_init_ts_functions(svga); 1854a49301eSmrg svga_init_vertex_functions(svga); 1864a49301eSmrg svga_init_constbuffer_functions(svga); 1874a49301eSmrg svga_init_query_functions(svga); 1883464ebd5Sriastradh svga_init_surface_functions(svga); 18901e04c3fSmrg svga_init_stream_output_functions(svga); 19001e04c3fSmrg svga_init_clear_functions(svga); 1917ec681f3Smrg svga_init_tracked_state(svga); 1924a49301eSmrg 19301e04c3fSmrg /* init misc state */ 19401e04c3fSmrg svga->curr.sample_mask = ~0; 1954a49301eSmrg 1963464ebd5Sriastradh /* debug */ 1973464ebd5Sriastradh svga->debug.no_swtnl = debug_get_option_no_swtnl(); 1983464ebd5Sriastradh svga->debug.force_swtnl = debug_get_option_force_swtnl(); 1993464ebd5Sriastradh svga->debug.use_min_mipmap = debug_get_option_use_min_mipmap(); 2003464ebd5Sriastradh svga->debug.no_line_width = debug_get_option_no_line_width(); 2013464ebd5Sriastradh svga->debug.force_hw_line_stipple = debug_get_option_force_hw_line_stipple(); 2024a49301eSmrg 20301e04c3fSmrg if (!(svga->blend_object_id_bm = util_bitmask_create())) 20401e04c3fSmrg goto cleanup; 20501e04c3fSmrg 20601e04c3fSmrg if (!(svga->ds_object_id_bm = util_bitmask_create())) 20701e04c3fSmrg goto cleanup; 20801e04c3fSmrg 20901e04c3fSmrg if (!(svga->input_element_object_id_bm = util_bitmask_create())) 21001e04c3fSmrg goto cleanup; 21101e04c3fSmrg 21201e04c3fSmrg if (!(svga->rast_object_id_bm = util_bitmask_create())) 21301e04c3fSmrg goto cleanup; 21401e04c3fSmrg 21501e04c3fSmrg if (!(svga->sampler_object_id_bm = util_bitmask_create())) 21601e04c3fSmrg goto cleanup; 21701e04c3fSmrg 21801e04c3fSmrg if (!(svga->sampler_view_id_bm = util_bitmask_create())) 21901e04c3fSmrg goto cleanup; 22001e04c3fSmrg 22101e04c3fSmrg if (!(svga->shader_id_bm = util_bitmask_create())) 22201e04c3fSmrg goto cleanup; 22301e04c3fSmrg 22401e04c3fSmrg if (!(svga->surface_view_id_bm = util_bitmask_create())) 22501e04c3fSmrg goto cleanup; 22601e04c3fSmrg 22701e04c3fSmrg if (!(svga->stream_output_id_bm = util_bitmask_create())) 22801e04c3fSmrg goto cleanup; 22901e04c3fSmrg 23001e04c3fSmrg if (!(svga->query_id_bm = util_bitmask_create())) 23101e04c3fSmrg goto cleanup; 232af69d88dSmrg 233af69d88dSmrg svga->hwtnl = svga_hwtnl_create(svga); 2344a49301eSmrg if (svga->hwtnl == NULL) 23501e04c3fSmrg goto cleanup; 2364a49301eSmrg 2373464ebd5Sriastradh if (!svga_init_swtnl(svga)) 23801e04c3fSmrg goto cleanup; 2394a49301eSmrg 24001e04c3fSmrg ret = svga_emit_initial_state(svga); 241af69d88dSmrg if (ret != PIPE_OK) 24201e04c3fSmrg goto cleanup; 24301e04c3fSmrg 24401e04c3fSmrg svga->const0_upload = u_upload_create(&svga->pipe, 24501e04c3fSmrg CONST0_UPLOAD_DEFAULT_SIZE, 2469f464c52Smaya PIPE_BIND_CONSTANT_BUFFER | 2479f464c52Smaya PIPE_BIND_CUSTOM, 24801e04c3fSmrg PIPE_USAGE_STREAM, 0); 24901e04c3fSmrg if (!svga->const0_upload) 25001e04c3fSmrg goto cleanup; 25101e04c3fSmrg 2527ec681f3Smrg u_upload_disable_persistent(svga->const0_upload); 2537ec681f3Smrg 25401e04c3fSmrg if (!svga_texture_transfer_map_upload_create(svga)) 25501e04c3fSmrg goto cleanup; 25601e04c3fSmrg 2574a49301eSmrg /* Avoid shortcircuiting state with initial value of zero. 2584a49301eSmrg */ 2594a49301eSmrg memset(&svga->state.hw_clear, 0xcd, sizeof(svga->state.hw_clear)); 26001e04c3fSmrg memset(&svga->state.hw_clear.framebuffer, 0x0, 2614a49301eSmrg sizeof(svga->state.hw_clear.framebuffer)); 2627ec681f3Smrg memset(&svga->state.hw_clear.rtv, 0, sizeof(svga->state.hw_clear.rtv)); 26301e04c3fSmrg svga->state.hw_clear.num_rendertargets = 0; 26401e04c3fSmrg svga->state.hw_clear.dsv = NULL; 2654a49301eSmrg 2664a49301eSmrg memset(&svga->state.hw_draw, 0xcd, sizeof(svga->state.hw_draw)); 2674a49301eSmrg memset(&svga->state.hw_draw.views, 0x0, sizeof(svga->state.hw_draw.views)); 26801e04c3fSmrg memset(&svga->state.hw_draw.num_samplers, 0, 26901e04c3fSmrg sizeof(svga->state.hw_draw.num_samplers)); 27001e04c3fSmrg memset(&svga->state.hw_draw.num_sampler_views, 0, 27101e04c3fSmrg sizeof(svga->state.hw_draw.num_sampler_views)); 27201e04c3fSmrg memset(svga->state.hw_draw.sampler_views, 0, 27301e04c3fSmrg sizeof(svga->state.hw_draw.sampler_views)); 2744a49301eSmrg svga->state.hw_draw.num_views = 0; 27501e04c3fSmrg svga->state.hw_draw.num_backed_views = 0; 27601e04c3fSmrg svga->state.hw_draw.rasterizer_discard = FALSE; 27701e04c3fSmrg 27801e04c3fSmrg /* Initialize the shader pointers */ 27901e04c3fSmrg svga->state.hw_draw.vs = NULL; 28001e04c3fSmrg svga->state.hw_draw.gs = NULL; 28101e04c3fSmrg svga->state.hw_draw.fs = NULL; 2827ec681f3Smrg svga->state.hw_draw.tcs = NULL; 2837ec681f3Smrg svga->state.hw_draw.tes = NULL; 28401e04c3fSmrg 28501e04c3fSmrg /* Initialize the currently bound buffer resources */ 28601e04c3fSmrg memset(svga->state.hw_draw.constbuf, 0, 28701e04c3fSmrg sizeof(svga->state.hw_draw.constbuf)); 28801e04c3fSmrg memset(svga->state.hw_draw.default_constbuf_size, 0, 28901e04c3fSmrg sizeof(svga->state.hw_draw.default_constbuf_size)); 29001e04c3fSmrg memset(svga->state.hw_draw.enabled_constbufs, 0, 29101e04c3fSmrg sizeof(svga->state.hw_draw.enabled_constbufs)); 29201e04c3fSmrg svga->state.hw_draw.ib = NULL; 29301e04c3fSmrg svga->state.hw_draw.num_vbuffers = 0; 29401e04c3fSmrg memset(svga->state.hw_draw.vbuffers, 0, 29501e04c3fSmrg sizeof(svga->state.hw_draw.vbuffers)); 29601e04c3fSmrg svga->state.hw_draw.const0_buffer = NULL; 29701e04c3fSmrg svga->state.hw_draw.const0_handle = NULL; 29801e04c3fSmrg 29901e04c3fSmrg /* Create a no-operation blend state which we will bind whenever the 30001e04c3fSmrg * requested blend state is impossible (e.g. due to having an integer 30101e04c3fSmrg * render target attached). 30201e04c3fSmrg * 30301e04c3fSmrg * XXX: We will probably actually need 16 of these, one for each possible 30401e04c3fSmrg * RGBA color mask (4 bits). Then, we would bind the one with a color mask 30501e04c3fSmrg * matching the blend state it is replacing. 30601e04c3fSmrg */ 30701e04c3fSmrg { 30801e04c3fSmrg struct pipe_blend_state noop_tmpl = {0}; 30901e04c3fSmrg unsigned i; 31001e04c3fSmrg 31101e04c3fSmrg for (i = 0; i < PIPE_MAX_COLOR_BUFS; ++i) { 31201e04c3fSmrg // Set the color mask to all-ones. Later this may change. 31301e04c3fSmrg noop_tmpl.rt[i].colormask = PIPE_MASK_RGBA; 31401e04c3fSmrg } 31501e04c3fSmrg svga->noop_blend = svga->pipe.create_blend_state(&svga->pipe, &noop_tmpl); 31601e04c3fSmrg } 3174a49301eSmrg 3187ec681f3Smrg svga->dirty = SVGA_NEW_ALL; 31901e04c3fSmrg svga->pred.query_id = SVGA3D_INVALID_ID; 32001e04c3fSmrg svga->disable_rasterizer = FALSE; 3214a49301eSmrg 3227ec681f3Smrg /** 3237ec681f3Smrg * Create stream output statistics queries used in the workaround for auto 3247ec681f3Smrg * draw with stream instancing. 3257ec681f3Smrg */ 3267ec681f3Smrg svga_create_stream_output_queries(svga); 3277ec681f3Smrg 32801e04c3fSmrg goto done; 3294a49301eSmrg 33001e04c3fSmrgcleanup: 3313464ebd5Sriastradh svga_destroy_swtnl(svga); 33201e04c3fSmrg 33301e04c3fSmrg if (svga->const0_upload) 33401e04c3fSmrg u_upload_destroy(svga->const0_upload); 33501e04c3fSmrg if (svga->pipe.const_uploader) 33601e04c3fSmrg u_upload_destroy(svga->pipe.const_uploader); 33701e04c3fSmrg if (svga->pipe.stream_uploader) 33801e04c3fSmrg u_upload_destroy(svga->pipe.stream_uploader); 33901e04c3fSmrg svga_texture_transfer_map_upload_destroy(svga); 34001e04c3fSmrg if (svga->hwtnl) 34101e04c3fSmrg svga_hwtnl_destroy(svga->hwtnl); 34201e04c3fSmrg if (svga->swc) 34301e04c3fSmrg svga->swc->destroy(svga->swc); 34401e04c3fSmrg util_bitmask_destroy(svga->blend_object_id_bm); 34501e04c3fSmrg util_bitmask_destroy(svga->ds_object_id_bm); 34601e04c3fSmrg util_bitmask_destroy(svga->input_element_object_id_bm); 34701e04c3fSmrg util_bitmask_destroy(svga->rast_object_id_bm); 34801e04c3fSmrg util_bitmask_destroy(svga->sampler_object_id_bm); 34901e04c3fSmrg util_bitmask_destroy(svga->sampler_view_id_bm); 35001e04c3fSmrg util_bitmask_destroy(svga->shader_id_bm); 35101e04c3fSmrg util_bitmask_destroy(svga->surface_view_id_bm); 35201e04c3fSmrg util_bitmask_destroy(svga->stream_output_id_bm); 35301e04c3fSmrg util_bitmask_destroy(svga->query_id_bm); 3544a49301eSmrg FREE(svga); 35501e04c3fSmrg svga = NULL; 35601e04c3fSmrg 35701e04c3fSmrgdone: 35801e04c3fSmrg SVGA_STATS_TIME_POP(svgascreen->sws); 35901e04c3fSmrg return svga ? &svga->pipe:NULL; 3604a49301eSmrg} 3614a49301eSmrg 3624a49301eSmrg 36301e04c3fSmrgvoid 36401e04c3fSmrgsvga_context_flush(struct svga_context *svga, 36501e04c3fSmrg struct pipe_fence_handle **pfence) 3664a49301eSmrg{ 3674a49301eSmrg struct svga_screen *svgascreen = svga_screen(svga->pipe.screen); 3683464ebd5Sriastradh struct pipe_fence_handle *fence = NULL; 36901e04c3fSmrg uint64_t t0; 37001e04c3fSmrg 37101e04c3fSmrg SVGA_STATS_TIME_PUSH(svga_sws(svga), SVGA_STATS_TIME_CONTEXTFLUSH); 3724a49301eSmrg 3734a49301eSmrg svga->curr.nr_fbs = 0; 3744a49301eSmrg 37501e04c3fSmrg /* Unmap the 0th/default constant buffer. The u_upload_unmap() function 37601e04c3fSmrg * will call pipe_context::transfer_flush_region() to indicate the 37701e04c3fSmrg * region of the buffer which was modified (and needs to be uploaded). 37801e04c3fSmrg */ 37901e04c3fSmrg if (svga->state.hw_draw.const0_handle) { 38001e04c3fSmrg assert(svga->state.hw_draw.const0_buffer); 38101e04c3fSmrg u_upload_unmap(svga->const0_upload); 38201e04c3fSmrg pipe_resource_reference(&svga->state.hw_draw.const0_buffer, NULL); 38301e04c3fSmrg svga->state.hw_draw.const0_handle = NULL; 38401e04c3fSmrg } 38501e04c3fSmrg 3863464ebd5Sriastradh /* Ensure that texture dma uploads are processed 3874a49301eSmrg * before submitting commands. 3884a49301eSmrg */ 3894a49301eSmrg svga_context_flush_buffers(svga); 3904a49301eSmrg 39101e04c3fSmrg svga->hud.command_buffer_size += 39201e04c3fSmrg svga->swc->get_command_buffer_size(svga->swc); 39301e04c3fSmrg 3944a49301eSmrg /* Flush pending commands to hardware: 3954a49301eSmrg */ 39601e04c3fSmrg t0 = svga_get_time(svga); 3973464ebd5Sriastradh svga->swc->flush(svga->swc, &fence); 39801e04c3fSmrg svga->hud.flush_time += (svga_get_time(svga) - t0); 3993464ebd5Sriastradh 40001e04c3fSmrg svga->hud.num_flushes++; 40101e04c3fSmrg 40201e04c3fSmrg svga_screen_cache_flush(svgascreen, svga, fence); 40301e04c3fSmrg 40401e04c3fSmrg SVGA3D_ResetLastCommand(svga->swc); 4053464ebd5Sriastradh 4063464ebd5Sriastradh /* To force the re-emission of rendertargets and texture sampler bindings on 4073464ebd5Sriastradh * the next command buffer. 4083464ebd5Sriastradh */ 40901e04c3fSmrg svga->rebind.flags.rendertargets = TRUE; 41001e04c3fSmrg svga->rebind.flags.texture_samplers = TRUE; 41101e04c3fSmrg 412af69d88dSmrg if (svga_have_gb_objects(svga)) { 41301e04c3fSmrg 41401e04c3fSmrg svga->rebind.flags.constbufs = TRUE; 41501e04c3fSmrg svga->rebind.flags.vs = TRUE; 41601e04c3fSmrg svga->rebind.flags.fs = TRUE; 41701e04c3fSmrg svga->rebind.flags.gs = TRUE; 41801e04c3fSmrg 4197ec681f3Smrg if (svga_have_sm5(svga)) { 4207ec681f3Smrg svga->rebind.flags.tcs = TRUE; 4217ec681f3Smrg svga->rebind.flags.tes = TRUE; 4227ec681f3Smrg } 4237ec681f3Smrg 42401e04c3fSmrg if (svga_need_to_rebind_resources(svga)) { 42501e04c3fSmrg svga->rebind.flags.query = TRUE; 42601e04c3fSmrg } 427af69d88dSmrg } 4284a49301eSmrg 4294a49301eSmrg if (SVGA_DEBUG & DEBUG_SYNC) { 4303464ebd5Sriastradh if (fence) 43101e04c3fSmrg svga->pipe.screen->fence_finish(svga->pipe.screen, NULL, fence, 4323464ebd5Sriastradh PIPE_TIMEOUT_INFINITE); 4334a49301eSmrg } 4343464ebd5Sriastradh 43501e04c3fSmrg if (pfence) 436af69d88dSmrg svgascreen->sws->fence_reference(svgascreen->sws, pfence, fence); 437af69d88dSmrg 438af69d88dSmrg svgascreen->sws->fence_reference(svgascreen->sws, &fence, NULL); 43901e04c3fSmrg 44001e04c3fSmrg SVGA_STATS_TIME_POP(svga_sws(svga)); 4414a49301eSmrg} 4424a49301eSmrg 4434a49301eSmrg 44401e04c3fSmrg/** 44501e04c3fSmrg * Flush pending commands and wait for completion with a fence. 44601e04c3fSmrg */ 44701e04c3fSmrgvoid 44801e04c3fSmrgsvga_context_finish(struct svga_context *svga) 44901e04c3fSmrg{ 45001e04c3fSmrg struct pipe_screen *screen = svga->pipe.screen; 45101e04c3fSmrg struct pipe_fence_handle *fence = NULL; 45201e04c3fSmrg 45301e04c3fSmrg SVGA_STATS_TIME_PUSH(svga_sws(svga), SVGA_STATS_TIME_CONTEXTFINISH); 45401e04c3fSmrg 45501e04c3fSmrg svga_context_flush(svga, &fence); 45601e04c3fSmrg screen->fence_finish(screen, NULL, fence, PIPE_TIMEOUT_INFINITE); 45701e04c3fSmrg screen->fence_reference(screen, &fence, NULL); 45801e04c3fSmrg 45901e04c3fSmrg SVGA_STATS_TIME_POP(svga_sws(svga)); 46001e04c3fSmrg} 46101e04c3fSmrg 46201e04c3fSmrg 46301e04c3fSmrg/** 46401e04c3fSmrg * Emit pending drawing commands to the command buffer. 46501e04c3fSmrg * If the command buffer overflows, we flush it and retry. 46601e04c3fSmrg * \sa svga_hwtnl_flush() 46701e04c3fSmrg */ 46801e04c3fSmrgvoid 46901e04c3fSmrgsvga_hwtnl_flush_retry(struct svga_context *svga) 4704a49301eSmrg{ 4714a49301eSmrg enum pipe_error ret = PIPE_OK; 4724a49301eSmrg 4737ec681f3Smrg SVGA_RETRY_OOM(svga, ret, svga_hwtnl_flush(svga->hwtnl)); 47401e04c3fSmrg assert(ret == PIPE_OK); 4754a49301eSmrg} 4764a49301eSmrg 4773464ebd5Sriastradh 478af69d88dSmrg/** 479af69d88dSmrg * Flush the primitive queue if this buffer is referred. 480af69d88dSmrg * 481af69d88dSmrg * Otherwise DMA commands on the referred buffer will be emitted too late. 482af69d88dSmrg */ 48301e04c3fSmrgvoid 48401e04c3fSmrgsvga_hwtnl_flush_buffer(struct svga_context *svga, 48501e04c3fSmrg struct pipe_resource *buffer) 486af69d88dSmrg{ 487af69d88dSmrg if (svga_hwtnl_is_buffer_referred(svga->hwtnl, buffer)) { 488af69d88dSmrg svga_hwtnl_flush_retry(svga); 489af69d88dSmrg } 490af69d88dSmrg} 491af69d88dSmrg 492af69d88dSmrg 49301e04c3fSmrg/** 49401e04c3fSmrg * Emit all operations pending on host surfaces. 49501e04c3fSmrg */ 49601e04c3fSmrgvoid 49701e04c3fSmrgsvga_surfaces_flush(struct svga_context *svga) 4983464ebd5Sriastradh{ 49901e04c3fSmrg SVGA_STATS_TIME_PUSH(svga_sws(svga), SVGA_STATS_TIME_SURFACEFLUSH); 5003464ebd5Sriastradh 5013464ebd5Sriastradh /* Emit buffered drawing commands. 5023464ebd5Sriastradh */ 50301e04c3fSmrg svga_hwtnl_flush_retry(svga); 5043464ebd5Sriastradh 50501e04c3fSmrg /* Emit back-copy from render target views to textures. 5063464ebd5Sriastradh */ 50701e04c3fSmrg svga_propagate_rendertargets(svga); 5083464ebd5Sriastradh 50901e04c3fSmrg SVGA_STATS_TIME_POP(svga_sws(svga)); 5103464ebd5Sriastradh} 5113464ebd5Sriastradh 5123464ebd5Sriastradh 5133464ebd5Sriastradhstruct svga_winsys_context * 51401e04c3fSmrgsvga_winsys_context(struct pipe_context *pipe) 5153464ebd5Sriastradh{ 51601e04c3fSmrg return svga_context(pipe)->swc; 5173464ebd5Sriastradh} 518