1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
|
#ifndef COMMON_CMDBUF_H
#define COMMON_CMDBUF_H
#include "radeon_bocs_wrapper.h"
void rcommonEnsureCmdBufSpace(radeonContextPtr rmesa, int dwords, const char *caller);
int rcommonFlushCmdBuf(radeonContextPtr rmesa, const char *caller);
int rcommonFlushCmdBufLocked(radeonContextPtr rmesa, const char *caller);
void rcommonInitCmdBuf(radeonContextPtr rmesa);
void rcommonDestroyCmdBuf(radeonContextPtr rmesa);
void rcommonBeginBatch(radeonContextPtr rmesa,
int n,
int dostate,
const char *file,
const char *function,
int line);
#define RADEON_CP_PACKET3_NOP 0xC0001000
#define RADEON_CP_PACKET3_NEXT_CHAR 0xC0001900
#define RADEON_CP_PACKET3_PLY_NEXTSCAN 0xC0001D00
#define RADEON_CP_PACKET3_SET_SCISSORS 0xC0001E00
#define RADEON_CP_PACKET3_3D_RNDR_GEN_INDX_PRIM 0xC0002300
#define RADEON_CP_PACKET3_LOAD_MICROCODE 0xC0002400
#define RADEON_CP_PACKET3_WAIT_FOR_IDLE 0xC0002600
#define RADEON_CP_PACKET3_3D_DRAW_VBUF 0xC0002800
#define RADEON_CP_PACKET3_3D_DRAW_IMMD 0xC0002900
#define RADEON_CP_PACKET3_3D_DRAW_INDX 0xC0002A00
#define RADEON_CP_PACKET3_LOAD_PALETTE 0xC0002C00
#define RADEON_CP_PACKET3_3D_LOAD_VBPNTR 0xC0002F00
#define RADEON_CP_PACKET3_CNTL_PAINT 0xC0009100
#define RADEON_CP_PACKET3_CNTL_BITBLT 0xC0009200
#define RADEON_CP_PACKET3_CNTL_SMALLTEXT 0xC0009300
#define RADEON_CP_PACKET3_CNTL_HOSTDATA_BLT 0xC0009400
#define RADEON_CP_PACKET3_CNTL_POLYLINE 0xC0009500
#define RADEON_CP_PACKET3_CNTL_POLYSCANLINES 0xC0009800
#define RADEON_CP_PACKET3_CNTL_PAINT_MULTI 0xC0009A00
#define RADEON_CP_PACKET3_CNTL_BITBLT_MULTI 0xC0009B00
#define RADEON_CP_PACKET3_CNTL_TRANS_BITBLT 0xC0009C00
/* r6xx/r7xx packet 3 type offsets */
#define R600_SET_CONFIG_REG_OFFSET 0x00008000
#define R600_SET_CONFIG_REG_END 0x0000ac00
#define R600_SET_CONTEXT_REG_OFFSET 0x00028000
#define R600_SET_CONTEXT_REG_END 0x00029000
#define R600_SET_ALU_CONST_OFFSET 0x00030000
#define R600_SET_ALU_CONST_END 0x00032000
#define R600_SET_RESOURCE_OFFSET 0x00038000
#define R600_SET_RESOURCE_END 0x0003c000
#define R600_SET_SAMPLER_OFFSET 0x0003c000
#define R600_SET_SAMPLER_END 0x0003cff0
#define R600_SET_CTL_CONST_OFFSET 0x0003cff0
#define R600_SET_CTL_CONST_END 0x0003e200
#define R600_SET_LOOP_CONST_OFFSET 0x0003e200
#define R600_SET_LOOP_CONST_END 0x0003e380
#define R600_SET_BOOL_CONST_OFFSET 0x0003e380
#define R600_SET_BOOL_CONST_END 0x00040000
/* r6xx/r7xx packet 3 types */
#define R600_IT_INDIRECT_BUFFER_END 0x00001700
#define R600_IT_SET_PREDICATION 0x00002000
#define R600_IT_REG_RMW 0x00002100
#define R600_IT_COND_EXEC 0x00002200
#define R600_IT_PRED_EXEC 0x00002300
#define R600_IT_START_3D_CMDBUF 0x00002400
#define R600_IT_DRAW_INDEX_2 0x00002700
#define R600_IT_CONTEXT_CONTROL 0x00002800
#define R600_IT_DRAW_INDEX_IMMD_BE 0x00002900
#define R600_IT_INDEX_TYPE 0x00002A00
#define R600_IT_DRAW_INDEX 0x00002B00
#define R600_IT_DRAW_INDEX_AUTO 0x00002D00
#define R600_IT_DRAW_INDEX_IMMD 0x00002E00
#define R600_IT_NUM_INSTANCES 0x00002F00
#define R600_IT_STRMOUT_BUFFER_UPDATE 0x00003400
#define R600_IT_INDIRECT_BUFFER_MP 0x00003800
#define R600_IT_MEM_SEMAPHORE 0x00003900
#define R600_IT_MPEG_INDEX 0x00003A00
#define R600_IT_WAIT_REG_MEM 0x00003C00
#define R600_IT_MEM_WRITE 0x00003D00
#define R600_IT_INDIRECT_BUFFER 0x00003200
#define R600_IT_CP_INTERRUPT 0x00004000
#define R600_IT_SURFACE_SYNC 0x00004300
#define R600_IT_ME_INITIALIZE 0x00004400
#define R600_IT_COND_WRITE 0x00004500
#define R600_IT_EVENT_WRITE 0x00004600
#define R600_IT_EVENT_WRITE_EOP 0x00004700
#define R600_IT_ONE_REG_WRITE 0x00005700
#define R600_IT_SET_CONFIG_REG 0x00006800
#define R600_IT_SET_CONTEXT_REG 0x00006900
#define R600_IT_SET_ALU_CONST 0x00006A00
#define R600_IT_SET_BOOL_CONST 0x00006B00
#define R600_IT_SET_LOOP_CONST 0x00006C00
#define R600_IT_SET_RESOURCE 0x00006D00
#define R600_IT_SET_SAMPLER 0x00006E00
#define R600_IT_SET_CTL_CONST 0x00006F00
#define R600_IT_SURFACE_BASE_UPDATE 0x00007300
#define CP_PACKET2 (2 << 30)
#define CP_PACKET0(reg, n) (RADEON_CP_PACKET0 | ((n)<<16) | ((reg)>>2))
#define CP_PACKET0_ONE(reg, n) (RADEON_CP_PACKET0 | RADEON_CP_PACKET0_ONE_REG_WR | ((n)<<16) | ((reg)>>2))
#define CP_PACKET3(pkt, n) (RADEON_CP_PACKET3 | (pkt) | ((n) << 16))
/**
* Every function writing to the command buffer needs to declare this
* to get the necessary local variables.
*/
#define BATCH_LOCALS(rmesa) \
const radeonContextPtr b_l_rmesa = rmesa
/**
* Prepare writing n dwords to the command buffer,
* including producing any necessary state emits on buffer wraparound.
*/
#define BEGIN_BATCH(n) rcommonBeginBatch(b_l_rmesa, n, 1, __FILE__, __FUNCTION__, __LINE__)
/**
* Same as BEGIN_BATCH, but do not cause automatic state emits.
*/
#define BEGIN_BATCH_NO_AUTOSTATE(n) rcommonBeginBatch(b_l_rmesa, n, 0, __FILE__, __FUNCTION__, __LINE__)
/**
* Write one dword to the command buffer.
*/
#define OUT_BATCH(data) \
do { \
radeon_cs_write_dword(b_l_rmesa->cmdbuf.cs, data);\
} while(0)
/**
* Write a relocated dword to the command buffer.
*/
#define OUT_BATCH_RELOC(data, bo, offset, rd, wd, flags) \
do { \
if (0 && offset) { \
fprintf(stderr, "(%s:%s:%d) offset : %d\n", \
__FILE__, __FUNCTION__, __LINE__, offset); \
} \
radeon_cs_write_dword(b_l_rmesa->cmdbuf.cs, offset); \
radeon_cs_write_reloc(b_l_rmesa->cmdbuf.cs, \
bo, rd, wd, flags); \
if (!b_l_rmesa->radeonScreen->kernel_mm) \
b_l_rmesa->cmdbuf.cs->section_cdw += 2; \
} while(0)
/**
* Write n dwords from ptr to the command buffer.
*/
#define OUT_BATCH_TABLE(ptr,n) \
do { \
int _i; \
for (_i=0; _i < n; _i++) {\
radeon_cs_write_dword(b_l_rmesa->cmdbuf.cs, ptr[_i]);\
}\
} while(0)
/**
* Finish writing dwords to the command buffer.
* The number of (direct or indirect) OUT_BATCH calls between the previous
* BEGIN_BATCH and END_BATCH must match the number specified at BEGIN_BATCH time.
*/
#define END_BATCH() \
do { \
radeon_cs_end(b_l_rmesa->cmdbuf.cs, __FILE__, __FUNCTION__, __LINE__);\
} while(0)
/**
* After the last END_BATCH() of rendering, this indicates that flushing
* the command buffer now is okay.
*/
#define COMMIT_BATCH() \
do { \
} while(0)
/** Single register write to command buffer; requires 2 dwords. */
#define OUT_BATCH_REGVAL(reg, val) \
OUT_BATCH(cmdpacket0(b_l_rmesa->radeonScreen, (reg), 1)); \
OUT_BATCH((val))
/** Continuous register range write to command buffer; requires 1 dword,
* expects count dwords afterwards for register contents. */
#define OUT_BATCH_REGSEQ(reg, count) \
OUT_BATCH(cmdpacket0(b_l_rmesa->radeonScreen, (reg), (count)))
/** Write a 32 bit float to the ring; requires 1 dword. */
#define OUT_BATCH_FLOAT32(f) \
OUT_BATCH(radeonPackFloat32((f)))
/* R600/R700 */
#define R600_OUT_BATCH_REGS(reg, num) \
do { \
if ((reg) >= R600_SET_CONFIG_REG_OFFSET && (reg) < R600_SET_CONFIG_REG_END) { \
OUT_BATCH(CP_PACKET3(R600_IT_SET_CONFIG_REG, (num))); \
OUT_BATCH(((reg) - R600_SET_CONFIG_REG_OFFSET) >> 2); \
} else if ((reg) >= R600_SET_CONTEXT_REG_OFFSET && (reg) < R600_SET_CONTEXT_REG_END) { \
OUT_BATCH(CP_PACKET3(R600_IT_SET_CONTEXT_REG, (num))); \
OUT_BATCH(((reg) - R600_SET_CONTEXT_REG_OFFSET) >> 2); \
} else if ((reg) >= R600_SET_ALU_CONST_OFFSET && (reg) < R600_SET_ALU_CONST_END) { \
OUT_BATCH(CP_PACKET3(R600_IT_SET_ALU_CONST, (num))); \
OUT_BATCH(((reg) - R600_SET_ALU_CONST_OFFSET) >> 2); \
} else if ((reg) >= R600_SET_RESOURCE_OFFSET && (reg) < R600_SET_RESOURCE_END) { \
OUT_BATCH(CP_PACKET3(R600_IT_SET_RESOURCE, (num))); \
OUT_BATCH(((reg) - R600_SET_RESOURCE_OFFSET) >> 2); \
} else if ((reg) >= R600_SET_SAMPLER_OFFSET && (reg) < R600_SET_SAMPLER_END) { \
OUT_BATCH(CP_PACKET3(R600_IT_SET_SAMPLER, (num))); \
OUT_BATCH(((reg) - R600_SET_SAMPLER_OFFSET) >> 2); \
} else if ((reg) >= R600_SET_CTL_CONST_OFFSET && (reg) < R600_SET_CTL_CONST_END) { \
OUT_BATCH(CP_PACKET3(R600_IT_SET_CTL_CONST, (num))); \
OUT_BATCH(((reg) - R600_SET_CTL_CONST_OFFSET) >> 2); \
} else if ((reg) >= R600_SET_LOOP_CONST_OFFSET && (reg) < R600_SET_LOOP_CONST_END) { \
OUT_BATCH(CP_PACKET3(R600_IT_SET_LOOP_CONST, (num))); \
OUT_BATCH(((reg) - R600_SET_LOOP_CONST_OFFSET) >> 2); \
} else if ((reg) >= R600_SET_BOOL_CONST_OFFSET && (reg) < R600_SET_BOOL_CONST_END) { \
OUT_BATCH(CP_PACKET3(R600_IT_SET_BOOL_CONST, (num))); \
OUT_BATCH(((reg) - R600_SET_BOOL_CONST_OFFSET) >> 2); \
} else { \
OUT_BATCH(cmdpacket0(b_l_rmesa->radeonScreen, (reg), (num))); \
} \
} while (0)
/** Single register write to command buffer; requires 3 dwords for most things. */
#define R600_OUT_BATCH_REGVAL(reg, val) \
R600_OUT_BATCH_REGS((reg), 1); \
OUT_BATCH((val))
/** Continuous register range write to command buffer; requires 1 dword,
* expects count dwords afterwards for register contents. */
#define R600_OUT_BATCH_REGSEQ(reg, count) \
R600_OUT_BATCH_REGS((reg), (count))
/* Fire the buffered vertices no matter what.
*/
static INLINE void radeon_firevertices(radeonContextPtr radeon)
{
if (radeon->cmdbuf.cs->cdw || radeon->dma.flush )
radeonFlush(radeon->glCtx);
}
#endif
|