sdk-core
v2026.11.05
PS2 SDK - core tier (build-critical EE/IOP modules)
Toggle main menu visibility
Loading...
Searching...
No Matches
vuhw.c
1
/*
2
# _____ ___ ____ ___ ____
3
# ____| | ____| | | |____|
4
# | ___| |____ ___| ____| | \ PS2DEV Open Source Project.
5
#-----------------------------------------------------------------------
6
# (c) 2009 Lion
7
# Licenced under Academic Free License version 2.0
8
# Review ps2sdk README & LICENSE files for further details.
9
*/
10
11
#include <
libvux.h
>
12
#ifndef _EE
13
#include <
string.h
>
14
#endif
15
16
void
Vu0IdMatrix(
VU_MATRIX
*m)
17
{
18
Vu0ResetMatrix(m);
19
}
20
21
void
Vu0ResetMatrix(
VU_MATRIX
*m)
22
{
23
#ifdef _EE
24
__asm__ __volatile__(
25
#
if
__GNUC__ > 3
26
"vmr32.xyzw $vf18, $vf0 \n"
27
"sqc2 $vf0, 0x30(%0) \n"
28
"vmr32.xyzw $vf17, $vf18 \n"
29
"sqc2 $vf18, 0x20(%0) \n"
30
"vmr32.xyzw $vf16, $vf17 \n"
31
"sqc2 $vf17, 0x10(%0) \n"
32
"sqc2 $vf16, 0x00(%0) \n"
33
#
else
34
"vmr32.xyzw vf18, vf00 \n"
35
"sqc2 vf00, 0x30(%0) \n"
36
"vmr32.xyzw vf17, vf18 \n"
37
"sqc2 vf18, 0x20(%0) \n"
38
"vmr32.xyzw vf16, vf17 \n"
39
"sqc2 vf17, 0x10(%0) \n"
40
"sqc2 vf16, 0x00(%0) \n"
41
#endif
42
43
: :
"r"
(m)
44
);
45
#else
46
memset(m, 0,
sizeof
(*m));
47
m->m[3][3] = 1.0f;
48
m->m[2][2] = 1.0f;
49
m->m[1][1] = 1.0f;
50
m->m[0][0] = 1.0f;
51
#endif
52
}
53
54
#if 0
55
void
VuxRotMatrix(
VU_MATRIX
*m,
VU_VECTOR
*r)
56
{
57
VU_MATRIX
mx,my,mz, m0;
58
59
VuxResetMatrix(m);
60
mx = my = mz = m0 = *m;
61
62
63
VuxRotMatrixX(&mx, r->x);
64
VuxRotMatrixY(&my, r->y);
65
VuxRotMatrixZ(&mz, r->z);
66
67
VuxMulMatrix(&mx, &my, &m0);
68
VuxMulMatrix(&m0, &mz, m);
69
}
70
#endif
71
72
void
Vu0TransMatrix(
VU_MATRIX
*m,
VU_VECTOR
*t)
73
{
74
75
#ifdef _EE
76
__asm__ __volatile__ (
77
#
if
__GNUC__ > 3
78
"lqc2 $vf1, 0(%1) \n"
// load 1 qword from 't' to vu's vf1
79
"sqc2 $vf1, 48(%0) \n"
// store vf1 data in 'm' with 48 bytes offset which is m[3][0]
80
#
else
81
"lqc2 vf1, 0(%1) \n"
// load 1 qword from 't' to vu's vf1
82
"sqc2 vf1, 48(%0) \n"
// store vf1 data in 'm' with 48 bytes offset which is m[3][0]
83
#endif
84
85
: :
"r"
(m),
"r"
(t)
86
);
87
#else
88
*(
VU_VECTOR
*)(&m->m[3][0]) = *t;
89
#endif
90
}
91
92
void
Vu0TransMatrixXYZ(
VU_MATRIX
*m,
float
x,
float
y,
float
z)
93
{
94
VU_VECTOR
t;
95
96
t.x = x;
97
t.y = y;
98
t.z = z;
99
t.w = 1.0f;
100
101
Vu0TransMatrix(m, &t);
102
}
103
104
/*
105
THIS SCALE IS CROP, CLEAN IT UP ************************(99999999(****************************
106
*/
107
108
void
Vu0ScaleMatrix(
VU_MATRIX
*m,
VU_VECTOR
*s)
109
{
110
111
#ifdef _EE
112
__asm__ __volatile__ (
113
#
if
__GNUC__ > 3
114
"lqc2 $vf1, 0(%1) \n"
// load 1 qword from 't' to vu's vf1
115
"lqc2 $vf10, 0(%0) \n"
// load m[0][0]
116
"lqc2 $vf11, 16(%0) \n"
// load m[1][0]
117
"lqc2 $vf12, 32(%0) \n"
// load m[2][0]
118
// "lqc2 $vf123,48(%0) \n" // load m[3][0]
119
120
"vmulx.x $vf10, $vf10, $vf1x \n"
// multiply [0][0] by s->x and store in [0][0]
121
"vmuly.y $vf11, $vf11, $vf1y \n"
122
"vmulz.z $vf12, $vf12, $vf1z \n"
123
124
125
"sqc2 $vf10, 0(%0) \n"
// store v m[0][0]
126
"sqc2 $vf11, 16(%0) \n"
// store v m[1][0]
127
"sqc2 $vf12, 32(%0) \n"
// store v m[2][0]
128
// "sqc2 $vf1, 48(%0) \n" // store v m[3][0]
129
#
else
130
"lqc2 vf1, 0(%1) \n"
// load 1 qword from 't' to vu's vf1
131
"lqc2 vf10, 0(%0) \n"
// load m[0][0]
132
"lqc2 vf11, 16(%0) \n"
// load m[1][0]
133
"lqc2 vf12, 32(%0) \n"
// load m[2][0]
134
// "lqc2 vf123,48(%0) \n" // load m[3][0]
135
136
"vmulx.x vf10, vf10, vf1x \n"
// multiply [0][0] by s->x and store in [0][0]
137
"vmuly.y vf11, vf11, vf1y \n"
138
"vmulz.z vf12, vf12, vf1z \n"
139
140
141
"sqc2 vf10, 0(%0) \n"
// store v m[0][0]
142
"sqc2 vf11, 16(%0) \n"
// store v m[1][0]
143
"sqc2 vf12, 32(%0) \n"
// store v m[2][0]
144
// "sqc2 vf1, 48(%0) \n" // store v m[3][0]
145
#endif
146
147
: :
"r"
(m),
"r"
(s)
148
);
149
#else
150
m->m[0][0] *= s->x;
151
m->m[1][1] *= s->y;
152
m->m[2][2] *= s->z;
153
#endif
154
155
}
156
157
void
Vu0ScaleMatrixXYZ(
VU_MATRIX
*m,
float
x,
float
y,
float
z)
158
{
159
VU_VECTOR
s;
160
s.x = x;
161
s.y = y;
162
s.z = z;
163
s.w = 1.0f;
164
165
Vu0ScaleMatrix(m, &s);
166
167
}
168
169
void
Vu0MulMatrix(
VU_MATRIX
*m0,
VU_MATRIX
*m1,
VU_MATRIX
*out)
170
{
171
172
#ifdef _EE
173
__asm__ __volatile__ (
174
#
if
__GNUC__ > 3
175
"lqc2 $vf1, 0x00(%0) \n"
176
"lqc2 $vf2, 0x10(%0) \n"
177
"lqc2 $vf3, 0x20(%0) \n"
178
"lqc2 $vf4, 0x30(%0) \n"
179
"lqc2 $vf5, 0x00(%1) \n"
180
"lqc2 $vf6, 0x10(%1) \n"
181
"lqc2 $vf7, 0x20(%1) \n"
182
"lqc2 $vf8, 0x30(%1) \n"
183
"vmulax.xyzw $ACC, $vf5, $vf1 \n"
184
"vmadday.xyzw $ACC, $vf6, $vf1 \n"
185
"vmaddaz.xyzw $ACC, $vf7, $vf1 \n"
186
"vmaddw.xyzw $vf1, $vf8, $vf1 \n"
187
"vmulax.xyzw $ACC, $vf5, $vf2 \n"
188
"vmadday.xyzw $ACC, $vf6, $vf2 \n"
189
"vmaddaz.xyzw $ACC, $vf7, $vf2 \n"
190
"vmaddw.xyzw $vf2, $vf8, $vf2 \n"
191
"vmulax.xyzw $ACC, $vf5, $vf3 \n"
192
"vmadday.xyzw $ACC, $vf6, $vf3 \n"
193
"vmaddaz.xyzw $ACC, $vf7, $vf3 \n"
194
"vmaddw.xyzw $vf3, $vf8, $vf3 \n"
195
"vmulax.xyzw $ACC, $vf5, $vf4 \n"
196
"vmadday.xyzw $ACC, $vf6, $vf4 \n"
197
"vmaddaz.xyzw $ACC, $vf7, $vf4 \n"
198
"vmaddw.xyzw $vf4, $vf8, $vf4 \n"
199
"sqc2 $vf1, 0x00(%2) \n"
200
"sqc2 $vf2, 0x10(%2) \n"
201
"sqc2 $vf3, 0x20(%2) \n"
202
"sqc2 $vf4, 0x30(%2) \n"
203
#
else
204
"lqc2 vf1, 0x00(%0) \n"
205
"lqc2 vf2, 0x10(%0) \n"
206
"lqc2 vf3, 0x20(%0) \n"
207
"lqc2 vf4, 0x30(%0) \n"
208
"lqc2 vf5, 0x00(%1) \n"
209
"lqc2 vf6, 0x10(%1) \n"
210
"lqc2 vf7, 0x20(%1) \n"
211
"lqc2 vf8, 0x30(%1) \n"
212
"vmulax.xyzw ACC, vf5, vf1 \n"
213
"vmadday.xyzw ACC, vf6, vf1 \n"
214
"vmaddaz.xyzw ACC, vf7, vf1 \n"
215
"vmaddw.xyzw vf1, vf8, vf1 \n"
216
"vmulax.xyzw ACC, vf5, vf2 \n"
217
"vmadday.xyzw ACC, vf6, vf2 \n"
218
"vmaddaz.xyzw ACC, vf7, vf2 \n"
219
"vmaddw.xyzw vf2, vf8, vf2 \n"
220
"vmulax.xyzw ACC, vf5, vf3 \n"
221
"vmadday.xyzw ACC, vf6, vf3 \n"
222
"vmaddaz.xyzw ACC, vf7, vf3 \n"
223
"vmaddw.xyzw vf3, vf8, vf3 \n"
224
"vmulax.xyzw ACC, vf5, vf4 \n"
225
"vmadday.xyzw ACC, vf6, vf4 \n"
226
"vmaddaz.xyzw ACC, vf7, vf4 \n"
227
"vmaddw.xyzw vf4, vf8, vf4 \n"
228
"sqc2 vf1, 0x00(%2) \n"
229
"sqc2 vf2, 0x10(%2) \n"
230
"sqc2 vf3, 0x20(%2) \n"
231
"sqc2 vf4, 0x30(%2) \n"
232
#endif
233
: :
"r"
(m0),
"r"
(m1),
"r"
(out)
234
);
235
#else
236
memset(out, 0,
sizeof
(*out));
237
int
i;
238
for
(i = 0; i < 4; i += 1)
239
{
240
int
j;
241
for
(j = 0; j < 4; j += 1)
242
{
243
int
k;
244
for
(k = 0; k < 4; k += 1)
245
{
246
out->m[i][k] += m1->m[j][k] * m0->m[i][j];
247
}
248
}
249
}
250
#endif
251
}
252
253
void
Vu0InverseMatrix(
VU_MATRIX
*in,
VU_MATRIX
*out)
254
{
255
(void)in;
256
(void)out;
257
}
258
259
void
Vu0ApplyMatrix(
VU_MATRIX
*m,
VU_VECTOR
*v0,
VU_VECTOR
*out)
260
{
261
#ifdef _EE
262
__asm__ __volatile__(
263
#
if
__GNUC__ > 3
264
"lqc2 $vf20, 0x00(%1) \n"
265
"lqc2 $vf16, 0x00(%0) \n"
266
"lqc2 $vf17, 0x10(%0) \n"
267
"lqc2 $vf18, 0x20(%0) \n"
268
"lqc2 $vf19, 0x30(%0) \n"
269
"vmulax.xyzw $ACC, $vf16,$vf20 \n"
270
"vmadday.xyzw $ACC, $vf17,$vf20 \n"
271
"vmaddaz.xyzw $ACC, $vf18,$vf20 \n"
272
"vmaddw.xyzw $vf20, $vf19,$vf20 \n"
273
"sqc2 $vf20,0x00(%2) \n"
274
#
else
275
"lqc2 vf20, 0x00(%1) \n"
276
"lqc2 vf16, 0x00(%0) \n"
277
"lqc2 vf17, 0x10(%0) \n"
278
"lqc2 vf18, 0x20(%0) \n"
279
"lqc2 vf19, 0x30(%0) \n"
280
"vmulax.xyzw ACC, vf16,vf20 \n"
281
"vmadday.xyzw ACC, vf17,vf20 \n"
282
"vmaddaz.xyzw ACC, vf18,vf20 \n"
283
"vmaddw.xyzw vf20, vf19,vf20 \n"
284
"sqc2 vf20,0x00(%2) \n"
285
#endif
286
: :
"r"
(m),
"r"
(v0),
"r"
(out)
287
);
288
#else
289
out->x = m->m[0][0] * v0->x + m->m[1][0] * v0->y + m->m[2][0] * v0->z + m->m[3][0] * v0->w;
290
out->y = m->m[0][1] * v0->x + m->m[1][1] * v0->y + m->m[2][1] * v0->z + m->m[3][1] * v0->w;
291
out->z = m->m[0][2] * v0->x + m->m[1][2] * v0->y + m->m[2][2] * v0->z + m->m[3][2] * v0->w;
292
out->w = m->m[0][3] * v0->x + m->m[1][3] * v0->y + m->m[2][3] * v0->z + m->m[3][3] * v0->w;
293
#endif
294
295
}
296
297
void
Vu0ApplyRotMatrix(
VU_MATRIX
*m,
VU_VECTOR
*v0,
VU_VECTOR
*out)
298
{
299
#ifdef _EE
300
__asm__ __volatile__(
301
#
if
__GNUC__ > 3
302
"lqc2 $vf20, 0x00(%1) \n"
303
"lqc2 $vf16, 0x00(%0) \n"
304
"lqc2 $vf17, 0x10(%0) \n"
305
"lqc2 $vf18, 0x20(%0) \n"
306
"vmulax.xyz $ACC, $vf16,$vf20 \n"
307
"vmadday.xyz $ACC, $vf17,$vf20 \n"
308
"vmaddz.xyz $vf20, $vf18,$vf20 \n"
309
"vmulw.w $vf20, $vf0, $vf0 \n"
// out->w = 1.0f
310
"sqc2 $vf20, 0x00(%2) \n"
// copy result to out
311
#
else
312
"lqc2 vf20, 0x00(%1) \n"
313
"lqc2 vf16, 0x00(%0) \n"
314
"lqc2 vf17, 0x10(%0) \n"
315
"lqc2 vf18, 0x20(%0) \n"
316
"vmulax.xyz ACC, vf16,vf20 \n"
317
"vmadday.xyz ACC, vf17,vf20 \n"
318
"vmaddz.xyz vf20, vf18,vf20 \n"
319
"vmulw.w vf20, vf0, vf0 \n"
// out->w = 1.0f
320
"sqc2 vf20, 0x00(%2) \n"
// copy result to out
321
#endif
322
: :
"r"
(m),
"r"
(v0),
"r"
(out)
323
);
324
#else
325
out->x = m->m[0][0] * v0->x + m->m[1][0] * v0->y + m->m[2][0] * v0->z;
326
out->y = m->m[0][1] * v0->x + m->m[1][1] * v0->y + m->m[2][1] * v0->z;
327
out->z = m->m[0][2] * v0->x + m->m[1][2] * v0->y + m->m[2][2] * v0->z;
328
out->w = 1.0f;
329
#endif
330
331
}
332
333
void
Vu0CopyMatrix(
VU_MATRIX
*dest,
VU_MATRIX
*src)
334
{
335
336
#ifdef _EE
337
__asm__ __volatile__ (
338
#
if
__GNUC__ > 3
339
"lqc2 $vf1, 0(%1) \n"
// load 1 qword from ee
340
"lqc2 $vf2, 16(%1) \n"
// load 1 qword from ee
341
"lqc2 $vf3, 32(%1) \n"
// load 1 qword from ee
342
"lqc2 $vf4, 48(%1) \n"
// load 1 qword from ee
343
344
"sqc2 $vf1, 0(%0) \n"
// store 1 qword in ee
345
"sqc2 $vf2, 16(%0) \n"
// store 1 qword in ee
346
"sqc2 $vf3, 32(%0) \n"
// store 1 qword in ee
347
"sqc2 $vf4, 48(%0) \n"
// store 1 qword in ee
348
#
else
349
"lqc2 vf1, 0(%1) \n"
// load 1 qword from ee
350
"lqc2 vf2, 16(%1) \n"
// load 1 qword from ee
351
"lqc2 vf3, 32(%1) \n"
// load 1 qword from ee
352
"lqc2 vf4, 48(%1) \n"
// load 1 qword from ee
353
354
"sqc2 vf1, 0(%0) \n"
// store 1 qword in ee
355
"sqc2 vf2, 16(%0) \n"
// store 1 qword in ee
356
"sqc2 vf3, 32(%0) \n"
// store 1 qword in ee
357
"sqc2 vf4, 48(%0) \n"
// store 1 qword in ee
358
#endif
359
360
: :
"r"
(dest),
"r"
(src)
361
);
362
#else
363
*dest = *src;
364
#endif
365
}
366
367
float
Vu0DotProduct(
VU_VECTOR
*v0,
VU_VECTOR
*v1)
368
{
369
float
ret=0;
370
371
#ifdef _EE
372
// "r" is a GPR constraint - qmfc2 copies vf3's raw bit pattern into a
373
// GPR, it's not a real int<->float conversion. GCC tolerated binding
374
// that straight to a float-typed C variable; clang requires an
375
// integer-typed operand for "r", so the raw bits go into a temp GPR
376
// value first and get reinterpreted as float via union afterward.
377
union
{
unsigned
int
i;
float
f; } raw;
378
__asm__ __volatile__ (
379
#
if
__GNUC__ > 3
380
"lqc2 $vf1, 0(%1) \n"
// load 1 qword from ee
381
"lqc2 $vf2, 0(%2) \n"
// load 1 qword from ee
382
383
"vmul.xyz $vf3, $vf1, $vf2 \n"
// mul v0 by v1
384
385
"vaddy.x $vf3, $vf3, $vf3y \n"
// add x+y and store in x
386
"vaddz.x $vf3, $vf3, $vf3z \n"
// add z+x and store in x
387
388
"qmfc2 %0, $vf3 \n"
// copy vector to ee reg
389
#
else
390
"lqc2 vf1, 0(%1) \n"
// load 1 qword from ee
391
"lqc2 vf2, 0(%2) \n"
// load 1 qword from ee
392
393
"vmul.xyz vf3, vf1, vf2 \n"
// mul v0 by v1
394
395
"vaddy.x vf3, vf3, vf3y \n"
// add x+y and store in x
396
"vaddz.x vf3, vf3, vf3z \n"
// add z+x and store in x
397
398
"qmfc2 %0, vf3 \n"
// copy vector to ee reg
399
#endif
400
:
"=r"
(raw.i) :
"r"
(v0),
"r"
(v1)
401
);
402
ret = raw.f;
403
#else
404
ret = (v0->x * v1->x + v0->y * v1->y + v0->z * v1->z);
405
#endif
406
407
return
ret;
408
}
libvux.h
string.h
VU_MATRIX
Definition
libvux.h:37
VU_VECTOR
Definition
libvux.h:45
core
libvux
src
vuhw.c
Generated by
1.18.0