Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/mesa
Path: blob/21.2-virgl/src/gallium/drivers/r600/r600_cs.h
4570 views
1
/*
2
* Copyright 2013 Advanced Micro Devices, Inc.
3
*
4
* Permission is hereby granted, free of charge, to any person obtaining a
5
* copy of this software and associated documentation files (the "Software"),
6
* to deal in the Software without restriction, including without limitation
7
* on the rights to use, copy, modify, merge, publish, distribute, sub
8
* license, and/or sell copies of the Software, and to permit persons to whom
9
* the Software is furnished to do so, subject to the following conditions:
10
*
11
* The above copyright notice and this permission notice (including the next
12
* paragraph) shall be included in all copies or substantial portions of the
13
* Software.
14
*
15
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
* FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
18
* THE AUTHOR(S) AND/OR THEIR SUPPLIERS BE LIABLE FOR ANY CLAIM,
19
* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
20
* OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
21
* USE OR OTHER DEALINGS IN THE SOFTWARE.
22
*
23
* Authors: Marek Olšák <[email protected]>
24
*/
25
26
/**
27
* This file contains helpers for writing commands to commands streams.
28
*/
29
30
#ifndef R600_CS_H
31
#define R600_CS_H
32
33
#include "r600_pipe_common.h"
34
#include "r600d_common.h"
35
36
/**
37
* Return true if there is enough memory in VRAM and GTT for the buffers
38
* added so far.
39
*
40
* \param vram VRAM memory size not added to the buffer list yet
41
* \param gtt GTT memory size not added to the buffer list yet
42
*/
43
static inline bool
44
radeon_cs_memory_below_limit(struct r600_common_screen *screen,
45
struct radeon_cmdbuf *cs,
46
uint64_t vram, uint64_t gtt)
47
{
48
vram += (uint64_t)cs->used_vram_kb * 1024;
49
gtt += (uint64_t)cs->used_gart_kb * 1024;
50
51
/* Anything that goes above the VRAM size should go to GTT. */
52
if (vram > screen->info.vram_size)
53
gtt += vram - screen->info.vram_size;
54
55
/* Now we just need to check if we have enough GTT. */
56
return gtt < screen->info.gart_size * 0.7;
57
}
58
59
/**
60
* Add a buffer to the buffer list for the given command stream (CS).
61
*
62
* All buffers used by a CS must be added to the list. This tells the kernel
63
* driver which buffers are used by GPU commands. Other buffers can
64
* be swapped out (not accessible) during execution.
65
*
66
* The buffer list becomes empty after every context flush and must be
67
* rebuilt.
68
*/
69
static inline unsigned radeon_add_to_buffer_list(struct r600_common_context *rctx,
70
struct r600_ring *ring,
71
struct r600_resource *rbo,
72
enum radeon_bo_usage usage,
73
enum radeon_bo_priority priority)
74
{
75
assert(usage);
76
return rctx->ws->cs_add_buffer(
77
&ring->cs, rbo->buf,
78
(enum radeon_bo_usage)(usage | RADEON_USAGE_SYNCHRONIZED),
79
rbo->domains, priority) * 4;
80
}
81
82
/**
83
* Same as above, but also checks memory usage and flushes the context
84
* accordingly.
85
*
86
* When this SHOULD NOT be used:
87
*
88
* - if r600_context_add_resource_size has been called for the buffer
89
* followed by *_need_cs_space for checking the memory usage
90
*
91
* - if r600_need_dma_space has been called for the buffer
92
*
93
* - when emitting state packets and draw packets (because preceding packets
94
* can't be re-emitted at that point)
95
*
96
* - if shader resource "enabled_mask" is not up-to-date or there is
97
* a different constraint disallowing a context flush
98
*/
99
static inline unsigned
100
radeon_add_to_buffer_list_check_mem(struct r600_common_context *rctx,
101
struct r600_ring *ring,
102
struct r600_resource *rbo,
103
enum radeon_bo_usage usage,
104
enum radeon_bo_priority priority,
105
bool check_mem)
106
{
107
if (check_mem &&
108
!radeon_cs_memory_below_limit(rctx->screen, &ring->cs,
109
rctx->vram + rbo->vram_usage,
110
rctx->gtt + rbo->gart_usage))
111
ring->flush(rctx, PIPE_FLUSH_ASYNC, NULL);
112
113
return radeon_add_to_buffer_list(rctx, ring, rbo, usage, priority);
114
}
115
116
static inline void r600_emit_reloc(struct r600_common_context *rctx,
117
struct r600_ring *ring, struct r600_resource *rbo,
118
enum radeon_bo_usage usage,
119
enum radeon_bo_priority priority)
120
{
121
struct radeon_cmdbuf *cs = &ring->cs;
122
bool has_vm = ((struct r600_common_screen*)rctx->b.screen)->info.r600_has_virtual_memory;
123
unsigned reloc = radeon_add_to_buffer_list(rctx, ring, rbo, usage, priority);
124
125
if (!has_vm) {
126
radeon_emit(cs, PKT3(PKT3_NOP, 0, 0));
127
radeon_emit(cs, reloc);
128
}
129
}
130
131
static inline void radeon_set_config_reg_seq(struct radeon_cmdbuf *cs, unsigned reg, unsigned num)
132
{
133
assert(reg < R600_CONTEXT_REG_OFFSET);
134
assert(cs->current.cdw + 2 + num <= cs->current.max_dw);
135
radeon_emit(cs, PKT3(PKT3_SET_CONFIG_REG, num, 0));
136
radeon_emit(cs, (reg - R600_CONFIG_REG_OFFSET) >> 2);
137
}
138
139
static inline void radeon_set_config_reg(struct radeon_cmdbuf *cs, unsigned reg, unsigned value)
140
{
141
radeon_set_config_reg_seq(cs, reg, 1);
142
radeon_emit(cs, value);
143
}
144
145
static inline void radeon_set_context_reg_seq(struct radeon_cmdbuf *cs, unsigned reg, unsigned num)
146
{
147
assert(reg >= R600_CONTEXT_REG_OFFSET);
148
assert(cs->current.cdw + 2 + num <= cs->current.max_dw);
149
radeon_emit(cs, PKT3(PKT3_SET_CONTEXT_REG, num, 0));
150
radeon_emit(cs, (reg - R600_CONTEXT_REG_OFFSET) >> 2);
151
}
152
153
static inline void radeon_set_context_reg(struct radeon_cmdbuf *cs, unsigned reg, unsigned value)
154
{
155
radeon_set_context_reg_seq(cs, reg, 1);
156
radeon_emit(cs, value);
157
}
158
159
static inline void radeon_set_context_reg_idx(struct radeon_cmdbuf *cs,
160
unsigned reg, unsigned idx,
161
unsigned value)
162
{
163
assert(reg >= R600_CONTEXT_REG_OFFSET);
164
assert(cs->current.cdw + 3 <= cs->current.max_dw);
165
radeon_emit(cs, PKT3(PKT3_SET_CONTEXT_REG, 1, 0));
166
radeon_emit(cs, (reg - R600_CONTEXT_REG_OFFSET) >> 2 | (idx << 28));
167
radeon_emit(cs, value);
168
}
169
170
static inline void radeon_set_sh_reg_seq(struct radeon_cmdbuf *cs, unsigned reg, unsigned num)
171
{
172
assert(reg >= SI_SH_REG_OFFSET && reg < SI_SH_REG_END);
173
assert(cs->current.cdw + 2 + num <= cs->current.max_dw);
174
radeon_emit(cs, PKT3(PKT3_SET_SH_REG, num, 0));
175
radeon_emit(cs, (reg - SI_SH_REG_OFFSET) >> 2);
176
}
177
178
static inline void radeon_set_sh_reg(struct radeon_cmdbuf *cs, unsigned reg, unsigned value)
179
{
180
radeon_set_sh_reg_seq(cs, reg, 1);
181
radeon_emit(cs, value);
182
}
183
184
static inline void radeon_set_uconfig_reg_seq(struct radeon_cmdbuf *cs, unsigned reg, unsigned num)
185
{
186
assert(reg >= CIK_UCONFIG_REG_OFFSET && reg < CIK_UCONFIG_REG_END);
187
assert(cs->current.cdw + 2 + num <= cs->current.max_dw);
188
radeon_emit(cs, PKT3(PKT3_SET_UCONFIG_REG, num, 0));
189
radeon_emit(cs, (reg - CIK_UCONFIG_REG_OFFSET) >> 2);
190
}
191
192
static inline void radeon_set_uconfig_reg(struct radeon_cmdbuf *cs, unsigned reg, unsigned value)
193
{
194
radeon_set_uconfig_reg_seq(cs, reg, 1);
195
radeon_emit(cs, value);
196
}
197
198
static inline void radeon_set_uconfig_reg_idx(struct radeon_cmdbuf *cs,
199
unsigned reg, unsigned idx,
200
unsigned value)
201
{
202
assert(reg >= CIK_UCONFIG_REG_OFFSET && reg < CIK_UCONFIG_REG_END);
203
assert(cs->current.cdw + 3 <= cs->current.max_dw);
204
radeon_emit(cs, PKT3(PKT3_SET_UCONFIG_REG, 1, 0));
205
radeon_emit(cs, (reg - CIK_UCONFIG_REG_OFFSET) >> 2 | (idx << 28));
206
radeon_emit(cs, value);
207
}
208
209
#endif
210
211