aboutsummaryrefslogtreecommitdiff
path: root/libpsn00b/psxgpu
diff options
context:
space:
mode:
authorJohn "Lameguy" Wilbert Villamor <lameguy64@gmail.com>2022-11-03 10:14:22 +0800
committerGitHub <noreply@github.com>2022-11-03 10:14:22 +0800
commit4139331d233b7a962e747c5564fa68a285f81cc8 (patch)
treed4d3374afd5e36e8580cc424ab2c63ee9e7d357c /libpsn00b/psxgpu
parente08a3d9366f8ca14a76b3dd569dac1fb9f569748 (diff)
parent37d963f724113e45d15aa9b8ee86baa9c4362b8f (diff)
downloadpsn00bsdk-4139331d233b7a962e747c5564fa68a285f81cc8.tar.gz
Merge pull request #60 from spicyjpeg/bugfix
Bugfixes, new serial port API and sound examples
Diffstat (limited to 'libpsn00b/psxgpu')
-rw-r--r--libpsn00b/psxgpu/common.c78
-rw-r--r--libpsn00b/psxgpu/image.c6
2 files changed, 44 insertions, 40 deletions
diff --git a/libpsn00b/psxgpu/common.c b/libpsn00b/psxgpu/common.c
index a262472..9f45f10 100644
--- a/libpsn00b/psxgpu/common.c
+++ b/libpsn00b/psxgpu/common.c
@@ -4,6 +4,7 @@
*/
#include <stdint.h>
+#include <assert.h>
#include <psxetc.h>
#include <psxapi.h>
#include <psxgpu.h>
@@ -37,6 +38,9 @@ static volatile uint16_t _last_hblank;
/* Private interrupt handlers */
+#define _ENTER_CRITICAL() uint16_t mask = IRQ_MASK; IRQ_MASK = 0;
+#define _EXIT_CRITICAL() IRQ_MASK = mask;
+
static void _vblank_handler(void) {
_vblank_counter++;
@@ -50,9 +54,10 @@ static void _gpu_dma_handler(void) {
__asm__ volatile("");
if (--_queue_length) {
- volatile QueueEntry *entry = &_draw_queue[_queue_head++];
- _queue_head %= QUEUE_LENGTH;
+ int head = _queue_head;
+ _queue_head = (head + 1) % QUEUE_LENGTH;
+ volatile QueueEntry *entry = &_draw_queue[head];
entry->func(entry->arg1, entry->arg2, entry->arg3);
} else {
GPU_GP1 = 0x04000000; // Disable DMA request
@@ -75,7 +80,7 @@ void ResetGraph(int mode) {
_gpu_video_mode = (GPU_GP1 >> 20) & 1;
ExitCriticalSection();
- _sdk_log("psxgpu: setup done, default mode is %s\n", _gpu_video_mode ? "PAL" : "NTSC");
+ _sdk_log("setup done, default mode is %s\n", _gpu_video_mode ? "PAL" : "NTSC");
}
if (mode == 3) {
@@ -113,8 +118,7 @@ static void _default_vsync_halt(void) {
return;
}
- _sdk_log("psxgpu: VSync() timeout\n");
- _sdk_dump_log();
+ _sdk_log("VSync() timeout\n");
ChangeClearPAD(0);
ChangeClearRCnt(3, 0);
}
@@ -130,7 +134,6 @@ int VSync(int mode) {
// Wait for at least one vertical blank event to occur.
do {
- _sdk_dump_log();
_vsync_halt_func();
// If interlaced mode is enabled, wait until the GPU starts displaying
@@ -146,19 +149,22 @@ int VSync(int mode) {
}
void *VSyncHaltFunction(void (*func)(void)) {
+ //_ENTER_CRITICAL();
+
void *old_callback = _vsync_halt_func;
_vsync_halt_func = func;
+ //_EXIT_CRITICAL();
return old_callback;
}
void *VSyncCallback(void (*func)(void)) {
- EnterCriticalSection();
+ _ENTER_CRITICAL();
void *old_callback = _vsync_callback;
_vsync_callback = func;
- ExitCriticalSection();
+ _EXIT_CRITICAL();
return old_callback;
}
@@ -177,37 +183,36 @@ int EnqueueDrawOp(
// to checking if DMA is busy; disabling them afterwards would create a
// race condition where the DMA transfer could end while interrupts are
// being disabled. Interrupts are disabled through the IRQ_MASK register
- // rather than by calling EnterCriticalSection() for performance reasons.
- uint16_t mask = IRQ_MASK;
- IRQ_MASK = 0;
-
- if (_queue_length) {
- if (_queue_length >= QUEUE_LENGTH) {
- IRQ_MASK = mask;
- _sdk_log("psxgpu: draw queue overflow, dropping commands\n");
- return -1;
- }
+ // rather than via syscalls for performance reasons.
+ _ENTER_CRITICAL();
+ int length = _queue_length;
- int length = _queue_length;
- _queue_length = length + 1;
+ if (!length) {
+ _queue_length = 1;
+ _EXIT_CRITICAL();
- volatile QueueEntry *entry = &_draw_queue[_queue_tail++];
- _queue_tail %= QUEUE_LENGTH;
-
- entry->func = func;
- entry->arg1 = arg1;
- entry->arg2 = arg2;
- entry->arg3 = arg3;
+ func(arg1, arg2, arg3);
+ return 0;
+ }
+ if (length >= QUEUE_LENGTH) {
+ _EXIT_CRITICAL();
- IRQ_MASK = mask;
- return length;
+ _sdk_log("draw queue overflow, dropping commands\n");
+ return -1;
}
- _queue_length = 1;
+ int tail = _queue_tail;
+ _queue_tail = (tail + 1) % QUEUE_LENGTH;
+ _queue_length = length + 1;
+
+ volatile QueueEntry *entry = &_draw_queue[tail];
+ entry->func = func;
+ entry->arg1 = arg1;
+ entry->arg2 = arg2;
+ entry->arg3 = arg3;
- IRQ_MASK = mask;
- func(arg1, arg2, arg3);
- return 0;
+ _EXIT_CRITICAL();
+ return length;
}
int DrawSync(int mode) {
@@ -230,20 +235,19 @@ int DrawSync(int mode) {
while (!(GPU_GP1 & (1 << 26)))
__asm__ volatile("");
} else {
- _sdk_log("psxgpu: DrawSync() timeout\n");
- _sdk_dump_log();
+ _sdk_log("DrawSync() timeout\n");
}
return _queue_length;
}
void *DrawSyncCallback(void (*func)(void)) {
- EnterCriticalSection();
+ _ENTER_CRITICAL();
void *old_callback = _drawsync_callback;
_drawsync_callback = func;
- ExitCriticalSection();
+ _EXIT_CRITICAL();
return old_callback;
}
diff --git a/libpsn00b/psxgpu/image.c b/libpsn00b/psxgpu/image.c
index 968dde5..bbdb7c8 100644
--- a/libpsn00b/psxgpu/image.c
+++ b/libpsn00b/psxgpu/image.c
@@ -4,7 +4,7 @@
*/
#include <stdint.h>
-#include <psxetc.h>
+#include <assert.h>
#include <psxgpu.h>
#include <hwregs_c.h>
@@ -15,11 +15,11 @@
static void _dma_transfer(const RECT *rect, uint32_t *data, int write) {
size_t length = rect->w * rect->h;
if (length % 2)
- _sdk_log("psxgpu: can't transfer an odd number of pixels\n");
+ _sdk_log("can't transfer an odd number of pixels\n");
length /= 2;
if ((length >= DMA_CHUNK_LENGTH) && (length % DMA_CHUNK_LENGTH)) {
- _sdk_log("psxgpu: transfer data length (%d) is not a multiple of %d, rounding\n", length, DMA_CHUNK_LENGTH);
+ _sdk_log("transfer data length (%d) is not a multiple of %d, rounding\n", length, DMA_CHUNK_LENGTH);
length += DMA_CHUNK_LENGTH - 1;
}