port: make it link and load

nothing happens after loading though
This commit is contained in:
fgsfds committed 2023-07-29 23:21:35 +02:00
1 parent c55f9c805c
commit da94644c38
68 files changed
+8291 -163

No files matched your search

+3 -1
View File
@@ -169,7 +169,8 @@ DEFINES := \
MATCHING=$(MATCHING) \
PAL=$(PAL) \
PIRACYCHECKS=$(PIRACYCHECKS) \
ROM_SIZE=$(ROM_SIZE)
ROM_SIZE=$(ROM_SIZE) \
PLATFORM_N64=1
ifeq ($(DEBUG),1)
DEFINES := $(DEFINES) DEBUG=1
@@ -296,6 +297,7 @@ INCLUDES = \
-I include \
-I include/PR \
-I src/include \
-I src/include/lib/libc \
-I src/generated/$(ROMID) \
-I src/lib/ultra/audio \
+20
View File
@@ -60,6 +60,8 @@
#else /* _LANGUAGE_C */
#ifdef PLATFORM_N64
#define K0_TO_K1(x) ((u32)(x)|0xA0000000) /* kseg0 to kseg1 */
#define K1_TO_K0(x) ((u32)(x)&0x9FFFFFFF) /* kseg1 to kseg0 */
#define K0_TO_PHYS(x) ((u32)(x)&0x1FFFFFFF) /* kseg0 to physical */
@@ -68,6 +70,24 @@
#define PHYS_TO_K0(x) ((u32)(x)|0x80000000) /* physical to kseg0 */
#define PHYS_TO_K1(x) ((u32)(x)|0xA0000000) /* physical to kseg1 */
#else /* PLATFORM_N64 */
#ifdef PLATFORM_64BIT
typedef u64 k_ptr_t;
#else
typedef u32 k_ptr_t;
#endif
#define K0_TO_K1(x) ((k_ptr_t)(x)) /* kseg0 to kseg1 */
#define K1_TO_K0(x) ((k_ptr_t)(x)) /* kseg1 to kseg0 */
#define K0_TO_PHYS(x) ((k_ptr_t)(x)) /* kseg0 to physical */
#define K1_TO_PHYS(x) ((k_ptr_t)(x)) /* kseg1 to physical */
#define KDM_TO_PHYS(x) ((k_ptr_t)(x)) /* direct mapped to physical */
#define PHYS_TO_K0(x) ((k_ptr_t)(x)) /* physical to kseg0 */
#define PHYS_TO_K1(x) ((k_ptr_t)(x)) /* physical to kseg1 */
#endif /* PLATFORM_N64 */
#endif /* _LANGUAGE_ASSEMBLY */
/*
+7 -2
View File
@@ -70,12 +70,17 @@ extern "C" {
#define OS_CYCLES_TO_NSEC(c) (((u64)(c)*(1000000000LL/15625000LL))/(OS_CPU_COUNTER/15625000LL))
#define OS_CYCLES_TO_USEC(c) (((u64)(c)*(1000000LL/15625LL))/(OS_CPU_COUNTER/15625LL))
#ifdef PLATFORM_N64
#define OS_K0_TO_PHYSICAL(x) (u32)(((char *)(x)-0x80000000))
#define OS_K1_TO_PHYSICAL(x) (u32)(((char *)(x)-0xa0000000))
#define OS_PHYSICAL_TO_K0(x) (void *)(((u32)(x)+0x80000000))
#define OS_PHYSICAL_TO_K1(x) (void *)(((u32)(x)+0xa0000000))
#else
#define OS_K0_TO_PHYSICAL(x) (uintptr_t)(x)
#define OS_K1_TO_PHYSICAL(x) (uintptr_t)(x)
#define OS_PHYSICAL_TO_K0(x) (void *)(x)
#define OS_PHYSICAL_TO_K1(x) (void *)(x)
#endif
/**************************************************************************
*
+18
View File
@@ -0,0 +1,18 @@
#ifndef _IN_FS_H
#define _IN_FS_H
#include <limits.h>
#include <PR/ultratypes.h>
#ifdef PATH_MAX
#define FS_MAXPATH PATH_MAX
#else
#define FS_MAXPATH 1024
#endif
s32 fsInit(void);
void *fsFileLoad(const char *name, u32 *outSize);
s32 fsFileSize(const char *name);
#endif
+31
View File
@@ -0,0 +1,31 @@
#ifndef _IN_INPUT_H
#define _IN_INPUT_H
#include <PR/ultratypes.h>
#include <PR/os_cont.h>
#define INPUT_MAX_CONTROLLERS MAXCONTROLLERS
#define INPUT_RUMBLE_STRENGTH 0.333f
// returns bitmask of connected controllers or -1 if failed
s32 inputInit(void);
// returns 0 if read, non-0 if failed
s32 inputReadController(s32 idx, OSContPad *npad);
// returns 1 if rumble is supported for specified controller
s32 inputRumbleSupported(s32 idx);
// returns 1 if specified controller is connected
s32 inputControllerConnected(s32 idx);
// returns bitmask of connected controllers
s32 inputControllerMask(void);
// 0 strength turns it off
void inputRumble(s32 idx, f32 strength, f32 time);
// call this every frame
void inputUpdate(void);
#endif
+33
View File
@@ -0,0 +1,33 @@
#ifndef _IN_PREPROCESS_H
#define _IN_PREPROCESS_H
#include <PR/ultratypes.h>
typedef void (*preprocessfunc)(u8 *data, u32 size);
void preprocessAnimations(u8 *data, u32 size);
void preprocessMpConfigs(u8 *data, u32 size);
void preprocessFont(u8 *data, u32 size);
void preprocessJpnFont(u8 *data, u32 size);
void preprocessALBankFile(u8 *data, u32 size);
void preprocessSequences(u8 *data, u32 size);
void preprocessFiringRange(u8 *data, u32 size);
void preprocessTexturesList(u8 *data, u32 size);
void preprocessBgSection1Header(u8 *data, u32 size);
void preprocessBgSection1(u8 *data, u32 size);
void preprocessBgSection2Header(u8 *data, u32 size);
void preprocessBgSection2(u8 *data, u32 size);
void preprocessBgSection3Header(u8 *data, u32 size);
void preprocessBgSection3(u8 *data, u32 size);
void preprocessBgRoom(u8 *data, u32 ofs);
void preprocessBgLights(u8 *data, u32 ofs);
void preprocessLangFile(u8 *data, u32 size);
void preprocessPadsFile(u8 *data, u32 size);
void preprocessTilesFile(u8 *data, u32 size);
void preprocessSetupFile(u8 *data, u32 size);
void preprocessModelFile(u8 *data, u32 size);
void preprocessGunFile(u8 *data, u32 size);
#endif
+22
View File
@@ -0,0 +1,22 @@
#ifndef _IN_ROMDATA_H
#define _IN_ROMDATA_H
#include <PR/ultratypes.h>
extern u8 *g_RomFile;
extern u32 g_RomFileSize;
s32 romdataInit(void);
u8 *romdataFileLoad(s32 fileNum, u32 *outSize);
void romdataFilePreprocess(s32 fileNum, s32 loadType, u8 *data, u32 size);
void romdataFileFree(s32 fileNum);
u8 *romdataFileGetData(s32 fileNum);
s32 romdataFileGetSize(s32 fileNum);
u8 *romdataSegGetData(const char *segName);
u8 *romdataSegGetDataEnd(const char *segName);
u32 romdataSegGetSize(const char *segName);
#endif
+11
View File
@@ -0,0 +1,11 @@
#ifndef _IN_SYSTEM_H
#define _IN_SYSTEM_H
#include <PR/ultratypes.h>
u64 sysGetTicks(void);
u64 sysGetTicksPerSecond(void);
void sysFatalError(const char *fmt, ...) __attribute__((noreturn));
#endif
+15
View File
@@ -0,0 +1,15 @@
#ifndef _IN_VIDEO_H
#define _IN_VIDEO_H
#include <PR/ultratypes.h>
#include <PR/gbi.h>
s32 videoInit(void);
void videoStartFrame(void);
void videoSubmitCommands(Gfx *cmds);
void videoClearScreen(void);
void videoEndFrame(void);
void *videoGetWindowHandle(void);
#endif
+19
View File
@@ -0,0 +1,19 @@
Copyright (c) 2020 Emill, MaikelChan
Redistribution and use in source forms, with or without modification,
are permitted provided that the following conditions are met:
1. Redistributions of source code must retain the above copyright notice, this
list of conditions and the following disclaimer.
2. Redistributions in binary form are not allowed except in cases where the binary contains no assets you do not have the right to distribute.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+41
View File
@@ -0,0 +1,41 @@
#include "gfx_cc.h"
void gfx_cc_get_features(uint32_t shader_id, struct CCFeatures *cc_features) {
for (int i = 0; i < 4; i++) {
cc_features->c[0][i] = (shader_id >> (i * 3)) & 7;
cc_features->c[1][i] = (shader_id >> (12 + i * 3)) & 7;
}
cc_features->opt_alpha = (shader_id & SHADER_OPT_ALPHA) != 0;
cc_features->opt_fog = (shader_id & SHADER_OPT_FOG) != 0;
cc_features->opt_texture_edge = (shader_id & SHADER_OPT_TEXTURE_EDGE) != 0;
cc_features->opt_noise = (shader_id & SHADER_OPT_NOISE) != 0;
cc_features->used_textures[0] = false;
cc_features->used_textures[1] = false;
cc_features->num_inputs = 0;
for (int i = 0; i < 2; i++) {
for (int j = 0; j < 4; j++) {
if (cc_features->c[i][j] >= SHADER_INPUT_1 && cc_features->c[i][j] <= SHADER_INPUT_4) {
if (cc_features->c[i][j] > cc_features->num_inputs) {
cc_features->num_inputs = cc_features->c[i][j];
}
}
if (cc_features->c[i][j] == SHADER_TEXEL0 || cc_features->c[i][j] == SHADER_TEXEL0A) {
cc_features->used_textures[0] = true;
}
if (cc_features->c[i][j] == SHADER_TEXEL1) {
cc_features->used_textures[1] = true;
}
}
}
cc_features->do_single[0] = cc_features->c[0][2] == 0;
cc_features->do_single[1] = cc_features->c[1][2] == 0;
cc_features->do_multiply[0] = cc_features->c[0][1] == 0 && cc_features->c[0][3] == 0;
cc_features->do_multiply[1] = cc_features->c[1][1] == 0 && cc_features->c[1][3] == 0;
cc_features->do_mix[0] = cc_features->c[0][1] == cc_features->c[0][3];
cc_features->do_mix[1] = cc_features->c[1][1] == cc_features->c[1][3];
cc_features->color_alpha_same = (shader_id & 0xfff) == ((shader_id >> 12) & 0xfff);
}
+58
View File
@@ -0,0 +1,58 @@
#ifndef GFX_CC_H
#define GFX_CC_H
#include <stdint.h>
#include <stdbool.h>
enum {
CC_0,
CC_TEXEL0,
CC_TEXEL1,
CC_PRIM,
CC_SHADE,
CC_ENV,
CC_TEXEL0A,
CC_LOD
};
enum {
SHADER_0,
SHADER_INPUT_1,
SHADER_INPUT_2,
SHADER_INPUT_3,
SHADER_INPUT_4,
SHADER_TEXEL0,
SHADER_TEXEL0A,
SHADER_TEXEL1
};
#define SHADER_OPT_ALPHA (1 << 24)
#define SHADER_OPT_FOG (1 << 25)
#define SHADER_OPT_TEXTURE_EDGE (1 << 26)
#define SHADER_OPT_NOISE (1 << 27)
struct CCFeatures {
uint8_t c[2][4];
bool opt_alpha;
bool opt_fog;
bool opt_texture_edge;
bool opt_noise;
bool used_textures[2];
int num_inputs;
bool do_single[2];
bool do_multiply[2];
bool do_mix[2];
bool color_alpha_same;
};
#ifdef __cplusplus
extern "C" {
#endif
void gfx_cc_get_features(uint32_t shader_id, struct CCFeatures *cc_features);
#ifdef __cplusplus
}
#endif
#endif
+510
View File
@@ -0,0 +1,510 @@
#include <stdlib.h>
#include <stdint.h>
#include <stdbool.h>
#include <SDL.h>
#ifndef _LANGUAGE_C
#define _LANGUAGE_C
#endif
#include <PR/gbi.h>
#include "glad/glad.h"
#include "gfx_cc.h"
#include "gfx_rendering_api.h"
struct ShaderProgram {
uint32_t shader_id;
GLuint opengl_program_id;
uint8_t num_inputs;
bool used_textures[2];
uint8_t num_floats;
GLint attrib_locations[7];
uint8_t attrib_sizes[7];
uint8_t num_attribs;
bool used_noise;
GLint frame_count_location;
GLint window_height_location;
};
static struct ShaderProgram shader_program_pool[64];
static uint8_t shader_program_pool_size;
static GLuint opengl_vbo;
static uint32_t frame_count;
static uint32_t current_height;
static bool gfx_opengl_z_is_from_0_to_1(void) {
return false;
}
static void gfx_opengl_vertex_array_set_attribs(struct ShaderProgram *prg) {
size_t num_floats = prg->num_floats;
size_t pos = 0;
for (int i = 0; i < prg->num_attribs; i++) {
glEnableVertexAttribArray(prg->attrib_locations[i]);
glVertexAttribPointer(prg->attrib_locations[i], prg->attrib_sizes[i], GL_FLOAT, GL_FALSE, num_floats * sizeof(float), (void *) (pos * sizeof(float)));
pos += prg->attrib_sizes[i];
}
}
static void gfx_opengl_set_uniforms(struct ShaderProgram *prg) {
if (prg->used_noise) {
glUniform1i(prg->frame_count_location, frame_count);
glUniform1i(prg->window_height_location, current_height);
}
}
static void gfx_opengl_unload_shader(struct ShaderProgram *old_prg) {
if (old_prg != NULL) {
for (int i = 0; i < old_prg->num_attribs; i++) {
glDisableVertexAttribArray(old_prg->attrib_locations[i]);
}
}
}
static void gfx_opengl_load_shader(struct ShaderProgram *new_prg) {
glUseProgram(new_prg->opengl_program_id);
gfx_opengl_vertex_array_set_attribs(new_prg);
gfx_opengl_set_uniforms(new_prg);
}
static void append_str(char *buf, size_t *len, const char *str) {
while (*str != '\0') buf[(*len)++] = *str++;
}
static void append_line(char *buf, size_t *len, const char *str) {
while (*str != '\0') buf[(*len)++] = *str++;
buf[(*len)++] = '\n';
}
static const char *shader_item_to_str(uint32_t item, bool with_alpha, bool only_alpha, bool inputs_have_alpha, bool hint_single_element) {
if (!only_alpha) {
switch (item) {
case SHADER_0:
return with_alpha ? "vec4(0.0, 0.0, 0.0, 0.0)" : "vec3(0.0, 0.0, 0.0)";
case SHADER_INPUT_1:
return with_alpha || !inputs_have_alpha ? "vInput1" : "vInput1.rgb";
case SHADER_INPUT_2:
return with_alpha || !inputs_have_alpha ? "vInput2" : "vInput2.rgb";
case SHADER_INPUT_3:
return with_alpha || !inputs_have_alpha ? "vInput3" : "vInput3.rgb";
case SHADER_INPUT_4:
return with_alpha || !inputs_have_alpha ? "vInput4" : "vInput4.rgb";
case SHADER_TEXEL0:
return with_alpha ? "texVal0" : "texVal0.rgb";
case SHADER_TEXEL0A:
return hint_single_element ? "texVal0.a" :
(with_alpha ? "vec4(texVal0.a, texVal0.a, texVal0.a, texVal0.a)" : "vec3(texVal0.a, texVal0.a, texVal0.a)");
case SHADER_TEXEL1:
return with_alpha ? "texVal1" : "texVal1.rgb";
}
} else {
switch (item) {
case SHADER_0:
return "0.0";
case SHADER_INPUT_1:
return "vInput1.a";
case SHADER_INPUT_2:
return "vInput2.a";
case SHADER_INPUT_3:
return "vInput3.a";
case SHADER_INPUT_4:
return "vInput4.a";
case SHADER_TEXEL0:
return "texVal0.a";
case SHADER_TEXEL0A:
return "texVal0.a";
case SHADER_TEXEL1:
return "texVal1.a";
}
}
return "";
}
static void append_formula(char *buf, size_t *len, uint8_t c[2][4], bool do_single, bool do_multiply, bool do_mix, bool with_alpha, bool only_alpha, bool opt_alpha) {
if (do_single) {
append_str(buf, len, shader_item_to_str(c[only_alpha][3], with_alpha, only_alpha, opt_alpha, false));
} else if (do_multiply) {
append_str(buf, len, shader_item_to_str(c[only_alpha][0], with_alpha, only_alpha, opt_alpha, false));
append_str(buf, len, " * ");
append_str(buf, len, shader_item_to_str(c[only_alpha][2], with_alpha, only_alpha, opt_alpha, true));
} else if (do_mix) {
append_str(buf, len, "mix(");
append_str(buf, len, shader_item_to_str(c[only_alpha][1], with_alpha, only_alpha, opt_alpha, false));
append_str(buf, len, ", ");
append_str(buf, len, shader_item_to_str(c[only_alpha][0], with_alpha, only_alpha, opt_alpha, false));
append_str(buf, len, ", ");
append_str(buf, len, shader_item_to_str(c[only_alpha][2], with_alpha, only_alpha, opt_alpha, true));
append_str(buf, len, ")");
} else {
append_str(buf, len, "(");
append_str(buf, len, shader_item_to_str(c[only_alpha][0], with_alpha, only_alpha, opt_alpha, false));
append_str(buf, len, " - ");
append_str(buf, len, shader_item_to_str(c[only_alpha][1], with_alpha, only_alpha, opt_alpha, false));
append_str(buf, len, ") * ");
append_str(buf, len, shader_item_to_str(c[only_alpha][2], with_alpha, only_alpha, opt_alpha, true));
append_str(buf, len, " + ");
append_str(buf, len, shader_item_to_str(c[only_alpha][3], with_alpha, only_alpha, opt_alpha, false));
}
}
static struct ShaderProgram *gfx_opengl_create_and_load_new_shader(uint32_t shader_id) {
struct CCFeatures cc_features;
gfx_cc_get_features(shader_id, &cc_features);
char vs_buf[1024];
char fs_buf[1024];
size_t vs_len = 0;
size_t fs_len = 0;
size_t num_floats = 4;
// Vertex shader
append_line(vs_buf, &vs_len, "#version 110");
append_line(vs_buf, &vs_len, "attribute vec4 aVtxPos;");
if (cc_features.used_textures[0] || cc_features.used_textures[1]) {
append_line(vs_buf, &vs_len, "attribute vec2 aTexCoord;");
append_line(vs_buf, &vs_len, "varying vec2 vTexCoord;");
num_floats += 2;
}
if (cc_features.opt_fog) {
append_line(vs_buf, &vs_len, "attribute vec4 aFog;");
append_line(vs_buf, &vs_len, "varying vec4 vFog;");
num_floats += 4;
}
for (int i = 0; i < cc_features.num_inputs; i++) {
vs_len += sprintf(vs_buf + vs_len, "attribute vec%d aInput%d;\n", cc_features.opt_alpha ? 4 : 3, i + 1);
vs_len += sprintf(vs_buf + vs_len, "varying vec%d vInput%d;\n", cc_features.opt_alpha ? 4 : 3, i + 1);
num_floats += cc_features.opt_alpha ? 4 : 3;
}
append_line(vs_buf, &vs_len, "void main() {");
if (cc_features.used_textures[0] || cc_features.used_textures[1]) {
append_line(vs_buf, &vs_len, "vTexCoord = aTexCoord;");
}
if (cc_features.opt_fog) {
append_line(vs_buf, &vs_len, "vFog = aFog;");
}
for (int i = 0; i < cc_features.num_inputs; i++) {
vs_len += sprintf(vs_buf + vs_len, "vInput%d = aInput%d;\n", i + 1, i + 1);
}
append_line(vs_buf, &vs_len, "gl_Position = aVtxPos;");
append_line(vs_buf, &vs_len, "}");
// Fragment shader
append_line(fs_buf, &fs_len, "#version 110");
//append_line(fs_buf, &fs_len, "precision mediump float;");
if (cc_features.used_textures[0] || cc_features.used_textures[1]) {
append_line(fs_buf, &fs_len, "varying vec2 vTexCoord;");
}
if (cc_features.opt_fog) {
append_line(fs_buf, &fs_len, "varying vec4 vFog;");
}
for (int i = 0; i < cc_features.num_inputs; i++) {
fs_len += sprintf(fs_buf + fs_len, "varying vec%d vInput%d;\n", cc_features.opt_alpha ? 4 : 3, i + 1);
}
if (cc_features.used_textures[0]) {
append_line(fs_buf, &fs_len, "uniform sampler2D uTex0;");
}
if (cc_features.used_textures[1]) {
append_line(fs_buf, &fs_len, "uniform sampler2D uTex1;");
}
if (cc_features.opt_alpha && cc_features.opt_noise) {
append_line(fs_buf, &fs_len, "uniform int frame_count;");
append_line(fs_buf, &fs_len, "uniform int window_height;");
append_line(fs_buf, &fs_len, "float random(in vec3 value) {");
append_line(fs_buf, &fs_len, " float random = dot(sin(value), vec3(12.9898, 78.233, 37.719));");
append_line(fs_buf, &fs_len, " return fract(sin(random) * 143758.5453);");
append_line(fs_buf, &fs_len, "}");
}
append_line(fs_buf, &fs_len, "void main() {");
if (cc_features.used_textures[0]) {
append_line(fs_buf, &fs_len, "vec4 texVal0 = texture2D(uTex0, vTexCoord);");
}
if (cc_features.used_textures[1]) {
append_line(fs_buf, &fs_len, "vec4 texVal1 = texture2D(uTex1, vTexCoord);");
}
append_str(fs_buf, &fs_len, cc_features.opt_alpha ? "vec4 texel = " : "vec3 texel = ");
if (!cc_features.color_alpha_same && cc_features.opt_alpha) {
append_str(fs_buf, &fs_len, "vec4(");
append_formula(fs_buf, &fs_len, cc_features.c, cc_features.do_single[0], cc_features.do_multiply[0], cc_features.do_mix[0], false, false, true);
append_str(fs_buf, &fs_len, ", ");
append_formula(fs_buf, &fs_len, cc_features.c, cc_features.do_single[1], cc_features.do_multiply[1], cc_features.do_mix[1], true, true, true);
append_str(fs_buf, &fs_len, ")");
} else {
append_formula(fs_buf, &fs_len, cc_features.c, cc_features.do_single[0], cc_features.do_multiply[0], cc_features.do_mix[0], cc_features.opt_alpha, false, cc_features.opt_alpha);
}
append_line(fs_buf, &fs_len, ";");
if (cc_features.opt_texture_edge && cc_features.opt_alpha) {
append_line(fs_buf, &fs_len, "if (texel.a > 0.3) texel.a = 1.0; else discard;");
}
// TODO discard if alpha is 0?
if (cc_features.opt_fog) {
if (cc_features.opt_alpha) {
append_line(fs_buf, &fs_len, "texel = vec4(mix(texel.rgb, vFog.rgb, vFog.a), texel.a);");
} else {
append_line(fs_buf, &fs_len, "texel = mix(texel, vFog.rgb, vFog.a);");
}
}
if (cc_features.opt_alpha && cc_features.opt_noise) {
append_line(fs_buf, &fs_len, "texel.a *= floor(clamp(random(vec3(floor(gl_FragCoord.xy * (240.0 / float(window_height))), float(frame_count))) + texel.a, 0.0, 1.0));");
}
if (cc_features.opt_alpha) {
append_line(fs_buf, &fs_len, "gl_FragColor = texel;");
} else {
append_line(fs_buf, &fs_len, "gl_FragColor = vec4(texel, 1.0);");
}
append_line(fs_buf, &fs_len, "}");
vs_buf[vs_len] = '\0';
fs_buf[fs_len] = '\0';
/*puts("Vertex shader:");
puts(vs_buf);
puts("Fragment shader:");
puts(fs_buf);
puts("End");*/
const GLchar *sources[2] = { vs_buf, fs_buf };
const GLint lengths[2] = { vs_len, fs_len };
GLint success;
GLuint vertex_shader = glCreateShader(GL_VERTEX_SHADER);
glShaderSource(vertex_shader, 1, &sources[0], &lengths[0]);
glCompileShader(vertex_shader);
glGetShaderiv(vertex_shader, GL_COMPILE_STATUS, &success);
if (!success) {
GLint max_length = 0;
glGetShaderiv(vertex_shader, GL_INFO_LOG_LENGTH, &max_length);
char error_log[1024];
fprintf(stderr, "Vertex shader compilation failed\n");
glGetShaderInfoLog(vertex_shader, max_length, &max_length, &error_log[0]);
fprintf(stderr, "%s\n", &error_log[0]);
abort();
}
GLuint fragment_shader = glCreateShader(GL_FRAGMENT_SHADER);
glShaderSource(fragment_shader, 1, &sources[1], &lengths[1]);
glCompileShader(fragment_shader);
glGetShaderiv(fragment_shader, GL_COMPILE_STATUS, &success);
if (!success) {
GLint max_length = 0;
glGetShaderiv(fragment_shader, GL_INFO_LOG_LENGTH, &max_length);
char error_log[1024];
fprintf(stderr, "Fragment shader compilation failed\n");
glGetShaderInfoLog(fragment_shader, max_length, &max_length, &error_log[0]);
fprintf(stderr, "%s\n", &error_log[0]);
abort();
}
GLuint shader_program = glCreateProgram();
glAttachShader(shader_program, vertex_shader);
glAttachShader(shader_program, fragment_shader);
glLinkProgram(shader_program);
size_t cnt = 0;
struct ShaderProgram *prg = &shader_program_pool[shader_program_pool_size++];
prg->attrib_locations[cnt] = glGetAttribLocation(shader_program, "aVtxPos");
prg->attrib_sizes[cnt] = 4;
++cnt;
if (cc_features.used_textures[0] || cc_features.used_textures[1]) {
prg->attrib_locations[cnt] = glGetAttribLocation(shader_program, "aTexCoord");
prg->attrib_sizes[cnt] = 2;
++cnt;
}
if (cc_features.opt_fog) {
prg->attrib_locations[cnt] = glGetAttribLocation(shader_program, "aFog");
prg->attrib_sizes[cnt] = 4;
++cnt;
}
for (int i = 0; i < cc_features.num_inputs; i++) {
char name[16];
sprintf(name, "aInput%d", i + 1);
prg->attrib_locations[cnt] = glGetAttribLocation(shader_program, name);
prg->attrib_sizes[cnt] = cc_features.opt_alpha ? 4 : 3;
++cnt;
}
prg->shader_id = shader_id;
prg->opengl_program_id = shader_program;
prg->num_inputs = cc_features.num_inputs;
prg->used_textures[0] = cc_features.used_textures[0];
prg->used_textures[1] = cc_features.used_textures[1];
prg->num_floats = num_floats;
prg->num_attribs = cnt;
gfx_opengl_load_shader(prg);
if (cc_features.used_textures[0]) {
GLint sampler_location = glGetUniformLocation(shader_program, "uTex0");
glUniform1i(sampler_location, 0);
}
if (cc_features.used_textures[1]) {
GLint sampler_location = glGetUniformLocation(shader_program, "uTex1");
glUniform1i(sampler_location, 1);
}
if (cc_features.opt_alpha && cc_features.opt_noise) {
prg->frame_count_location = glGetUniformLocation(shader_program, "frame_count");
prg->window_height_location = glGetUniformLocation(shader_program, "window_height");
prg->used_noise = true;
} else {
prg->used_noise = false;
}
return prg;
}
static struct ShaderProgram *gfx_opengl_lookup_shader(uint32_t shader_id) {
for (size_t i = 0; i < shader_program_pool_size; i++) {
if (shader_program_pool[i].shader_id == shader_id) {
return &shader_program_pool[i];
}
}
return NULL;
}
static void gfx_opengl_shader_get_info(struct ShaderProgram *prg, uint8_t *num_inputs, bool used_textures[2]) {
*num_inputs = prg->num_inputs;
used_textures[0] = prg->used_textures[0];
used_textures[1] = prg->used_textures[1];
}
static GLuint gfx_opengl_new_texture(void) {
GLuint ret;
glGenTextures(1, &ret);
return ret;
}
static void gfx_opengl_select_texture(int tile, GLuint texture_id) {
glActiveTexture(GL_TEXTURE0 + tile);
glBindTexture(GL_TEXTURE_2D, texture_id);
}
static void gfx_opengl_upload_texture(const uint8_t *rgba32_buf, int width, int height) {
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, rgba32_buf);
}
static uint32_t gfx_cm_to_opengl(uint32_t val) {
if (val & G_TX_CLAMP) {
return GL_CLAMP_TO_EDGE;
}
return (val & G_TX_MIRROR) ? GL_MIRRORED_REPEAT : GL_REPEAT;
}
static void gfx_opengl_set_sampler_parameters(int tile, bool linear_filter, uint32_t cms, uint32_t cmt) {
glActiveTexture(GL_TEXTURE0 + tile);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, linear_filter ? GL_LINEAR : GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, linear_filter ? GL_LINEAR : GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, gfx_cm_to_opengl(cms));
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, gfx_cm_to_opengl(cmt));
}
static void gfx_opengl_set_depth_test(bool depth_test) {
if (depth_test) {
glEnable(GL_DEPTH_TEST);
} else {
glDisable(GL_DEPTH_TEST);
}
}
static void gfx_opengl_set_depth_mask(bool z_upd) {
glDepthMask(z_upd ? GL_TRUE : GL_FALSE);
}
static void gfx_opengl_set_zmode_decal(bool zmode_decal) {
if (zmode_decal) {
glPolygonOffset(-2, -2);
glEnable(GL_POLYGON_OFFSET_FILL);
} else {
glPolygonOffset(0, 0);
glDisable(GL_POLYGON_OFFSET_FILL);
}
}
static void gfx_opengl_set_viewport(int x, int y, int width, int height) {
glViewport(x, y, width, height);
current_height = height;
}
static void gfx_opengl_set_scissor(int x, int y, int width, int height) {
glScissor(x, y, width, height);
}
static void gfx_opengl_set_use_alpha(bool use_alpha) {
if (use_alpha) {
glEnable(GL_BLEND);
} else {
glDisable(GL_BLEND);
}
}
static void gfx_opengl_draw_triangles(float buf_vbo[], size_t buf_vbo_len, size_t buf_vbo_num_tris) {
//printf("flushing %d tris\n", buf_vbo_num_tris);
glBufferData(GL_ARRAY_BUFFER, sizeof(float) * buf_vbo_len, buf_vbo, GL_STREAM_DRAW);
glDrawArrays(GL_TRIANGLES, 0, 3 * buf_vbo_num_tris);
}
static void gfx_opengl_init(void) {
gladLoadGLES2Loader(SDL_GL_GetProcAddress);
glGenBuffers(1, &opengl_vbo);
glBindBuffer(GL_ARRAY_BUFFER, opengl_vbo);
glDepthFunc(GL_LEQUAL);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
}
static void gfx_opengl_on_resize(void) {
}
static void gfx_opengl_start_frame(void) {
frame_count++;
glDisable(GL_SCISSOR_TEST);
glDepthMask(GL_TRUE); // Must be set to clear Z-buffer
glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glEnable(GL_SCISSOR_TEST);
}
static void gfx_opengl_end_frame(void) {
}
static void gfx_opengl_finish_render(void) {
}
struct GfxRenderingAPI gfx_opengl_api = {
gfx_opengl_z_is_from_0_to_1,
gfx_opengl_unload_shader,
gfx_opengl_load_shader,
gfx_opengl_create_and_load_new_shader,
gfx_opengl_lookup_shader,
gfx_opengl_shader_get_info,
gfx_opengl_new_texture,
gfx_opengl_select_texture,
gfx_opengl_upload_texture,
gfx_opengl_set_sampler_parameters,
gfx_opengl_set_depth_test,
gfx_opengl_set_depth_mask,
gfx_opengl_set_zmode_decal,
gfx_opengl_set_viewport,
gfx_opengl_set_scissor,
gfx_opengl_set_use_alpha,
gfx_opengl_draw_triangles,
gfx_opengl_init,
gfx_opengl_on_resize,
gfx_opengl_start_frame,
gfx_opengl_end_frame,
gfx_opengl_finish_render
};
+8
View File
@@ -0,0 +1,8 @@
#ifndef GFX_OPENGL_H
#define GFX_OPENGL_H
#include "gfx_rendering_api.h"
extern struct GfxRenderingAPI gfx_opengl_api;
#endif
File diff suppressed because it is too large. Load diff
+36
View File
@@ -0,0 +1,36 @@
#ifndef GFX_PC_H
#define GFX_PC_H
#include <stdbool.h>
#include <stdint.h>
#ifndef _LANGUAGE_C
#define _LANGUAGE_C
#endif
#include <PR/gbi.h>
struct GfxRenderingAPI;
struct GfxWindowManagerAPI;
struct GfxDimensions {
uint32_t width, height;
float aspect_ratio;
};
extern struct GfxDimensions gfx_current_dimensions;
#ifdef __cplusplus
extern "C" {
#endif
void gfx_init(struct GfxWindowManagerAPI *wapi, struct GfxRenderingAPI *rapi, const char *game_name, bool start_in_fullscreen);
struct GfxRenderingAPI *gfx_get_current_rendering_api(void);
void gfx_start_frame(void);
void gfx_run(Gfx *commands);
void gfx_end_frame(void);
#ifdef __cplusplus
}
#endif
#endif
@@ -0,0 +1,35 @@
#ifndef GFX_RENDERING_API_H
#define GFX_RENDERING_API_H
#include <stddef.h>
#include <stdint.h>
#include <stdbool.h>
struct ShaderProgram;
struct GfxRenderingAPI {
bool (*z_is_from_0_to_1)(void);
void (*unload_shader)(struct ShaderProgram *old_prg);
void (*load_shader)(struct ShaderProgram *new_prg);
struct ShaderProgram *(*create_and_load_new_shader)(uint32_t shader_id);
struct ShaderProgram *(*lookup_shader)(uint32_t shader_id);
void (*shader_get_info)(struct ShaderProgram *prg, uint8_t *num_inputs, bool used_textures[2]);
uint32_t (*new_texture)(void);
void (*select_texture)(int tile, uint32_t texture_id);
void (*upload_texture)(const uint8_t *rgba32_buf, int width, int height);
void (*set_sampler_parameters)(int sampler, bool linear_filter, uint32_t cms, uint32_t cmt);
void (*set_depth_test)(bool depth_test);
void (*set_depth_mask)(bool z_upd);
void (*set_zmode_decal)(bool zmode_decal);
void (*set_viewport)(int x, int y, int width, int height);
void (*set_scissor)(int x, int y, int width, int height);
void (*set_use_alpha)(bool use_alpha);
void (*draw_triangles)(float buf_vbo[], size_t buf_vbo_len, size_t buf_vbo_num_tris);
void (*init)(void);
void (*on_resize)(void);
void (*start_frame)(void);
void (*end_frame)(void);
void (*finish_render)(void);
};
#endif
@@ -0,0 +1,7 @@
#ifndef GFX_SCREEN_CONFIG_H
#define GFX_SCREEN_CONFIG_H
#define DESIRED_SCREEN_WIDTH 640
#define DESIRED_SCREEN_HEIGHT 480
#endif
+191
View File
@@ -0,0 +1,191 @@
#include <stdlib.h>
#include <stdio.h>
#include <SDL.h>
#include "gfx_window_manager_api.h"
#include "gfx_screen_config.h"
#define GFX_API_NAME "SDL2 - OpenGL"
static SDL_Window *wnd;
static int vsync_enabled = 0;
static unsigned int window_width = DESIRED_SCREEN_WIDTH;
static unsigned int window_height = DESIRED_SCREEN_HEIGHT;
static bool fullscreen_state;
static void (*on_fullscreen_changed_callback)(bool is_now_fullscreen);
static void set_fullscreen(bool on, bool call_callback) {
if (fullscreen_state == on) {
return;
}
fullscreen_state = on;
if (on) {
SDL_DisplayMode mode;
SDL_GetDesktopDisplayMode(0, &mode);
window_width = mode.w;
window_height = mode.h;
} else {
window_width = DESIRED_SCREEN_WIDTH;
window_height = DESIRED_SCREEN_HEIGHT;
}
SDL_SetWindowSize(wnd, window_width, window_height);
SDL_SetWindowFullscreen(wnd, on ? SDL_WINDOW_FULLSCREEN : 0);
if (on_fullscreen_changed_callback != NULL && call_callback) {
on_fullscreen_changed_callback(on);
}
}
static void test_vsync(void) {
// Even if SDL_GL_SetSwapInterval succeeds, it doesn't mean that VSync actually works.
// A 60 Hz monitor should have a swap interval of 16.67 milliseconds.
// Try to detect the length of a vsync by swapping buffers some times.
// Since the graphics card may enqueue a fixed number of frames,
// first send in four dummy frames to hopefully fill the queue.
// This method will fail if the refresh rate is changed, which, in
// combination with that we can't control the queue size (i.e. lag)
// is a reason this generic SDL2 backend should only be used as last resort.
Uint32 start;
Uint32 end;
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
start = SDL_GetTicks();
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
SDL_GL_SwapWindow(wnd);
end = SDL_GetTicks();
float average = 4.0 * 1000.0 / (end - start);
vsync_enabled = 1;
if (average > 27 && average < 33) {
SDL_GL_SetSwapInterval(1);
} else if (average > 57 && average < 63) {
SDL_GL_SetSwapInterval(2);
} else if (average > 86 && average < 94) {
SDL_GL_SetSwapInterval(3);
} else if (average > 115 && average < 125) {
SDL_GL_SetSwapInterval(4);
} else {
vsync_enabled = 0;
}
}
static void gfx_sdl_init(const char *game_name, bool start_in_fullscreen) {
SDL_Init(SDL_INIT_VIDEO);
SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 24);
SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);
//SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 1);
//SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, 4);
char title[512];
int len = sprintf(title, "%s (%s)", game_name, GFX_API_NAME);
wnd = SDL_CreateWindow(title, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED,
window_width, window_height, SDL_WINDOW_OPENGL | SDL_WINDOW_SHOWN | SDL_WINDOW_RESIZABLE);
if (start_in_fullscreen) {
set_fullscreen(true, false);
}
SDL_GL_CreateContext(wnd);
SDL_GL_SetSwapInterval(1);
test_vsync();
if (!vsync_enabled)
puts("Warning: VSync is not enabled or not working. Falling back to timer for synchronization");
}
static void gfx_sdl_set_fullscreen_changed_callback(void (*on_fullscreen_changed)(bool is_now_fullscreen)) {
on_fullscreen_changed_callback = on_fullscreen_changed;
}
static void gfx_sdl_set_fullscreen(bool enable) {
set_fullscreen(enable, true);
}
static void gfx_sdl_main_loop(void (*run_one_game_iter)(void)) {
while (1) {
run_one_game_iter();
}
}
static void gfx_sdl_get_dimensions(uint32_t *width, uint32_t *height) {
*width = window_width;
*height = window_height;
}
static void gfx_sdl_handle_events(void) {
SDL_Event event;
while (SDL_PollEvent(&event)) {
switch (event.type) {
case SDL_WINDOWEVENT:
if (event.window.event == SDL_WINDOWEVENT_SIZE_CHANGED) {
window_width = event.window.data1;
window_height = event.window.data2;
}
break;
case SDL_QUIT:
exit(0);
}
}
}
static bool gfx_sdl_start_frame(void) {
return true;
}
static void sync_framerate_with_timer(void) {
// Number of milliseconds a frame should take (60 fps)
const Uint32 FRAME_TIME = 1000 / 60;
static Uint32 last_time;
Uint32 elapsed = SDL_GetTicks() - last_time;
if (elapsed < FRAME_TIME)
SDL_Delay(FRAME_TIME - elapsed);
last_time += FRAME_TIME;
}
static void gfx_sdl_swap_buffers_begin(void) {
if (!vsync_enabled) {
sync_framerate_with_timer();
}
SDL_GL_SwapWindow(wnd);
}
static void gfx_sdl_swap_buffers_end(void) {
}
static double gfx_sdl_get_time(void) {
return 0.0;
}
static void *gfx_sdl_get_window_handle(void) {
return wnd;
}
struct GfxWindowManagerAPI gfx_sdl = {
gfx_sdl_init,
gfx_sdl_set_fullscreen_changed_callback,
gfx_sdl_set_fullscreen,
gfx_sdl_main_loop,
gfx_sdl_get_dimensions,
gfx_sdl_handle_events,
gfx_sdl_start_frame,
gfx_sdl_swap_buffers_begin,
gfx_sdl_swap_buffers_end,
gfx_sdl_get_time,
gfx_sdl_get_window_handle,
};
+8
View File
@@ -0,0 +1,8 @@
#ifndef GFX_SDL_H
#define GFX_SDL_H
#include "gfx_window_manager_api.h"
extern struct GfxWindowManagerAPI gfx_sdl;
#endif
@@ -0,0 +1,21 @@
#ifndef GFX_WINDOW_MANAGER_API_H
#define GFX_WINDOW_MANAGER_API_H
#include <stdint.h>
#include <stdbool.h>
struct GfxWindowManagerAPI {
void (*init)(const char *game_name, bool start_in_fullscreen);
void (*set_fullscreen_changed_callback)(void (*on_fullscreen_changed)(bool is_now_fullscreen));
void (*set_fullscreen)(bool enable);
void (*main_loop)(void (*run_one_game_iter)(void));
void (*get_dimensions)(uint32_t *width, uint32_t *height);
void (*handle_events)(void);
bool (*start_frame)(void);
void (*swap_buffers_begin)(void);
void (*swap_buffers_end)(void);
double (*get_time)(void); // For debug
void *(*get_window_handle)(void);
};
#endif
+475
View File
@@ -0,0 +1,475 @@
/*
OpenGL ES loader generated by glad 0.1.34 on Wed Jul 26 19:11:08 2023.
Language/Generator: C/C++
Specification: gl
APIs: gles2=2.0
Profile: compatibility
Extensions:
Loader: True
Local files: True
Omit khrplatform: False
Reproducible: False
Commandline:
--profile="compatibility" --api="gles2=2.0" --generator="c" --spec="gl" --local-files --extensions=""
Online:
https://glad.dav1d.de/#profile=compatibility&language=c&specification=gl&loader=on&api=gles2%3D2.0
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "glad.h"
struct gladGLversionStruct GLVersion = { 0, 0 };
#if defined(GL_ES_VERSION_3_0) || defined(GL_VERSION_3_0)
#define _GLAD_IS_SOME_NEW_VERSION 1
#endif
static int max_loaded_major;
static int max_loaded_minor;
static const char *exts = NULL;
static int num_exts_i = 0;
static char **exts_i = NULL;
static int get_exts(void) {
#ifdef _GLAD_IS_SOME_NEW_VERSION
if(max_loaded_major < 3) {
#endif
exts = (const char *)glGetString(GL_EXTENSIONS);
#ifdef _GLAD_IS_SOME_NEW_VERSION
} else {
unsigned int index;
num_exts_i = 0;
glGetIntegerv(GL_NUM_EXTENSIONS, &num_exts_i);
if (num_exts_i > 0) {
exts_i = (char **)malloc((size_t)num_exts_i * (sizeof *exts_i));
}
if (exts_i == NULL) {
return 0;
}
for(index = 0; index < (unsigned)num_exts_i; index++) {
const char *gl_str_tmp = (const char*)glGetStringi(GL_EXTENSIONS, index);
size_t len = strlen(gl_str_tmp);
char *local_str = (char*)malloc((len+1) * sizeof(char));
if(local_str != NULL) {
memcpy(local_str, gl_str_tmp, (len+1) * sizeof(char));
}
exts_i[index] = local_str;
}
}
#endif
return 1;
}
static void free_exts(void) {
if (exts_i != NULL) {
int index;
for(index = 0; index < num_exts_i; index++) {
free((char *)exts_i[index]);
}
free((void *)exts_i);
exts_i = NULL;
}
}
static int has_ext(const char *ext) {
#ifdef _GLAD_IS_SOME_NEW_VERSION
if(max_loaded_major < 3) {
#endif
const char *extensions;
const char *loc;
const char *terminator;
extensions = exts;
if(extensions == NULL || ext == NULL) {
return 0;
}
while(1) {
loc = strstr(extensions, ext);
if(loc == NULL) {
return 0;
}
terminator = loc + strlen(ext);
if((loc == extensions || *(loc - 1) == ' ') &&
(*terminator == ' ' || *terminator == '\0')) {
return 1;
}
extensions = terminator;
}
#ifdef _GLAD_IS_SOME_NEW_VERSION
} else {
int index;
if(exts_i == NULL) return 0;
for(index = 0; index < num_exts_i; index++) {
const char *e = exts_i[index];
if(exts_i[index] != NULL && strcmp(e, ext) == 0) {
return 1;
}
}
}
#endif
return 0;
}
int GLAD_GL_ES_VERSION_2_0 = 0;
PFNGLACTIVETEXTUREPROC glad_glActiveTexture = NULL;
PFNGLATTACHSHADERPROC glad_glAttachShader = NULL;
PFNGLBINDATTRIBLOCATIONPROC glad_glBindAttribLocation = NULL;
PFNGLBINDBUFFERPROC glad_glBindBuffer = NULL;
PFNGLBINDFRAMEBUFFERPROC glad_glBindFramebuffer = NULL;
PFNGLBINDRENDERBUFFERPROC glad_glBindRenderbuffer = NULL;
PFNGLBINDTEXTUREPROC glad_glBindTexture = NULL;
PFNGLBLENDCOLORPROC glad_glBlendColor = NULL;
PFNGLBLENDEQUATIONPROC glad_glBlendEquation = NULL;
PFNGLBLENDEQUATIONSEPARATEPROC glad_glBlendEquationSeparate = NULL;
PFNGLBLENDFUNCPROC glad_glBlendFunc = NULL;
PFNGLBLENDFUNCSEPARATEPROC glad_glBlendFuncSeparate = NULL;
PFNGLBUFFERDATAPROC glad_glBufferData = NULL;
PFNGLBUFFERSUBDATAPROC glad_glBufferSubData = NULL;
PFNGLCHECKFRAMEBUFFERSTATUSPROC glad_glCheckFramebufferStatus = NULL;
PFNGLCLEARPROC glad_glClear = NULL;
PFNGLCLEARCOLORPROC glad_glClearColor = NULL;
PFNGLCLEARDEPTHFPROC glad_glClearDepthf = NULL;
PFNGLCLEARSTENCILPROC glad_glClearStencil = NULL;
PFNGLCOLORMASKPROC glad_glColorMask = NULL;
PFNGLCOMPILESHADERPROC glad_glCompileShader = NULL;
PFNGLCOMPRESSEDTEXIMAGE2DPROC glad_glCompressedTexImage2D = NULL;
PFNGLCOMPRESSEDTEXSUBIMAGE2DPROC glad_glCompressedTexSubImage2D = NULL;
PFNGLCOPYTEXIMAGE2DPROC glad_glCopyTexImage2D = NULL;
PFNGLCOPYTEXSUBIMAGE2DPROC glad_glCopyTexSubImage2D = NULL;
PFNGLCREATEPROGRAMPROC glad_glCreateProgram = NULL;
PFNGLCREATESHADERPROC glad_glCreateShader = NULL;
PFNGLCULLFACEPROC glad_glCullFace = NULL;
PFNGLDELETEBUFFERSPROC glad_glDeleteBuffers = NULL;
PFNGLDELETEFRAMEBUFFERSPROC glad_glDeleteFramebuffers = NULL;
PFNGLDELETEPROGRAMPROC glad_glDeleteProgram = NULL;
PFNGLDELETERENDERBUFFERSPROC glad_glDeleteRenderbuffers = NULL;
PFNGLDELETESHADERPROC glad_glDeleteShader = NULL;
PFNGLDELETETEXTURESPROC glad_glDeleteTextures = NULL;
PFNGLDEPTHFUNCPROC glad_glDepthFunc = NULL;
PFNGLDEPTHMASKPROC glad_glDepthMask = NULL;
PFNGLDEPTHRANGEFPROC glad_glDepthRangef = NULL;
PFNGLDETACHSHADERPROC glad_glDetachShader = NULL;
PFNGLDISABLEPROC glad_glDisable = NULL;
PFNGLDISABLEVERTEXATTRIBARRAYPROC glad_glDisableVertexAttribArray = NULL;
PFNGLDRAWARRAYSPROC glad_glDrawArrays = NULL;
PFNGLDRAWELEMENTSPROC glad_glDrawElements = NULL;
PFNGLENABLEPROC glad_glEnable = NULL;
PFNGLENABLEVERTEXATTRIBARRAYPROC glad_glEnableVertexAttribArray = NULL;
PFNGLFINISHPROC glad_glFinish = NULL;
PFNGLFLUSHPROC glad_glFlush = NULL;
PFNGLFRAMEBUFFERRENDERBUFFERPROC glad_glFramebufferRenderbuffer = NULL;
PFNGLFRAMEBUFFERTEXTURE2DPROC glad_glFramebufferTexture2D = NULL;
PFNGLFRONTFACEPROC glad_glFrontFace = NULL;
PFNGLGENBUFFERSPROC glad_glGenBuffers = NULL;
PFNGLGENFRAMEBUFFERSPROC glad_glGenFramebuffers = NULL;
PFNGLGENRENDERBUFFERSPROC glad_glGenRenderbuffers = NULL;
PFNGLGENTEXTURESPROC glad_glGenTextures = NULL;
PFNGLGENERATEMIPMAPPROC glad_glGenerateMipmap = NULL;
PFNGLGETACTIVEATTRIBPROC glad_glGetActiveAttrib = NULL;
PFNGLGETACTIVEUNIFORMPROC glad_glGetActiveUniform = NULL;
PFNGLGETATTACHEDSHADERSPROC glad_glGetAttachedShaders = NULL;
PFNGLGETATTRIBLOCATIONPROC glad_glGetAttribLocation = NULL;
PFNGLGETBOOLEANVPROC glad_glGetBooleanv = NULL;
PFNGLGETBUFFERPARAMETERIVPROC glad_glGetBufferParameteriv = NULL;
PFNGLGETERRORPROC glad_glGetError = NULL;
PFNGLGETFLOATVPROC glad_glGetFloatv = NULL;
PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVPROC glad_glGetFramebufferAttachmentParameteriv = NULL;
PFNGLGETINTEGERVPROC glad_glGetIntegerv = NULL;
PFNGLGETPROGRAMINFOLOGPROC glad_glGetProgramInfoLog = NULL;
PFNGLGETPROGRAMIVPROC glad_glGetProgramiv = NULL;
PFNGLGETRENDERBUFFERPARAMETERIVPROC glad_glGetRenderbufferParameteriv = NULL;
PFNGLGETSHADERINFOLOGPROC glad_glGetShaderInfoLog = NULL;
PFNGLGETSHADERPRECISIONFORMATPROC glad_glGetShaderPrecisionFormat = NULL;
PFNGLGETSHADERSOURCEPROC glad_glGetShaderSource = NULL;
PFNGLGETSHADERIVPROC glad_glGetShaderiv = NULL;
PFNGLGETSTRINGPROC glad_glGetString = NULL;
PFNGLGETTEXPARAMETERFVPROC glad_glGetTexParameterfv = NULL;
PFNGLGETTEXPARAMETERIVPROC glad_glGetTexParameteriv = NULL;
PFNGLGETUNIFORMLOCATIONPROC glad_glGetUniformLocation = NULL;
PFNGLGETUNIFORMFVPROC glad_glGetUniformfv = NULL;
PFNGLGETUNIFORMIVPROC glad_glGetUniformiv = NULL;
PFNGLGETVERTEXATTRIBPOINTERVPROC glad_glGetVertexAttribPointerv = NULL;
PFNGLGETVERTEXATTRIBFVPROC glad_glGetVertexAttribfv = NULL;
PFNGLGETVERTEXATTRIBIVPROC glad_glGetVertexAttribiv = NULL;
PFNGLHINTPROC glad_glHint = NULL;
PFNGLISBUFFERPROC glad_glIsBuffer = NULL;
PFNGLISENABLEDPROC glad_glIsEnabled = NULL;
PFNGLISFRAMEBUFFERPROC glad_glIsFramebuffer = NULL;
PFNGLISPROGRAMPROC glad_glIsProgram = NULL;
PFNGLISRENDERBUFFERPROC glad_glIsRenderbuffer = NULL;
PFNGLISSHADERPROC glad_glIsShader = NULL;
PFNGLISTEXTUREPROC glad_glIsTexture = NULL;
PFNGLLINEWIDTHPROC glad_glLineWidth = NULL;
PFNGLLINKPROGRAMPROC glad_glLinkProgram = NULL;
PFNGLPIXELSTOREIPROC glad_glPixelStorei = NULL;
PFNGLPOLYGONOFFSETPROC glad_glPolygonOffset = NULL;
PFNGLREADPIXELSPROC glad_glReadPixels = NULL;
PFNGLRELEASESHADERCOMPILERPROC glad_glReleaseShaderCompiler = NULL;
PFNGLRENDERBUFFERSTORAGEPROC glad_glRenderbufferStorage = NULL;
PFNGLSAMPLECOVERAGEPROC glad_glSampleCoverage = NULL;
PFNGLSCISSORPROC glad_glScissor = NULL;
PFNGLSHADERBINARYPROC glad_glShaderBinary = NULL;
PFNGLSHADERSOURCEPROC glad_glShaderSource = NULL;
PFNGLSTENCILFUNCPROC glad_glStencilFunc = NULL;
PFNGLSTENCILFUNCSEPARATEPROC glad_glStencilFuncSeparate = NULL;
PFNGLSTENCILMASKPROC glad_glStencilMask = NULL;
PFNGLSTENCILMASKSEPARATEPROC glad_glStencilMaskSeparate = NULL;
PFNGLSTENCILOPPROC glad_glStencilOp = NULL;
PFNGLSTENCILOPSEPARATEPROC glad_glStencilOpSeparate = NULL;
PFNGLTEXIMAGE2DPROC glad_glTexImage2D = NULL;
PFNGLTEXPARAMETERFPROC glad_glTexParameterf = NULL;
PFNGLTEXPARAMETERFVPROC glad_glTexParameterfv = NULL;
PFNGLTEXPARAMETERIPROC glad_glTexParameteri = NULL;
PFNGLTEXPARAMETERIVPROC glad_glTexParameteriv = NULL;
PFNGLTEXSUBIMAGE2DPROC glad_glTexSubImage2D = NULL;
PFNGLUNIFORM1FPROC glad_glUniform1f = NULL;
PFNGLUNIFORM1FVPROC glad_glUniform1fv = NULL;
PFNGLUNIFORM1IPROC glad_glUniform1i = NULL;
PFNGLUNIFORM1IVPROC glad_glUniform1iv = NULL;
PFNGLUNIFORM2FPROC glad_glUniform2f = NULL;
PFNGLUNIFORM2FVPROC glad_glUniform2fv = NULL;
PFNGLUNIFORM2IPROC glad_glUniform2i = NULL;
PFNGLUNIFORM2IVPROC glad_glUniform2iv = NULL;
PFNGLUNIFORM3FPROC glad_glUniform3f = NULL;
PFNGLUNIFORM3FVPROC glad_glUniform3fv = NULL;
PFNGLUNIFORM3IPROC glad_glUniform3i = NULL;
PFNGLUNIFORM3IVPROC glad_glUniform3iv = NULL;
PFNGLUNIFORM4FPROC glad_glUniform4f = NULL;
PFNGLUNIFORM4FVPROC glad_glUniform4fv = NULL;
PFNGLUNIFORM4IPROC glad_glUniform4i = NULL;
PFNGLUNIFORM4IVPROC glad_glUniform4iv = NULL;
PFNGLUNIFORMMATRIX2FVPROC glad_glUniformMatrix2fv = NULL;
PFNGLUNIFORMMATRIX3FVPROC glad_glUniformMatrix3fv = NULL;
PFNGLUNIFORMMATRIX4FVPROC glad_glUniformMatrix4fv = NULL;
PFNGLUSEPROGRAMPROC glad_glUseProgram = NULL;
PFNGLVALIDATEPROGRAMPROC glad_glValidateProgram = NULL;
PFNGLVERTEXATTRIB1FPROC glad_glVertexAttrib1f = NULL;
PFNGLVERTEXATTRIB1FVPROC glad_glVertexAttrib1fv = NULL;
PFNGLVERTEXATTRIB2FPROC glad_glVertexAttrib2f = NULL;
PFNGLVERTEXATTRIB2FVPROC glad_glVertexAttrib2fv = NULL;
PFNGLVERTEXATTRIB3FPROC glad_glVertexAttrib3f = NULL;
PFNGLVERTEXATTRIB3FVPROC glad_glVertexAttrib3fv = NULL;
PFNGLVERTEXATTRIB4FPROC glad_glVertexAttrib4f = NULL;
PFNGLVERTEXATTRIB4FVPROC glad_glVertexAttrib4fv = NULL;
PFNGLVERTEXATTRIBPOINTERPROC glad_glVertexAttribPointer = NULL;
PFNGLVIEWPORTPROC glad_glViewport = NULL;
static void load_GL_ES_VERSION_2_0(GLADloadproc load) {
if(!GLAD_GL_ES_VERSION_2_0) return;
glad_glActiveTexture = (PFNGLACTIVETEXTUREPROC)load("glActiveTexture");
glad_glAttachShader = (PFNGLATTACHSHADERPROC)load("glAttachShader");
glad_glBindAttribLocation = (PFNGLBINDATTRIBLOCATIONPROC)load("glBindAttribLocation");
glad_glBindBuffer = (PFNGLBINDBUFFERPROC)load("glBindBuffer");
glad_glBindFramebuffer = (PFNGLBINDFRAMEBUFFERPROC)load("glBindFramebuffer");
glad_glBindRenderbuffer = (PFNGLBINDRENDERBUFFERPROC)load("glBindRenderbuffer");
glad_glBindTexture = (PFNGLBINDTEXTUREPROC)load("glBindTexture");
glad_glBlendColor = (PFNGLBLENDCOLORPROC)load("glBlendColor");
glad_glBlendEquation = (PFNGLBLENDEQUATIONPROC)load("glBlendEquation");
glad_glBlendEquationSeparate = (PFNGLBLENDEQUATIONSEPARATEPROC)load("glBlendEquationSeparate");
glad_glBlendFunc = (PFNGLBLENDFUNCPROC)load("glBlendFunc");
glad_glBlendFuncSeparate = (PFNGLBLENDFUNCSEPARATEPROC)load("glBlendFuncSeparate");
glad_glBufferData = (PFNGLBUFFERDATAPROC)load("glBufferData");
glad_glBufferSubData = (PFNGLBUFFERSUBDATAPROC)load("glBufferSubData");
glad_glCheckFramebufferStatus = (PFNGLCHECKFRAMEBUFFERSTATUSPROC)load("glCheckFramebufferStatus");
glad_glClear = (PFNGLCLEARPROC)load("glClear");
glad_glClearColor = (PFNGLCLEARCOLORPROC)load("glClearColor");
glad_glClearDepthf = (PFNGLCLEARDEPTHFPROC)load("glClearDepthf");
glad_glClearStencil = (PFNGLCLEARSTENCILPROC)load("glClearStencil");
glad_glColorMask = (PFNGLCOLORMASKPROC)load("glColorMask");
glad_glCompileShader = (PFNGLCOMPILESHADERPROC)load("glCompileShader");
glad_glCompressedTexImage2D = (PFNGLCOMPRESSEDTEXIMAGE2DPROC)load("glCompressedTexImage2D");
glad_glCompressedTexSubImage2D = (PFNGLCOMPRESSEDTEXSUBIMAGE2DPROC)load("glCompressedTexSubImage2D");
glad_glCopyTexImage2D = (PFNGLCOPYTEXIMAGE2DPROC)load("glCopyTexImage2D");
glad_glCopyTexSubImage2D = (PFNGLCOPYTEXSUBIMAGE2DPROC)load("glCopyTexSubImage2D");
glad_glCreateProgram = (PFNGLCREATEPROGRAMPROC)load("glCreateProgram");
glad_glCreateShader = (PFNGLCREATESHADERPROC)load("glCreateShader");
glad_glCullFace = (PFNGLCULLFACEPROC)load("glCullFace");
glad_glDeleteBuffers = (PFNGLDELETEBUFFERSPROC)load("glDeleteBuffers");
glad_glDeleteFramebuffers = (PFNGLDELETEFRAMEBUFFERSPROC)load("glDeleteFramebuffers");
glad_glDeleteProgram = (PFNGLDELETEPROGRAMPROC)load("glDeleteProgram");
glad_glDeleteRenderbuffers = (PFNGLDELETERENDERBUFFERSPROC)load("glDeleteRenderbuffers");
glad_glDeleteShader = (PFNGLDELETESHADERPROC)load("glDeleteShader");
glad_glDeleteTextures = (PFNGLDELETETEXTURESPROC)load("glDeleteTextures");
glad_glDepthFunc = (PFNGLDEPTHFUNCPROC)load("glDepthFunc");
glad_glDepthMask = (PFNGLDEPTHMASKPROC)load("glDepthMask");
glad_glDepthRangef = (PFNGLDEPTHRANGEFPROC)load("glDepthRangef");
glad_glDetachShader = (PFNGLDETACHSHADERPROC)load("glDetachShader");
glad_glDisable = (PFNGLDISABLEPROC)load("glDisable");
glad_glDisableVertexAttribArray = (PFNGLDISABLEVERTEXATTRIBARRAYPROC)load("glDisableVertexAttribArray");
glad_glDrawArrays = (PFNGLDRAWARRAYSPROC)load("glDrawArrays");
glad_glDrawElements = (PFNGLDRAWELEMENTSPROC)load("glDrawElements");
glad_glEnable = (PFNGLENABLEPROC)load("glEnable");
glad_glEnableVertexAttribArray = (PFNGLENABLEVERTEXATTRIBARRAYPROC)load("glEnableVertexAttribArray");
glad_glFinish = (PFNGLFINISHPROC)load("glFinish");
glad_glFlush = (PFNGLFLUSHPROC)load("glFlush");
glad_glFramebufferRenderbuffer = (PFNGLFRAMEBUFFERRENDERBUFFERPROC)load("glFramebufferRenderbuffer");
glad_glFramebufferTexture2D = (PFNGLFRAMEBUFFERTEXTURE2DPROC)load("glFramebufferTexture2D");
glad_glFrontFace = (PFNGLFRONTFACEPROC)load("glFrontFace");
glad_glGenBuffers = (PFNGLGENBUFFERSPROC)load("glGenBuffers");
glad_glGenerateMipmap = (PFNGLGENERATEMIPMAPPROC)load("glGenerateMipmap");
glad_glGenFramebuffers = (PFNGLGENFRAMEBUFFERSPROC)load("glGenFramebuffers");
glad_glGenRenderbuffers = (PFNGLGENRENDERBUFFERSPROC)load("glGenRenderbuffers");
glad_glGenTextures = (PFNGLGENTEXTURESPROC)load("glGenTextures");
glad_glGetActiveAttrib = (PFNGLGETACTIVEATTRIBPROC)load("glGetActiveAttrib");
glad_glGetActiveUniform = (PFNGLGETACTIVEUNIFORMPROC)load("glGetActiveUniform");
glad_glGetAttachedShaders = (PFNGLGETATTACHEDSHADERSPROC)load("glGetAttachedShaders");
glad_glGetAttribLocation = (PFNGLGETATTRIBLOCATIONPROC)load("glGetAttribLocation");
glad_glGetBooleanv = (PFNGLGETBOOLEANVPROC)load("glGetBooleanv");
glad_glGetBufferParameteriv = (PFNGLGETBUFFERPARAMETERIVPROC)load("glGetBufferParameteriv");
glad_glGetError = (PFNGLGETERRORPROC)load("glGetError");
glad_glGetFloatv = (PFNGLGETFLOATVPROC)load("glGetFloatv");
glad_glGetFramebufferAttachmentParameteriv = (PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVPROC)load("glGetFramebufferAttachmentParameteriv");
glad_glGetIntegerv = (PFNGLGETINTEGERVPROC)load("glGetIntegerv");
glad_glGetProgramiv = (PFNGLGETPROGRAMIVPROC)load("glGetProgramiv");
glad_glGetProgramInfoLog = (PFNGLGETPROGRAMINFOLOGPROC)load("glGetProgramInfoLog");
glad_glGetRenderbufferParameteriv = (PFNGLGETRENDERBUFFERPARAMETERIVPROC)load("glGetRenderbufferParameteriv");
glad_glGetShaderiv = (PFNGLGETSHADERIVPROC)load("glGetShaderiv");
glad_glGetShaderInfoLog = (PFNGLGETSHADERINFOLOGPROC)load("glGetShaderInfoLog");
glad_glGetShaderPrecisionFormat = (PFNGLGETSHADERPRECISIONFORMATPROC)load("glGetShaderPrecisionFormat");
glad_glGetShaderSource = (PFNGLGETSHADERSOURCEPROC)load("glGetShaderSource");
glad_glGetString = (PFNGLGETSTRINGPROC)load("glGetString");
glad_glGetTexParameterfv = (PFNGLGETTEXPARAMETERFVPROC)load("glGetTexParameterfv");
glad_glGetTexParameteriv = (PFNGLGETTEXPARAMETERIVPROC)load("glGetTexParameteriv");
glad_glGetUniformfv = (PFNGLGETUNIFORMFVPROC)load("glGetUniformfv");
glad_glGetUniformiv = (PFNGLGETUNIFORMIVPROC)load("glGetUniformiv");
glad_glGetUniformLocation = (PFNGLGETUNIFORMLOCATIONPROC)load("glGetUniformLocation");
glad_glGetVertexAttribfv = (PFNGLGETVERTEXATTRIBFVPROC)load("glGetVertexAttribfv");
glad_glGetVertexAttribiv = (PFNGLGETVERTEXATTRIBIVPROC)load("glGetVertexAttribiv");
glad_glGetVertexAttribPointerv = (PFNGLGETVERTEXATTRIBPOINTERVPROC)load("glGetVertexAttribPointerv");
glad_glHint = (PFNGLHINTPROC)load("glHint");
glad_glIsBuffer = (PFNGLISBUFFERPROC)load("glIsBuffer");
glad_glIsEnabled = (PFNGLISENABLEDPROC)load("glIsEnabled");
glad_glIsFramebuffer = (PFNGLISFRAMEBUFFERPROC)load("glIsFramebuffer");
glad_glIsProgram = (PFNGLISPROGRAMPROC)load("glIsProgram");
glad_glIsRenderbuffer = (PFNGLISRENDERBUFFERPROC)load("glIsRenderbuffer");
glad_glIsShader = (PFNGLISSHADERPROC)load("glIsShader");
glad_glIsTexture = (PFNGLISTEXTUREPROC)load("glIsTexture");
glad_glLineWidth = (PFNGLLINEWIDTHPROC)load("glLineWidth");
glad_glLinkProgram = (PFNGLLINKPROGRAMPROC)load("glLinkProgram");
glad_glPixelStorei = (PFNGLPIXELSTOREIPROC)load("glPixelStorei");
glad_glPolygonOffset = (PFNGLPOLYGONOFFSETPROC)load("glPolygonOffset");
glad_glReadPixels = (PFNGLREADPIXELSPROC)load("glReadPixels");
glad_glReleaseShaderCompiler = (PFNGLRELEASESHADERCOMPILERPROC)load("glReleaseShaderCompiler");
glad_glRenderbufferStorage = (PFNGLRENDERBUFFERSTORAGEPROC)load("glRenderbufferStorage");
glad_glSampleCoverage = (PFNGLSAMPLECOVERAGEPROC)load("glSampleCoverage");
glad_glScissor = (PFNGLSCISSORPROC)load("glScissor");
glad_glShaderBinary = (PFNGLSHADERBINARYPROC)load("glShaderBinary");
glad_glShaderSource = (PFNGLSHADERSOURCEPROC)load("glShaderSource");
glad_glStencilFunc = (PFNGLSTENCILFUNCPROC)load("glStencilFunc");
glad_glStencilFuncSeparate = (PFNGLSTENCILFUNCSEPARATEPROC)load("glStencilFuncSeparate");
glad_glStencilMask = (PFNGLSTENCILMASKPROC)load("glStencilMask");
glad_glStencilMaskSeparate = (PFNGLSTENCILMASKSEPARATEPROC)load("glStencilMaskSeparate");
glad_glStencilOp = (PFNGLSTENCILOPPROC)load("glStencilOp");
glad_glStencilOpSeparate = (PFNGLSTENCILOPSEPARATEPROC)load("glStencilOpSeparate");
glad_glTexImage2D = (PFNGLTEXIMAGE2DPROC)load("glTexImage2D");
glad_glTexParameterf = (PFNGLTEXPARAMETERFPROC)load("glTexParameterf");
glad_glTexParameterfv = (PFNGLTEXPARAMETERFVPROC)load("glTexParameterfv");
glad_glTexParameteri = (PFNGLTEXPARAMETERIPROC)load("glTexParameteri");
glad_glTexParameteriv = (PFNGLTEXPARAMETERIVPROC)load("glTexParameteriv");
glad_glTexSubImage2D = (PFNGLTEXSUBIMAGE2DPROC)load("glTexSubImage2D");
glad_glUniform1f = (PFNGLUNIFORM1FPROC)load("glUniform1f");
glad_glUniform1fv = (PFNGLUNIFORM1FVPROC)load("glUniform1fv");
glad_glUniform1i = (PFNGLUNIFORM1IPROC)load("glUniform1i");
glad_glUniform1iv = (PFNGLUNIFORM1IVPROC)load("glUniform1iv");
glad_glUniform2f = (PFNGLUNIFORM2FPROC)load("glUniform2f");
glad_glUniform2fv = (PFNGLUNIFORM2FVPROC)load("glUniform2fv");
glad_glUniform2i = (PFNGLUNIFORM2IPROC)load("glUniform2i");
glad_glUniform2iv = (PFNGLUNIFORM2IVPROC)load("glUniform2iv");
glad_glUniform3f = (PFNGLUNIFORM3FPROC)load("glUniform3f");
glad_glUniform3fv = (PFNGLUNIFORM3FVPROC)load("glUniform3fv");
glad_glUniform3i = (PFNGLUNIFORM3IPROC)load("glUniform3i");
glad_glUniform3iv = (PFNGLUNIFORM3IVPROC)load("glUniform3iv");
glad_glUniform4f = (PFNGLUNIFORM4FPROC)load("glUniform4f");
glad_glUniform4fv = (PFNGLUNIFORM4FVPROC)load("glUniform4fv");
glad_glUniform4i = (PFNGLUNIFORM4IPROC)load("glUniform4i");
glad_glUniform4iv = (PFNGLUNIFORM4IVPROC)load("glUniform4iv");
glad_glUniformMatrix2fv = (PFNGLUNIFORMMATRIX2FVPROC)load("glUniformMatrix2fv");
glad_glUniformMatrix3fv = (PFNGLUNIFORMMATRIX3FVPROC)load("glUniformMatrix3fv");
glad_glUniformMatrix4fv = (PFNGLUNIFORMMATRIX4FVPROC)load("glUniformMatrix4fv");
glad_glUseProgram = (PFNGLUSEPROGRAMPROC)load("glUseProgram");
glad_glValidateProgram = (PFNGLVALIDATEPROGRAMPROC)load("glValidateProgram");
glad_glVertexAttrib1f = (PFNGLVERTEXATTRIB1FPROC)load("glVertexAttrib1f");
glad_glVertexAttrib1fv = (PFNGLVERTEXATTRIB1FVPROC)load("glVertexAttrib1fv");
glad_glVertexAttrib2f = (PFNGLVERTEXATTRIB2FPROC)load("glVertexAttrib2f");
glad_glVertexAttrib2fv = (PFNGLVERTEXATTRIB2FVPROC)load("glVertexAttrib2fv");
glad_glVertexAttrib3f = (PFNGLVERTEXATTRIB3FPROC)load("glVertexAttrib3f");
glad_glVertexAttrib3fv = (PFNGLVERTEXATTRIB3FVPROC)load("glVertexAttrib3fv");
glad_glVertexAttrib4f = (PFNGLVERTEXATTRIB4FPROC)load("glVertexAttrib4f");
glad_glVertexAttrib4fv = (PFNGLVERTEXATTRIB4FVPROC)load("glVertexAttrib4fv");
glad_glVertexAttribPointer = (PFNGLVERTEXATTRIBPOINTERPROC)load("glVertexAttribPointer");
glad_glViewport = (PFNGLVIEWPORTPROC)load("glViewport");
}
static int find_extensionsGLES2(void) {
if (!get_exts()) return 0;
(void)&has_ext;
free_exts();
return 1;
}
static void find_coreGLES2(void) {
/* Thank you @elmindreda
* https://github.com/elmindreda/greg/blob/master/templates/greg.c.in#L176
* https://github.com/glfw/glfw/blob/master/src/context.c#L36
*/
int i, major, minor;
const char* version;
const char* prefixes[] = {
"OpenGL ES-CM ",
"OpenGL ES-CL ",
"OpenGL ES ",
NULL
};
version = (const char*) glGetString(GL_VERSION);
if (!version) return;
for (i = 0; prefixes[i]; i++) {
const size_t length = strlen(prefixes[i]);
if (strncmp(version, prefixes[i], length) == 0) {
version += length;
break;
}
}
/* PR #18 */
#ifdef _MSC_VER
sscanf_s(version, "%d.%d", &major, &minor);
#else
sscanf(version, "%d.%d", &major, &minor);
#endif
GLVersion.major = major; GLVersion.minor = minor;
max_loaded_major = major; max_loaded_minor = minor;
GLAD_GL_ES_VERSION_2_0 = (major == 2 && minor >= 0) || major > 2;
if (GLVersion.major > 2 || (GLVersion.major >= 2 && GLVersion.minor >= 0)) {
max_loaded_major = 2;
max_loaded_minor = 0;
}
}
int gladLoadGLES2Loader(GLADloadproc load) {
GLVersion.major = 0; GLVersion.minor = 0;
glGetString = (PFNGLGETSTRINGPROC)load("glGetString");
if(glGetString == NULL) return 0;
if(glGetString(GL_VERSION) == NULL) return 0;
find_coreGLES2();
load_GL_ES_VERSION_2_0(load);
if (!find_extensionsGLES2()) return 0;
return GLVersion.major != 0 || GLVersion.minor != 0;
}
+874
View File
@@ -0,0 +1,874 @@
/*
OpenGL ES loader generated by glad 0.1.34 on Wed Jul 26 19:11:08 2023.
Language/Generator: C/C++
Specification: gl
APIs: gles2=2.0
Profile: compatibility
Extensions:
Loader: True
Local files: True
Omit khrplatform: False
Reproducible: False
Commandline:
--profile="compatibility" --api="gles2=2.0" --generator="c" --spec="gl" --local-files --extensions=""
Online:
https://glad.dav1d.de/#profile=compatibility&language=c&specification=gl&loader=on&api=gles2%3D2.0
*/
#ifndef __glad_h_
#define __glad_h_
#ifdef __gl2_h_
#error OpenGL ES 2 header already included, remove this include, glad already provides it
#endif
#define __gl2_h_
#ifdef __gl3_h_
#error OpenGL ES 3 header already included, remove this include, glad already provides it
#endif
#define __gl3_h_
#if defined(_WIN32) && !defined(APIENTRY) && !defined(__CYGWIN__) && !defined(__SCITECH_SNAP__)
#define APIENTRY __stdcall
#endif
#ifndef APIENTRY
#define APIENTRY
#endif
#ifndef APIENTRYP
#define APIENTRYP APIENTRY *
#endif
#ifndef GLAPIENTRY
#define GLAPIENTRY APIENTRY
#endif
#ifdef __cplusplus
extern "C" {
#endif
struct gladGLversionStruct {
int major;
int minor;
};
typedef void* (* GLADloadproc)(const char *name);
#ifndef GLAPI
# if defined(GLAD_GLAPI_EXPORT)
# if defined(_WIN32) || defined(__CYGWIN__)
# if defined(GLAD_GLAPI_EXPORT_BUILD)
# if defined(__GNUC__)
# define GLAPI __attribute__ ((dllexport)) extern
# else
# define GLAPI __declspec(dllexport) extern
# endif
# else
# if defined(__GNUC__)
# define GLAPI __attribute__ ((dllimport)) extern
# else
# define GLAPI __declspec(dllimport) extern
# endif
# endif
# elif defined(__GNUC__) && defined(GLAD_GLAPI_EXPORT_BUILD)
# define GLAPI __attribute__ ((visibility ("default"))) extern
# else
# define GLAPI extern
# endif
# else
# define GLAPI extern
# endif
#endif
GLAPI struct gladGLversionStruct GLVersion;
GLAPI int gladLoadGLES2Loader(GLADloadproc);
#include "khrplatform.h"
typedef unsigned int GLenum;
typedef unsigned char GLboolean;
typedef unsigned int GLbitfield;
typedef void GLvoid;
typedef khronos_int8_t GLbyte;
typedef khronos_uint8_t GLubyte;
typedef khronos_int16_t GLshort;
typedef khronos_uint16_t GLushort;
typedef int GLint;
typedef unsigned int GLuint;
typedef khronos_int32_t GLclampx;
typedef int GLsizei;
typedef khronos_float_t GLfloat;
typedef khronos_float_t GLclampf;
typedef double GLdouble;
typedef double GLclampd;
typedef void *GLeglClientBufferEXT;
typedef void *GLeglImageOES;
typedef char GLchar;
typedef char GLcharARB;
#ifdef __APPLE__
typedef void *GLhandleARB;
#else
typedef unsigned int GLhandleARB;
#endif
typedef khronos_uint16_t GLhalf;
typedef khronos_uint16_t GLhalfARB;
typedef khronos_int32_t GLfixed;
typedef khronos_intptr_t GLintptr;
typedef khronos_intptr_t GLintptrARB;
typedef khronos_ssize_t GLsizeiptr;
typedef khronos_ssize_t GLsizeiptrARB;
typedef khronos_int64_t GLint64;
typedef khronos_int64_t GLint64EXT;
typedef khronos_uint64_t GLuint64;
typedef khronos_uint64_t GLuint64EXT;
typedef struct __GLsync *GLsync;
struct _cl_context;
struct _cl_event;
typedef void (APIENTRY *GLDEBUGPROC)(GLenum source,GLenum type,GLuint id,GLenum severity,GLsizei length,const GLchar *message,const void *userParam);
typedef void (APIENTRY *GLDEBUGPROCARB)(GLenum source,GLenum type,GLuint id,GLenum severity,GLsizei length,const GLchar *message,const void *userParam);
typedef void (APIENTRY *GLDEBUGPROCKHR)(GLenum source,GLenum type,GLuint id,GLenum severity,GLsizei length,const GLchar *message,const void *userParam);
typedef void (APIENTRY *GLDEBUGPROCAMD)(GLuint id,GLenum category,GLenum severity,GLsizei length,const GLchar *message,void *userParam);
typedef unsigned short GLhalfNV;
typedef GLintptr GLvdpauSurfaceNV;
typedef void (APIENTRY *GLVULKANPROCNV)(void);
#define GL_DEPTH_BUFFER_BIT 0x00000100
#define GL_STENCIL_BUFFER_BIT 0x00000400
#define GL_COLOR_BUFFER_BIT 0x00004000
#define GL_FALSE 0
#define GL_TRUE 1
#define GL_POINTS 0x0000
#define GL_LINES 0x0001
#define GL_LINE_LOOP 0x0002
#define GL_LINE_STRIP 0x0003
#define GL_TRIANGLES 0x0004
#define GL_TRIANGLE_STRIP 0x0005
#define GL_TRIANGLE_FAN 0x0006
#define GL_ZERO 0
#define GL_ONE 1
#define GL_SRC_COLOR 0x0300
#define GL_ONE_MINUS_SRC_COLOR 0x0301
#define GL_SRC_ALPHA 0x0302
#define GL_ONE_MINUS_SRC_ALPHA 0x0303
#define GL_DST_ALPHA 0x0304
#define GL_ONE_MINUS_DST_ALPHA 0x0305
#define GL_DST_COLOR 0x0306
#define GL_ONE_MINUS_DST_COLOR 0x0307
#define GL_SRC_ALPHA_SATURATE 0x0308
#define GL_FUNC_ADD 0x8006
#define GL_BLEND_EQUATION 0x8009
#define GL_BLEND_EQUATION_RGB 0x8009
#define GL_BLEND_EQUATION_ALPHA 0x883D
#define GL_FUNC_SUBTRACT 0x800A
#define GL_FUNC_REVERSE_SUBTRACT 0x800B
#define GL_BLEND_DST_RGB 0x80C8
#define GL_BLEND_SRC_RGB 0x80C9
#define GL_BLEND_DST_ALPHA 0x80CA
#define GL_BLEND_SRC_ALPHA 0x80CB
#define GL_CONSTANT_COLOR 0x8001
#define GL_ONE_MINUS_CONSTANT_COLOR 0x8002
#define GL_CONSTANT_ALPHA 0x8003
#define GL_ONE_MINUS_CONSTANT_ALPHA 0x8004
#define GL_BLEND_COLOR 0x8005
#define GL_ARRAY_BUFFER 0x8892
#define GL_ELEMENT_ARRAY_BUFFER 0x8893
#define GL_ARRAY_BUFFER_BINDING 0x8894
#define GL_ELEMENT_ARRAY_BUFFER_BINDING 0x8895
#define GL_STREAM_DRAW 0x88E0
#define GL_STATIC_DRAW 0x88E4
#define GL_DYNAMIC_DRAW 0x88E8
#define GL_BUFFER_SIZE 0x8764
#define GL_BUFFER_USAGE 0x8765
#define GL_CURRENT_VERTEX_ATTRIB 0x8626
#define GL_FRONT 0x0404
#define GL_BACK 0x0405
#define GL_FRONT_AND_BACK 0x0408
#define GL_TEXTURE_2D 0x0DE1
#define GL_CULL_FACE 0x0B44
#define GL_BLEND 0x0BE2
#define GL_DITHER 0x0BD0
#define GL_STENCIL_TEST 0x0B90
#define GL_DEPTH_TEST 0x0B71
#define GL_SCISSOR_TEST 0x0C11
#define GL_POLYGON_OFFSET_FILL 0x8037
#define GL_SAMPLE_ALPHA_TO_COVERAGE 0x809E
#define GL_SAMPLE_COVERAGE 0x80A0
#define GL_NO_ERROR 0
#define GL_INVALID_ENUM 0x0500
#define GL_INVALID_VALUE 0x0501
#define GL_INVALID_OPERATION 0x0502
#define GL_OUT_OF_MEMORY 0x0505
#define GL_CW 0x0900
#define GL_CCW 0x0901
#define GL_LINE_WIDTH 0x0B21
#define GL_ALIASED_POINT_SIZE_RANGE 0x846D
#define GL_ALIASED_LINE_WIDTH_RANGE 0x846E
#define GL_CULL_FACE_MODE 0x0B45
#define GL_FRONT_FACE 0x0B46
#define GL_DEPTH_RANGE 0x0B70
#define GL_DEPTH_WRITEMASK 0x0B72
#define GL_DEPTH_CLEAR_VALUE 0x0B73
#define GL_DEPTH_FUNC 0x0B74
#define GL_STENCIL_CLEAR_VALUE 0x0B91
#define GL_STENCIL_FUNC 0x0B92
#define GL_STENCIL_FAIL 0x0B94
#define GL_STENCIL_PASS_DEPTH_FAIL 0x0B95
#define GL_STENCIL_PASS_DEPTH_PASS 0x0B96
#define GL_STENCIL_REF 0x0B97
#define GL_STENCIL_VALUE_MASK 0x0B93
#define GL_STENCIL_WRITEMASK 0x0B98
#define GL_STENCIL_BACK_FUNC 0x8800
#define GL_STENCIL_BACK_FAIL 0x8801
#define GL_STENCIL_BACK_PASS_DEPTH_FAIL 0x8802
#define GL_STENCIL_BACK_PASS_DEPTH_PASS 0x8803
#define GL_STENCIL_BACK_REF 0x8CA3
#define GL_STENCIL_BACK_VALUE_MASK 0x8CA4
#define GL_STENCIL_BACK_WRITEMASK 0x8CA5
#define GL_VIEWPORT 0x0BA2
#define GL_SCISSOR_BOX 0x0C10
#define GL_COLOR_CLEAR_VALUE 0x0C22
#define GL_COLOR_WRITEMASK 0x0C23
#define GL_UNPACK_ALIGNMENT 0x0CF5
#define GL_PACK_ALIGNMENT 0x0D05
#define GL_MAX_TEXTURE_SIZE 0x0D33
#define GL_MAX_VIEWPORT_DIMS 0x0D3A
#define GL_SUBPIXEL_BITS 0x0D50
#define GL_RED_BITS 0x0D52
#define GL_GREEN_BITS 0x0D53
#define GL_BLUE_BITS 0x0D54
#define GL_ALPHA_BITS 0x0D55
#define GL_DEPTH_BITS 0x0D56
#define GL_STENCIL_BITS 0x0D57
#define GL_POLYGON_OFFSET_UNITS 0x2A00
#define GL_POLYGON_OFFSET_FACTOR 0x8038
#define GL_TEXTURE_BINDING_2D 0x8069
#define GL_SAMPLE_BUFFERS 0x80A8
#define GL_SAMPLES 0x80A9
#define GL_SAMPLE_COVERAGE_VALUE 0x80AA
#define GL_SAMPLE_COVERAGE_INVERT 0x80AB
#define GL_NUM_COMPRESSED_TEXTURE_FORMATS 0x86A2
#define GL_COMPRESSED_TEXTURE_FORMATS 0x86A3
#define GL_DONT_CARE 0x1100
#define GL_FASTEST 0x1101
#define GL_NICEST 0x1102
#define GL_GENERATE_MIPMAP_HINT 0x8192
#define GL_BYTE 0x1400
#define GL_UNSIGNED_BYTE 0x1401
#define GL_SHORT 0x1402
#define GL_UNSIGNED_SHORT 0x1403
#define GL_INT 0x1404
#define GL_UNSIGNED_INT 0x1405
#define GL_FLOAT 0x1406
#define GL_FIXED 0x140C
#define GL_DEPTH_COMPONENT 0x1902
#define GL_ALPHA 0x1906
#define GL_RGB 0x1907
#define GL_RGBA 0x1908
#define GL_LUMINANCE 0x1909
#define GL_LUMINANCE_ALPHA 0x190A
#define GL_UNSIGNED_SHORT_4_4_4_4 0x8033
#define GL_UNSIGNED_SHORT_5_5_5_1 0x8034
#define GL_UNSIGNED_SHORT_5_6_5 0x8363
#define GL_FRAGMENT_SHADER 0x8B30
#define GL_VERTEX_SHADER 0x8B31
#define GL_MAX_VERTEX_ATTRIBS 0x8869
#define GL_MAX_VERTEX_UNIFORM_VECTORS 0x8DFB
#define GL_MAX_VARYING_VECTORS 0x8DFC
#define GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS 0x8B4D
#define GL_MAX_VERTEX_TEXTURE_IMAGE_UNITS 0x8B4C
#define GL_MAX_TEXTURE_IMAGE_UNITS 0x8872
#define GL_MAX_FRAGMENT_UNIFORM_VECTORS 0x8DFD
#define GL_SHADER_TYPE 0x8B4F
#define GL_DELETE_STATUS 0x8B80
#define GL_LINK_STATUS 0x8B82
#define GL_VALIDATE_STATUS 0x8B83
#define GL_ATTACHED_SHADERS 0x8B85
#define GL_ACTIVE_UNIFORMS 0x8B86
#define GL_ACTIVE_UNIFORM_MAX_LENGTH 0x8B87
#define GL_ACTIVE_ATTRIBUTES 0x8B89
#define GL_ACTIVE_ATTRIBUTE_MAX_LENGTH 0x8B8A
#define GL_SHADING_LANGUAGE_VERSION 0x8B8C
#define GL_CURRENT_PROGRAM 0x8B8D
#define GL_NEVER 0x0200
#define GL_LESS 0x0201
#define GL_EQUAL 0x0202
#define GL_LEQUAL 0x0203
#define GL_GREATER 0x0204
#define GL_NOTEQUAL 0x0205
#define GL_GEQUAL 0x0206
#define GL_ALWAYS 0x0207
#define GL_KEEP 0x1E00
#define GL_REPLACE 0x1E01
#define GL_INCR 0x1E02
#define GL_DECR 0x1E03
#define GL_INVERT 0x150A
#define GL_INCR_WRAP 0x8507
#define GL_DECR_WRAP 0x8508
#define GL_VENDOR 0x1F00
#define GL_RENDERER 0x1F01
#define GL_VERSION 0x1F02
#define GL_EXTENSIONS 0x1F03
#define GL_NEAREST 0x2600
#define GL_LINEAR 0x2601
#define GL_NEAREST_MIPMAP_NEAREST 0x2700
#define GL_LINEAR_MIPMAP_NEAREST 0x2701
#define GL_NEAREST_MIPMAP_LINEAR 0x2702
#define GL_LINEAR_MIPMAP_LINEAR 0x2703
#define GL_TEXTURE_MAG_FILTER 0x2800
#define GL_TEXTURE_MIN_FILTER 0x2801
#define GL_TEXTURE_WRAP_S 0x2802
#define GL_TEXTURE_WRAP_T 0x2803
#define GL_TEXTURE 0x1702
#define GL_TEXTURE_CUBE_MAP 0x8513
#define GL_TEXTURE_BINDING_CUBE_MAP 0x8514
#define GL_TEXTURE_CUBE_MAP_POSITIVE_X 0x8515
#define GL_TEXTURE_CUBE_MAP_NEGATIVE_X 0x8516
#define GL_TEXTURE_CUBE_MAP_POSITIVE_Y 0x8517
#define GL_TEXTURE_CUBE_MAP_NEGATIVE_Y 0x8518
#define GL_TEXTURE_CUBE_MAP_POSITIVE_Z 0x8519
#define GL_TEXTURE_CUBE_MAP_NEGATIVE_Z 0x851A
#define GL_MAX_CUBE_MAP_TEXTURE_SIZE 0x851C
#define GL_TEXTURE0 0x84C0
#define GL_TEXTURE1 0x84C1
#define GL_TEXTURE2 0x84C2
#define GL_TEXTURE3 0x84C3
#define GL_TEXTURE4 0x84C4
#define GL_TEXTURE5 0x84C5
#define GL_TEXTURE6 0x84C6
#define GL_TEXTURE7 0x84C7
#define GL_TEXTURE8 0x84C8
#define GL_TEXTURE9 0x84C9
#define GL_TEXTURE10 0x84CA
#define GL_TEXTURE11 0x84CB
#define GL_TEXTURE12 0x84CC
#define GL_TEXTURE13 0x84CD
#define GL_TEXTURE14 0x84CE
#define GL_TEXTURE15 0x84CF
#define GL_TEXTURE16 0x84D0
#define GL_TEXTURE17 0x84D1
#define GL_TEXTURE18 0x84D2
#define GL_TEXTURE19 0x84D3
#define GL_TEXTURE20 0x84D4
#define GL_TEXTURE21 0x84D5
#define GL_TEXTURE22 0x84D6
#define GL_TEXTURE23 0x84D7
#define GL_TEXTURE24 0x84D8
#define GL_TEXTURE25 0x84D9
#define GL_TEXTURE26 0x84DA
#define GL_TEXTURE27 0x84DB
#define GL_TEXTURE28 0x84DC
#define GL_TEXTURE29 0x84DD
#define GL_TEXTURE30 0x84DE
#define GL_TEXTURE31 0x84DF
#define GL_ACTIVE_TEXTURE 0x84E0
#define GL_REPEAT 0x2901
#define GL_CLAMP_TO_EDGE 0x812F
#define GL_MIRRORED_REPEAT 0x8370
#define GL_FLOAT_VEC2 0x8B50
#define GL_FLOAT_VEC3 0x8B51
#define GL_FLOAT_VEC4 0x8B52
#define GL_INT_VEC2 0x8B53
#define GL_INT_VEC3 0x8B54
#define GL_INT_VEC4 0x8B55
#define GL_BOOL 0x8B56
#define GL_BOOL_VEC2 0x8B57
#define GL_BOOL_VEC3 0x8B58
#define GL_BOOL_VEC4 0x8B59
#define GL_FLOAT_MAT2 0x8B5A
#define GL_FLOAT_MAT3 0x8B5B
#define GL_FLOAT_MAT4 0x8B5C
#define GL_SAMPLER_2D 0x8B5E
#define GL_SAMPLER_CUBE 0x8B60
#define GL_VERTEX_ATTRIB_ARRAY_ENABLED 0x8622
#define GL_VERTEX_ATTRIB_ARRAY_SIZE 0x8623
#define GL_VERTEX_ATTRIB_ARRAY_STRIDE 0x8624
#define GL_VERTEX_ATTRIB_ARRAY_TYPE 0x8625
#define GL_VERTEX_ATTRIB_ARRAY_NORMALIZED 0x886A
#define GL_VERTEX_ATTRIB_ARRAY_POINTER 0x8645
#define GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING 0x889F
#define GL_IMPLEMENTATION_COLOR_READ_TYPE 0x8B9A
#define GL_IMPLEMENTATION_COLOR_READ_FORMAT 0x8B9B
#define GL_COMPILE_STATUS 0x8B81
#define GL_INFO_LOG_LENGTH 0x8B84
#define GL_SHADER_SOURCE_LENGTH 0x8B88
#define GL_SHADER_COMPILER 0x8DFA
#define GL_SHADER_BINARY_FORMATS 0x8DF8
#define GL_NUM_SHADER_BINARY_FORMATS 0x8DF9
#define GL_LOW_FLOAT 0x8DF0
#define GL_MEDIUM_FLOAT 0x8DF1
#define GL_HIGH_FLOAT 0x8DF2
#define GL_LOW_INT 0x8DF3
#define GL_MEDIUM_INT 0x8DF4
#define GL_HIGH_INT 0x8DF5
#define GL_FRAMEBUFFER 0x8D40
#define GL_RENDERBUFFER 0x8D41
#define GL_RGBA4 0x8056
#define GL_RGB5_A1 0x8057
#define GL_RGB565 0x8D62
#define GL_DEPTH_COMPONENT16 0x81A5
#define GL_STENCIL_INDEX8 0x8D48
#define GL_RENDERBUFFER_WIDTH 0x8D42
#define GL_RENDERBUFFER_HEIGHT 0x8D43
#define GL_RENDERBUFFER_INTERNAL_FORMAT 0x8D44
#define GL_RENDERBUFFER_RED_SIZE 0x8D50
#define GL_RENDERBUFFER_GREEN_SIZE 0x8D51
#define GL_RENDERBUFFER_BLUE_SIZE 0x8D52
#define GL_RENDERBUFFER_ALPHA_SIZE 0x8D53
#define GL_RENDERBUFFER_DEPTH_SIZE 0x8D54
#define GL_RENDERBUFFER_STENCIL_SIZE 0x8D55
#define GL_FRAMEBUFFER_ATTACHMENT_OBJECT_TYPE 0x8CD0
#define GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME 0x8CD1
#define GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LEVEL 0x8CD2
#define GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_CUBE_MAP_FACE 0x8CD3
#define GL_COLOR_ATTACHMENT0 0x8CE0
#define GL_DEPTH_ATTACHMENT 0x8D00
#define GL_STENCIL_ATTACHMENT 0x8D20
#define GL_NONE 0
#define GL_FRAMEBUFFER_COMPLETE 0x8CD5
#define GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT 0x8CD6
#define GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT 0x8CD7
#define GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS 0x8CD9
#define GL_FRAMEBUFFER_UNSUPPORTED 0x8CDD
#define GL_FRAMEBUFFER_BINDING 0x8CA6
#define GL_RENDERBUFFER_BINDING 0x8CA7
#define GL_MAX_RENDERBUFFER_SIZE 0x84E8
#define GL_INVALID_FRAMEBUFFER_OPERATION 0x0506
#ifndef GL_ES_VERSION_2_0
#define GL_ES_VERSION_2_0 1
GLAPI int GLAD_GL_ES_VERSION_2_0;
typedef void (APIENTRYP PFNGLACTIVETEXTUREPROC)(GLenum texture);
GLAPI PFNGLACTIVETEXTUREPROC glad_glActiveTexture;
#define glActiveTexture glad_glActiveTexture
typedef void (APIENTRYP PFNGLATTACHSHADERPROC)(GLuint program, GLuint shader);
GLAPI PFNGLATTACHSHADERPROC glad_glAttachShader;
#define glAttachShader glad_glAttachShader
typedef void (APIENTRYP PFNGLBINDATTRIBLOCATIONPROC)(GLuint program, GLuint index, const GLchar *name);
GLAPI PFNGLBINDATTRIBLOCATIONPROC glad_glBindAttribLocation;
#define glBindAttribLocation glad_glBindAttribLocation
typedef void (APIENTRYP PFNGLBINDBUFFERPROC)(GLenum target, GLuint buffer);
GLAPI PFNGLBINDBUFFERPROC glad_glBindBuffer;
#define glBindBuffer glad_glBindBuffer
typedef void (APIENTRYP PFNGLBINDFRAMEBUFFERPROC)(GLenum target, GLuint framebuffer);
GLAPI PFNGLBINDFRAMEBUFFERPROC glad_glBindFramebuffer;
#define glBindFramebuffer glad_glBindFramebuffer
typedef void (APIENTRYP PFNGLBINDRENDERBUFFERPROC)(GLenum target, GLuint renderbuffer);
GLAPI PFNGLBINDRENDERBUFFERPROC glad_glBindRenderbuffer;
#define glBindRenderbuffer glad_glBindRenderbuffer
typedef void (APIENTRYP PFNGLBINDTEXTUREPROC)(GLenum target, GLuint texture);
GLAPI PFNGLBINDTEXTUREPROC glad_glBindTexture;
#define glBindTexture glad_glBindTexture
typedef void (APIENTRYP PFNGLBLENDCOLORPROC)(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha);
GLAPI PFNGLBLENDCOLORPROC glad_glBlendColor;
#define glBlendColor glad_glBlendColor
typedef void (APIENTRYP PFNGLBLENDEQUATIONPROC)(GLenum mode);
GLAPI PFNGLBLENDEQUATIONPROC glad_glBlendEquation;
#define glBlendEquation glad_glBlendEquation
typedef void (APIENTRYP PFNGLBLENDEQUATIONSEPARATEPROC)(GLenum modeRGB, GLenum modeAlpha);
GLAPI PFNGLBLENDEQUATIONSEPARATEPROC glad_glBlendEquationSeparate;
#define glBlendEquationSeparate glad_glBlendEquationSeparate
typedef void (APIENTRYP PFNGLBLENDFUNCPROC)(GLenum sfactor, GLenum dfactor);
GLAPI PFNGLBLENDFUNCPROC glad_glBlendFunc;
#define glBlendFunc glad_glBlendFunc
typedef void (APIENTRYP PFNGLBLENDFUNCSEPARATEPROC)(GLenum sfactorRGB, GLenum dfactorRGB, GLenum sfactorAlpha, GLenum dfactorAlpha);
GLAPI PFNGLBLENDFUNCSEPARATEPROC glad_glBlendFuncSeparate;
#define glBlendFuncSeparate glad_glBlendFuncSeparate
typedef void (APIENTRYP PFNGLBUFFERDATAPROC)(GLenum target, GLsizeiptr size, const void *data, GLenum usage);
GLAPI PFNGLBUFFERDATAPROC glad_glBufferData;
#define glBufferData glad_glBufferData
typedef void (APIENTRYP PFNGLBUFFERSUBDATAPROC)(GLenum target, GLintptr offset, GLsizeiptr size, const void *data);
GLAPI PFNGLBUFFERSUBDATAPROC glad_glBufferSubData;
#define glBufferSubData glad_glBufferSubData
typedef GLenum (APIENTRYP PFNGLCHECKFRAMEBUFFERSTATUSPROC)(GLenum target);
GLAPI PFNGLCHECKFRAMEBUFFERSTATUSPROC glad_glCheckFramebufferStatus;
#define glCheckFramebufferStatus glad_glCheckFramebufferStatus
typedef void (APIENTRYP PFNGLCLEARPROC)(GLbitfield mask);
GLAPI PFNGLCLEARPROC glad_glClear;
#define glClear glad_glClear
typedef void (APIENTRYP PFNGLCLEARCOLORPROC)(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha);
GLAPI PFNGLCLEARCOLORPROC glad_glClearColor;
#define glClearColor glad_glClearColor
typedef void (APIENTRYP PFNGLCLEARDEPTHFPROC)(GLfloat d);
GLAPI PFNGLCLEARDEPTHFPROC glad_glClearDepthf;
#define glClearDepthf glad_glClearDepthf
typedef void (APIENTRYP PFNGLCLEARSTENCILPROC)(GLint s);
GLAPI PFNGLCLEARSTENCILPROC glad_glClearStencil;
#define glClearStencil glad_glClearStencil
typedef void (APIENTRYP PFNGLCOLORMASKPROC)(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha);
GLAPI PFNGLCOLORMASKPROC glad_glColorMask;
#define glColorMask glad_glColorMask
typedef void (APIENTRYP PFNGLCOMPILESHADERPROC)(GLuint shader);
GLAPI PFNGLCOMPILESHADERPROC glad_glCompileShader;
#define glCompileShader glad_glCompileShader
typedef void (APIENTRYP PFNGLCOMPRESSEDTEXIMAGE2DPROC)(GLenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLint border, GLsizei imageSize, const void *data);
GLAPI PFNGLCOMPRESSEDTEXIMAGE2DPROC glad_glCompressedTexImage2D;
#define glCompressedTexImage2D glad_glCompressedTexImage2D
typedef void (APIENTRYP PFNGLCOMPRESSEDTEXSUBIMAGE2DPROC)(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const void *data);
GLAPI PFNGLCOMPRESSEDTEXSUBIMAGE2DPROC glad_glCompressedTexSubImage2D;
#define glCompressedTexSubImage2D glad_glCompressedTexSubImage2D
typedef void (APIENTRYP PFNGLCOPYTEXIMAGE2DPROC)(GLenum target, GLint level, GLenum internalformat, GLint x, GLint y, GLsizei width, GLsizei height, GLint border);
GLAPI PFNGLCOPYTEXIMAGE2DPROC glad_glCopyTexImage2D;
#define glCopyTexImage2D glad_glCopyTexImage2D
typedef void (APIENTRYP PFNGLCOPYTEXSUBIMAGE2DPROC)(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height);
GLAPI PFNGLCOPYTEXSUBIMAGE2DPROC glad_glCopyTexSubImage2D;
#define glCopyTexSubImage2D glad_glCopyTexSubImage2D
typedef GLuint (APIENTRYP PFNGLCREATEPROGRAMPROC)(void);
GLAPI PFNGLCREATEPROGRAMPROC glad_glCreateProgram;
#define glCreateProgram glad_glCreateProgram
typedef GLuint (APIENTRYP PFNGLCREATESHADERPROC)(GLenum type);
GLAPI PFNGLCREATESHADERPROC glad_glCreateShader;
#define glCreateShader glad_glCreateShader
typedef void (APIENTRYP PFNGLCULLFACEPROC)(GLenum mode);
GLAPI PFNGLCULLFACEPROC glad_glCullFace;
#define glCullFace glad_glCullFace
typedef void (APIENTRYP PFNGLDELETEBUFFERSPROC)(GLsizei n, const GLuint *buffers);
GLAPI PFNGLDELETEBUFFERSPROC glad_glDeleteBuffers;
#define glDeleteBuffers glad_glDeleteBuffers
typedef void (APIENTRYP PFNGLDELETEFRAMEBUFFERSPROC)(GLsizei n, const GLuint *framebuffers);
GLAPI PFNGLDELETEFRAMEBUFFERSPROC glad_glDeleteFramebuffers;
#define glDeleteFramebuffers glad_glDeleteFramebuffers
typedef void (APIENTRYP PFNGLDELETEPROGRAMPROC)(GLuint program);
GLAPI PFNGLDELETEPROGRAMPROC glad_glDeleteProgram;
#define glDeleteProgram glad_glDeleteProgram
typedef void (APIENTRYP PFNGLDELETERENDERBUFFERSPROC)(GLsizei n, const GLuint *renderbuffers);
GLAPI PFNGLDELETERENDERBUFFERSPROC glad_glDeleteRenderbuffers;
#define glDeleteRenderbuffers glad_glDeleteRenderbuffers
typedef void (APIENTRYP PFNGLDELETESHADERPROC)(GLuint shader);
GLAPI PFNGLDELETESHADERPROC glad_glDeleteShader;
#define glDeleteShader glad_glDeleteShader
typedef void (APIENTRYP PFNGLDELETETEXTURESPROC)(GLsizei n, const GLuint *textures);
GLAPI PFNGLDELETETEXTURESPROC glad_glDeleteTextures;
#define glDeleteTextures glad_glDeleteTextures
typedef void (APIENTRYP PFNGLDEPTHFUNCPROC)(GLenum func);
GLAPI PFNGLDEPTHFUNCPROC glad_glDepthFunc;
#define glDepthFunc glad_glDepthFunc
typedef void (APIENTRYP PFNGLDEPTHMASKPROC)(GLboolean flag);
GLAPI PFNGLDEPTHMASKPROC glad_glDepthMask;
#define glDepthMask glad_glDepthMask
typedef void (APIENTRYP PFNGLDEPTHRANGEFPROC)(GLfloat n, GLfloat f);
GLAPI PFNGLDEPTHRANGEFPROC glad_glDepthRangef;
#define glDepthRangef glad_glDepthRangef
typedef void (APIENTRYP PFNGLDETACHSHADERPROC)(GLuint program, GLuint shader);
GLAPI PFNGLDETACHSHADERPROC glad_glDetachShader;
#define glDetachShader glad_glDetachShader
typedef void (APIENTRYP PFNGLDISABLEPROC)(GLenum cap);
GLAPI PFNGLDISABLEPROC glad_glDisable;
#define glDisable glad_glDisable
typedef void (APIENTRYP PFNGLDISABLEVERTEXATTRIBARRAYPROC)(GLuint index);
GLAPI PFNGLDISABLEVERTEXATTRIBARRAYPROC glad_glDisableVertexAttribArray;
#define glDisableVertexAttribArray glad_glDisableVertexAttribArray
typedef void (APIENTRYP PFNGLDRAWARRAYSPROC)(GLenum mode, GLint first, GLsizei count);
GLAPI PFNGLDRAWARRAYSPROC glad_glDrawArrays;
#define glDrawArrays glad_glDrawArrays
typedef void (APIENTRYP PFNGLDRAWELEMENTSPROC)(GLenum mode, GLsizei count, GLenum type, const void *indices);
GLAPI PFNGLDRAWELEMENTSPROC glad_glDrawElements;
#define glDrawElements glad_glDrawElements
typedef void (APIENTRYP PFNGLENABLEPROC)(GLenum cap);
GLAPI PFNGLENABLEPROC glad_glEnable;
#define glEnable glad_glEnable
typedef void (APIENTRYP PFNGLENABLEVERTEXATTRIBARRAYPROC)(GLuint index);
GLAPI PFNGLENABLEVERTEXATTRIBARRAYPROC glad_glEnableVertexAttribArray;
#define glEnableVertexAttribArray glad_glEnableVertexAttribArray
typedef void (APIENTRYP PFNGLFINISHPROC)(void);
GLAPI PFNGLFINISHPROC glad_glFinish;
#define glFinish glad_glFinish
typedef void (APIENTRYP PFNGLFLUSHPROC)(void);
GLAPI PFNGLFLUSHPROC glad_glFlush;
#define glFlush glad_glFlush
typedef void (APIENTRYP PFNGLFRAMEBUFFERRENDERBUFFERPROC)(GLenum target, GLenum attachment, GLenum renderbuffertarget, GLuint renderbuffer);
GLAPI PFNGLFRAMEBUFFERRENDERBUFFERPROC glad_glFramebufferRenderbuffer;
#define glFramebufferRenderbuffer glad_glFramebufferRenderbuffer
typedef void (APIENTRYP PFNGLFRAMEBUFFERTEXTURE2DPROC)(GLenum target, GLenum attachment, GLenum textarget, GLuint texture, GLint level);
GLAPI PFNGLFRAMEBUFFERTEXTURE2DPROC glad_glFramebufferTexture2D;
#define glFramebufferTexture2D glad_glFramebufferTexture2D
typedef void (APIENTRYP PFNGLFRONTFACEPROC)(GLenum mode);
GLAPI PFNGLFRONTFACEPROC glad_glFrontFace;
#define glFrontFace glad_glFrontFace
typedef void (APIENTRYP PFNGLGENBUFFERSPROC)(GLsizei n, GLuint *buffers);
GLAPI PFNGLGENBUFFERSPROC glad_glGenBuffers;
#define glGenBuffers glad_glGenBuffers
typedef void (APIENTRYP PFNGLGENERATEMIPMAPPROC)(GLenum target);
GLAPI PFNGLGENERATEMIPMAPPROC glad_glGenerateMipmap;
#define glGenerateMipmap glad_glGenerateMipmap
typedef void (APIENTRYP PFNGLGENFRAMEBUFFERSPROC)(GLsizei n, GLuint *framebuffers);
GLAPI PFNGLGENFRAMEBUFFERSPROC glad_glGenFramebuffers;
#define glGenFramebuffers glad_glGenFramebuffers
typedef void (APIENTRYP PFNGLGENRENDERBUFFERSPROC)(GLsizei n, GLuint *renderbuffers);
GLAPI PFNGLGENRENDERBUFFERSPROC glad_glGenRenderbuffers;
#define glGenRenderbuffers glad_glGenRenderbuffers
typedef void (APIENTRYP PFNGLGENTEXTURESPROC)(GLsizei n, GLuint *textures);
GLAPI PFNGLGENTEXTURESPROC glad_glGenTextures;
#define glGenTextures glad_glGenTextures
typedef void (APIENTRYP PFNGLGETACTIVEATTRIBPROC)(GLuint program, GLuint index, GLsizei bufSize, GLsizei *length, GLint *size, GLenum *type, GLchar *name);
GLAPI PFNGLGETACTIVEATTRIBPROC glad_glGetActiveAttrib;
#define glGetActiveAttrib glad_glGetActiveAttrib
typedef void (APIENTRYP PFNGLGETACTIVEUNIFORMPROC)(GLuint program, GLuint index, GLsizei bufSize, GLsizei *length, GLint *size, GLenum *type, GLchar *name);
GLAPI PFNGLGETACTIVEUNIFORMPROC glad_glGetActiveUniform;
#define glGetActiveUniform glad_glGetActiveUniform
typedef void (APIENTRYP PFNGLGETATTACHEDSHADERSPROC)(GLuint program, GLsizei maxCount, GLsizei *count, GLuint *shaders);
GLAPI PFNGLGETATTACHEDSHADERSPROC glad_glGetAttachedShaders;
#define glGetAttachedShaders glad_glGetAttachedShaders
typedef GLint (APIENTRYP PFNGLGETATTRIBLOCATIONPROC)(GLuint program, const GLchar *name);
GLAPI PFNGLGETATTRIBLOCATIONPROC glad_glGetAttribLocation;
#define glGetAttribLocation glad_glGetAttribLocation
typedef void (APIENTRYP PFNGLGETBOOLEANVPROC)(GLenum pname, GLboolean *data);
GLAPI PFNGLGETBOOLEANVPROC glad_glGetBooleanv;
#define glGetBooleanv glad_glGetBooleanv
typedef void (APIENTRYP PFNGLGETBUFFERPARAMETERIVPROC)(GLenum target, GLenum pname, GLint *params);
GLAPI PFNGLGETBUFFERPARAMETERIVPROC glad_glGetBufferParameteriv;
#define glGetBufferParameteriv glad_glGetBufferParameteriv
typedef GLenum (APIENTRYP PFNGLGETERRORPROC)(void);
GLAPI PFNGLGETERRORPROC glad_glGetError;
#define glGetError glad_glGetError
typedef void (APIENTRYP PFNGLGETFLOATVPROC)(GLenum pname, GLfloat *data);
GLAPI PFNGLGETFLOATVPROC glad_glGetFloatv;
#define glGetFloatv glad_glGetFloatv
typedef void (APIENTRYP PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVPROC)(GLenum target, GLenum attachment, GLenum pname, GLint *params);
GLAPI PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVPROC glad_glGetFramebufferAttachmentParameteriv;
#define glGetFramebufferAttachmentParameteriv glad_glGetFramebufferAttachmentParameteriv
typedef void (APIENTRYP PFNGLGETINTEGERVPROC)(GLenum pname, GLint *data);
GLAPI PFNGLGETINTEGERVPROC glad_glGetIntegerv;
#define glGetIntegerv glad_glGetIntegerv
typedef void (APIENTRYP PFNGLGETPROGRAMIVPROC)(GLuint program, GLenum pname, GLint *params);
GLAPI PFNGLGETPROGRAMIVPROC glad_glGetProgramiv;
#define glGetProgramiv glad_glGetProgramiv
typedef void (APIENTRYP PFNGLGETPROGRAMINFOLOGPROC)(GLuint program, GLsizei bufSize, GLsizei *length, GLchar *infoLog);
GLAPI PFNGLGETPROGRAMINFOLOGPROC glad_glGetProgramInfoLog;
#define glGetProgramInfoLog glad_glGetProgramInfoLog
typedef void (APIENTRYP PFNGLGETRENDERBUFFERPARAMETERIVPROC)(GLenum target, GLenum pname, GLint *params);
GLAPI PFNGLGETRENDERBUFFERPARAMETERIVPROC glad_glGetRenderbufferParameteriv;
#define glGetRenderbufferParameteriv glad_glGetRenderbufferParameteriv
typedef void (APIENTRYP PFNGLGETSHADERIVPROC)(GLuint shader, GLenum pname, GLint *params);
GLAPI PFNGLGETSHADERIVPROC glad_glGetShaderiv;
#define glGetShaderiv glad_glGetShaderiv
typedef void (APIENTRYP PFNGLGETSHADERINFOLOGPROC)(GLuint shader, GLsizei bufSize, GLsizei *length, GLchar *infoLog);
GLAPI PFNGLGETSHADERINFOLOGPROC glad_glGetShaderInfoLog;
#define glGetShaderInfoLog glad_glGetShaderInfoLog
typedef void (APIENTRYP PFNGLGETSHADERPRECISIONFORMATPROC)(GLenum shadertype, GLenum precisiontype, GLint *range, GLint *precision);
GLAPI PFNGLGETSHADERPRECISIONFORMATPROC glad_glGetShaderPrecisionFormat;
#define glGetShaderPrecisionFormat glad_glGetShaderPrecisionFormat
typedef void (APIENTRYP PFNGLGETSHADERSOURCEPROC)(GLuint shader, GLsizei bufSize, GLsizei *length, GLchar *source);
GLAPI PFNGLGETSHADERSOURCEPROC glad_glGetShaderSource;
#define glGetShaderSource glad_glGetShaderSource
typedef const GLubyte * (APIENTRYP PFNGLGETSTRINGPROC)(GLenum name);
GLAPI PFNGLGETSTRINGPROC glad_glGetString;
#define glGetString glad_glGetString
typedef void (APIENTRYP PFNGLGETTEXPARAMETERFVPROC)(GLenum target, GLenum pname, GLfloat *params);
GLAPI PFNGLGETTEXPARAMETERFVPROC glad_glGetTexParameterfv;
#define glGetTexParameterfv glad_glGetTexParameterfv
typedef void (APIENTRYP PFNGLGETTEXPARAMETERIVPROC)(GLenum target, GLenum pname, GLint *params);
GLAPI PFNGLGETTEXPARAMETERIVPROC glad_glGetTexParameteriv;
#define glGetTexParameteriv glad_glGetTexParameteriv
typedef void (APIENTRYP PFNGLGETUNIFORMFVPROC)(GLuint program, GLint location, GLfloat *params);
GLAPI PFNGLGETUNIFORMFVPROC glad_glGetUniformfv;
#define glGetUniformfv glad_glGetUniformfv
typedef void (APIENTRYP PFNGLGETUNIFORMIVPROC)(GLuint program, GLint location, GLint *params);
GLAPI PFNGLGETUNIFORMIVPROC glad_glGetUniformiv;
#define glGetUniformiv glad_glGetUniformiv
typedef GLint (APIENTRYP PFNGLGETUNIFORMLOCATIONPROC)(GLuint program, const GLchar *name);
GLAPI PFNGLGETUNIFORMLOCATIONPROC glad_glGetUniformLocation;
#define glGetUniformLocation glad_glGetUniformLocation
typedef void (APIENTRYP PFNGLGETVERTEXATTRIBFVPROC)(GLuint index, GLenum pname, GLfloat *params);
GLAPI PFNGLGETVERTEXATTRIBFVPROC glad_glGetVertexAttribfv;
#define glGetVertexAttribfv glad_glGetVertexAttribfv
typedef void (APIENTRYP PFNGLGETVERTEXATTRIBIVPROC)(GLuint index, GLenum pname, GLint *params);
GLAPI PFNGLGETVERTEXATTRIBIVPROC glad_glGetVertexAttribiv;
#define glGetVertexAttribiv glad_glGetVertexAttribiv
typedef void (APIENTRYP PFNGLGETVERTEXATTRIBPOINTERVPROC)(GLuint index, GLenum pname, void **pointer);
GLAPI PFNGLGETVERTEXATTRIBPOINTERVPROC glad_glGetVertexAttribPointerv;
#define glGetVertexAttribPointerv glad_glGetVertexAttribPointerv
typedef void (APIENTRYP PFNGLHINTPROC)(GLenum target, GLenum mode);
GLAPI PFNGLHINTPROC glad_glHint;
#define glHint glad_glHint
typedef GLboolean (APIENTRYP PFNGLISBUFFERPROC)(GLuint buffer);
GLAPI PFNGLISBUFFERPROC glad_glIsBuffer;
#define glIsBuffer glad_glIsBuffer
typedef GLboolean (APIENTRYP PFNGLISENABLEDPROC)(GLenum cap);
GLAPI PFNGLISENABLEDPROC glad_glIsEnabled;
#define glIsEnabled glad_glIsEnabled
typedef GLboolean (APIENTRYP PFNGLISFRAMEBUFFERPROC)(GLuint framebuffer);
GLAPI PFNGLISFRAMEBUFFERPROC glad_glIsFramebuffer;
#define glIsFramebuffer glad_glIsFramebuffer
typedef GLboolean (APIENTRYP PFNGLISPROGRAMPROC)(GLuint program);
GLAPI PFNGLISPROGRAMPROC glad_glIsProgram;
#define glIsProgram glad_glIsProgram
typedef GLboolean (APIENTRYP PFNGLISRENDERBUFFERPROC)(GLuint renderbuffer);
GLAPI PFNGLISRENDERBUFFERPROC glad_glIsRenderbuffer;
#define glIsRenderbuffer glad_glIsRenderbuffer
typedef GLboolean (APIENTRYP PFNGLISSHADERPROC)(GLuint shader);
GLAPI PFNGLISSHADERPROC glad_glIsShader;
#define glIsShader glad_glIsShader
typedef GLboolean (APIENTRYP PFNGLISTEXTUREPROC)(GLuint texture);
GLAPI PFNGLISTEXTUREPROC glad_glIsTexture;
#define glIsTexture glad_glIsTexture
typedef void (APIENTRYP PFNGLLINEWIDTHPROC)(GLfloat width);
GLAPI PFNGLLINEWIDTHPROC glad_glLineWidth;
#define glLineWidth glad_glLineWidth
typedef void (APIENTRYP PFNGLLINKPROGRAMPROC)(GLuint program);
GLAPI PFNGLLINKPROGRAMPROC glad_glLinkProgram;
#define glLinkProgram glad_glLinkProgram
typedef void (APIENTRYP PFNGLPIXELSTOREIPROC)(GLenum pname, GLint param);
GLAPI PFNGLPIXELSTOREIPROC glad_glPixelStorei;
#define glPixelStorei glad_glPixelStorei
typedef void (APIENTRYP PFNGLPOLYGONOFFSETPROC)(GLfloat factor, GLfloat units);
GLAPI PFNGLPOLYGONOFFSETPROC glad_glPolygonOffset;
#define glPolygonOffset glad_glPolygonOffset
typedef void (APIENTRYP PFNGLREADPIXELSPROC)(GLint x, GLint y, GLsizei width, GLsizei height, GLenum format, GLenum type, void *pixels);
GLAPI PFNGLREADPIXELSPROC glad_glReadPixels;
#define glReadPixels glad_glReadPixels
typedef void (APIENTRYP PFNGLRELEASESHADERCOMPILERPROC)(void);
GLAPI PFNGLRELEASESHADERCOMPILERPROC glad_glReleaseShaderCompiler;
#define glReleaseShaderCompiler glad_glReleaseShaderCompiler
typedef void (APIENTRYP PFNGLRENDERBUFFERSTORAGEPROC)(GLenum target, GLenum internalformat, GLsizei width, GLsizei height);
GLAPI PFNGLRENDERBUFFERSTORAGEPROC glad_glRenderbufferStorage;
#define glRenderbufferStorage glad_glRenderbufferStorage
typedef void (APIENTRYP PFNGLSAMPLECOVERAGEPROC)(GLfloat value, GLboolean invert);
GLAPI PFNGLSAMPLECOVERAGEPROC glad_glSampleCoverage;
#define glSampleCoverage glad_glSampleCoverage
typedef void (APIENTRYP PFNGLSCISSORPROC)(GLint x, GLint y, GLsizei width, GLsizei height);
GLAPI PFNGLSCISSORPROC glad_glScissor;
#define glScissor glad_glScissor
typedef void (APIENTRYP PFNGLSHADERBINARYPROC)(GLsizei count, const GLuint *shaders, GLenum binaryFormat, const void *binary, GLsizei length);
GLAPI PFNGLSHADERBINARYPROC glad_glShaderBinary;
#define glShaderBinary glad_glShaderBinary
typedef void (APIENTRYP PFNGLSHADERSOURCEPROC)(GLuint shader, GLsizei count, const GLchar *const*string, const GLint *length);
GLAPI PFNGLSHADERSOURCEPROC glad_glShaderSource;
#define glShaderSource glad_glShaderSource
typedef void (APIENTRYP PFNGLSTENCILFUNCPROC)(GLenum func, GLint ref, GLuint mask);
GLAPI PFNGLSTENCILFUNCPROC glad_glStencilFunc;
#define glStencilFunc glad_glStencilFunc
typedef void (APIENTRYP PFNGLSTENCILFUNCSEPARATEPROC)(GLenum face, GLenum func, GLint ref, GLuint mask);
GLAPI PFNGLSTENCILFUNCSEPARATEPROC glad_glStencilFuncSeparate;
#define glStencilFuncSeparate glad_glStencilFuncSeparate
typedef void (APIENTRYP PFNGLSTENCILMASKPROC)(GLuint mask);
GLAPI PFNGLSTENCILMASKPROC glad_glStencilMask;
#define glStencilMask glad_glStencilMask
typedef void (APIENTRYP PFNGLSTENCILMASKSEPARATEPROC)(GLenum face, GLuint mask);
GLAPI PFNGLSTENCILMASKSEPARATEPROC glad_glStencilMaskSeparate;
#define glStencilMaskSeparate glad_glStencilMaskSeparate
typedef void (APIENTRYP PFNGLSTENCILOPPROC)(GLenum fail, GLenum zfail, GLenum zpass);
GLAPI PFNGLSTENCILOPPROC glad_glStencilOp;
#define glStencilOp glad_glStencilOp
typedef void (APIENTRYP PFNGLSTENCILOPSEPARATEPROC)(GLenum face, GLenum sfail, GLenum dpfail, GLenum dppass);
GLAPI PFNGLSTENCILOPSEPARATEPROC glad_glStencilOpSeparate;
#define glStencilOpSeparate glad_glStencilOpSeparate
typedef void (APIENTRYP PFNGLTEXIMAGE2DPROC)(GLenum target, GLint level, GLint internalformat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, const void *pixels);
GLAPI PFNGLTEXIMAGE2DPROC glad_glTexImage2D;
#define glTexImage2D glad_glTexImage2D
typedef void (APIENTRYP PFNGLTEXPARAMETERFPROC)(GLenum target, GLenum pname, GLfloat param);
GLAPI PFNGLTEXPARAMETERFPROC glad_glTexParameterf;
#define glTexParameterf glad_glTexParameterf
typedef void (APIENTRYP PFNGLTEXPARAMETERFVPROC)(GLenum target, GLenum pname, const GLfloat *params);
GLAPI PFNGLTEXPARAMETERFVPROC glad_glTexParameterfv;
#define glTexParameterfv glad_glTexParameterfv
typedef void (APIENTRYP PFNGLTEXPARAMETERIPROC)(GLenum target, GLenum pname, GLint param);
GLAPI PFNGLTEXPARAMETERIPROC glad_glTexParameteri;
#define glTexParameteri glad_glTexParameteri
typedef void (APIENTRYP PFNGLTEXPARAMETERIVPROC)(GLenum target, GLenum pname, const GLint *params);
GLAPI PFNGLTEXPARAMETERIVPROC glad_glTexParameteriv;
#define glTexParameteriv glad_glTexParameteriv
typedef void (APIENTRYP PFNGLTEXSUBIMAGE2DPROC)(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, const void *pixels);
GLAPI PFNGLTEXSUBIMAGE2DPROC glad_glTexSubImage2D;
#define glTexSubImage2D glad_glTexSubImage2D
typedef void (APIENTRYP PFNGLUNIFORM1FPROC)(GLint location, GLfloat v0);
GLAPI PFNGLUNIFORM1FPROC glad_glUniform1f;
#define glUniform1f glad_glUniform1f
typedef void (APIENTRYP PFNGLUNIFORM1FVPROC)(GLint location, GLsizei count, const GLfloat *value);
GLAPI PFNGLUNIFORM1FVPROC glad_glUniform1fv;
#define glUniform1fv glad_glUniform1fv
typedef void (APIENTRYP PFNGLUNIFORM1IPROC)(GLint location, GLint v0);
GLAPI PFNGLUNIFORM1IPROC glad_glUniform1i;
#define glUniform1i glad_glUniform1i
typedef void (APIENTRYP PFNGLUNIFORM1IVPROC)(GLint location, GLsizei count, const GLint *value);
GLAPI PFNGLUNIFORM1IVPROC glad_glUniform1iv;
#define glUniform1iv glad_glUniform1iv
typedef void (APIENTRYP PFNGLUNIFORM2FPROC)(GLint location, GLfloat v0, GLfloat v1);
GLAPI PFNGLUNIFORM2FPROC glad_glUniform2f;
#define glUniform2f glad_glUniform2f
typedef void (APIENTRYP PFNGLUNIFORM2FVPROC)(GLint location, GLsizei count, const GLfloat *value);
GLAPI PFNGLUNIFORM2FVPROC glad_glUniform2fv;
#define glUniform2fv glad_glUniform2fv
typedef void (APIENTRYP PFNGLUNIFORM2IPROC)(GLint location, GLint v0, GLint v1);
GLAPI PFNGLUNIFORM2IPROC glad_glUniform2i;
#define glUniform2i glad_glUniform2i
typedef void (APIENTRYP PFNGLUNIFORM2IVPROC)(GLint location, GLsizei count, const GLint *value);
GLAPI PFNGLUNIFORM2IVPROC glad_glUniform2iv;
#define glUniform2iv glad_glUniform2iv
typedef void (APIENTRYP PFNGLUNIFORM3FPROC)(GLint location, GLfloat v0, GLfloat v1, GLfloat v2);
GLAPI PFNGLUNIFORM3FPROC glad_glUniform3f;
#define glUniform3f glad_glUniform3f
typedef void (APIENTRYP PFNGLUNIFORM3FVPROC)(GLint location, GLsizei count, const GLfloat *value);
GLAPI PFNGLUNIFORM3FVPROC glad_glUniform3fv;
#define glUniform3fv glad_glUniform3fv
typedef void (APIENTRYP PFNGLUNIFORM3IPROC)(GLint location, GLint v0, GLint v1, GLint v2);
GLAPI PFNGLUNIFORM3IPROC glad_glUniform3i;
#define glUniform3i glad_glUniform3i
typedef void (APIENTRYP PFNGLUNIFORM3IVPROC)(GLint location, GLsizei count, const GLint *value);
GLAPI PFNGLUNIFORM3IVPROC glad_glUniform3iv;
#define glUniform3iv glad_glUniform3iv
typedef void (APIENTRYP PFNGLUNIFORM4FPROC)(GLint location, GLfloat v0, GLfloat v1, GLfloat v2, GLfloat v3);
GLAPI PFNGLUNIFORM4FPROC glad_glUniform4f;
#define glUniform4f glad_glUniform4f
typedef void (APIENTRYP PFNGLUNIFORM4FVPROC)(GLint location, GLsizei count, const GLfloat *value);
GLAPI PFNGLUNIFORM4FVPROC glad_glUniform4fv;
#define glUniform4fv glad_glUniform4fv
typedef void (APIENTRYP PFNGLUNIFORM4IPROC)(GLint location, GLint v0, GLint v1, GLint v2, GLint v3);
GLAPI PFNGLUNIFORM4IPROC glad_glUniform4i;
#define glUniform4i glad_glUniform4i
typedef void (APIENTRYP PFNGLUNIFORM4IVPROC)(GLint location, GLsizei count, const GLint *value);
GLAPI PFNGLUNIFORM4IVPROC glad_glUniform4iv;
#define glUniform4iv glad_glUniform4iv
typedef void (APIENTRYP PFNGLUNIFORMMATRIX2FVPROC)(GLint location, GLsizei count, GLboolean transpose, const GLfloat *value);
GLAPI PFNGLUNIFORMMATRIX2FVPROC glad_glUniformMatrix2fv;
#define glUniformMatrix2fv glad_glUniformMatrix2fv
typedef void (APIENTRYP PFNGLUNIFORMMATRIX3FVPROC)(GLint location, GLsizei count, GLboolean transpose, const GLfloat *value);
GLAPI PFNGLUNIFORMMATRIX3FVPROC glad_glUniformMatrix3fv;
#define glUniformMatrix3fv glad_glUniformMatrix3fv
typedef void (APIENTRYP PFNGLUNIFORMMATRIX4FVPROC)(GLint location, GLsizei count, GLboolean transpose, const GLfloat *value);
GLAPI PFNGLUNIFORMMATRIX4FVPROC glad_glUniformMatrix4fv;
#define glUniformMatrix4fv glad_glUniformMatrix4fv
typedef void (APIENTRYP PFNGLUSEPROGRAMPROC)(GLuint program);
GLAPI PFNGLUSEPROGRAMPROC glad_glUseProgram;
#define glUseProgram glad_glUseProgram
typedef void (APIENTRYP PFNGLVALIDATEPROGRAMPROC)(GLuint program);
GLAPI PFNGLVALIDATEPROGRAMPROC glad_glValidateProgram;
#define glValidateProgram glad_glValidateProgram
typedef void (APIENTRYP PFNGLVERTEXATTRIB1FPROC)(GLuint index, GLfloat x);
GLAPI PFNGLVERTEXATTRIB1FPROC glad_glVertexAttrib1f;
#define glVertexAttrib1f glad_glVertexAttrib1f
typedef void (APIENTRYP PFNGLVERTEXATTRIB1FVPROC)(GLuint index, const GLfloat *v);
GLAPI PFNGLVERTEXATTRIB1FVPROC glad_glVertexAttrib1fv;
#define glVertexAttrib1fv glad_glVertexAttrib1fv
typedef void (APIENTRYP PFNGLVERTEXATTRIB2FPROC)(GLuint index, GLfloat x, GLfloat y);
GLAPI PFNGLVERTEXATTRIB2FPROC glad_glVertexAttrib2f;
#define glVertexAttrib2f glad_glVertexAttrib2f
typedef void (APIENTRYP PFNGLVERTEXATTRIB2FVPROC)(GLuint index, const GLfloat *v);
GLAPI PFNGLVERTEXATTRIB2FVPROC glad_glVertexAttrib2fv;
#define glVertexAttrib2fv glad_glVertexAttrib2fv
typedef void (APIENTRYP PFNGLVERTEXATTRIB3FPROC)(GLuint index, GLfloat x, GLfloat y, GLfloat z);
GLAPI PFNGLVERTEXATTRIB3FPROC glad_glVertexAttrib3f;
#define glVertexAttrib3f glad_glVertexAttrib3f
typedef void (APIENTRYP PFNGLVERTEXATTRIB3FVPROC)(GLuint index, const GLfloat *v);
GLAPI PFNGLVERTEXATTRIB3FVPROC glad_glVertexAttrib3fv;
#define glVertexAttrib3fv glad_glVertexAttrib3fv
typedef void (APIENTRYP PFNGLVERTEXATTRIB4FPROC)(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w);
GLAPI PFNGLVERTEXATTRIB4FPROC glad_glVertexAttrib4f;
#define glVertexAttrib4f glad_glVertexAttrib4f
typedef void (APIENTRYP PFNGLVERTEXATTRIB4FVPROC)(GLuint index, const GLfloat *v);
GLAPI PFNGLVERTEXATTRIB4FVPROC glad_glVertexAttrib4fv;
#define glVertexAttrib4fv glad_glVertexAttrib4fv
typedef void (APIENTRYP PFNGLVERTEXATTRIBPOINTERPROC)(GLuint index, GLint size, GLenum type, GLboolean normalized, GLsizei stride, const void *pointer);
GLAPI PFNGLVERTEXATTRIBPOINTERPROC glad_glVertexAttribPointer;
#define glVertexAttribPointer glad_glVertexAttribPointer
typedef void (APIENTRYP PFNGLVIEWPORTPROC)(GLint x, GLint y, GLsizei width, GLsizei height);
GLAPI PFNGLVIEWPORTPROC glad_glViewport;
#define glViewport glad_glViewport
#endif
#ifdef __cplusplus
}
#endif
#endif
+311
View File
@@ -0,0 +1,311 @@
#ifndef __khrplatform_h_
#define __khrplatform_h_
/*
** Copyright (c) 2008-2018 The Khronos Group Inc.
**
** Permission is hereby granted, free of charge, to any person obtaining a
** copy of this software and/or associated documentation files (the
** "Materials"), to deal in the Materials without restriction, including
** without limitation the rights to use, copy, modify, merge, publish,
** distribute, sublicense, and/or sell copies of the Materials, and to
** permit persons to whom the Materials are furnished to do so, subject to
** the following conditions:
**
** The above copyright notice and this permission notice shall be included
** in all copies or substantial portions of the Materials.
**
** THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
** EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
** MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
** IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
** CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
** TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
** MATERIALS OR THE USE OR OTHER DEALINGS IN THE MATERIALS.
*/
/* Khronos platform-specific types and definitions.
*
* The master copy of khrplatform.h is maintained in the Khronos EGL
* Registry repository at https://github.com/KhronosGroup/EGL-Registry
* The last semantic modification to khrplatform.h was at commit ID:
* 67a3e0864c2d75ea5287b9f3d2eb74a745936692
*
* Adopters may modify this file to suit their platform. Adopters are
* encouraged to submit platform specific modifications to the Khronos
* group so that they can be included in future versions of this file.
* Please submit changes by filing pull requests or issues on
* the EGL Registry repository linked above.
*
*
* See the Implementer's Guidelines for information about where this file
* should be located on your system and for more details of its use:
* http://www.khronos.org/registry/implementers_guide.pdf
*
* This file should be included as
* #include <KHR/khrplatform.h>
* by Khronos client API header files that use its types and defines.
*
* The types in khrplatform.h should only be used to define API-specific types.
*
* Types defined in khrplatform.h:
* khronos_int8_t signed 8 bit
* khronos_uint8_t unsigned 8 bit
* khronos_int16_t signed 16 bit
* khronos_uint16_t unsigned 16 bit
* khronos_int32_t signed 32 bit
* khronos_uint32_t unsigned 32 bit
* khronos_int64_t signed 64 bit
* khronos_uint64_t unsigned 64 bit
* khronos_intptr_t signed same number of bits as a pointer
* khronos_uintptr_t unsigned same number of bits as a pointer
* khronos_ssize_t signed size
* khronos_usize_t unsigned size
* khronos_float_t signed 32 bit floating point
* khronos_time_ns_t unsigned 64 bit time in nanoseconds
* khronos_utime_nanoseconds_t unsigned time interval or absolute time in
* nanoseconds
* khronos_stime_nanoseconds_t signed time interval in nanoseconds
* khronos_boolean_enum_t enumerated boolean type. This should
* only be used as a base type when a client API's boolean type is
* an enum. Client APIs which use an integer or other type for
* booleans cannot use this as the base type for their boolean.
*
* Tokens defined in khrplatform.h:
*
* KHRONOS_FALSE, KHRONOS_TRUE Enumerated boolean false/true values.
*
* KHRONOS_SUPPORT_INT64 is 1 if 64 bit integers are supported; otherwise 0.
* KHRONOS_SUPPORT_FLOAT is 1 if floats are supported; otherwise 0.
*
* Calling convention macros defined in this file:
* KHRONOS_APICALL
* KHRONOS_APIENTRY
* KHRONOS_APIATTRIBUTES
*
* These may be used in function prototypes as:
*
* KHRONOS_APICALL void KHRONOS_APIENTRY funcname(
* int arg1,
* int arg2) KHRONOS_APIATTRIBUTES;
*/
#if defined(__SCITECH_SNAP__) && !defined(KHRONOS_STATIC)
# define KHRONOS_STATIC 1
#endif
/*-------------------------------------------------------------------------
* Definition of KHRONOS_APICALL
*-------------------------------------------------------------------------
* This precedes the return type of the function in the function prototype.
*/
#if defined(KHRONOS_STATIC)
/* If the preprocessor constant KHRONOS_STATIC is defined, make the
* header compatible with static linking. */
# define KHRONOS_APICALL
#elif defined(_WIN32)
# define KHRONOS_APICALL __declspec(dllimport)
#elif defined (__SYMBIAN32__)
# define KHRONOS_APICALL IMPORT_C
#elif defined(__ANDROID__)
# define KHRONOS_APICALL __attribute__((visibility("default")))
#else
# define KHRONOS_APICALL
#endif
/*-------------------------------------------------------------------------
* Definition of KHRONOS_APIENTRY
*-------------------------------------------------------------------------
* This follows the return type of the function and precedes the function
* name in the function prototype.
*/
#if defined(_WIN32) && !defined(_WIN32_WCE) && !defined(__SCITECH_SNAP__)
/* Win32 but not WinCE */
# define KHRONOS_APIENTRY __stdcall
#else
# define KHRONOS_APIENTRY
#endif
/*-------------------------------------------------------------------------
* Definition of KHRONOS_APIATTRIBUTES
*-------------------------------------------------------------------------
* This follows the closing parenthesis of the function prototype arguments.
*/
#if defined (__ARMCC_2__)
#define KHRONOS_APIATTRIBUTES __softfp
#else
#define KHRONOS_APIATTRIBUTES
#endif
/*-------------------------------------------------------------------------
* basic type definitions
*-----------------------------------------------------------------------*/
#if (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) || defined(__GNUC__) || defined(__SCO__) || defined(__USLC__)
/*
* Using <stdint.h>
*/
#include <stdint.h>
typedef int32_t khronos_int32_t;
typedef uint32_t khronos_uint32_t;
typedef int64_t khronos_int64_t;
typedef uint64_t khronos_uint64_t;
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
/*
* To support platform where unsigned long cannot be used interchangeably with
* inptr_t (e.g. CHERI-extended ISAs), we can use the stdint.h intptr_t.
* Ideally, we could just use (u)intptr_t everywhere, but this could result in
* ABI breakage if khronos_uintptr_t is changed from unsigned long to
* unsigned long long or similar (this results in different C++ name mangling).
* To avoid changes for existing platforms, we restrict usage of intptr_t to
* platforms where the size of a pointer is larger than the size of long.
*/
#if defined(__SIZEOF_LONG__) && defined(__SIZEOF_POINTER__)
#if __SIZEOF_POINTER__ > __SIZEOF_LONG__
#define KHRONOS_USE_INTPTR_T
#endif
#endif
#elif defined(__VMS ) || defined(__sgi)
/*
* Using <inttypes.h>
*/
#include <inttypes.h>
typedef int32_t khronos_int32_t;
typedef uint32_t khronos_uint32_t;
typedef int64_t khronos_int64_t;
typedef uint64_t khronos_uint64_t;
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
#elif defined(_WIN32) && !defined(__SCITECH_SNAP__)
/*
* Win32
*/
typedef __int32 khronos_int32_t;
typedef unsigned __int32 khronos_uint32_t;
typedef __int64 khronos_int64_t;
typedef unsigned __int64 khronos_uint64_t;
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
#elif defined(__sun__) || defined(__digital__)
/*
* Sun or Digital
*/
typedef int khronos_int32_t;
typedef unsigned int khronos_uint32_t;
#if defined(__arch64__) || defined(_LP64)
typedef long int khronos_int64_t;
typedef unsigned long int khronos_uint64_t;
#else
typedef long long int khronos_int64_t;
typedef unsigned long long int khronos_uint64_t;
#endif /* __arch64__ */
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
#elif 0
/*
* Hypothetical platform with no float or int64 support
*/
typedef int khronos_int32_t;
typedef unsigned int khronos_uint32_t;
#define KHRONOS_SUPPORT_INT64 0
#define KHRONOS_SUPPORT_FLOAT 0
#else
/*
* Generic fallback
*/
#include <stdint.h>
typedef int32_t khronos_int32_t;
typedef uint32_t khronos_uint32_t;
typedef int64_t khronos_int64_t;
typedef uint64_t khronos_uint64_t;
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
#endif
/*
* Types that are (so far) the same on all platforms
*/
typedef signed char khronos_int8_t;
typedef unsigned char khronos_uint8_t;
typedef signed short int khronos_int16_t;
typedef unsigned short int khronos_uint16_t;
/*
* Types that differ between LLP64 and LP64 architectures - in LLP64,
* pointers are 64 bits, but 'long' is still 32 bits. Win64 appears
* to be the only LLP64 architecture in current use.
*/
#ifdef KHRONOS_USE_INTPTR_T
typedef intptr_t khronos_intptr_t;
typedef uintptr_t khronos_uintptr_t;
#elif defined(_WIN64)
typedef signed long long int khronos_intptr_t;
typedef unsigned long long int khronos_uintptr_t;
#else
typedef signed long int khronos_intptr_t;
typedef unsigned long int khronos_uintptr_t;
#endif
#if defined(_WIN64)
typedef signed long long int khronos_ssize_t;
typedef unsigned long long int khronos_usize_t;
#else
typedef signed long int khronos_ssize_t;
typedef unsigned long int khronos_usize_t;
#endif
#if KHRONOS_SUPPORT_FLOAT
/*
* Float type
*/
typedef float khronos_float_t;
#endif
#if KHRONOS_SUPPORT_INT64
/* Time types
*
* These types can be used to represent a time interval in nanoseconds or
* an absolute Unadjusted System Time. Unadjusted System Time is the number
* of nanoseconds since some arbitrary system event (e.g. since the last
* time the system booted). The Unadjusted System Time is an unsigned
* 64 bit value that wraps back to 0 every 584 years. Time intervals
* may be either signed or unsigned.
*/
typedef khronos_uint64_t khronos_utime_nanoseconds_t;
typedef khronos_int64_t khronos_stime_nanoseconds_t;
#endif
/*
* Dummy value used to pad enum types to 32 bits.
*/
#ifndef KHRONOS_MAX_ENUM
#define KHRONOS_MAX_ENUM 0x7FFFFFFF
#endif
/*
* Enumerated boolean type
*
* Values other than zero should be considered to be true. Therefore
* comparisons should not be made against KHRONOS_TRUE.
*/
typedef enum {
KHRONOS_FALSE = 0,
KHRONOS_TRUE = 1,
KHRONOS_BOOLEAN_ENUM_FORCE_SIZE = KHRONOS_MAX_ENUM
} khronos_boolean_enum_t;
#endif /* __khrplatform_h_ */
+39
View File
@@ -0,0 +1,39 @@
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <PR/ultratypes.h>
u8 g_CrashHasMessage = 0;
s32 g_CrashEnabled = 0;
static char crashMsg[1024];
void crashCreateThread(void)
{
// TODO: install a crash handler of some sort
}
void crashSetMessage(char *string)
{
strncpy(crashMsg, string, sizeof(crashMsg) - 1);
fprintf(stderr, "crashSetMessage: %s\n", crashMsg);
g_CrashHasMessage = 1;
}
void crashReset(void)
{
crashMsg[0] = 0;
g_CrashHasMessage = 0;
}
void crashAppendChar(char c)
{
g_CrashHasMessage = 1;
for (u32 i = 0; i < sizeof(crashMsg) - 1; ++i) {
if (crashMsg[i] == '\0') {
crashMsg[i] = c;
crashMsg[i + 1] = '\0';
break;
}
}
}
+89
View File
@@ -0,0 +1,89 @@
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <limits.h>
#include <sys/stat.h>
#include <PR/ultratypes.h>
#include "fs.h"
#ifdef PATH_MAX
#define FS_MAXPATH PATH_MAX
#else
#define FS_MAXPATH 1024
#endif
#define FS_BASEDIR "data"
#define FS_MAX_FILES 2048
static char baseDir[FS_MAXPATH + 1];
static struct {
char *name[FS_MAXPATH + 1];
s32 size;
void *data;
} fileSlots[FS_MAX_FILES];
static const char *fsFullPath(const char *relPath)
{
static char pathBuf[FS_MAXPATH];
snprintf(pathBuf, sizeof(pathBuf), "%s/%s", baseDir, relPath);
return pathBuf;
}
s32 fsInit(void)
{
// TODO: support appdata/home/whatever
strcpy(baseDir, FS_BASEDIR);
return 0;
}
void *fsFileLoad(const char *name, u32 *outSize)
{
const char *fullName = fsFullPath(name);
FILE *f = fopen(fullName, "rb");
if (!f) {
fprintf(stderr, "fsFileLoad: could not find file: %s\n", fullName);
return NULL;
}
fseek(f, 0, SEEK_END);
const s32 size = ftell(f);
fseek(f, 0, SEEK_SET);
if (size < 0) {
fprintf(stderr, "fsFileLoad: empty file or invalid size (%d): %s\n", size, fullName);
fclose(f);
return NULL;
}
void *buf = NULL;
if (size) {
buf = calloc(1, size + 1); // sick hack for a free null terminator
if (!buf) {
fprintf(stderr, "fsFileLoad: could not alloc %d bytes for file: %s\n", size, fullName);
fclose(f);
return NULL;
}
fread(buf, 1, size, f);
}
fclose(f);
if (outSize) {
*outSize = size;
}
return buf;
}
s32 fsFileSize(const char *name)
{
const char *fullName = fsFullPath(name);
struct stat st;
if (stat(fullName, &st) < 0) {
return -1;
} else {
return st.st_size;
}
}
+137
View File
@@ -0,0 +1,137 @@
#include <SDL.h>
#include <PR/ultratypes.h>
#include <PR/os_thread.h>
#include <PR/os_cont.h>
#include "input.h"
static SDL_GameController *pads[INPUT_MAX_CONTROLLERS];
static SDL_Haptic *haptics[INPUT_MAX_CONTROLLERS];
static const u16 buttonMap[] = {
/* SDL_CONTROLLER_BUTTON_A */ A_BUTTON,
/* SDL_CONTROLLER_BUTTON_B */ B_BUTTON,
/* SDL_CONTROLLER_BUTTON_X */ Z_TRIG,
/* SDL_CONTROLLER_BUTTON_Y */ Z_TRIG,
/* SDL_CONTROLLER_BUTTON_BACK */ START_BUTTON,
/* SDL_CONTROLLER_BUTTON_GUIDE */ 0,
/* SDL_CONTROLLER_BUTTON_START */ START_BUTTON,
/* SDL_CONTROLLER_BUTTON_LEFTSTICK */ 0,
/* SDL_CONTROLLER_BUTTON_RIGHTSTICK */ 0,
/* SDL_CONTROLLER_BUTTON_LEFTSHOULDER */ L_TRIG,
/* SDL_CONTROLLER_BUTTON_RIGHTSHOULDER */ R_TRIG,
/* SDL_CONTROLLER_BUTTON_DPAD_UP */ U_JPAD,
/* SDL_CONTROLLER_BUTTON_DPAD_DOWN */ D_JPAD,
/* SDL_CONTROLLER_BUTTON_DPAD_LEFT */ L_JPAD,
/* SDL_CONTROLLER_BUTTON_DPAD_RIGHT */ R_JPAD,
};
static const u16 buttonTrigLeft = Z_TRIG;
static const u16 buttonTrigRight = Z_TRIG;
static s32 connectedMask = 0;
s32 inputInit(void)
{
if (!SDL_WasInit(SDL_INIT_GAMECONTROLLER)) {
if (SDL_InitSubSystem(SDL_INIT_GAMECONTROLLER) != 0) {
return -1;
}
}
const s32 numJoys = SDL_NumJoysticks();
s32 ret = 0;
for (s32 jidx = 0, cidx = 0; jidx < numJoys && cidx < INPUT_MAX_CONTROLLERS; ++jidx) {
if (SDL_IsGameController(jidx)) {
pads[cidx] = SDL_GameControllerOpen(jidx);
if (pads[cidx]) {
SDL_Haptic *hap = SDL_HapticOpen(jidx);
if (hap) {
if (SDL_HapticRumbleSupported(hap) && (SDL_HapticRumbleInit(hap) == 0)) {
haptics[cidx] = hap;
} else {
SDL_HapticClose(hap);
}
}
ret |= 1 << cidx;
++cidx;
}
}
}
connectedMask = ret;
return ret;
}
s32 inputReadController(s32 idx, OSContPad *npad)
{
if (idx < 0 || idx >= INPUT_MAX_CONTROLLERS || !pads[idx] || !npad) {
return -1;
}
const s16 leftX = SDL_GameControllerGetAxis(pads[idx], SDL_CONTROLLER_AXIS_LEFTX);
const s16 leftY = SDL_GameControllerGetAxis(pads[idx], SDL_CONTROLLER_AXIS_LEFTY);
const s16 rightX = SDL_GameControllerGetAxis(pads[idx], SDL_CONTROLLER_AXIS_RIGHTX);
const s16 rightY = SDL_GameControllerGetAxis(pads[idx], SDL_CONTROLLER_AXIS_RIGHTY);
npad->button = 0;
if (rightX < -0x4000) npad->button |= L_CBUTTONS;
if (rightX > +0x4000) npad->button |= R_CBUTTONS;
if (rightY < -0x4000) npad->button |= U_CBUTTONS;
if (rightY > +0x4000) npad->button |= D_CBUTTONS;
for (size_t i = 0; i < sizeof(buttonMap) / sizeof(*buttonMap); ++i) {
if (buttonMap[i]) {
if (SDL_GameControllerGetButton(pads[idx], i)) {
npad->button |= buttonMap[i];
}
}
}
const s32 stickY = -leftY / 0x100;
npad->stick_x = leftX / 0x100;
npad->stick_y = (stickY == 128) ? 127 : stickY;
return 0;
}
void inputUpdate(void)
{
SDL_GameControllerUpdate();
// TODO: handle controller changes
}
s32 inputControllerConnected(s32 idx)
{
if (idx < 0 || idx >= INPUT_MAX_CONTROLLERS) {
return 0;
}
return !!pads[idx];
}
s32 inputRumbleSupported(s32 idx)
{
if (idx < 0 || idx >= INPUT_MAX_CONTROLLERS) {
return 0;
}
return !!haptics[idx];
}
void inputRumble(s32 idx, f32 strength, f32 time)
{
if (idx < 0 || idx >= INPUT_MAX_CONTROLLERS || !haptics[idx]) {
return;
}
if (strength <= 0.f) {
SDL_HapticRumbleStop(haptics[idx]);
} else {
SDL_HapticRumblePlay(haptics[idx], strength, (u32)(time * 1000.f));
}
}
s32 inputControllerMask(void)
{
return connectedMask;
}
+446
View File
@@ -0,0 +1,446 @@
#include <stdlib.h>
#include <stdio.h>
#include <stdarg.h>
#include <string.h>
#include <PR/os_internal.h>
#include <PR/rcp.h>
#include "system.h"
#include "input.h"
#include "video.h"
#define EEPROM_SIZE (EEP16K_MAXBLOCKS * 8)
#define EEPROM_FNAME "eeprom.bin"
#define OS_COUNTER_RATE 46875000ULL
u64 osClockRate = OS_CLOCK_RATE;
u32 osMemSize = 16 * 1024 * 1024; /* expansion pak installed plus some extra */
s32 osTvType = OS_TV_NTSC; /* 0 = PAL, 1 = NTSC, 2 = MPAL */
s32 osResetType = 0; /* 0 = cold reset */
s32 osViClock = VI_NTSC_CLOCK;
/* Time */
OSTime osGetTime(void)
{
// u64 should be enough to last a while
return (sysGetTicks() * OS_COUNTER_RATE) / sysGetTicksPerSecond();
}
u32 osGetCount(void)
{
return (u32)osGetTime();
}
/* Thread */
void osCreateThread(OSThread *thrd, OSId id, void (*entry)(void *), void *arg, void *sp, OSPri p)
{
thrd->id = id;
thrd->state = OS_STATE_STOPPED;
}
void osDestroyThread(OSThread *thrd)
{
thrd->id = 0;
thrd->state = 0;
}
void osYieldThread(void)
{
}
void osStartThread(OSThread *thrd)
{
thrd->state = OS_STATE_RUNNING;
}
void osStopThread(OSThread *thrd)
{
thrd->state = OS_STATE_STOPPED;
}
OSPri osGetThreadPri(OSThread *thrd)
{
return 0;
}
void osSetThreadPri(OSThread *thrd, OSPri pri)
{
}
/* Mesg */
void osCreateMesgQueue(OSMesgQueue *mq, OSMesg *msgBuf, s32 count)
{
mq->validCount = 0;
mq->first = 0;
mq->msgCount = count;
mq->msg = msgBuf;
}
void osSetEventMesg(OSEvent e, OSMesgQueue *mq, OSMesg msg)
{
}
s32 osSendMesg(OSMesgQueue *mq, OSMesg msg, s32 flag)
{
return 0;
}
s32 osRecvMesg(OSMesgQueue *mq, OSMesg *msg, s32 flag)
{
return 0;
}
/* Vi */
void osCreateViManager(OSPri pri)
{
}
void osViSetMode(OSViMode *mode)
{
}
void osViSetEvent(OSMesgQueue *mq, OSMesg msg, u32 retraceCount)
{
}
void osViBlack(u8 active)
{
if (active) {
videoClearScreen();
}
}
void osViSetSpecialFeatures(u32 func)
{
}
void osViSwapBuffer(void *vaddr)
{
}
void osViSetXScale(f32 value)
{
}
void osViSetYScale(f32 value)
{
}
/* Ai */
s32 osAiSetFrequency(u32 frequency)
{
register unsigned int dacRate;
register char bitRate;
register float f;
f = osViClock / (float)frequency + .5f;
dacRate = f;
if (dacRate < AI_MIN_DAC_RATE) {
return -1;
}
bitRate = dacRate / 66;
if (bitRate > AI_MAX_BIT_RATE) {
bitRate = AI_MAX_BIT_RATE;
}
return osViClock / (s32)dacRate;
}
u32 osAiGetLength(void)
{
return 0;
}
s32 osAiSetNextBuffer(void *bufPtr, u32 size)
{
return 0;
}
/* Cont */
s32 osContInit(OSMesgQueue *mesgq, u8 *bitpattern, OSContStatus *data)
{
if (bitpattern) {
*bitpattern = inputControllerMask();
}
if (data) {
osContGetQuery(data);
}
return 0;
}
s32 osContStartReadData(OSMesgQueue *mesgq)
{
osSendMesg(mesgq, (OSMesg)0, OS_MESG_NOBLOCK);
return 0;
}
void osContGetReadData(OSContPad *pad)
{
// game always passes in an array of 4 OSContPads
for (s32 i = 0; i < MAXCONTROLLERS; ++i, ++pad) {
pad->button = 0;
pad->stick_x = 0;
pad->stick_y = 0;
if (inputReadController(i, pad) < 0) {
pad->errno = CONT_NO_RESPONSE_ERROR;
} else {
pad->errno = 0;
}
}
}
s32 osContStartQuery(OSMesgQueue *mq)
{
return 0;
}
void osContGetQuery(OSContStatus *status)
{
// also always 4 status structs here
for (s32 i = 0; i < MAXCONTROLLERS; ++i, ++status) {
if (inputControllerConnected(i)) {
status->errno = 0;
status->type = CONT_ABSOLUTE;
status->status = 1;
} else {
status->errno = CONT_NO_RESPONSE_ERROR;
status->type = 0;
status->status = 0;
}
}
}
/* Motor */
s32 osMotorProbe(OSMesgQueue *ctrlrqueue, OSPfs* pfs, s32 channel)
{
if (pfs && inputRumbleSupported(channel)) {
pfs->queue = ctrlrqueue;
pfs->channel = channel;
pfs->activebank = 0xff;
pfs->status = PFS_MOTOR_INITIALIZED;
return 0;
}
return PFS_ERR_NOPACK;
}
s32 __osMotorAccess(OSPfs *pfs, s32 cmd)
{
if (!pfs || pfs->channel < 0 || pfs->channel >= INPUT_MAX_CONTROLLERS) {
return PFS_ERR_NOPACK;
}
const f32 strength = (cmd == MOTOR_START) ? INPUT_RUMBLE_STRENGTH : 0.f;
inputRumble(pfs->channel, strength, 5.f); // hope someone turns it off in those 5 seconds
return 0;
}
/* Eeprom */
s32 osEepromProbe(OSMesgQueue *mq)
{
return EEPROM_TYPE_16K;
}
s32 osEepromLongRead(OSMesgQueue *mq, u8 address, u8 *buffer, int nbytes)
{
u8 content[EEPROM_SIZE];
s32 ret = -1;
FILE *fp = fopen(EEPROM_FNAME, "rb");
if (fp == NULL) {
return -1;
}
if (fread(content, 1, EEPROM_SIZE, fp) == EEPROM_SIZE) {
memcpy(buffer, content + address * 8, nbytes);
ret = 0;
}
fclose(fp);
return ret;
}
s32 osEepromLongWrite(OSMesgQueue *mq, u8 address, u8 *buffer, int nbytes)
{
u8 content[EEPROM_SIZE] = { 0 };
if (address != 0 || nbytes != EEPROM_SIZE) {
osEepromLongRead(mq, 0, content, EEPROM_SIZE);
}
memcpy(content + address * 8, buffer, nbytes);
FILE* fp = fopen(EEPROM_FNAME, "wb");
if (fp == NULL) {
return -1;
}
s32 ret = fwrite(content, 1, EEPROM_SIZE, fp) == EEPROM_SIZE ? 0 : -1;
fclose(fp);
return ret;
}
/* Pfs */
s32 osPfsIsPlug(OSMesgQueue *queue, u8 *pattern)
{
if (pattern) {
*pattern = 0;
}
return 0;
}
s32 osPfsInitPak(OSMesgQueue *queue, OSPfs *pfs, s32 channel, s32 *arg3)
{
return PFS_ERR_NOPACK;
}
s32 osPfsChecker(OSPfs *pfs)
{
return PFS_ERR_NOPACK;
}
s32 osPfsFreeBlocks(OSPfs *pfs, s32 *remaining)
{
return PFS_ERR_NOPACK;
}
s32 osPfsNumFiles(OSPfs *pfs, s32 *max_files, s32 *files_used)
{
return PFS_ERR_NOPACK;
}
s32 osPfsAllocateFile(OSPfs *pfs, u16 company_code, u32 game_code, u8 *game_name, u8 *ext_name, int num_bytes, s32 *file_no)
{
return PFS_ERR_NOPACK;
}
s32 osPfsFindFile(OSPfs *pfs, u16 company_code, u32 game_code, u8 *game_name, u8 *ext_name, s32 *file_no)
{
return PFS_ERR_NOPACK;
}
s32 osPfsDeleteFile(OSPfs *pfs, u16 company_code, u32 game_code, u8 *game_name, u8 *ext_name)
{
return PFS_ERR_NOPACK;
}
s32 osPfsReSizeFile(OSPfs *pfs, u16 company_code, u32 game_code, u8 *game_name, u8 *ext_name, int length)
{
return PFS_ERR_NOPACK;
}
s32 osPfsFileState(OSPfs *pfs, s32 fileNo, OSPfsState *state)
{
return PFS_ERR_NOPACK;
}
s32 osPfsReadWriteFile(OSPfs* pfs, s32 fileNo, u8 flag, int offset, int size, u8* data)
{
return PFS_ERR_NOPACK;
}
/* Gbpak */
s32 osGbpakInit(OSMesgQueue *, OSPfs *, int)
{
return PFS_ERR_NOPACK;
}
s32 osGbpakPower(OSPfs *, s32)
{
return PFS_ERR_NOPACK;
}
s32 osGbpakReadWrite(OSPfs *, u16, u16, u8 *, u16)
{
return PFS_ERR_NOPACK;
}
s32 osGbpakReadId(OSPfs *, OSGbpakId *, u8 *)
{
return PFS_ERR_NOPACK;
}
/* Misc */
void osWritebackDCacheAll(void)
{
}
void osWritebackDCache(void *a, s32 b)
{
}
void osInvalDCache(void *a, s32 b)
{
}
s32 osPiStartDma(OSIoMesg *mb, s32 priority, s32 direction, uintptr_t devAddr, void *vAddr, size_t nbytes, OSMesgQueue *mq)
{
memcpy(vAddr, (const void *)devAddr, nbytes);
return 0;
}
s32 osPiReadIo(u32 devaddr, u32 *data)
{
return 0;
}
uintptr_t osVirtualToPhysical(void *addr)
{
return (uintptr_t)addr;
}
u32 osGetMemSize(void)
{
return osMemSize;
}
OSIntMask osGetIntMask(void)
{
return 0;
}
OSIntMask osSetIntMask(OSIntMask mask)
{
return 0;
}
/* libc compatibility wrappers */
#ifndef HAVE_BZERO
void bzero(void *ptr, s32 size)
{
memset(ptr, 0, size);
}
#endif
#ifndef HAVE_BCOPY
void bcopy(const void *src, void *dst, s32 n)
{
memcpy(dst, src, n);
}
#endif
#ifndef HAVE_BCMP
s32 bcmp(const void *s1, const void *s2, s32 n)
{
return memcmp(s1, s2, n);
}
#endif
+74
View File
@@ -0,0 +1,74 @@
#include <stdlib.h>
#include <stdio.h>
#include <PR/ultratypes.h>
#include <PR/sched.h>
#include <PR/os_message.h>
#include "lib/main.h"
#include "bss.h"
#include "video.h"
#include "input.h"
#include "fs.h"
#include "romdata.h"
#include "system.h"
u32 g_OsMemSize = 0;
u8 g_Is4Mb = 0;
s8 g_Resetting = false;
OSSched g_Sched;
OSMesgQueue g_MainMesgQueue;
OSMesg g_MainMesgBuf[32];
u8 *g_MempHeap = NULL;
u32 g_MempHeapSize = 0;
u32 g_VmNumTlbMisses = 0;
u32 g_VmNumPageMisses = 0;
u32 g_VmNumPageReplaces = 0;
u8 g_VmShowStats = 0;
s32 bootGetMemSize(void)
{
return (s32)g_OsMemSize;
}
void *bootAllocateStack(s32 threadid, s32 size)
{
static u8 bruh[0x1000];
return bruh;
}
void bootCreateSched(void)
{
osCreateMesgQueue(&g_MainMesgQueue, g_MainMesgBuf, ARRAYCOUNT(g_MainMesgBuf));
if (osTvType == OS_TV_MPAL) {
osCreateScheduler(&g_Sched, NULL, OS_VI_MPAL_LAN1, 1);
} else {
osCreateScheduler(&g_Sched, NULL, OS_VI_NTSC_LAN1, 1);
}
}
int main(int argc, const char **argv)
{
fsInit();
videoInit();
inputInit();
romdataInit();
bootCreateSched();
g_OsMemSize = osGetMemSize();
g_SndDisabled = true; // for now
g_MempHeapSize = g_OsMemSize;
g_MempHeap = calloc(1, g_MempHeapSize);
if (!g_MempHeap) {
sysFatalError("Could not alloc %u bytes for memp heap.", g_MempHeapSize);
}
mainProc();
return 0;
}
+644
View File
@@ -0,0 +1,644 @@
#include <stdlib.h>
#include <assert.h>
#include <ultra64.h>
#include <PR/sched.h>
#include "lib/sched.h"
#include "lib/vars.h"
#include "constants.h"
#include "game/camdraw.h"
#include "game/cheats.h"
#include "game/debug.h"
#include "game/file.h"
#include "game/lang.h"
#include "game/race.h"
#include "game/body.h"
#include "game/stubs/game_000840.h"
#include "game/stubs/game_000850.h"
#include "game/stubs/game_000860.h"
#include "game/stubs/game_000870.h"
#include "game/smoke.h"
#include "game/stubs/game_0008e0.h"
#include "game/stubs/game_0008f0.h"
#include "game/stubs/game_000900.h"
#include "game/stubs/game_000910.h"
#include "game/tex.h"
#include "game/stubs/game_00b180.h"
#include "game/stubs/game_00b200.h"
#include "game/challenge.h"
#include "game/title.h"
#include "game/pdmode.h"
#include "game/objectives.h"
#include "game/endscreen.h"
#include "game/playermgr.h"
#include "game/game_1531a0.h"
#include "game/gfxmemory.h"
#include "game/lang.h"
#include "game/lv.h"
#include "game/timing.h"
#include "game/music.h"
#include "game/stubs/game_175f50.h"
#include "game/game_175f90.h"
#include "game/zbuf.h"
#include "game/game_1a78b0.h"
#include "game/mplayer/mplayer.h"
#include "game/pak.h"
#include "game/splat.h"
#include "game/utils.h"
#include "bss.h"
#include "lib/audiomgr.h"
#include "lib/args.h"
#include "lib/boot.h"
#include "lib/vm.h"
#include "lib/rzip.h"
#include "lib/vi.h"
#include "lib/fault.h"
#include "lib/crash.h"
#include "lib/dma.h"
#include "lib/joy.h"
#include "lib/main.h"
#include "lib/snd.h"
#include "lib/memp.h"
#include "lib/mema.h"
#include "lib/profile.h"
#include "lib/videbug.h"
#include "lib/debughud.h"
#include "lib/anim.h"
#include "lib/rdp.h"
#include "lib/lib_34d0.h"
#include "lib/lib_2f490.h"
#include "lib/rmon.h"
#include "lib/rng.h"
#include "lib/str.h"
#include "data.h"
#include "types.h"
#include "video.h"
#include "input.h"
extern u8 *g_MempHeap;
extern u32 g_MempHeapSize;
void rngSetSeed(u32 seed);
void schedFrame(OSSched *sc);
bool var8005d9b0 = false;
s32 g_StageNum = STAGE_TITLE;
u32 g_MainMemaHeapSize = 1024 * 300;
bool var8005d9bc = false;
s32 var8005d9c0 = 0;
s32 var8005d9c4 = 0;
bool g_MainGameLogicEnabled = true;
u32 g_MainNumGfxTasks = 0;
bool g_MainIsEndscreen = false;
s32 g_DoBootPakMenu = 0;
u32 var8005dd3c = 0x00000000;
u32 var8005dd40 = 0x00000000;
u32 var8005dd44 = 0x00000000;
u32 var8005dd48 = 0x00000000;
u32 var8005dd4c = 0x00000000;
u32 var8005dd50 = 0x00000000;
s32 g_MainChangeToStageNum = -1;
bool g_MainIsDebugMenuOpen = false;
struct stageallocation g_StageAllocations8Mb[] = {
{ STAGE_CITRAINING, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_DEFECTION, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_INVESTIGATION, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_EXTRACTION, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_CHICAGO, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_G5BUILDING, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_VILLA, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma600" },
{ STAGE_INFILTRATION, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma500" },
{ STAGE_RESCUE, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma500" },
{ STAGE_ESCAPE, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma500" },
{ STAGE_AIRBASE, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_AIRFORCEONE, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_CRASHSITE, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_PELAGIC, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_DEEPSEA, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_DEFENSE, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_ATTACKSHIP, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_SKEDARRUINS, "-ml0 -me0 -mgfx110 -mgfxtra80 -mvtx100 -ma700" },
{ STAGE_MP_SKEDAR, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_RAVINE, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_PIPES, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_G5BUILDING, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_SEWERS, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_WAREHOUSE, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_BASE, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_COMPLEX, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_TEMPLE, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_FELICITY, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_AREA52, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_GRID, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_CARPARK, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_RUINS, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_FORTRESS, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_MP_VILLA, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_RUN, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP2, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP6, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP7, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP8, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP14, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP16, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP17, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP18, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP19, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_MP20, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_ASH, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_28, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_MBR, "-ml0 -me0 -mgfx120 -mvtx100 -ma700" },
{ STAGE_TEST_SILO, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_24, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_MAIANSOS, "-ml0 -me0 -mgfx120 -mvtx100 -ma500" },
{ STAGE_RETAKING, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_TEST_DEST, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_2B, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_WAR, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_TEST_UFF, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_TEST_OLD, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_DUEL, "-ml0 -me0 -mgfx120 -mvtx100 -ma700" },
{ STAGE_TEST_LAM, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
{ STAGE_TEST_ARCH, "-ml0 -me0 -mgfx200 -mvtx200 -ma400" },
{ STAGE_TEST_LEN, "-ml0 -me0 -mgfx120 -mvtx98 -ma300" },
{ STAGE_TITLE, "-ml0 -me0 -mgfx80 -mvtx20 -ma001" },
{ 0, "-ml0 -me0 -mgfx120 -mvtx98 -ma300" },
};
struct stageallocation g_StageAllocations4Mb[] = {
{ STAGE_MP_SKEDAR, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_PIPES, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_AREA52, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_RAVINE, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_G5BUILDING, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_SEWERS, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_WAREHOUSE, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_BASE, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_COMPLEX, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_TEMPLE, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_FELICITY, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_GRID, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_TEST_RUN, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_CARPARK, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_RUINS, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_MP_FORTRESS, "-ml0 -me0 -mgfx96 -mvtx96 -ma130" },
{ STAGE_MP_VILLA, "-ml0 -me0 -mgfx96 -mvtx96 -ma140" },
{ STAGE_TEST_MP2, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_MP6, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_MP7, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_MP8, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_MP14, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_MP16, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_MP17, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_MP18, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_MP19, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_MP20, "-ml0 -me0 -mgfx96 -mvtx96 -ma115" },
{ STAGE_TEST_LEN, "-ml0 -me0 -mgfx100 -mvtx96 -ma120" },
{ STAGE_4MBMENU, "-mgfx100 -mvtx50 -ma50" },
{ STAGE_TITLE, "-ml0 -me0 -mgfx80 -mvtx20 -ma001" },
{ 0, "-ml0 -me0 -mgfx100 -mvtx96 -ma300" },
};
Gfx var8005dcc8[] = {
gsSPSegment(0x00, 0x00000000),
gsSPDisplayList(&var800613a0),
gsSPDisplayList(&var80061380),
gsDPFullSync(),
gsSPEndDisplayList(),
};
Gfx var8005dcf0[] = {
gsSPSegment(0x00, 0x00000000),
gsSPDisplayList(&var800613a0),
gsSPDisplayList(&var80061380),
gsDPFullSync(),
gsSPEndDisplayList(),
};
s32 g_MainIsBooting = 1;
void mainInit(void)
{
s32 x;
s32 i;
s32 j;
u32 addr;
faultInit();
dmaInit();
amgrInit();
varsInit();
mempInit();
memaInit();
joyInit();
joyReset();
g_Is4Mb = (osGetMemSize() <= 0x400000);
g_VmShowStats = 0;
// no copyright screen
viConfigureForLegal();
viBlack(true);
filesInit();
if (var8005d9b0) {
argSetString(" -ml0 -me0 -mgfx100 -mvtx50 -mt700 -ma400");
}
mempSetHeap(g_MempHeap, g_MempHeapSize);
mempResetPool(MEMPOOL_8);
mempResetPool(MEMPOOL_PERMANENT);
crashReset();
challengesInit();
utilsInit();
texInit();
langInit();
lvInit();
cheatsInit();
textInit();
dhudInit();
playermgrInit();
frametimeInit();
profileInit();
smokesInit();
mpInit();
pheadInit();
paksInit();
pheadInit2();
animsInit();
racesInit();
bodiesInit();
titleInit();
g_MainIsBooting = 0;
}
void mainProc(void)
{
mainInit();
rdpInit();
sndInit();
while (true) {
mainLoop();
}
}
/**
* It's suspected that this function would have allowed developers to override
* the value of variables while the game is running in order to view their
* effects immediately rather than having to recompile the game each time.
*
* The developers would have used rmon to create a table of name/value pairs,
* then this function would have looked up the given variable name in the table
* and written the new value to the variable's address.
*/
void mainOverrideVariable(char *name, void *value)
{
// empty
}
/**
* This function enters an infinite loop which iterates once per stage load.
* Within this loop is an inner loop which runs very frequently and decides
* whether to run mainTick on each iteration.
*
* NTSC beta checks two shorts at an offset 64MB into the development board
* and refuses to continue if they are not any of the allowed values.
* Decomp patches these reads in its build system so it can be played
* without the development board.
*/
void mainLoop(void)
{
s32 ending = false;
s32 index;
s32 numplayers;
u32 stack;
func0f175f98();
var8005d9c4 = 0;
argGetLevel(&g_StageNum);
if (g_DoBootPakMenu) {
g_Vars.unk0004e4 = 0xfd;
g_StageNum = STAGE_BOOTPAKMENU;
}
if (g_StageNum != STAGE_TITLE) {
titleSetNextStage(g_StageNum);
if (g_StageNum < STAGE_TITLE) {
func0f01b148(0);
if (argFindByPrefix(1, "-hard")) {
lvSetDifficulty(argFindByPrefix(1, "-hard")[0] - '0');
}
}
}
if (g_StageNum == STAGE_CITRAINING && IS4MB()) {
g_StageNum = STAGE_4MBMENU;
}
rngSetSeed(osGetCount());
// Outer loop - this is infinite because ending is never changed
while (!ending) {
g_MainNumGfxTasks = 0;
g_MainGameLogicEnabled = true;
g_MainIsEndscreen = false;
if (var8005d9b0 && var8005d9c4 == 0) {
index = -1;
if (IS4MB()) {
if (g_StageNum < STAGE_TITLE && getNumPlayers() >= 2) {
index = 0; \
while (g_StageAllocations4Mb[index].stagenum) { \
if (g_StageAllocations4Mb[index].stagenum == g_StageNum + 400) { \
break; \
} \
index++;
}
if (g_StageAllocations4Mb[index].stagenum == 0) {
index = -1;
}
}
if (index);
if (index < 0) {
index = 0;
while (g_StageAllocations4Mb[index].stagenum) {
if (g_StageNum == g_StageAllocations4Mb[index].stagenum) {
break;
}
index++;
}
}
argSetString(g_StageAllocations4Mb[index].string);
} else {
// 8MB
if (g_StageNum < STAGE_TITLE && getNumPlayers() >= 2) {
index = 0; \
while (g_StageAllocations8Mb[index].stagenum) { \
if (g_StageNum + 400 == g_StageAllocations8Mb[index].stagenum) { \
break; \
} \
index++;
}
if (g_StageAllocations8Mb[index].stagenum == 0) {
index = -1;
}
}
if (index < 0) {
index = 0;
while (g_StageAllocations8Mb[index].stagenum) {
if (g_StageNum == g_StageAllocations8Mb[index].stagenum) {
break;
}
index++;
}
}
argSetString(g_StageAllocations8Mb[index].string);
}
}
var8005d9c4 = 0;
mempResetPool(MEMPOOL_7);
mempResetPool(MEMPOOL_STAGE);
filesStop(4);
if (argFindByPrefix(1, "-ma")) {
g_MainMemaHeapSize = strtol(argFindByPrefix(1, "-ma"), NULL, 0) * 1024;
}
memaReset(mempAlloc(g_MainMemaHeapSize, MEMPOOL_STAGE), g_MainMemaHeapSize);
langReset(g_StageNum);
playermgrReset();
if (g_StageNum >= STAGE_TITLE) {
numplayers = 0;
} else {
if (argFindByPrefix(1, "-play")) {
numplayers = strtol(argFindByPrefix(1, "-play"), NULL, 0);
} else {
numplayers = 1;
}
if (getNumPlayers() >= 2) {
numplayers = getNumPlayers();
}
}
if (numplayers < 2) {
g_Vars.bondplayernum = 0;
g_Vars.coopplayernum = -1;
g_Vars.antiplayernum = -1;
} else if (argFindByPrefix(1, "-coop")) {
g_Vars.bondplayernum = 0;
g_Vars.coopplayernum = 1;
g_Vars.antiplayernum = -1;
} else if (argFindByPrefix(1, "-anti")) {
g_Vars.bondplayernum = 0;
g_Vars.coopplayernum = -1;
g_Vars.antiplayernum = 1;
}
playermgrAllocatePlayers(numplayers);
if (argFindByPrefix(1, "-mpbots")) {
g_Vars.lvmpbotlevel = 1;
}
if (g_Vars.coopplayernum >= 0 || g_Vars.antiplayernum >= 0) {
g_MpSetup.chrslots = 0x03;
mpReset();
} else if (g_Vars.perfectbuddynum) {
mpReset();
} else if (g_Vars.mplayerisrunning == false
&& (numplayers >= 2 || g_Vars.lvmpbotlevel || argFindByPrefix(1, "-play"))) {
g_MpSetup.chrslots = 1;
if (numplayers >= 2) {
g_MpSetup.chrslots |= 1 << 1;
}
if (numplayers >= 3) {
g_MpSetup.chrslots |= 1 << 2;
}
if (numplayers >= 4) {
g_MpSetup.chrslots |= 1 << 3;
}
g_MpSetup.stagenum = g_StageNum;
mpReset();
}
gfxReset();
joyReset();
dhudReset();
zbufReset(g_StageNum);
lvReset(g_StageNum);
viReset(g_StageNum);
frametimeCalculate();
profileReset();
while (g_MainChangeToStageNum < 0) {
const s32 cycles = osGetCount() - g_Vars.thisframestartt;
if (cycles >= g_Vars.mininc60 * CYCLES_PER_FRAME - CYCLES_PER_FRAME / 2) {
schedStartFrame(&g_Sched);
mainTick();
schedEndFrame(&g_Sched);
}
}
lvStop();
mempDisablePool(MEMPOOL_STAGE);
mempDisablePool(MEMPOOL_7);
filesStop(4);
viBlack(true);
pak0f116994();
g_StageNum = g_MainChangeToStageNum;
g_MainChangeToStageNum = -1;
}
}
void mainTick(void)
{
Gfx *gdl;
Gfx *gdlstart;
OSScMsg msg = {OS_SC_DONE_MSG};
s32 i;
if (g_MainChangeToStageNum < 0) {
frametimeCalculate();
profileReset();
profileSetMarker(PROFILE_MAINTICK_START);
joyDebugJoy();
schedSetCrashEnable2(false);
if (g_MainGameLogicEnabled) {
gdl = gdlstart = gfxGetMasterDisplayList();
gDPSetTile(gdl++, G_IM_FMT_RGBA, G_IM_SIZ_16b, 0, 0x0000, G_TX_LOADTILE, 0, G_TX_NOMIRROR | G_TX_WRAP, G_TX_NOMASK, G_TX_NOLOD, G_TX_NOMIRROR | G_TX_WRAP, G_TX_NOMASK, G_TX_NOLOD);
gDPSetTile(gdl++, G_IM_FMT_RGBA, G_IM_SIZ_4b, 0, 0x0100, 6, 0, G_TX_NOMIRROR | G_TX_WRAP, G_TX_NOMASK, G_TX_NOLOD, G_TX_NOMIRROR | G_TX_WRAP, G_TX_NOMASK, G_TX_NOLOD);
lvTick();
playermgrShuffle();
if (g_StageNum < STAGE_TITLE) {
for (i = 0; i < PLAYERCOUNT(); i++) {
setCurrentPlayerNum(playermgrGetPlayerAtOrder(i));
if (g_StageNum != STAGE_TEST_OLD || !titleIsKeepingMode()) {
viSetViewPosition(g_Vars.currentplayer->viewleft, g_Vars.currentplayer->viewtop);
viSetFovAspectAndSize(
g_Vars.currentplayer->fovy, g_Vars.currentplayer->aspect,
g_Vars.currentplayer->viewwidth, g_Vars.currentplayer->viewheight);
}
lvTickPlayer();
}
}
gdl = lvRender(gdl);
if (debugGetProfileMode() >= 2) {
gdl = profileRender(gdl);
}
gDPFullSync(gdl++);
gSPEndDisplayList(gdl++);
}
if (g_MainGameLogicEnabled) {
gfxSwapBuffers();
viUpdateMode();
}
rdpCreateTask(gdlstart, gdl, 0, (s32) &msg);
memaPrint();
profileSetMarker(PROFILE_MAINTICK_END);
}
}
void mainEndStage(void)
{
sndStopNosedive();
if (!g_MainIsEndscreen) {
pak0f11c6d0();
joyDisableTemporarily();
if (g_Vars.coopplayernum >= 0) {
s32 prevplayernum = g_Vars.currentplayernum;
s32 i;
for (i = 0; i < PLAYERCOUNT(); i++) {
setCurrentPlayerNum(i);
endscreenPushCoop();
}
setCurrentPlayerNum(prevplayernum);
musicStartMenu();
} else if (g_Vars.antiplayernum >= 0) {
s32 prevplayernum = g_Vars.currentplayernum;
s32 i;
for (i = 0; i < PLAYERCOUNT(); i++) {
setCurrentPlayerNum(i);
endscreenPushAnti();
}
setCurrentPlayerNum(prevplayernum);
musicStartMenu();
} else if (g_Vars.normmplayerisrunning) {
mpEndMatch();
} else {
endscreenPrepare();
musicStartMenu();
}
}
g_MainIsEndscreen = true;
}
/**
* Change to the given stage at the end of the current frame.
*/
void mainChangeToStage(s32 stagenum)
{
pak0f11c6d0();
g_MainChangeToStageNum = stagenum;
}
s32 mainGetStageNum(void)
{
return g_StageNum;
}
void func0000e990(void)
{
objectivesCheckAll();
objectivesDisableChecking();
mainEndStage();
}
+388
View File
@@ -0,0 +1,388 @@
#include <PR/ultratypes.h>
#include <PR/sched.h>
#include "lib/boot.h"
#include "lib/sched.h"
#include "constants.h"
#include "game/menugfx.h"
#include "bss.h"
#include "lib/args.h"
#include "lib/audiomgr.h"
#include "lib/reset.h"
#include "lib/rzip.h"
#include "lib/crash.h"
#include "lib/main.h"
#include "lib/snd.h"
#include "lib/pimgr.h"
#include "lib/profile.h"
#include "lib/rmon.h"
#include "lib/lib_48150.h"
#include "lib/vi.h"
#include "lib/joy.h"
#include "data.h"
#include "types.h"
#include "video.h"
#include "input.h"
/*
* private typedefs and defines
*/
#define VIDEO_MSG 666
#define RSP_DONE_MSG 667
#define RDP_DONE_MSG 668
#define PRE_NMI_MSG 669
/*
* OSScTask state
*/
#define OS_SC_DP 0x0001 /* set if still needs dp */
#define OS_SC_SP 0x0002 /* set if still needs sp */
#define OS_SC_YIELD 0x0010 /* set if yield requested */
#define OS_SC_YIELDED 0x0020 /* set if yield completed */
/*
* OSScTask->flags type identifier
*/
#define OS_SC_XBUS (OS_SC_SP | OS_SC_DP)
#define OS_SC_DRAM (OS_SC_SP | OS_SC_DP | OS_SC_DRAM_DLIST)
#define OS_SC_DP_XBUS (OS_SC_SP)
#define OS_SC_DP_DRAM (OS_SC_SP | OS_SC_DRAM_DLIST)
#define OS_SC_SP_XBUS (OS_SC_DP)
#define OS_SC_SP_DRAM (OS_SC_DP | OS_SC_DRAM_DLIST)
/*
* private functions
*/
void __scMain(void *arg);
void __scHandleTasks(OSSched *s);
void __scHandleRSP(OSSched *s);
void __scHandleRDP(OSSched *s);
void __scAppendList(OSSched *s, OSScTask *t);
OSScTask *__scTaskReady(OSScTask *t);
s32 __scTaskComplete(OSSched *s,OSScTask *t);
void __scExec(OSSched *sc, OSScTask *sp, OSScTask *dp);
void __scYield(OSSched *s);
s32 __scSchedule(OSSched *sc, OSScTask **sp, OSScTask **dp, s32 availRCP);
OSViMode var8008dcc0[NUM_GFXTASKS];
OSViMode *var8008dd60[NUM_GFXTASKS];
OSViMode var8008dd68[NUM_GFXTASKS];
s32 var8008de08;
s32 g_ViCurVStart0;
s32 g_ViCurVStart1;
u32 var8008de14;
OSTimer g_SchedRspTimer;
u32 g_SchedDpCounters[4];
struct artifact g_ArtifactLists[3][120];
u8 g_SchedSpecialArtifactIndexes[3];
s32 g_SchedWriteArtifactsIndex;
s32 g_SchedFrontArtifactsIndex;
s32 g_SchedPendingArtifactsIndex;
bool g_SchedCrashedUnexpectedly = false;
bool g_SchedCrashEnable1 = false;
bool g_SchedCrashEnable2 = false;
u32 g_SchedCrashRenderInterval = 45000000;
u32 g_SchedCrashLastRendered = 0;
s32 var8005ce74 = 0;
f32 g_ViXScalesBySlot[NUM_GFXTASKS] = {1, 1};
f32 g_ViYScalesBySlot[NUM_GFXTASKS] = {1, 1};
bool g_SchedViModesPending[NUM_GFXTASKS] = {false, false};
s32 g_ViUnblackTimer = NUM_FRAMEBUFFERS + 1;
s32 g_ViShakeDirection = 1;
s32 g_ViShakeIntensity = 0;
s32 g_ViShakeTimer = 0;
u32 var8005cea0 = 0;
u32 var8005cea4 = 0;
OSScMsg g_SchedRspMsg = {OS_SC_RSP_MSG};
bool g_SchedIsFirstTask = true;
void schedSetCrashEnable1(bool enable)
{
g_SchedCrashEnable1 = enable;
}
void schedSetCrashedUnexpectedly(bool enable)
{
g_SchedCrashedUnexpectedly = enable;
}
void schedSetCrashEnable2(bool enable)
{
g_SchedCrashEnable2 = enable;
}
void schedSetCrashRenderInterval(u32 cycles)
{
g_SchedCrashRenderInterval = cycles;
}
void schedRenderCrashOnBuffer(void *framebuffer)
{
if ((g_SchedCrashEnable2 && g_SchedCrashEnable1) || g_SchedCrashedUnexpectedly) {
// crashRenderFrame(framebuffer);
g_SchedCrashLastRendered = osGetCount();
}
}
void schedRenderCrashPeriodically(u32 framecount)
{
if ((framecount & 0xf) == 0 && ((g_SchedCrashEnable2 && g_SchedCrashEnable1) || g_SchedCrashedUnexpectedly)) {
if (osGetCount() - g_SchedCrashLastRendered > g_SchedCrashRenderInterval) {
// crashRenderFrame(g_FrameBuffers[0]);
// crashRenderFrame(g_FrameBuffers[1]);
}
}
}
void schedInitCrashLastRendered(void)
{
g_SchedCrashLastRendered = osGetCount();
}
void osCreateScheduler(OSSched *sc, OSThread *thread, u8 mode, u32 numFields)
{
sc->curRSPTask = 0;
sc->curRDPTask = 0;
sc->clientList = 0;
sc->frameCount = 0;
sc->audioListHead = 0;
sc->gfxListHead = 0;
sc->audioListTail = 0;
sc->gfxListTail = 0;
sc->retraceMsg.type = OS_SC_RETRACE_MSG;
sc->prenmiMsg.type = OS_SC_PRE_NMI_MSG;
sc->thread = thread;
osCreateMesgQueue(&sc->interruptQ, sc->intBuf, OS_SC_MAX_MESGS);
osCreateMesgQueue(&sc->cmdQ, sc->cmdMsgBuf, OS_SC_MAX_MESGS);
osCreateViManager(OS_PRIORITY_VIMGR);
var8008de08 = osViModeTable[mode].comRegs.hStart;
g_ViCurVStart0 = osViModeTable[mode].fldRegs[0].vStart;
g_ViCurVStart1 = osViModeTable[mode].fldRegs[1].vStart;
var8008dd60[0] = &var8008dd68[0];
var8008dd60[1] = &var8008dd68[1];
var8008dd68[0] = osViModeTable[mode];
var8008dd68[1] = osViModeTable[mode];
osViSetEvent(&sc->interruptQ, (OSMesg)VIDEO_MSG, numFields);
schedInitCrashLastRendered();
}
void osScAddClient(OSSched *sc, OSScClient *c, OSMesgQueue *msgQ, bool is30fps)
{
c->msgQ = msgQ;
c->is30fps = is30fps;
c->next = sc->clientList;
sc->clientList = c;
}
OSMesgQueue *osScGetCmdQ(OSSched *sc)
{
return &sc->cmdQ;
}
void __scUpdateViMode(void)
{
if (g_SchedIsFirstTask) {
osViBlack(false);
g_SchedIsFirstTask = false;
}
var8005ce74 = (var8005ce74 + 1) % 2;
if (g_SchedViModesPending[1 - var8005ce74]) {
if (var8008dd60[1 - var8005ce74]->comRegs.width != var8008dcc0[1 - var8005ce74].comRegs.width
|| var8008dd60[1 - var8005ce74]->comRegs.xScale != var8008dcc0[1 - var8005ce74].comRegs.xScale
|| var8008dd60[1 - var8005ce74]->fldRegs[0].yScale != var8008dcc0[1 - var8005ce74].fldRegs[0].yScale
|| var8008dd60[1 - var8005ce74]->fldRegs[1].yScale != var8008dcc0[1 - var8005ce74].fldRegs[1].yScale
|| var8008dd60[1 - var8005ce74]->fldRegs[0].origin != var8008dcc0[1 - var8005ce74].fldRegs[0].origin
|| var8008dd60[1 - var8005ce74]->fldRegs[1].origin != var8008dcc0[1 - var8005ce74].fldRegs[1].origin) {
osViSetMode(var8008dd60[1 - var8005ce74]);
osViBlack(g_ViUnblackTimer);
osViSetXScale(g_ViXScalesBySlot[1 - var8005ce74]);
osViSetYScale(g_ViYScalesBySlot[1 - var8005ce74]);
osViSetSpecialFeatures(OS_VI_GAMMA_OFF | OS_VI_DITHER_FILTER_ON);
}
g_SchedViModesPending[1 - var8005ce74] = false;
}
if (g_ViUnblackTimer != 0 && g_ViUnblackTimer <= NUM_FRAMEBUFFERS) {
g_ViUnblackTimer--;
}
}
/**
* Nintendo's sheduler accepts tasks on a "command" message queue.
* This isn't used here.
*
* In PD, the main and audio threads submit tasks by calling this function
* instead. It temporarily increases the calling thread's priority above the
* scheduler, adds the task to the linked list directly and attempts to execute
* it. This is faster than the queue method because it avoids switching threads.
*/
void schedSubmitTask(OSSched *sc, OSScTask *t)
{
if (sc->doAudio && t->list.t.type == M_AUDTASK) {
// TODO: audio frame
} else if (t->list.t.type == M_GFXTASK) {
videoSubmitCommands((Gfx *)t->list.t.data_ptr);
}
}
void schedStartFrame(OSSched *sc)
{
videoStartFrame();
}
/**
* Handle a retrace (vsync) event.
*
* Audio tasks are scheduled based on retrace + a timer (approximately 6ms).
* On NTSC, this is done on every second frame if 8MB, or every second frame
* if 4MB. I guess less memory means the audio queue has to be kept smaller
* and processed more frequently. On PAL, it's every second frame regardless.
*
* Controller input is polled here.
*
* Lastly, if there's crash information available then it will be checked and
* rendered periodically (once every 16 retraces). I guess this makes it render
* if the RDP has hung.
*/
void schedEndFrame(OSSched *sc)
{
sc->frameCount++;
#if PAL
if (!g_Resetting && (sc->frameCount & 1)) {
// osStopTimer(&g_SchedRspTimer);
// osSetTimer(&g_SchedRspTimer, 280000, 0, amgrGetFrameMesgQueue(), &g_SchedRspMsg);
}
#else
if (!g_Resetting && ((sc->frameCount & 1) || IS4MB())) {
// osStopTimer(&g_SchedRspTimer);
// osSetTimer(&g_SchedRspTimer, 280000, 0, amgrGetFrameMesgQueue(), &g_SchedRspMsg);
}
#endif
if (!g_Resetting) {
viHandleRetrace();
}
inputUpdate();
joysHandleRetrace();
sndHandleRetrace();
schedRenderCrashPeriodically(sc->frameCount);
videoEndFrame();
// check for vid mode changes
__scUpdateViMode();
}
void schedInitArtifacts(void)
{
s32 i;
s32 j;
for (i = 0; i < 3; i++) {
for (j = 0; j < MAX_ARTIFACTS; j++) {
g_ArtifactLists[i][j].type = ARTIFACTTYPE_FREE;
}
g_SchedSpecialArtifactIndexes[i] = 0;
}
}
/**
* The write list is an artifact list that is not currently being displayed on
* the screen. Update logic can write here to put artifacts on the next frame.
*/
struct artifact *schedGetWriteArtifacts(void)
{
return g_ArtifactLists[g_SchedWriteArtifactsIndex];
}
/**
* The front list is the artifact list that is currently being displayed on the
* screen. Rendering logic reads this list. The list may be re-used for multiple
* frames in a row during lag.
*/
struct artifact *schedGetFrontArtifacts(void)
{
return g_ArtifactLists[g_SchedFrontArtifactsIndex];
}
/**
* The pending list is possibly misnamed. I'm not sure how this list works.
*
* @TODO: Investigate.
*/
struct artifact *schedGetPendingArtifacts(void)
{
return g_ArtifactLists[g_SchedPendingArtifactsIndex];
}
void schedIncrementWriteArtifacts(void)
{
g_SchedWriteArtifactsIndex = (g_SchedWriteArtifactsIndex + 1) % 3;
}
void schedIncrementFrontArtifacts(void)
{
g_SchedFrontArtifactsIndex = (g_SchedFrontArtifactsIndex + 1) % 3;
}
void schedIncrementPendingArtifacts(void)
{
g_SchedPendingArtifactsIndex = (g_SchedPendingArtifactsIndex + 1) % 3;
}
void schedResetArtifacts(void)
{
g_SchedWriteArtifactsIndex = 0;
g_SchedFrontArtifactsIndex = 1;
g_SchedPendingArtifactsIndex = 0;
}
void schedUpdatePendingArtifacts(void)
{
struct artifact *artifacts = schedGetPendingArtifacts();
s32 i;
for (i = 0; i < MAX_ARTIFACTS; i++) {
struct artifact *artifact = &artifacts[i];
if (artifact->type != ARTIFACTTYPE_FREE) {
u16 *unk08 = artifact->unk08;
u16 value08 = unk08[0];
if (g_SchedSpecialArtifactIndexes[g_SchedPendingArtifactsIndex] == 1) {
u16 *unk0c = artifact->unk0c.u16p;
u16 value0c = unk0c[0];
if (value0c > value08) {
artifact->unk02 = value08;
} else {
artifact->unk02 = value0c;
}
} else {
artifact->unk02 = value08;
}
}
}
g_SchedSpecialArtifactIndexes[g_SchedPendingArtifactsIndex] = 0;
schedIncrementPendingArtifacts();
}
void schedConsiderScreenshot(void)
{
}
+901
View File
@@ -0,0 +1,901 @@
#include <stdlib.h>
#include <stdio.h>
#include <PR/ultratypes.h>
#include <PR/gbi.h>
#include <PR/libaudio.h>
#include "platform.h"
#include "data.h"
#include "bss.h"
#include "preprocess.h"
#include "romdata.h"
#define PD_BEFIELD_I16(x) x = PD_BE16(x)
#define PD_BEFIELD_I32(x) x = PD_BE32(x)
#define PD_BEFIELD_F32(x) *(u32 *)&x = PD_BE32(*(u32 *)&x)
#define PD_BEFIELD_PTR(x) x = (void *)PD_BE32((u32)x)
#define PD_PTR_BASE(x, b) (void *)((u8 *)b + (u32)x)
#define PD_PTR_BASEOFS(x, b, d) (void *)((u8 *)b + (u32)x - d)
static inline void preprocessALWaveTable(ALWaveTable *tbl, u8 *bankBase)
{
if ((uintptr_t)tbl->base < 0x02000000) {
// already swapped (maybe come up with a better check)
return;
}
PD_BEFIELD_I32(tbl->len);
PD_BEFIELD_PTR(tbl->base);
if (tbl->type == AL_ADPCM_WAVE) {
if (tbl->waveInfo.adpcmWave.loop ) {
PD_BEFIELD_PTR(tbl->waveInfo.adpcmWave.loop);
ALADPCMloop *loop = PD_PTR_BASE(tbl->waveInfo.adpcmWave.loop, bankBase);
PD_BEFIELD_I32(loop->count);
PD_BEFIELD_I32(loop->start);
PD_BEFIELD_I32(loop->end);
/* TODO: this goes into the mixer -- swapping not required?
for (s32 i = 0; i < 16; ++i) {
PD_BEFIELD_I16(loop->state[i]);
}
*/
}
if (tbl->waveInfo.adpcmWave.book) {
PD_BEFIELD_PTR(tbl->waveInfo.adpcmWave.book);
ALADPCMBook *book = PD_PTR_BASE(tbl->waveInfo.adpcmWave.book, bankBase);
PD_BEFIELD_I32(book->npredictors);
PD_BEFIELD_I32(book->order);
/* TODO: this goes into the mixer -- swapping not required?
const s32 bookSize = book->order * book->npredictors * ADPCMVSIZE;
for (s32 i = 0; i < bookSize && i < 128; ++i) {
PD_BEFIELD_I16(book->book[i]);
}
*/
}
} else if (tbl->type == AL_RAW16_WAVE) {
if (tbl->waveInfo.rawWave.loop) {
PD_BEFIELD_PTR(tbl->waveInfo.rawWave.loop);
ALRawLoop *loop = PD_PTR_BASE(tbl->waveInfo.rawWave.loop, bankBase);
PD_BEFIELD_I32(loop->count);
PD_BEFIELD_I32(loop->start);
PD_BEFIELD_I32(loop->end);
}
}
}
static inline void preprocessALSound(ALSound *snd, u8 *bankBase)
{
if ((uintptr_t)snd->wavetable < 0x02000000) {
// already swapped (maybe come up with a better check)
return;
}
if (snd->envelope) {
PD_BEFIELD_PTR(snd->envelope);
ALEnvelope *env = PD_PTR_BASE(snd->envelope, bankBase);
PD_BEFIELD_I32(env->attackTime);
PD_BEFIELD_I32(env->releaseTime);
PD_BEFIELD_I32(env->decayTime);
}
if (snd->keyMap) {
PD_BEFIELD_PTR(snd->keyMap);
}
if (snd->wavetable) {
PD_BEFIELD_PTR(snd->wavetable);
preprocessALWaveTable(PD_PTR_BASE(snd->wavetable, bankBase), bankBase);
}
}
static inline void preprocessALInstrument(ALInstrument *inst, u8 *bankBase)
{
if ((uintptr_t)inst->soundArray[0] < 0x02000000) {
// already swapped (maybe come up with a better check)
return;
}
PD_BEFIELD_I16(inst->bendRange);
PD_BEFIELD_I16(inst->soundCount);
for (s16 i = 0; i < inst->soundCount; ++i) {
PD_BEFIELD_PTR(inst->soundArray[i]);
preprocessALSound(PD_PTR_BASE(inst->soundArray[i], bankBase), bankBase);
}
}
static inline void preprocessALBank(ALBank *bank, u8 *bankBase)
{
if ((uintptr_t)bank->instArray[0] < 0x02000000) {
// already swapped (maybe come up with a better check)
return;
}
PD_BEFIELD_I32(bank->sampleRate);
PD_BEFIELD_I16(bank->instCount);
if (bank->percussion) {
PD_BEFIELD_PTR(bank->percussion);
preprocessALInstrument(PD_PTR_BASE(bank->percussion, bankBase), bankBase);
}
for (s16 i = 0; i < bank->instCount; ++i) {
PD_BEFIELD_PTR(bank->instArray[i]);
preprocessALInstrument(PD_PTR_BASE(bank->instArray[i], bankBase), bankBase);
}
}
static inline void preprocessGfx(Gfx *gdl)
{
while (gdl) {
const u8 opcode = gdl->bytes[0];
PD_BEFIELD_I32(gdl->words.w0);
PD_BEFIELD_I32(gdl->words.w1);
if (opcode == G_ENDDL) {
break;
}
++gdl;
}
}
static inline void preprocessVtx(Vtx *vtx)
{
PD_BEFIELD_I16(vtx->x);
PD_BEFIELD_I16(vtx->y);
PD_BEFIELD_I16(vtx->z);
PD_BEFIELD_I16(vtx->s);
PD_BEFIELD_I16(vtx->t);
}
static void preprocessModelGunDL(struct modelrodata_gundl *gundl, u8 *base, u32 ofs)
{
PD_BEFIELD_PTR(gundl->opagdl);
PD_BEFIELD_PTR(gundl->xlugdl);
PD_BEFIELD_PTR(gundl->baseaddr);
PD_BEFIELD_PTR(gundl->vertices);
PD_BEFIELD_I32(gundl->numvertices);
PD_BEFIELD_I16(gundl->unk12);
Vtx *vtx = PD_PTR_BASEOFS(gundl->vertices, base, ofs);
for (s16 i = 0; i < gundl->numvertices; ++i, ++vtx) {
preprocessVtx(vtx);
}
preprocessGfx(PD_PTR_BASEOFS(gundl->opagdl, base, ofs));
preprocessGfx(PD_PTR_BASEOFS(gundl->xlugdl, base, ofs));
}
static void preprocessModelDL(struct modelrodata_dl *dl, u8 *base, u32 ofs)
{
PD_BEFIELD_PTR(dl->opagdl);
PD_BEFIELD_PTR(dl->xlugdl);
PD_BEFIELD_PTR(dl->colours);
PD_BEFIELD_PTR(dl->vertices);
PD_BEFIELD_I16(dl->numvertices);
PD_BEFIELD_I16(dl->numcolours);
PD_BEFIELD_I16(dl->mcount);
PD_BEFIELD_I16(dl->rwdataindex);
Vtx *vtx = PD_PTR_BASEOFS(dl->vertices, base, ofs);
for (s16 i = 0; i < dl->numvertices; ++i, ++vtx) {
preprocessVtx(vtx);
}
preprocessGfx(PD_PTR_BASEOFS(dl->opagdl, base, ofs));
preprocessGfx(PD_PTR_BASEOFS(dl->xlugdl, base, ofs));
}
static void preprocessModelNode(struct modelnode *node, u8 *base, u32 ofs)
{
PD_BEFIELD_I16(node->type);
PD_BEFIELD_PTR(node->child);
PD_BEFIELD_PTR(node->next);
PD_BEFIELD_PTR(node->parent);
if (!node->rodata) {
return;
}
PD_BEFIELD_PTR(node->rodata);
union modelrodata* ro = PD_PTR_BASEOFS(node->rodata, base, ofs);
switch (node->type & 0xff) {
case MODELNODETYPE_CHRINFO:
PD_BEFIELD_I16(ro->chrinfo.animpart);
PD_BEFIELD_I16(ro->chrinfo.mtxindex);
PD_BEFIELD_I16(ro->chrinfo.rwdataindex);
PD_BEFIELD_F32(ro->chrinfo.unk04);
break;
case MODELNODETYPE_POSITION:
PD_BEFIELD_F32(ro->position.drawdist);
PD_BEFIELD_F32(ro->position.pos.x);
PD_BEFIELD_F32(ro->position.pos.y);
PD_BEFIELD_F32(ro->position.pos.z);
PD_BEFIELD_I16(ro->position.part);
PD_BEFIELD_I16(ro->position.mtxindex0);
PD_BEFIELD_I16(ro->position.mtxindex1);
PD_BEFIELD_I16(ro->position.mtxindex2);
break;
case MODELNODETYPE_GUNDL:
preprocessModelGunDL(&ro->gundl, base, ofs);
break;
case MODELNODETYPE_05:
break;
case MODELNODETYPE_DISTANCE:
PD_BEFIELD_F32(ro->distance.near);
PD_BEFIELD_F32(ro->distance.far);
PD_BEFIELD_I16(ro->distance.rwdataindex);
PD_BEFIELD_PTR(ro->distance.target);
// TODO: assuming target points to one of the nodes we'll swap by following node->next
break;
case MODELNODETYPE_REORDER:
PD_BEFIELD_F32(ro->reorder.unk00);
PD_BEFIELD_F32(ro->reorder.unk04);
PD_BEFIELD_F32(ro->reorder.unk08);
PD_BEFIELD_F32(ro->reorder.unk0c[0]);
PD_BEFIELD_F32(ro->reorder.unk0c[1]);
PD_BEFIELD_F32(ro->reorder.unk0c[2]);
PD_BEFIELD_I16(ro->reorder.rwdataindex);
PD_BEFIELD_I16(ro->reorder.side);
break;
case MODELNODETYPE_BBOX:
PD_BEFIELD_F32(ro->bbox.xmin);
PD_BEFIELD_F32(ro->bbox.xmax);
PD_BEFIELD_F32(ro->bbox.ymin);
PD_BEFIELD_F32(ro->bbox.ymax);
PD_BEFIELD_F32(ro->bbox.zmin);
PD_BEFIELD_F32(ro->bbox.zmax);
PD_BEFIELD_I32(ro->bbox.hitpart);
break;
case MODELNODETYPE_0B:
PD_BEFIELD_PTR(ro->type0b.baseaddr);
PD_BEFIELD_I16(ro->type0b.rwdataindex);
PD_BEFIELD_I32(ro->type0b.unk00);
PD_BEFIELD_PTR(ro->type0b.unk3c);
// TODO: do we need to swap the rest of the words?
break;
case MODELNODETYPE_CHRGUNFIRE:
PD_BEFIELD_PTR(ro->chrgunfire.baseaddr);
PD_BEFIELD_PTR(ro->chrgunfire.texture);
PD_BEFIELD_I16(ro->chrgunfire.rwdataindex);
PD_BEFIELD_F32(ro->chrgunfire.pos.x);
PD_BEFIELD_F32(ro->chrgunfire.pos.y);
PD_BEFIELD_F32(ro->chrgunfire.pos.z);
PD_BEFIELD_F32(ro->chrgunfire.dim.x);
PD_BEFIELD_F32(ro->chrgunfire.dim.y);
PD_BEFIELD_F32(ro->chrgunfire.dim.z);
PD_BEFIELD_F32(ro->chrgunfire.unk1c);
// TODO: do we swap contents of *texture or is it part of mdl->textureconfigs[]?
break;
case MODELNODETYPE_0D:
PD_BEFIELD_PTR(ro->type0d.baseaddr);
PD_BEFIELD_PTR(ro->type0d.unk10);
PD_BEFIELD_PTR(ro->type0d.unk14);
// TODO: do we need to swap the rest of the words?
break;
case MODELNODETYPE_0E:
case MODELNODETYPE_0F:
break;
case MODELNODETYPE_11:
PD_BEFIELD_PTR(ro->type11.unk14);
// TODO: do we need to swap the rest of the words?
break;
case MODELNODETYPE_TOGGLE:
PD_BEFIELD_I16(ro->toggle.rwdataindex);
PD_BEFIELD_PTR(ro->toggle.target);
// TODO: assuming target points to one of the nodes we'll swap by following node->next
break;
case MODELNODETYPE_DL:
preprocessModelDL(&ro->dl, base, ofs);
break;
case 0x19:
PD_BEFIELD_I32(ro->type19.numvertices);
for (s32 i = 0; i < ARRAYCOUNT(ro->type19.vertices); ++i) {
PD_BEFIELD_F32(ro->type19.vertices[i].x);
PD_BEFIELD_F32(ro->type19.vertices[i].y);
PD_BEFIELD_F32(ro->type19.vertices[i].z);
}
break;
default:
fprintf(stderr, "preprocessModelNode: node at %p: unknown node->type: 0x%02x\n", node, node->type & 0xff);
break;
}
if (node->child) {
node = PD_PTR_BASEOFS(node->child, base, ofs);
} else {
while (node) {
if (node->next) {
node = PD_PTR_BASEOFS(node->next, base, ofs);
break;
}
node = PD_PTR_BASEOFS(node->parent, base, ofs);
}
}
}
static inline void preprocessPadData(u8 *ptr)
{
// for some insane reason pads are packed
// header is always 1 word, the rest of the fields depends on the flags
u32 *header = (u32 *) ptr;
PD_BEFIELD_I32(header[0]);
ptr += 4;
if ((*header >> 14) & PADFLAG_INTPOS) {
// position is 3x s16
s16 *sbuffer = (s16 *) ptr;
PD_BEFIELD_I16(sbuffer[0]);
PD_BEFIELD_I16(sbuffer[1]);
PD_BEFIELD_I16(sbuffer[2]);
ptr += 8;
} else {
// position is 3x f32
f32 *fbuffer = (f32 *) ptr;
PD_BEFIELD_F32(fbuffer[0]);
PD_BEFIELD_F32(fbuffer[1]);
PD_BEFIELD_F32(fbuffer[2]);
ptr += 12;
}
if (!((*header >> 14) & (PADFLAG_UPALIGNTOX | PADFLAG_UPALIGNTOY | PADFLAG_UPALIGNTOZ))) {
// up vector, 3x f32
f32 *fbuffer = (f32 *) ptr;
PD_BEFIELD_F32(fbuffer[0]);
PD_BEFIELD_F32(fbuffer[1]);
PD_BEFIELD_F32(fbuffer[2]);
ptr += 12;
}
if (!((*header >> 14) & (PADFLAG_LOOKALIGNTOX | PADFLAG_LOOKALIGNTOY | PADFLAG_LOOKALIGNTOZ))) {
// look vector, 3x f32
f32 *fbuffer = (f32 *) ptr;
PD_BEFIELD_F32(fbuffer[0]);
PD_BEFIELD_F32(fbuffer[1]);
PD_BEFIELD_F32(fbuffer[2]);
ptr += 12;
}
if ((*header >> 14) & PADFLAG_HASBBOXDATA) {
// bbox, 3x f32 mins + 3x f32 maxs
f32 *fbuffer = (f32 *) ptr;
PD_BEFIELD_F32(fbuffer[0]);
PD_BEFIELD_F32(fbuffer[1]);
PD_BEFIELD_F32(fbuffer[2]);
PD_BEFIELD_F32(fbuffer[3]);
PD_BEFIELD_F32(fbuffer[4]);
PD_BEFIELD_F32(fbuffer[5]);
}
}
void preprocessAnimations(u8 *data, u32 size)
{
// set the anim table pointers as well
extern u8 *_animationsTableRomStart;
extern u8 *_animationsTableRomEnd;
// the animation table is at the end of the segment
u32 *animtbl = (void *)(data + size - 0x38a0);
_animationsTableRomStart = (u8 *)animtbl;
_animationsTableRomEnd = data + size;
PD_BEFIELD_I32(*animtbl);
const u32 count = *animtbl++;
struct animtableentry *anim = (struct animtableentry *)animtbl;
for (u32 i = 0; i < count; ++i, ++anim) {
PD_BEFIELD_I16(anim->numframes);
PD_BEFIELD_I16(anim->bytesperframe);
PD_BEFIELD_I16(anim->headerlen);
PD_BEFIELD_I32(anim->data);
}
}
void preprocessMpConfigs(u8 *data, u32 size)
{
const u32 count = size / sizeof(struct mpconfig);
struct mpconfig *cfg = (struct mpconfig *)data;
for (u32 i = 0; i < count; ++i, ++cfg) {
PD_BEFIELD_I32(cfg->setup.options);
PD_BEFIELD_I16(cfg->setup.teamscorelimit);
PD_BEFIELD_I16(cfg->setup.chrslots);
// TODO: are these required or are they always 0?
PD_BEFIELD_I16(cfg->setup.fileguid.deviceserial);
PD_BEFIELD_I32(cfg->setup.fileguid.fileid);
}
}
void preprocessFont(u8 *data, u32 size)
{
struct font *fnt = (struct font *)data;
for (s32 i = 0; i < ARRAYCOUNT(fnt->kerning); ++i) {
PD_BEFIELD_I32(fnt->kerning[i]);
}
for (s32 i = 0; i < ARRAYCOUNT(fnt->chars); ++i) {
PD_BEFIELD_I32(fnt->chars[i].kerningindex);
PD_BEFIELD_PTR(fnt->chars[i].pixeldata);
}
}
void preprocessJpnFont(u8 *data, u32 size)
{
// ???
}
void preprocessALBankFile(u8 *data, u32 size)
{
ALBankFile *bankf = (ALBankFile *)data;
PD_BEFIELD_I16(bankf->revision);
PD_BEFIELD_I16(bankf->bankCount);
for (s16 i = 0; i < bankf->bankCount; ++i) {
PD_BEFIELD_PTR(bankf->bankArray[i]);
preprocessALBank(PD_PTR_BASE(bankf->bankArray[i], data), data);
}
}
void preprocessSequences(u8 *data, u32 size)
{
struct seqtable *seq = (struct seqtable *)data;
PD_BEFIELD_I16(seq->count);
for (s16 i = 0; i < seq->count; ++i) {
PD_BEFIELD_I16(seq->entries[i].binlen);
PD_BEFIELD_I16(seq->entries[i].ziplen);
PD_BEFIELD_I32(seq->entries[i].romaddr);
}
}
void preprocessFiringRange(u8 *data, u32 size)
{
// u16 texts[9] is the first and only thing we care about here
// probably no sense supporting custom sizes either
u16 *texts = (u16 *)data;
for (s32 i = 0; i < 9; ++i) {
PD_BEFIELD_I16(texts[i]);
}
}
void preprocessTexturesList(u8 *data, u32 size)
{
struct texture *tex = (struct texture *)data;
const u32 count = size / sizeof(*tex);
for (u32 i = 0; i < count; ++i, ++tex) {
// TODO: it sure looks like none of the fields except soundsurfacetype, surfacetype and dataoffset are set
// just swap the last 3 bytes of the first word
const u32 dofs = (u32)tex->dataoffset << 8;
tex->dataoffset = PD_BE32(dofs);
}
}
void preprocessModel(u8 *base, u32 ofs)
{
struct modeldef *mdl = (struct modeldef *)base;
PD_BEFIELD_I16(mdl->nummatrices);
PD_BEFIELD_I16(mdl->numparts);
PD_BEFIELD_I16(mdl->numtexconfigs);
PD_BEFIELD_I16(mdl->rwdatalen);
PD_BEFIELD_F32(mdl->scale);
if (mdl->skel) {
PD_BEFIELD_PTR(mdl->skel);
if ((u32)mdl->skel >= 0x10000) {
// skeleton is a pointer instead of an index
// preprocessSkeleton((struct skeleton *)(base + (u32)mdl->skel)); // TODO
}
}
if (mdl->parts) {
PD_BEFIELD_PTR(mdl->parts);
struct modelnode **parts = PD_PTR_BASEOFS(mdl->parts, base, ofs);
for (s16 i = 0; i < mdl->numparts; ++i) {
PD_BEFIELD_PTR(parts[i]);
}
s16 *partnums = (s16 *)&parts[mdl->numparts];
for (s16 i = 0; i < mdl->numparts; ++i) {
PD_BEFIELD_I16(partnums[i]);
}
}
if (mdl->texconfigs) {
PD_BEFIELD_PTR(mdl->texconfigs);
struct textureconfig *texconfigs = PD_PTR_BASEOFS(mdl->texconfigs, base, ofs);
for (s16 i = 0; i < mdl->numtexconfigs; ++i) {
PD_BEFIELD_I32(texconfigs[i].texturenum);
}
}
if (mdl->rootnode) {
PD_BEFIELD_PTR(mdl->rootnode);
preprocessModelNode(PD_PTR_BASEOFS(mdl->rootnode, base, ofs), base, ofs);
}
}
void preprocessLangFile(u8 *data, u32 size)
{
// lang banks are just an offset table + text data right after
// offsets are from the beginning of the bank
// however we cannot preprocess them in advance because the length of the
// offset table is unknown, so that's done in lang.c on demand instead
}
void preprocessPadsFile(u8 *data, u32 size)
{
struct padsfileheader *hdr = (void *)data;
PD_BEFIELD_I32(hdr->numpads);
PD_BEFIELD_I32(hdr->numcovers);
for (s32 i = 0; i < hdr->numpads; ++i) {
if (hdr->padoffsets[i]) {
PD_BEFIELD_I32(hdr->padoffsets[i]);
preprocessPadData(PD_PTR_BASE(hdr->padoffsets[i], hdr));
}
}
if (hdr->numcovers && hdr->coversoffset) {
PD_BEFIELD_I32(hdr->coversoffset);
struct coverdefinition *def = PD_PTR_BASE(hdr->coversoffset, hdr);
for (s32 i = 0; i < hdr->numcovers; ++i, ++def) {
PD_BEFIELD_I16(def->flags);
PD_BEFIELD_F32(def->look.x);
PD_BEFIELD_F32(def->look.y);
PD_BEFIELD_F32(def->look.z);
PD_BEFIELD_F32(def->pos.x);
PD_BEFIELD_F32(def->pos.y);
PD_BEFIELD_F32(def->pos.z);
}
}
if (hdr->waypointsoffset) {
PD_BEFIELD_I32(hdr->waypointsoffset);
struct waypoint *wp = PD_PTR_BASE(hdr->waypointsoffset, hdr);
while (wp->padnum) {
PD_BEFIELD_I32(wp->padnum);
PD_BEFIELD_I32(wp->groupnum);
PD_BEFIELD_I32(wp->step);
PD_BEFIELD_PTR(wp->neighbours);
++wp;
}
}
if (hdr->waygroupsoffset) {
PD_BEFIELD_I32(hdr->waygroupsoffset);
struct waygroup *wg = PD_PTR_BASE(hdr->waygroupsoffset, hdr);
while (wg->neighbours) {
PD_BEFIELD_PTR(wg->neighbours);
PD_BEFIELD_PTR(wg->waypoints);
PD_BEFIELD_I32(wg->step);
++wg;
}
}
}
void preprocessTilesFile(u8 *data, u32 size)
{
u32 *roomTable = (u32 *)data;
PD_BEFIELD_I32(roomTable[0]);
const u32 numRooms = roomTable[0];
++roomTable;
u32 *rooms = roomTable;
for (u32 i = 0; i < numRooms; ++i) {
PD_BEFIELD_I32(rooms[i]);
}
struct geo *geo = (struct geo *)(data + rooms[0]);
struct geo *end = (struct geo *)(data + rooms[numRooms]);
while (geo < end) {
PD_BEFIELD_I16(geo->flags);
switch (geo->type) {
case GEOTYPE_TILE_I: {
struct geotilei *tile = (struct geotilei *)geo;
PD_BEFIELD_I16(tile->floorcol);
PD_BEFIELD_I16(tile->floortype);
for (u32 i = 0; i < geo->numvertices; ++i) {
PD_BEFIELD_I16(tile->vertices[i][0]);
PD_BEFIELD_I16(tile->vertices[i][1]);
PD_BEFIELD_I16(tile->vertices[i][2]);
}
geo = (struct geo *)((u8 *)geo + (uintptr_t)(geo->numvertices - 0x40) * 6 + 0x18e);
break;
}
case GEOTYPE_TILE_F: {
struct geotilef *tile = (struct geotilef *)geo;
PD_BEFIELD_I16(tile->floorcol);
PD_BEFIELD_I16(tile->floortype);
for (u32 i = 0; i < geo->numvertices; ++i) {
PD_BEFIELD_F32(tile->vertices[i].x);
PD_BEFIELD_F32(tile->vertices[i].y);
PD_BEFIELD_F32(tile->vertices[i].z);
}
geo = (struct geo *)((u8 *)geo + (uintptr_t)(geo->numvertices - 0x40) * 12 + 0x310);
break;
}
case GEOTYPE_BLOCK: {
struct geoblock *blk = (struct geoblock *)geo;
PD_BEFIELD_F32(blk->ymin);
PD_BEFIELD_F32(blk->ymax);
for (u32 i = 0; i < geo->numvertices; ++i) {
PD_BEFIELD_F32(blk->vertices[i][0]);
PD_BEFIELD_F32(blk->vertices[i][1]);
}
geo = (struct geo *)((u8 *)geo + sizeof(struct geoblock));
break;
}
case GEOTYPE_CYL: {
struct geocyl *cyl = (struct geocyl *)geo;
PD_BEFIELD_F32(cyl->x);
PD_BEFIELD_F32(cyl->z);
PD_BEFIELD_F32(cyl->radius);
PD_BEFIELD_F32(cyl->ymin);
PD_BEFIELD_F32(cyl->ymax);
geo = (struct geo *)((u8 *)geo + sizeof(struct geocyl));
break;
}
default:
break;
}
}
}
void preprocessSetupFile(u8 *data, u32 size)
{
struct stagesetup *set = (void *)data;
if (set->intro) {
PD_BEFIELD_PTR(set->intro);
for (s32 *p = PD_PTR_BASE(set->intro, set); (u8 *)p < data + size; ++p) {
PD_BEFIELD_I32(*p);
if (*p == 0x0c /*endintro*/) {
break;
}
}
}
if (set->props) {
PD_BEFIELD_PTR(set->props);
for (s32 *p = PD_PTR_BASE(set->props, set); (u8 *)p < data + size; ++p) {
PD_BEFIELD_I32(*p);
if (*p == 0x34 /*endprops*/) {
break;
}
}
}
if (set->paths) {
PD_BEFIELD_PTR(set->paths);
struct path *p = PD_PTR_BASE(set->paths, set);
while ((u8 *)p < data + size && p->pads) {
PD_BEFIELD_PTR(p->pads);
PD_BEFIELD_I16(p->len);
s32 *pp = PD_PTR_BASE(p->pads, set);
while ((u8 *)pp < data + size) {
PD_BEFIELD_I32(*pp);
if (*pp < 0) {
break;
}
}
}
}
if (set->ailists) {
PD_BEFIELD_PTR(set->ailists);
struct ailist *p = PD_PTR_BASE(set->ailists, set);
while ((u8 *)p < data + size && p->list) {
PD_BEFIELD_I32(p->id);
PD_BEFIELD_PTR(p->list);
// the actual command lists are made up of variable length instructions,
// but they don't do any wonky word casting, so they should probably work as is
}
}
// the rest of the pointers are set after loading
}
void preprocessModelFile(u8 *data, u32 size)
{
preprocessModel(data, size);
}
void preprocessGunFile(u8 *data, u32 size)
{
preprocessModel(data, size);
}
void preprocessBgSection1Header(u8 *data, u32 size)
{
u32 *header = (u32 *)data;
PD_BEFIELD_I32(header[0]); // inflatedsize
PD_BEFIELD_I32(header[1]); // section1size
PD_BEFIELD_I32(header[2]); // primcompsize
}
void preprocessBgSection1(u8 *data, u32 ofs) {
struct {
u32 unk00;
u32 roomsofs;
u32 portalsofs;
u32 commandsofs;
u32 lightsofs;
u32 stanofs;
} __attribute__((packed)) *header = (void *)data;
PD_BEFIELD_I32(header->unk00);
PD_BEFIELD_I32(header->roomsofs);
PD_BEFIELD_I32(header->portalsofs);
struct bgroom *rm = PD_PTR_BASEOFS(header->roomsofs, data, ofs);
for (; rm->unk00; ++rm) {
PD_BEFIELD_I32(rm->unk00);
PD_BEFIELD_F32(rm->pos.x);
PD_BEFIELD_F32(rm->pos.y);
PD_BEFIELD_F32(rm->pos.z);
}
struct bgportal *portals = PD_PTR_BASEOFS(header->portalsofs, data, ofs);
s32 numportals = 0;
u32 offset = 0;
for (struct bgportal *prt = portals; prt->verticesoffset; ++prt) {
PD_BEFIELD_I16(prt->verticesoffset);
PD_BEFIELD_I16(prt->roomnum1);
PD_BEFIELD_I16(prt->roomnum2);
++numportals;
offset += sizeof(struct bgportal);
}
offset += sizeof(struct bgportal);
// see bgBuildTables for an explanation of what the fuck this is
for (s32 i = 1; 1; i++) {
for (s32 j = 0; j < numportals; j++) {
if (portals[j].verticesoffset == i) {
portals[j].verticesoffset = offset;
}
}
struct portalvertices *pverts = PD_PTR_BASE(offset, portals);
for (u32 i = 0; i < pverts->count; ++i) {
PD_BEFIELD_F32(pverts->vertices[i].x);
PD_BEFIELD_F32(pverts->vertices[i].y);
PD_BEFIELD_F32(pverts->vertices[i].z);
}
}
if (header->commandsofs) {
PD_BEFIELD_I32(header->commandsofs);
struct bgcmd *cmd = PD_PTR_BASEOFS(header->commandsofs, data, ofs);
for (; cmd->type != 0x00; cmd++) {
PD_BEFIELD_I32(cmd->param);
}
}
if (header->lightsofs) {
PD_BEFIELD_I32(header->lightsofs);
// data swapping done later in preprocessBgLights
}
if (header->stanofs) {
PD_BEFIELD_I32(header->stanofs);
// unused, so won't swap the contents
}
}
void preprocessBgSection2Header(u8 *data, u32 size)
{
u16 *header = (u16 *)data;
PD_BEFIELD_I16(header[0]); // inflatedsize
PD_BEFIELD_I16(header[1]); // section2compsize
}
void preprocessBgSection2(u8 *data, u32 size)
{
// section2 is a texture id list
u16 *section2 = (u16 *)data;
for (s32 i = 0; i < size; ++i) {
PD_BEFIELD_I16(section2[i]);
}
}
void preprocessBgSection3Header(u8 *data, u32 size)
{
u16 *header = (u16 *)data;
PD_BEFIELD_I16(header[0]);
PD_BEFIELD_I16(header[1]);
}
void preprocessBgSection3(u8 *data, u32 size)
{
// room bounding boxes, 6x s16 per room
s16 *bbox = (s16 *)data;
for (s32 i = 1; i < g_Vars.roomcount; ++i) {
PD_BEFIELD_I16(*bbox); ++bbox;
PD_BEFIELD_I16(*bbox); ++bbox;
PD_BEFIELD_I16(*bbox); ++bbox;
PD_BEFIELD_I16(*bbox); ++bbox;
PD_BEFIELD_I16(*bbox); ++bbox;
PD_BEFIELD_I16(*bbox); ++bbox;
}
// gfxdatalen list
u16 *gfxdatalen = (u16 *)bbox;
for (s32 i = 1; i < g_Vars.roomcount; ++i) {
PD_BEFIELD_I16(*gfxdatalen); ++gfxdatalen;
}
}
void preprocessBgRoom(u8 *data, u32 ofs) {
struct roomgfxdata *rgfx = (void *)data;
PD_BEFIELD_I16(rgfx->numvertices);
PD_BEFIELD_I16(rgfx->numcolours);
PD_BEFIELD_I16(rgfx->numlights);
PD_BEFIELD_I16(rgfx->lightsindex);
PD_BEFIELD_PTR(rgfx->vertices);
PD_BEFIELD_PTR(rgfx->opablocks);
PD_BEFIELD_PTR(rgfx->xlublocks);
PD_BEFIELD_PTR(rgfx->colours);
Vtx *vertices = PD_PTR_BASEOFS(rgfx->vertices, data, ofs);
Vtx *vtx = vertices;
for (s32 i = 0; i < rgfx->numvertices; ++i, ++vtx) {
preprocessVtx(vtx);
}
// here's hoping that xlublocks and opablocks aren't completely separate trees
struct roomblock *blk = rgfx->blocks;
struct roomblock *end = (void *)vertices;
struct coord *tmp;
for (; blk + 1 <= end; blk++) {
PD_BEFIELD_PTR(blk->next);
switch (blk->type) {
case ROOMBLOCKTYPE_LEAF:
if (blk->gdl) {
PD_BEFIELD_PTR(blk->gdl);
preprocessGfx(PD_PTR_BASEOFS(blk->gdl, data, ofs));
}
break;
case ROOMBLOCKTYPE_PARENT:
PD_BEFIELD_PTR(blk->child);
PD_BEFIELD_PTR(blk->unk0c);
tmp = PD_PTR_BASEOFS(blk->unk0c, data, ofs);
for (s32 i = 0; i < 2; ++i) {
PD_BEFIELD_F32(tmp[i].x);
PD_BEFIELD_F32(tmp[i].y);
PD_BEFIELD_F32(tmp[i].z);
}
if ((u8 *)tmp < (u8 *)end) {
end = (void *)tmp;
}
break;
default:
break;
}
}
}
void preprocessBgLights(u8 *data, u32 ofs)
{
struct light *lbase = (void *)data;
if (!lbase) {
return;
}
for (s32 i = 0; i < g_Vars.roomcount; ++i) {
if (g_Rooms[i].numlights) {
struct light *lit = &lbase[g_Rooms[i].lightindex];
for (s32 i = 0; i < g_Rooms[i].numlights; ++i, ++lit) {
PD_BEFIELD_I16(lit->bbox->x);
PD_BEFIELD_I16(lit->bbox->y);
PD_BEFIELD_I16(lit->bbox->z);
PD_BEFIELD_I16(lit->colour); // TODO: required?
PD_BEFIELD_I16(lit->roomnum);
}
}
}
}
+417
View File
@@ -0,0 +1,417 @@
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <PR/ultratypes.h>
#include <PR/ultratypes.h>
#include "lib/rzip.h"
#include "romdata.h"
#include "fs.h"
#include "system.h"
#include "preprocess.h"
#include "platform.h"
/**
* asset files and ROM segments can be replaced by optional external files,
* but asset filenames still have to be either pulled from the ROM or from an
* external file, so stuff can't be completely custom
*
* all data is assumed to be big endian, so it has to be byteswapped
* at load time, which is fucking terrible
*/
#define ROMDATA_ROM_NAME "pd.ntsc-final.z64"
#define ROMDATA_ROM_SIZE 33554432
#define ROMDATA_ROM_HASH // TODO
#define ROMDATA_FILEDIR "files"
#define ROMDATA_SEGDIR "segs"
// for ntsc-final
#define ROMDATA_FILES_OFS 0x28080
#define ROMDATA_DATA_OFS 0x39850
#define ROMDATA_MAX_FILES 2048
u8 *g_RomFile;
u32 g_RomFileSize;
static u8 *romDataSeg;
static u32 romDataSegSize;
struct romfile {
u8 **segstart;
u8 **segend;
const char *name;
u8 *data;
u32 size;
preprocessfunc preprocess;
s32 external;
s32 preprocessed;
};
static struct romfile fileSlots[ROMDATA_MAX_FILES];
#define ROMSEG_START(n) _ ## n ## SegmentRomStart
#define ROMSEG_END(n) _ ## n ## SegmentRomEnd
/* segment table for ntsc-final */
/* size will get calculated automatically if it is 0 */
/* if there are replacement files in the data dir, they will be loaded instead */
#define ROMSEG_LIST() \
ROMSEG_DECL_SEG(fontjpnsingle, 0x194b20, 0x0, preprocessJpnFont ) \
ROMSEG_DECL_SEG(fontjpnmulti, 0x19fb40, 0x0, preprocessJpnFont ) \
ROMSEG_DECL_SEG(animations, 0x1a15c0, 0x0, preprocessAnimations ) \
ROMSEG_DECL_SEG(mpconfigs, 0x7d0a40, 0x11E0, preprocessMpConfigs ) \
ROMSEG_DECL_SEG(mpstringsE, 0x7d1c20, 0x3700, NULL ) \
ROMSEG_DECL_SEG(mpstringsJ, 0x7d5320, 0x3700, NULL ) \
ROMSEG_DECL_SEG(mpstringsP, 0x7d8a20, 0x3700, NULL ) \
ROMSEG_DECL_SEG(mpstringsG, 0x7dc120, 0x3700, NULL ) \
ROMSEG_DECL_SEG(mpstringsF, 0x7df820, 0x3700, NULL ) \
ROMSEG_DECL_SEG(mpstringsS, 0x7e2f20, 0x3700, NULL ) \
ROMSEG_DECL_SEG(mpstringsI, 0x7e6620, 0x3700, NULL ) \
ROMSEG_DECL_SEG(firingrange, 0x7e9d20, 0x1550, preprocessFiringRange ) \
ROMSEG_DECL_SEG(fonttahoma, 0x7f7860, 0x0, preprocessFont ) \
ROMSEG_DECL_SEG(fontnumeric, 0x7f8b20, 0x0, preprocessFont ) \
ROMSEG_DECL_SEG(fonthandelgothicsm, 0x7f9d30, 0x0, preprocessFont ) \
ROMSEG_DECL_SEG(fonthandelgothicxs, 0x7fbfb0, 0x0, preprocessFont ) \
ROMSEG_DECL_SEG(fonthandelgothicmd, 0x7fdd80, 0x0, preprocessFont ) \
ROMSEG_DECL_SEG(fonthandelgothiclg, 0x8008e0, 0x0, preprocessFont ) \
ROMSEG_DECL_SEG(sfxctl, 0x80a250, 0x2fb80, preprocessALBankFile ) \
ROMSEG_DECL_SEG(sfxtbl, 0x839dd0, 0x4c2160, NULL ) \
ROMSEG_DECL_SEG(seqctl, 0xcfbf30, 0xa060, preprocessALBankFile ) \
ROMSEG_DECL_SEG(seqtbl, 0xd05f90, 0x17c070, NULL ) \
ROMSEG_DECL_SEG(sequences, 0xe82000, 0x563a0, preprocessSequences ) \
ROMSEG_DECL_SEG(texturesdata, 0x1d65f40, 0x291d60, NULL ) \
ROMSEG_DECL_SEG(textureslist, 0x1ff7ca0, 0x6d80, preprocessTexturesList )
// declare the vars first
#undef ROMSEG_DECL_SEG
#define ROMSEG_DECL_SEG(name, ofs, size, preproc) u8 *ROMSEG_START(name), *ROMSEG_END(name);
ROMSEG_LIST()
// this is part of the animations seg and as such does not follow the naming convention
// these are set in preprocessAnimations
u8 *_animationsTableRomStart;
u8 *_animationsTableRomEnd;
// then build the table
#undef ROMSEG_DECL_SEG
#define ROMSEG_DECL_SEG(name, ofs, size, preproc) { &ROMSEG_START(name), &ROMSEG_END(name), #name, (u8 *)ofs, size, preproc },
static struct romfile romSegs[] = {
ROMSEG_LIST()
{ NULL, NULL, NULL, NULL, 0, NULL },
};
/* the game sets g_LoadType to the type of file it expects, */
/* so we can hijack that in fileLoad and automatically byteswap the file */
static preprocessfunc filePreprocFuncs[] = {
/* LOADTYPE_NONE */ NULL,
/* LOADTYPE_BG */ NULL, // loaded in parts
/* LOADTYPE_TILES */ preprocessTilesFile,
/* LOADTYPE_LANG */ preprocessLangFile,
/* LOADTYPE_SETUP */ preprocessSetupFile,
/* LOADTYPE_PADS */ preprocessPadsFile,
/* LOADTYPE_MODEL */ preprocessModelFile,
/* LOADTYPE_GUN */ preprocessGunFile,
};
static inline void romdataLoadRom(void)
{
g_RomFile = fsFileLoad(ROMDATA_ROM_NAME, &g_RomFileSize);
if (!g_RomFile) {
sysFatalError("Could not open ROM file " ROMDATA_ROM_NAME ".\nEnsure that it is in the data directory.");
}
if (g_RomFileSize != ROMDATA_ROM_SIZE) {
sysFatalError("Wrong ROM file size.\nExpected: %u\nGot: %u", ROMDATA_ROM_SIZE, g_RomFileSize);
}
if (memcmp(g_RomFile + 0x3b, "NPDE", 4) || memcmp(g_RomFile + 0x20, "Perfect Dark", 12)) {
sysFatalError("Wrong ROM file.\nEnsure that it is the correct NTSC v1.1 ROM in z64 format.");
}
// inflate the compressed data segment since that's where some useful stuff is
u8 *zipped = g_RomFile + ROMDATA_DATA_OFS;
if (!zipped) {
sysFatalError("Data segment not found.");
}
if (!rzipIs1173(zipped)) {
sysFatalError("Data segment is not 1173-compressed.");
}
const u32 dataSegLen = ((u32)zipped[2] << 16) | ((u32)zipped[3] << 8) | (u32)zipped[4];
if (dataSegLen < ROMDATA_FILES_OFS) {
sysFatalError("Data segment too small (%u), need at least %u.", dataSegLen, ROMDATA_FILES_OFS);
}
u8 *dataSeg = calloc(1, dataSegLen);
if (!dataSeg) {
sysFatalError("Could not allocate %u bytes for data segment.", dataSegLen);
}
u8 scratch[5 * 1024];
if (rzipInflate(zipped, dataSeg, scratch) < 0) {
free(dataSeg);
sysFatalError("Could not inflate data segment.");
}
romDataSeg = dataSeg;
romDataSegSize = dataSegLen;
}
static inline void romdataInitSegment(struct romfile *seg)
{
if (!seg->size) {
// size unknown
if (seg[1].name) {
// use next segment's base to calculate
seg->size = seg[1].data - seg->data;
} else {
// this is the last segment, calculate based on rom size
seg->size = (u8 *)g_RomFileSize - seg->data;
}
}
// check if we have an external replacement and load it if so
u8 *newData = NULL;
const s32 extFileSize = fsFileSize(seg->name);
if (extFileSize > 0) {
char tmp[FS_MAXPATH];
snprintf(tmp, sizeof(tmp), ROMDATA_SEGDIR "/%s", seg->name);
newData = fsFileLoad(tmp, &seg->size);
}
if (!newData) {
// no external data, just make it point to the rom
if (g_RomFile) {
newData = g_RomFile + (uintptr_t)seg->data;
printf("loading segment %s from ROM (offset %08x pointer %p)\n", seg->name, (u32)seg->data, newData);
fflush(stdout);
} else {
sysFatalError("No ROM or external file for segment:\n%s", seg->name);
}
} else {
// loaded external data
seg->external = 1;
printf("loading segment %s from file (pointer %p)\n", seg->name, newData);
fflush(stdout);
}
seg->data = newData;
if (seg->segstart) {
*seg->segstart = seg->data;
}
if (seg->segend) {
*seg->segend = seg->data + seg->size;
}
// call the post load function if any
if (seg->preprocess && !seg->preprocessed) {
seg->preprocess(seg->data, seg->size);
seg->preprocessed = 1;
}
}
static inline s32 romdataLoadExternalFileList(void)
{
romDataSeg = fsFileLoad("filenames.lst", &romDataSegSize); // this null terminates the file by itself
if (!romDataSeg || !romDataSegSize) {
return 0;
}
s32 n = 1;
char *p = (char *)romDataSeg;
while (*p && n < ROMDATA_MAX_FILES) {
// skip whitespace
while (*p && isspace(*p)) ++p;
if (*p) {
const char *start = p;
// skip to next whitespace or end of file
while (*p && !isspace(*p)) ++p;
// null terminate the name if needed
if (*p) {
*p++ = '\0';
}
fileSlots[n++].name = start;
}
}
return n - 1;
}
static inline void romdataInitFiles(void)
{
if (!g_RomFile) {
// no ROM; try to load the file name list from disk
if (!romdataLoadExternalFileList()) {
sysFatalError("No ROM or external file for filename table.");
}
return;
}
// the file offset table is in the data seg
const u32 *offsets = (u32 *)(romDataSeg + ROMDATA_FILES_OFS);
u32 i;
for (i = 1; offsets[i]; ++i) {
if (offsets + i + 1 < (u32 *)(romDataSeg + romDataSegSize)) {
const u32 nextofs = PD_BE32(offsets[i + 1]);
const u32 ofs = PD_BE32(offsets[i]);
fileSlots[i].data = g_RomFile + ofs;
fileSlots[i].size = nextofs - ofs;
fileSlots[i].external = 0;
fileSlots[i].preprocessed = 0;
}
}
// last offset is to the name table
const u32 *nameOffsets = (u32 *)(g_RomFile + PD_BE32(offsets[i - 1]));
for (i = 1; nameOffsets[i]; ++i) {
const u32 ofs = PD_BE32(nameOffsets[i]);
fileSlots[i].name = (const char *)nameOffsets + ofs; // ofs is relative to the start of the name table
printf("file %d name `%s` ofs %d size %u\n", i, fileSlots[i].name, fileSlots[i].data - g_RomFile, fileSlots[i].size);
}
}
static inline struct romfile *romdataGetSeg(const char *name)
{
struct romfile *seg = romSegs;
while (seg->name && strcmp(name, seg->name)) {
++seg;
}
return seg;
}
s32 romdataInit(void)
{
romdataLoadRom();
// set segments to point to the rom or load them externally
for (struct romfile *seg = romSegs; seg->name; ++seg) {
romdataInitSegment(seg);
}
// load file table from the files segment
romdataInitFiles();
printf("romdataInit: loaded rom, size = %u\n", g_RomFileSize);
fflush(stdout);
return 0;
}
s32 romdataFileGetSize(s32 fileNum)
{
if (fileNum < 1 || fileNum >= ROMDATA_MAX_FILES) {
fprintf(stderr, "romdataFileGetSize: invalid file num %d", fileNum);
return -1;
}
if (!fileSlots[fileNum].data) {
fprintf(stderr, "romdataFileGetSize: file %d is not loaded", fileNum);
return -1;
}
return fileSlots[fileNum].size;
}
u8 *romdataFileGetData(s32 fileNum)
{
if (fileNum < 1 || fileNum >= ROMDATA_MAX_FILES) {
fprintf(stderr, "romdataFileGetData: invalid file num %d", fileNum);
return NULL;
}
if (!fileSlots[fileNum].data) {
fprintf(stderr, "romdataFileGetData: file %d is not loaded, loading", fileNum);
return romdataFileLoad(fileNum, NULL);
}
return fileSlots[fileNum].data;
}
u8 *romdataFileLoad(s32 fileNum, u32 *outSize)
{
if (fileNum < 1 || fileNum >= ROMDATA_MAX_FILES) {
fprintf(stderr, "romdataFileLoad: invalid file num %d", fileNum);
return NULL;
}
u8 *out = NULL;
// try to load external file
if (!fileSlots[fileNum].external) {
char tmp[FS_MAXPATH] = { 0 };
snprintf(tmp, sizeof(tmp), ROMDATA_FILEDIR "/%s", fileSlots[fileNum].name);
if (fsFileSize(tmp) > 0) {
u32 size = 0;
out = fsFileLoad(tmp, &size);
if (out && size) {
printf("file %d (%s) loaded externally\n", fileNum, fileSlots[fileNum].name);
fileSlots[fileNum].data = out;
fileSlots[fileNum].size = size;
fileSlots[fileNum].external = 1;
}
}
}
if (!out) {
out = fileSlots[fileNum].data;
}
if (out && outSize) {
*outSize = fileSlots[fileNum].size;
}
return out;
}
void romdataFilePreprocess(s32 fileNum, s32 loadType, u8 *data, u32 size)
{
if (fileNum < 1 || fileNum >= ROMDATA_MAX_FILES) {
fprintf(stderr, "romdataFilePreprocess: invalid file num %d", fileNum);
return;
}
if (data && size /* && !fileSlots[fileNum].preprocessed*/) {
if (loadType && loadType < (u32)ARRAYCOUNT(filePreprocFuncs) && filePreprocFuncs[loadType]) {
filePreprocFuncs[loadType](data, size);
// fileSlots[fileNum].preprocessed = 1;
}
}
}
void romdataFileFree(s32 fileNum)
{
if (fileNum < 1 || fileNum >= ROMDATA_MAX_FILES) {
fprintf(stderr, "fsFileFree: invalid file num %d", fileNum);
return;
}
if (!fileSlots[fileNum].external) {
fprintf(stderr, "fsFileFree: file %d not external", fileNum);
return;
}
free(fileSlots[fileNum].data);
fileSlots[fileNum].data = NULL;
fileSlots[fileNum].external = 0;
}
u8 *romdataSegGetData(const char *segName)
{
return romdataGetSeg(segName)->data;
}
u8 *romdataSegGetDataEnd(const char *segName)
{
struct romfile *seg = romdataGetSeg(segName);
return seg->data + seg->size;
}
u32 romdataSegGetSize(const char *segName)
{
return romdataGetSeg(segName)->size;
}
+47
View File
@@ -0,0 +1,47 @@
#include <stdlib.h>
#include <stdarg.h>
#include <stdio.h>
#include <string.h>
#include <SDL.h>
#include <PR/ultratypes.h>
#include "system.h"
static u64 startTick = 0;
static u64 tickFreq = 0;
static void sysInitTicks(void)
{
tickFreq = SDL_GetPerformanceFrequency();
startTick = SDL_GetPerformanceCounter();
}
u64 sysGetTicks(void)
{
if (tickFreq == 0) {
sysInitTicks();
}
return (SDL_GetPerformanceCounter() - startTick);
}
u64 sysGetTicksPerSecond(void)
{
if (tickFreq == 0) {
sysInitTicks();
}
return tickFreq;
}
void sysFatalError(const char *fmt, ...)
{
char errmsg[2048] = { 0 };
va_list ap;
va_start(ap, fmt);
vsnprintf(errmsg, sizeof(errmsg), fmt, ap);
va_end(ap);
fprintf(stderr, "FATAL ERROR: %s\n", errmsg);
SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "Fatal error", errmsg, NULL);
exit(1);
}
+59
View File
@@ -0,0 +1,59 @@
#include <stdlib.h>
#include <stdio.h>
#include <stdbool.h>
#include <PR/ultratypes.h>
#include <PR/gbi.h>
#include "../n64-fast3d-engine/gfx_pc.h"
#include "../n64-fast3d-engine/gfx_sdl2.h"
#include "../n64-fast3d-engine/gfx_opengl.h"
static struct GfxWindowManagerAPI *wmAPI;
static struct GfxRenderingAPI *renderingAPI;
static bool initDone = false;
s32 videoInit(void)
{
wmAPI = &gfx_sdl;
renderingAPI = &gfx_opengl_api;
gfx_init(wmAPI, renderingAPI, "PD", false);
initDone = true;
return 0;
}
void videoStartFrame(void)
{
if (initDone) {
gfx_start_frame();
}
}
void videoSubmitCommands(Gfx *cmds)
{
if (initDone) {
gfx_run(cmds);
}
}
void videoEndFrame(void)
{
if (initDone) {
gfx_end_frame();
}
}
void videoClearScreen(void)
{
videoStartFrame();
// TODO: clear
videoEndFrame();
}
void *videoGetWindowHandle(void)
{
if (initDone && wmAPI) {
return wmAPI->get_window_handle();
}
return NULL;
}
+30
View File
@@ -43,6 +43,9 @@
#include "data.h"
#include "gbiex.h"
#include "types.h"
#ifndef PLATFORM_N64
#include "preprocess.h"
#endif
#define BGCMD_END 0x00
#define BGCMD_PUSH 0x01
@@ -1492,6 +1495,9 @@ void bgReset(s32 stagenum)
// Copy section 1 header to stack and parse into variables
header = (u8 *)ALIGN16((uintptr_t)headerbuffer);
bgLoadFile(header, 0, 0x40);
#ifndef PLATFORM_N64
preprocessBgSection1Header(header, 0x40);
#endif
inflatedsize = *(u32 *)&header[0];
section1compsize = *(u32 *)&header[4];
primcompsize = *(u32 *)&header[8];
@@ -1516,6 +1522,10 @@ void bgReset(s32 stagenum)
scratch += 0xc;
bgInflate((u8 *) scratch, g_BgPrimaryData, primcompsize);
#ifndef PLATFORM_N64
preprocessBgSection1(g_BgPrimaryData, 0x0f000000);
#endif
// Shrink the allocation (ie. free the scratch space)
mempRealloc(g_BgPrimaryData, inflatedsize, MEMPOOL_STAGE);
@@ -1523,6 +1533,9 @@ void bgReset(s32 stagenum)
section2start = section1compsize + 0xc;
bgLoadFile(header, section2start, 0x40);
#ifndef PLATFORM_N64
preprocessBgSection2Header(header, 0x40);
#endif
inflatedsize = (*(u16 *) &header[0] & 0x7fff) - 1;
section2compsize = *(u16 *) &header[2];
@@ -1552,6 +1565,10 @@ void bgReset(s32 stagenum)
// Iterate texture IDs and ensure they're loaded
inflatedsize = (*(u16 *) &header[0] & 0x7fff) >> 1;
#ifndef PLATFORM_N64
preprocessBgSection2((u8 *)section2, inflatedsize);
#endif
for (i = 0; i ^ inflatedsize; i++) {
texLoadFromTextureNum(section2[i] & 0xffff & 0xffff & 0xffff & 0xffff & 0xffff & 0xffff & 0xffff & 0xffff, NULL);
}
@@ -1891,6 +1908,9 @@ void bgBuildTables(s32 stagenum)
// Load and read the header
header = (u8 *)ALIGN16((uintptr_t)headerbuffer);
bgLoadFile(header, g_BgSection3, 0x40);
#ifndef PLATFORM_N64
preprocessBgSection3Header(header, 0x40);
#endif
inflatedsize = (*(u16 *)&header[0] & 0x7fff) - 1;
section3compsize = *(u16 *)&header[2];
inflatedsize = (inflatedsize | 0xf) + 1;
@@ -1909,6 +1929,9 @@ void bgBuildTables(s32 stagenum)
bgLoadFile(scratch, g_BgSection3 + 4, ((section3compsize - 1) | 0xf) + 1);
bgInflate(scratch, section3, section3compsize);
#ifndef PLATFORM_N64
preprocessBgSection3(section3, section3compsize);
#endif
// Section 3 starts with a table of room bounding boxes
bboxptr = (s16 *) section3;
@@ -1966,6 +1989,10 @@ void bgBuildTables(s32 stagenum)
numlightsptr++;
}
#ifndef PLATFORM_N64
preprocessBgLights(g_BgLightsFileData, 0);
#endif
// Free the section 3 allocation
mempRealloc(section3, 0, MEMPOOL_STAGE);
@@ -2795,6 +2822,9 @@ void bgLoadRoom(s32 roomnum)
// Inflate the data to the left side of the allocation
inflatedlen = bgInflate(memaddr, allocation, g_BgRooms[roomnum + 1].unk00 - g_BgRooms[roomnum].unk00);
#ifndef PLATFORM_N64
preprocessBgRoom(allocation, g_BgRooms[roomnum].unk00);
#endif
g_Rooms[roomnum].gfxdata = (struct roomgfxdata *)allocation;
+38 -24
View File
@@ -367,41 +367,55 @@ bool challengeIsCompletedByChrWithNumPlayersBySlot(s32 mpchrnum, s32 slot, s32 n
return false;
}
#ifdef PLATFORM_N64
#define BTYPE s32
#else
#define BTYPE uintptr_t
#endif
struct mpconfigfull *challengeLoadConfig(s32 confignum, u8 *buffer, s32 len)
{
struct mpconfigfull *mpconfig;
u8 buffer2[sizeof(struct mpstrings) + 40];
struct mpstrings *loadedstrings;
s32 bank;
BTYPE bank;
u32 language_id = langGetFileNumOffset();
#ifdef PLATFORM_N64
extern struct mpconfig _mpconfigsSegmentRomStart[];
extern struct mpstrings _mpstringsESegmentRomStart;
extern struct mpstrings _mpstringsJSegmentRomStart;
extern struct mpstrings _mpstringsPSegmentRomStart;
extern struct mpstrings _mpstringsGSegmentRomStart;
extern struct mpstrings _mpstringsFSegmentRomStart;
extern struct mpstrings _mpstringsSSegmentRomStart;
extern struct mpstrings _mpstringsISegmentRomStart;
extern struct mpstrings _mpstringsESegmentRomEnd;
extern struct mpstrings _mpstringsJSegmentRomEnd;
extern struct mpstrings _mpstringsPSegmentRomEnd;
extern struct mpstrings _mpstringsGSegmentRomEnd;
extern struct mpstrings _mpstringsFSegmentRomEnd;
extern struct mpstrings _mpstringsSSegmentRomEnd;
extern struct mpstrings _mpstringsISegmentRomEnd;
#else
extern u8 EXT_SEG _mpconfigsSegmentRomStart;
#endif
extern struct mpstrings EXT_SEG _mpstringsESegmentRomStart;
extern struct mpstrings EXT_SEG _mpstringsJSegmentRomStart;
extern struct mpstrings EXT_SEG _mpstringsPSegmentRomStart;
extern struct mpstrings EXT_SEG _mpstringsGSegmentRomStart;
extern struct mpstrings EXT_SEG _mpstringsFSegmentRomStart;
extern struct mpstrings EXT_SEG _mpstringsSSegmentRomStart;
extern struct mpstrings EXT_SEG _mpstringsISegmentRomStart;
extern struct mpstrings EXT_SEG _mpstringsESegmentRomEnd;
extern struct mpstrings EXT_SEG _mpstringsJSegmentRomEnd;
extern struct mpstrings EXT_SEG _mpstringsPSegmentRomEnd;
extern struct mpstrings EXT_SEG _mpstringsGSegmentRomEnd;
extern struct mpstrings EXT_SEG _mpstringsFSegmentRomEnd;
extern struct mpstrings EXT_SEG _mpstringsSSegmentRomEnd;
extern struct mpstrings EXT_SEG _mpstringsISegmentRomEnd;
s32 banks[][2] = {
{ (s32)&_mpstringsESegmentRomStart, (s32)&_mpstringsESegmentRomEnd },
{ (s32)&_mpstringsJSegmentRomStart, (s32)&_mpstringsJSegmentRomEnd },
{ (s32)&_mpstringsPSegmentRomStart, (s32)&_mpstringsPSegmentRomEnd },
{ (s32)&_mpstringsGSegmentRomStart, (s32)&_mpstringsGSegmentRomEnd },
{ (s32)&_mpstringsFSegmentRomStart, (s32)&_mpstringsFSegmentRomEnd },
{ (s32)&_mpstringsSSegmentRomStart, (s32)&_mpstringsSSegmentRomEnd },
{ (s32)&_mpstringsISegmentRomStart, (s32)&_mpstringsISegmentRomEnd },
BTYPE banks[][2] = {
{ (BTYPE)REF_SEG _mpstringsESegmentRomStart, (BTYPE)REF_SEG _mpstringsESegmentRomEnd },
{ (BTYPE)REF_SEG _mpstringsJSegmentRomStart, (BTYPE)REF_SEG _mpstringsJSegmentRomEnd },
{ (BTYPE)REF_SEG _mpstringsPSegmentRomStart, (BTYPE)REF_SEG _mpstringsPSegmentRomEnd },
{ (BTYPE)REF_SEG _mpstringsGSegmentRomStart, (BTYPE)REF_SEG _mpstringsGSegmentRomEnd },
{ (BTYPE)REF_SEG _mpstringsFSegmentRomStart, (BTYPE)REF_SEG _mpstringsFSegmentRomEnd },
{ (BTYPE)REF_SEG _mpstringsSSegmentRomStart, (BTYPE)REF_SEG _mpstringsSSegmentRomEnd },
{ (BTYPE)REF_SEG _mpstringsISegmentRomStart, (BTYPE)REF_SEG _mpstringsISegmentRomEnd },
};
// Load mpconfigs
mpconfig = dmaExecWithAutoAlign(buffer, (s32)&_mpconfigsSegmentRomStart[confignum], sizeof(struct mpconfig));
#ifdef PLATFORM_N64
mpconfig = dmaExecWithAutoAlign(buffer, (BTYPE)&_mpconfigsSegmentRomStart[confignum], sizeof(struct mpconfig));
#else
mpconfig = dmaExecWithAutoAlign(buffer, (BTYPE)REF_SEG _mpconfigsSegmentRomStart + confignum * sizeof(struct mpconfig), sizeof(struct mpconfig));
#endif
// Load mpstrings
bank = banks[language_id][0];
+64 -2
View File
@@ -10,6 +10,9 @@
#include "lib/rzip.h"
#include "data.h"
#include "types.h"
#ifndef PLATFORM_N64
#include "romdata.h"
#endif
/**
* This file contains functions relating to ROM asset files.
@@ -49,6 +52,14 @@
* functions that support this theory.
*/
/**
* Currently the port just takes the filename from the filename[] array and feeds it
* into its own FS API that just loads it from disk. The whole file number/slot system
* is still mostly intact as a kludge. This will probably be removed later and reworked
* to just use filenames.
*/
#ifdef PLATFORM_N64
extern void *_file_bg_sev_seg;
extern void *_file_bg_silo_seg;
extern void *_file_bg_stat_seg;
@@ -2068,7 +2079,9 @@ extern void *_file_Asaucerexp1M;
extern void *_file_PjaplogoZ;
extern void *_file_PjappdZ;
#endif
extern void *_filenamesSegmentRomStart;
#endif // PLATFORM_N64
struct fileinfo g_FileInfo[NUM_FILES];
@@ -2076,6 +2089,7 @@ struct fileinfo g_FileInfo[NUM_FILES];
u32 var800aa570;
#endif
#ifdef PLATFORM_N64
u32 g_FileTable[] = {
/*0x0000*/ 0,
/*0x0001*/ (uintptr_t) &_file_bg_sev_seg,
@@ -4099,14 +4113,22 @@ u32 g_FileTable[] = {
#endif
(uintptr_t) &_filenamesSegmentRomStart,
};
#else // PLATFORM_N64
u32 g_FileTable[NUM_FILES + 1]; // TODO: this is only used to get the filenum, remove this
#endif // PLATFORM_N64
romptr_t fileGetRomAddress(s32 filenum)
{
#ifdef PLATFORM_N64
return (romptr_t) g_FileTable[filenum];
#else
return (romptr_t) romdataFileGetData(filenum);
#endif
}
u32 fileGetRomSizeByTableAddress(u32 *filetableaddr)
{
#ifdef PLATFORM_N64
u32 size;
if (filetableaddr[1]) {
@@ -4116,6 +4138,10 @@ u32 fileGetRomSizeByTableAddress(u32 *filetableaddr)
}
return size;
#else
const s32 size = romdataFileGetSize(filetableaddr - g_FileTable);
return (size < 0) ? 0 : size;
#endif
}
s32 fileGetRomSize(s32 filenum)
@@ -4128,9 +4154,21 @@ u32 file0f166ea8(u32 *filetableaddr)
return 0;
}
void fileLoad(u8 *dst, u32 allocationlen, u32 *romaddrptr, struct fileinfo *info)
void fileLoad(u8 *dst, u32 allocationlen, romptr_t *romaddrptr, struct fileinfo *info)
{
#ifndef PLATFORM_N64
// load the file first
const s32 filenum = (u32 *)romaddrptr - g_FileTable;
u32 romsize = 0;
u8 *filedata = romdataFileLoad(filenum, &romsize);
if (!filedata) {
return;
}
romaddrptr = (romptr_t *)&filedata;
#else
u32 romsize = fileGetRomSizeByTableAddress(romaddrptr);
#endif
u8 buffer[5 * 1024];
if (allocationlen == 0) {
@@ -4167,6 +4205,12 @@ void fileLoad(u8 *dst, u32 allocationlen, u32 *romaddrptr, struct fileinfo *info
info->loadedsize = result;
}
}
#ifndef PLATFORM_N64
// byteswap/preprocess file according to g_LoadType right after inflating it
const u32 dstsize = allocationlen ? info->loadedsize : romsize;
romdataFilePreprocess(filenum, g_LoadType, dst, dstsize);
#endif
}
void filesInit(void)
@@ -4181,7 +4225,9 @@ void filesInit(void)
info->loadedsize = 0;
info->allocsize = 0;
#ifdef PLATFORM_N64
fileGetRomSizeByTableAddress((u32 *)(g_FileTable + i));
#endif
if (g_FileTable);
if (g_FileInfo);
@@ -4195,7 +4241,16 @@ void fileLoadPartToAddr(u16 filenum, void *memaddr, s32 offset, u32 len)
u32 stack[2];
if (fileGetRomSizeByTableAddress((u32 *)&g_FileTable[filenum])) {
#ifdef PLATFORM_N64
dmaExec(memaddr, (romptr_t) g_FileTable[filenum] + offset, len);
#else
const u8 *src = romdataFileGetData(filenum);
if (src) {
dmaExec(memaddr, (uintptr_t) src + offset, len);
}
// this intentionally does not execute romdataFilePreprocess,
// because bg files are loaded and inflated in parts
#endif
}
}
@@ -4207,13 +4262,17 @@ u32 fileGetInflatedSize(s32 filenum)
#if VERSION < VERSION_NTSC_1_0
char message[128];
#endif
u32 romaddr;
uintptr_t romaddr;
romaddrptr = &g_FileTable[filenum];
if (1);
#ifdef PLATFORM_N64
romaddr = *romaddrptr;
#else
romaddr = (uintptr_t)romdataFileGetData(filenum);
#endif
ptr = (u8 *) ((uintptr_t) &buffer[0x10] & ~0xf);
if (romaddr == 0) {
@@ -4272,6 +4331,9 @@ void *fileLoadToNew(s32 filenum, u32 method)
void fileRemove(s32 filenum)
{
g_FileTable[filenum] = 0;
#ifndef PLATFORM_N64
romdataFileFree(filenum);
#endif
}
void *fileLoadToAddr(s32 filenum, s32 method, u8 *ptr, u32 size)
+42 -42
View File
@@ -198,9 +198,9 @@ void text0f1531dc(bool arg0)
void textLoadFont(u8 *romstart, u8 *romend, struct font **fontptr, struct fontchar **charsptr, bool monospace)
{
extern u8 _fonthandelgothicsmSegmentRomStart;
extern u8 _fonthandelgothicxsSegmentRomStart;
extern u8 _fonthandelgothicmdSegmentRomStart;
extern u8 EXT_SEG _fonthandelgothicsmSegmentRomStart;
extern u8 EXT_SEG _fonthandelgothicxsSegmentRomStart;
extern u8 EXT_SEG _fonthandelgothicmdSegmentRomStart;
u32 len;
s32 maxwidth;
@@ -213,9 +213,9 @@ void textLoadFont(u8 *romstart, u8 *romend, struct font **fontptr, struct fontch
#if PAL
// PAL has more characters in these fonts
if (romstart == &_fonthandelgothicsmSegmentRomStart
|| romstart == &_fonthandelgothicxsSegmentRomStart
|| romstart == &_fonthandelgothicmdSegmentRomStart) {
if (romstart == REF_SEG _fonthandelgothicsmSegmentRomStart
|| romstart == REF_SEG _fonthandelgothicxsSegmentRomStart
|| romstart == REF_SEG _fonthandelgothicmdSegmentRomStart) {
numchars = 135;
}
#endif
@@ -236,7 +236,7 @@ void textLoadFont(u8 *romstart, u8 *romend, struct font **fontptr, struct fontch
}
#if VERSION >= VERSION_JPN_FINAL
if (romstart == &_fonthandelgothicsmSegmentRomStart) {
if (romstart == REF_SEG _fonthandelgothicsmSegmentRomStart) {
for (i = 0; i < NUMCHARS(); i++) {
chars[i].baseline++;
}
@@ -264,9 +264,9 @@ void textLoadFont(u8 *romstart, u8 *romend, struct font **fontptr, struct fontch
*charsptr = chars;
#if PAL
if (romstart == &_fonthandelgothicsmSegmentRomStart
|| romstart == &_fonthandelgothicxsSegmentRomStart
|| romstart == &_fonthandelgothicmdSegmentRomStart) {
if (romstart == REF_SEG _fonthandelgothicsmSegmentRomStart
|| romstart == REF_SEG _fonthandelgothicxsSegmentRomStart
|| romstart == REF_SEG _fonthandelgothicmdSegmentRomStart) {
// Increment the baseline of the pipe character.
// It is suspected that the pipe character is used as a reference to set
// the size for all other text, so changing this increases the line
@@ -278,16 +278,16 @@ void textLoadFont(u8 *romstart, u8 *romend, struct font **fontptr, struct fontch
void textReset(void)
{
extern u8 _fontbankgothicSegmentRomStart, _fontbankgothicSegmentRomEnd;
extern u8 _fontzurichSegmentRomStart, _fontzurichSegmentRomEnd;
extern u8 _fonttahomaSegmentRomStart, _fonttahomaSegmentRomEnd;
extern u8 _fontnumericSegmentRomStart, _fontnumericSegmentRomEnd;
extern u8 _fonthandelgothicsmSegmentRomStart, _fonthandelgothicsmSegmentRomEnd;
extern u8 _fonthandelgothicxsSegmentRomStart, _fonthandelgothicxsSegmentRomEnd;
extern u8 _fonthandelgothicmdSegmentRomStart, _fonthandelgothicmdSegmentRomEnd;
extern u8 _fonthandelgothiclgSegmentRomStart, _fonthandelgothiclgSegmentRomEnd;
extern u8 _fontocramdSegmentRomStart, _fontocramdSegmentRomEnd;
extern u8 _fontocralgSegmentRomStart, _fontocralgSegmentRomEnd;
extern u8 EXT_SEG _fontbankgothicSegmentRomStart, EXT_SEG _fontbankgothicSegmentRomEnd;
extern u8 EXT_SEG _fontzurichSegmentRomStart, EXT_SEG _fontzurichSegmentRomEnd;
extern u8 EXT_SEG _fonttahomaSegmentRomStart, EXT_SEG _fonttahomaSegmentRomEnd;
extern u8 EXT_SEG _fontnumericSegmentRomStart, EXT_SEG _fontnumericSegmentRomEnd;
extern u8 EXT_SEG _fonthandelgothicsmSegmentRomStart, EXT_SEG _fonthandelgothicsmSegmentRomEnd;
extern u8 EXT_SEG _fonthandelgothicxsSegmentRomStart, EXT_SEG _fonthandelgothicxsSegmentRomEnd;
extern u8 EXT_SEG _fonthandelgothicmdSegmentRomStart, EXT_SEG _fonthandelgothicmdSegmentRomEnd;
extern u8 EXT_SEG _fonthandelgothiclgSegmentRomStart, EXT_SEG _fonthandelgothiclgSegmentRomEnd;
extern u8 EXT_SEG _fontocramdSegmentRomStart, EXT_SEG _fontocramdSegmentRomEnd;
extern u8 EXT_SEG _fontocralgSegmentRomStart, EXT_SEG _fontocralgSegmentRomEnd;
var8007faec = 0;
g_FontTahoma2 = NULL;
@@ -322,17 +322,17 @@ void textReset(void)
var8007fae8 = 0;
if (g_Vars.stagenum == STAGE_TITLE) {
textLoadFont(&_fonthandelgothicsmSegmentRomStart, &_fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
textLoadFont(&_fonthandelgothicmdSegmentRomStart, &_fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
textLoadFont(&_fonthandelgothiclgSegmentRomStart, &_fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
textLoadFont(REF_SEG _fonthandelgothicsmSegmentRomStart, REF_SEG _fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
textLoadFont(REF_SEG _fonthandelgothicmdSegmentRomStart, REF_SEG _fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
textLoadFont(REF_SEG _fonthandelgothiclgSegmentRomStart, REF_SEG _fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
} else if (g_Vars.stagenum == STAGE_CREDITS) {
textLoadFont(&_fonthandelgothicxsSegmentRomStart, &_fonthandelgothicxsSegmentRomEnd, &g_FontHandelGothicXs, &g_CharsHandelGothicXs, false);
textLoadFont(&_fonthandelgothicsmSegmentRomStart, &_fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
textLoadFont(&_fonthandelgothicmdSegmentRomStart, &_fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
textLoadFont(&_fonthandelgothiclgSegmentRomStart, &_fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
textLoadFont(REF_SEG _fonthandelgothicxsSegmentRomStart, REF_SEG _fonthandelgothicxsSegmentRomEnd, &g_FontHandelGothicXs, &g_CharsHandelGothicXs, false);
textLoadFont(REF_SEG _fonthandelgothicsmSegmentRomStart, REF_SEG _fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
textLoadFont(REF_SEG _fonthandelgothicmdSegmentRomStart, REF_SEG _fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
textLoadFont(REF_SEG _fonthandelgothiclgSegmentRomStart, REF_SEG _fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
} else {
#if VERSION >= VERSION_JPN_FINAL
textLoadFont(&_fontnumericSegmentRomStart, &_fontnumericSegmentRomEnd, &g_FontNumeric, &g_CharsNumeric, false);
textLoadFont(REF_SEG _fontnumericSegmentRomStart, REF_SEG _fontnumericSegmentRomEnd, &g_FontNumeric, &g_CharsNumeric, false);
if (g_Vars.normmplayerisrunning) {
if (IS4MB()) {
@@ -347,40 +347,40 @@ void textReset(void)
}
}
textLoadFont(&_fonthandelgothicsmSegmentRomStart, &_fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
textLoadFont(REF_SEG _fonthandelgothicsmSegmentRomStart, REF_SEG _fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
if (!g_Vars.normmplayerisrunning || IS8MB()) {
textLoadFont(&_fonthandelgothicmdSegmentRomStart, &_fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
textLoadFont(REF_SEG _fonthandelgothicmdSegmentRomStart, REF_SEG _fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
}
if (g_Vars.stagenum == STAGE_TEST_OLD) {
textLoadFont(&_fonthandelgothiclgSegmentRomStart, &_fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
textLoadFont(REF_SEG _fonthandelgothiclgSegmentRomStart, REF_SEG _fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
}
textLoadFont(&_fonthandelgothicxsSegmentRomStart, &_fonthandelgothicxsSegmentRomEnd, &g_FontHandelGothicXs, &g_CharsHandelGothicXs, false);
#elif VERSION >= VERSION_PAL_BETA
textLoadFont(&_fontnumericSegmentRomStart, &_fontnumericSegmentRomEnd, &g_FontNumeric, &g_CharsNumeric, false);
textLoadFont(&_fonthandelgothicxsSegmentRomStart, &_fonthandelgothicxsSegmentRomEnd, &g_FontHandelGothicXs, &g_CharsHandelGothicXs, false);
textLoadFont(&_fonthandelgothicsmSegmentRomStart, &_fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
textLoadFont(REF_SEG _fontnumericSegmentRomStart, REF_SEG _fontnumericSegmentRomEnd, &g_FontNumeric, &g_CharsNumeric, false);
textLoadFont(REF_SEG _fonthandelgothicxsSegmentRomStart, REF_SEG _fonthandelgothicxsSegmentRomEnd, &g_FontHandelGothicXs, &g_CharsHandelGothicXs, false);
textLoadFont(REF_SEG _fonthandelgothicsmSegmentRomStart, REF_SEG _fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
if (!g_Vars.normmplayerisrunning) {
textLoadFont(&_fonthandelgothicmdSegmentRomStart, &_fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
textLoadFont(REF_SEG _fonthandelgothicmdSegmentRomStart, REF_SEG _fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
}
if (g_Vars.stagenum == STAGE_TEST_OLD) {
textLoadFont(&_fonthandelgothiclgSegmentRomStart, &_fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
textLoadFont(REF_SEG _fonthandelgothiclgSegmentRomStart, REF_SEG _fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
}
#else
// This unused GE font exists in NTSC but was removed in the PAL version
textLoadFont(&_fonttahomaSegmentRomStart, &_fonttahomaSegmentRomEnd, &g_FontTahoma2, &g_FontTahoma1, false);
textLoadFont(REF_SEG _fonttahomaSegmentRomStart, &_fonttahomaSegmentRomEnd, &g_FontTahoma2, &g_FontTahoma1, false);
textLoadFont(&_fontnumericSegmentRomStart, &_fontnumericSegmentRomEnd, &g_FontNumeric, &g_CharsNumeric, false);
textLoadFont(&_fonthandelgothicxsSegmentRomStart, &_fonthandelgothicxsSegmentRomEnd, &g_FontHandelGothicXs, &g_CharsHandelGothicXs, false);
textLoadFont(&_fonthandelgothicsmSegmentRomStart, &_fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
textLoadFont(&_fonthandelgothicmdSegmentRomStart, &_fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
textLoadFont(REF_SEG _fontnumericSegmentRomStart, REF_SEG _fontnumericSegmentRomEnd, &g_FontNumeric, &g_CharsNumeric, false);
textLoadFont(REF_SEG _fonthandelgothicxsSegmentRomStart, REF_SEG _fonthandelgothicxsSegmentRomEnd, &g_FontHandelGothicXs, &g_CharsHandelGothicXs, false);
textLoadFont(REF_SEG _fonthandelgothicsmSegmentRomStart, REF_SEG _fonthandelgothicsmSegmentRomEnd, &g_FontHandelGothicSm, &g_CharsHandelGothicSm, false);
textLoadFont(REF_SEG _fonthandelgothicmdSegmentRomStart, REF_SEG _fonthandelgothicmdSegmentRomEnd, &g_FontHandelGothicMd, &g_CharsHandelGothicMd, false);
if (g_Vars.stagenum == STAGE_TEST_OLD) {
textLoadFont(&_fonthandelgothiclgSegmentRomStart, &_fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
textLoadFont(REF_SEG _fonthandelgothiclgSegmentRomStart, REF_SEG _fonthandelgothiclgSegmentRomEnd, &g_FontHandelGothicLg, &g_CharsHandelGothicLg, false);
}
#endif
}
+9 -5
View File
@@ -38,6 +38,8 @@ u32 var80062494 = 0x00000001;
s32 var80062498 = 0;
u32 var8006249c = 0x00000000;
#ifdef PLATFORM_N64
extern u8 var020043f8;
extern u8 var02004468;
extern u8 var02004700;
@@ -138,13 +140,13 @@ Gfx *getitle0f0155f0(Gfx *gdl, s32 arg1, u8 arg2)
return gdl;
}
extern u8 _getitleSegmentRomStart;
extern u8 _getitleSegmentStart;
extern u8 _getitleSegmentEnd;
extern u8 EXT_SEG _getitleSegmentRomStart;
extern u8 EXT_SEG _getitleSegmentStart;
extern u8 EXT_SEG _getitleSegmentEnd;
void getitleLoad(void *addr, u32 arg1)
{
u32 len = (romptr_t)&_getitleSegmentEnd - (romptr_t)&_getitleSegmentStart;
u32 len = (romptr_t) REF_SEG _getitleSegmentEnd - (romptr_t) REF_SEG _getitleSegmentStart;
var80062414 = 0;
var8009cc8c = 880;
@@ -152,7 +154,7 @@ void getitleLoad(void *addr, u32 arg1)
var80062498 = 0;
var8009cc90 = addr;
dmaExec(var8009cc90, (romptr_t) &_getitleSegmentRomStart, ALIGN64(len));
dmaExec(var8009cc90, (romptr_t) REF_SEG _getitleSegmentRomStart, ALIGN64(len));
}
Gfx *getitleRender(Gfx *gdl)
@@ -211,3 +213,5 @@ bool getitle0f0160e8(void)
{
return (var80062414 ^ 2) == 0;
}
#endif // PLATFORM_N64
+4
View File
@@ -106,7 +106,11 @@ s32 hudmsgIsZoomRangeVisible(void)
* with the return type we need, and link it to the same address as viGetHeight
* via the linker config.
*/
#ifdef PLATFORM_N64
extern s32 viGetHeight_hack(void);
#else
#define viGetHeight_hack viGetHeight
#endif
Gfx *hudmsgRenderMissionTimer(Gfx *gdl, u32 alpha)
{
+5 -4
View File
@@ -9,6 +9,7 @@
#include "lib/main.h"
#include "data.h"
#include "types.h"
#include "platform.h"
/**
* Officially, the NTSC versions are American English only, while the PAL
@@ -213,9 +214,9 @@ u32 langGetLangBankIndexFromStagenum(s32 stagenum)
return bank;
}
extern u8 _fontjpnSegmentRomStart;
extern u8 _fontjpnsingleSegmentRomStart;
extern u8 _fontjpnmultiSegmentRomStart;
extern u8 EXT_SEG _fontjpnSegmentRomStart;
extern u8 EXT_SEG _fontjpnsingleSegmentRomStart;
extern u8 EXT_SEG _fontjpnmultiSegmentRomStart;
struct jpncharpixels *langGetJpnCharPixels(s32 codepoint)
{
@@ -403,7 +404,7 @@ char *langGet(s32 textid)
u32 addr;
if (bank && bank[textindex]) {
addr = (uintptr_t)bank + bank[textindex];
addr = (uintptr_t)bank + PD_BE32(bank[textindex]);
} else {
addr = 0;
}
+7 -3
View File
@@ -4237,7 +4237,11 @@ void ammocrateTick(struct prop *prop)
* function with the third argument and link it to the same address as
* nbombCreateStorm via the linker config.
*/
#ifdef PLATFORM_N64
void nbombCreateStorm_hack(struct coord *pos, struct prop *ownerprop, struct prop *nbombprop);
#else
#define nbombCreateStorm_hack(x, y, z) nbombCreateStorm(x, y)
#endif
/**
* Handles the following:
@@ -14251,7 +14255,7 @@ void objApplyMomentum(struct defaultobj *obj, struct coord *speed, f32 rotation,
}
#if PIRACYCHECKS
extern u8 _blankSegmentRomStart;
extern u8 EXT_SEG _blankSegmentRomStart;
/**
* This function is called whenever a player exits a lift as well as on tick
@@ -14294,7 +14298,7 @@ void piracyRestore(void)
}
// Copy the writeaddr/copylen pairs from ROM to the buffer
dmaExec(ptr, (romptr_t) &_blankSegmentRomStart, 0x40);
dmaExec(ptr, (romptr_t) REF_SEG _blankSegmentRomStart, 0x40);
// Calculate what needs to be copied and where
i = 0;
@@ -14312,7 +14316,7 @@ void piracyRestore(void)
// Copy it
if (copylen != 0) {
dmaExec((void *) writeaddr, (romptr_t) &_blankSegmentRomStart + readoffset, copylen);
dmaExec((void *) writeaddr, (romptr_t) REF_SEG _blankSegmentRomStart + readoffset, copylen);
}
// Increment the index, so the next time the function is called
+8 -3
View File
@@ -2084,7 +2084,7 @@ void texLoadFromDisplayList(Gfx *gdl, struct texpool *pool, s32 arg2)
}
}
extern u8 _texturesdataSegmentRomStart;
extern u8 EXT_SEG _texturesdataSegmentRomStart;
/**
* Load and decompress a texture from ROM.
@@ -2179,7 +2179,7 @@ void texLoad(s32 *updateword, struct texpool *pool, bool arg2)
// Copy the compressed texture to RAM
dmaExec(alignedcompbuffer,
(romptr_t) &_texturesdataSegmentRomStart + (thisoffset & 0xfffffff8),
(romptr_t) REF_SEG _texturesdataSegmentRomStart + (thisoffset & 0xfffffff8),
((u32) (nextoffset - thisoffset) + 0x1f) >> 4 << 4);
compptr = (u8 *) alignedcompbuffer + (thisoffset & 7);
@@ -2263,7 +2263,12 @@ void texLoad(s32 *updateword, struct texpool *pool, bool arg2)
pool->rightpos->next = 0;
if (tail != NULL) {
tail->next = (uintptr_t) pool->rightpos & 0xffffff;
tail->next = (uintptr_t) pool->rightpos
#ifdef PLATFORM_N64
& 0xffffff;
#else
;
#endif
} else {
pool->head = pool->rightpos;
}
+4 -4
View File
@@ -8,12 +8,12 @@
void texInit(void)
{
extern u8 _textureslistSegmentRomStart;
extern u8 _textureslistSegmentRomEnd;
extern u8 EXT_SEG _textureslistSegmentRomStart;
extern u8 EXT_SEG _textureslistSegmentRomEnd;
u32 len = ((&_textureslistSegmentRomEnd - &_textureslistSegmentRomStart) + 15) & -16;
u32 len = ((REF_SEG _textureslistSegmentRomEnd - REF_SEG _textureslistSegmentRomStart) + 15) & -16;
g_Textures = mempAlloc(len, MEMPOOL_PERMANENT);
dmaExec(g_Textures, (romptr_t) &_textureslistSegmentRomStart, len);
dmaExec(g_Textures, (romptr_t) REF_SEG _textureslistSegmentRomStart, len);
}
+15 -4
View File
@@ -37,20 +37,26 @@ extern Gfx *g_TexGdl3;
extern struct textureconfig *g_TexRedLinesConfigs;
extern struct textureconfig *g_TexGroup11Configs;
extern u8 _textureconfigSegmentRomStart;
extern u8 _textureconfigSegmentStart;
extern u8 _textureconfigSegmentEnd;
extern u8 EXT_SEG _textureconfigSegmentRomStart;
extern u8 EXT_SEG _textureconfigSegmentStart;
extern u8 EXT_SEG _textureconfigSegmentEnd;
void texReset(void)
{
s32 stage;
#ifdef PLATFORM_N64
u32 len = &_textureconfigSegmentEnd - &_textureconfigSegmentStart;
#endif
s32 i;
#ifdef PLATFORM_N64
g_TextureConfigSegment = mempAlloc(len, MEMPOOL_STAGE);
dmaExec(g_TextureConfigSegment, (romptr_t)&_textureconfigSegmentRomStart, len);
g_TexBase = (uintptr_t)g_TextureConfigSegment - ROM_SIZE * 1024 * 1024;
#else
g_TexBase = 0;
#endif
g_TexGdl1 = (Gfx *)(g_TexBase + (uintptr_t)g_TcGdl1);
g_TexGdl2 = (Gfx *)(g_TexBase + (uintptr_t)g_TcGdl2);
g_TexGdl3 = (Gfx *)(g_TexBase + (uintptr_t)g_TcGdl3);
@@ -72,7 +78,12 @@ void texReset(void)
g_TexGeneralConfigs = (struct textureconfig *)(g_TexBase + (uintptr_t)g_TcGeneralConfigs);
g_TexRadarConfigs = (struct textureconfig *)(g_TexBase + (uintptr_t)g_TcRadarConfigs);
#ifdef PLATFORM_N64
g_TexNumConfigs = (len - (uintptr_t)&g_TcWallhitConfigs + ROM_SIZE * 1024 * 1024) / sizeof(struct textureconfig);
#else
// TODO: load this shit externally for fuck's sake
g_TexNumConfigs = 18 + 5 + 6 + 2 + 96 + 3 + 6 + 10 + 1 + 56 + 1;
#endif
g_TexWords = mempAlloc(ALIGN16(g_TexNumConfigs * 4), MEMPOOL_STAGE);
for (i = 0; i < g_TexNumConfigs; i++) {
+8
View File
@@ -4,6 +4,14 @@
#include "constants.h"
#include "types.h"
#ifdef PLATFORM_N64
#define EXT_SEG
#define REF_SEG &
#else
#define EXT_SEG *
#define REF_SEG
#endif
#define bool s32
#define ubool u32
+4 -4
View File
@@ -5,11 +5,11 @@
#include "types.h"
void dmaInit(void);
void dmaStart(void *memaddr, u32 romaddr, u32 len, bool priority);
void dmaStart(void *memaddr, romptr_t romaddr, u32 len, bool priority);
void dmaCheckPiracy(void *memaddr, u32 len);
void dmaWait(void);
void dmaExec(void *memaddr, u32 romaddr, u32 len);
void dmaExecHighPriority(void *memaddr, u32 romaddr, u32 len);
void *dmaExecWithAutoAlign(void *memaddr, u32 romaddr, u32 len);
void dmaExec(void *memaddr, romptr_t romaddr, u32 len);
void dmaExecHighPriority(void *memaddr, romptr_t romaddr, u32 len);
void *dmaExecWithAutoAlign(void *memaddr, romptr_t romaddr, u32 len);
#endif
+2
View File
@@ -23,5 +23,7 @@ void schedIncrementFrontArtifacts(void);
void schedUpdatePendingArtifacts(void);
void schedConsiderScreenshot(void);
void schedSetCrashedUnexpectedly(bool enable);
void schedStartFrame(OSSched *sc);
void schedEndFrame(OSSched *sc);
#endif
+5
View File
@@ -4,6 +4,7 @@
#include "data.h"
#include "types.h"
#ifdef PLATFORM_N64
char *strcpy(char *dst, const char *src);
char *strncpy(char *dst, const char *src, s32 len);
char *strcat(char *dst, const char *src);
@@ -14,5 +15,9 @@ s32 isdigit(char c);
s32 isalpha(char c);
s32 isspace(char c);
s32 strtol(const char *src, const char **endptr, s32 base);
#else
#include <string.h>
#include <ctype.h>
#endif
#endif
+7
View File
@@ -1,6 +1,13 @@
#ifndef IN_MATH_H
#define IN_MATH_H
#ifndef PLATFORM_N64
#include_next <math.h>
#undef M_PI
#undef M_TAU
#undef errno // fuck off
#endif
// @bug?
#define M_BADPI 3.141092641f
#define M_PI 3.141592741f
+75
View File
@@ -0,0 +1,75 @@
#ifndef _IN_PLATFORM_H
#define _IN_PLATFORM_H
// detect OS
#if defined(_WIN32)
#define PLATFORM_WIN32 1
#else
// assume POSIX compatible
#define PLATFORM_POSIX 1
#if defined(__linux__)
#define PLATFORM_LINUX 1
#else // TODO
#error "Unknown platform."
#endif
#endif
// detect arch
#if defined(__x86_64__) || defined(_M_X64)
#define PLATFORM_X86_64 1
#define PLATFORM_64BIT 1
#elif defined(__i386__) || defined(_X86_) || defined(_M_IX86)
#define PLATFORM_X86 1
#else // TODO
#error "Unknown CPU arch."
#endif
// detect endianness
#if defined(__BYTE_ORDER__) && defined(__ORDER_BIG_ENDIAN__)
#if __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__
#define PLATFORM_BIG_ENDIAN 1
#else
#define PLATFORM_LITTLE_ENDIAN 1
#endif
#elif __BIG_ENDIAN__
#define PLATFORM_BIG_ENDIAN 1
#else
#error "Could not determine endianness."
#endif
// byteswap macros
#ifdef __GNUC__
#define PD_BSWAP16(x) __builtin_bswap16(x)
#define PD_BSWAP32(x) __builtin_bswap32(x)
#define PD_BSWAP64(x) __builtin_bswap64(x)
#else
#error "Implement PD_BSWAP macros for your compiler."
#endif
#ifdef PLATFORM_BIG_ENDIAN
#define PD_BE16(x) (x)
#define PD_BE32(x) (x)
#define PD_BE64(x) (x)
#define PD_LE16(x) PD_BSWAP16(x)
#define PD_LE32(x) PD_BSWAP32(x)
#define PD_LE64(x) PD_BSWAP64(x)
#else
#define PD_BE16(x) PD_BSWAP16(x)
#define PD_BE32(x) PD_BSWAP32(x)
#define PD_BE64(x) PD_BSWAP64(x)
#define PD_LE16(x) (x)
#define PD_LE32(x) (x)
#define PD_LE64(x) (x)
#endif
// TODO: use uintptr_t or something
#ifdef PLATFORM_64BIT
#define PD_BEPTR(x) PD_BE64(x)
#define PD_LEPTR(x) PD_LE64(x)
#else
#define PD_BEPTR(x) PD_BE32(x)
#define PD_LEPTR(x) PD_LE32(x)
#endif
#endif
+2 -2
View File
@@ -1,5 +1,5 @@
#ifndef STDARG_H
#define STDARG_H
#ifndef N64_STDARG_H
#define N64_STDARG_H
// When not building with IDO, use the builtin vaarg macros for portability.
#ifndef __sgi
+13 -3
View File
@@ -1,5 +1,12 @@
#ifndef __STDLIB_H__
#define __STDLIB_H__
#ifndef __N64_STDLIB_H__
#define __N64_STDLIB_H__
#ifndef PLATFORM_N64
#include_next <stdlib.h>
#undef errno // fuck off
#else // PLATFORM_N64
#ifndef NULL
#define NULL 0
@@ -18,4 +25,7 @@ typedef struct ldiv_t
lldiv_t lldiv(long long num, long long denom);
ldiv_t ldiv(long num, long denom);
#endif /* !__STDLIB_H__ */
#endif // PLATFORM_N64
#endif /* !__N64_STDLIB_H__ */
+14 -3
View File
@@ -1,5 +1,8 @@
#ifndef __STRING_H__
#define __STRING_H__
#ifndef __N64_STRING_H__
#define __N64_STRING_H__
#ifdef PLATFORM_N64
#ifdef __cplusplus
extern "C" {
#endif
@@ -52,4 +55,12 @@ extern size_t strlen(const char *);
#ifdef __cplusplus
}
#endif
#endif /* !__STRING_H__ */
#else
#include_next <string.h>
#undef errno // fuck off
#endif
#endif /* !__N64_STRING_H__ */
+11
View File
@@ -11,9 +11,16 @@
#define bool s32
#define ubool u32
#ifdef PLATFORM_N64
#define intptr_t s32
#define uintptr_t u32
#define romptr_t u32
#else
#include <stdint.h>
#undef errno // fuck off
#define romptr_t uintptr_t
#endif
typedef s32 PakErr1;
typedef s32 PakErr2;
@@ -6239,7 +6246,11 @@ struct tex {
/*0x0c*/ u32 lutmodeindex : 2;
/*0x0c*/ u32 unk0c_02 : 1;
/*0x0c*/ u32 unk0c_03 : 1;
#ifdef PLATFORM_N64
/*0x0c*/ u32 next : 24;
#else
/*0x0c*/ uintptr_t next;
#endif
};
struct texcacheitem {
+6 -6
View File
@@ -39,17 +39,17 @@ s32 g_AnimMaxHeaderLength = 608;
bool g_AnimHostEnabled = false;
u8 *g_AnimHostSegment = NULL;
extern u8 _animationsTableRomStart;
extern u8 _animationsTableRomEnd;
extern u8 EXT_SEG _animationsTableRomStart;
extern u8 EXT_SEG _animationsTableRomEnd;
void animsInit(void)
{
s32 i;
u32 *ptr;
u32 tablelen = ALIGN64(&_animationsTableRomEnd - &_animationsTableRomStart);
u32 tablelen = ALIGN64(REF_SEG _animationsTableRomEnd - REF_SEG _animationsTableRomStart);
ptr = mempAlloc(tablelen, MEMPOOL_PERMANENT);
dmaExec(ptr, (romptr_t) &_animationsTableRomStart, tablelen);
dmaExec(ptr, (romptr_t) REF_SEG _animationsTableRomStart, tablelen);
g_NumAnimations = g_NumRomAnimations = ptr[0];
g_Anims = g_RomAnims = (struct animtableentry *)&ptr[1];
@@ -131,7 +131,7 @@ s32 animGetNumAnimations(void)
return g_NumAnimations;
}
extern u8 _animationsSegmentRomStart;
extern u8 EXT_SEG _animationsSegmentRomStart;
u8 *animDma(u8 *dst, u32 segoffset, u32 len)
{
@@ -140,7 +140,7 @@ u8 *animDma(u8 *dst, u32 segoffset, u32 len)
return dst;
}
return dmaExecWithAutoAlign(dst, (romptr_t) &_animationsSegmentRomStart + segoffset, len);
return dmaExecWithAutoAlign(dst, (romptr_t) REF_SEG _animationsSegmentRomStart + segoffset, len);
}
/**
+2
View File
@@ -283,12 +283,14 @@ void amgrHandleFrameMsg(AudioInfo *info, AudioInfo *previnfo)
g_AmgrCurrentCmdList->flags = OS_SC_NEEDS_RSP;
g_AmgrCurrentCmdList->list.t.type = M_AUDTASK;
g_AmgrCurrentCmdList->list.t.flags = 0;
#ifdef PLATFORM_N64
g_AmgrCurrentCmdList->list.t.ucode_boot = (u64 *) &rspbootTextStart;
g_AmgrCurrentCmdList->list.t.ucode_boot_size = (uintptr_t) &rspbootTextEnd - (uintptr_t) &rspbootTextStart;
g_AmgrCurrentCmdList->list.t.ucode = (u64 *) &aspTextStart;
g_AmgrCurrentCmdList->list.t.ucode_data = (u64 *) &aspDataStart;
g_AmgrCurrentCmdList->list.t.ucode_size = SP_UCODE_SIZE;
g_AmgrCurrentCmdList->list.t.ucode_data_size = SP_UCODE_DATA_SIZE;
#endif
g_AmgrCurrentCmdList->list.t.data_ptr = (u64 *) datastart;
g_AmgrCurrentCmdList->list.t.data_size = (cmd - datastart) * sizeof(Acmd);
g_AmgrCurrentCmdList->list.t.yield_data_ptr = NULL;
+10 -4
View File
@@ -28,8 +28,9 @@ void dmaInit(void)
osCreateMesgQueue(&g_DmaMesgQueue, g_DmaMesgs, ARRAYCOUNT(g_DmaMesgs));
}
void dmaStart(void *memaddr, u32 romaddr, u32 len, bool priority)
void dmaStart(void *memaddr, romptr_t romaddr, u32 len, bool priority)
{
#ifdef PLATFORM_N64
u32 numiterations;
u32 remainder;
s32 i;
@@ -73,6 +74,9 @@ void dmaStart(void *memaddr, u32 romaddr, u32 len, bool priority)
osPiStartDma(&g_DmaIoMsgs[i], priority, 0, romaddr, memaddr, remainder, &g_DmaMesgQueue);
}
#else // PLATFORM_N64
bcopy((const void *)romaddr, memaddr, len);
#endif // PLATFORM_N64
}
#if VERSION >= VERSION_NTSC_1_0
@@ -121,6 +125,7 @@ void dmaCheckPiracy(void *memaddr, u32 len)
void dmaWait(void)
{
#ifdef PLATFORM_N64
u32 stack;
OSIoMesg *msg;
s32 i;
@@ -137,9 +142,10 @@ void dmaWait(void)
g_DmaSlotsBusy[i] = false;
g_DmaNumSlotsBusy--;
}
#endif
}
void dmaExec(void *memaddr, u32 romaddr, u32 len)
void dmaExec(void *memaddr, romptr_t romaddr, u32 len)
{
dmaStart(memaddr, romaddr, len, false);
dmaWait();
@@ -148,7 +154,7 @@ void dmaExec(void *memaddr, u32 romaddr, u32 len)
#endif
}
void dmaExecHighPriority(void *memaddr, u32 romaddr, u32 len)
void dmaExecHighPriority(void *memaddr, romptr_t romaddr, u32 len)
{
dmaStart(memaddr, romaddr, len, true);
dmaWait();
@@ -172,7 +178,7 @@ void dmaExecHighPriority(void *memaddr, u32 romaddr, u32 len)
* If a length of zero is passed, no DMA is done. This can be used to retrieve
* the memory address that would have been returned.
*/
void *dmaExecWithAutoAlign(void *memaddr, u32 romaddr, u32 len)
void *dmaExecWithAutoAlign(void *memaddr, romptr_t romaddr, u32 len)
{
u32 alignedrom = ALIGN2(romaddr);
u32 alignedmem = ALIGN16((uintptr_t) memaddr);
+8 -8
View File
@@ -305,11 +305,11 @@ Gfx var8005dcf0[] = {
s32 g_MainIsBooting = 1;
extern u8 _accessingpakSegmentRomStart;
extern u8 _accessingpakSegmentRomEnd;
extern u8 _copyrightSegmentRomStart;
extern u8 _copyrightSegmentRomEnd;
extern u8 _bssSegmentEnd;
extern u8 EXT_SEG _accessingpakSegmentRomStart;
extern u8 EXT_SEG _accessingpakSegmentRomEnd;
extern u8 EXT_SEG _copyrightSegmentRomStart;
extern u8 EXT_SEG _copyrightSegmentRomEnd;
extern u8 EXT_SEG _bssSegmentEnd;
/**
* Initialise various subsystems, display the copyright or accessing pak texture,
@@ -429,9 +429,9 @@ void mainInit(void)
// DMA the compressed texture from the ROM to the framebuffer.
// It's using the framebuffer as a temporary data buffer.
if (g_DoBootPakMenu) {
dmaExec(fb, (romptr_t) &_accessingpakSegmentRomStart, &_accessingpakSegmentRomEnd - &_accessingpakSegmentRomStart);
dmaExec(fb, (romptr_t) REF_SEG _accessingpakSegmentRomStart, REF_SEG _accessingpakSegmentRomEnd - REF_SEG _accessingpakSegmentRomStart);
} else {
dmaExec(fb, (romptr_t) &_copyrightSegmentRomStart, &_copyrightSegmentRomEnd - &_copyrightSegmentRomStart);
dmaExec(fb, (romptr_t) REF_SEG _copyrightSegmentRomStart, REF_SEG _copyrightSegmentRomEnd - REF_SEG _copyrightSegmentRomStart);
}
// This is required for a match
@@ -630,7 +630,7 @@ void mainInit(void)
argSetString(" -ml0 -me0 -mgfx100 -mvtx50 -mt700 -ma400");
}
start = (u8 *) PHYS_TO_K0(osVirtualToPhysical(&_bssSegmentEnd));
start = (u8 *) PHYS_TO_K0(osVirtualToPhysical(REF_SEG _bssSegmentEnd));
if (g_VmMarker);
mempSetHeap(start, g_VmMarker - start);
+21
View File
@@ -43,6 +43,11 @@
* memp memory is to load a new stage which wipes the stage pool.
*/
#ifndef PLATFORM_N64
// TODO: set this in a config or something
#define MEMP_EXPANSION_POOL_SIZE (8 * 1024 * 1024)
#endif
struct memorypool {
/*0x00*/ u8 *start;
/*0x04*/ u8 *leftpos;
@@ -82,6 +87,15 @@ void mempSetHeap(u8 *heapstart, u32 heaplen)
g_MempExpansionPools[i].prevallocation = 0;
}
#ifndef PLATFORM_N64
// separate the heap space into onboard and expansion
u32 expansionlen = 0;
if (heaplen > MEMP_EXPANSION_POOL_SIZE) {
heaplen -= MEMP_EXPANSION_POOL_SIZE;
expansionlen = MEMP_EXPANSION_POOL_SIZE;
}
#endif
g_MempOnboardPools[MEMPOOL_0].start = heapstart;
g_MempOnboardPools[MEMPOOL_0].rightpos = heapstart + heaplen;
g_MempOnboardPools[MEMPOOL_PERMANENT].start = heapstart;
@@ -89,6 +103,7 @@ void mempSetHeap(u8 *heapstart, u32 heaplen)
g_MempOnboardPools[MEMPOOL_STAGE].start = heapstart;
g_MempOnboardPools[MEMPOOL_STAGE].rightpos = heapstart + heaplen;
#ifdef PLATFORM_N64
// If 8MB, reserve the entire expansion pak for the stage pool
#if VERSION >= VERSION_NTSC_1_0
extraend = (u8 *) K0BASE + bootGetMemSize();
@@ -105,6 +120,12 @@ void mempSetHeap(u8 *heapstart, u32 heaplen)
g_MempExpansionPools[MEMPOOL_STAGE].start = (u8 *) K0BASE + 4 * 1024 * 1024;
g_MempExpansionPools[MEMPOOL_STAGE].rightpos = extraend;
}
#else
if (expansionlen) {
g_MempExpansionPools[MEMPOOL_STAGE].start = heapstart + heaplen;
g_MempExpansionPools[MEMPOOL_STAGE].rightpos = heapstart + heaplen + expansionlen;
}
#endif
for (i = 0; i < ARRAYCOUNT(g_MempOnboardPools); i++) {
g_MempOnboardPools[i].end = g_MempOnboardPools[i].rightpos;
+28
View File
@@ -0,0 +1,28 @@
#include <ultra64.h>
#include "internal.h"
#include "mp3.h"
s32 mp3utilGetBits(u8 *buffer, s32 *count, s32 numbits)
{
return 0;
}
s32 mp3util000462f8(u8 *arg0, s32 *arg1, s32 arg2, s32 arg3, s32 arg4, s32 arg5, s16 **arg6, u8 **arg7)
{
return 0;
}
s32 mp3util000464a8(u8 *arg0, s32 *arg1, s32 arg2, s32 arg3, s32 arg4, s16 **arg5, u8 **arg6)
{
return 0;
}
void func00046650(struct asistream_4f64 *arg0, s32 arg1, struct asistream_4f64 *arg2, struct asistream_4f64 *arg3, void *arg4)
{
}
void func00047550(struct asistream_4f64 *arg0, s32 arg1, struct asistream_4f64 *arg2, struct asistream_4f64 *arg3)
{
}
+4
View File
@@ -298,6 +298,7 @@ void mtx00015f88(f32 mult, Mtxf *mtx)
u32 mtxGetObfuscatedRomBase(void)
{
#ifdef PLATFORM_N64
u32 value;
osRecvMesg(&__osPiAccessQueue, NULL, OS_MESG_BLOCK * 0x10000);
@@ -312,6 +313,9 @@ u32 mtxGetObfuscatedRomBase(void)
osSendMesg(&__osPiAccessQueue, 0, 0);
return value;
#else
return 0;
#endif
}
void mtxF2L(Mtxf *src, Mtxf *dst)
+2
View File
@@ -83,6 +83,7 @@ void rdpCreateTask(Gfx *gdlstart, Gfx *gdlend, u32 arg2, s32 msg)
sctask = &g_RdpCurTask->sctask;
task = &sctask->list;
#ifdef PLATFORM_N64
task->t.ucode_boot = (u64 *) rspbootTextStart;
task->t.ucode_boot_size = (uintptr_t) rspbootTextEnd - (uintptr_t) rspbootTextStart;
@@ -90,6 +91,7 @@ void rdpCreateTask(Gfx *gdlstart, Gfx *gdlend, u32 arg2, s32 msg)
task->t.ucode = (u64 *) &gspTextStart;
task->t.ucode_data = (u64 *) &gspDataStart;
#endif
task->t.output_buff = (u64 *)g_RdpOutBufferStart;
task->t.output_buff_size = (u64 *)g_RdpOutBufferEnd;
task->t.data_ptr = (u64 *) gdlstart;
+12
View File
@@ -1,3 +1,4 @@
#ifdef PLATFORM_N64
#include <ultra64.h>
#include <stdarg.h>
#include "constants.h"
@@ -6,6 +7,11 @@
#include "lib/libc/xprintf.h"
#include "data.h"
#include "types.h"
#else
#include <stdio.h>
#include <stdarg.h>
#include "types.h"
#endif
void rmonproc()
{
@@ -69,5 +75,11 @@ void rmonPrintf(const char *format, ...)
va_list ap;
va_start(ap, format);
#ifdef PLATFORM_N64
_Printf(rmonProut, NULL, format, ap);
#else
fprintf(stderr, "rmonPrintf: ");
vfprintf(stderr, format, ap);
va_end(ap);
#endif
}
+100
View File
@@ -0,0 +1,100 @@
// see https://github.com/n64decomp/007/blob/master/tools/mktex/src/libpdtex/reader.c
// and https://github.com/doomhack/perfect_dark/blob/master/src/lib/rzip.c
#include <zlib.h>
// OSContPad has a field called errno because fuck you
#undef errno
#include "lib/rzip.h"
void *var80091558; // g_RzipUnused
bool rzipIs1172(void *buffer)
{
const u8* src = buffer;
return (src[0] == 0x11 && src[1] == 0x72);
}
bool rzipIs1173(void *buffer)
{
const u8* src = buffer;
return (src[0] == 0x11 && src[1] == 0x73);
}
static inline s32 rzipInflate1172(z_stream *strm, u8 *src, void *dst)
{
strm->avail_in = 0x2000;
strm->next_in = src;
do {
strm->avail_out = 0x2000;
strm->next_out = dst;
if (inflate(strm, Z_FINISH) == Z_STREAM_ERROR) {
rmonPrintf("rzipInflate1172: Z_STREAM_ERROR\n");
return 0;
}
} while (strm->avail_out == 0);
return strm->total_out;
}
static inline s32 rzipInflate1173(z_stream *strm, u8 *src, void *dst, u32 dstLen)
{
strm->avail_in = -1; // compressed size unknown
strm->next_in = src;
strm->avail_out = dstLen;
strm->next_out = dst;
if (inflate(strm, Z_SYNC_FLUSH) == Z_STREAM_ERROR) {
rmonPrintf("rzipInflate1173: Z_STREAM_ERROR\n");
return 0;
}
return strm->total_out;
}
s32 rzipInflate(void *srcp, void *dst, void *scratch)
{
s32 ret = 0;
u8 *src = srcp;
z_stream strm = { 0 };
ret = inflateInit2(&strm, -15);
if (ret != Z_OK) {
rmonPrintf("rzipInflate: inflateInit2 failed: %d\n", ret);
return 0;
}
if (rzipIs1173(src)) {
// 1173, we know the uncompressed length
const u32 dstLen = ((u32)src[2] << 16) | ((u32)src[3] << 8) | (u32)src[4];
ret = rzipInflate1173(&strm, src + 5, dst, dstLen);
} else if (rzipIs1172(src)) {
// 1172, uncompressed length unknown
ret = rzipInflate1172(&strm, src + 2, dst);
} else {
rmonPrintf("rzipInflate: input not in any known rare zip format\n");
ret = 0;
}
inflateEnd(&strm);
if (ret) {
var80091558 = strm.next_in;
return strm.total_out;
} else {
return 0;
}
}
u32 rzipInit(void)
{
// this builds tables in the original assembly version, we don't need that
return 0;
}
void *rzipGetSomething(void)
{
return var80091558;
}
+27 -27
View File
@@ -843,12 +843,12 @@ s16 var8005ecf8[] = {
-1,
};
extern u8 _sfxctlSegmentRomStart;
extern u8 _sfxtblSegmentRomStart;
extern u8 _seqctlSegmentRomStart;
extern u8 _seqctlSegmentRomEnd;
extern u8 _seqtblSegmentRomStart;
extern u8 _sequencesSegmentRomStart;
extern u8 EXT_SEG _sfxctlSegmentRomStart;
extern u8 EXT_SEG _sfxtblSegmentRomStart;
extern u8 EXT_SEG _seqctlSegmentRomStart;
extern u8 EXT_SEG _seqctlSegmentRomEnd;
extern u8 EXT_SEG _seqtblSegmentRomStart;
extern u8 EXT_SEG _sequencesSegmentRomStart;
bool sndIsPlayingMp3(void)
{
@@ -933,19 +933,19 @@ void sndLoadSfxCtl(void)
// Load the first 256 bytes of the ctl file.
size = 256;
dmaExec(buffer, (romptr_t) &_sfxctlSegmentRomStart, size);
dmaExec(buffer, (romptr_t) REF_SEG _sfxctlSegmentRomStart, size);
// Get the ROM address of the first (and only) bank,
// then load the first 256 bytes of the bank.
file = (ALBankFile *) buffer;
romaddr = (romptr_t)&_sfxctlSegmentRomStart;
romaddr = (romptr_t) REF_SEG _sfxctlSegmentRomStart;
romaddr += (u32)file->bankArray[0];
dmaExec(buffer, romaddr, size);
// Get the ROM address of the first (and only) instrument,
// then load the first 256 bytes of the instrument.
bank = (ALBank *) buffer;
romaddr = (romptr_t)&_sfxctlSegmentRomStart;
romaddr = (romptr_t) REF_SEG _sfxctlSegmentRomStart;
romaddr += (u32)bank->instArray[0];
dmaExec(buffer, romaddr, size);
@@ -966,7 +966,7 @@ void sndLoadSfxCtl(void)
// Convert ctl-local offsets to ROM offsets
for (i = 0; i < g_NumSounds; i++) {
g_ALSoundRomOffsets[i] += (romptr_t) &_sfxctlSegmentRomStart;
g_ALSoundRomOffsets[i] += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
}
// Allocate and initialise cache
@@ -1011,7 +1011,7 @@ ALEnvelope *sndLoadEnvelope(u32 offset, u16 cacheindex)
s32 sum1;
s32 sum2;
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
do {
dmaExecHighPriority(s2, offset, 0x40);
@@ -1034,7 +1034,7 @@ ALEnvelope *sndLoadEnvelope(u32 offset, u16 cacheindex)
u8 sp5f[0x50];
ALEnvelope *s1 = (ALEnvelope *)ALIGN16((uintptr_t)sp5f);
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
dmaExecHighPriority(s1, offset, 0x40);
#endif
@@ -1058,7 +1058,7 @@ ALKeyMap *sndLoadKeymap(u32 offset, u16 cacheindex)
s32 sum1;
s32 sum2;
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
do {
dmaExecHighPriority(s2, offset, 0x40);
@@ -1081,7 +1081,7 @@ ALKeyMap *sndLoadKeymap(u32 offset, u16 cacheindex)
u8 sp5f[0x50];
ALKeyMap *s1 = (ALKeyMap *)ALIGN16((uintptr_t)sp5f);
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
dmaExecHighPriority(s1, offset, 0x40);
#endif
@@ -1105,7 +1105,7 @@ ALADPCMBook *sndLoadAdpcmBook(u32 offset, u16 cacheindex)
s32 sum1;
s32 sum2;
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
do {
dmaExecHighPriority(s2, offset, 0x140);
@@ -1128,7 +1128,7 @@ ALADPCMBook *sndLoadAdpcmBook(u32 offset, u16 cacheindex)
u8 sp5f[0x150];
ALADPCMBook *s1 = (ALADPCMBook *)ALIGN16((uintptr_t)sp5f);
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
dmaExecHighPriority(s1, offset, 0x140);
#endif
@@ -1156,7 +1156,7 @@ ALADPCMloop *sndLoadAdpcmLoop(u32 offset, u16 cacheindex)
return NULL;
}
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
do {
dmaExecHighPriority(s2, offset, 0x40);
@@ -1183,7 +1183,7 @@ ALADPCMloop *sndLoadAdpcmLoop(u32 offset, u16 cacheindex)
return NULL;
}
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
dmaExecHighPriority(s1, offset, 0x40);
#endif
@@ -1208,7 +1208,7 @@ ALWaveTable *sndLoadWavetable(u32 offset, u16 cacheindex)
s32 sum2;
ALWaveTable *tmp;
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
do {
dmaExecHighPriority(s2, offset, 0x40);
@@ -1232,7 +1232,7 @@ ALWaveTable *sndLoadWavetable(u32 offset, u16 cacheindex)
ALWaveTable *s1 = (ALWaveTable *)ALIGN16((uintptr_t)sp5f);
ALWaveTable *tmp;
offset += (romptr_t)&_sfxctlSegmentRomStart;
offset += (romptr_t) REF_SEG _sfxctlSegmentRomStart;
dmaExecHighPriority(s1, offset, 0x40);
#endif
@@ -1241,7 +1241,7 @@ ALWaveTable *sndLoadWavetable(u32 offset, u16 cacheindex)
*tmp = *s1;
tmp->base += (romptr_t)&_sfxtblSegmentRomStart;
tmp->base += (romptr_t) REF_SEG _sfxtblSegmentRomStart;
if (tmp->type == AL_ADPCM_WAVE) {
tmp->waveInfo.adpcmWave.book = sndLoadAdpcmBook((uintptr_t)tmp->waveInfo.adpcmWave.book, cacheindex);
@@ -1453,7 +1453,7 @@ void sndInit(void)
if (!g_SndDisabled) {
// Allocate memory for the audio heap,
// clear it and give it to the audio library
u32 len = &_seqctlSegmentRomEnd - &_seqctlSegmentRomStart;
u32 len = REF_SEG _seqctlSegmentRomEnd - REF_SEG _seqctlSegmentRomStart;
u8 *ptr = mempAlloc(heaplen, MEMPOOL_PERMANENT);
s32 i;
u8 *heapstart = ptr;
@@ -1478,25 +1478,25 @@ void sndInit(void)
// Load seq.ctl
var80095200 = 0xffffffff;
bankfile = alHeapAlloc(&g_SndHeap, 1, len);
dmaExec(bankfile, (romptr_t) &_seqctlSegmentRomStart, len);
dmaExec(bankfile, (romptr_t) REF_SEG _seqctlSegmentRomStart, len);
// Load seq.tbl
alBnkfNew(bankfile, &_seqtblSegmentRomStart);
alBnkfNew(bankfile, REF_SEG _seqtblSegmentRomStart);
// Load the sequences table. To do this, load the header of the
// sequences segment and read the number of sequences, then allocate
// enough space for the table and load it.
var80095204 = bankfile->bankArray[0];
g_SeqTable = alHeapDBAlloc(0, 0, &g_SndHeap, 1, 0x10);
dmaExec(g_SeqTable, (romptr_t) &_sequencesSegmentRomStart, 0x10);
dmaExec(g_SeqTable, (romptr_t) REF_SEG _sequencesSegmentRomStart, 0x10);
len = g_SeqTable->count * sizeof(struct seqtableentry) + 4;
g_SeqTable = alHeapDBAlloc(0, 0, &g_SndHeap, 1, len);
dmaExec(g_SeqTable, (romptr_t) &_sequencesSegmentRomStart, (len + 0xf) & 0xfffffff0);
dmaExec(g_SeqTable, (romptr_t) REF_SEG _sequencesSegmentRomStart, (len + 0xf) & 0xfffffff0);
// Promote segment-relative offsets to ROM addresses
for (i = 0; i < g_SeqTable->count; i++) {
g_SeqTable->entries[i].romaddr += (romptr_t) &_sequencesSegmentRomStart;
g_SeqTable->entries[i].romaddr += (romptr_t) REF_SEG _sequencesSegmentRomStart;
}
synconfig.maxVVoices = 44;
+12 -12
View File
@@ -95,9 +95,9 @@ s32 g_VmNumPages = 0;
u32 var8005cf88 = 0;
extern u8 _gameSegmentStart;
extern u8 _gameSegmentEnd;
extern u8 _gamezipSegmentRomStart;
extern u8 EXT_SEG _gameSegmentStart;
extern u8 EXT_SEG _gameSegmentEnd;
extern u8 EXT_SEG _gamezipSegmentRomStart;
extern u32 g_VmPhysicalSlots;
extern u32 *g_VmVirtualToPhysicalTable;
@@ -207,24 +207,24 @@ void vmInit(void)
{
g_Is4Mb = true;
g_VmNumPages = (s32)((&_gameSegmentEnd - &_gameSegmentStart) + (VM_PAGE_SIZE - 1)) / VM_PAGE_SIZE;
g_VmNumPages = (s32)((REF_SEG _gameSegmentEnd - REF_SEG _gameSegmentStart) + (VM_PAGE_SIZE - 1)) / VM_PAGE_SIZE;
g_VmRamEnd = 0x7f000000 + VM_PAGE_SIZE * g_VmNumPages;
g_VmVirtualToPhysicalTableEnd = STACK_START;
gameseg = (u8 *) (STACK_START - g_VmNumPages * 8);
g_VmVirtualToPhysicalTable = (u32 *) gameseg;
numpages = (u32) (((uintptr_t) &_gameSegmentEnd - (uintptr_t) &_gameSegmentStart) + (VM_PAGE_SIZE - 1)) / VM_PAGE_SIZE;
numpages = (u32) (((uintptr_t) REF_SEG _gameSegmentEnd - (uintptr_t) REF_SEG _gameSegmentStart) + (VM_PAGE_SIZE - 1)) / VM_PAGE_SIZE;
numentries = numpages + 1;
g_VmZipTable = (u32 *) ((uintptr_t) ((u32 *) gameseg - (numentries + 4)) & ~0xf);
// Load gamezips pointer list
dmaExec(g_VmZipTable, (romptr_t) &_gamezipSegmentRomStart, ALIGN16((numentries + 1) << 2));
dmaExec(g_VmZipTable, (romptr_t) REF_SEG _gamezipSegmentRomStart, ALIGN16((numentries + 1) << 2));
// Make pointers absolute instead of relative to their segment
for (pagenum = 0; pagenum < numentries; pagenum++) {
g_VmZipTable[pagenum] += (romptr_t) &_gamezipSegmentRomStart;
g_VmZipTable[pagenum] += (romptr_t) REF_SEG _gamezipSegmentRomStart;
}
// Find the size of the biggest compressed zip
@@ -262,14 +262,14 @@ void vmInit(void)
// Expansion pak is being used
g_Is4Mb = numentries * false;
numpages = (u32)((&_gameSegmentEnd - &_gameSegmentStart) + (VM_PAGE_SIZE - 1)) / VM_PAGE_SIZE;
numpages = (u32)((REF_SEG _gameSegmentEnd - REF_SEG _gameSegmentStart) + (VM_PAGE_SIZE - 1)) / VM_PAGE_SIZE;
s7 = (u8 *) STACK_START;
#if VERSION >= VERSION_NTSC_1_0
numentries = numpages + 1;
gameseg = (u8 *) ((uintptr_t) (s7 - (u8 *) ALIGN64((uintptr_t) &_gameSegmentEnd - (uintptr_t) &_gameSegmentStart)) & 0xfffe0000);
gameseg = (u8 *) ((uintptr_t) (s7 - (u8 *) ALIGN64((uintptr_t) REF_SEG _gameSegmentEnd - (uintptr_t) REF_SEG _gameSegmentStart)) & 0xfffe0000);
#else
gameseg = (u8 *) ((uintptr_t) (s7 - (u8 *) ALIGN64((uintptr_t) &_gameSegmentEnd - (uintptr_t) &_gameSegmentStart)) & 0xfffe0000);
gameseg = (u8 *) ((uintptr_t) (s7 - (u8 *) ALIGN64((uintptr_t) REF_SEG _gameSegmentEnd - (uintptr_t) REF_SEG _gameSegmentStart)) & 0xfffe0000);
numentries = numpages + 1;
#endif
@@ -278,7 +278,7 @@ void vmInit(void)
numentries2 = numentries;
// Load gamezips pointer list
dmaExec(romaddrs, (romptr_t) &_gamezipSegmentRomStart, ALIGN16((numentries2 + 1) << 2));
dmaExec(romaddrs, (romptr_t) REF_SEG _gamezipSegmentRomStart, ALIGN16((numentries2 + 1) << 2));
if (pagenum);
@@ -290,7 +290,7 @@ void vmInit(void)
// Make pointers absolute instead of relative to their segment
for (ITER = 0; ITER < numentries2; ITER++) { \
romaddrs[ITER] += (romptr_t) &_gamezipSegmentRomStart;
romaddrs[ITER] += (romptr_t) REF_SEG _gamezipSegmentRomStart;
}
// Load each zip from the ROM and inflate them to the game segment