diff --git a/examples/example.d b/examples/example.d index aa553dc..b5ea3fc 100644 --- a/examples/example.d +++ b/examples/example.d @@ -3,6 +3,9 @@ import core.stdc.stdlib; import usbextreme; extern(C) int main(int argc, char[]* argv) { + usb_extreme_headers headers; + usb_extreme_filestat[10] filestatsBuf = void; + if (argc < 2) { printf("Usage: open-usbextreme-example \n"); return 1; @@ -29,18 +32,14 @@ extern(C) int main(int argc, char[]* argv) { fread(data, size, 1, f); fclose(f); - usb_extreme_headers headers; - if (oueReadHeaders(headers, data[0..size]) <= 0) { return 1; } + + auto filestats = oueRead(filestatsBuf, headers); - usb_extreme_filestat[10] filestats = void; - int nstats = oueRead(filestats, headers); - - int i; - for(i = 0; i < nstats; i++) { - printf("Game name [%d]: %s\n", filestats[i].offset, filestats[i].name.ptr); + foreach (filestat; filestats) { + printf("Game name [%d]: %s\n", filestat.offset, filestat.name.ptr); } return 0; diff --git a/include/usbextreme.di b/include/usbextreme.di index c71a425..2da204e 100644 --- a/include/usbextreme.di +++ b/include/usbextreme.di @@ -64,6 +64,7 @@ enum UsbExtremeVersion { V0 = 0, V1, + Unknown, } enum SCECdvdMediaType { @@ -83,16 +84,16 @@ enum SCECdvdMediaType SCECdDVDV, SCECdIllegalMediaoffset, } -extern (D) int isOue(const(void)[] headers); +extern (D) bool isOue(const(void)[] headers); extern (D) UsbExtremeVersion getVersion(uint8_t usbExtremeVersion); -extern (D) int oueNumHeaders(ref int num_headers, const(void)[] headers); +extern (D) int oueNumHeaders(const(void)[] headers); extern (D) int ouePointHeaders(ref const(usb_extreme_base)[] headers, const(void)[] raw_headers); -extern (D) int oueHeadersVersion(ref UsbExtremeVersion oueVersion, const(void)[] headers); +extern (D) UsbExtremeVersion oueHeadersVersion(const(void)[] headers); extern (D) int oueReadHeaders(ref usb_extreme_headers headers, const(void)[] raw_headers); -extern (D) int oueRead(usb_extreme_filestat[] filestat, const(usb_extreme_headers) headers); +extern (D) usb_extreme_filestat[] oueRead(usb_extreme_filestat[] filestats, const(usb_extreme_headers) headers); private R[] castArray(R, T)(T[] array) { auto ptr = array.ptr; auto castPtr = cast(R*)ptr; - return castPtr[0..array.length / R.sizeof]; + return castPtr[0..array.length * T.sizeof / R.sizeof]; } diff --git a/include/usbextreme.h b/include/usbextreme.h index 44899d0..92c7b7d 100644 --- a/include/usbextreme.h +++ b/include/usbextreme.h @@ -38,7 +38,8 @@ typedef enum { typedef enum { USB_EXTREME_V0 = 0x00, - USB_EXTREME_V1 + USB_EXTREME_V1, + USB_EXTREME_UNKNOWN } usb_extreme_versions; typedef struct __attribute__((__packed__)) { diff --git a/lib/cabi.d b/lib/cabi.d index 7a02540..d4f10e4 100644 --- a/lib/cabi.d +++ b/lib/cabi.d @@ -11,7 +11,9 @@ extern(C) UsbExtremeVersion get_version(uint8_t usbExtremeVersion) { } extern(C) int oue_num_headers(int *num_headers, const(void) *headers, size_t headerslen) { - return oueNumHeaders(*num_headers, headers[0..headerslen]); + auto result = oueNumHeaders(headers[0..headerslen]); + *num_headers = result; + return result; } extern(C) int oue_point_headers(const(usb_extreme_base)** headers, const(void)* raw_headers, size_t headerslen) { @@ -21,7 +23,14 @@ extern(C) int oue_point_headers(const(usb_extreme_base)** headers, const(void)* } extern(C) int oue_version(UsbExtremeVersion* oueVersion, const(void) *headers, size_t headerslen) { - return oueHeadersVersion(*oueVersion, headers[0..headerslen]); + auto result = oueHeadersVersion(headers[0..headerslen]); + + if (result == UsbExtremeVersion.Unknown) { + return -1; + } + + *oueVersion = result; + return 1; } extern(C) int oue_read_headers(usb_extreme_headers* headers, const(void)* raw_headers, size_t headerslen) { @@ -29,5 +38,6 @@ extern(C) int oue_read_headers(usb_extreme_headers* headers, const(void)* raw_he } extern(C) int oue_read(usb_extreme_filestat* filestat, const(usb_extreme_headers) headers, int filestats_nlen) { - return oueRead(filestat[0..filestats_nlen], headers); + auto result = oueRead(filestat[0..filestats_nlen], headers); + return cast(int) result.length; } diff --git a/lib/usbextreme.d b/lib/usbextreme.d index c9aab5c..c645fb7 100644 --- a/lib/usbextreme.d +++ b/lib/usbextreme.d @@ -57,7 +57,8 @@ struct usb_extreme_filestat { enum UsbExtremeVersion { V0 = 0x00, - V1 + V1, + Unknown } enum SCECdvdMediaType { @@ -80,16 +81,16 @@ enum SCECdvdMediaType { SCECdIllegalMediaoffset } -extern(D) int isOue(const(void)[] headers) { +extern(D) bool isOue(const(void)[] headers) { auto headers_oeu = castArray!(const usb_extreme_base)(headers); foreach (header; headers_oeu) { if (header.magic != USBEXTREME_MAGIC) { - return 0; + return false; } } - return 1; + return true; } extern(D) UsbExtremeVersion getVersion(uint8_t usbExtremeVersion) { @@ -108,21 +109,20 @@ extern(D) UsbExtremeVersion getVersion(uint8_t usbExtremeVersion) { } } -extern(D) int oueNumHeaders(ref int num_headers, const(void)[] headers) { +extern(D) int oueNumHeaders(const(void)[] headers) { auto headers_nlen = cast(int) (castArray!(usb_extreme_base)(headers).length); if (!isOue(headers)) { return -1; } - num_headers = headers_nlen; return headers_nlen; } extern(D) int ouePointHeaders(ref const(usb_extreme_base)[] headers, const(void)[] raw_headers) { - int headers_nlen; + auto headers_nlen = oueNumHeaders(raw_headers); - if (oueNumHeaders(headers_nlen, raw_headers) <= 0) { + if (headers_nlen <= 0) { return -1; } @@ -130,12 +130,12 @@ extern(D) int ouePointHeaders(ref const(usb_extreme_base)[] headers, const(void) return headers_nlen; } -extern(D) int oueHeadersVersion(ref UsbExtremeVersion oueVersion, const(void)[] headers) { +extern(D) UsbExtremeVersion oueHeadersVersion(const(void)[] headers) { auto headers_oeu = castArray!(usb_extreme_v1)(headers); auto first_version = UsbExtremeVersion.V0; if (!isOue(headers)) { - return -1; + return UsbExtremeVersion.Unknown; } foreach (i, header; headers_oeu) { @@ -143,25 +143,23 @@ extern(D) int oueHeadersVersion(ref UsbExtremeVersion oueVersion, const(void)[] first_version = getVersion(header.usb_extreme_version); } else { if (first_version != getVersion(header.usb_extreme_version)) { - oueVersion = UsbExtremeVersion.V0; - return -2; + return UsbExtremeVersion.V0; } } } - oueVersion = first_version; - return 1; + return first_version; } extern(D) int oueReadHeaders(ref usb_extreme_headers headers, const(void)[] raw_headers) { - UsbExtremeVersion oueVersion; - auto num_headers = cast(int) (raw_headers.length / USBEXTREME_HEADER_SIZE); + auto oueVersion = oueHeadersVersion(raw_headers); + auto num_headers = oueNumHeaders(raw_headers); if (!isOue(raw_headers)) { return -1; } - if (oueHeadersVersion(oueVersion, raw_headers) <= 0) { + if (oueVersion == UsbExtremeVersion.Unknown) { return -1; } @@ -174,43 +172,38 @@ extern(D) int oueReadHeaders(ref usb_extreme_headers headers, const(void)[] raw_ return 1; } -extern(D) int oueRead(usb_extreme_filestat[] filestat, const(usb_extreme_headers) headers) { - import core.stdc.string : strncpy, strncat; +extern(D) usb_extreme_filestat[] oueRead(usb_extreme_filestat[] filestats, const(usb_extreme_headers) headers) { + auto headers_full = castArray!(usb_extreme_v1)(headers.headers[0..headers.num_headers]); + auto headersLength = headers_full.length; + int fileStatsLength = 0; - int offset = cast(int) filestat.length; - auto headers_full = cast(usb_extreme_v1*) headers.headers; - usb_extreme_v1 header; - usb_extreme_filestat filestats_temp = {0, ['0'], SCECdvdMediaType.SCECdNODISC, 0, 0, UsbExtremeVersion.V0}; - uint16_t size = 0; - uint8_t video_mode = 0; - uint8_t usb_extreme_version; - int i; - - for(i = 0; i < headers.num_headers; i++) { - if(offset == 0) { - return i; + foreach (i, ref filestat; filestats) { + if (headersLength == 0) { + return filestats[0..i]; } - - header = headers_full[i]; - strncpy(filestats_temp.name.ptr, header.name.ptr, USBEXTREME_NAME_LENGTH); - usb_extreme_version = header.usb_extreme_version; - - if(usb_extreme_version >= 1) { + + auto header = headers_full[i]; + filestat.name[0..USBEXTREME_NAME_LENGTH] = header.name[0..$]; + auto headerVersion = getVersion(header.usb_extreme_version); + uint16_t size = 0; + uint8_t videoMode = 0; + + if (headerVersion >= 1) { size = header.size; - video_mode = header.video_mode; - strncat(filestats_temp.name.ptr, header.name_ext.ptr, USBEXTREME_NAME_EXT_LENGTH); + videoMode = header.video_mode; + filestat.name[USBEXTREME_NAME_LENGTH..USBEXTREME_NAME_LENGTH + USBEXTREME_NAME_EXT_LENGTH] = header.name_ext[0..$]; } - - filestats_temp.size = size; - filestats_temp.type = cast(SCECdvdMediaType) header.type; - filestats_temp.offset = i; - filestats_temp.video_mode = video_mode; - filestats_temp.usb_extreme_version = cast(UsbExtremeVersion) usb_extreme_version; - filestat[i] = filestats_temp; - offset -= 1; + + filestat.size = size; + filestat.type = cast(SCECdvdMediaType) header.type; + filestat.offset = cast(int) i; + filestat.video_mode = videoMode; + filestat.usb_extreme_version = headerVersion; + headersLength -= 1; + fileStatsLength += 1; } - - return i; + + return filestats[0..fileStatsLength]; } private R[] castArray(R, T) (T[] array) { // Workaround for https://issues.dlang.org/show_bug.cgi?id=20088