summaryrefslogtreecommitdiffstats
path: root/libmpeg2
diff options
context:
space:
mode:
authorhenry <henry@b3059339-0415-0410-9bf9-f77b7e298cf2>2004-08-02 11:26:43 +0000
committerhenry <henry@b3059339-0415-0410-9bf9-f77b7e298cf2>2004-08-02 11:26:43 +0000
commit943139cc78038c3aea0837229298cb2c08e3f8a2 (patch)
tree56b2a2dac2c09fe1016e3e146ec19cb2aae0777a /libmpeg2
parent4779094c4be9af5ec0c5145d8a460b75e4a510c8 (diff)
downloadmpv-943139cc78038c3aea0837229298cb2c08e3f8a2.tar.bz2
mpv-943139cc78038c3aea0837229298cb2c08e3f8a2.tar.xz
Importing libmpeg2 from mpeg2dec-0.4.0b
git-svn-id: svn://svn.mplayerhq.hu/mplayer/trunk@12933 b3059339-0415-0410-9bf9-f77b7e298cf2
Diffstat (limited to 'libmpeg2')
-rw-r--r--libmpeg2/Makefile4
-rw-r--r--libmpeg2/alloc.c54
-rw-r--r--libmpeg2/alpha_asm.h75
-rw-r--r--libmpeg2/attributes.h2
-rw-r--r--libmpeg2/convert.h56
-rw-r--r--libmpeg2/cpu_accel.c54
-rw-r--r--libmpeg2/cpu_state.c4
-rw-r--r--libmpeg2/decode.c255
-rw-r--r--libmpeg2/header.c643
-rw-r--r--libmpeg2/idct.c95
-rw-r--r--libmpeg2/idct_alpha.c75
-rw-r--r--libmpeg2/idct_altivec.c128
-rw-r--r--libmpeg2/idct_mlib.c60
-rw-r--r--libmpeg2/idct_mmx.c10
-rw-r--r--libmpeg2/mmx.h2
-rw-r--r--libmpeg2/motion_comp.c7
-rw-r--r--libmpeg2/motion_comp_alpha.c198
-rw-r--r--libmpeg2/motion_comp_altivec.c1
-rw-r--r--libmpeg2/motion_comp_mlib.c190
-rw-r--r--libmpeg2/motion_comp_mmx.c2
-rw-r--r--libmpeg2/motion_comp_vis.c2061
-rw-r--r--libmpeg2/mpeg2.h136
-rw-r--r--libmpeg2/mpeg2_internal.h144
-rw-r--r--libmpeg2/slice.c1299
-rw-r--r--libmpeg2/vis.h328
-rw-r--r--libmpeg2/vlc.h87
26 files changed, 4299 insertions, 1671 deletions
diff --git a/libmpeg2/Makefile b/libmpeg2/Makefile
index b7e93d796b..2c4c77b467 100644
--- a/libmpeg2/Makefile
+++ b/libmpeg2/Makefile
@@ -3,10 +3,10 @@ LIBNAME = libmpeg2.a
include ../config.mak
-SRCS = alloc.c cpu_accel.c cpu_state.c decode.c header.c idct.c idct_alpha.c idct_mlib.c idct_mmx.c motion_comp.c motion_comp_alpha.c motion_comp_mlib.c motion_comp_mmx.c slice.c
+SRCS = alloc.c cpu_accel.c cpu_state.c decode.c header.c idct.c idct_alpha.c idct_mmx.c motion_comp.c motion_comp_alpha.c motion_comp_mmx.c slice.c
OBJS = $(SRCS:.c=.o)
-INCLUDE = -I. -I../libvo -I.. $(EXTRA_INC) $(MLIB_INC)
+INCLUDE = -I. -I../libvo -I.. $(EXTRA_INC)
CFLAGS = $(OPTFLAGS) $(INCLUDE) -DMPG12PLAY
ifeq ($(TARGET_ALTIVEC),yes)
diff --git a/libmpeg2/alloc.c b/libmpeg2/alloc.c
index 2e4792e94d..0698937bce 100644
--- a/libmpeg2/alloc.c
+++ b/libmpeg2/alloc.c
@@ -21,56 +21,50 @@
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
-#include "config.h"
-
#include <stdlib.h>
#include <inttypes.h>
#include "mpeg2.h"
-#include "mpeg2_internal.h"
-
-#if defined(HAVE_MEMALIGN) && !defined(__cplusplus)
-/* some systems have memalign() but no declaration for it */
-void * memalign (size_t align, size_t size);
-#endif
-void * (* mpeg2_malloc_hook) (int size, int reason) = NULL;
-int (* mpeg2_free_hook) (void * buf) = NULL;
+static void * (* malloc_hook) (unsigned size, mpeg2_alloc_t reason) = NULL;
+static int (* free_hook) (void * buf) = NULL;
-void * mpeg2_malloc (int size, int reason)
+void * mpeg2_malloc (unsigned size, mpeg2_alloc_t reason)
{
char * buf;
- if (mpeg2_malloc_hook) {
- buf = (char *) mpeg2_malloc_hook (size, reason);
+ if (malloc_hook) {
+ buf = (char *) malloc_hook (size, reason);
if (buf)
return buf;
}
-#if defined(HAVE_MEMALIGN) && !defined(__cplusplus) && !defined(DEBUG)
- return memalign (16, size);
-#else
- buf = (char *) malloc (size + 15 + sizeof (void **));
- if (buf) {
- char * align_buf;
+ if (size) {
+ buf = (char *) malloc (size + 63 + sizeof (void **));
+ if (buf) {
+ char * align_buf;
- align_buf = buf + 15 + sizeof (void **);
- align_buf -= (long)align_buf & 15;
- *(((void **)align_buf) - 1) = buf;
- return align_buf;
+ align_buf = buf + 63 + sizeof (void **);
+ align_buf -= (long)align_buf & 63;
+ *(((void **)align_buf) - 1) = buf;
+ return align_buf;
+ }
}
return NULL;
-#endif
}
void mpeg2_free (void * buf)
{
- if (mpeg2_free_hook && mpeg2_free_hook (buf))
+ if (free_hook && free_hook (buf))
return;
-#if defined(HAVE_MEMALIGN) && !defined(__cplusplus) && !defined(DEBUG)
- free (buf);
-#else
- free (*(((void **)buf) - 1));
-#endif
+ if (buf)
+ free (*(((void **)buf) - 1));
+}
+
+void mpeg2_malloc_hooks (void * malloc (unsigned, mpeg2_alloc_t),
+ int free (void *))
+{
+ malloc_hook = malloc;
+ free_hook = free;
}
diff --git a/libmpeg2/alpha_asm.h b/libmpeg2/alpha_asm.h
index 6864ccc2e7..bf1081f249 100644
--- a/libmpeg2/alpha_asm.h
+++ b/libmpeg2/alpha_asm.h
@@ -1,6 +1,6 @@
/*
* Alpha assembly macros
- * Copyright (c) 2002 Falk Hueffner <falk@debian.org>
+ * Copyright (c) 2002-2003 Falk Hueffner <falk@debian.org>
*
* This file is part of mpeg2dec, a free MPEG-2 video stream decoder.
* See http://libmpeg2.sourceforge.net/ for updates.
@@ -83,22 +83,11 @@ struct unaligned_long { uint64_t l; } __attribute__((packed));
#define ldq_u(p) (*(const uint64_t *) (((uint64_t) (p)) & ~7ul))
#define uldq(a) (((const struct unaligned_long *) (a))->l)
-#if GNUC_PREREQ(3,0)
-/* Unfortunately, __builtin_prefetch is slightly buggy on Alpha. The
- defines here are kludged so we still get the right
- instruction. This needs to be adapted as soon as gcc is fixed. */
-# define prefetch(p) __builtin_prefetch((p), 0, 1)
-# define prefetch_en(p) __builtin_prefetch((p), 1, 1)
-# define prefetch_m(p) __builtin_prefetch((p), 0, 0)
-# define prefetch_men(p) __builtin_prefetch((p), 1, 0)
-#else
-# define prefetch(p) asm volatile("ldl $31,%0" : : "m"(*(const char *) (p)) : "memory")
-# define prefetch_en(p) asm volatile("ldq $31,%0" : : "m"(*(const char *) (p)) : "memory")
-# define prefetch_m(p) asm volatile("lds $f31,%0" : : "m"(*(const char *) (p)) : "memory")
-# define prefetch_men(p) asm volatile("ldt $f31,%0" : : "m"(*(const char *) (p)) : "memory")
-#endif
-
#if GNUC_PREREQ(3,3)
+#define prefetch(p) __builtin_prefetch((p), 0, 1)
+#define prefetch_en(p) __builtin_prefetch((p), 0, 0)
+#define prefetch_m(p) __builtin_prefetch((p), 1, 1)
+#define prefetch_men(p) __builtin_prefetch((p), 1, 0)
#define cmpbge __builtin_alpha_cmpbge
/* Avoid warnings. */
#define extql(a, b) __builtin_alpha_extql(a, (uint64_t) (b))
@@ -109,6 +98,24 @@ struct unaligned_long { uint64_t l; } __attribute__((packed));
#define amask __builtin_alpha_amask
#define implver __builtin_alpha_implver
#define rpcc __builtin_alpha_rpcc
+#else
+#define prefetch(p) asm volatile("ldl $31,%0" : : "m"(*(const char *) (p)) : "memory")
+#define prefetch_en(p) asm volatile("ldq $31,%0" : : "m"(*(const char *) (p)) : "memory")
+#define prefetch_m(p) asm volatile("lds $f31,%0" : : "m"(*(const char *) (p)) : "memory")
+#define prefetch_men(p) asm volatile("ldt $f31,%0" : : "m"(*(const char *) (p)) : "memory")
+#define cmpbge(a, b) ({ uint64_t __r; asm ("cmpbge %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
+#define extql(a, b) ({ uint64_t __r; asm ("extql %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
+#define extwl(a, b) ({ uint64_t __r; asm ("extwl %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
+#define extqh(a, b) ({ uint64_t __r; asm ("extqh %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
+#define zap(a, b) ({ uint64_t __r; asm ("zap %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
+#define zapnot(a, b) ({ uint64_t __r; asm ("zapnot %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
+#define amask(a) ({ uint64_t __r; asm ("amask %1,%0" : "=r" (__r) : "rI" (a)); __r; })
+#define implver() ({ uint64_t __r; asm ("implver %0" : "=r" (__r)); __r; })
+#define rpcc() ({ uint64_t __r; asm volatile ("rpcc %0" : "=r" (__r)); __r; })
+#endif
+#define wh64(p) asm volatile("wh64 (%0)" : : "r"(p) : "memory")
+
+#if GNUC_PREREQ(3,3) && defined(__alpha_max__)
#define minub8 __builtin_alpha_minub8
#define minsb8 __builtin_alpha_minsb8
#define minuw4 __builtin_alpha_minuw4
@@ -123,30 +130,20 @@ struct unaligned_long { uint64_t l; } __attribute__((packed));
#define unpkbl __builtin_alpha_unpkbl
#define unpkbw __builtin_alpha_unpkbw
#else
-#define cmpbge(a, b) ({ uint64_t __r; asm ("cmpbge %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
-#define extql(a, b) ({ uint64_t __r; asm ("extql %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
-#define extwl(a, b) ({ uint64_t __r; asm ("extwl %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
-#define extqh(a, b) ({ uint64_t __r; asm ("extqh %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
-#define zap(a, b) ({ uint64_t __r; asm ("zap %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
-#define zapnot(a, b) ({ uint64_t __r; asm ("zapnot %r1,%2,%0" : "=r" (__r) : "rJ" (a), "rI" (b)); __r; })
-#define amask(a) ({ uint64_t __r; asm ("amask %1,%0" : "=r" (__r) : "rI" (a)); __r; })
-#define implver() ({ uint64_t __r; asm ("implver %0" : "=r" (__r)); __r; })
-#define rpcc() ({ uint64_t __r; asm volatile ("rpcc %0" : "=r" (__r)); __r; })
-#define minub8(a, b) ({ uint64_t __r; asm ("minub8 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
-#define minsb8(a, b) ({ uint64_t __r; asm ("minsb8 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
-#define minuw4(a, b) ({ uint64_t __r; asm ("minuw4 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
-#define minsw4(a, b) ({ uint64_t __r; asm ("minsw4 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
-#define maxub8(a, b) ({ uint64_t __r; asm ("maxub8 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
-#define maxsb8(a, b) ({ uint64_t __r; asm ("maxsb8 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
-#define maxuw4(a, b) ({ uint64_t __r; asm ("maxuw4 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
-#define maxsw4(a, b) ({ uint64_t __r; asm ("maxsw4 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
-#define perr(a, b) ({ uint64_t __r; asm ("perr %r1,%r2,%0" : "=r" (__r) : "%rJ" (a), "rJ" (b)); __r; })
-#define pklb(a) ({ uint64_t __r; asm ("pklb %r1,%0" : "=r" (__r) : "rJ" (a)); __r; })
-#define pkwb(a) ({ uint64_t __r; asm ("pkwb %r1,%0" : "=r" (__r) : "rJ" (a)); __r; })
-#define unpkbl(a) ({ uint64_t __r; asm ("unpkbl %r1,%0" : "=r" (__r) : "rJ" (a)); __r; })
-#define unpkbw(a) ({ uint64_t __r; asm ("unpkbw %r1,%0" : "=r" (__r) : "rJ" (a)); __r; })
+#define minub8(a, b) ({ uint64_t __r; asm (".arch ev6; minub8 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
+#define minsb8(a, b) ({ uint64_t __r; asm (".arch ev6; minsb8 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
+#define minuw4(a, b) ({ uint64_t __r; asm (".arch ev6; minuw4 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
+#define minsw4(a, b) ({ uint64_t __r; asm (".arch ev6; minsw4 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
+#define maxub8(a, b) ({ uint64_t __r; asm (".arch ev6; maxub8 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
+#define maxsb8(a, b) ({ uint64_t __r; asm (".arch ev6; maxsb8 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
+#define maxuw4(a, b) ({ uint64_t __r; asm (".arch ev6; maxuw4 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
+#define maxsw4(a, b) ({ uint64_t __r; asm (".arch ev6; maxsw4 %r1,%2,%0" : "=r" (__r) : "%rJ" (a), "rI" (b)); __r; })
+#define perr(a, b) ({ uint64_t __r; asm (".arch ev6; perr %r1,%r2,%0" : "=r" (__r) : "%rJ" (a), "rJ" (b)); __r; })
+#define pklb(a) ({ uint64_t __r; asm (".arch ev6; pklb %r1,%0" : "=r" (__r) : "rJ" (a)); __r; })
+#define pkwb(a) ({ uint64_t __r; asm (".arch ev6; pkwb %r1,%0" : "=r" (__r) : "rJ" (a)); __r; })
+#define unpkbl(a) ({ uint64_t __r; asm (".arch ev6; unpkbl %r1,%0" : "=r" (__r) : "rJ" (a)); __r; })
+#define unpkbw(a) ({ uint64_t __r; asm (".arch ev6; unpkbw %r1,%0" : "=r" (__r) : "rJ" (a)); __r; })
#endif
-#define wh64(p) asm volatile("wh64 (%0)" : : "r"(p) : "memory")
#elif defined(__DECC) /* Digital/Compaq/hp "ccc" compiler */
diff --git a/libmpeg2/attributes.h b/libmpeg2/attributes.h
index 96a86b26c0..eefbc0dd1b 100644
--- a/libmpeg2/attributes.h
+++ b/libmpeg2/attributes.h
@@ -1,6 +1,6 @@
/*
* attributes.h
- * Copyright (C) 2000-2002 Michel Lespinasse <walken@zoy.org>
+ * Copyright (C) 2000-2003 Michel Lespinasse <walken@zoy.org>
* Copyright (C) 1999-2000 Aaron Holtzman <aholtzma@ess.engr.uvic.ca>
*
* This file is part of mpeg2dec, a free MPEG-2 video stream decoder.
diff --git a/libmpeg2/convert.h b/libmpeg2/convert.h
deleted file mode 100644
index fd51fd84c2..0000000000
--- a/libmpeg2/convert.h
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * convert.h
- * Copyright (C) 2000-2002 Michel Lespinasse <walken@zoy.org>
- * Copyright (C) 1999-2000 Aaron Holtzman <aholtzma@ess.engr.uvic.ca>
- *
- * This file is part of mpeg2dec, a free MPEG-2 video stream decoder.
- * See http://libmpeg2.sourceforge.net/ for updates.
- *
- * mpeg2dec is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * mpeg2dec is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#ifndef CONVERT_H
-#define CONVERT_H
-
-#define CONVERT_FRAME 0
-#define CONVERT_TOP_FIELD 1
-#define CONVERT_BOTTOM_FIELD 2
-#define CONVERT_BOTH_FIELDS 3
-
-typedef struct convert_init_s {
- void * id;
- int id_size;
- int buf_size[3];
- void (* start) (void * id, uint8_t * const * dest, int flags);
- void (* copy) (void * id, uint8_t * const * src, unsigned int v_offset);
-} convert_init_t;
-
-typedef void convert_t (int width, int height, uint32_t accel, void * arg,
- convert_init_t * result);
-
-convert_t convert_rgb32;
-convert_t convert_rgb24;
-convert_t convert_rgb16;
-convert_t convert_rgb15;
-convert_t convert_bgr32;
-convert_t convert_bgr24;
-convert_t convert_bgr16;
-convert_t convert_bgr15;
-
-#define CONVERT_RGB 0
-#define CONVERT_BGR 1
-convert_t * convert_rgb (int order, int bpp);
-
-#endif /* CONVERT_H */
diff --git a/libmpeg2/cpu_accel.c b/libmpeg2/cpu_accel.c
index c2c91e5c0a..e87f5b20a9 100644
--- a/libmpeg2/cpu_accel.c
+++ b/libmpeg2/cpu_accel.c
@@ -26,6 +26,8 @@
#include <inttypes.h>
#include "mpeg2.h"
+#include "attributes.h"
+#include "mpeg2_internal.h"
#ifdef ACCEL_DETECT
#ifdef ARCH_X86
@@ -35,7 +37,7 @@ static inline uint32_t arch_accel (void)
int AMD;
uint32_t caps;
-#ifndef PIC
+#if !defined(PIC) && !defined(__PIC__)
#define cpuid(op,eax,ebx,ecx,edx) \
__asm__ ("cpuid" \
: "=a" (eax), \
@@ -106,7 +108,7 @@ static inline uint32_t arch_accel (void)
}
#endif /* ARCH_X86 */
-#ifdef ARCH_PPC
+#if defined(ARCH_PPC) || defined(ARCH_SPARC)
#include <signal.h>
#include <setjmp.h>
@@ -124,6 +126,7 @@ static RETSIGTYPE sigill_handler (int sig)
siglongjmp (jmpbuf, 1);
}
+#ifdef ARCH_PPC
static inline uint32_t arch_accel (void)
{
static RETSIGTYPE (* oldsig) (int);
@@ -146,11 +149,49 @@ static inline uint32_t arch_accel (void)
:
: "r" (-1));
+ canjump = 0;
+
signal (SIGILL, oldsig);
return MPEG2_ACCEL_PPC_ALTIVEC;
}
#endif /* ARCH_PPC */
+#ifdef ARCH_SPARC
+static inline uint32_t arch_accel (void)
+{
+ static RETSIGTYPE (* oldsig) (int);
+
+ oldsig = signal (SIGILL, sigill_handler);
+ if (sigsetjmp (jmpbuf, 1)) {
+ signal (SIGILL, oldsig);
+ return 0;
+ }
+
+ canjump = 1;
+
+ /* pdist %f0, %f0, %f0 */
+ __asm__ __volatile__(".word\t0x81b007c0");
+
+ canjump = 0;
+
+ if (sigsetjmp (jmpbuf, 1)) {
+ signal (SIGILL, oldsig);
+ return MPEG2_ACCEL_SPARC_VIS;
+ }
+
+ canjump = 1;
+
+ /* edge8n %g0, %g0, %g0 */
+ __asm__ __volatile__(".word\t0x81b00020");
+
+ canjump = 0;
+
+ signal (SIGILL, oldsig);
+ return MPEG2_ACCEL_SPARC_VIS | MPEG2_ACCEL_SPARC_VIS2;
+}
+#endif /* ARCH_SPARC */
+#endif /* ARCH_PPC || ARCH_SPARC */
+
#ifdef ARCH_ALPHA
static inline uint32_t arch_accel (void)
{
@@ -167,7 +208,7 @@ static inline uint32_t arch_accel (void)
#endif
}
#endif /* ARCH_ALPHA */
-#endif
+#endif /* ACCEL_DETECT */
uint32_t mpeg2_detect_accel (void)
{
@@ -175,11 +216,8 @@ uint32_t mpeg2_detect_accel (void)
accel = 0;
#ifdef ACCEL_DETECT
-#ifdef LIBMPEG2_MLIB
- accel = MPEG2_ACCEL_MLIB;
-#endif
-#if defined (ARCH_X86) || defined (ARCH_PPC) || defined (ARCH_ALPHA)
- accel |= arch_accel ();
+#if defined (ARCH_X86) || defined (ARCH_PPC) || defined (ARCH_ALPHA) || defined (ARCH_SPARC)
+ accel = arch_accel ();
#endif
#endif
return accel;
diff --git a/libmpeg2/cpu_state.c b/libmpeg2/cpu_state.c
index e6544c6904..2a032dec00 100644
--- a/libmpeg2/cpu_state.c
+++ b/libmpeg2/cpu_state.c
@@ -27,8 +27,8 @@
#include <inttypes.h>
#include "mpeg2.h"
-#include "mpeg2_internal.h"
#include "attributes.h"
+#include "mpeg2_internal.h"
#ifdef ARCH_X86
#include "mmx.h"
#endif
@@ -43,7 +43,7 @@ static void state_restore_mmx (cpu_state_t * state)
}
#endif
-#if defined(ARCH_PPC) && defined(HAVE_ALTIVEC)
+#ifdef ARCH_PPC
#ifdef HAVE_ALTIVEC_H /* gnu */
#define LI(a,b) "li " #a "," #b "\n\t"
#define STVX0(a,b,c) "stvx " #a ",0," #c "\n\t"
diff --git a/libmpeg2/decode.c b/libmpeg2/decode.c
index fa87a824c1..bba2af4954 100644
--- a/libmpeg2/decode.c
+++ b/libmpeg2/decode.c
@@ -1,6 +1,6 @@
/*
* decode.c
- * Copyright (C) 2000-2002 Michel Lespinasse <walken@zoy.org>
+ * Copyright (C) 2000-2003 Michel Lespinasse <walken@zoy.org>
* Copyright (C) 1999-2000 Aaron Holtzman <aholtzma@ess.engr.uvic.ca>
*
* This file is part of mpeg2dec, a free MPEG-2 video stream decoder.
@@ -28,8 +28,8 @@
#include <inttypes.h>
#include "mpeg2.h"
+#include "attributes.h"
#include "mpeg2_internal.h"
-#include "convert.h"
static int mpeg2_accels = 0;
@@ -44,7 +44,6 @@ static inline int skip_chunk (mpeg2dec_t * mpeg2dec, int bytes)
{
uint8_t * current;
uint32_t shift;
- uint8_t * chunk_ptr;
uint8_t * limit;
uint8_t byte;
@@ -53,7 +52,6 @@ static inline int skip_chunk (mpeg2dec_t * mpeg2dec, int bytes)
current = mpeg2dec->buf_start;
shift = mpeg2dec->shift;
- chunk_ptr = mpeg2dec->chunk_ptr;
limit = current + bytes;
do {
@@ -116,69 +114,54 @@ void mpeg2_buffer (mpeg2dec_t * mpeg2dec, uint8_t * start, uint8_t * end)
mpeg2dec->buf_end = end;
}
-static inline int seek_chunk (mpeg2dec_t * mpeg2dec)
+int mpeg2_getpos (mpeg2dec_t * mpeg2dec)
+{
+ return mpeg2dec->buf_end - mpeg2dec->buf_start;
+}
+
+static inline mpeg2_state_t seek_chunk (mpeg2dec_t * mpeg2dec)
{
int size, skipped;
size = mpeg2dec->buf_end - mpeg2dec->buf_start;
skipped = skip_chunk (mpeg2dec, size);
if (!skipped) {
- mpeg2dec->bytes_since_pts += size;
- return -1;
+ mpeg2dec->bytes_since_tag += size;
+ return STATE_BUFFER;
}
- mpeg2dec->bytes_since_pts += skipped;
+ mpeg2dec->bytes_since_tag += skipped;
mpeg2dec->code = mpeg2dec->buf_start[-1];
- return 0;
+ return (mpeg2_state_t)-1;
}
-int mpeg2_seek_header (mpeg2dec_t * mpeg2dec)
+mpeg2_state_t mpeg2_seek_header (mpeg2dec_t * mpeg2dec)
{
while (mpeg2dec->code != 0xb3 &&
((mpeg2dec->code != 0xb7 && mpeg2dec->code != 0xb8 &&
- mpeg2dec->code) || mpeg2dec->sequence.width == -1))
- if (seek_chunk (mpeg2dec))
- return -1;
+ mpeg2dec->code) || mpeg2dec->sequence.width == (unsigned)-1))
+ if (seek_chunk (mpeg2dec) == STATE_BUFFER)
+ return STATE_BUFFER;
mpeg2dec->chunk_start = mpeg2dec->chunk_ptr = mpeg2dec->chunk_buffer;
- return mpeg2_parse_header (mpeg2dec);
-}
-
-int mpeg2_seek_sequence (mpeg2dec_t * mpeg2dec)
-{
- mpeg2dec->sequence.width = -1;
- return mpeg2_seek_header (mpeg2dec);
+ mpeg2dec->user_data_len = 0;
+ return (mpeg2dec->code ? mpeg2_parse_header (mpeg2dec) :
+ mpeg2_header_picture_start (mpeg2dec));
}
#define RECEIVED(code,state) (((state) << 8) + (code))
-int mpeg2_parse (mpeg2dec_t * mpeg2dec)
+mpeg2_state_t mpeg2_parse (mpeg2dec_t * mpeg2dec)
{
int size_buffer, size_chunk, copied;
- if(mpeg2dec->code==0xff){
- // FIXME: we need to resync stream (esp. mpeg2dec-->code) as we
- // left parser at 0x1FF last time at the end of prev. chunk.
- // Why? mpeg2dec->action is set to mpeg2_header_picture_start, but
- // it will call mpeg2_parse_header() too...
- //
- // following code copied from mpeg2_seek_header():
- while (mpeg2dec->code != 0xb3 &&
- ((mpeg2dec->code != 0xb7 && mpeg2dec->code != 0xb8 &&
- mpeg2dec->code) || mpeg2dec->sequence.width == -1))
- if (seek_chunk (mpeg2dec))
- return -1;
- mpeg2dec->chunk_start = mpeg2dec->chunk_ptr = mpeg2dec->chunk_buffer;
- }
-
if (mpeg2dec->action) {
- int state;
+ mpeg2_state_t state;
state = mpeg2dec->action (mpeg2dec);
- if (state)
+ if ((int)state >= 0)
return state;
}
-
+
while (1) {
- //printf("code=0x%X \n",mpeg2dec->code);
while ((unsigned) (mpeg2dec->code - mpeg2dec->first_decode_slice) <
mpeg2dec->nb_decode_slices) {
size_buffer = mpeg2dec->buf_end - mpeg2dec->buf_start;
@@ -187,20 +170,20 @@ int mpeg2_parse (mpeg2dec_t * mpeg2dec)
if (size_buffer <= size_chunk) {
copied = copy_chunk (mpeg2dec, size_buffer);
if (!copied) {
- mpeg2dec->bytes_since_pts += size_buffer;
+ mpeg2dec->bytes_since_tag += size_buffer;
mpeg2dec->chunk_ptr += size_buffer;
- return -1;
+ return STATE_BUFFER;
}
} else {
copied = copy_chunk (mpeg2dec, size_chunk);
if (!copied) {
/* filled the chunk buffer without finding a start code */
- mpeg2dec->bytes_since_pts += size_chunk;
+ mpeg2dec->bytes_since_tag += size_chunk;
mpeg2dec->action = seek_chunk;
return STATE_INVALID;
}
}
- mpeg2dec->bytes_since_pts += copied;
+ mpeg2dec->bytes_since_tag += copied;
mpeg2_slice (&(mpeg2dec->decoder), mpeg2dec->code,
mpeg2dec->chunk_start);
@@ -209,37 +192,29 @@ int mpeg2_parse (mpeg2dec_t * mpeg2dec)
}
if ((unsigned) (mpeg2dec->code - 1) >= 0xb0 - 1)
break;
- if (seek_chunk (mpeg2dec))
- return -1;
- }
-
- //printf("next_code=0x%X state=%d \n",mpeg2dec->code,mpeg2dec->state);
-
- if(mpeg2dec->code==0xff){
- mpeg2dec->action = mpeg2_header_picture_start; //mpeg2_seek_header;
- return mpeg2dec->state;
+ if (seek_chunk (mpeg2dec) == STATE_BUFFER)
+ return STATE_BUFFER;
}
- switch (RECEIVED (mpeg2dec->code, mpeg2dec->state)) {
- case RECEIVED (0x00, STATE_SLICE_1ST):
- case RECEIVED (0x00, STATE_SLICE):
+ switch (mpeg2dec->code) {
+ case 0x00:
mpeg2dec->action = mpeg2_header_picture_start;
- break;
- case RECEIVED (0xb7, STATE_SLICE):
+ return mpeg2dec->state;
+ case 0xb7:
mpeg2dec->action = mpeg2_header_end;
break;
- case RECEIVED (0xb3, STATE_SLICE):
- case RECEIVED (0xb8, STATE_SLICE):
+ case 0xb3:
+ case 0xb8:
mpeg2dec->action = mpeg2_parse_header;
break;
default:
- mpeg2dec->action = mpeg2_seek_header;
+ mpeg2dec->action = seek_chunk;
return STATE_INVALID;
}
- return mpeg2dec->state;
+ return (mpeg2dec->state == STATE_SLICE) ? STATE_SLICE : STATE_INVALID;
}
-int mpeg2_parse_header (mpeg2dec_t * mpeg2dec)
+mpeg2_state_t mpeg2_parse_header (mpeg2dec_t * mpeg2dec)
{
static int (* process_header[]) (mpeg2dec_t * mpeg2dec) = {
mpeg2_header_picture, mpeg2_header_extension, mpeg2_header_user_data,
@@ -248,6 +223,7 @@ int mpeg2_parse_header (mpeg2dec_t * mpeg2dec)
int size_buffer, size_chunk, copied;
mpeg2dec->action = mpeg2_parse_header;
+ mpeg2dec->info.user_data = NULL; mpeg2dec->info.user_data_len = 0;
while (1) {
size_buffer = mpeg2dec->buf_end - mpeg2dec->buf_start;
size_chunk = (mpeg2dec->chunk_buffer + BUFFER_SIZE -
@@ -255,26 +231,21 @@ int mpeg2_parse_header (mpeg2dec_t * mpeg2dec)
if (size_buffer <= size_chunk) {
copied = copy_chunk (mpeg2dec, size_buffer);
if (!copied) {
- mpeg2dec->bytes_since_pts += size_buffer;
+ mpeg2dec->bytes_since_tag += size_buffer;
mpeg2dec->chunk_ptr += size_buffer;
- return -1;
+ return STATE_BUFFER;
}
} else {
copied = copy_chunk (mpeg2dec, size_chunk);
if (!copied) {
/* filled the chunk buffer without finding a start code */
- mpeg2dec->bytes_since_pts += size_chunk;
+ mpeg2dec->bytes_since_tag += size_chunk;
mpeg2dec->code = 0xb4;
mpeg2dec->action = mpeg2_seek_header;
return STATE_INVALID;
}
}
- mpeg2dec->bytes_since_pts += copied;
-
- //printf("header_code=0x%X state=%d \n",mpeg2dec->code,mpeg2dec->state);
-
-// if(!mpeg2dec->code && mpeg2dec->state==7)
-
+ mpeg2dec->bytes_since_tag += copied;
if (process_header[mpeg2dec->code & 0x0b] (mpeg2dec)) {
mpeg2dec->code = mpeg2dec->buf_start[-1];
@@ -283,9 +254,6 @@ int mpeg2_parse_header (mpeg2dec_t * mpeg2dec)
}
mpeg2dec->code = mpeg2dec->buf_start[-1];
-
- //printf("next_header_code=0x%X state=%d \n",mpeg2dec->code,mpeg2dec->state);
-
switch (RECEIVED (mpeg2dec->code, mpeg2dec->state)) {
/* state transition after a sequence header */
@@ -297,10 +265,12 @@ int mpeg2_parse_header (mpeg2dec_t * mpeg2dec)
/* other legal state transitions */
case RECEIVED (0x00, STATE_GOP):
+ mpeg2_header_gop_finalize (mpeg2dec);
mpeg2dec->action = mpeg2_header_picture_start;
break;
case RECEIVED (0x01, STATE_PICTURE):
case RECEIVED (0x01, STATE_PICTURE_2ND):
+ mpeg2_header_picture_finalize (mpeg2dec, mpeg2_accels);
mpeg2dec->action = mpeg2_header_slice_start;
break;
@@ -321,56 +291,58 @@ int mpeg2_parse_header (mpeg2dec_t * mpeg2dec)
}
mpeg2dec->chunk_start = mpeg2dec->chunk_ptr = mpeg2dec->chunk_buffer;
+ mpeg2dec->user_data_len = 0;
return mpeg2dec->state;
}
}
-void mpeg2_convert (mpeg2dec_t * mpeg2dec,
- void (* convert) (int, int, uint32_t, void *,
- struct convert_init_s *), void * arg)
+int mpeg2_convert (mpeg2dec_t * mpeg2dec, mpeg2_convert_t convert, void * arg)
{
- convert_init_t convert_init;
- int size;
-
- convert_init.id = NULL;
- convert (mpeg2dec->decoder.width, mpeg2dec->decoder.height,
- mpeg2_accels, arg, &convert_init);
- if (convert_init.id_size) {
- convert_init.id = mpeg2dec->convert_id =
- mpeg2_malloc (convert_init.id_size, ALLOC_CONVERT_ID);
- convert (mpeg2dec->decoder.width, mpeg2dec->decoder.height,
- mpeg2_accels, arg, &convert_init);
+ mpeg2_convert_init_t convert_init;
+ int error;
+
+ error = convert (MPEG2_CONVERT_SET, NULL, &(mpeg2dec->sequence), 0,
+ mpeg2_accels, arg, &convert_init);
+ if (!error) {
+ mpeg2dec->convert = convert;
+ mpeg2dec->convert_arg = arg;
+ mpeg2dec->convert_id_size = convert_init.id_size;
+ mpeg2dec->convert_stride = 0;
}
- mpeg2dec->convert_size[0] = size = convert_init.buf_size[0];
- mpeg2dec->convert_size[1] = size += convert_init.buf_size[1];
- mpeg2dec->convert_size[2] = size += convert_init.buf_size[2];
- mpeg2dec->convert_start = convert_init.start;
- mpeg2dec->convert_copy = convert_init.copy;
-
- size = mpeg2dec->decoder.width * mpeg2dec->decoder.height >> 2;
- mpeg2dec->yuv_buf[0][0] = (uint8_t *) mpeg2_malloc (6 * size, ALLOC_YUV);
- mpeg2dec->yuv_buf[0][1] = mpeg2dec->yuv_buf[0][0] + 4 * size;
- mpeg2dec->yuv_buf[0][2] = mpeg2dec->yuv_buf[0][0] + 5 * size;
- mpeg2dec->yuv_buf[1][0] = (uint8_t *) mpeg2_malloc (6 * size, ALLOC_YUV);
- mpeg2dec->yuv_buf[1][1] = mpeg2dec->yuv_buf[1][0] + 4 * size;
- mpeg2dec->yuv_buf[1][2] = mpeg2dec->yuv_buf[1][0] + 5 * size;
- size = mpeg2dec->decoder.width * 8;
- mpeg2dec->yuv_buf[2][0] = (uint8_t *) mpeg2_malloc (6 * size, ALLOC_YUV);
- mpeg2dec->yuv_buf[2][1] = mpeg2dec->yuv_buf[2][0] + 4 * size;
- mpeg2dec->yuv_buf[2][2] = mpeg2dec->yuv_buf[2][0] + 5 * size;
+ return error;
+}
+
+int mpeg2_stride (mpeg2dec_t * mpeg2dec, int stride)
+{
+ if (!mpeg2dec->convert) {
+ if (stride < (int) mpeg2dec->sequence.width)
+ stride = mpeg2dec->sequence.width;
+ mpeg2dec->decoder.stride_frame = stride;
+ } else {
+ mpeg2_convert_init_t convert_init;
+
+ stride = mpeg2dec->convert (MPEG2_CONVERT_STRIDE, NULL,
+ &(mpeg2dec->sequence), stride,
+ mpeg2_accels, mpeg2dec->convert_arg,
+ &convert_init);
+ mpeg2dec->convert_id_size = convert_init.id_size;
+ mpeg2dec->convert_stride = stride;
+ }
+ return stride;
}
void mpeg2_set_buf (mpeg2dec_t * mpeg2dec, uint8_t * buf[3], void * id)
{
- fbuf_t * fbuf;
+ mpeg2_fbuf_t * fbuf;
if (mpeg2dec->custom_fbuf) {
- mpeg2_set_fbuf (mpeg2dec, mpeg2dec->decoder.coding_type);
- fbuf = mpeg2dec->fbuf[0];
if (mpeg2dec->state == STATE_SEQUENCE) {
mpeg2dec->fbuf[2] = mpeg2dec->fbuf[1];
mpeg2dec->fbuf[1] = mpeg2dec->fbuf[0];
}
+ mpeg2_set_fbuf (mpeg2dec, (mpeg2dec->decoder.coding_type ==
+ PIC_FLAG_CODING_TYPE_B));
+ fbuf = mpeg2dec->fbuf[0];
} else {
fbuf = &(mpeg2dec->fbuf_alloc[mpeg2dec->alloc_index].fbuf);
mpeg2dec->alloc_index_user = ++mpeg2dec->alloc_index;
@@ -409,12 +381,14 @@ void mpeg2_slice_region (mpeg2dec_t * mpeg2dec, int start, int end)
mpeg2dec->nb