Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include "n64.h"
- unsigned char * SourceBuffer;
- unsigned char * TargetBuffer;
- unsigned char * TextureBuffer;
- int Filesize = 0;
- int TexFilesize = 0;
- char * SourceFilename;
- char * TargetFilename;
- char * TextureFilename;
- int OffsetPairs = 0;
- unsigned int SourceOffset[512];
- unsigned int TargetOffset[512];
- unsigned int TextureTgtOffset;
- int ConvertBuffer(unsigned char * Src, unsigned char * Tgt)
- {
- // tag OK: command converts correctly
- // tag NG: command doesn't yet convert correctly / conversion is untested / isn't yet covered
- // tag XX: command is deliberately ignored
- int Pair = 0;
- int Offset = 0;
- unsigned int w0 = 0, w1 = 0;
- while(Pair < OffsetPairs) {
- Offset = SourceOffset[Pair];
- while(Offset < TargetOffset[Pair]) {
- w0 = (Src[Offset] << 24) + (Src[Offset + 1] << 16) + (Src[Offset + 2] << 8) + Src[Offset + 3];
- w1 = (Src[Offset + 4] << 24) + (Src[Offset + 5] << 16) + (Src[Offset + 6] << 8) + Src[Offset + 7];
- switch(Src[Offset]) {
- case G_SETTIMG:
- printf("- Found G_SETTIMG at 0x%06X...", Offset);
- Tgt[Offset] = Src[Offset];
- Tgt[Offset + 1] = Src[Offset + 1];
- Tgt[Offset + 2] = Src[Offset + 2];
- Tgt[Offset + 3] = Src[Offset + 3];
- // write address
- if(Src[Offset + 4] == 0x09) {
- // if texture originally from RAM segment 0x09 (textures)
- unsigned int new_w1 = 0x03000000 + (w1 & 0x00FFFFFF) + TextureTgtOffset;
- Tgt[Offset + 4] = (new_w1 & 0xFF000000) >> 24;
- Tgt[Offset + 5] = (new_w1 & 0x00FF0000) >> 16;
- Tgt[Offset + 6] = (new_w1 & 0x0000FF00) >> 8;
- Tgt[Offset + 7] = (new_w1 & 0x000000FF);
- } else if(Src[Offset + 4] == 0x07) {
- // if texture originally from RAM segment 0x07 (level display lists)
- unsigned int new_w1 = 0x03000000 + (w1 & 0x00FFFFFF) + TextureTgtOffset + TexFilesize;
- Tgt[Offset + 4] = (new_w1 & 0xFF000000) >> 24;
- Tgt[Offset + 5] = (new_w1 & 0x00FF0000) >> 16;
- Tgt[Offset + 6] = (new_w1 & 0x0000FF00) >> 8;
- Tgt[Offset + 7] = (new_w1 & 0x000000FF);
- // WARNING: textures must manually be pasted to the end of the converted file!
- } else {
- // just write original data, results in garbage
- Tgt[Offset + 4] = Src[Offset + 4];
- Tgt[Offset + 5] = Src[Offset + 5];
- Tgt[Offset + 6] = Src[Offset + 6];
- Tgt[Offset + 7] = Src[Offset + 7];
- }
- printf("\t\tOK\n");
- break;
- case F3D_VTX:
- printf("- Found F3D_VTX at 0x%06X...", Offset);
- // write address
- Tgt[Offset + 4] = 0x03;
- Tgt[Offset + 5] = Src[Offset + 5];
- Tgt[Offset + 6] = Src[Offset + 6];
- Tgt[Offset + 7] = Src[Offset + 7];
- // extract n & v0
- unsigned int n = _SHIFTR(w0, 20, 4) + 1;
- unsigned int v0 = _SHIFTR(w0, 16, 4);
- // write n & v0
- w0 = F3DEX2_VTX << 24;
- unsigned int new_v0 = (n + v0) << 12;
- w0 += new_v0;
- unsigned int new_n = n * 2;
- w0 += new_n;
- Tgt[Offset] = (w0 & 0xFF000000) >> 24;
- Tgt[Offset + 1] = (w0 & 0x00FF0000) >> 16;
- Tgt[Offset + 2] = (w0 & 0x0000FF00) >> 8;
- Tgt[Offset + 3] = (w0 & 0x000000FF);
- // write vtx data to target buffer
- if(Src[Offset + 4] == 0x07) {
- int vtxoffset = (w1 & 0x00FFFFFF);
- memcpy(&Tgt[vtxoffset], &Src[vtxoffset], n * 0x10);
- }
- printf("\t\t\tOK\n");
- break;
- case F3D_TRI1:
- printf("- Found F3D_TRI1 at 0x%06X...", Offset);
- Tgt[Offset] = F3DEX2_TRI1;
- Tgt[Offset + 1] = (Src[Offset + 5] / 0x0A) * 2;
- Tgt[Offset + 2] = (Src[Offset + 6] / 0x0A) * 2;
- Tgt[Offset + 3] = (Src[Offset + 7] / 0x0A) * 2;
- printf("\t\t\tOK\n");
- break;
- case F3D_TRI4:
- printf("- Found F3D_TRI4 at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_SPNOOP;
- printf("\t\t\tXX\n");
- break;
- case F3D_TEXTURE:
- printf("- Found F3D_TEXTURE at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_TEXTURE;
- Tgt[Offset + 1] = Src[Offset + 1];
- Tgt[Offset + 2] = Src[Offset + 2];
- Tgt[Offset + 3] = _SHIFTL(Src[Offset + 3], 1, 7); // convert "on"
- Tgt[Offset + 4] = Src[Offset + 4];
- Tgt[Offset + 5] = Src[Offset + 5];
- Tgt[Offset + 6] = Src[Offset + 6];
- Tgt[Offset + 7] = Src[Offset + 7];
- printf("\t\tOK\n");
- break;
- case F3D_SETGEOMETRYMODE:
- printf("- Found F3D_SETGEOMETRYMODE at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_GEOMETRYMODE;
- Tgt[Offset + 1] = 0xFF;
- Tgt[Offset + 2] = 0xFF;
- Tgt[Offset + 3] = 0xFF;
- Tgt[Offset + 4] = 0x00;
- Tgt[Offset + 5] = Src[Offset + 5];
- Tgt[Offset + 6] = Src[Offset + 6];
- Tgt[Offset + 7] = Src[Offset + 7];
- printf("\tOK\n");
- break;
- case F3D_CLEARGEOMETRYMODE:
- printf("- Found F3D_CLEARGEOMETRYMODE at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_GEOMETRYMODE;
- Tgt[Offset + 1] = ~Src[Offset + 5];
- Tgt[Offset + 2] = ~Src[Offset + 6];
- Tgt[Offset + 3] = ~Src[Offset + 7];
- printf("\tOK\n");
- break;
- case F3D_CULLDL:
- printf("- Found F3D_CULLDL at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_SPNOOP;
- printf("\t\t\tXX\n");
- break;
- case F3D_SETOTHERMODE_H:
- printf("- Found F3D_SETOTHERMODE_H at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_SETOTHERMODE_H;
- Tgt[Offset + 1] = Src[Offset + 1];
- Tgt[Offset + 2] = Src[Offset + 2];
- Tgt[Offset + 3] = Src[Offset + 3];
- Tgt[Offset + 4] = Src[Offset + 4];
- Tgt[Offset + 5] = Src[Offset + 5];
- Tgt[Offset + 6] = Src[Offset + 6];
- Tgt[Offset + 7] = Src[Offset + 7];
- printf("\t\tNG\n");
- break;
- case F3D_SETOTHERMODE_L:
- printf("- Found F3D_SETOTHERMODE_L at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_SETOTHERMODE_L;
- Tgt[Offset + 1] = Src[Offset + 1];
- Tgt[Offset + 2] = Src[Offset + 2];
- Tgt[Offset + 3] = Src[Offset + 3];
- Tgt[Offset + 4] = Src[Offset + 4];
- Tgt[Offset + 5] = Src[Offset + 5];
- Tgt[Offset + 6] = Src[Offset + 6];
- Tgt[Offset + 7] = Src[Offset + 7];
- printf("\t\tNG\n");
- break;
- case F3D_RDPHALF_1:
- printf("- Found F3D_RDPHALF_1 at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_RDPHALF_1;
- Tgt[Offset + 1] = Src[Offset + 1];
- Tgt[Offset + 2] = Src[Offset + 2];
- Tgt[Offset + 3] = Src[Offset + 3];
- Tgt[Offset + 4] = Src[Offset + 4];
- Tgt[Offset + 5] = Src[Offset + 5];
- Tgt[Offset + 6] = Src[Offset + 6];
- Tgt[Offset + 7] = Src[Offset + 7];
- printf("\t\tOK\n");
- break;
- case F3D_MOVEMEM:
- printf("- Found F3D_MOVEMEM at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_SPNOOP;
- printf("\t\tXX\n");
- break;
- case F3D_MOVEWORD:
- printf("- Found F3D_MOVEWORD at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_SPNOOP;
- printf("\t\t\tXX\n");
- break;
- case F3D_DL:
- printf("- Found F3D_DL at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_DL;
- Tgt[Offset + 1] = Src[Offset + 1];
- Tgt[Offset + 2] = Src[Offset + 2];
- Tgt[Offset + 3] = Src[Offset + 3];
- Tgt[Offset + 4] = 0x03;
- Tgt[Offset + 5] = Src[Offset + 5];
- Tgt[Offset + 6] = Src[Offset + 6];
- Tgt[Offset + 7] = Src[Offset + 7];
- printf("\t\t\tOK\n");
- break;
- case F3D_ENDDL:
- printf("- Found F3D_ENDDL at 0x%06X... ", Offset);
- Tgt[Offset] = F3DEX2_ENDDL;
- printf("\t\tOK\n");
- break;
- default:
- memcpy(&Tgt[Offset], &Src[Offset], 8);
- break;
- }
- Offset += 8;
- }
- Pair++;
- }
- return 0;
- }
- int main(int argc, char * argv[])
- {
- printf("SM64 Fast3D to Zelda F3DEX2 Converter\nJanuary 2010 by xdaniel\n\n");
- // check for argument count and count parity
- if((argc < 7) || ((argc - 1) & 1)) {
- printf("Syntax error!\n\n");
- printf("Usage:\n - <source filename> <target filename> <texture filename>\n <texture target offset> [<DList start offset> <DList end offset> ...]\n\n");
- return 1;
- }
- // get source and target filenames
- SourceFilename = (char*) malloc(sizeof(char) * strlen(argv[1]));
- strcpy(SourceFilename, argv[1]);
- TargetFilename = (char*) malloc(sizeof(char) * strlen(argv[2]));
- strcpy(TargetFilename, argv[2]);
- // get texture filename and target offset
- TextureFilename = (char*) malloc(sizeof(char) * strlen(argv[3]));
- strcpy(TextureFilename, argv[3]);
- sscanf(argv[4], "%x", &TextureTgtOffset);
- // get amount of offset pairs specified
- OffsetPairs = (argc - 5) / 2;
- // check if offset pairs are valid, and if yes add them to the offset arrays
- int i = 0, TempSource = 0, TempTarget = 0;
- while(i < OffsetPairs) {
- sscanf(argv[5 + (i * 2)], "%x", &TempSource);
- sscanf(argv[6 + (i * 2)], "%x", &TempTarget);
- if(TempSource < TempTarget) {
- SourceOffset[i] = TempSource;
- TargetOffset[i] = TempTarget;
- } else {
- printf("Error: source offset 0x%02X greater than target 0x%02X!\n", TempSource, TempTarget);
- }
- i++;
- }
- OffsetPairs = i;
- // load texture file
- printf("Loading %s...\n", TextureFilename);
- FILE * file = fopen(TextureFilename, "rb");
- fseek(file, 0, SEEK_END);
- TexFilesize = ftell(file);
- rewind(file);
- TextureBuffer = (unsigned char*) malloc (sizeof(char) * TexFilesize);
- fread(TextureBuffer, 1, TexFilesize, file);
- fclose(file);
- // load source file and create buffers
- printf("Loading %s, creating buffers...\n", SourceFilename);
- file = fopen(SourceFilename, "rb");
- Filesize = TextureTgtOffset + TexFilesize;
- SourceBuffer = (unsigned char*) malloc (sizeof(char) * Filesize);
- fread(SourceBuffer, 1, Filesize, file);
- TargetBuffer = (unsigned char*) malloc (sizeof(char) * Filesize);
- memset(TargetBuffer, 0x00, Filesize);
- fclose(file);
- // do the conversion!
- printf("Converting F3D to F3DEX2...\n");
- ConvertBuffer(SourceBuffer, TargetBuffer);
- // copy texture buffer to the converted buffer
- memcpy(&TargetBuffer[TextureTgtOffset], TextureBuffer, TexFilesize);
- // save the converted buffer back to file
- printf("Saving converted buffer to %s...\n", TargetFilename);
- file = fopen(TargetFilename, "wb");
- fwrite(TargetBuffer, 1, Filesize, file);
- fclose(file);
- // we're done
- printf("\nDone!\n");
- return 0;
- }
- ----
- #define _SHIFTL( v, s, w ) \
- (((unsigned int)v & ((0x01 << w) - 1)) << s)
- #define _SHIFTR( v, s, w ) \
- (((unsigned int)v >> s) & ((0x01 << w) - 1))
- #define G_SETTIMG 0xFD
- #define F3D_SPNOOP 0x00
- #define F3D_MTX 0x01
- #define F3D_RESERVED0 0x02
- #define F3D_MOVEMEM 0x03
- #define F3D_VTX 0x04
- #define F3D_RESERVED1 0x05
- #define F3D_DL 0x06
- #define F3D_RESERVED2 0x07
- #define F3D_RESERVED3 0x08
- #define F3D_SPRITE2D_BASE 0x09
- #define F3D_TRI1 0xBF
- #define F3D_CULLDL 0xBE
- #define F3D_POPMTX 0xBD
- #define F3D_MOVEWORD 0xBC
- #define F3D_TEXTURE 0xBB
- #define F3D_SETOTHERMODE_H 0xBA
- #define F3D_SETOTHERMODE_L 0xB9
- #define F3D_ENDDL 0xB8
- #define F3D_SETGEOMETRYMODE 0xB7
- #define F3D_CLEARGEOMETRYMODE 0xB6
- #define F3D_QUAD 0xB5
- #define F3D_RDPHALF_1 0xB4
- #define F3D_RDPHALF_2 0xB3
- #define F3D_RDPHALF_CONT 0xB2
- #define F3D_TRI4 0xB1
- #define F3DEX2_VTX 0x01
- #define F3DEX2_MODIFYVTX 0x02
- #define F3DEX2_CULLDL 0x03
- #define F3DEX2_BRANCH_Z 0x04
- #define F3DEX2_TRI1 0x05
- #define F3DEX2_TRI2 0x06
- #define F3DEX2_QUAD 0x07
- #define F3DEX2_RDPHALF_2 0xF1
- #define F3DEX2_SETOTHERMODE_H 0xE3
- #define F3DEX2_SETOTHERMODE_L 0xE2
- #define F3DEX2_RDPHALF_1 0xE1
- #define F3DEX2_SPNOOP 0xE0
- #define F3DEX2_ENDDL 0xDF
- #define F3DEX2_DL 0xDE
- #define F3DEX2_LOAD_UCODE 0xDD
- #define F3DEX2_MOVEMEM 0xDC
- #define F3DEX2_MOVEWORD 0xDB
- #define F3DEX2_MTX 0xDA
- #define F3DEX2_GEOMETRYMODE 0xD9
- #define F3DEX2_POPMTX 0xD8
- #define F3DEX2_TEXTURE 0xD7
- #define F3DEX2_DMA_IO 0xD6
- #define F3DEX2_SPECIAL_1 0xD5
- #define F3DEX2_SPECIAL_2 0xD4
- #define F3DEX2_SPECIAL_3 0xD3
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement