|
From: kosmirror <kos...@us...> - 2025-08-31 21:15:39
|
This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "A pseudo Operating System for the Dreamcast.".
The branch, master has been updated
via 1d3584ab7c0bcdc90a92ef0058a9554cd203d428 (commit)
from e36c93953498011fd1216ddd5a951be6452167a7 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 1d3584ab7c0bcdc90a92ef0058a9554cd203d428
Author: Ruslan Rostovtsev <sw...@21...>
Date: Mon Sep 1 04:15:22 2025 +0700
iso9660: Fix streaming DMA alignment and data corruption. (#1173)
- Fixed DMA Crash: Replaced `malloc` with `aligned_alloc` in `iso_open` to ensure the
file handle's internal DMA buffer is always 32-byte aligned, preventing
"Unaligned memory" errors.
- Fixed Data Corruption: Corrected the logic in `iso_read` to properly handle leftover
data in the stream buffer between reads. This prevents data from being skipped
when a small read is followed by a larger one.
-----------------------------------------------------------------------
Summary of changes:
kernel/arch/dreamcast/fs/fs_iso9660.c | 46 +++++++++++++++++++++++------------
1 file changed, 31 insertions(+), 15 deletions(-)
diff --git a/kernel/arch/dreamcast/fs/fs_iso9660.c b/kernel/arch/dreamcast/fs/fs_iso9660.c
index 7c745482..67642e9d 100644
--- a/kernel/arch/dreamcast/fs/fs_iso9660.c
+++ b/kernel/arch/dreamcast/fs/fs_iso9660.c
@@ -616,6 +616,7 @@ static inline void iso_abort_stream(bool lock) {
mutex_lock(&fh_mutex);
cdrom_stream_stop(false);
+ stream_fd->stream_part = 0;
stream_fd = NULL;
if(lock)
@@ -652,7 +653,7 @@ static void * iso_open(vfs_handler_t * vfs, const char *fn, int mode) {
return 0;
}
- fd = malloc(sizeof(*fd));
+ fd = aligned_alloc(32, sizeof(*fd));
if(!fd) {
errno = ENOMEM;
return 0;
@@ -694,7 +695,8 @@ static int iso_close(void * h) {
/* Read from a file */
static ssize_t iso_read(void * h, void *buf, size_t bytes) {
- int rv, toread, thissect, c;
+ int rv, c;
+ size_t toread, thissect;
uint8 * outbuf;
size_t remain_size = 0, req_size;
uint32_t sector;
@@ -717,6 +719,23 @@ static ssize_t iso_read(void * h, void *buf, size_t bytes) {
if(toread == 0) break;
+ /* If we have partial data from a stream, use it */
+ if(fd->stream_part > 0) {
+ size_t avail = 32 - fd->stream_part;
+ size_t given = (toread > avail) ? avail : toread;
+
+ memcpy(outbuf, &fd->stream_data[fd->stream_part], given);
+ fd->stream_part = (fd->stream_part + given) & 31;
+
+ outbuf += given;
+ fd->ptr += given;
+ bytes -= given;
+ rv += given;
+ toread -= given;
+
+ if(toread == 0) continue;
+ }
+
/* How much more can we read in the current sector? */
thissect = 2048 - (fd->ptr % 2048);
sector = fd->first_extent + (fd->ptr / 2048);
@@ -778,21 +797,18 @@ static ssize_t iso_read(void * h, void *buf, size_t bytes) {
toread = (toread > thissect) ? thissect : toread;
- if(fd->stream_part > 0) {
- memcpy(outbuf, &fd->stream_data[fd->stream_part - 1], toread);
- fd->stream_part = 0;
+ c = cdrom_stream_request(fd->stream_data, 32, 0);
+ if(c) {
+ goto read_error;
}
- else {
- c = cdrom_stream_request(fd->stream_data, 32, 0);
- if(c) {
- goto read_error;
- }
- fd->stream_part = toread;
- while(cdrom_stream_progress(&remain_size) == 1) {
- thd_pass();
- }
- memcpy(outbuf, fd->stream_data, toread);
+
+ while(cdrom_stream_progress(&remain_size) == 1) {
+ thd_pass();
}
+
+ memcpy(outbuf, fd->stream_data, toread);
+ fd->stream_part = toread & 31;
+
// dbglog(DBG_DEBUG, "Stream request: read=%d remain=%d part=%d out=%p fd=%p\n",
// toread, remain_size, fd->stream_part, outbuf, fd);
hooks/post-receive
--
A pseudo Operating System for the Dreamcast.
|