4 * avi vobsub subtitle stream dumper (c) 2004 Tobias Diedrich
5 * Licensed under GNU GPLv2 or (at your option) any later version.
7 * The subtitles are dumped to stdout.
17 #define FCC(a,b,c,d) (((a))|((b)<<8)|((c)<<16)|((d)<<24))
19 #define FCC_RIFF FCC('R','I','F','F')
20 #define FCC_LIST FCC('L','I','S','T')
21 #define FCC_strh FCC('s','t','r','h')
22 #define FCC_txts FCC('t','x','t','s')
23 #define FCC_GAB2 FCC('G','A','B','2')
25 #define GAB_LANGUAGE 0
27 #define GAB_LANGUAGE_UNICODE 2
28 #define GAB_ENTRY_UNICODE 3
29 #define GAB_RAWTEXTSUBTITLE 4
31 static unsigned int getle16(FILE* f
){
40 static unsigned int getle(FILE* f
){
45 res
|= fgetc(f
) << 16;
46 res
|= fgetc(f
) << 24;
51 static void skip(FILE *f
, int len
)
54 fseek(f
,len
,SEEK_CUR
);
56 void *buf
= malloc(len
);
62 static int stream_id(unsigned int id
)
65 c1
= (char)(id
& 0xff);
66 c2
= (char)((id
>> 8) & 0xff);
67 if (c1
>= '0' && c1
<= '9' &&
68 c2
>= '0' && c2
<= '9') {
76 static int dumpsub_gab2(FILE *f
, int size
) {
79 while (ret
+ 6 <= size
) {
84 id
= getle16(f
); ret
+= 2;
85 len
= getle(f
); ret
+= 4;
86 if (ret
+ len
> size
) break;
89 ret
+= fread(buf
, 1, len
, f
);
92 case GAB_LANGUAGE_UNICODE
: /* FIXME: convert to utf-8; endianness */
93 for (i
=0; i
<len
; i
++) buf
[i
] = buf
[i
*2];
95 fprintf(stderr
, "LANGUAGE: %s\n", buf
);
97 case GAB_ENTRY_UNICODE
: /* FIXME: convert to utf-8; endianness */
98 for (i
=0; i
<len
; i
++) buf
[i
] = buf
[i
*2];
100 fprintf(stderr
, "ENTRY: %s\n", buf
);
102 case GAB_RAWTEXTSUBTITLE
:
106 fprintf(stderr
, "Unknown type %d, len %d\n", id
, len
);
115 static void dump(FILE *f
) {
116 unsigned int id
, len
;
126 if (id
== FCC_RIFF
||
130 } else if (id
== FCC_strh
) {
131 id
= getle(f
); len
-= 4;
132 fprintf(stderr
, "Stream %d is %c%c%c%c",
138 if (id
== FCC_txts
) {
140 fprintf(stderr
, " (subtitle stream)");
142 fprintf(stderr
, ".\n");
144 } else if (stream_id(id
) == substream
) {
146 subid
= getle(f
); len
-= 4;
147 if (subid
!= FCC_GAB2
) {
149 "Unknown subtitle chunk %c%c%c%c (%08x).\n",
150 id
, id
>> 8, id
>> 16, id
>> 24, subid
);
153 len
-= dumpsub_gab2(f
, len
);
161 int main(int argc
,char* argv
[])
166 fprintf(stderr
, "Usage: %s <avi>\n", argv
[0]);
170 if (strcmp(argv
[argc
-1], "-") == 0) f
=stdin
;
171 else f
=fopen(argv
[argc
-1],"rb");
174 fprintf(stderr
, "Could not open '%s': %s\n",
175 argv
[argc
-1], strerror(errno
));