00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "util/macro.h"
00021
00022 #include "mobj_parse.h"
00023 #include "hdmv_insn.h"
00024
00025 #include <stdio.h>
00026
00027 static const char * const psr_info[128] = {
00028 "/* PSR0: Interactive graphics stream number */",
00029 "/* PSR1: Primary audio stream number */",
00030 "/* PSR2: PG TextST stream number and PiP PG stream number */",
00031 "/* PSR3: Angle number */",
00032 "/* PSR4: Title number */",
00033 "/* PSR5: Chapter number */",
00034 "/* PSR6: PlayList ID */",
00035 "/* PSR7: PlayItem ID */",
00036 "/* PSR8: Presentation time */",
00037 "/* PSR9: Navigation timer */",
00038 "/* PSR10: Selected button ID */",
00039 "/* PSR11: Page ID */",
00040 "/* PSR12: User style number */",
00041 "/* RO: PSR13: User age */",
00042 "/* PSR14: Secondary audio stream number and secondary video stream number */",
00043 "/* RO: PSR15: player capability for audio */",
00044 "/* RO: PSR16: Language code for audio */",
00045 "/* RO: PSR17: Language code for PG and Text subtitles */",
00046 "/* RO: PSR18: Menu description language code */",
00047 "/* RO: PSR19: Country code */",
00048 "/* RO: PSR20: Region code */ /* 1 - A, 2 - B, 4 - C */",
00049 "/* PSR21 */",
00050 "/* PSR22 */",
00051 "/* PSR23 */",
00052 "/* PSR24 */",
00053 "/* PSR25 */",
00054 "/* PSR26 */",
00055 "/* PSR27 */",
00056 "/* PSR28 */",
00057 "/* RO: PSR29: player capability for video */",
00058 "/* RO: PSR30: player capability for text subtitle */",
00059 "/* RO: PSR31: Player profile and version */",
00060 "/* PSR32 */",
00061 "/* PSR33 */",
00062 "/* PSR34 */",
00063 "/* PSR35 */",
00064 "/* PSR36: backup PSR4 */",
00065 "/* PSR37: backup PSR5 */",
00066 "/* PSR38: backup PSR6 */",
00067 "/* PSR39: backup PSR7 */",
00068 "/* PSR40: backup PSR8 */",
00069 "/* PSR41: */",
00070 "/* PSR42: backup PSR10 */",
00071 "/* PSR43: backup PSR11 */",
00072 "/* PSR44: backup PSR12 */",
00073 "/* PSR45: */",
00074 "/* PSR46: */",
00075 "/* PSR47: */",
00076 "/* RO: PSR48: Characteristic text caps */",
00077 "/* RO: PSR49: Characteristic text caps */",
00078 "/* RO: PSR50: Characteristic text caps */",
00079 "/* RO: PSR51: Characteristic text caps */",
00080 "/* RO: PSR52: Characteristic text caps */",
00081 "/* RO: PSR53: Characteristic text caps */",
00082 "/* RO: PSR54: Characteristic text caps */",
00083 "/* RO: PSR55: Characteristic text caps */",
00084 "/* RO: PSR56: Characteristic text caps */",
00085 "/* RO: PSR57: Characteristic text caps */",
00086 "/* RO: PSR58: Characteristic text caps */",
00087 "/* RO: PSR59: Characteristic text caps */",
00088 "/* RO: PSR60: Characteristic text caps */",
00089 "/* RO: PSR61: Characteristic text caps */",
00090 };
00091
00092 static const char * const insn_groups[4] = {
00093 "BRANCH",
00094 "COMPARE",
00095 "SET",
00096 };
00097
00098 static const char * const insn_group_branch[8] = {
00099 "GOTO",
00100 "JUMP",
00101 "PLAY",
00102 };
00103
00104 static const char * const insn_group_set[8] = {
00105 "SET",
00106 "SETSYSTEM",
00107 };
00108
00109 static const char * const insn_opt_set[32] = {
00110 NULL,
00111 "move",
00112 "swap",
00113 "add",
00114 "sub",
00115 "mul",
00116 "div",
00117 "mod",
00118 "rnd",
00119 "and",
00120 "or",
00121 "xor",
00122 "bset",
00123 "bclr",
00124 "shl",
00125 "shr",
00126 };
00127
00128 static const char * const insn_opt_setsys[32] = {
00129 NULL,
00130 "SET_STREAM",
00131 "SET_NV_TIMER",
00132 "SET_BUTTON_PAGE",
00133 "ENABLE_BUTTON",
00134 "DISABLE_BUTTON",
00135 "SET_SEC_STREAM",
00136 "POPUP_OFF",
00137 "STILL_ON",
00138 "STILL_OFF",
00139 };
00140
00141 static const char * const insn_opt_cmp[16] = {
00142 NULL,
00143 "bc",
00144 "eq",
00145 "ne",
00146 "ge",
00147 "gt",
00148 "le",
00149 "lt",
00150 };
00151
00152 static const char * const insn_opt_goto[16] = {
00153 "nop",
00154 "goto",
00155 "break",
00156 };
00157
00158 static const char * const insn_opt_jump[16] = {
00159 "JUMP_OBJECT",
00160 "JUMP_TITLE",
00161 "CALL_OBJECT",
00162 "CALL_TITLE",
00163 "RESUME"
00164 };
00165
00166 static const char * const insn_opt_play[16] = {
00167 "PLAY_PL",
00168 "PLAY_PL_PI",
00169 "PLAY_PL_MK",
00170 "TERMINATE_PL",
00171 "LINK_PI",
00172 "LINK_MK"
00173 };
00174
00175 static int _sprint_operand(char *buf, int imm, uint32_t op, int *psr)
00176 {
00177 char *start = buf;
00178
00179 if (!imm) {
00180 if (op & 0x80000000) {
00181 buf += sprintf(buf, "PSR%-3u", op & 0x7f);
00182 *psr = op & 0x7f;
00183 } else {
00184 buf += sprintf(buf, "r%-5u", op & 0xfff);
00185 }
00186 } else {
00187 if (op < 99999)
00188 buf += sprintf(buf, "%-6u", op);
00189 else
00190 buf += sprintf(buf, "0x%-4x", op);
00191 }
00192
00193 return buf - start;
00194 }
00195
00196 static int _sprint_operands(char *buf, MOBJ_CMD *cmd)
00197 {
00198 char *start = buf;
00199 HDMV_INSN *insn = &cmd->insn;
00200 int psr1 = -1, psr2 = -1;
00201
00202 if (insn->op_cnt > 0) {
00203 buf += _sprint_operand(buf, insn->imm_op1, cmd->dst, &psr1);
00204
00205 if (insn->op_cnt > 1) {
00206 buf += sprintf(buf, ",\t");
00207 buf += _sprint_operand(buf, insn->imm_op2, cmd->src, &psr2);
00208 } else {
00209 buf += sprintf(buf, " \t ");
00210 }
00211 } else {
00212 buf += sprintf(buf, " \t ");
00213 }
00214
00215 if (psr1 >= 0)
00216 buf += sprintf(buf, " %s", psr_info[psr1]);
00217 if (psr2 >= 0 && psr2 != psr1)
00218 buf += sprintf(buf, " %s", psr_info[psr2]);
00219
00220 return buf - start;
00221 }
00222
00223 static int _sprint_operands_hex(char *buf, MOBJ_CMD *cmd)
00224 {
00225 char *start = buf;
00226 HDMV_INSN *insn = &cmd->insn;
00227
00228 if (insn->op_cnt > 0) {
00229 buf += sprintf(buf, "0x%-4x", cmd->dst);
00230 }
00231 if (insn->op_cnt > 1) {
00232 buf += sprintf(buf, ",\t0x%-4x", cmd->src);
00233 }
00234
00235 return buf - start;
00236 }
00237
00238 int mobj_sprint_cmd(char *buf, MOBJ_CMD *cmd)
00239 {
00240 char *start = buf;
00241 HDMV_INSN *insn = &cmd->insn;
00242
00243 buf += sprintf(buf, "%08x %08x,%08x ", MKINT_BE32((uint8_t*)&cmd->insn), cmd->dst, cmd->src);
00244
00245 switch(insn->grp) {
00246 case INSN_GROUP_BRANCH:
00247 switch(insn->sub_grp) {
00248 case BRANCH_GOTO:
00249 if (insn_opt_goto[insn->branch_opt]) {
00250 buf += sprintf(buf, "%-10s ", insn_opt_goto[insn->branch_opt]);
00251 buf += _sprint_operands(buf, cmd);
00252 } else {
00253 buf += sprintf(buf, "[unknown BRANCH/GOTO option in opcode 0x%08x] ", *(uint32_t*)insn);
00254 }
00255 break;
00256 case BRANCH_JUMP:
00257 if (insn_opt_jump[insn->branch_opt]) {
00258 buf += sprintf(buf, "%-10s ", insn_opt_jump[insn->branch_opt]);
00259 buf += _sprint_operands(buf, cmd);
00260 } else {
00261 buf += sprintf(buf, "[unknown BRANCH/JUMP option in opcode 0x%08x] ", *(uint32_t*)insn);
00262 }
00263 break;
00264 case BRANCH_PLAY:
00265 if (insn_opt_play[insn->branch_opt]) {
00266 buf += sprintf(buf, "%-10s ", insn_opt_play[insn->branch_opt]);
00267 buf += _sprint_operands(buf, cmd);
00268 } else {
00269 buf += sprintf(buf, "[unknown BRANCH/PLAY option in opcode 0x%08x] ", *(uint32_t*)insn);
00270 }
00271 break;
00272 default:
00273 buf += sprintf(buf, "[unknown BRANCH subgroup in opcode 0x%08x] ", *(uint32_t*)insn);
00274 break;
00275 }
00276 break;
00277
00278 case INSN_GROUP_CMP:
00279 if (insn_opt_cmp[insn->cmp_opt]) {
00280 buf += sprintf(buf, "%-10s ", insn_opt_cmp[insn->cmp_opt]);
00281 buf += _sprint_operands(buf, cmd);
00282 } else {
00283 buf += sprintf(buf, "[unknown COMPARE option in opcode 0x%08x] ", *(uint32_t*)insn);
00284 }
00285 break;
00286
00287 case INSN_GROUP_SET:
00288 switch (insn->sub_grp) {
00289 case SET_SET:
00290 if (insn_opt_set[insn->set_opt]) {
00291 buf += sprintf(buf, "%-10s ", insn_opt_set[insn->set_opt]);
00292 buf += _sprint_operands(buf, cmd);
00293 } else {
00294 buf += sprintf(buf, "[unknown SET option in opcode 0x%08x] ", *(uint32_t*)insn);
00295 }
00296 break;
00297 case SET_SETSYSTEM:
00298 if (insn_opt_setsys[insn->set_opt]) {
00299 buf += sprintf(buf, "%-10s ", insn_opt_setsys[insn->set_opt]);
00300 buf += _sprint_operands_hex(buf, cmd);
00301 } else {
00302 buf += sprintf(buf, "[unknown SETSYSTEM option in opcode 0x%08x] ", *(uint32_t*)insn);
00303 }
00304 break;
00305 default:
00306 buf += sprintf(buf, "[unknown SET subgroup in opcode 0x%08x] ", *(uint32_t*)insn);
00307 break;
00308 }
00309 break;
00310
00311 default:
00312 buf += sprintf(buf, "[unknown group in opcode 0x%08x] ", *(uint32_t*)insn);
00313 break;
00314 }
00315
00316 return buf - start;
00317 }
00318