From: Michael R. <mr...@us...> - 2003-04-07 18:11:04
|
Update of /cvsroot/xine/xine-lib/src/input/libdvdnav In directory sc8-pr-cvs1:/tmp/cvs-serv18837/src/input/libdvdnav Modified Files: Makefile.am decoder.c decoder.h diff_against_cvs.patch dvd_types.h dvdnav.c dvdnav.h dvdnav_events.h highlight.c navigation.c searching.c vm.c vm.h vmcmd.c vmcmd.h Log Message: merging libdvdnav, since some nice fixes took place Index: Makefile.am =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/Makefile.am,v retrieving revision 1.8 retrieving revision 1.9 diff -u -r1.8 -r1.9 --- Makefile.am 22 Oct 2002 23:50:16 -0000 1.8 +++ Makefile.am 7 Apr 2003 18:10:44 -0000 1.9 @@ -1,6 +1,7 @@ DVD_CFLAGS = -D_FILE_OFFSET_BITS=64 -D_LARGEFILE64_SOURCE \ -I$(top_srcdir)/src/input/libdvdread/ +AM_CPPFLAGS = -DDVDNAV_COMPILE AM_CFLAGS = $(DVD_CFLAGS) @ANSI_FLAGS@ noinst_LTLIBRARIES = libdvdnav.la Index: decoder.c =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/decoder.c,v retrieving revision 1.7 retrieving revision 1.8 diff -u -r1.7 -r1.8 --- decoder.c 29 Mar 2003 13:19:08 -0000 1.7 +++ decoder.c 7 Apr 2003 18:10:45 -0000 1.8 @@ -42,7 +42,7 @@ if (count == 0) return 0; - if ( ((count+start) > 64) || + if ( ((start - count) < -1) || (count > 32) || (start > 63) || (count < 0) || @@ -50,8 +50,8 @@ fprintf(MSG_OUT, "libdvdnav: Bad call to vm_getbits. Parameter out of range\n"); assert(0); } - bit_mask >>= start; - bits = 64-count-start; + bit_mask >>= 63 - start; + bits = start + 1 - count; examining = ((bit_mask >> bits) << bits ); command->examined |= examining; result = (command->instruction & bit_mask) >> bits; @@ -110,11 +110,11 @@ /* Eval register or immediate data. AAAA_AAAA BBBB_BBBB, if immediate use all 16 bits for data else use lower eight bits for the system or general purpose register. */ -static uint16_t eval_reg_or_data(command_t* command, int32_t imm, int32_t byte) { +static uint16_t eval_reg_or_data(command_t* command, int32_t imm, int32_t start) { if(imm) { /* immediate */ - return vm_getbits(command, (byte*8), 16); + return vm_getbits(command, start, 16); } else { - return eval_reg(command, vm_getbits(command, ((byte + 1)*8), 8)); + return eval_reg(command, vm_getbits(command, (start - 8), 8)); } } @@ -122,11 +122,11 @@ xBBB_BBBB, if immediate use all 7 bits for data else use lower four bits for the general purpose register number. */ /* Evaluates gprm or data depending on bit, data is in byte n */ -uint16_t eval_reg_or_data_2(command_t* command, int32_t imm, int32_t byte) { +uint16_t eval_reg_or_data_2(command_t* command, int32_t imm, int32_t start) { if(imm) /* immediate */ - return vm_getbits(command, ((byte*8)+1), 7); + return vm_getbits(command, (start - 1), 7); else - return get_GPRM(command->registers, (vm_getbits(command, ((byte*8)+4), 4)) ); + return get_GPRM(command->registers, (vm_getbits(command, (start - 4), 4)) ); } @@ -157,10 +157,10 @@ /* Evaluate if version 1. Has comparison data in byte 3 and 4-5 (immediate or register) */ static int32_t eval_if_version_1(command_t* command) { - uint8_t op = vm_getbits(command, 9, 3); + uint8_t op = vm_getbits(command, 54, 3); if(op) { - return eval_compare(op, eval_reg(command, vm_getbits(command, 24, 8)), - eval_reg_or_data(command, vm_getbits(command, 8, 1), 4)); + return eval_compare(op, eval_reg(command, vm_getbits(command, 39, 8)), + eval_reg_or_data(command, vm_getbits(command, 55, 1), 31)); } return 1; } @@ -168,10 +168,10 @@ /* Evaluate if version 2. This version only compares register which are in byte 6 and 7 */ static int32_t eval_if_version_2(command_t* command) { - uint8_t op = vm_getbits(command, 9, 3); + uint8_t op = vm_getbits(command, 54, 3); if(op) { - return eval_compare(op, eval_reg(command, vm_getbits(command, 48, 8)), - eval_reg(command, vm_getbits(command, 56, 8))); + return eval_compare(op, eval_reg(command, vm_getbits(command, 15, 8)), + eval_reg(command, vm_getbits(command, 7, 8))); } return 1; } @@ -179,10 +179,10 @@ /* Evaluate if version 3. Has comparison data in byte 2 and 6-7 (immediate or register) */ static int32_t eval_if_version_3(command_t* command) { - uint8_t op = vm_getbits(command, 9, 3); + uint8_t op = vm_getbits(command, 54, 3); if(op) { - return eval_compare(op, eval_reg(command, vm_getbits(command, 16, 8)), - eval_reg_or_data(command, vm_getbits(command, 8, 1), 6)); + return eval_compare(op, eval_reg(command, vm_getbits(command, 47, 8)), + eval_reg_or_data(command, vm_getbits(command, 55, 1), 15)); } return 1; } @@ -191,10 +191,10 @@ Has comparison data in byte 1 and 4-5 (immediate or register) The register in byte 1 is only the lowe nibble (4 bits) */ static int32_t eval_if_version_4(command_t* command) { - uint8_t op = vm_getbits(command, 9, 3); + uint8_t op = vm_getbits(command, 54, 3); if(op) { - return eval_compare(op, eval_reg(command, vm_getbits(command, 12, 4)), - eval_reg_or_data(command, vm_getbits(command, 8, 1), 4)); + return eval_compare(op, eval_reg(command, vm_getbits(command, 51, 4)), + eval_reg_or_data(command, vm_getbits(command, 55, 1), 31)); } return 1; } @@ -204,20 +204,20 @@ static int32_t eval_special_instruction(command_t* command, int32_t cond) { int32_t line, level; - switch(vm_getbits(command, 12, 4)) { + switch(vm_getbits(command, 51, 4)) { case 0: /* NOP */ line = 0; return cond ? line : 0; case 1: /* Goto line */ - line = vm_getbits(command, 56, 8); + line = vm_getbits(command, 7, 8); return cond ? line : 0; case 2: /* Break */ /* max number of rows < 256, so we will end this set */ line = 256; return cond ? 256 : 0; case 3: /* Set temporary parental level and goto */ - line = vm_getbits(command, 56, 8); - level = vm_getbits(command, 52, 4); + line = vm_getbits(command, 7, 8); + level = vm_getbits(command, 11, 4); if(cond) { /* This always succeeds now, if we want real parental protection */ /* we need to ask the user and have passwords and stuff. */ @@ -232,8 +232,8 @@ Return 1 if link, or 0 if no link Actual link instruction is in return_values parameter */ static int32_t eval_link_subins(command_t* command, int32_t cond, link_t *return_values) { - uint16_t button = vm_getbits(command, 48, 6); - uint8_t linkop = vm_getbits(command, 59, 5); + uint16_t button = vm_getbits(command, 15, 6); + uint8_t linkop = vm_getbits(command, 4, 5); if(linkop > 0x10) return 0; /* Unknown Link by Sub-Instruction command */ @@ -249,29 +249,29 @@ Return 1 if link, or 0 if no link Actual link instruction is in return_values parameter */ static int32_t eval_link_instruction(command_t* command, int32_t cond, link_t *return_values) { - uint8_t op = vm_getbits(command, 12, 4); + uint8_t op = vm_getbits(command, 51, 4); switch(op) { case 1: return eval_link_subins(command, cond, return_values); case 4: return_values->command = LinkPGCN; - return_values->data1 = vm_getbits(command, 49, 15); + return_values->data1 = vm_getbits(command, 14, 15); return cond; case 5: return_values->command = LinkPTTN; - return_values->data1 = vm_getbits(command, 54, 10); - return_values->data2 = vm_getbits(command, 48, 6); + return_values->data1 = vm_getbits(command, 9, 10); + return_values->data2 = vm_getbits(command, 15, 6); return cond; case 6: return_values->command = LinkPGN; - return_values->data1 = vm_getbits(command, 57, 7); - return_values->data2 = vm_getbits(command, 48, 6); + return_values->data1 = vm_getbits(command, 6, 7); + return_values->data2 = vm_getbits(command, 15, 6); return cond; case 7: return_values->command = LinkCN; - return_values->data1 = vm_getbits(command, 56, 8); - return_values->data2 = vm_getbits(command, 48, 6); + return_values->data1 = vm_getbits(command, 7, 8); + return_values->data2 = vm_getbits(command, 15, 6); return cond; } return 0; @@ -283,64 +283,64 @@ actual jump instruction is in return_values parameter */ static int32_t eval_jump_instruction(command_t* command, int32_t cond, link_t *return_values) { - switch(vm_getbits(command, 12, 4)) { + switch(vm_getbits(command, 51, 4)) { case 1: return_values->command = Exit; return cond; case 2: return_values->command = JumpTT; - return_values->data1 = vm_getbits(command, 41, 7); + return_values->data1 = vm_getbits(command, 22, 7); return cond; case 3: return_values->command = JumpVTS_TT; - return_values->data1 = vm_getbits(command, 41, 7); + return_values->data1 = vm_getbits(command, 22, 7); return cond; case 5: return_values->command = JumpVTS_PTT; - return_values->data1 = vm_getbits(command, 41, 7); - return_values->data2 = vm_getbits(command, 22, 10); + return_values->data1 = vm_getbits(command, 22, 7); + return_values->data2 = vm_getbits(command, 41, 10); return cond; case 6: - switch(vm_getbits(command, 40, 2)) { + switch(vm_getbits(command, 23, 2)) { case 0: return_values->command = JumpSS_FP; return cond; case 1: return_values->command = JumpSS_VMGM_MENU; - return_values->data1 = vm_getbits(command, 44, 4); + return_values->data1 = vm_getbits(command, 19, 4); return cond; case 2: return_values->command = JumpSS_VTSM; - return_values->data1 = vm_getbits(command, 32, 8); - return_values->data2 = vm_getbits(command, 24, 8); - return_values->data3 = vm_getbits(command, 44, 4); + return_values->data1 = vm_getbits(command, 31, 8); + return_values->data2 = vm_getbits(command, 39, 8); + return_values->data3 = vm_getbits(command, 19, 4); return cond; case 3: return_values->command = JumpSS_VMGM_PGC; - return_values->data1 = vm_getbits(command, 17, 15); + return_values->data1 = vm_getbits(command, 46, 15); return cond; } break; case 8: - switch(vm_getbits(command, 40, 2)) { + switch(vm_getbits(command, 23, 2)) { case 0: return_values->command = CallSS_FP; - return_values->data1 = vm_getbits(command, 32, 8); + return_values->data1 = vm_getbits(command, 31, 8); return cond; case 1: return_values->command = CallSS_VMGM_MENU; - return_values->data1 = vm_getbits(command, 44, 4); - return_values->data2 = vm_getbits(command, 32, 8); + return_values->data1 = vm_getbits(command, 19, 4); + return_values->data2 = vm_getbits(command, 31, 8); return cond; case 2: return_values->command = CallSS_VTSM; - return_values->data1 = vm_getbits(command, 44, 4); - return_values->data2 = vm_getbits(command, 32, 8); + return_values->data1 = vm_getbits(command, 19, 4); + return_values->data2 = vm_getbits(command, 31, 8); return cond; case 3: return_values->command = CallSS_VMGM_PGC; - return_values->data1 = vm_getbits(command, 17, 15); - return_values->data2 = vm_getbits(command, 32, 8); + return_values->data1 = vm_getbits(command, 46, 15); + return_values->data2 = vm_getbits(command, 31, 8); return cond; } break; @@ -354,11 +354,11 @@ int32_t i; uint16_t data, data2; - switch(vm_getbits(command, 4, 4)) { + switch(vm_getbits(command, 59, 4)) { case 1: /* Set system reg 1 &| 2 &| 3 (Audio, Subp. Angle) */ for(i = 1; i <= 3; i++) { - if(vm_getbits(command, ((2 + i)*8), 1)) { - data = eval_reg_or_data_2(command, vm_getbits(command, 3, 1), 2 + i); + if(vm_getbits(command, 63 - ((2 + i)*8), 1)) { + data = eval_reg_or_data_2(command, vm_getbits(command, 60, 1), (47 - (i*8))); if(cond) { command->registers->SPRM[i] = data; } @@ -366,17 +366,17 @@ } break; case 2: /* Set system reg 9 & 10 (Navigation timer, Title PGC number) */ - data = eval_reg_or_data(command, vm_getbits(command, 3, 1), 2); - data2 = vm_getbits(command, 40, 8); /* ?? size */ + data = eval_reg_or_data(command, vm_getbits(command, 60, 1), 47); + data2 = vm_getbits(command, 23, 8); /* ?? size */ if(cond) { command->registers->SPRM[9] = data; /* time */ command->registers->SPRM[10] = data2; /* pgcN */ } break; case 3: /* Mode: Counter / Register + Set */ - data = eval_reg_or_data(command, vm_getbits(command, 3, 1), 2); - data2 = vm_getbits(command, 44, 4); - if(vm_getbits(command, 40, 1)) { + data = eval_reg_or_data(command, vm_getbits(command, 60, 1), 47); + data2 = vm_getbits(command, 19, 4); + if(vm_getbits(command, 23, 1)) { command->registers->GPRM_mode[data2] |= 1; /* Set bit 0 */ } else { command->registers->GPRM_mode[data2] &= ~ 0x01; /* Reset bit 0 */ @@ -386,13 +386,13 @@ } break; case 6: /* Set system reg 8 (Highlighted button) */ - data = eval_reg_or_data(command, vm_getbits(command, 3, 1), 4); /* Not system reg!! */ + data = eval_reg_or_data(command, vm_getbits(command, 60, 1), 31); /* Not system reg!! */ if(cond) { command->registers->SPRM[8] = data; } break; } - if(vm_getbits(command, 12, 4)) { + if(vm_getbits(command, 51, 4)) { return eval_link_instruction(command, cond, return_values); } return 0; @@ -426,21 +426,25 @@ break; case 5: tmp = get_GPRM(command->registers, reg) * data; - if(tmp >= shortmax) tmp = shortmax; + if(tmp > shortmax) tmp = shortmax; set_GPRM(command->registers, reg, (uint16_t)tmp); break; case 6: if (data != 0) { set_GPRM(command->registers, reg, (get_GPRM(command->registers, reg) / data) ); } else { - set_GPRM(command->registers, reg, 0); /* Avoid that divide by zero! */ + set_GPRM(command->registers, reg, 0xffff); /* Avoid that divide by zero! */ } break; case 7: - set_GPRM(command->registers, reg, (get_GPRM(command->registers, reg) % data) ); + if (data != 0) { + set_GPRM(command->registers, reg, (get_GPRM(command->registers, reg) % data) ); + } else { + set_GPRM(command->registers, reg, 0xffff); /* Avoid that divide by zero! */ + } break; - case 8: /* SPECIAL CASE - RND! */ - set_GPRM(command->registers, reg, ((uint16_t) ((float) data * rand()/(RAND_MAX+1.0))) ); + case 8: /* SPECIAL CASE - RND! Return numbers between 1 and data. */ + set_GPRM(command->registers, reg, 1 + ((uint16_t) ((float) data * rand()/(RAND_MAX+1.0))) ); break; case 9: set_GPRM(command->registers, reg, (get_GPRM(command->registers, reg) & data) ); @@ -456,10 +460,10 @@ /* Evaluate set instruction, combined with either Link or Compare. */ static void eval_set_version_1(command_t* command, int32_t cond) { - uint8_t op = vm_getbits(command, 4, 4); - uint8_t reg = vm_getbits(command, 28, 4); /* FIXME: This is different from vmcmd.c!!! */ - uint8_t reg2 = vm_getbits(command, 44, 4); - uint16_t data = eval_reg_or_data(command, vm_getbits(command, 3, 1), 4); + uint8_t op = vm_getbits(command, 59, 4); + uint8_t reg = vm_getbits(command, 35, 4); /* FIXME: This is different from vmcmd.c!!! */ + uint8_t reg2 = vm_getbits(command, 19, 4); + uint16_t data = eval_reg_or_data(command, vm_getbits(command, 60, 1), 31); if(cond) { eval_set_op(command, op, reg, reg2, data); @@ -469,10 +473,10 @@ /* Evaluate set instruction, combined with both Link and Compare. */ static void eval_set_version_2(command_t* command, int32_t cond) { - uint8_t op = vm_getbits(command, 4, 4); - uint8_t reg = vm_getbits(command, 12, 4); - uint8_t reg2 = vm_getbits(command, 28, 4); /* FIXME: This is different from vmcmd.c!!! */ - uint16_t data = eval_reg_or_data(command, vm_getbits(command, 3, 1), 2); + uint8_t op = vm_getbits(command, 59, 4); + uint8_t reg = vm_getbits(command, 51, 4); + uint8_t reg2 = vm_getbits(command, 35, 4); /* FIXME: This is different from vmcmd.c!!! */ + uint16_t data = eval_reg_or_data(command, vm_getbits(command, 60, 1), 47); if(cond) { eval_set_op(command, op, reg, reg2, data); @@ -498,7 +502,7 @@ command.registers = registers; memset(return_values, 0, sizeof(link_t)); - switch(vm_getbits(&command, 0, 3)) { /* three first old_bits */ + switch(vm_getbits(&command, 63, 3)) { /* three first old_bits */ case 0: /* Special instructions */ cond = eval_if_version_1(&command); res = eval_special_instruction(&command, cond); @@ -508,7 +512,7 @@ } break; case 1: /* Link/jump instructions */ - if(vm_getbits(&command, 3, 1)) { + if(vm_getbits(&command, 60, 1)) { cond = eval_if_version_2(&command); res = eval_jump_instruction(&command, cond, return_values); } else { @@ -527,7 +531,7 @@ case 3: /* Set instructions, either Compare or Link may be used */ cond = eval_if_version_3(&command); eval_set_version_1(&command, cond); - if(vm_getbits(&command, 12, 4)) { + if(vm_getbits(&command, 51, 4)) { res = eval_link_instruction(&command, cond, return_values); } if(res) @@ -541,6 +545,7 @@ res = -1; break; case 5: /* Compare -> (Set and Link Sub-Instruction) */ + /* FIXME: These are wrong. Need to be updated from vmcmd.c */ cond = eval_if_version_4(&command); eval_set_version_2(&command, cond); res = eval_link_subins(&command, cond, return_values); @@ -548,6 +553,7 @@ res = -1; break; case 6: /* Compare -> Set, allways Link Sub-Instruction */ + /* FIXME: These are wrong. Need to be updated from vmcmd.c */ cond = eval_if_version_4(&command); eval_set_version_2(&command, cond); res = eval_link_subins(&command, /*True*/ 1, return_values); @@ -555,7 +561,7 @@ res = -1; break; default: /* Unknown command */ - fprintf(MSG_OUT, "libdvdnav: WARNING: Unknown Command=%x\n", vm_getbits(&command, 0, 3)); + fprintf(MSG_OUT, "libdvdnav: WARNING: Unknown Command=%x\n", vm_getbits(&command, 63, 3)); assert(0); } /* Check if there are bits not yet examined */ @@ -578,10 +584,10 @@ #ifdef TRACE /* DEBUG */ fprintf(MSG_OUT, "libdvdnav: Registers before transaction\n"); - vmPrint_registers( registers ); + vm_print_registers( registers ); fprintf(MSG_OUT, "libdvdnav: Full list of commands to execute\n"); for(i = 0; i < num_commands; i++) - vmPrint_CMD(i, &commands[i]); + vm_print_cmd(i, &commands[i]); fprintf(MSG_OUT, "libdvdnav: --------------------------------------------\n"); fprintf(MSG_OUT, "libdvdnav: Single stepping commands\n"); #endif @@ -591,7 +597,7 @@ int32_t line; #ifdef TRACE - vmPrint_CMD(i, &commands[i]); + vm_print_cmd(i, &commands[i]); #endif line = eval_command(&commands[i].bytes[0], registers, return_values); @@ -599,7 +605,7 @@ if (line < 0) { /* Link command */ #ifdef TRACE fprintf(MSG_OUT, "libdvdnav: Registers after transaction\n"); - vmPrint_registers( registers ); + vm_print_registers( registers ); fprintf(MSG_OUT, "libdvdnav: eval: Doing Link/Jump/Call\n"); #endif return 1; @@ -616,7 +622,7 @@ memset(return_values, 0, sizeof(link_t)); #ifdef TRACE fprintf(MSG_OUT, "libdvdnav: Registers after transaction\n"); - vmPrint_registers( registers ); + vm_print_registers( registers ); #endif return 0; } @@ -689,7 +695,7 @@ return "*** (bug)"; } -void vmPrint_LINK(link_t value) { +void vm_print_link(link_t value) { char *cmd = linkcmd2str(value.command); switch(value.command) { @@ -745,7 +751,7 @@ } } -void vmPrint_registers( registers_t *registers ) { +void vm_print_registers( registers_t *registers ) { int32_t i; fprintf(MSG_OUT, "libdvdnav: # "); for(i = 0; i < 24; i++) Index: decoder.h =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/decoder.h,v retrieving revision 1.6 retrieving revision 1.7 diff -u -r1.6 -r1.7 --- decoder.h 29 Mar 2003 13:19:08 -0000 1.6 +++ decoder.h 7 Apr 2003 18:10:46 -0000 1.7 @@ -109,10 +109,10 @@ #ifdef TRACE /* for debugging: prints a link in readable form */ -void vmPrint_LINK(link_t value); +void vm_print_link(link_t value); /* for debugging: dumps VM registers */ -void vmPrint_registers( registers_t *registers ); +void vm_print_registers( registers_t *registers ); #endif #endif /* DECODER_H_INCLUDED */ Index: diff_against_cvs.patch =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/diff_against_cvs.patch,v retrieving revision 1.11 retrieving revision 1.12 diff -u -r1.11 -r1.12 --- diff_against_cvs.patch 29 Mar 2003 13:19:08 -0000 1.11 +++ diff_against_cvs.patch 7 Apr 2003 18:10:47 -0000 1.12 @@ -42,20 +42,20 @@ this = (dvdnav_t*)malloc(sizeof(dvdnav_t)); --- src/input/libdvdnav/dvdnav.h Thu Jul 25 17:26:00 2002 +++ src/input/libdvdnav/dvdnav.h Fri Aug 9 22:01:19 2002 -@@ -40,8 +40,8 @@ - /* Various useful types */ - #include "dvd_types.h" +@@ -41,8 +41,8 @@ + # include <dvdnav/dvd_types.h> + #endif -#include <dvdread/dvd_reader.h> -#include <dvdread/ifo_types.h> /* For vm_cmd_t */ +#include "dvd_reader.h" +#include "ifo_types.h" /* For vm_cmd_t */ - /** - * Opaque data-type can be viewed as a 'DVD handle'. You should get + + /********************************************************************* --- src/input/libdvdnav/dvdnav_events.h Fri Jul 5 16:55:04 2002 +++ src/input/libdvdnav/dvdnav_events.h Fri Aug 9 22:01:50 2002 -@@ -24,9 +24,9 @@ +@@ -28,9 +28,9 @@ #ifndef DVDNAV_EVENTS_H_INCLUDED #define DVDNAV_EVENTS_H_INCLUDED @@ -66,8 +66,8 @@ +#include "dvd_reader.h" +#include "nav_types.h" - /** - * \file dvdnav_events.h + + /* --- src/input/libdvdnav/dvdnav_internal.h Fri Aug 2 15:01:39 2002 +++ src/input/libdvdnav/dvdnav_internal.h Fri Aug 9 22:02:18 2002 @@ -1,3 +1,4 @@ Index: dvd_types.h =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/dvd_types.h,v retrieving revision 1.2 retrieving revision 1.3 diff -u -r1.2 -r1.3 --- dvd_types.h 20 Sep 2002 12:53:53 -0000 1.2 +++ dvd_types.h 7 Apr 2003 18:10:47 -0000 1.3 @@ -48,6 +48,7 @@ * DVD Menu */ typedef enum { + DVD_MENU_Escape = 0, /**< TBD */ DVD_MENU_Title = 2, /**< TBD */ DVD_MENU_Root = 3, /**< TBD */ DVD_MENU_Subpicture = 4, /**< TBD */ Index: dvdnav.c =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/dvdnav.c,v retrieving revision 1.23 retrieving revision 1.24 diff -u -r1.23 -r1.24 --- dvdnav.c 6 Apr 2003 13:09:38 -0000 1.23 +++ dvdnav.c 7 Apr 2003 18:10:47 -0000 1.24 @@ -471,6 +471,9 @@ } } this->position_current.hop_channel = this->position_next.hop_channel; + /* update VOBU info */ + this->vobu.vobu_start = this->position_next.cell_start + this->position_next.block; + this->vobu.vobu_next = 0; /* Make blockN == vobu_length to do expected_nav */ this->vobu.vobu_length = 0; this->vobu.blockN = 0; @@ -590,7 +593,7 @@ cell_event->pgN = state->pgN; cell_event->cell_length = dvdnav_convert_time(&state->pgc->cell_playback[state->cellN-1].playback_time); - + cell_event->pg_length = 0; /* Find start cell of program. */ first_cell_nr = state->pgc->program_map[state->pgN-1]; @@ -613,7 +616,7 @@ for (i = 1; i < state->pgc->program_map[state->pgN-1]; i++) cell_event->pg_start += dvdnav_convert_time(&state->pgc->cell_playback[i - 1].playback_time); - + this->position_current.cell = this->position_next.cell; this->position_current.cell_restart = this->position_next.cell_restart; this->position_current.cell_start = this->position_next.cell_start; @@ -821,9 +824,15 @@ uint8_t dvdnav_get_video_aspect(dvdnav_t *this) { uint8_t retval; - if(!this) + if(!this) { + printerr("Passed a NULL pointer."); return -1; - + } + if(!this->started) { + printerr("Virtual DVD machine not started."); + return -1; + } + pthread_mutex_lock(&this->vm_lock); retval = (uint8_t)vm_get_video_aspect(this->vm); pthread_mutex_unlock(&this->vm_lock); @@ -834,8 +843,14 @@ uint8_t dvdnav_get_video_scale_permission(dvdnav_t *this) { uint8_t retval; - if(!this) + if(!this) { + printerr("Passed a NULL pointer."); return -1; + } + if(!this->started) { + printerr("Virtual DVD machine not started."); + return -1; + } pthread_mutex_lock(&this->vm_lock); retval = (uint8_t)vm_get_video_scale_permission(this->vm); @@ -847,8 +862,14 @@ uint16_t dvdnav_audio_stream_to_lang(dvdnav_t *this, uint8_t stream) { audio_attr_t attr; - if(!this) + if(!this) { + printerr("Passed a NULL pointer."); + return -1; + } + if(!this->started) { + printerr("Virtual DVD machine not started."); return -1; + } pthread_mutex_lock(&this->vm_lock); attr = vm_get_audio_attr(this->vm, stream); @@ -863,8 +884,14 @@ uint16_t dvdnav_spu_stream_to_lang(dvdnav_t *this, uint8_t stream) { subp_attr_t attr; - if(!this) + if(!this) { + printerr("Passed a NULL pointer."); return -1; + } + if(!this->started) { + printerr("Virtual DVD machine not started."); + return -1; + } pthread_mutex_lock(&this->vm_lock); attr = vm_get_subp_attr(this->vm, stream); @@ -879,11 +906,18 @@ int8_t dvdnav_get_audio_logical_stream(dvdnav_t *this, uint8_t audio_num) { int8_t retval; - if(!this) + if(!this) { + printerr("Passed a NULL pointer."); + return -1; + } + if(!this->started) { + printerr("Virtual DVD machine not started."); return -1; + } pthread_mutex_lock(&this->vm_lock); if (!this->vm->state.pgc) { + printerr("No current PGC."); pthread_mutex_unlock(&this->vm_lock); return -1; } @@ -896,11 +930,18 @@ int8_t dvdnav_get_spu_logical_stream(dvdnav_t *this, uint8_t subp_num) { int8_t retval; - if(!this) + if(!this) { + printerr("Passed a NULL pointer."); return -1; + } + if(!this->started) { + printerr("Virtual DVD machine not started."); + return -1; + } pthread_mutex_lock(&this->vm_lock); if (!this->vm->state.pgc) { + printerr("No current PGC."); pthread_mutex_unlock(&this->vm_lock); return -1; } @@ -913,11 +954,18 @@ int8_t dvdnav_get_active_audio_stream(dvdnav_t *this) { int8_t retval; - if(!this) + if(!this) { + printerr("Passed a NULL pointer."); return -1; + } + if(!this->started) { + printerr("Virtual DVD machine not started."); + return -1; + } pthread_mutex_lock(&this->vm_lock); if (!this->vm->state.pgc) { + printerr("No current PGC."); pthread_mutex_unlock(&this->vm_lock); return -1; } @@ -930,11 +978,18 @@ int8_t dvdnav_get_active_spu_stream(dvdnav_t *this) { int8_t retval; - if(!this) + if(!this) { + printerr("Passed a NULL pointer."); + return -1; + } + if(!this->started) { + printerr("Virtual DVD machine not started."); return -1; + } pthread_mutex_lock(&this->vm_lock); if (!this->vm->state.pgc) { + printerr("No current PGC."); pthread_mutex_unlock(&this->vm_lock); return -1; } @@ -947,8 +1002,14 @@ static int8_t dvdnav_is_domain(dvdnav_t *this, domain_t domain) { int8_t retval; - if (!this || !this->started) + if(!this) { + printerr("Passed a NULL pointer."); return -1; + } + if(!this->started) { + printerr("Virtual DVD machine not started."); + return -1; + } pthread_mutex_lock(&this->vm_lock); retval = (this->vm->state.domain == domain); @@ -1029,6 +1090,9 @@ /* * $Log$ + * Revision 1.24 2003/04/07 18:10:47 mroi + * merging libdvdnav, since some nice fixes took place + * * Revision 1.23 2003/04/06 13:09:38 mroi * report start of PG as well * Index: dvdnav.h =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/dvdnav.h,v retrieving revision 1.8 retrieving revision 1.9 diff -u -r1.8 -r1.9 --- dvdnav.h 25 Mar 2003 13:17:21 -0000 1.8 +++ dvdnav.h 7 Apr 2003 18:10:48 -0000 1.9 @@ -21,10 +21,9 @@ * */ -/** - * \file dvdnav.h - * The main file you should include if you want to access dvdnav - * functionality. +/* + * This is the main header file applications should include if they want + * to access dvdnav functionality. */ [...1159 lines suppressed...] + * Are we in the Video Title Set domain? */ int8_t dvdnav_is_domain_vts(dvdnav_t *self); -/** - * @} - */ - -/* - * The following info appears on the front page of the reference manual. It is - * included here to keep it with the main dvdnav source files. The copyright notice - * refers to the comments _only_. All machine-readable source code is covered by - * the copyright notice at the top of this file. - * - * Oh, and the official language of the documentation is English -- - * English English (as in the English spoken in England) not US English. - */ #ifdef __cplusplus } Index: dvdnav_events.h =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/dvdnav_events.h,v retrieving revision 1.10 retrieving revision 1.11 diff -u -r1.10 -r1.11 --- dvdnav_events.h 6 Apr 2003 13:09:38 -0000 1.10 +++ dvdnav_events.h 7 Apr 2003 18:10:48 -0000 1.11 @@ -21,6 +21,10 @@ * */ +/* + * This header defines events and event types + */ + #ifndef DVDNAV_EVENTS_H_INCLUDED #define DVDNAV_EVENTS_H_INCLUDED @@ -28,105 +32,213 @@ #include "dvd_reader.h" #include "nav_types.h" -/** - * \file dvdnav_events.h - * This header defines events and event types + +/* + * DVDNAV_BLOCK_OK + * + * A regular data block from the DVD has been returned. + * This one should be demuxed and decoded for playback. */ +#define DVDNAV_BLOCK_OK 0 -/*** EVENTS ***/ -#define DVDNAV_BLOCK_OK 0 /*!< The next block was returned */ -#define DVDNAV_NOP 1 /*!< No action should be taken */ -#define DVDNAV_STILL_FRAME 2 /*!< The preceeding block was the last in a still frame */ -#define DVDNAV_SPU_STREAM_CHANGE 3 /*!< The SPU stream was changed */ -#define DVDNAV_AUDIO_STREAM_CHANGE 4 /*!< The Audio stream was changed */ -#define DVDNAV_VTS_CHANGE 5 /*!< We have changed VTS */ -#define DVDNAV_CELL_CHANGE 6 /*!< We have jumped to a new cell */ -#define DVDNAV_NAV_PACKET 7 /*!< The packet just passed was a NAV packet */ -#define DVDNAV_STOP 8 /*!< The last block was final, no more are coming */ -#define DVDNAV_HIGHLIGHT 9 /*!< Change highlight region */ -#define DVDNAV_SPU_CLUT_CHANGE 10 /*!< SPU CLUT changed */ -#define DVDNAV_HOP_CHANNEL 12 /*!< Sent when non-seemless stream change has happed */ -#define DVDNAV_WAIT 13 /*!< The application should wait for its fifos to run dry */ - - -/*** EVENT TYPES ***/ - -/** - * Structure providing information on DVDNAV_STILL_FRAME events. - */ -typedef struct { - int length; /*!< - The length (in seconds) the still frame - should be displayed for, or 0xff if - indefinite. */ -} dvdnav_still_event_t; +/* + * DVDNAV_NOP + * + * Just ignore this. + */ +#define DVDNAV_NOP 1 -/** - * Structure providing information on DVDNAV_SPU_STREAM_CHANGE events. + +/* + * DVDNAV_STILL_FRAME + * + * We have reached a still frame. The player application should wait + * the amount of time specified by the still's length while still handling + * user input to make menus and other interactive stills work. + * The last delivered frame should be kept showing. + * Once the still has timed out, call dvdnav_skip_still(). + * A length of 0xff means an infinite still which has to be skipped + * indirectly by some user interaction. */ +#define DVDNAV_STILL_FRAME 2 + typedef struct { - int physical_wide; /*!< The physical (MPEG) stream number for widescreen display. */ - int physical_letterbox; /*!< The physical (MPEG) stream number for letterboxed display. */ - int physical_pan_scan; /*!< The physical (MPEG) stream number for pan&scan display. */ - int logical; /*!< The logical (DVD) stream number. */ + /* The length (in seconds) the still frame should be displayed for, + * or 0xff if infinite. */ + int length; +} dvdnav_still_event_t; + + +/* + * DVDNAV_SPU_STREAM_CHANGE + * + * Inform the SPU decoding/overlaying engine to switch SPU channels. + */ +#define DVDNAV_SPU_STREAM_CHANGE 3 + +typedef struct { + /* The physical (MPEG) stream number for widescreen SPU display. + * Use this, if you blend the SPU on an anamorphic image before + * unsqueezing it. */ + int physical_wide; + + /* The physical (MPEG) stream number for letterboxed display. + * Use this, if you blend the SPU on an anamorphic image after + * unsqueezing it. */ + int physical_letterbox; + + /* The physical (MPEG) stream number for pan&scan display. + * Use this, if you blend the SPU on an anamorphic image after + * unsqueezing it the pan&scan way. */ + int physical_pan_scan; + + /* The logical (DVD) stream number. */ + int logical; } dvdnav_spu_stream_change_event_t; -/** - * Structure providing information on DVDNAV_AUDIO_STREAM_CHANGE events. + +/* + * DVDNAV_AUDIO_STREAM_CHANGE + * + * Inform the audio decoder to switch channels. */ +#define DVDNAV_AUDIO_STREAM_CHANGE 4 + typedef struct { - int physical; /*!< The physical (MPEG) stream number. */ - int logical; /*!< The logical (DVD) stream number. */ + /* The physical (MPEG) stream number. */ + int physical; + + /* The logical (DVD) stream number. */ + int logical; } dvdnav_audio_stream_change_event_t; -/** - * Structure providing information on DVDNAV_VTS_CHANGE events. - */ + +/* + * DVDNAV_VTS_CHANGE + * + * Some status information like video aspect and video scale permissions do + * not change inside a VTS. Therefore this event can be used to query such + * information only when necessary and update the decoding/displaying + * accordingly. + */ +#define DVDNAV_VTS_CHANGE 5 + typedef struct { - int old_vtsN; /*!< The old VTS number */ - dvd_read_domain_t old_domain; /*!< The old domain */ - int new_vtsN; /*!< The new VTS number */ - dvd_read_domain_t new_domain; /*!< The new domain */ + int old_vtsN; /* the old VTS number */ + dvd_read_domain_t old_domain; /* the old domain */ + int new_vtsN; /* the new VTS number */ + dvd_read_domain_t new_domain; /* the new domain */ } dvdnav_vts_change_event_t; -/** - * Structure providing information on DVDNAV_CELL_CHANGE events. - */ -typedef struct { - int cellN; /*!< The new cell number */ - int pgN; /*!< The current program number */ - int64_t cell_length; /*!< The length of the current cell in PTS ticks */ - int64_t pg_length; /*!< The length of the current program in PTS ticks */ - int64_t pgc_length; /*!< The length of the current program chain in PTS ticks */ - int64_t cell_start; /*!< The start time of the current cell relatively to the PGC in PTS ticks */ - int64_t pg_start; /*!< The start time of the current PG relatively to the PGC in PTS ticks */ + +/* + * DVDNAV_CELL_CHANGE + * + * Some status information like the current Title and Part numbers do not + * change inside a cell. Therefore this event can be used to query such + * information only when necessary and update the decoding/displaying + * accordingly. + * Some useful information for accurate time display is also reported + * together with this event. + */ +#define DVDNAV_CELL_CHANGE 6 + +typedef struct { + int cellN; /* the new cell number */ + int pgN; /* the current program number */ + int64_t cell_length; /* the length of the current cell in PTS ticks */ + int64_t pg_length; /* the length of the current program in PTS ticks */ + int64_t pgc_length; /* the length of the current program chain in PTS ticks */ + int64_t cell_start; /* the start time of the current cell relatively to the PGC in PTS ticks */ + int64_t pg_start; /* the start time of the current PG relatively to the PGC in PTS ticks */ } dvdnav_cell_change_event_t; -/* FIXME: These are unused. */ -#if 0 -/** - * Structure providing information on DVDNAV_NAV_PACKET events. - */ -typedef struct { - pci_t *pci; - dsi_t *dsi; -} dvdnav_nav_packet_event_t; -#endif - -/** - * Structure providing information on DVDNAV_HIGHLIGHT events. - * The event only fills in display and buttonN. - * The rest can be get with dvdnav_get_highlight_area(). - */ -typedef struct { - int display; /*!< 0 - hide, 1 - show, entries below only guaranteed useful - if this is '1' */ - uint32_t palette; /*!< The CLUT entries for the highlight palette - (4-bits per entry -> 4 entries) */ - uint16_t sx,sy,ex,ey; /*!< The start/end x,y positions */ - uint32_t pts; /*!< Highlight PTS to match with SPU */ - uint32_t buttonN; /*!< Button number for the SPU decoder. */ + +/* + * DVDNAV_NAV_PACKET + * + * NAV packets are useful for various purposes. They define the button + * highlight areas and VM commands of DVD menus, so they should in any + * case be sent to the SPU decoder/overlaying engine for the menus to work. + * NAV packets also provide a way to detect PTS discontinuities, because + * they carry the start and end PTS values for the current VOBU. + * (pci.vobu_s_ptm and pci.vobu_e_ptm) Whenever the start PTS of the + * current NAV does not match the end PTS of the previous NAV, a PTS + * discontinuity has occured. + * NAV packets can also be used for time display, because they are + * timestamped relatively to the current Cell. + */ +#define DVDNAV_NAV_PACKET 7 + + +/* + * DVDNAV_STOP + * + * Applications should end playback here. A subsequent dvdnav_get_next_block() + * call will restart the VM from the beginning of the DVD. + */ +#define DVDNAV_STOP 8 + + +/* + * DVDNAV_HIGHLIGHT + * + * The current button highlight changed. Inform the overlaying engine to + * highlight a different button. Please note, that at the moment only mode 1 + * highlights are reported this way. That means, when the button highlight + * has been moved around by some function call, you will receive an event + * telling you the new button. But when a button gets activated, you have + * to handle the mode 2 highlighting (that is some different colour the + * button turns to on activation) in your application. + */ +#define DVDNAV_HIGHLIGHT 9 + +typedef struct { + /* highlight mode: 0 - hide, 1 - show, 2 - activate, currently always 1 */ + int display; + + /* FIXME: these fields are currently not set */ + uint32_t palette; /* The CLUT entries for the highlight palette + (4-bits per entry -> 4 entries) */ + uint16_t sx,sy,ex,ey; /* The start/end x,y positions */ + uint32_t pts; /* Highlight PTS to match with SPU */ + + /* button number for the SPU decoder/overlaying engine */ + uint32_t buttonN; } dvdnav_highlight_event_t; + + +/* + * DVDNAV_SPU_CLUT_CHANGE + * + * Inform the SPU decoder/overlaying engine to update its colour lookup table. + * The CLUT is given as 16 uint32_t's in the buffer. + */ +#define DVDNAV_SPU_CLUT_CHANGE 10 + + +/* + * DVDNAV_HOP_CHANNEL + * + * A non-seamless operation has been performed. Applications can drop all + * their internal fifo's content, which will speed up the response. + */ +#define DVDNAV_HOP_CHANNEL 12 + + +/* + * DVDNAV_WAIT + * + * We have reached a point in DVD playback, where timing is critical. + * Player application with internal fifos can introduce state + * inconsistencies, because libdvdnav is always the fifo's length + * ahead in the stream compared to what the application sees. + * Such applications should wait until their fifos are empty + * when they receive this type of event. + * Once this is achieved, call dvdnav_skip_wait(). + */ +#define DVDNAV_WAIT 13 + #endif /* DVDNAV_EVENTS_H_INCLUDED */ Index: highlight.c =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/highlight.c,v retrieving revision 1.11 retrieving revision 1.12 diff -u -r1.11 -r1.12 --- highlight.c 29 Mar 2003 13:19:09 -0000 1.11 +++ highlight.c 7 Apr 2003 18:10:49 -0000 1.12 @@ -175,7 +175,7 @@ fprintf(MSG_OUT, "libdvdnav: %02x ", btni->cmd.bytes[k]); } fprintf(MSG_OUT, "| "); - vmPrint_mnemonic(&btni->cmd); + vm_print_mnemonic(&btni->cmd); fprintf(MSG_OUT, "\n"); } } Index: navigation.c =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/navigation.c,v retrieving revision 1.7 retrieving revision 1.8 diff -u -r1.7 -r1.8 --- navigation.c 29 Mar 2003 13:19:09 -0000 1.7 +++ navigation.c 7 Apr 2003 18:10:50 -0000 1.8 @@ -110,15 +110,24 @@ pthread_mutex_unlock(&this->vm_lock); return S_ERR; } - if (this->vm->state.domain != VTS_DOMAIN) { - printerr("Not in VTS domain."); + if ( (this->vm->state.domain == VTSM_DOMAIN) + || (this->vm->state.domain == VMGM_DOMAIN) ) { + /* Get current Menu ID: into *part. */ + vm_get_current_menu(this->vm, part); + if (*part > -1) { + *title = 0; + pthread_mutex_unlock(&this->vm_lock); + return S_OK; + } + } + if (this->vm->state.domain == VTS_DOMAIN) { + retval = vm_get_current_title_part(this->vm, title, part); pthread_mutex_unlock(&this->vm_lock); - return S_ERR; + return retval ? S_OK : S_ERR; } - retval = vm_get_current_title_part(this->vm, title, part); + printerr("Not in a title or menu."); pthread_mutex_unlock(&this->vm_lock); - - return retval ? S_OK : S_ERR; + return S_ERR; } dvdnav_status_t dvdnav_title_play(dvdnav_t *this, int title) { @@ -153,6 +162,12 @@ pthread_mutex_unlock(&this->vm_lock); return S_ERR; } + if((part < 1) || (part > this->vm->vmgi->tt_srpt->title[title-1].nr_of_ptts)) { + printerr("Part out of range."); + pthread_mutex_unlock(&this->vm_lock); + return S_ERR; + } + retval = vm_jump_title_part(this->vm, title, part); if (retval) this->vm->hop_channel++; @@ -188,7 +203,7 @@ } pthread_mutex_lock(&this->vm_lock); - vm_stop(this->vm); + this->vm->stopped = 1; pthread_mutex_unlock(&this->vm_lock); return S_OK; } Index: searching.c =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/searching.c,v retrieving revision 1.13 retrieving revision 1.14 diff -u -r1.13 -r1.14 --- searching.c 29 Mar 2003 13:19:09 -0000 1.13 +++ searching.c 7 Apr 2003 18:10:50 -0000 1.14 @@ -357,6 +357,20 @@ /* make a copy of current VM and try to navigate the copy to the menu */ try_vm = vm_new_copy(this->vm); + if ( (menu == DVD_MENU_Escape) && (this->vm->state.domain != VTS_DOMAIN)) { + /* Try resume */ + if (vm_jump_resume(try_vm) && !try_vm->stopped) { + /* merge changes on success */ + vm_merge(this->vm, try_vm); + vm_free_copy(try_vm); + this->position_current.still = 0; + this->vm->hop_channel++; + pthread_mutex_unlock(&this->vm_lock); + return S_OK; + } + } + if (menu == DVD_MENU_Escape) menu = DVD_MENU_Title; + if (vm_jump_menu(try_vm, menu) && !try_vm->stopped) { /* merge changes on success */ vm_merge(this->vm, try_vm); Index: vm.c =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/vm.c,v retrieving revision 1.18 retrieving revision 1.19 diff -u -r1.18 -r1.19 --- vm.c 1 Apr 2003 19:42:41 -0000 1.18 +++ vm.c 7 Apr 2003 18:10:50 -0000 1.19 @@ -479,13 +479,20 @@ } int vm_jump_title_part(vm_t *vm, int title, int part) { + link_t link; + if(!set_PTT(vm, title, part)) return 0; /* Some DVDs do not want us to jump directly into a title and have * PGC pre commands taking us back to some menu. Since we do not like that, - * we do not execute PGC pre commands but directly play the PG. */ + * we do not execute PGC pre commands that would do a jump. */ /* process_command(vm, play_PGC_PG(vm, (vm->state).pgN)); */ - process_command(vm, play_PG(vm)); + link = play_PGC_PG(vm, (vm->state).pgN); + if (link.command != PlayThis) + /* jump occured -> ignore it and play the PG anyway */ + process_command(vm, play_PG(vm)); + else + process_command(vm, link); return 1; } @@ -539,6 +546,7 @@ case VMGM_DOMAIN: switch(menuid) { case DVD_MENU_Title: + case DVD_MENU_Escape: (vm->state).domain = VMGM_DOMAIN; break; case DVD_MENU_Root: @@ -563,6 +571,16 @@ return 0; } +int vm_jump_resume(vm_t *vm) { + link_t link_values = { LinkRSM, 0, 0, 0 }; + + if (!(vm->state).rsm_vtsN) /* Do we have resume info? */ + return 0; + if (!process_command(vm, link_values)) + return 0; + return 1; +} + int vm_exec_cmd(vm_t *vm, vm_cmd_t *cmd) { link_t link_values; @@ -575,6 +593,15 @@ /* getting information */ +int vm_get_current_menu(vm_t *vm, int *menuid) { + pgcit_t* pgcit; + int pgcn; + pgcn = (vm->state).pgcN; + pgcit = get_PGCIT(vm); + *menuid = pgcit->pgci_srp[pgcn - 1].entry_id & 0xf ; + return 1; +} + int vm_get_current_title_part(vm_t *vm, int *title_result, int *part_result) { vts_ptt_srpt_t *vts_ptt_srpt; int title, part = 0, vts_ttn; @@ -915,7 +942,7 @@ link_t link_values; #ifdef TRACE - fprintf(MSG_OUT, "libdvdnav: play_PGC:"); + fprintf(MSG_OUT, "libdvdnav: play_PGC_PG:"); if((vm->state).domain != FP_DOMAIN) { fprintf(MSG_OUT, " (vm->state).pgcN (%i)\n", get_PGCN(vm)); } else { @@ -1172,7 +1199,7 @@ #ifdef TRACE fprintf(MSG_OUT, "libdvdnav: Before printout starts:\n"); - vmPrint_LINK(link_values); + vm_print_link(link_values); fprintf(MSG_OUT, "libdvdnav: Link values %i %i %i %i\n", link_values.command, link_values.data1, link_values.data2, link_values.data3); vm_print_current_domain_state(vm); @@ -1570,6 +1597,7 @@ static int set_FP_PGC(vm_t *vm) { (vm->state).domain = FP_DOMAIN; (vm->state).pgc = vm->vmgi->first_play_pgc; + (vm->state).pgcN = vm->vmgi->vmgi_mat->first_play_pgc; return 1; } @@ -1593,6 +1621,7 @@ } (vm->state).pgc = pgcit->pgci_srp[pgcN - 1].pgc; + (vm->state).pgcN = pgcN; (vm->state).pgN = 1; if((vm->state).domain == VTS_DOMAIN) @@ -1720,6 +1749,7 @@ return 0; /* error */ } +/* FIXME: we have a pgcN member in the vm's state now, so this should be obsolete */ static int get_PGCN(vm_t *vm) { pgcit_t *pgcit; int pgcN = 1; @@ -1818,6 +1848,9 @@ /* * $Log$ + * Revision 1.19 2003/04/07 18:10:50 mroi + * merging libdvdnav, since some nice fixes took place + * * Revision 1.18 2003/04/01 19:42:41 jcdutton * Add some comments. * Remove a FIXME comment. Index: vm.h =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/vm.h,v retrieving revision 1.7 retrieving revision 1.8 diff -u -r1.7 -r1.8 --- vm.h 29 Mar 2003 13:19:09 -0000 1.7 +++ vm.h 7 Apr 2003 18:10:52 -0000 1.8 @@ -47,6 +47,7 @@ domain_t domain; int vtsN; /* 0 is vmgm? */ pgc_t *pgc; /* either this or 'int pgcN' is enough? */ + int pgcN; /* but provide pgcN for quick lookup */ int pgN; /* is this needed? can allways fid pgN from cellN? */ int cellN; int32_t cell_restart; /* get cell to restart */ @@ -148,9 +149,11 @@ int vm_jump_prev_pg(vm_t *vm); int vm_jump_up(vm_t *vm); int vm_jump_menu(vm_t *vm, DVDMenuID_t menuid); +int vm_jump_resume(vm_t *vm); int vm_exec_cmd(vm_t *vm, vm_cmd_t *cmd); /* getting information */ +int vm_get_current_menu(vm_t *vm, int *menuid); int vm_get_current_title_part(vm_t *vm, int *title_result, int *part_result); int vm_get_audio_stream(vm_t *vm, int audioN); int vm_get_subp_stream(vm_t *vm, int subpN, int mode); Index: vmcmd.c =================================================================== RCS file: /cvsroot/xine/xine-lib/src/input/libdvdnav/vmcmd.c,v retrieving revision 1.4 retrieving revision 1.5 diff -u -r1.4 -r1.5 --- vmcmd.c 29 Mar 2003 13:19:09 -0000 1.4 +++ vmcmd.c 7 Apr 2003 18:10:52 -0000 1.5 @@ -114,22 +114,26 @@ NULL, NULL, }; - + static void print_system_reg(uint16_t reg) { if(reg < sizeof(system_reg_abbr_table) / sizeof(char *)) - fprintf(MSG_OUT, " %s (SRPM:%d)", system_reg_table[reg], reg); + fprintf(MSG_OUT, "%s (SRPM:%d)", system_reg_table[reg], reg); else fprintf(MSG_OUT, " WARNING: Unknown system register ( reg=%d ) ", reg); } +static void print_g_reg(uint8_t reg) { + if(reg < 16) + fprintf(MSG_OUT, "g[%" PRIu8 "]", reg); + else + fprintf(MSG_OUT, " WARNING: Unknown general register "); +} + static void print_reg(uint8_t reg) { if(reg & 0x80) print_system_reg(reg & 0x7f); else - if(reg < 16) - fprintf(MSG_OUT, " g[%" PRIu8 "]", reg); - else - fprintf(MSG_OUT, " WARNING: Unknown general register "); + print_g_reg(reg & 0x7f); } static void print_cmp_op(uint8_t op) { @@ -146,99 +150,133 @@ fprintf(MSG_OUT, " WARNING: Unknown set op "); } -static void print_reg_or_data(command_t* command, int immediate, int byte) { +static void print_reg_or_data(command_t* command, int immediate, int start) { if(immediate) { - int i = vm_getbits(command, (byte*8), 16); + int i = vm_getbits(command, start, 16); fprintf(MSG_OUT, "0x%x", i); if(isprint(i & 0xff) && isprint((i>>8) & 0xff)) fprintf(MSG_OUT, " (\"%c%c\")", (char)((i>>8) & 0xff), (char)(i & 0xff)); } else { - print_reg(vm_getbits(command, ((byte + 1)*8), 8)); + print_reg(vm_getbits(command, start - 8, 8)); } } -static void print_reg_or_data_2(command_t* command, int immediate, int byte) { +static void print_reg_or_data_2(command_t* command, int immediate, int start) { if(immediate) - fprintf(MSG_OUT, "0x%x", vm_getbits(command, ((byte*8)+1), 7)); + fprintf(MSG_OUT, "0x%x", vm_getbits(command, start - 1, 7)); else - fprintf(MSG_OUT, "g[%" PRIu8 "]", vm_getbits(command, ((byte*8)+4), 4)); + fprintf(MSG_OUT, "g[%" PRIu8 "]", vm_getbits(command, start - 4, 4)); } +static void print_reg_or_data_3(command_t* command, int immediate, int start) { + if(immediate) { + int i = vm_getbits(command, start, 16); + + fprintf(MSG_OUT, "0x%x", i); + if(isprint(i & 0xff) && isprint((i>>8) & 0xff)) + fprintf(MSG_OUT, " (\"%c%c\")", (char)((i>>8) & 0xff), (char)(i & 0xff)); + } else { + print_reg(vm_getbits(command, start, 8)); + } +} + + static void print_if_version_1(command_t* command) { - uint8_t op = vm_getbits(command, 9, 3); + uint8_t op = vm_getbits(command, 54, 3); if(op) { fprintf(MSG_OUT, "if ("); - print_reg(vm_getbits(command,24,8)); + print_g_reg(vm_getbits(command,39,8)); print_cmp_op(op); - print_reg_or_data(command, vm_getbits(command, 8,1), 4); + print_reg_or_data(command, vm_getbits(command, 55,1), 31); fprintf(MSG_OUT, ") "); } } static void print_if_version_2(command_t* command) { - uint8_t op = vm_getbits(command, 9, 3); + uint8_t op = vm_getbits(command, 54, 3); if(op) { fprintf(MSG_OUT, "if ("); - print_reg(vm_getbits(command, 48, 8)); + print_reg(vm_getbits(command, 15, 8)); print_cmp_op(op); - print_reg(vm_getbits(command, 56, 8)); + print_reg(vm_getbits(command, 7, 8)); fprintf(MSG_OUT, ") "); } } static void print_if_version_3(command_t* command) { - uint8_t op = vm_getbits(command, 9, 3); + uint8_t op = vm_getbits(command, 54, 3); if(op) { fprintf(MSG_OUT, "if ("); - print_reg(vm_getbits(command, 20, 4)); + print_g_reg(vm_getbits(command, 43, 4)); print_cmp_op(op); - print_reg_or_data(command, vm_getbits(command, 8, 1), 6); + print_reg_or_data(command, vm_getbits(command, 55, 1), 15); fprintf(MSG_OUT, ") "); } } static void print_if_version_4(command_t* command) { - uint8_t op = vm_getbits(command, 9, 3); - + uint8_t op = vm_getbits(command, 54, 3); + if(op) { fprintf(MSG_OUT, "if ("); - print_reg(vm_getbits(command, 12, 4)); + print_g_reg(vm_getbits(command, 51, 4)); print_cmp_op(op); - print_reg_or_data(command, vm_getbits(command, 8, 1), 4); + print_reg_or_data(command, vm_getbits(command, 55, 1), 31); fprintf(MSG_OUT, ") "); } } +static void print_if_version_5(command_t* command) { + uint8_t op = vm_getbits(command, 54, 3); + int set_immediate = vm_getbits(command, 60, 1); + + if(op) { + if (set_immediate) { + fprintf(MSG_OUT, "if ("); + print_g_reg(vm_getbits(command, 31, 8)); + print_cmp_op(op); + print_reg(vm_getbits(command, 23, 8)); + fprintf(MSG_OUT, ") "); + } else { + fprintf(MSG_OUT, "if ("); + print_g_reg(vm_getbits(command, 39, 8)); + print_cmp_op(op); + print_reg_or_data(command, vm_getbits(command, 55, 1), 31); + fprintf(MSG_OUT, ") "); + } + } +} + static void print_special_instruction(command_t* command) { - uint8_t op = vm_getbits(command, 12, 4); + uint8_t op = vm_getbits(command, 51, 4); switch(op) { case 0: /* NOP */ fprintf(MSG_OUT, "Nop"); break; case 1: /* Goto line */ - fprintf(MSG_OUT, "Goto %" PRIu8, vm_getbits(command, 56, 8)); + fprintf(MSG_OUT, "Goto %" PRIu8, vm_getbits(command, 7, 8)); break; case 2: /* Break */ fprintf(MSG_OUT, "Break"); break; case 3: /* Parental level */ fprintf(MSG_OUT, "SetTmpPML %" PRIu8 ", Goto %" PRIu8, - vm_getbits(command, 52, 4), vm_getbits(command, 56, 8)); + vm_getbits(command, 11, 4), vm_getbits(command, 7, 8)); break; default: fprintf(MSG_OUT, "WARNING: Unknown special instruction (%i)", - vm_getbits(command, 12, 4)); + vm_getbits(command, 51, 4)); } } static void print_linksub_instruction(command_t* command) { - int linkop = vm_getbits(command, 59, 5); - int button = vm_getbits(command, 48, 6); + int linkop = vm_getbits(command, 7, 8); + int button = vm_getbits(command, 15, 6); if(linkop < sizeof(link_table)/sizeof(char *) && link_table[linkop] != NULL) fprintf(MSG_OUT, "%s (button %" PRIu8 ")", link_table[linkop], button); @@ -247,7 +285,7 @@ } static void print_link_instruction(command_t* command, int optional) { - uint8_t op = vm_getbits(command, 12, 4); + uint8_t op = vm_getbits(command, 51, 4); if(optional && op) fprintf(MSG_OUT, ", "); @@ -261,19 +299,19 @@ print_linksub_instruction(command); break; case 4: - fprintf(MSG_OUT, "LinkPGCN %" PRIu16, vm_getbits(command, 49, 15)); + fprintf(MSG_OUT, "LinkPGCN %" PRIu16, vm_getbits(command, 14, 15)); break; case 5: fprintf(MSG_OUT, "LinkPTT %" PRIu16 " (button %" PRIu8 ")", - vm_getbits(command, 54, 10), vm_getbits(command, 48, 6)); + vm_getbits(command, 9, 10), vm_getbits(command, 15, 6)); break; case 6: fprintf(MSG_OUT, "LinkPGN %" PRIu8 " (button %" PRIu8 ")", - vm_getbits(command, 57, 7), vm_getbits(command, 48, 6)); + vm_getbits(command, 6, 7), vm_getbits(command, 15, 6)); break; case 7: fprintf(MSG_OUT, "LinkCN %" PRIu8 " (button %" PRIu8 ")", - vm_getbits(command, 56, 8), vm_getbits(command, 48, 6)); + vm_getbits(command, 7, 8), vm_getbits(command, 15, 6)); break; default: fprintf(MSG_OUT, "WARNING: Unknown link instruction"); @@ -281,54 +319,54 @@ } static void print_jump_instruction(command_t* command) { - switch(vm_getbits(command, 12, 4)) { + switch(vm_getbits(command, 51, 4)) { case 1: fprintf(MSG_OUT, "Exit"); break; case 2: - fprintf(MSG_OUT, "JumpTT %" PRIu8, vm_getbits(command, 41, 7)); + fprintf(MSG_OUT, "JumpTT %" PRIu8, vm_getbits(command, 22, 7)); break; case 3: - fprintf(MSG_OUT, "JumpVTS_TT %" PRIu8, vm_getbits(command, 41, 7)); + fprintf(MSG_OUT, "JumpVTS_TT %" PRIu8, vm_getbits(command, 22, 7)); break; case 5: fprintf(MSG_OUT, "JumpVTS_PTT %" PRIu8 ":%" PRIu16, - vm_getbits(command, 41, 7), vm_getbits(command, 22, 10)); + vm_getbits(command, 22, 7), vm_getbits(command, 41, 10)); break; case 6: - switch(vm_getbits(command, 40, 2)) { + switch(vm_getbits(command, 23, 2)) { case 0: fprintf(MSG_OUT, "JumpSS FP"); break; case 1: - fprintf(MSG_OUT, "JumpSS VMGM (menu %" PRIu8 ")", vm_getbits(command, 44, 4)); + fprintf(MSG_OUT, "JumpSS VMGM (menu %" PRIu8 ")", vm_getbits(command, 19, 4)); break; case 2: fprintf(MSG_OUT, "JumpSS VTSM (vts %" PRIu8 ", title %" PRIu8 - ", menu %" PRIu8 ")", vm_getbits(command, 32, 8), vm_getbits(command, 24, 8), vm_getbits(command, 44, 4)); + ", menu %" PRIu8 ")", vm_getbits(command, 30, 7), vm_getbits(command, 38, 7), vm_getbits(command, 19, 4)); break; case 3: - fprintf(MSG_OUT, "JumpSS VMGM (pgc %" PRIu8 ")", vm_getbits(command, 17, 15)); + fprintf(MSG_OUT, "JumpSS VMGM (pgc %" PRIu8 ")", vm_getbits(command, 46, 15)); break; } break; case 8: - switch(vm_getbits(command, 40, 2)) { + switch(vm_getbits(command, 23, 2)) { case 0: fprintf(MSG_OUT, "CallSS FP (rsm_cell %" PRIu8 ")", - vm_getbits(command, 32, 8)); + vm_getbits(command, 31, 8)); break; case 1: fprintf(MSG_OUT, "CallSS VMGM (menu %" PRIu8 - ", rsm_cell %" PRIu8 ")", vm_getbits(command, 44, 4), vm_getbits(command, 32, 8)); + ", rsm_cell %" PRIu8 ")", vm_getbits(command, 19, 4), vm_getbits(command, 31, 8)); break; case 2: fprintf(MSG_OUT, "CallSS VTSM (menu %" PRIu8 - ", rsm_cell %" PRIu8 ")", vm_getbits(command, 44, 4), vm_getbits(command, 32, 8)); + ", rsm_cell %" PRIu8 ")", vm_getbits(command, 19, 4), vm_getbits(command, 31, 8)); break; case 3: fprintf(MSG_OUT, "CallSS VMGM (pgc %" PRIu8 ", rsm_cell %" PRIu8 ")", - vm_getbits(command, 17, 15), vm_getbits(command, 32, 8)); + vm_getbits(command, 46, 15), vm_getbits(command, 31, 8)); break; } break; @@ -339,14 +377,16 @@ static void print_system_set(command_t* command) { int i; +/* FIXME: What about SPRM11 ? Karaoke */ +/* Surely there must be some system set command for that ? */ - switch(vm_getbits(command, 4, 4)) { + switch(vm_getbits(command, 59, 4)) { case 1: /* Set system reg 1 &| 2 &| 3 (Audio, Subp. Angle) */ for(i = 1; i <= 3; i++) { - if(vm_getbits(command, ((2+i)*8), 1)) { + if(vm_getbits(command, 47 - (i*8), 1)) { print_system_reg(i); fprintf(MSG_OUT, " = "); - print_reg_or_data_2(command, vm_getbits(command, 3, 1), 2 + i); + print_reg_or_data_2(command, vm_getbits(command, 60, 1), 47 - (i*8) ); fprintf(MSG_OUT, " "); } } @@ -354,59 +394,72 @@ case 2: /* Set system reg 9 & 10 (Navigation timer, Title PGC number) */ print_system_reg(9); fprintf(MSG_OUT, " = "); - print_reg_or_data(command, vm_getbits(command, 3, ... [truncated message content] |