Seems related to [[Silky]], which is probably misnamed. {{{#!highlight c++ // Dumper for Fortissimo EXS's script #include #include #include bool is_jis_surrogate(uint8_t c) { if(c >= 0x80 and c <= 0xA0) return true; if(c >= 0xE0) return true; return false; } bool silent = false; bool debug = false; void output(int c) { if (!silent) printf("%c", c); } void print_string(FILE * f) { if (!silent and debug) printf("printing from %X\n", ftell(f)); int c = fgetc(f); while(c > 0 and c < 0x100) { c = (c+0x20)%0x100; if(is_jis_surrogate(c)) { if (!silent) output(c); c = fgetc(f); if(c == 0) break; output((c+0x20)%0x100); } else { if(c == 0x0A) { //output(c); } else { if (!silent) output(c); } } c = fgetc(f); } if (!silent) puts(""); } #define eat_string() \ { \ c = fgetc(f); \ while(c > 0) \ c = fgetc(f); \ } int main(int argc, char ** argv) { // feed .MES files for(int i = 1; i < argc; i++) { auto f = fopen(argv[i], "rb"); if(!f) return puts("failed to open"), 0; if (debug) printf("reading %s\n", argv[i]); uint32_t numlines; fread(&numlines, 4, 1, f); uint32_t startpoint = numlines*4; fseek(f, startpoint, SEEK_CUR); if (debug) printf("startpoint 0x%X\n", startpoint); uint8_t last_command = 0; uint32_t last_command_location = 0; int c = 0; while(1) { c = fgetc(f); if(c < 0) break; // Opcode handling to stay in sync. Not proper reverse engineering, 95% guesswork. switch(c) { case 0x6B: // like a scene header of some sort last_command = c; last_command_location = ftell(f)-1; fseek(f, 1, SEEK_CUR); continue; case 0x00: case 0x02: case 0x03: case 0x04: case 0x05: case 0x07: case 0x08: case 0x09: case 0x0A: case 0x0B: case 0x0D: case 0x0E: case 0x0F: case 0x11: case 0x12: case 0x13: case 0x14: case 0x15: case 0x16: case 0x17: case 0x19: case 0x1A: case 0x1B: case 0x1C: case 0x1E: case 0x21: case 0x22: case 0x26: // ???? last_command = c; last_command_location = ftell(f)-1; fseek(f, 2, SEEK_CUR); continue; case 0x51: // ? case 0x52: // ? case 0x53: // ? case 0x54: // ? case 0x55: // ? case 0x56: // ? (related to 3F and 40?) case 0x57: // ? case 0x58: // ? case 0x5D: // ? case 0x5E: // ? case 0x5F: // ? case 0x60: // ? case 0x61: // ? case 0x62: // ? case 0x64: // ? case 0x66: // ? case 0x67: // ? case 0x68: // ? last_command = c; last_command_location = ftell(f)-1; fseek(f, 8, SEEK_CUR); continue; case 0x30: // stack related? case 0x31: // ? (system\stat_chip06) case 0x32: // ? (system\gotitle) case 0x33: // ? (system\cgpage01) case 0x35: // ? (SCEAN_START) (SCEAN_NEXT1) ("00") (advmenu_start) case 0x36: // voice related case 0x37: // (return_sub) case 0x38: // play movie? (movie\ff_op_fripside.mpg) case 0x3A: // ? (SCEAN_NEXT1) (return_txt) (CloseMes) case 0x3B: // ? (advmenu_start) case 0x3C: // ? ("logo_end0") case 0x3F: // ? (SCEAN_END) case 0x40: // ? (SCEAN_START) case 0x43: // ? (@tスキップしますか?) case 0x44: // ? ("00") ("01") case 0x45: // ? ("最初からシーンを再生") case 0x47: // voice related case 0x48: // voice related case 0x49: // ? (music_play_end) case 0x4B: // ? ("1.00") last_command = c; last_command_location = ftell(f)-1; eat_string(); continue; case 0x2A: // ? (system\messwin) case 0x2B: // music related case 0x2D: // ? (advmenu) case 0x2C: // music related case 0x2E: // related to end of scene file last_command = c; last_command_location = ftell(f)-1; fseek(f, 1, SEEK_CUR); // slot? eat_string(); continue; case 0x4D: // ? (speaker name?) case 0x4E: // "normal" text case 0x4F: // choice last_command = c; last_command_location = ftell(f)-1; if(c != 0x4D) print_string(f); else eat_string(); continue; } if(c < 0) break; printf("Unknown command %02X at %08X in %s\n", uint8_t(c), ftell(f)-1, argv[i]); printf("Next byte is %02X\n", fgetc(f)); printf("Last command was %02X at %08X\n", last_command, last_command_location); exit(0); } fclose(f); if (!silent) puts(""); } } }}}