hlsdemux: Enable support for external subtitles
[platform/upstream/gstreamer.git] / ext / closedcaption / misc.h
1 /*
2  *  libzvbi -- Miscellaneous cows and chickens
3  *
4  *  Copyright (C) 2000-2003 Iñaki García Etxebarria
5  *  Copyright (C) 2002-2007 Michael H. Schimek
6  *
7  *  This library is free software; you can redistribute it and/or
8  *  modify it under the terms of the GNU Library General Public
9  *  License as published by the Free Software Foundation; either
10  *  version 2 of the License, or (at your option) any later version.
11  *
12  *  This library is distributed in the hope that it will be useful,
13  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  *  Library General Public License for more details.
16  *
17  *  You should have received a copy of the GNU Library General Public
18  *  License along with this library; if not, write to the
19  *  Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
20  *  Boston, MA  02110-1301  USA.
21  */
22
23 /* $Id: misc.h,v 1.24 2013-07-02 02:32:31 mschimek Exp $ */
24
25 #ifndef MISC_H
26 #define MISC_H
27
28 #include <stdio.h>
29 #include <stdlib.h>
30 #include <stddef.h>
31 #include <stdarg.h>
32 #include <string.h>
33 #include <inttypes.h>           /* (u)intXX_t */
34 #include <sys/types.h>          /* (s)size_t */
35 #include <float.h>              /* DBL_MAX */
36 #include <limits.h>             /* (S)SIZE_MAX */
37 #include <assert.h>
38 #include <glib.h>
39 #include <gst/gst.h>
40
41 #include "macros.h"
42
43 #define N_ELEMENTS(array) (sizeof (array) / sizeof (*(array)))
44
45 #ifdef __GNUC__
46
47 #if __GNUC__ < 3
48 /* Expect expression usually true/false, schedule accordingly. */
49 #  define likely(expr) (expr)
50 #  define unlikely(expr) (expr)
51 #else
52 #  define likely(expr) __builtin_expect(expr, 1)
53 #  define unlikely(expr) __builtin_expect(expr, 0)
54 #endif
55
56 #undef __i386__
57 #undef __i686__
58 /* FIXME #cpu is deprecated
59 #if #cpu (i386)
60 #  define __i386__ 1
61 #endif
62 #if #cpu (i686)
63 #  define __i686__ 1
64 #endif
65 */
66
67 /* &x == PARENT (&x.tm_min, struct tm, tm_min),
68    safer than &x == (struct tm *) &x.tm_min. A NULL _ptr is safe and
69    will return NULL, not -offsetof(_member). */
70 #undef PARENT
71 #define PARENT(_ptr, _type, _member) ({                                 \
72         __typeof__ (&((_type *) 0)->_member) _p = (_ptr);               \
73         (_p != 0) ? (_type *)(((char *) _p) - offsetof (_type,          \
74           _member)) : (_type *) 0;                                      \
75 })
76
77 /* Like PARENT(), to be used with const _ptr. */
78 #define CONST_PARENT(_ptr, _type, _member) ({                           \
79         __typeof__ (&((const _type *) 0)->_member) _p = (_ptr);         \
80         (_p != 0) ? (const _type *)(((const char *) _p) - offsetof      \
81          (const _type, _member)) : (const _type *) 0;                   \
82 })
83
84 /* Note the following macros have no side effects only when you
85    compile with GCC, so don't expect this. */
86
87 /* Absolute value of int, long or long long without a branch.
88    Note ABS (INT_MIN) -> INT_MAX + 1. */
89 #undef ABS
90 #define ABS(n) ({                                                       \
91         register __typeof__ (n) _n = (n), _t = _n;                      \
92         if (-1 == (-1 >> 1)) { /* do we have signed shifts? */          \
93                 _t >>= sizeof (_t) * 8 - 1;                             \
94                 _n ^= _t;                                               \
95                 _n -= _t;                                               \
96         } else if (_n < 0) { /* also warns if n is unsigned type */     \
97                 _n = -_n;                                               \
98         }                                                               \
99         /* return */ _n;                                                \
100 })
101
102 #undef MIN
103 #define MIN(x, y) ({                                                    \
104         __typeof__ (x) _x = (x);                                        \
105         __typeof__ (y) _y = (y);                                        \
106         (void)(&_x == &_y); /* warn if types do not match */            \
107         /* return */ (_x < _y) ? _x : _y;                               \
108 })
109
110 #undef MAX
111 #define MAX(x, y) ({                                                    \
112         __typeof__ (x) _x = (x);                                        \
113         __typeof__ (y) _y = (y);                                        \
114         (void)(&_x == &_y); /* warn if types do not match */            \
115         /* return */ (_x > _y) ? _x : _y;                               \
116 })
117
118 /* Note other compilers may swap only int, long or pointer. */
119 #undef SWAP
120 #define SWAP(x, y)                                                      \
121 do {                                                                    \
122         __typeof__ (x) _x = x;                                          \
123         x = y;                                                          \
124         y = _x;                                                         \
125 } while (0)
126
127 #undef SATURATE
128 #ifdef __i686__ /* has conditional move */
129 #define SATURATE(n, min, max) ({                                        \
130         __typeof__ (n) _n = (n);                                        \
131         __typeof__ (n) _min = (min);                                    \
132         __typeof__ (n) _max = (max);                                    \
133         (void)(&_n == &_min); /* warn if types do not match */          \
134         (void)(&_n == &_max);                                           \
135         if (_n < _min)                                                  \
136                 _n = _min;                                              \
137         if (_n > _max)                                                  \
138                 _n = _max;                                              \
139         /* return */ _n;                                                \
140 })
141 #else
142 #define SATURATE(n, min, max) ({                                        \
143         __typeof__ (n) _n = (n);                                        \
144         __typeof__ (n) _min = (min);                                    \
145         __typeof__ (n) _max = (max);                                    \
146         (void)(&_n == &_min); /* warn if types do not match */          \
147         (void)(&_n == &_max);                                           \
148         if (_n < _min)                                                  \
149                 _n = _min;                                              \
150         else if (_n > _max)                                             \
151                 _n = _max;                                              \
152         /* return */ _n;                                                \
153 })
154 #endif
155
156 #else /* !__GNUC__ */
157
158 #define likely(expr) (expr)
159 #define unlikely(expr) (expr)
160 #undef __i386__
161 #undef __i686__
162
163 static char *
164 PARENT_HELPER (char *p, unsigned int offset)
165 { return (0 == p) ? ((char *) 0) : p - offset; }
166
167 static const char *
168 CONST_PARENT_HELPER (const char *p, unsigned int offset)
169 { return (0 == p) ? ((char *) 0) : p - offset; }
170
171 #define PARENT(_ptr, _type, _member)                                    \
172         ((0 == offsetof (_type, _member)) ? (_type *)(_ptr)             \
173          : (_type *) PARENT_HELPER ((char *)(_ptr), offsetof (_type, _member)))
174 #define CONST_PARENT(_ptr, _type, _member)                              \
175         ((0 == offsetof (const _type, _member)) ? (const _type *)(_ptr) \
176          : (const _type *) CONST_PARENT_HELPER ((const char *)(_ptr),   \
177           offsetof (const _type, _member)))
178
179 #undef ABS
180 #define ABS(n) (((n) < 0) ? -(n) : (n))
181
182 #undef MIN
183 #define MIN(x, y) (((x) < (y)) ? (x) : (y))
184
185 #undef MAX
186 #define MAX(x, y) (((x) > (y)) ? (x) : (y))
187
188 #undef SWAP
189 #define SWAP(x, y)                                                      \
190 do {                                                                    \
191         long _x = x;                                                    \
192         x = y;                                                          \
193         y = _x;                                                         \
194 } while (0)
195
196 #undef SATURATE
197 #define SATURATE(n, min, max) MIN (MAX (min, n), max)
198
199 #endif /* !__GNUC__ */
200
201 /* 32 bit constant byte reverse, e.g. 0xAABBCCDD -> 0xDDCCBBAA. */
202 #define SWAB32(m)                                                       \
203         (+ (((m) & 0xFF000000) >> 24)                                   \
204          + (((m) & 0xFF0000) >> 8)                                      \
205          + (((m) & 0xFF00) << 8)                                        \
206          + (((m) & 0xFF) << 24))
207
208 #ifdef HAVE_BUILTIN_POPCOUNT
209 #  define popcnt(x) __builtin_popcount ((uint32_t)(x))
210 #else
211 #  define popcnt(x) _vbi_popcnt (x)
212 #endif
213
214 extern unsigned int
215 _vbi_popcnt                     (uint32_t               x);
216
217 /* NB GCC inlines and optimizes these functions when size is const. */
218 #define SET(var) memset (&(var), ~0, sizeof (var))
219
220 #define CLEAR(var) memset (&(var), 0, sizeof (var))
221
222 /* Useful to copy arrays, otherwise use assignment. */
223 #define COPY(d, s)                                                      \
224         (assert (sizeof (d) == sizeof (s)), memcpy (d, s, sizeof (d)))
225
226 /* Copy string const into char array. */
227 #define STRACPY(array, s)                                               \
228 do {                                                                    \
229         /* Complain if s is no string const or won't fit. */            \
230         const char t_[sizeof (array) - 1] _vbi_unused = s;              \
231                                                                         \
232         memcpy (array, s, sizeof (s));                                  \
233 } while (0)
234
235 /* Copy bits through mask. */
236 #define COPY_SET_MASK(dest, from, mask)                                 \
237         (dest ^= (from) ^ (dest & (mask)))
238
239 /* Set bits if cond is TRUE, clear if FALSE. */
240 #define COPY_SET_COND(dest, bits, cond)                                 \
241          ((cond) ? (dest |= (bits)) : (dest &= ~(bits)))
242
243 /* Set and clear bits. */
244 #define COPY_SET_CLEAR(dest, set, clear)                                \
245         (dest = (dest & ~(clear)) | (set))
246
247 /* For applications, debugging and fault injection during unit tests. */
248
249 #define vbi_malloc malloc
250 #define vbi_realloc realloc
251 #define vbi_strdup strdup
252 #define vbi_free free
253
254 #define vbi_cache_malloc vbi_malloc
255 #define vbi_cache_free vbi_free
256
257 /* Helper functions. */
258
259 _vbi_inline int
260 _vbi_to_ascii                   (int                    c)
261 {
262         if (c < 0)
263                 return '?';
264
265         c &= 0x7F;
266
267         if (c < 0x20 || c >= 0x7F)
268                 return '.';
269
270         return c;
271 }
272
273 typedef struct {
274         const char *            key;
275         int                     value;
276 } _vbi_key_value_pair;
277
278 extern vbi_bool
279 _vbi_keyword_lookup             (int *                  value,
280                                  const char **          inout_s,
281                                  const _vbi_key_value_pair * table,
282                                  unsigned int           n_pairs)
283   _vbi_nonnull ((1, 2, 3));
284
285 extern void
286 _vbi_shrink_vector_capacity     (void **                vector,
287                                  size_t *               capacity,
288                                  size_t                 min_capacity,
289                                  size_t                 element_size)
290   _vbi_nonnull ((1, 2));
291 extern vbi_bool
292 _vbi_grow_vector_capacity       (void **                vector,
293                                  size_t *               capacity,
294                                  size_t                 min_capacity,
295                                  size_t                 element_size)
296   _vbi_nonnull ((1, 2));
297
298 GST_DEBUG_CATEGORY_EXTERN (libzvbi_debug);
299
300 #ifndef GST_DISABLE_GST_DEBUG
301 /* Logging stuff. */
302 #ifdef G_HAVE_ISO_VARARGS
303 #define VBI_CAT_LEVEL_LOG(level,object,...) G_STMT_START{               \
304   if (G_UNLIKELY ((level) <= GST_LEVEL_MAX && (level) <= _gst_debug_min)) {                                             \
305           gst_debug_log (libzvbi_debug, (level), __FILE__, GST_FUNCTION, __LINE__, \
306         (GObject *) (object), __VA_ARGS__);                             \
307   }                                                                     \
308 }G_STMT_END
309 #else /* G_HAVE_GNUC_VARARGS */
310 #ifdef G_HAVE_GNUC_VARARGS
311 #define VBI_CAT_LEVEL_LOG(level,object,args...) G_STMT_START{   \
312   if (G_UNLIKELY ((level) <= GST_LEVEL_MAX && (level) <= _gst_debug_min)) {                                             \
313           gst_debug_log (libzvbi_debug, (level), __FILE__, GST_FUNCTION, __LINE__, \
314         (GObject *) (object), ##args );                                 \
315   }                                                                     \
316 }G_STMT_END
317 #else /* no variadic macros, use inline */
318 static inline void
319 VBI_CAT_LEVEL_LOG_valist (GstDebugCategory * cat,
320     GstDebugLevel level, gpointer object, const char *format, va_list varargs)
321 {
322   if (G_UNLIKELY ((level) <= GST_LEVEL_MAX && (level) <= _gst_debug_min)) {
323     gst_debug_log_valist (cat, level, "", "", 0, (GObject *) object, format,
324         varargs);
325   }
326 }
327
328 static inline void
329 VBI_CAT_LEVEL_LOG (GstDebugLevel level,
330     gpointer object, const char *format, ...)
331 {
332   va_list varargs;
333
334   va_start (varargs, format);
335   GST_CAT_LEVEL_LOG_valist (libzvbi_debug, level, object, format, varargs);
336   va_end (varargs);
337 }
338 #endif
339 #endif /* G_HAVE_ISO_VARARGS */
340 #else
341 static inline void
342 VBI_CAT_LEVEL_LOG (GstDebugLevel level,
343     gpointer object, const char *format, ...)
344 {
345 }
346 #endif  /* GST_DISABLE_GST_DEBUG */
347
348 #ifdef G_HAVE_GNUC_VARARGS
349 #define error(hook, templ, args...)                                     \
350         VBI_CAT_LEVEL_LOG (GST_LEVEL_ERROR, NULL, templ , ##args)
351 #define warning(hook, templ, args...)                                   \
352         VBI_CAT_LEVEL_LOG (GST_LEVEL_WARNING, NULL, templ , ##args)
353 #define notice(hook, templ, args...)                                    \
354         VBI_CAT_LEVEL_LOG (GST_LEVEL_INFO, NULL, templ , ##args)
355 #define info(hook, templ, args...)                                      \
356         VBI_CAT_LEVEL_LOG (GST_LEVEL_INFO, NULL, templ , ##args)
357 #define debug1(hook, templ, args...)                                    \
358         VBI_CAT_LEVEL_LOG (GST_LEVEL_DEBUG, NULL, templ , ##args)
359 #define debug2(hook, templ, args...)                                    \
360         VBI_CAT_LEVEL_LOG (GST_LEVEL_LOG, NULL, templ , ##args)
361 #define debug3(hook, templ, args...)                                    \
362         VBI_CAT_LEVEL_LOG (GST_LEVEL_TRACE, NULL, templ , ##args)
363 #elif defined(G_HAVE_ISO_VARARGS)
364 #define error(hook, templ, ...)                                 \
365         VBI_CAT_LEVEL_LOG (GST_LEVEL_ERROR, NULL, templ, __VA_ARGS__)
366 #define warning(hook, templ, ...)                                       \
367         VBI_CAT_LEVEL_LOG (GST_LEVEL_WARNING, NULL, templ, __VA_ARGS__)
368 #define notice(hook, templ, ...)                                        \
369         VBI_CAT_LEVEL_LOG (GST_LEVEL_INFO, NULL, templ, __VA_ARGS__)
370 #define info(hook, templ, ...)                                  \
371         VBI_CAT_LEVEL_LOG (GST_LEVEL_INFO, NULL, templ, __VA_ARGS__)
372 #define debug1(hook, templ, ...)                                        \
373         VBI_CAT_LEVEL_LOG (GST_LEVEL_DEBUG, NULL, templ, __VA_ARGS__)
374 #define debug2(hook, templ, ...)                                        \
375         VBI_CAT_LEVEL_LOG (GST_LEVEL_LOG, NULL, templ, __VA_ARGS__)
376 #define debug3(hook, templ, ...)                                        \
377         VBI_CAT_LEVEL_LOG (GST_LEVEL_TRACE, NULL, templ, __VA_ARGS__)
378 #else
379 /* if someone needs this, they can implement the inline functions for it */
380 #error "variadic macros are required"
381 #endif
382
383
384 #if 0                           /* Replaced logging with GStreamer logging system */
385 extern _vbi_log_hook            _vbi_global_log;
386
387 extern void
388 _vbi_log_vprintf                (vbi_log_fn *           log_fn,
389                                  void *                 user_data,
390                                  vbi_log_mask           level,
391                                  const char *           source_file,
392                                  const char *           context,
393                                  const char *           templ,
394                                  va_list                ap)
395   _vbi_nonnull ((1, 4, 5, 6));
396 extern void
397 _vbi_log_printf         (vbi_log_fn *           log_fn,
398                                  void *                 user_data,
399                                  vbi_log_mask           level,
400                                  const char *           source_file,
401                                  const char *           context,
402                                  const char *           templ,
403                                  ...)
404   _vbi_nonnull ((1, 4, 5, 6)) _vbi_format ((printf, 6, 7));
405
406 #define _vbi_log(hook, level, templ, args...)                           \
407 do {                                                                    \
408         _vbi_log_hook *_h = hook;                                       \
409                                                                         \
410         if ((NULL != _h && 0 != (_h->mask & level))                     \
411             || (_h = &_vbi_global_log, 0 != (_h->mask & level)))        \
412                 _vbi_log_printf (_h->fn, _h->user_data,         \
413                                   level, __FILE__, __FUNCTION__,        \
414                                   templ , ##args);                      \
415 } while (0)
416
417 #define _vbi_vlog(hook, level, templ, ap)                               \
418 do {                                                                    \
419         _vbi_log_hook *_h = hook;                                       \
420                                                                         \
421         if ((NULL != _h && 0 != (_h->mask & level))                     \
422             || (_h = &_vbi_global_log, 0 != (_h->mask & level)))        \
423                 _vbi_log_vprintf (_h->fn, _h->user_data,                \
424                                   level, __FILE__, __FUNCTION__,        \
425                                   templ, ap);                           \
426 } while (0)
427 #define error(hook, templ, args...)                                     \
428         _vbi_log (hook, VBI_LOG_ERROR, templ , ##args)
429 #define warning(hook, templ, args...)                                   \
430         _vbi_log (hook, VBI_LOG_ERROR, templ , ##args)
431 #define notice(hook, templ, args...)                                    \
432         _vbi_log (hook, VBI_LOG_NOTICE, templ , ##args)
433 #define info(hook, templ, args...)                                      \
434         _vbi_log (hook, VBI_LOG_INFO, templ , ##args)
435 #define debug1(hook, templ, args...)                                    \
436         _vbi_log (hook, VBI_LOG_DEBUG, templ , ##args)
437 #define debug2(hook, templ, args...)                                    \
438         _vbi_log (hook, VBI_LOG_DEBUG2, templ , ##args)
439 #define debug3(hook, templ, args...)                                    \
440         _vbi_log (hook, VBI_LOG_DEBUG3, templ , ##args)
441 #endif
442
443 /* Portability stuff. */
444
445 /* These should be defined in inttypes.h. */
446 #ifndef PRId64
447 #  define PRId64 "lld"
448 #endif
449 #ifndef PRIu64
450 #  define PRIu64 "llu"
451 #endif
452 #ifndef PRIx64
453 #  define PRIx64 "llx"
454 #endif
455
456 /* Should be defined in C99 limits.h? */
457 #ifndef SIZE_MAX
458 #  define SIZE_MAX ((size_t) -1)
459 #endif
460
461 #ifndef TIME_MIN
462 #  define TIME_MIN (_vbi_time_min ())
463 _vbi_inline time_t
464 _vbi_time_min                   (void)
465 {
466         const time_t t = (time_t) -1.25;
467
468         if (t < -1) {
469                 return (time_t)((sizeof (time_t) > 4) ? DBL_MIN : FLT_MIN);
470         } else if (t < 0) {
471                 return ((uint64_t) 1) << (sizeof (time_t) * 8 - 1);
472         } else {
473                 return 0;
474         }
475 }
476 #endif
477
478 #ifndef TIME_MAX
479 #  define TIME_MAX (_vbi_time_max ())
480 _vbi_inline time_t
481 _vbi_time_max                   (void)
482 {
483         const time_t t = (time_t) -1.25;
484
485         if (t < -1) {
486                 return (time_t)((sizeof (time_t) > 4) ? DBL_MAX : FLT_MAX);
487         } else if (t < 0) {
488                 /* Most likely signed 32 or 64 bit. */
489                 return (((uint64_t) 1) << (sizeof (time_t) * 8 - 1)) - 1;
490         } else {
491                 return -1;
492         }
493 }
494 #endif
495
496 /* __va_copy is a GNU extension. */
497 #ifndef __va_copy
498 #  define __va_copy(ap1, ap2) do { ap1 = ap2; } while (0)
499 #endif
500
501 #if 0
502 /* Use this instead of strncpy(). strlcpy() is a BSD extension. */
503 #ifndef HAVE_STRLCPY
504 #  define strlcpy _vbi_strlcpy
505 #endif
506 #undef strncpy
507 #define strncpy use_strlcpy_instead
508
509 extern size_t
510 _vbi_strlcpy                    (char *                 dst,
511                                  const char *           src,
512                                  size_t                 size)
513   _vbi_nonnull ((1, 2));
514 #endif
515
516 /* /\* strndup() is a BSD/GNU extension. *\/ */
517 /* #ifndef HAVE_STRNDUP */
518 /* #  define strndup _vbi_strndup */
519 /* #endif */
520
521 /* extern char * */
522 /* _vbi_strndup                 (const char *           s, */
523 /*                               size_t                 len) */
524 /*   _vbi_nonnull ((1)); */
525
526 /* vasprintf() is a GNU extension. */
527 #ifndef HAVE_VASPRINTF
528 #  define vasprintf _vbi_vasprintf
529 #endif
530
531 extern int
532 _vbi_vasprintf                  (char **                dstp,
533                                  const char *           templ,
534                                  va_list                ap)
535   _vbi_nonnull ((1, 2));
536
537 /* asprintf() is a GNU extension. */
538 #ifndef HAVE_ASPRINTF
539 #  define asprintf _vbi_asprintf
540 #endif
541
542 extern int
543 _vbi_asprintf                   (char **                dstp,
544                                  const char *           templ,
545                                  ...)
546   _vbi_nonnull ((1, 2)) _vbi_format ((printf, 2, 3));
547
548 #undef sprintf
549 #define sprintf use_snprintf_or_asprintf_instead
550
551 #endif /* MISC_H */
552
553 /*
554 Local variables:
555 c-set-style: K&R
556 c-basic-offset: 8
557 End:
558 */