mirror of
https://gitlab.com/skmp/dca3-game.git
synced 2025-08-31 10:21:45 +02:00
Merge branch 'skmp/async-pedsfx-load' into 'main'
Some checks are pending
re3 conan+cmake / build-cmake (openal, glfw, macos-latest, gl3) (push) Waiting to run
re3 conan+cmake / build-cmake (openal, glfw, ubuntu-18.04, gl3) (push) Waiting to run
re3 conan+cmake / build-cmake (openal, glfw, windows-latest, gl3) (push) Waiting to run
re3 conan+cmake / build-cmake (openal, windows-latest, d3d9) (push) Waiting to run
re3 cmake devkitA64 (Nintendo Switch) / build-nintendo-switch (push) Waiting to run
re3 premake amd64 / build (Debug, win-amd64-librw_d3d9-oal) (push) Waiting to run
re3 premake amd64 / build (Debug, win-amd64-librw_gl3_glfw-oal) (push) Waiting to run
re3 premake amd64 / build (Release, win-amd64-librw_d3d9-oal) (push) Waiting to run
re3 premake amd64 / build (Release, win-amd64-librw_gl3_glfw-oal) (push) Waiting to run
re3 premake x86 / build (Debug, win-x86-librw_d3d9-mss) (push) Waiting to run
re3 premake x86 / build (Debug, win-x86-librw_d3d9-oal) (push) Waiting to run
re3 premake x86 / build (Debug, win-x86-librw_gl3_glfw-mss) (push) Waiting to run
re3 premake x86 / build (Debug, win-x86-librw_gl3_glfw-oal) (push) Waiting to run
re3 premake x86 / build (Release, win-x86-librw_d3d9-mss) (push) Waiting to run
re3 premake x86 / build (Release, win-x86-librw_d3d9-oal) (push) Waiting to run
re3 premake x86 / build (Release, win-x86-librw_gl3_glfw-mss) (push) Waiting to run
re3 premake x86 / build (Release, win-x86-librw_gl3_glfw-oal) (push) Waiting to run
re3 premake x86 / build (Vanilla, win-x86-librw_d3d9-mss) (push) Waiting to run
re3 premake x86 / build (Vanilla, win-x86-librw_d3d9-oal) (push) Waiting to run
re3 premake x86 / build (Vanilla, win-x86-librw_gl3_glfw-mss) (push) Waiting to run
re3 premake x86 / build (Vanilla, win-x86-librw_gl3_glfw-oal) (push) Waiting to run
Some checks are pending
re3 conan+cmake / build-cmake (openal, glfw, macos-latest, gl3) (push) Waiting to run
re3 conan+cmake / build-cmake (openal, glfw, ubuntu-18.04, gl3) (push) Waiting to run
re3 conan+cmake / build-cmake (openal, glfw, windows-latest, gl3) (push) Waiting to run
re3 conan+cmake / build-cmake (openal, windows-latest, d3d9) (push) Waiting to run
re3 cmake devkitA64 (Nintendo Switch) / build-nintendo-switch (push) Waiting to run
re3 premake amd64 / build (Debug, win-amd64-librw_d3d9-oal) (push) Waiting to run
re3 premake amd64 / build (Debug, win-amd64-librw_gl3_glfw-oal) (push) Waiting to run
re3 premake amd64 / build (Release, win-amd64-librw_d3d9-oal) (push) Waiting to run
re3 premake amd64 / build (Release, win-amd64-librw_gl3_glfw-oal) (push) Waiting to run
re3 premake x86 / build (Debug, win-x86-librw_d3d9-mss) (push) Waiting to run
re3 premake x86 / build (Debug, win-x86-librw_d3d9-oal) (push) Waiting to run
re3 premake x86 / build (Debug, win-x86-librw_gl3_glfw-mss) (push) Waiting to run
re3 premake x86 / build (Debug, win-x86-librw_gl3_glfw-oal) (push) Waiting to run
re3 premake x86 / build (Release, win-x86-librw_d3d9-mss) (push) Waiting to run
re3 premake x86 / build (Release, win-x86-librw_d3d9-oal) (push) Waiting to run
re3 premake x86 / build (Release, win-x86-librw_gl3_glfw-mss) (push) Waiting to run
re3 premake x86 / build (Release, win-x86-librw_gl3_glfw-oal) (push) Waiting to run
re3 premake x86 / build (Vanilla, win-x86-librw_d3d9-mss) (push) Waiting to run
re3 premake x86 / build (Vanilla, win-x86-librw_d3d9-oal) (push) Waiting to run
re3 premake x86 / build (Vanilla, win-x86-librw_gl3_glfw-mss) (push) Waiting to run
re3 premake x86 / build (Vanilla, win-x86-librw_gl3_glfw-oal) (push) Waiting to run
PedSfx: Read from I/O thread, load them on the background See merge request skmp/dca3-game!10
This commit is contained in:
@@ -6302,7 +6302,7 @@ cPedComments::Process()
|
|||||||
{
|
{
|
||||||
case LOADING_STATUS_NOT_LOADED:
|
case LOADING_STATUS_NOT_LOADED:
|
||||||
SampleManager.LoadPedComment(sampleIndex);
|
SampleManager.LoadPedComment(sampleIndex);
|
||||||
#ifdef GTA_PS2 // on PC ped comment is loaded at once
|
#if defined(GTA_PS2) || defined(RW_DC) // on PC ped comment is loaded at once
|
||||||
break;
|
break;
|
||||||
#endif
|
#endif
|
||||||
case LOADING_STATUS_LOADED:
|
case LOADING_STATUS_LOADED:
|
||||||
|
@@ -166,8 +166,12 @@ struct sfx_bank {
|
|||||||
std::map<int, sfx_bank> sfx_banks;
|
std::map<int, sfx_bank> sfx_banks;
|
||||||
|
|
||||||
int nPedSlotSfx[MAX_PEDSFX];
|
int nPedSlotSfx[MAX_PEDSFX];
|
||||||
|
uint32 nPedSlotSfxReqId[MAX_PEDSFX];
|
||||||
uintptr_t nPedSlotSfxAddr[MAX_PEDSFX];
|
uintptr_t nPedSlotSfxAddr[MAX_PEDSFX];
|
||||||
uint8_t nCurrentPedSlot;
|
uint8_t nCurrentPedSlot;
|
||||||
|
file_t fdPedSfx;
|
||||||
|
volatile uint32 nPedSfxReqReadId = 1;
|
||||||
|
volatile uint32 nPedSfxReqNextId = 1;
|
||||||
|
|
||||||
struct WavHeader {
|
struct WavHeader {
|
||||||
// RIFF Header
|
// RIFF Header
|
||||||
@@ -442,15 +446,22 @@ cSampleManager::Initialise(void)
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
nPedSfxReqNextId = 1;
|
||||||
|
nPedSfxReqReadId = 1;
|
||||||
for ( int32 i = 0; i < MAX_PEDSFX; i++ )
|
for ( int32 i = 0; i < MAX_PEDSFX; i++ )
|
||||||
{
|
{
|
||||||
nPedSlotSfx[i] = -1;
|
nPedSlotSfx[i] = -1;
|
||||||
|
nPedSlotSfxReqId[i] = 0;
|
||||||
nPedSlotSfxAddr[i] = snd_mem_malloc(PED_BLOCKSIZE_ADPCM);
|
nPedSlotSfxAddr[i] = snd_mem_malloc(PED_BLOCKSIZE_ADPCM);
|
||||||
debugf("PedSlot %d buffer: %p\n", i, (void*)nPedSlotSfxAddr[i]);
|
debugf("PedSlot %d buffer: %p\n", i, (void*)nPedSlotSfxAddr[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
nCurrentPedSlot = 0;
|
nCurrentPedSlot = 0;
|
||||||
|
|
||||||
|
fdPedSfx = fs_open(SampleBankDataFilename, O_RDONLY);
|
||||||
|
|
||||||
|
assert(fdPedSfx >= 0);
|
||||||
|
|
||||||
_dcAudioInitialized = true;
|
_dcAudioInitialized = true;
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
@@ -458,7 +469,7 @@ cSampleManager::Initialise(void)
|
|||||||
void
|
void
|
||||||
cSampleManager::Terminate(void)
|
cSampleManager::Terminate(void)
|
||||||
{
|
{
|
||||||
|
fs_close(fdPedSfx);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool8 cSampleManager::CheckForAnAudioFileOnCD(void)
|
bool8 cSampleManager::CheckForAnAudioFileOnCD(void)
|
||||||
@@ -637,7 +648,7 @@ cSampleManager::IsPedCommentLoaded(uint32 nComment)
|
|||||||
slot += ARRAY_SIZE(nPedSlotSfx);
|
slot += ARRAY_SIZE(nPedSlotSfx);
|
||||||
#endif
|
#endif
|
||||||
if ( nComment == nPedSlotSfx[slot] )
|
if ( nComment == nPedSlotSfx[slot] )
|
||||||
return LOADING_STATUS_LOADED;
|
return nPedSlotSfxReqId[slot] <= nPedSfxReqReadId ? LOADING_STATUS_LOADED : LOADING_STATUS_LOADING;
|
||||||
}
|
}
|
||||||
|
|
||||||
return LOADING_STATUS_NOT_LOADED;
|
return LOADING_STATUS_NOT_LOADED;
|
||||||
@@ -698,27 +709,28 @@ cSampleManager::LoadPedComment(uint32 nComment)
|
|||||||
|
|
||||||
assert(m_aSamples[nComment].nByteSize < PED_BLOCKSIZE_ADPCM);
|
assert(m_aSamples[nComment].nByteSize < PED_BLOCKSIZE_ADPCM);
|
||||||
|
|
||||||
file_t fd = fs_open(SampleBankDataFilename, O_RDONLY);
|
CdStreamQueueAudioRead(nComment, (void*)nPedSlotSfxAddr[nCurrentPedSlot], m_aSamples[nComment].nByteSize, m_aSamples[nComment].nFileOffset, [](AudioReadCmd* cmd) {
|
||||||
|
debugf("Loading ped comment %d, offset: %d, size: %d\n", nComment, m_aSamples[nComment].nFileOffset, m_aSamples[nComment].nByteSize);
|
||||||
assert(fd >= 0);
|
fs_seek(fdPedSfx, cmd->seek, SEEK_SET);
|
||||||
debugf("Loading ped comment %d, offset: %d, size: %d\n", nComment, m_aSamples[nComment].nFileOffset, m_aSamples[nComment].nByteSize);
|
|
||||||
fs_seek(fd, m_aSamples[nComment].nFileOffset, SEEK_SET);
|
|
||||||
|
|
||||||
|
|
||||||
// TODO: When we can dma directly to AICA, we can use this instead
|
// TODO: When we can dma directly to AICA, we can use this instead
|
||||||
// fs_read(fd, SPU_BASE_U8 + nPedSlotSfxAddr[nCurrentPedSlot], sizeof(nPedSlotSfxAddr));
|
// fs_read(fdPedSfx, SPU_BASE_U8 + (uintptr_t)cmd->dest, cmd->size);
|
||||||
|
|
||||||
void* stagingBuffer = memalign(32, m_aSamples[nComment].nByteSize);
|
void* stagingBuffer = memalign(32, cmd->size);
|
||||||
assert(stagingBuffer != 0);
|
assert(stagingBuffer != 0);
|
||||||
debugf("Allocated %d bytes at %p\n", m_aSamples[nComment].nByteSize, stagingBuffer);
|
debugf("Allocated %d bytes at %p\n", cmd->size, stagingBuffer);
|
||||||
int rs = fs_read(fd, stagingBuffer, m_aSamples[nComment].nByteSize);
|
int rs = fs_read(fdPedSfx, stagingBuffer, cmd->size);
|
||||||
debugf("Read %d bytes, expected %d\n", rs, m_aSamples[nComment].nByteSize);
|
debugf("Read %d bytes, expected %d\n", rs, cmd->size);
|
||||||
assert(rs == m_aSamples[nComment].nByteSize);
|
assert(rs == cmd->size);
|
||||||
|
|
||||||
fs_close(fd);
|
spu_memload((uintptr_t)cmd->dest, stagingBuffer, cmd->size);
|
||||||
|
free(stagingBuffer);
|
||||||
|
nPedSfxReqReadId = nPedSfxReqReadId + 1;
|
||||||
|
});
|
||||||
|
|
||||||
spu_memload(nPedSlotSfxAddr[nCurrentPedSlot], stagingBuffer, m_aSamples[nComment].nByteSize);
|
nPedSlotSfxReqId[nCurrentPedSlot] = ++nPedSfxReqNextId;
|
||||||
free(stagingBuffer);
|
|
||||||
nPedSlotSfx[nCurrentPedSlot] = nComment;
|
nPedSlotSfx[nCurrentPedSlot] = nComment;
|
||||||
|
|
||||||
if ( ++nCurrentPedSlot >= MAX_PEDSFX )
|
if ( ++nCurrentPedSlot >= MAX_PEDSFX )
|
||||||
|
@@ -1,4 +1,5 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
#include <functional>
|
||||||
|
|
||||||
#define CDSTREAM_SECTOR_SIZE 2048
|
#define CDSTREAM_SECTOR_SIZE 2048
|
||||||
|
|
||||||
@@ -43,7 +44,14 @@ char *CdStreamGetImageName(int32 cd);
|
|||||||
void CdStreamRemoveImages(void);
|
void CdStreamRemoveImages(void);
|
||||||
int32 CdStreamGetNumImages(void);
|
int32 CdStreamGetNumImages(void);
|
||||||
|
|
||||||
void CdStreamQueueAudioRead(int fd, void* pBuffer, size_t bytes, size_t seek);
|
struct AudioReadCmd {
|
||||||
|
void* dest;
|
||||||
|
int fd;
|
||||||
|
size_t size;
|
||||||
|
size_t seek;
|
||||||
|
std::function<void(AudioReadCmd*)> callback;
|
||||||
|
};
|
||||||
|
void CdStreamQueueAudioRead(int fd, void* pBuffer, size_t bytes, size_t seek, std::function<void(AudioReadCmd*)> callback = nullptr);
|
||||||
void CdStreamDiscardAudioRead(int fd);
|
void CdStreamDiscardAudioRead(int fd);
|
||||||
|
|
||||||
#ifdef FLUSHABLE_STREAMING
|
#ifdef FLUSHABLE_STREAMING
|
||||||
|
@@ -26,12 +26,6 @@
|
|||||||
#include "CdStream.h"
|
#include "CdStream.h"
|
||||||
#include "rwcore.h"
|
#include "rwcore.h"
|
||||||
#include "MemoryMgr.h"
|
#include "MemoryMgr.h"
|
||||||
struct AudioReadCmd {
|
|
||||||
void* dest;
|
|
||||||
int fd;
|
|
||||||
size_t size;
|
|
||||||
size_t seek;
|
|
||||||
};
|
|
||||||
|
|
||||||
#define CDDEBUG(f, ...) debug ("%s: " f "\n", "cdvd_stream", ## __VA_ARGS__)
|
#define CDDEBUG(f, ...) debug ("%s: " f "\n", "cdvd_stream", ## __VA_ARGS__)
|
||||||
#define CDTRACE(f, ...) printf("%s: " f "\n", "cdvd_stream", ## __VA_ARGS__)
|
#define CDTRACE(f, ...) printf("%s: " f "\n", "cdvd_stream", ## __VA_ARGS__)
|
||||||
@@ -489,8 +483,16 @@ std::vector<AudioReadCmd> pendingAudioReads;
|
|||||||
std::mutex pendingAudioReadsMutex;
|
std::mutex pendingAudioReadsMutex;
|
||||||
#endif
|
#endif
|
||||||
// Will replace a previous read request for the same file descriptor
|
// Will replace a previous read request for the same file descriptor
|
||||||
void CdStreamQueueAudioRead(int fd, void* pBuffer, size_t bytes, size_t seek) {
|
void CdStreamQueueAudioRead(int fd, void* pBuffer, size_t bytes, size_t seek, std::function<void(AudioReadCmd*)> callback) {
|
||||||
AudioReadCmd cmd = { pBuffer, fd, bytes, seek};
|
AudioReadCmd cmd = { pBuffer, fd, bytes, seek};
|
||||||
|
if (!callback) {
|
||||||
|
cmd.callback = [](AudioReadCmd* cmd){
|
||||||
|
lseek(cmd->fd, cmd->seek, SEEK_SET);
|
||||||
|
read(cmd->fd, cmd->dest, cmd->size);
|
||||||
|
};
|
||||||
|
} else {
|
||||||
|
cmd.callback = callback;
|
||||||
|
}
|
||||||
{
|
{
|
||||||
#if !defined(DC_SH4)
|
#if !defined(DC_SH4)
|
||||||
std::lock_guard<std::mutex> lock(pendingAudioReadsMutex);
|
std::lock_guard<std::mutex> lock(pendingAudioReadsMutex);
|
||||||
@@ -514,6 +516,7 @@ void CdStreamQueueAudioRead(int fd, void* pBuffer, size_t bytes, size_t seek) {
|
|||||||
sem_post(gCdStreamSema);
|
sem_post(gCdStreamSema);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void CdStreamDiscardAudioRead(int fd) {
|
void CdStreamDiscardAudioRead(int fd) {
|
||||||
#if !defined(DC_SH4)
|
#if !defined(DC_SH4)
|
||||||
std::lock_guard<std::mutex> lock(pendingAudioReadsMutex);
|
std::lock_guard<std::mutex> lock(pendingAudioReadsMutex);
|
||||||
@@ -564,8 +567,7 @@ int read_loop(int fd, void* pBuffer, size_t bytes) {
|
|||||||
total_read += read_bytes;
|
total_read += read_bytes;
|
||||||
auto cmd = CdStreamNextAudioRead();
|
auto cmd = CdStreamNextAudioRead();
|
||||||
while (cmd.fd != -1) {
|
while (cmd.fd != -1) {
|
||||||
lseek(cmd.fd, cmd.seek, SEEK_SET);
|
cmd.callback(&cmd);
|
||||||
read(cmd.fd, cmd.dest, cmd.size);
|
|
||||||
cmd = CdStreamNextAudioRead();
|
cmd = CdStreamNextAudioRead();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -581,8 +583,7 @@ void *CdStreamThread(void *param)
|
|||||||
|
|
||||||
auto cmd = CdStreamNextAudioRead();
|
auto cmd = CdStreamNextAudioRead();
|
||||||
while (cmd.fd != -1) {
|
while (cmd.fd != -1) {
|
||||||
lseek(cmd.fd, cmd.seek, SEEK_SET);
|
cmd.callback(&cmd);
|
||||||
read(cmd.fd, cmd.dest, cmd.size);
|
|
||||||
cmd = CdStreamNextAudioRead();
|
cmd = CdStreamNextAudioRead();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user