diff options
Diffstat (limited to 'src/plugins/mpeg_extractor.c')
-rw-r--r-- | src/plugins/mpeg_extractor.c | 253 |
1 files changed, 129 insertions, 124 deletions
diff --git a/src/plugins/mpeg_extractor.c b/src/plugins/mpeg_extractor.c index 627cae0..9c5f0b8 100644 --- a/src/plugins/mpeg_extractor.c +++ b/src/plugins/mpeg_extractor.c | |||
@@ -34,7 +34,11 @@ | |||
34 | * @param t type of the meta data | 34 | * @param t type of the meta data |
35 | * @param s meta data value in utf8 format | 35 | * @param s meta data value in utf8 format |
36 | */ | 36 | */ |
37 | #define ADD(s,t) do { if (0 != ec->proc (ec->cls, "mpeg", t, EXTRACTOR_METAFORMAT_UTF8, "text/plain", s, strlen (s) + 1)) goto EXIT; } while (0) | 37 | #define ADD(s,t) do { if (0 != ec->proc (ec->cls, "mpeg", t, \ |
38 | EXTRACTOR_METAFORMAT_UTF8, \ | ||
39 | "text/plain", s, strlen (s) \ | ||
40 | + 1)) goto EXIT; \ | ||
41 | } while (0) | ||
38 | 42 | ||
39 | 43 | ||
40 | /** | 44 | /** |
@@ -68,10 +72,10 @@ EXTRACTOR_mpeg_extract_method (struct EXTRACTOR_ExtractContext *ec) | |||
68 | if (NULL == (handle = mpeg2_init ())) | 72 | if (NULL == (handle = mpeg2_init ())) |
69 | return; | 73 | return; |
70 | if (NULL == (info = mpeg2_info (handle))) | 74 | if (NULL == (info = mpeg2_info (handle))) |
71 | { | 75 | { |
72 | mpeg2_close (handle); | 76 | mpeg2_close (handle); |
73 | return; | 77 | return; |
74 | } | 78 | } |
75 | fsize = ec->get_size (ec->cls); | 79 | fsize = ec->get_size (ec->cls); |
76 | buf = NULL; | 80 | buf = NULL; |
77 | have_gop = 0; | 81 | have_gop = 0; |
@@ -86,130 +90,131 @@ EXTRACTOR_mpeg_extract_method (struct EXTRACTOR_ExtractContext *ec) | |||
86 | fmac = 0; | 90 | fmac = 0; |
87 | lformat[0] = '\0'; | 91 | lformat[0] = '\0'; |
88 | while (1) | 92 | while (1) |
93 | { | ||
94 | state = mpeg2_parse (handle); | ||
95 | switch (state) | ||
89 | { | 96 | { |
90 | state = mpeg2_parse (handle); | 97 | case STATE_BUFFER: |
91 | switch (state) | 98 | if (fail_count > 16) |
92 | { | 99 | goto EXIT; /* do not read large non-mpeg files */ |
93 | case STATE_BUFFER: | 100 | fail_count++; |
94 | if (fail_count > 16) | 101 | if (0 >= (avail = ec->read (ec->cls, |
95 | goto EXIT; /* do not read large non-mpeg files */ | 102 | &buf, |
96 | fail_count++; | 103 | 16 * 1024))) |
97 | if (0 >= (avail = ec->read (ec->cls, | 104 | goto EXIT; |
98 | &buf, | 105 | mpeg2_buffer (handle, buf, buf + avail); |
99 | 16 * 1024))) | 106 | break; |
100 | goto EXIT; | 107 | case STATE_SEQUENCE: |
101 | mpeg2_buffer (handle, buf, buf + avail); | 108 | fail_count = 0; |
102 | break; | 109 | format[0] = fsize; |
103 | case STATE_SEQUENCE: | 110 | format[0]++; |
104 | fail_count = 0; | 111 | if (0 == mime) |
105 | format[0] = fsize; | 112 | { |
106 | format[0]++; | 113 | mime = 1; |
107 | if (0 == mime) | 114 | ADD ("video/mpeg", EXTRACTOR_METATYPE_MIMETYPE); |
108 | { | 115 | } |
109 | mime = 1; | 116 | snprintf (format, |
110 | ADD ("video/mpeg", EXTRACTOR_METATYPE_MIMETYPE); | 117 | sizeof(format), "%ux%u", |
111 | } | 118 | info->sequence->width, info->sequence->height); |
112 | snprintf (format, | 119 | if (0 != strcmp (lformat, |
113 | sizeof(format), "%ux%u", | 120 | format)) |
114 | info->sequence->width, info->sequence->height); | 121 | { |
115 | if (0 != strcmp (lformat, | 122 | strcpy (lformat, |
116 | format)) | 123 | format); |
117 | { | 124 | ADD (format, EXTRACTOR_METATYPE_IMAGE_DIMENSIONS); |
118 | strcpy (lformat, | 125 | } |
119 | format); | 126 | switch (info->sequence->flags & SEQ_VIDEO_FORMAT_UNSPECIFIED) |
120 | ADD (format, EXTRACTOR_METATYPE_IMAGE_DIMENSIONS); | 127 | { |
121 | } | 128 | case SEQ_VIDEO_FORMAT_PAL: |
122 | switch (info->sequence->flags & SEQ_VIDEO_FORMAT_UNSPECIFIED) | 129 | if (0 == fpal) |
123 | { | 130 | { |
124 | case SEQ_VIDEO_FORMAT_PAL: | 131 | fpal = 1; |
125 | if (0 == fpal) | 132 | ADD ("PAL", EXTRACTOR_METATYPE_BROADCAST_TELEVISION_SYSTEM); |
126 | { | 133 | } |
127 | fpal = 1; | 134 | break; |
128 | ADD ("PAL", EXTRACTOR_METATYPE_BROADCAST_TELEVISION_SYSTEM); | 135 | case SEQ_VIDEO_FORMAT_NTSC: |
129 | } | 136 | if (0 == fntsc) |
130 | break; | 137 | { |
131 | case SEQ_VIDEO_FORMAT_NTSC: | 138 | fntsc = 1; |
132 | if (0 == fntsc) | 139 | ADD ("NTSC", EXTRACTOR_METATYPE_BROADCAST_TELEVISION_SYSTEM); |
133 | { | 140 | } |
134 | fntsc = 1; | 141 | break; |
135 | ADD ("NTSC", EXTRACTOR_METATYPE_BROADCAST_TELEVISION_SYSTEM); | 142 | case SEQ_VIDEO_FORMAT_SECAM: |
136 | } | 143 | if (0 == fsecam) |
137 | break; | 144 | { |
138 | case SEQ_VIDEO_FORMAT_SECAM: | 145 | fsecam = 1; |
139 | if (0 == fsecam) | 146 | ADD ("SECAM", EXTRACTOR_METATYPE_BROADCAST_TELEVISION_SYSTEM); |
140 | { | 147 | } |
141 | fsecam = 1; | 148 | break; |
142 | ADD ("SECAM", EXTRACTOR_METATYPE_BROADCAST_TELEVISION_SYSTEM); | 149 | case SEQ_VIDEO_FORMAT_MAC: |
143 | } | 150 | if (0 == fmac) |
144 | break; | 151 | { |
145 | case SEQ_VIDEO_FORMAT_MAC: | 152 | fmac = 1; |
146 | if (0 == fmac) | 153 | ADD ("MAC", EXTRACTOR_METATYPE_BROADCAST_TELEVISION_SYSTEM); |
147 | { | 154 | } |
148 | fmac = 1; | 155 | break; |
149 | ADD ("MAC", EXTRACTOR_METATYPE_BROADCAST_TELEVISION_SYSTEM); | 156 | default: |
150 | } | 157 | break; |
151 | break; | 158 | } |
152 | default: | 159 | if ((info->sequence->flags & SEQ_FLAG_MPEG2) > 0) |
153 | break; | 160 | { |
154 | } | 161 | if (0 == fmt1) |
155 | if ((info->sequence->flags & SEQ_FLAG_MPEG2) > 0) | 162 | { |
156 | { | 163 | fmt1 = 1; |
157 | if (0 == fmt1) | 164 | ADD ("MPEG2", EXTRACTOR_METATYPE_FORMAT_VERSION); |
158 | { | 165 | } |
159 | fmt1 = 1; | 166 | } |
160 | ADD ("MPEG2", EXTRACTOR_METATYPE_FORMAT_VERSION); | 167 | else |
161 | } | 168 | { |
162 | } | 169 | if (0 == fmt2) |
163 | else | 170 | { |
164 | { | 171 | fmt2 = 1; |
165 | if (0 == fmt2) | 172 | ADD ("MPEG1", EXTRACTOR_METATYPE_FORMAT_VERSION); |
166 | { | 173 | } |
167 | fmt2 = 1; | 174 | } |
168 | ADD ("MPEG1", EXTRACTOR_METATYPE_FORMAT_VERSION); | 175 | if ( (0 == did_seek) && |
169 | } | 176 | (fsize != -1) && |
170 | } | 177 | (fsize > 1024 * 256 * 2) ) |
171 | if ( (0 == did_seek) && | 178 | { |
172 | (fsize != -1) && | 179 | /* skip to the end of the mpeg for speed */ |
173 | (fsize > 1024 * 256 * 2) ) | 180 | did_seek = 1; |
174 | { | 181 | ec->seek (ec->cls, |
175 | /* skip to the end of the mpeg for speed */ | 182 | fsize - 256 * 1024, |
176 | did_seek = 1; | 183 | SEEK_SET); |
177 | ec->seek (ec->cls, | 184 | } |
178 | fsize - 256 * 1024, | 185 | break; |
179 | SEEK_SET); | 186 | case STATE_GOP: |
180 | } | 187 | fail_count = 0; |
181 | break; | 188 | if ( (NULL != info->gop) && |
182 | case STATE_GOP: | 189 | (0 != info->gop->pictures) ) |
183 | fail_count = 0; | 190 | { |
184 | if ( (NULL != info->gop) && | 191 | snprintf (gop_format, |
185 | (0 != info->gop->pictures) ) | 192 | sizeof (gop_format), |
186 | { | 193 | "%02u:%02u:%02u (%u frames)", |
187 | snprintf (gop_format, | 194 | info->gop->hours, |
188 | sizeof (gop_format), | 195 | info->gop->minutes, |
189 | "%02u:%02u:%02u (%u frames)", | 196 | info->gop->seconds, |
190 | info->gop->hours, | 197 | info->gop->pictures); |
191 | info->gop->minutes, | 198 | have_gop = 1; |
192 | info->gop->seconds, | 199 | } |
193 | info->gop->pictures); | 200 | break; |
194 | have_gop = 1; | 201 | case STATE_SLICE: |
195 | } | 202 | fail_count = 0; |
196 | break; | 203 | break; |
197 | case STATE_SLICE: | 204 | case STATE_END: |
198 | fail_count = 0; | 205 | fail_count = 0; |
199 | break; | 206 | break; |
200 | case STATE_END: | 207 | case STATE_INVALID: |
201 | fail_count = 0; | 208 | goto EXIT; |
202 | break; | 209 | default: |
203 | case STATE_INVALID: | 210 | break; |
204 | goto EXIT; | ||
205 | default: | ||
206 | break; | ||
207 | } | ||
208 | } | 211 | } |
209 | EXIT: | 212 | } |
213 | EXIT: | ||
210 | if (1 == have_gop) | 214 | if (1 == have_gop) |
211 | ADD (gop_format, EXTRACTOR_METATYPE_DURATION); | 215 | ADD (gop_format, EXTRACTOR_METATYPE_DURATION); |
212 | mpeg2_close (handle); | 216 | mpeg2_close (handle); |
213 | } | 217 | } |
214 | 218 | ||
219 | |||
215 | /* end of mpeg_extractor.c */ | 220 | /* end of mpeg_extractor.c */ |