#include #include #include "rtv.h" #define expect(x) do { \ if (!(x)) { \ fprintf(stderr, "Unexpected %s %d\n", #x, __LINE__); \ fprintf(stdout, "Unexpected %s %d\n", #x, __LINE__); \ } \ } while(0) u16 rtv_to_u16(unsigned char ** pp) { unsigned char * p; u16 r; p = *pp; r = *p++; r <<= 8; r |= *p++; *pp = p; return r; } u32 rtv_to_u32(unsigned char ** pp) { unsigned char * p; u32 r; p = *pp; r = rtv_to_u16(&p); r <<= 16; r |= rtv_to_u16(&p); *pp = p; return r; } u64 rtv_to_u64(unsigned char ** pp) { unsigned char * p; u64 r; p = *pp; r = rtv_to_u32(&p); r <<= 32; r |= rtv_to_u32(&p); *pp = p; return r; } static void clearstring(unsigned char * p) { while (*p) *p++ = 0; } static unsigned char * dump_show(unsigned char * buf) { unsigned char * p; u32 flags; u32 start_time; u32 tmsid; u16 minutes; u16 unk1; u16 unk2; u16 record_length; u8 title_length, episode_length, description_length, actor_length, guest_length, suzuki_length, producer_length, director_length; p = buf; flags = rtv_to_u32(&p); start_time = rtv_to_u32(&p); tmsid = rtv_to_u32(&p); minutes = rtv_to_u16(&p); unk1 = rtv_to_u16(&p); unk2 = rtv_to_u16(&p); record_length = rtv_to_u16(&p); title_length = *p++; episode_length = *p++; description_length = *p++; actor_length = *p++; guest_length = *p++; suzuki_length = *p++; producer_length = *p++; director_length = *p++; printf("Flags: %lx\n", flags); printf("Start time: %ld\n", start_time); printf("TMS ID: %ld\n", tmsid); printf("Minutes: %ld\n", minutes); printf("Unk1: %ld %lx\n", unk1, unk1); printf("Unk2: %ld %lx\n", unk2, unk2); printf("Record Len: %d\n", record_length); /* XXX I'm not sure the order of movie & parts is right, if they're ever both used */ if (flags & 0x0020) { u16 mpaa, stars, year, runtime; mpaa = rtv_to_u16(&p); stars = rtv_to_u16(&p); year = rtv_to_u16(&p); runtime = rtv_to_u16(&p); printf("Title: %.*s\n", title_length-1, p); printf("MPAA: %d\n", mpaa); printf("Stars: %d\n", stars); printf("Year: %d\n", year); printf("Runtime: %d\n", runtime); } if (flags & 0x0040) { u16 part, of; part = rtv_to_u16(&p); of = rtv_to_u16(&p); printf("Part: %d/%d\n", part, of); } if (title_length > 1) printf("Title: %.*s\n", title_length-1, p); p += title_length; if (episode_length > 1) printf("Episode: %.*s\n", episode_length-1, p); p += episode_length; if (description_length > 1) printf("Description:%.*s\n", description_length-1, p); p += description_length; if (actor_length > 1) printf("Actor: %.*s\n", actor_length-1, p); p += actor_length; if (guest_length > 1) printf("Guest: %.*s\n", guest_length-1, p); p += guest_length; if (suzuki_length > 1) printf("Suzuki: %.*s\n", suzuki_length-1, p); p += suzuki_length; if (producer_length > 1) printf("Producer: %.*s\n", producer_length-1, p); p += producer_length; if (director_length > 1) printf("Director: %.*s\n", director_length-1, p); p += director_length; printf("\n"); expect(record_length - (p - buf) <= 3); return buf + record_length; } static int dump_channel(FILE * in) { unsigned char headbuf[12]; unsigned char * buf; unsigned char * p; u32 mod_time, tmsid, datalength; if (fread(headbuf, 12, 1, in) <= 0) return -1; p = headbuf; mod_time = rtv_to_u32(&p); tmsid = rtv_to_u32(&p); datalength = rtv_to_u32(&p); printf("Channel %lu as of %lu (%d bytes)\n--------------------------------------------\n", (unsigned long)tmsid, (unsigned long)mod_time, datalength); buf = malloc(datalength); fread(buf, datalength, 1, in); p = buf; while (p < buf + datalength) { p = dump_show(p); } expect(p == buf + datalength); return 0; } int main(int argc, char ** argv) { while (dump_channel(stdin) == 0) ; }