KallistiOS git master
Independent SDK for the Sega Dreamcast
Loading...
Searching...
No Matches
sq.h
Go to the documentation of this file.
1/* KallistiOS ##version##
2
3 kernel/arch/dreamcast/include/dc/sq.h
4 Copyright (C) 2000-2001 Andrew Kieschnick
5 Copyright (C) 2023 Falco Girgis
6 Copyright (C) 2023 Ruslan Rostovtsev
7 Copyright (C) 2023-2024 Andy Barajas
8*/
9
10/** \file dc/sq.h
11 \ingroup store_queues
12 \brief Functions to access the SH4 Store Queues.
13
14 \author Andrew Kieschnick
15 \author Falco Girgis
16 \author Andy Barajas
17 \author Ruslan Rostovtsev
18*/
19
20/** \defgroup store_queues Store Queues
21 \brief SH4 CPU Peripheral for burst memory transactions.
22 \ingroup system
23
24 The store queues are a way to do efficient burst transfers from the CPU to
25 external memory. They can be used in a variety of ways, such as to transfer
26 a texture to PVR memory. The transfers are in units of 32-bytes, and the
27 destinations must be 32-byte aligned.
28
29 \note
30 Mastery over knowing when and how to utilize the store queues is
31 important when trying to push the limits of the Dreamcast, specifically
32 when transferring chunks of data between regions of memory. It is often
33 the case that the DMA is faster for transactions which are consistently
34 large; however, the store queues tend to have better performance and
35 have less configuration overhead when bursting smaller chunks of data.
36*/
37
38#ifndef __DC_SQ_H
39#define __DC_SQ_H
40
41#include <sys/cdefs.h>
42__BEGIN_DECLS
43
44#include <stdint.h>
45#include <arch/memory.h>
46#include <arch/cache.h>
47
48/** \brief Mask dest to Store Queue area as address
49 \ingroup store_queues
50*/
51#define SQ_MASK_DEST_ADDR(dest) \
52 (MEM_AREA_SQ_BASE | ((uintptr_t)(dest) & 0x03ffffe0))
53
54/** \brief Mask dest to Store Queue area as pointer
55 \ingroup store_queues
56*/
57#define SQ_MASK_DEST(dest) \
58 ((uint32_t *)(void *) SQ_MASK_DEST_ADDR(dest))
59
60/** \brief Lock Store Queues
61 \ingroup store_queues
62
63 Locks the store queues so that they cannot be used from another thread
64 until unlocked.
65
66 \warning
67 This function is called automatically by the store queue API provided by KOS;
68 however, it must be called manually when driving the SQs directly from outside
69 of this API.
70
71 \param dest The destination address.
72 \return The translated address that can be directly written to.
73
74 \sa sq_unlock()
75*/
76uint32_t *sq_lock(void *dest);
77
78/** \brief Unlock Store Queues
79 \ingroup store_queues
80
81 Unlocks the store queues so that they can be used from any thread.
82
83 \note
84 sq_lock() should've already been called previously.
85
86 \warning
87 sq_lock() and sq_unlock() are called automatically by the store queue API provided
88 by KOS; however, they must be called manually when driving the SQs directly from
89 outside this API.
90
91 \sa sq_lock()
92*/
93void sq_unlock(void);
94
95/** \brief Wait for both Store Queues to complete
96 \ingroup store_queues
97
98 Wait for both store queues to complete by writing to SQ area.
99
100 \sa sq_lock()
101*/
102void sq_wait(void);
103
104/** \brief Write-back one Store Queue
105 \ingroup store_queues
106
107 Initiates write-back from SQ buffer to external memory.
108
109 \param dest The address to copy to (32-byte aligned).
110
111 \sa sq_wait()
112*/
113#define sq_flush(dest) dcache_wback_sq(dest)
114
115/** \brief Copy a block of memory.
116 \ingroup store_queues
117
118 This function is similar to memcpy4(), but uses the store queues to do its
119 work.
120
121 \warning
122 The dest pointer must be at least 32-byte aligned, the src pointer
123 must be at least 4-byte aligned (8-byte aligned uses fast path),
124 and n must be a multiple of 32!
125
126 \param dest The address to copy to (32-byte aligned).
127 \param src The address to copy from (32-bit (4/8-byte) aligned).
128 \param n The number of bytes to copy (multiple of 32).
129 \return The original value of dest.
130
131 \sa sq_fast_cpy()
132*/
133void *sq_cpy(void *dest, const void *src, size_t n);
134
135/** \brief Copy a block of memory.
136 \ingroup store_queues
137
138 This function is similar to sq_cpy() but expects the user to lock/unlock
139 the store queues before and after as well as having different requirements
140 for the params.
141
142 \warning
143 The dest pointer must be at least 32-byte aligned that already has been
144 masked by SQ_MASK_DEST(), the src pointer must be at least 8-byte aligned,
145 and n must be the number of 32-byte blocks you want to copy.
146
147 \param dest The store queue address to copy to (32-byte aligned).
148 \param src The address to copy from (8-byte aligned).
149 \param n The number of 32-byte blocks to copy.
150 \return The original value of dest.
151
152 \sa sq_cpy()
153 */
154void *sq_fast_cpy(void *dest, const void *src, size_t n);
155
156/** \brief Set a block of memory to an 8-bit value.
157 \ingroup store_queues
158
159 This function is similar to calling memset(), but uses the store queues to
160 do its work.
161
162 \warning
163 The dest pointer must be a 32-byte aligned with n being a multiple of 32,
164 and only the low 8-bits are used from c.
165
166 \param dest The address to begin setting at (32-byte aligned).
167 \param c The value to set (in the low 8-bits).
168 \param n The number of bytes to set (multiple of 32).
169 \return The original value of dest.
170
171 \sa sq_set16(), sq_set32()
172*/
173void *sq_set(void *dest, uint32_t c, size_t n);
174
175/** \brief Set a block of memory to a 16-bit value.
176 \ingroup store_queues
177
178 This function is similar to calling memset2(), but uses the store queues to
179 do its work.
180
181 \warning
182 The dest pointer must be a 32-byte aligned with n being a multiple of 32,
183 and only the low 16-bits are used from c.
184
185 \param dest The address to begin setting at (32-byte aligned).
186 \param c The value to set (in the low 16-bits).
187 \param n The number of bytes to set (multiple of 32).
188 \return The original value of dest.
189
190 \sa sq_set(), sq_set32()
191*/
192void *sq_set16(void *dest, uint32_t c, size_t n);
193
194/** \brief Set a block of memory to a 32-bit value.
195 \ingroup store_queues
196
197 This function is similar to calling memset4(), but uses the store queues to
198 do its work.
199
200 \warning
201 The dest pointer must be a 32-byte aligned with n being a multiple of 32!
202
203 \param dest The address to begin setting at (32-byte aligned).
204 \param c The value to set (all 32-bits).
205 \param n The number of bytes to set (multiple of 32).
206 \return The original value of dest.
207
208 \sa sq_set(), sq_set16()
209*/
210void *sq_set32(void *dest, uint32_t c, size_t n);
211
212/** \brief Clear a block of memory.
213 \ingroup store_queues
214
215 This function is similar to calling memset() with a value to set of 0, but
216 uses the store queues to do its work.
217
218 \warning
219 The dest pointer must be a 32-byte aligned with n being a multiple of 32!
220
221 \param dest The address to begin clearing at (32-byte aligned).
222 \param n The number of bytes to clear (multiple of 32).
223*/
224void sq_clr(void *dest, size_t n);
225
226
227__END_DECLS
228
229#endif
Cache management functionality.
void * sq_fast_cpy(void *dest, const void *src, size_t n)
Copy a block of memory.
void * sq_set(void *dest, uint32_t c, size_t n)
Set a block of memory to an 8-bit value.
void sq_wait(void)
Wait for both Store Queues to complete.
void * sq_set16(void *dest, uint32_t c, size_t n)
Set a block of memory to a 16-bit value.
void * sq_set32(void *dest, uint32_t c, size_t n)
Set a block of memory to a 32-bit value.
void sq_unlock(void)
Unlock Store Queues.
void * sq_cpy(void *dest, const void *src, size_t n)
Copy a block of memory.
uint32_t * sq_lock(void *dest)
Lock Store Queues.
void sq_clr(void *dest, size_t n)
Clear a block of memory.
Constants for areas of the system memory map.