Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
V
vlc
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Redmine
Redmine
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Operations
Operations
Metrics
Environments
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
videolan
vlc
Commits
41bcd8c6
Commit
41bcd8c6
authored
Apr 17, 2009
by
Rémi Denis-Courmont
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Remove libmpeg2 copy for XvMC
parent
a2180073
Changes
14
Hide whitespace changes
Inline
Side-by-side
Showing
14 changed files
with
0 additions
and
4901 deletions
+0
-4901
modules/codec/xvmc/alloc.c
modules/codec/xvmc/alloc.c
+0
-74
modules/codec/xvmc/attributes.h
modules/codec/xvmc/attributes.h
+0
-37
modules/codec/xvmc/cpu_accel.c
modules/codec/xvmc/cpu_accel.c
+0
-116
modules/codec/xvmc/cpu_state.c
modules/codec/xvmc/cpu_state.c
+0
-52
modules/codec/xvmc/decode.c
modules/codec/xvmc/decode.c
+0
-496
modules/codec/xvmc/header.c
modules/codec/xvmc/header.c
+0
-994
modules/codec/xvmc/motion_comp.c
modules/codec/xvmc/motion_comp.c
+0
-113
modules/codec/xvmc/motion_comp_mmx.c
modules/codec/xvmc/motion_comp_mmx.c
+0
-998
modules/codec/xvmc/mpeg2.h
modules/codec/xvmc/mpeg2.h
+0
-207
modules/codec/xvmc/slice.c
modules/codec/xvmc/slice.c
+0
-845
modules/codec/xvmc/slice_xvmc_vld.c
modules/codec/xvmc/slice_xvmc_vld.c
+0
-309
modules/codec/xvmc/vlc.h
modules/codec/xvmc/vlc.h
+0
-453
modules/codec/xvmc/xvmc_vld.h
modules/codec/xvmc/xvmc_vld.h
+0
-34
modules/codec/xvmc/xxmc-config.h
modules/codec/xvmc/xxmc-config.h
+0
-173
No files found.
modules/codec/xvmc/alloc.c
deleted
100644 → 0
View file @
a2180073
/* $Id$
* alloc.c
* 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.
* 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
*/
#include <stddef.h>
#include <inttypes.h>
#include <stdlib.h>
#include "mpeg2.h"
static
void
*
(
*
malloc_hook
)
(
unsigned
size
,
mpeg2_alloc_t
reason
)
=
NULL
;
static
int
(
*
free_hook
)
(
void
*
buf
)
=
NULL
;
void
*
mpeg2_malloc
(
unsigned
size
,
mpeg2_alloc_t
reason
)
{
char
*
buf
=
NULL
;
if
(
malloc_hook
)
{
buf
=
(
char
*
)
malloc_hook
(
size
,
reason
);
if
(
buf
)
return
buf
;
}
if
(
size
)
{
buf
=
(
char
*
)
malloc
(
size
+
63
+
sizeof
(
void
**
));
if
(
buf
)
{
char
*
align_buf
=
NULL
;
align_buf
=
buf
+
63
+
sizeof
(
void
**
);
align_buf
-=
(
long
)
align_buf
&
63
;
*
(((
void
**
)
align_buf
)
-
1
)
=
buf
;
return
align_buf
;
}
}
return
NULL
;
}
void
mpeg2_free
(
void
*
buf
)
{
if
(
free_hook
&&
free_hook
(
buf
))
return
;
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
;
}
modules/codec/xvmc/attributes.h
deleted
100644 → 0
View file @
a2180073
/* $Id$
* attributes.h
* 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.
* 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
*/
/* use gcc attribs to align critical data structures */
#ifdef ATTRIBUTE_ALIGNED_MAX
# define ATTR_ALIGN(align) __attribute__ ((__aligned__ ((ATTRIBUTE_ALIGNED_MAX < align) ? ATTRIBUTE_ALIGNED_MAX : align)))
#else
# define ATTR_ALIGN(align)
#endif
#ifdef HAVE_BUILTIN_EXPECT
# define likely(x) __builtin_expect ((x) != 0, 1)
# define unlikely(x) __builtin_expect ((x) != 0, 0)
#else
# define likely(x) (x)
# define unlikely(x) (x)
#endif
modules/codec/xvmc/cpu_accel.c
deleted
100644 → 0
View file @
a2180073
/* $Id$
* cpu_accel.c
* 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.
* 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
*/
#include <inttypes.h>
#include "mpeg2.h"
#include "attributes.h"
#include "mpeg2_internal.h"
static
inline
uint32_t
arch_accel
(
void
)
{
uint32_t
eax
,
ebx
,
ecx
,
edx
;
int
AMD
;
uint32_t
caps
;
#if defined(__x86_64__) || (!defined(PIC) && !defined(__PIC__))
#define cpuid(op,eax,ebx,ecx,edx) \
__asm__ ("cpuid" \
: "=a" (eax), \
"=b" (ebx), \
"=c" (ecx), \
"=d" (edx) \
: "a" (op) \
: "cc")
#else
/* PIC version : save ebx (not needed on x86_64) */
#define cpuid(op,eax,ebx,ecx,edx) \
__asm__ ("push %%ebx\n\t" \
"cpuid\n\t" \
"movl %%ebx,%1\n\t" \
"pop %%ebx" \
: "=a" (eax), \
"=r" (ebx), \
"=c" (ecx), \
"=d" (edx) \
: "a" (op) \
: "cc")
#endif
#ifndef __x86_64__
/* x86_64 supports the cpuid op */
__asm__
(
"pushf
\n\t
"
"pushf
\n\t
"
"pop %0
\n\t
"
"movl %0,%1
\n\t
"
"xorl $0x200000,%0
\n\t
"
"push %0
\n\t
"
"popf
\n\t
"
"pushf
\n\t
"
"pop %0
\n\t
"
"popf"
:
"=r"
(
eax
),
"=r"
(
ebx
)
:
:
"cc"
);
if
(
eax
==
ebx
)
/* no cpuid */
return
0
;
#endif
cpuid
(
0x00000000
,
eax
,
ebx
,
ecx
,
edx
);
if
(
!
eax
)
/* vendor string only */
return
0
;
AMD
=
(
ebx
==
0x68747541
)
&&
(
ecx
==
0x444d4163
)
&&
(
edx
==
0x69746e65
);
cpuid
(
0x00000001
,
eax
,
ebx
,
ecx
,
edx
);
if
(
!
(
edx
&
0x00800000
))
/* no MMX */
return
0
;
caps
=
MPEG2_ACCEL_X86_MMX
;
if
(
edx
&
0x02000000
)
/* SSE - identical to AMD MMX extensions */
caps
=
MPEG2_ACCEL_X86_MMX
|
MPEG2_ACCEL_X86_MMXEXT
;
cpuid
(
0x80000000
,
eax
,
ebx
,
ecx
,
edx
);
if
(
eax
<
0x80000001
)
/* no extended capabilities */
return
caps
;
cpuid
(
0x80000001
,
eax
,
ebx
,
ecx
,
edx
);
if
(
edx
&
0x80000000
)
caps
|=
MPEG2_ACCEL_X86_3DNOW
;
if
(
AMD
&&
(
edx
&
0x00400000
))
/* AMD MMX extensions */
caps
|=
MPEG2_ACCEL_X86_MMXEXT
;
return
caps
;
}
uint32_t
mpeg2_detect_accel
(
void
)
{
uint32_t
accel
;
accel
=
0
;
accel
=
arch_accel
();
return
accel
;
}
modules/codec/xvmc/cpu_state.c
deleted
100644 → 0
View file @
a2180073
/* $Id$
* cpu_state.c
* 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.
* 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
*/
#include "xxmc-config.h"
#include <stddef.h>
#include <inttypes.h>
#include "mpeg2.h"
#include "attributes.h"
#include "mpeg2_internal.h"
#ifdef ARCH_X86
# include "mmx.h"
#endif
void
(
*
mpeg2_cpu_state_save
)
(
cpu_state_t
*
state
)
=
NULL
;
void
(
*
mpeg2_cpu_state_restore
)
(
cpu_state_t
*
state
)
=
NULL
;
static
void
state_restore_mmx
(
cpu_state_t
*
state
)
{
emms
();
}
void
mpeg2_cpu_state_init
(
uint32_t
accel
)
{
if
(
accel
&
MPEG2_ACCEL_X86_MMX
)
{
mpeg2_cpu_state_restore
=
state_restore_mmx
;
}
}
modules/codec/xvmc/decode.c
deleted
100644 → 0
View file @
a2180073
/* $Id$
* decode.c
* 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.
* 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
*/
#ifdef HAVE_CONFIG_H
# include "config.h"
#endif
#include <vlc_common.h>
#include <vlc_vout.h>
#include "xxmc-config.h"
#include <inttypes.h>
#include "mpeg2.h"
#include "attributes.h"
#include "mpeg2_internal.h"
#include "xvmc_vld.h"
static
int
mpeg2_accels
=
0
;
#define BUFFER_SIZE (1194 * 1024)
const
mpeg2_info_t
*
mpeg2_info
(
mpeg2dec_t
*
mpeg2dec
)
{
return
&
(
mpeg2dec
->
info
);
}
static
inline
int
skip_chunk
(
mpeg2dec_t
*
mpeg2dec
,
int
bytes
)
{
uint8_t
*
current
=
NULL
;
uint32_t
shift
;
uint8_t
*
limit
=
NULL
;
uint8_t
byte
;
if
(
!
bytes
)
return
0
;
current
=
mpeg2dec
->
buf_start
;
shift
=
mpeg2dec
->
shift
;
limit
=
current
+
bytes
;
do
{
byte
=
*
current
++
;
if
(
shift
==
0x00000100
)
{
int
skipped
;
mpeg2dec
->
shift
=
0xffffff00
;
skipped
=
current
-
mpeg2dec
->
buf_start
;
mpeg2dec
->
buf_start
=
current
;
return
skipped
;
}
shift
=
(
shift
|
byte
)
<<
8
;
}
while
(
current
<
limit
);
mpeg2dec
->
shift
=
shift
;
mpeg2dec
->
buf_start
=
current
;
return
0
;
}
static
inline
int
copy_chunk
(
mpeg2dec_t
*
mpeg2dec
,
int
bytes
)
{
uint8_t
*
current
=
NULL
;
uint32_t
shift
;
uint8_t
*
chunk_ptr
=
NULL
;
uint8_t
*
limit
=
NULL
;
uint8_t
byte
;
if
(
!
bytes
)
return
0
;
current
=
mpeg2dec
->
buf_start
;
shift
=
mpeg2dec
->
shift
;
chunk_ptr
=
mpeg2dec
->
chunk_ptr
;
limit
=
current
+
bytes
;
do
{
byte
=
*
current
++
;
if
(
shift
==
0x00000100
)
{
int
copied
;
mpeg2dec
->
shift
=
0xffffff00
;
mpeg2dec
->
chunk_size
=
chunk_ptr
-
mpeg2dec
->
chunk_start
-
3
;
mpeg2dec
->
chunk_ptr
=
chunk_ptr
+
1
;
copied
=
current
-
mpeg2dec
->
buf_start
;
mpeg2dec
->
buf_start
=
current
;
return
copied
;
}
shift
=
(
shift
|
byte
)
<<
8
;
*
chunk_ptr
++
=
byte
;
}
while
(
current
<
limit
);
mpeg2dec
->
shift
=
shift
;
mpeg2dec
->
buf_start
=
current
;
return
0
;
}
void
mpeg2_buffer
(
mpeg2dec_t
*
mpeg2dec
,
uint8_t
*
start
,
uint8_t
*
end
)
{
mpeg2dec
->
buf_start
=
start
;
mpeg2dec
->
buf_end
=
end
;
}
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_tag
+=
size
;
return
STATE_BUFFER
;
}
mpeg2dec
->
bytes_since_tag
+=
skipped
;
mpeg2dec
->
code
=
mpeg2dec
->
buf_start
[
-
1
];
return
(
mpeg2_state_t
)
-
1
;
}
mpeg2_state_t
mpeg2_seek_header
(
mpeg2dec_t
*
mpeg2dec
)
{
while
(
(
mpeg2dec
->
code
!=
0xb3
)
&&
(((
mpeg2dec
->
code
!=
0xb7
)
&&
(
mpeg2dec
->
code
!=
0xb8
)
&&
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
;
mpeg2dec
->
user_data_len
=
0
;
return
(
mpeg2dec
->
code
?
mpeg2_parse_header
(
mpeg2dec
)
:
mpeg2_header_picture_start
(
mpeg2dec
));
}
#define RECEIVED(code,state) (((state) << 8) + (code))
mpeg2_state_t
mpeg2_parse
(
mpeg2dec_t
*
mpeg2dec
)
{
int
size_buffer
,
size_chunk
,
copied
;
if
(
mpeg2dec
->
action
)
{
mpeg2_state_t
state
;
state
=
mpeg2dec
->
action
(
mpeg2dec
);
if
((
int
)
state
>=
0
)
return
state
;
}
while
(
1
)
{
while
(
(
unsigned
int
)
(
mpeg2dec
->
code
-
mpeg2dec
->
first_decode_slice
)
<
mpeg2dec
->
nb_decode_slices
)
{
size_buffer
=
mpeg2dec
->
buf_end
-
mpeg2dec
->
buf_start
;
size_chunk
=
(
mpeg2dec
->
chunk_buffer
+
BUFFER_SIZE
-
mpeg2dec
->
chunk_ptr
);
if
(
size_buffer
<=
size_chunk
)
{
copied
=
copy_chunk
(
mpeg2dec
,
size_buffer
);
if
(
!
copied
)
{
mpeg2dec
->
bytes_since_tag
+=
size_buffer
;
mpeg2dec
->
chunk_ptr
+=
size_buffer
;
return
STATE_BUFFER
;
}
}
else
{
copied
=
copy_chunk
(
mpeg2dec
,
size_chunk
);
if
(
!
copied
)
{
/* filled the chunk buffer without finding a start code */
mpeg2dec
->
bytes_since_tag
+=
size_chunk
;
mpeg2dec
->
action
=
seek_chunk
;
return
STATE_INVALID
;
}
}
mpeg2dec
->
bytes_since_tag
+=
copied
;
mpeg2_xxmc_slice
(
mpeg2dec
,
NULL
,
mpeg2dec
->
code
,
mpeg2dec
->
chunk_start
,
mpeg2dec
->
chunk_size
);
mpeg2dec
->
prev_code
=
mpeg2dec
->
code
;
mpeg2dec
->
code
=
mpeg2dec
->
buf_start
[
-
1
];
mpeg2dec
->
chunk_ptr
=
mpeg2dec
->
chunk_start
;
}
if
(
(
unsigned
int
)
(
mpeg2dec
->
code
-
1
)
>=
(
0xb0
-
1
)
)
break
;
if
(
seek_chunk
(
mpeg2dec
)
==
STATE_BUFFER
)
return
STATE_BUFFER
;
}
switch
(
mpeg2dec
->
code
)
{
case
0x00
:
mpeg2dec
->
action
=
mpeg2_header_picture_start
;
return
mpeg2dec
->
state
;
case
0xb7
:
mpeg2dec
->
action
=
mpeg2_header_end
;
break
;
case
0xb3
:
case
0xb8
:
mpeg2dec
->
action
=
mpeg2_parse_header
;
break
;
default:
mpeg2dec
->
action
=
seek_chunk
;
return
STATE_INVALID
;
}
return
(
mpeg2dec
->
state
==
STATE_SLICE
)
?
STATE_SLICE
:
STATE_INVALID
;
}
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
,
mpeg2_header_sequence
,
NULL
,
NULL
,
NULL
,
NULL
,
mpeg2_header_gop
};
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
-
mpeg2dec
->
chunk_ptr
);
if
(
size_buffer
<=
size_chunk
)
{
copied
=
copy_chunk
(
mpeg2dec
,
size_buffer
);
if
(
!
copied
)
{
mpeg2dec
->
bytes_since_tag
+=
size_buffer
;
mpeg2dec
->
chunk_ptr
+=
size_buffer
;
return
STATE_BUFFER
;
}
}
else
{
copied
=
copy_chunk
(
mpeg2dec
,
size_chunk
);
if
(
!
copied
)
{
/* filled the chunk buffer without finding a start code */
mpeg2dec
->
bytes_since_tag
+=
size_chunk
;
mpeg2dec
->
code
=
0xb4
;
mpeg2dec
->
action
=
mpeg2_seek_header
;
return
STATE_INVALID
;
}
}
mpeg2dec
->
bytes_since_tag
+=
copied
;
if
(
process_header
[
mpeg2dec
->
code
&
0x0b
](
mpeg2dec
)
)
{
mpeg2dec
->
code
=
mpeg2dec
->
buf_start
[
-
1
];
mpeg2dec
->
action
=
mpeg2_seek_header
;
return
STATE_INVALID
;
}
mpeg2dec
->
code
=
mpeg2dec
->
buf_start
[
-
1
];
switch
(
RECEIVED
(
mpeg2dec
->
code
,
mpeg2dec
->
state
)
)
{
/* state transition after a sequence header */
case
RECEIVED
(
0x00
,
STATE_SEQUENCE
):
mpeg2dec
->
action
=
mpeg2_header_picture_start
;
case
RECEIVED
(
0xb8
,
STATE_SEQUENCE
):
mpeg2_header_sequence_finalize
(
mpeg2dec
);
break
;
/* 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
;
/* legal headers within a given state */
case
RECEIVED
(
0xb2
,
STATE_SEQUENCE
):
case
RECEIVED
(
0xb2
,
STATE_GOP
):
case
RECEIVED
(
0xb2
,
STATE_PICTURE
):
case
RECEIVED
(
0xb2
,
STATE_PICTURE_2ND
):
case
RECEIVED
(
0xb5
,
STATE_SEQUENCE
):
case
RECEIVED
(
0xb5
,
STATE_PICTURE
):
case
RECEIVED
(
0xb5
,
STATE_PICTURE_2ND
):
mpeg2dec
->
chunk_ptr
=
mpeg2dec
->
chunk_start
;
continue
;
default:
mpeg2dec
->
action
=
mpeg2_seek_header
;
return
STATE_INVALID
;
}
mpeg2dec
->
chunk_start
=
mpeg2dec
->
chunk_ptr
=
mpeg2dec
->
chunk_buffer
;
mpeg2dec
->
user_data_len
=
0
;
return
mpeg2dec
->
state
;
}
}
int
mpeg2_convert
(
mpeg2dec_t
*
mpeg2dec
,
mpeg2_convert_t
convert
,
void
*
arg
)
{
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
;
}
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
)
{
mpeg2_fbuf_t
*
fbuf
;
if
(
mpeg2dec
->
custom_fbuf
)
{
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
;
}
fbuf
->
buf
[
0
]
=
buf
[
0
];
fbuf
->
buf
[
1
]
=
buf
[
1
];
fbuf
->
buf
[
2
]
=
buf
[
2
];
fbuf
->
id
=
id
;
}
void
mpeg2_custom_fbuf
(
mpeg2dec_t
*
mpeg2dec
,
int
custom_fbuf
)
{
mpeg2dec
->
custom_fbuf
=
custom_fbuf
;
}
void
mpeg2_skip
(
mpeg2dec_t
*
mpeg2dec
,
int
skip
)
{
mpeg2dec
->
first_decode_slice
=
1
;
mpeg2dec
->
nb_decode_slices
=
skip
?
0
:
(
0xb0
-
1
);
}
void
mpeg2_slice_region
(
mpeg2dec_t
*
mpeg2dec
,
int
start
,
int
end
)
{
start
=
(
start
<
1
)
?
1
:
(
start
>
0xb0
)
?
0xb0
:
start
;
end
=
(
end
<
start
)
?
start
:
(
end
>
0xb0
)
?
0xb0
:
end
;
mpeg2dec
->
first_decode_slice
=
start
;
mpeg2dec
->
nb_decode_slices
=
end
-
start
;
}
void
mpeg2_tag_picture
(
mpeg2dec_t
*
mpeg2dec
,
uint32_t
tag
,
uint32_t
tag2
)
{
mpeg2dec
->
tag_previous
=
mpeg2dec
->
tag_current
;
mpeg2dec
->
tag2_previous
=
mpeg2dec
->
tag2_current
;
mpeg2dec
->
tag_current
=
tag
;
mpeg2dec
->
tag2_current
=
tag2
;
mpeg2dec
->
num_tags
++
;
mpeg2dec
->
bytes_since_tag
=
0
;
}
uint32_t
mpeg2_accel
(
uint32_t
accel
)
{
if
(
!
mpeg2_accels
)
{
if
(
accel
&
MPEG2_ACCEL_DETECT
)
accel
|=
mpeg2_detect_accel
();
mpeg2_accels
=
accel
|=
MPEG2_ACCEL_DETECT
;
mpeg2_cpu_state_init
(
accel
);
/* mpeg2_idct_init (accel); */
mpeg2_mc_init
(
accel
);
}
return
mpeg2_accels
&
~
MPEG2_ACCEL_DETECT
;
}
void
mpeg2_reset
(
mpeg2dec_t
*
mpeg2dec
,
int
full_reset
)
{
mpeg2dec
->
buf_start
=
mpeg2dec
->
buf_end
=
NULL
;
mpeg2dec
->
num_tags
=
0
;
mpeg2dec
->
shift
=
0xffffff00
;
mpeg2dec
->
code
=
0xb4
;
mpeg2dec
->
action
=
mpeg2_seek_header
;
mpeg2dec
->
state
=
STATE_INVALID
;
mpeg2dec
->
first
=
1
;
mpeg2dec
->
ptr_forward_ref_picture
=
NULL
;
mpeg2dec
->
ptr_backward_ref_picture
=
NULL
;
mpeg2_reset_info
(
&
(
mpeg2dec
->
info
));
mpeg2dec
->
info
.
gop
=
NULL
;
mpeg2dec
->
info
.
user_data
=
NULL
;
mpeg2dec
->
info
.
user_data_len
=
0
;
if
(
full_reset
)
{
mpeg2dec
->
info
.
sequence
=
NULL
;
mpeg2_header_state_init
(
mpeg2dec
);
}
}
mpeg2dec_t
*
mpeg2_init
(
void
)
{
mpeg2dec_t
*
mpeg2dec
=
NULL
;
mpeg2_accel
(
MPEG2_ACCEL_DETECT
);
mpeg2dec
=
(
mpeg2dec_t
*
)
mpeg2_malloc
(
sizeof
(
mpeg2dec_t
),
MPEG2_ALLOC_MPEG2DEC
);
if
(
mpeg2dec
==
NULL
)
return
NULL
;
memset
(
mpeg2dec
->
decoder
.
DCTblock
,
0
,
64
*
sizeof
(
int16_t
)
);
memset
(
mpeg2dec
->
quantizer_matrix
,
0
,
4
*
64
*
sizeof
(
uint8_t
)
);
mpeg2dec
->
chunk_buffer
=
(
uint8_t
*
)
mpeg2_malloc
(
BUFFER_SIZE
+
4
,
MPEG2_ALLOC_CHUNK
);
mpeg2dec
->
sequence
.
width
=
(
unsigned
int
)
-
1
;
mpeg2_reset
(
mpeg2dec
,
1
);
return
mpeg2dec
;
}
void
mpeg2_close
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2_header_state_init
(
mpeg2dec
);
mpeg2_free
(
mpeg2dec
->
chunk_buffer
);
mpeg2_free
(
mpeg2dec
);
}
modules/codec/xvmc/header.c
deleted
100644 → 0
View file @
a2180073
/* $Id$
* header.c
* Copyright (C) 2000-2003 Michel Lespinasse <walken@zoy.org>
* Copyright (C) 2003 Regis Duchesne <hpreg@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
*/
#ifdef HAVE_CONFIG_H
# include "config.h"
#endif
#include <vlc_common.h>
#include <inttypes.h>
#include "xxmc-config.h"
#include "mpeg2.h"
#include "attributes.h"
#include "mpeg2_internal.h"
#define SEQ_EXT 2
#define SEQ_DISPLAY_EXT 4
#define QUANT_MATRIX_EXT 8
#define COPYRIGHT_EXT 0x10
#define PIC_DISPLAY_EXT 0x80
#define PIC_CODING_EXT 0x100
/* default intra quant matrix, in zig-zag order */
static
const
uint8_t
default_intra_quantizer_matrix
[
64
]
ATTR_ALIGN
(
16
)
=
{
8
,
16
,
16
,
19
,
16
,
19
,
22
,
22
,
22
,
22
,
22
,
22
,
26
,
24
,
26
,
27
,
27
,
27
,
26
,
26
,
26
,
26
,
27
,
27
,
27
,
29
,
29
,
29
,
34
,
34
,
34
,
29
,
29
,
29
,
27
,
27
,
29
,
29
,
32
,
32
,
34
,
34
,
37
,
38
,
37
,
35
,
35
,
34
,
35
,
38
,
38
,
40
,
40
,
40
,
48
,
48
,
46
,
46
,
56
,
56
,
58
,
69
,
69
,
83
};
uint8_t
mpeg2_scan_norm
[
64
]
ATTR_ALIGN
(
16
)
=
{
/* Zig-Zag scan pattern */
0
,
1
,
8
,
16
,
9
,
2
,
3
,
10
,
17
,
24
,
32
,
25
,
18
,
11
,
4
,
5
,
12
,
19
,
26
,
33
,
40
,
48
,
41
,
34
,
27
,
20
,
13
,
6
,
7
,
14
,
21
,
28
,
35
,
42
,
49
,
56
,
57
,
50
,
43
,
36
,
29
,
22
,
15
,
23
,
30
,
37
,
44
,
51
,
58
,
59
,
52
,
45
,
38
,
31
,
39
,
46
,
53
,
60
,
61
,
54
,
47
,
55
,
62
,
63
};
uint8_t
mpeg2_scan_alt
[
64
]
ATTR_ALIGN
(
16
)
=
{
/* Alternate scan pattern */
0
,
8
,
16
,
24
,
1
,
9
,
2
,
10
,
17
,
25
,
32
,
40
,
48
,
56
,
57
,
49
,
41
,
33
,
26
,
18
,
3
,
11
,
4
,
12
,
19
,
27
,
34
,
42
,
50
,
58
,
35
,
43
,
51
,
59
,
20
,
28
,
5
,
13
,
6
,
14
,
21
,
29
,
36
,
44
,
52
,
60
,
37
,
45
,
53
,
61
,
22
,
30
,
7
,
15
,
23
,
31
,
38
,
46
,
54
,
62
,
39
,
47
,
55
,
63
};
void
mpeg2_header_state_init
(
mpeg2dec_t
*
mpeg2dec
)
{
if
(
mpeg2dec
->
sequence
.
width
!=
(
unsigned
int
)
-
1
)
{
int
i
;
mpeg2dec
->
sequence
.
width
=
(
unsigned
int
)
-
1
;
if
(
!
mpeg2dec
->
custom_fbuf
)
{
for
(
i
=
mpeg2dec
->
alloc_index_user
;
i
<
mpeg2dec
->
alloc_index
;
i
++
)
{
mpeg2_free
(
mpeg2dec
->
fbuf_alloc
[
i
].
fbuf
.
buf
[
0
]
);
mpeg2_free
(
mpeg2dec
->
fbuf_alloc
[
i
].
fbuf
.
buf
[
1
]
);
mpeg2_free
(
mpeg2dec
->
fbuf_alloc
[
i
].
fbuf
.
buf
[
2
]
);
}
}
if
(
mpeg2dec
->
convert_start
)
{
for
(
i
=
0
;
i
<
3
;
i
++
)
{
mpeg2_free
(
mpeg2dec
->
yuv_buf
[
i
][
0
]
);
mpeg2_free
(
mpeg2dec
->
yuv_buf
[
i
][
1
]
);
mpeg2_free
(
mpeg2dec
->
yuv_buf
[
i
][
2
]
);
}
}
if
(
mpeg2dec
->
decoder
.
convert_id
)
mpeg2_free
(
mpeg2dec
->
decoder
.
convert_id
);
}
mpeg2dec
->
decoder
.
coding_type
=
I_TYPE
;
mpeg2dec
->
decoder
.
convert
=
NULL
;
mpeg2dec
->
decoder
.
convert_id
=
NULL
;
mpeg2dec
->
decoder
.
load_intra_quantizer_matrix
=
1
;
mpeg2dec
->
decoder
.
load_non_intra_quantizer_matrix
=
1
;
mpeg2dec
->
picture
=
mpeg2dec
->
pictures
;
mpeg2dec
->
fbuf
[
0
]
=
&
mpeg2dec
->
fbuf_alloc
[
0
].
fbuf
;
mpeg2dec
->
fbuf
[
1
]
=
&
mpeg2dec
->
fbuf_alloc
[
1
].
fbuf
;
mpeg2dec
->
fbuf
[
2
]
=
&
mpeg2dec
->
fbuf_alloc
[
2
].
fbuf
;
mpeg2dec
->
first
=
1
;
mpeg2dec
->
alloc_index
=
0
;
mpeg2dec
->
alloc_index_user
=
0
;
mpeg2dec
->
first_decode_slice
=
1
;
mpeg2dec
->
nb_decode_slices
=
0xb0
-
1
;
mpeg2dec
->
convert
=
NULL
;
mpeg2dec
->
convert_start
=
NULL
;
mpeg2dec
->
custom_fbuf
=
0
;
mpeg2dec
->
yuv_index
=
0
;
}
void
mpeg2_reset_info
(
mpeg2_info_t
*
info
)
{
info
->
current_picture
=
info
->
current_picture_2nd
=
NULL
;
info
->
display_picture
=
info
->
display_picture_2nd
=
NULL
;
info
->
current_fbuf
=
info
->
display_fbuf
=
info
->
discard_fbuf
=
NULL
;
}
static
void
info_user_data
(
mpeg2dec_t
*
mpeg2dec
)
{
if
(
mpeg2dec
->
user_data_len
)
{
mpeg2dec
->
info
.
user_data
=
mpeg2dec
->
chunk_buffer
;
mpeg2dec
->
info
.
user_data_len
=
mpeg2dec
->
user_data_len
-
3
;
}
}
int
mpeg2_header_sequence
(
mpeg2dec_t
*
mpeg2dec
)
{
uint8_t
*
buffer
=
mpeg2dec
->
chunk_start
;
mpeg2_sequence_t
*
sequence
=
&
(
mpeg2dec
->
new_sequence
);
static
unsigned
int
frame_period
[
16
]
=
{
0
,
1126125
,
1125000
,
1080000
,
900900
,
900000
,
540000
,
450450
,
450000
,
/* unofficial: xing 15 fps */
1800000
,
/* unofficial: libmpeg3 "Unofficial economy rates" 5/10/12/15 fps */
5400000
,
2700000
,
2250000
,
1800000
,
0
,
0
};
int
i
;
if
(
(
buffer
[
6
]
&
0x20
)
!=
0x20
)
/* missing marker_bit */
return
1
;
i
=
(
buffer
[
0
]
<<
16
)
|
(
buffer
[
1
]
<<
8
)
|
buffer
[
2
];
if
(
!
(
sequence
->
display_width
=
sequence
->
picture_width
=
i
>>
12
)
)
return
1
;
if
(
!
(
sequence
->
display_height
=
sequence
->
picture_height
=
i
&
0xfff
)
)
return
1
;
sequence
->
width
=
(
sequence
->
picture_width
+
15
)
&
~
15
;
sequence
->
height
=
(
sequence
->
picture_height
+
15
)
&
~
15
;
sequence
->
chroma_width
=
sequence
->
width
>>
1
;
sequence
->
chroma_height
=
sequence
->
height
>>
1
;
sequence
->
flags
=
(
SEQ_FLAG_PROGRESSIVE_SEQUENCE
|
SEQ_VIDEO_FORMAT_UNSPECIFIED
);
sequence
->
aspect_ratio_information
=
buffer
[
3
]
>>
4
;
sequence
->
pixel_width
=
sequence
->
aspect_ratio_information
;
/* aspect ratio */
sequence
->
frame_period
=
frame_period
[
buffer
[
3
]
&
15
];
sequence
->
byte_rate
=
(
buffer
[
4
]
<<
10
)
|
(
buffer
[
5
]
<<
2
)
|
(
buffer
[
6
]
>>
6
);
sequence
->
vbv_buffer_size
=
((
buffer
[
6
]
<<
16
)
|
(
buffer
[
7
]
<<
8
))
&
0x1ff800
;
if
(
buffer
[
7
]
&
4
)
sequence
->
flags
|=
SEQ_FLAG_CONSTRAINED_PARAMETERS
;
mpeg2dec
->
copy_matrix
=
3
;
if
(
buffer
[
7
]
&
2
)
{
for
(
i
=
0
;
i
<
64
;
i
++
)
mpeg2dec
->
new_quantizer_matrix
[
0
][
mpeg2_scan_norm
[
i
]]
=
(
buffer
[
i
+
7
]
<<
7
)
|
(
buffer
[
i
+
8
]
>>
1
);
buffer
+=
64
;
}
else
{
for
(
i
=
0
;
i
<
64
;
i
++
)
mpeg2dec
->
new_quantizer_matrix
[
0
][
mpeg2_scan_norm
[
i
]]
=
default_intra_quantizer_matrix
[
i
];
}
if
(
buffer
[
7
]
&
1
)
{
for
(
i
=
0
;
i
<
64
;
i
++
)
mpeg2dec
->
new_quantizer_matrix
[
1
][
mpeg2_scan_norm
[
i
]]
=
buffer
[
i
+
8
];
}
else
memset
(
mpeg2dec
->
new_quantizer_matrix
[
1
],
16
,
64
);
mpeg2dec
->
decoder
.
load_intra_quantizer_matrix
=
1
;
mpeg2dec
->
decoder
.
load_non_intra_quantizer_matrix
=
1
;
sequence
->
profile_level_id
=
0x80
;
sequence
->
colour_primaries
=
0
;
sequence
->
transfer_characteristics
=
0
;
sequence
->
matrix_coefficients
=
0
;
mpeg2dec
->
ext_state
=
SEQ_EXT
;
mpeg2dec
->
state
=
STATE_SEQUENCE
;
mpeg2dec
->
display_offset_x
=
mpeg2dec
->
display_offset_y
=
0
;
mpeg2dec
->
ptr_forward_ref_picture
=
NULL
;
mpeg2dec
->
ptr_backward_ref_picture
=
NULL
;
return
0
;
}
static
int
sequence_ext
(
mpeg2dec_t
*
mpeg2dec
)
{
uint8_t
*
buffer
=
mpeg2dec
->
chunk_start
;
mpeg2_sequence_t
*
sequence
=
&
(
mpeg2dec
->
new_sequence
);
uint32_t
flags
;
if
(
!
(
buffer
[
3
]
&
1
)
)
return
1
;
sequence
->
profile_level_id
=
(
buffer
[
0
]
<<
4
)
|
(
buffer
[
1
]
>>
4
);
sequence
->
display_width
=
sequence
->
picture_width
+=
((
buffer
[
1
]
<<
13
)
|
(
buffer
[
2
]
<<
5
))
&
0x3000
;
sequence
->
display_height
=
sequence
->
picture_height
+=
(
buffer
[
2
]
<<
7
)
&
0x3000
;
sequence
->
width
=
(
sequence
->
picture_width
+
15
)
&
~
15
;
sequence
->
height
=
(
sequence
->
picture_height
+
15
)
&
~
15
;
flags
=
sequence
->
flags
|
SEQ_FLAG_MPEG2
;
if
(
!
(
buffer
[
1
]
&
8
)
)
{
flags
&=
~
SEQ_FLAG_PROGRESSIVE_SEQUENCE
;
sequence
->
height
=
(
sequence
->
height
+
31
)
&
~
31
;
}
if
(
buffer
[
5
]
&
0x80
)
flags
|=
SEQ_FLAG_LOW_DELAY
;
sequence
->
flags
=
flags
;
sequence
->
chroma_width
=
sequence
->
width
;
sequence
->
chroma_height
=
sequence
->
height
;
switch
(
buffer
[
1
]
&
6
)
{
case
0
:
/* invalid */
return
1
;
case
2
:
/* 4:2:0 */
sequence
->
chroma_height
>>=
1
;
case
4
:
/* 4:2:2 */
sequence
->
chroma_width
>>=
1
;
}
sequence
->
byte_rate
+=
((
buffer
[
2
]
<<
25
)
|
(
buffer
[
3
]
<<
17
))
&
0x3ffc0000
;
sequence
->
vbv_buffer_size
|=
buffer
[
4
]
<<
21
;
sequence
->
frame_period
=
sequence
->
frame_period
*
((
buffer
[
5
]
&
31
)
+
1
)
/
(((
buffer
[
5
]
>>
2
)
&
3
)
+
1
);
mpeg2dec
->
ext_state
=
SEQ_DISPLAY_EXT
;
return
0
;
}
static
int
sequence_display_ext
(
mpeg2dec_t
*
mpeg2dec
)
{
uint8_t
*
buffer
=
mpeg2dec
->
chunk_start
;
mpeg2_sequence_t
*
sequence
=
&
(
mpeg2dec
->
new_sequence
);
uint32_t
flags
;
flags
=
((
sequence
->
flags
&
~
SEQ_MASK_VIDEO_FORMAT
)
|
((
buffer
[
0
]
<<
4
)
&
SEQ_MASK_VIDEO_FORMAT
));
if
(
buffer
[
0
]
&
1
)
{
flags
|=
SEQ_FLAG_COLOUR_DESCRIPTION
;
sequence
->
colour_primaries
=
buffer
[
1
];
sequence
->
transfer_characteristics
=
buffer
[
2
];
sequence
->
matrix_coefficients
=
buffer
[
3
];
buffer
+=
3
;
}
if
(
!
(
buffer
[
2
]
&
2
)
)
/* missing marker_bit */
return
1
;
sequence
->
display_width
=
(
buffer
[
1
]
<<
6
)
|
(
buffer
[
2
]
>>
2
);
sequence
->
display_height
=
((
buffer
[
2
]
&
1
)
<<
13
)
|
(
buffer
[
3
]
<<
5
)
|
(
buffer
[
4
]
>>
3
);
return
0
;
}
static
inline
void
finalize_sequence
(
mpeg2_sequence_t
*
sequence
)
{
int
width
;
int
height
;
sequence
->
byte_rate
*=
50
;
if
(
sequence
->
flags
&
SEQ_FLAG_MPEG2
)
{
switch
(
sequence
->
pixel_width
)
{
case
1
:
/* square pixels */
sequence
->
pixel_width
=
sequence
->
pixel_height
=
1
;
return
;
case
2
:
/* 4:3 aspect ratio */
width
=
4
;
height
=
3
;
break
;
case
3
:
/* 16:9 aspect ratio */
width
=
16
;
height
=
9
;
break
;
case
4
:
/* 2.21:1 aspect ratio */
width
=
221
;
height
=
100
;
break
;
default:
/* illegal */
sequence
->
pixel_width
=
sequence
->
pixel_height
=
0
;
return
;
}
width
*=
sequence
->
display_height
;
height
*=
sequence
->
display_width
;
}
else
{
if
(
sequence
->
byte_rate
==
50
*
0x3ffff
)
sequence
->
byte_rate
=
0
;
/* mpeg-1 VBR */
switch
(
sequence
->
pixel_width
)
{
case
0
:
case
15
:
/* illegal */
sequence
->
pixel_width
=
sequence
->
pixel_height
=
0
;
return
;
case
1
:
/* square pixels */
sequence
->
pixel_width
=
sequence
->
pixel_height
=
1
;
return
;
case
3
:
/* 720x576 16:9 */
sequence
->
pixel_width
=
64
;
sequence
->
pixel_height
=
45
;
return
;
case
6
:
/* 720x480 16:9 */
sequence
->
pixel_width
=
32
;
sequence
->
pixel_height
=
27
;
return
;
case
12
:
/* 720*480 4:3 */
sequence
->
pixel_width
=
8
;
sequence
->
pixel_height
=
9
;
return
;
default:
height
=
88
*
sequence
->
pixel_width
+
1171
;
width
=
2000
;
}
}
sequence
->
pixel_width
=
width
;
sequence
->
pixel_height
=
height
;
while
(
width
)
{
/* find greatest common divisor */
int
tmp
=
width
;
width
=
height
%
tmp
;
height
=
tmp
;
}
sequence
->
pixel_width
/=
height
;
sequence
->
pixel_height
/=
height
;
}
static
void
copy_matrix
(
mpeg2dec_t
*
mpeg2dec
,
int
index
)
{
if
(
memcmp
(
mpeg2dec
->
quantizer_matrix
[
index
],
mpeg2dec
->
new_quantizer_matrix
[
index
],
64
)
)
{
memcpy
(
mpeg2dec
->
quantizer_matrix
[
index
],
mpeg2dec
->
new_quantizer_matrix
[
index
],
64
);
mpeg2dec
->
scaled
[
index
]
=
-
1
;
}
}
static
void
finalize_matrix
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2_decoder_t
*
decoder
=
&
(
mpeg2dec
->
decoder
);
int
i
;
for
(
i
=
0
;
i
<
2
;
i
++
)
{
if
(
mpeg2dec
->
copy_matrix
&
(
1
<<
i
)
)
copy_matrix
(
mpeg2dec
,
i
);
if
(
(
mpeg2dec
->
copy_matrix
&
(
4
<<
i
))
&&
memcmp
(
mpeg2dec
->
quantizer_matrix
[
i
],
mpeg2dec
->
new_quantizer_matrix
[
i
+
2
],
64
)
)
{
copy_matrix
(
mpeg2dec
,
i
+
2
);
decoder
->
chroma_quantizer
[
i
]
=
decoder
->
quantizer_prescale
[
i
+
2
];
}
else
if
(
mpeg2dec
->
copy_matrix
&
(
5
<<
i
)
)
decoder
->
chroma_quantizer
[
i
]
=
decoder
->
quantizer_prescale
[
i
];
}
#if 0
decoder->load_intra_quantizer_matrix = 1;
decoder->load_non_intra_quantizer_matrix = 1;
#endif
}
static
mpeg2_state_t
invalid_end_action
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2_reset_info
(
&
(
mpeg2dec
->
info
)
);
mpeg2dec
->
info
.
gop
=
NULL
;
info_user_data
(
mpeg2dec
);
mpeg2_header_state_init
(
mpeg2dec
);
mpeg2dec
->
sequence
=
mpeg2dec
->
new_sequence
;
mpeg2dec
->
action
=
mpeg2_seek_header
;
mpeg2dec
->
state
=
STATE_SEQUENCE
;
return
STATE_SEQUENCE
;
}
void
mpeg2_header_sequence_finalize
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2_sequence_t
*
sequence
=
&
(
mpeg2dec
->
new_sequence
);
mpeg2_decoder_t
*
decoder
=
&
(
mpeg2dec
->
decoder
);
finalize_sequence
(
sequence
);
finalize_matrix
(
mpeg2dec
);
decoder
->
mpeg1
=
!
(
sequence
->
flags
&
SEQ_FLAG_MPEG2
);
decoder
->
progressive_sequence
=
(
sequence
->
flags
&
SEQ_FLAG_PROGRESSIVE_SEQUENCE
);
decoder
->
aspect_ratio_information
=
sequence
->
aspect_ratio_information
;
decoder
->
width
=
sequence
->
width
;
decoder
->
height
=
sequence
->
height
;
decoder
->
vertical_position_extension
=
(
sequence
->
picture_height
>
2800
);
decoder
->
chroma_format
=
((
sequence
->
chroma_width
==
sequence
->
width
)
+
(
sequence
->
chroma_height
==
sequence
->
height
));
if
(
mpeg2dec
->
sequence
.
width
!=
(
unsigned
int
)
-
1
)
{
unsigned
int
new_byte_rate
;
/*
* According to 6.1.1.6, repeat sequence headers should be
* identical to the original. However some DVDs dont respect
* that and have different bitrates in the repeat sequence
* headers. So we'll ignore that in the comparison and still
* consider these as repeat sequence headers.
*
* However, be careful not to alter the current sequence when
* returning STATE_INVALID_END.
*/
new_byte_rate
=
sequence
->
byte_rate
;
sequence
->
byte_rate
=
mpeg2dec
->
sequence
.
byte_rate
;
if
(
memcmp
(
&
(
mpeg2dec
->
sequence
),
sequence
,
sizeof
(
mpeg2_sequence_t
))
)
{
decoder
->
stride_frame
=
sequence
->
width
;
sequence
->
byte_rate
=
new_byte_rate
;
mpeg2_header_end
(
mpeg2dec
);
mpeg2dec
->
action
=
invalid_end_action
;
mpeg2dec
->
state
=
STATE_INVALID_END
;
return
;
}
sequence
->
byte_rate
=
new_byte_rate
;
mpeg2dec
->
state
=
STATE_SEQUENCE_REPEATED
;
}
else
decoder
->
stride_frame
=
sequence
->
width
;
mpeg2dec
->
sequence
=
*
sequence
;
mpeg2_reset_info
(
&
(
mpeg2dec
->
info
)
);
mpeg2dec
->
info
.
sequence
=
&
(
mpeg2dec
->
sequence
);
mpeg2dec
->
info
.
gop
=
NULL
;
info_user_data
(
mpeg2dec
);
}
int
mpeg2_header_gop
(
mpeg2dec_t
*
mpeg2dec
)
{
uint8_t
*
buffer
=
mpeg2dec
->
chunk_start
;
mpeg2_gop_t
*
gop
=
&
(
mpeg2dec
->
new_gop
);
if
(
!
(
buffer
[
1
]
&
8
)
)
return
1
;
gop
->
hours
=
(
buffer
[
0
]
>>
2
)
&
31
;
gop
->
minutes
=
((
buffer
[
0
]
<<
4
)
|
(
buffer
[
1
]
>>
4
))
&
63
;
gop
->
seconds
=
((
buffer
[
1
]
<<
3
)
|
(
buffer
[
2
]
>>
5
))
&
63
;
gop
->
pictures
=
((
buffer
[
2
]
<<
1
)
|
(
buffer
[
3
]
>>
7
))
&
63
;
gop
->
flags
=
(
buffer
[
0
]
>>
7
)
|
((
buffer
[
3
]
>>
4
)
&
6
);
mpeg2dec
->
state
=
STATE_GOP
;
return
0
;
}
void
mpeg2_header_gop_finalize
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2dec
->
gop
=
mpeg2dec
->
new_gop
;
mpeg2_reset_info
(
&
(
mpeg2dec
->
info
)
);
mpeg2dec
->
info
.
gop
=
&
(
mpeg2dec
->
gop
);
info_user_data
(
mpeg2dec
);
}
void
mpeg2_set_fbuf
(
mpeg2dec_t
*
mpeg2dec
,
int
b_type
)
{
int
i
;
for
(
i
=
0
;
i
<
3
;
i
++
)
{
if
(
(
mpeg2dec
->
fbuf
[
1
]
!=
&
mpeg2dec
->
fbuf_alloc
[
i
].
fbuf
)
&&
(
mpeg2dec
->
fbuf
[
2
]
!=
&
mpeg2dec
->
fbuf_alloc
[
i
].
fbuf
)
)
{
mpeg2dec
->
fbuf
[
0
]
=
&
mpeg2dec
->
fbuf_alloc
[
i
].
fbuf
;
mpeg2dec
->
info
.
current_fbuf
=
mpeg2dec
->
fbuf
[
0
];
if
(
b_type
||
(
mpeg2dec
->
sequence
.
flags
&
SEQ_FLAG_LOW_DELAY
)
)
{
if
(
b_type
||
mpeg2dec
->
convert
)
mpeg2dec
->
info
.
discard_fbuf
=
mpeg2dec
->
fbuf
[
0
];
mpeg2dec
->
info
.
display_fbuf
=
mpeg2dec
->
fbuf
[
0
];
}
}
break
;
}
}
mpeg2_state_t
mpeg2_header_picture_start
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2_picture_t
*
picture
=
&
(
mpeg2dec
->
new_picture
);
mpeg2dec
->
state
=
((
mpeg2dec
->
state
!=
STATE_SLICE_1ST
)
?
STATE_PICTURE
:
STATE_PICTURE_2ND
);
picture
->
flags
=
0
;
picture
->
tag
=
picture
->
tag2
=
0
;
if
(
mpeg2dec
->
num_tags
)
{
if
(
mpeg2dec
->
bytes_since_tag
>=
4
)
{
mpeg2dec
->
num_tags
=
0
;
picture
->
tag
=
mpeg2dec
->
tag_current
;
picture
->
tag2
=
mpeg2dec
->
tag2_current
;
picture
->
flags
=
PIC_FLAG_TAGS
;
}
else
if
(
mpeg2dec
->
num_tags
>
1
)
{
mpeg2dec
->
num_tags
=
1
;
picture
->
tag
=
mpeg2dec
->
tag_previous
;
picture
->
tag2
=
mpeg2dec
->
tag2_previous
;
picture
->
flags
=
PIC_FLAG_TAGS
;
}
}
picture
->
display_offset
[
0
].
x
=
picture
->
display_offset
[
1
].
x
=
picture
->
display_offset
[
2
].
x
=
mpeg2dec
->
display_offset_x
;
picture
->
display_offset
[
0
].
y
=
picture
->
display_offset
[
1
].
y
=
picture
->
display_offset
[
2
].
y
=
mpeg2dec
->
display_offset_y
;
return
mpeg2_parse_header
(
mpeg2dec
);
}
int
mpeg2_header_picture
(
mpeg2dec_t
*
mpeg2dec
)
{
uint8_t
*
buffer
=
mpeg2dec
->
chunk_start
;
mpeg2_picture_t
*
picture
=
&
(
mpeg2dec
->
new_picture
);
mpeg2_decoder_t
*
decoder
=
&
(
mpeg2dec
->
decoder
);
int
type
;
type
=
(
buffer
[
1
]
>>
3
)
&
7
;
mpeg2dec
->
ext_state
=
PIC_CODING_EXT
;
picture
->
temporal_reference
=
(
buffer
[
0
]
<<
2
)
|
(
buffer
[
1
]
>>
6
);
picture
->
flags
|=
type
;
if
(
(
type
==
PIC_FLAG_CODING_TYPE_P
)
||
(
type
==
PIC_FLAG_CODING_TYPE_B
)
)
{
/* forward_f_code and backward_f_code - used in mpeg1 only */
decoder
->
f_motion
.
f_code
[
1
]
=
(
buffer
[
3
]
>>
2
)
&
1
;
decoder
->
f_motion
.
f_code
[
0
]
=
(((
buffer
[
3
]
<<
1
)
|
(
buffer
[
4
]
>>
7
))
&
7
)
-
1
;
decoder
->
b_motion
.
f_code
[
1
]
=
(
buffer
[
4
]
>>
6
)
&
1
;
decoder
->
b_motion
.
f_code
[
0
]
=
((
buffer
[
4
]
>>
3
)
&
7
)
-
1
;
}
/* XXXXXX decode extra_information_picture as well */
picture
->
nb_fields
=
2
;
mpeg2dec
->
q_scale_type
=
0
;
decoder
->
intra_dc_precision
=
7
;
decoder
->
frame_pred_frame_dct
=
1
;
decoder
->
concealment_motion_vectors
=
0
;
decoder
->
scan
=
mpeg2_scan_norm
;
decoder
->
picture_structure
=
FRAME_PICTURE
;
mpeg2dec
->
copy_matrix
=
0
;
return
0
;
}
static
int
picture_coding_ext
(
mpeg2dec_t
*
mpeg2dec
)
{
uint8_t
*
buffer
=
mpeg2dec
->
chunk_start
;
mpeg2_picture_t
*
picture
=
&
(
mpeg2dec
->
new_picture
);
mpeg2_decoder_t
*
decoder
=
&
(
mpeg2dec
->
decoder
);
uint32_t
flags
;
/* pre subtract 1 for use later in compute_motion_vector */
decoder
->
f_motion
.
f_code
[
0
]
=
(
buffer
[
0
]
&
15
)
-
1
;
decoder
->
f_motion
.
f_code
[
1
]
=
(
buffer
[
1
]
>>
4
)
-
1
;
decoder
->
b_motion
.
f_code
[
0
]
=
(
buffer
[
1
]
&
15
)
-
1
;
decoder
->
b_motion
.
f_code
[
1
]
=
(
buffer
[
2
]
>>
4
)
-
1
;
flags
=
picture
->
flags
;
decoder
->
intra_dc_precision
=
7
-
((
buffer
[
2
]
>>
2
)
&
3
);
decoder
->
picture_structure
=
buffer
[
2
]
&
3
;
switch
(
decoder
->
picture_structure
)
{
case
TOP_FIELD
:
//flags |= PIC_FLAG_TOP_FIELD_FIRST;
case
BOTTOM_FIELD
:
picture
->
nb_fields
=
1
;
break
;
case
FRAME_PICTURE
:
if
(
!
(
mpeg2dec
->
sequence
.
flags
&
SEQ_FLAG_PROGRESSIVE_SEQUENCE
)
)
{
picture
->
nb_fields
=
(
buffer
[
3
]
&
2
)
?
3
:
2
;
flags
|=
(
buffer
[
3
]
&
128
)
?
PIC_FLAG_TOP_FIELD_FIRST
:
0
;
}
else
picture
->
nb_fields
=
(
buffer
[
3
]
&
2
)
?
((
buffer
[
3
]
&
128
)
?
6
:
4
)
:
2
;
break
;
default:
return
1
;
}
decoder
->
top_field_first
=
buffer
[
3
]
>>
7
;
if
(
decoder
->
top_field_first
)
flags
|=
PIC_FLAG_TOP_FIELD_FIRST
;
decoder
->
frame_pred_frame_dct
=
(
buffer
[
3
]
>>
6
)
&
1
;
decoder
->
concealment_motion_vectors
=
(
buffer
[
3
]
>>
5
)
&
1
;
decoder
->
q_scale_type
=
(
buffer
[
3
]
>>
4
)
&
1
;
mpeg2dec
->
q_scale_type
=
buffer
[
3
]
&
16
;
decoder
->
intra_vlc_format
=
(
buffer
[
3
]
>>
3
)
&
1
;
decoder
->
scan
=
(
buffer
[
3
]
&
4
)
?
mpeg2_scan_alt
:
mpeg2_scan_norm
;
flags
|=
(
buffer
[
4
]
&
0x80
)
?
PIC_FLAG_PROGRESSIVE_FRAME
:
0
;
if
(
buffer
[
4
]
&
0x40
)
flags
|=
(((
buffer
[
4
]
<<
26
)
|
(
buffer
[
5
]
<<
18
)
|
(
buffer
[
6
]
<<
10
))
&
PIC_MASK_COMPOSITE_DISPLAY
)
|
PIC_FLAG_COMPOSITE_DISPLAY
;
picture
->
flags
=
flags
;
mpeg2dec
->
ext_state
=
PIC_DISPLAY_EXT
|
COPYRIGHT_EXT
|
QUANT_MATRIX_EXT
;
return
0
;
}
static
int
picture_display_ext
(
mpeg2dec_t
*
mpeg2dec
)
{
uint8_t
*
buffer
=
mpeg2dec
->
chunk_start
;
mpeg2_picture_t
*
picture
=
&
(
mpeg2dec
->
new_picture
);
int
i
,
nb_pos
;
nb_pos
=
picture
->
nb_fields
;
if
(
mpeg2dec
->
sequence
.
flags
&
SEQ_FLAG_PROGRESSIVE_SEQUENCE
)
nb_pos
>>=
1
;
for
(
i
=
0
;
i
<
nb_pos
;
i
++
)
{
int
x
,
y
;
x
=
((
buffer
[
4
*
i
]
<<
24
)
|
(
buffer
[
4
*
i
+
1
]
<<
16
)
|
(
buffer
[
4
*
i
+
2
]
<<
8
)
|
buffer
[
4
*
i
+
3
])
>>
(
11
-
2
*
i
);
y
=
((
buffer
[
4
*
i
+
2
]
<<
24
)
|
(
buffer
[
4
*
i
+
3
]
<<
16
)
|
(
buffer
[
4
*
i
+
4
]
<<
8
)
|
buffer
[
4
*
i
+
5
])
>>
(
10
-
2
*
i
);
if
(
!
(
x
&
y
&
1
)
)
return
1
;
picture
->
display_offset
[
i
].
x
=
mpeg2dec
->
display_offset_x
=
x
>>
1
;
picture
->
display_offset
[
i
].
y
=
mpeg2dec
->
display_offset_y
=
y
>>
1
;
}
for
(
;
i
<
3
;
i
++
)
{
picture
->
display_offset
[
i
].
x
=
mpeg2dec
->
display_offset_x
;
picture
->
display_offset
[
i
].
y
=
mpeg2dec
->
display_offset_y
;
}
return
0
;
}
void
mpeg2_header_picture_finalize
(
mpeg2dec_t
*
mpeg2dec
,
uint32_t
accels
)
{
mpeg2_decoder_t
*
decoder
=
&
(
mpeg2dec
->
decoder
);
int
old_type_b
=
(
decoder
->
coding_type
==
B_TYPE
);
int
low_delay
=
mpeg2dec
->
sequence
.
flags
&
SEQ_FLAG_LOW_DELAY
;
finalize_matrix
(
mpeg2dec
);
decoder
->
coding_type
=
mpeg2dec
->
new_picture
.
flags
&
PIC_MASK_CODING_TYPE
;
/* move in header_process_picture_header */
decoder
->
second_field
=
(
decoder
->
picture_structure
!=
FRAME_PICTURE
)
&&
!
(
decoder
->
second_field
);
if
(
mpeg2dec
->
state
==
STATE_PICTURE
)
{
mpeg2_picture_t
*
picture
;
mpeg2_picture_t
*
other
;
/* decoder->second_field = 0; */
picture
=
other
=
mpeg2dec
->
pictures
;
if
(
old_type_b
^
(
mpeg2dec
->
picture
<
mpeg2dec
->
pictures
+
2
)
)
picture
+=
2
;
else
other
+=
2
;
mpeg2dec
->
picture
=
picture
;
*
picture
=
mpeg2dec
->
new_picture
;
if
(
!
old_type_b
)
{
mpeg2dec
->
fbuf
[
2
]
=
mpeg2dec
->
fbuf
[
1
];
mpeg2dec
->
fbuf
[
1
]
=
mpeg2dec
->
fbuf
[
0
];
}
mpeg2dec
->
fbuf
[
0
]
=
NULL
;
mpeg2_reset_info
(
&
(
mpeg2dec
->
info
));
mpeg2dec
->
info
.
current_picture
=
picture
;
mpeg2dec
->
info
.
display_picture
=
picture
;
if
(
decoder
->
coding_type
!=
B_TYPE
)
{
if
(
!
low_delay
)
{
if
(
mpeg2dec
->
first
)
{
mpeg2dec
->
info
.
display_picture
=
NULL
;
mpeg2dec
->
first
=
0
;
}
else
{
mpeg2dec
->
info
.
display_picture
=
other
;
if
(
other
->
nb_fields
==
1
)
mpeg2dec
->
info
.
display_picture_2nd
=
other
+
1
;
mpeg2dec
->
info
.
display_fbuf
=
mpeg2dec
->
fbuf
[
1
];
}
}
if
(
!
low_delay
+
!
mpeg2dec
->
convert
)
mpeg2dec
->
info
.
discard_fbuf
=
mpeg2dec
->
fbuf
[
!
low_delay
+
!
mpeg2dec
->
convert
];
}
if
(
mpeg2dec
->
convert
)
{
mpeg2_convert_init_t
convert_init
;
if
(
!
mpeg2dec
->
convert_start
)
{
int
y_size
,
uv_size
;
mpeg2dec
->
decoder
.
convert_id
=
mpeg2_malloc
(
mpeg2dec
->
convert_id_size
,
MPEG2_ALLOC_CONVERT_ID
);
mpeg2dec
->
convert
(
MPEG2_CONVERT_START
,
mpeg2dec
->
decoder
.
convert_id
,
&
(
mpeg2dec
->
sequence
),
mpeg2dec
->
convert_stride
,
accels
,
mpeg2dec
->
convert_arg
,
&
convert_init
);
mpeg2dec
->
convert_start
=
convert_init
.
start
;
mpeg2dec
->
decoder
.
convert
=
convert_init
.
copy
;
y_size
=
decoder
->
stride_frame
*
mpeg2dec
->
sequence
.
height
;
uv_size
=
y_size
>>
(
2
-
mpeg2dec
->
decoder
.
chroma_format
);
mpeg2dec
->
yuv_buf
[
0
][
0
]
=
(
uint8_t
*
)
mpeg2_malloc
(
y_size
,
MPEG2_ALLOC_YUV
);
mpeg2dec
->
yuv_buf
[
0
][
1
]
=
(
uint8_t
*
)
mpeg2_malloc
(
uv_size
,
MPEG2_ALLOC_YUV
);
mpeg2dec
->
yuv_buf
[
0
][
2
]
=
(
uint8_t
*
)
mpeg2_malloc
(
uv_size
,
MPEG2_ALLOC_YUV
);
mpeg2dec
->
yuv_buf
[
1
][
0
]
=
(
uint8_t
*
)
mpeg2_malloc
(
y_size
,
MPEG2_ALLOC_YUV
);
mpeg2dec
->
yuv_buf
[
1
][
1
]
=
(
uint8_t
*
)
mpeg2_malloc
(
uv_size
,
MPEG2_ALLOC_YUV
);
mpeg2dec
->
yuv_buf
[
1
][
2
]
=
(
uint8_t
*
)
mpeg2_malloc
(
uv_size
,
MPEG2_ALLOC_YUV
);
y_size
=
decoder
->
stride_frame
*
32
;
uv_size
=
y_size
>>
(
2
-
mpeg2dec
->
decoder
.
chroma_format
);
mpeg2dec
->
yuv_buf
[
2
][
0
]
=
(
uint8_t
*
)
mpeg2_malloc
(
y_size
,
MPEG2_ALLOC_YUV
);
mpeg2dec
->
yuv_buf
[
2
][
1
]
=
(
uint8_t
*
)
mpeg2_malloc
(
uv_size
,
MPEG2_ALLOC_YUV
);
mpeg2dec
->
yuv_buf
[
2
][
2
]
=
(
uint8_t
*
)
mpeg2_malloc
(
uv_size
,
MPEG2_ALLOC_YUV
);
}
if
(
!
mpeg2dec
->
custom_fbuf
)
{
while
(
mpeg2dec
->
alloc_index
<
3
)
{
mpeg2_fbuf_t
*
fbuf
;
fbuf
=
&
mpeg2dec
->
fbuf_alloc
[
mpeg2dec
->
alloc_index
++
].
fbuf
;
fbuf
->
id
=
NULL
;
fbuf
->
buf
[
0
]
=
(
uint8_t
*
)
mpeg2_malloc
(
convert_init
.
buf_size
[
0
],
MPEG2_ALLOC_CONVERTED
);
fbuf
->
buf
[
1
]
=
(
uint8_t
*
)
mpeg2_malloc
(
convert_init
.
buf_size
[
1
],
MPEG2_ALLOC_CONVERTED
);
fbuf
->
buf
[
2
]
=
(
uint8_t
*
)
mpeg2_malloc
(
convert_init
.
buf_size
[
2
],
MPEG2_ALLOC_CONVERTED
);
}
mpeg2_set_fbuf
(
mpeg2dec
,
(
decoder
->
coding_type
==
B_TYPE
)
);
}
}
else
if
(
!
mpeg2dec
->
custom_fbuf
)
{
while
(
mpeg2dec
->
alloc_index
<
3
)
{
mpeg2_fbuf_t
*
fbuf
;
int
y_size
,
uv_size
;
fbuf
=
&
(
mpeg2dec
->
fbuf_alloc
[
mpeg2dec
->
alloc_index
++
].
fbuf
);
fbuf
->
id
=
NULL
;
y_size
=
decoder
->
stride_frame
*
mpeg2dec
->
sequence
.
height
;
uv_size
=
y_size
>>
(
2
-
decoder
->
chroma_format
);
fbuf
->
buf
[
0
]
=
(
uint8_t
*
)
mpeg2_malloc
(
y_size
,
MPEG2_ALLOC_YUV
);
fbuf
->
buf
[
1
]
=
(
uint8_t
*
)
mpeg2_malloc
(
uv_size
,
MPEG2_ALLOC_YUV
);
fbuf
->
buf
[
2
]
=
(
uint8_t
*
)
mpeg2_malloc
(
uv_size
,
MPEG2_ALLOC_YUV
);
}
mpeg2_set_fbuf
(
mpeg2dec
,
(
decoder
->
coding_type
==
B_TYPE
));
}
}
else
{
/* decoder->second_field = 1; */
mpeg2dec
->
picture
++
;
/* second field picture */
*
(
mpeg2dec
->
picture
)
=
mpeg2dec
->
new_picture
;
mpeg2dec
->
info
.
current_picture_2nd
=
mpeg2dec
->
picture
;
if
(
low_delay
||
decoder
->
coding_type
==
B_TYPE
)
mpeg2dec
->
info
.
display_picture_2nd
=
mpeg2dec
->
picture
;
}
info_user_data
(
mpeg2dec
);
}
static
int
copyright_ext
(
mpeg2dec_t
*
mpeg2dec
)
{
return
0
;
}
static
int
quant_matrix_ext
(
mpeg2dec_t
*
mpeg2dec
)
{
uint8_t
*
buffer
=
mpeg2dec
->
chunk_start
;
int
i
,
j
;
for
(
i
=
0
;
i
<
4
;
i
++
)
{
if
(
buffer
[
0
]
&
(
8
>>
i
))
{
for
(
j
=
0
;
j
<
64
;
j
++
)
mpeg2dec
->
new_quantizer_matrix
[
i
][
mpeg2_scan_norm
[
j
]]
=
(
buffer
[
j
]
<<
(
i
+
5
))
|
(
buffer
[
j
+
1
]
>>
(
3
-
i
));
mpeg2dec
->
copy_matrix
|=
1
<<
i
;
buffer
+=
64
;
}
}
return
0
;
}
int
mpeg2_header_extension
(
mpeg2dec_t
*
mpeg2dec
)
{
static
int
(
*
parser
[])
(
mpeg2dec_t
*
)
=
{
0
,
sequence_ext
,
sequence_display_ext
,
quant_matrix_ext
,
copyright_ext
,
0
,
0
,
picture_display_ext
,
picture_coding_ext
};
int
ext
,
ext_bit
;
ext
=
mpeg2dec
->
chunk_start
[
0
]
>>
4
;
ext_bit
=
1
<<
ext
;
if
(
!
(
mpeg2dec
->
ext_state
&
ext_bit
)
)
return
0
;
/* ignore illegal extensions */
mpeg2dec
->
ext_state
&=
~
ext_bit
;
return
parser
[
ext
]
(
mpeg2dec
);
}
int
mpeg2_header_user_data
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2dec
->
user_data_len
+=
mpeg2dec
->
chunk_ptr
-
1
-
mpeg2dec
->
chunk_start
;
mpeg2dec
->
chunk_start
=
mpeg2dec
->
chunk_ptr
-
1
;
return
0
;
}
static
void
prescale
(
mpeg2dec_t
*
mpeg2dec
,
int
index
)
{
static
int
non_linear_scale
[]
=
{
0
,
1
,
2
,
3
,
4
,
5
,
6
,
7
,
8
,
10
,
12
,
14
,
16
,
18
,
20
,
22
,
24
,
28
,
32
,
36
,
40
,
44
,
48
,
52
,
56
,
64
,
72
,
80
,
88
,
96
,
104
,
112
};
int
i
,
j
,
k
;
mpeg2_decoder_t
*
decoder
=
&
(
mpeg2dec
->
decoder
);
if
(
mpeg2dec
->
scaled
[
index
]
!=
mpeg2dec
->
q_scale_type
)
{
mpeg2dec
->
scaled
[
index
]
=
mpeg2dec
->
q_scale_type
;
for
(
i
=
0
;
i
<
32
;
i
++
)
{
k
=
mpeg2dec
->
q_scale_type
?
non_linear_scale
[
i
]
:
(
i
<<
1
);
for
(
j
=
0
;
j
<
64
;
j
++
)
decoder
->
quantizer_prescale
[
index
][
i
][
j
]
=
k
*
mpeg2dec
->
quantizer_matrix
[
index
][
j
];
}
}
}
mpeg2_state_t
mpeg2_header_slice_start
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2_decoder_t
*
decoder
=
&
(
mpeg2dec
->
decoder
);
mpeg2dec
->
info
.
user_data
=
NULL
;
mpeg2dec
->
info
.
user_data_len
=
0
;
mpeg2dec
->
state
=
((
mpeg2dec
->
picture
->
nb_fields
>
1
||
mpeg2dec
->
state
==
STATE_PICTURE_2ND
)
?
STATE_SLICE
:
STATE_SLICE_1ST
);
if
(
mpeg2dec
->
decoder
.
coding_type
!=
D_TYPE
)
{
prescale
(
mpeg2dec
,
0
);
if
(
decoder
->
chroma_quantizer
[
0
]
==
decoder
->
quantizer_prescale
[
2
]
)
prescale
(
mpeg2dec
,
2
);
if
(
mpeg2dec
->
decoder
.
coding_type
!=
I_TYPE
)
{
prescale
(
mpeg2dec
,
1
);
if
(
decoder
->
chroma_quantizer
[
1
]
==
decoder
->
quantizer_prescale
[
3
]
)
prescale
(
mpeg2dec
,
3
);
}
}
if
(
!
(
mpeg2dec
->
nb_decode_slices
)
)
mpeg2dec
->
picture
->
flags
|=
PIC_FLAG_SKIP
;
else
if
(
mpeg2dec
->
convert_start
)
{
mpeg2dec
->
convert_start
(
decoder
->
convert_id
,
mpeg2dec
->
fbuf
[
0
],
mpeg2dec
->
picture
,
mpeg2dec
->
info
.
gop
);
if
(
mpeg2dec
->
decoder
.
coding_type
==
B_TYPE
)
mpeg2_init_fbuf
(
&
(
mpeg2dec
->
decoder
),
mpeg2dec
->
yuv_buf
[
2
],
mpeg2dec
->
yuv_buf
[
mpeg2dec
->
yuv_index
^
1
],
mpeg2dec
->
yuv_buf
[
mpeg2dec
->
yuv_index
]
);
else
{
mpeg2_init_fbuf
(
&
(
mpeg2dec
->
decoder
),
mpeg2dec
->
yuv_buf
[
mpeg2dec
->
yuv_index
^
1
],
mpeg2dec
->
yuv_buf
[
mpeg2dec
->
yuv_index
],
mpeg2dec
->
yuv_buf
[
mpeg2dec
->
yuv_index
]
);
if
(
mpeg2dec
->
state
==
STATE_SLICE
)
mpeg2dec
->
yuv_index
^=
1
;
}
}
else
{
int
b_type
;
b_type
=
(
mpeg2dec
->
decoder
.
coding_type
==
B_TYPE
);
mpeg2_init_fbuf
(
&
(
mpeg2dec
->
decoder
),
mpeg2dec
->
fbuf
[
0
]
->
buf
,
mpeg2dec
->
fbuf
[
b_type
+
1
]
->
buf
,
mpeg2dec
->
fbuf
[
b_type
]
->
buf
);
}
mpeg2dec
->
action
=
NULL
;
return
(
mpeg2_state_t
)
-
1
;
}
static
mpeg2_state_t
seek_sequence
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2_reset_info
(
&
(
mpeg2dec
->
info
));
mpeg2dec
->
info
.
sequence
=
NULL
;
mpeg2dec
->
info
.
gop
=
NULL
;
mpeg2_header_state_init
(
mpeg2dec
);
mpeg2dec
->
action
=
mpeg2_seek_header
;
return
mpeg2_seek_header
(
mpeg2dec
);
}
mpeg2_state_t
mpeg2_header_end
(
mpeg2dec_t
*
mpeg2dec
)
{
mpeg2_picture_t
*
picture
;
int
b_type
;
b_type
=
(
mpeg2dec
->
decoder
.
coding_type
==
B_TYPE
);
picture
=
mpeg2dec
->
pictures
;
if
(
(
mpeg2dec
->
picture
>=
picture
+
2
)
^
b_type
)
picture
=
mpeg2dec
->
pictures
+
2
;
mpeg2_reset_info
(
&
(
mpeg2dec
->
info
));
if
(
!
(
mpeg2dec
->
sequence
.
flags
&
SEQ_FLAG_LOW_DELAY
)
)
{
mpeg2dec
->
info
.
display_picture
=
picture
;
if
(
picture
->
nb_fields
==
1
)
mpeg2dec
->
info
.
display_picture_2nd
=
picture
+
1
;
mpeg2dec
->
info
.
display_fbuf
=
mpeg2dec
->
fbuf
[
b_type
];
if
(
!
mpeg2dec
->
convert
)
mpeg2dec
->
info
.
discard_fbuf
=
mpeg2dec
->
fbuf
[
b_type
+
1
];
}
else
if
(
!
mpeg2dec
->
convert
)
mpeg2dec
->
info
.
discard_fbuf
=
mpeg2dec
->
fbuf
[
b_type
];
mpeg2dec
->
action
=
seek_sequence
;
return
STATE_END
;
}
modules/codec/xvmc/motion_comp.c
deleted
100644 → 0
View file @
a2180073
/* $Id$
* motion_comp.c
* 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.
* 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
*/
#include "config.h"
#include <inttypes.h>
#include "mpeg2.h"
#include "attributes.h"
#include "mpeg2_internal.h"
mpeg2_mc_t
mpeg2_mc
;
void
mpeg2_mc_init
(
uint32_t
accel
)
{
if
(
accel
&
MPEG2_ACCEL_X86_MMXEXT
)
mpeg2_mc
=
mpeg2_mc_mmxext
;
else
if
(
accel
&
MPEG2_ACCEL_X86_3DNOW
)
mpeg2_mc
=
mpeg2_mc_3dnow
;
else
if
(
accel
&
MPEG2_ACCEL_X86_MMX
)
mpeg2_mc
=
mpeg2_mc_mmx
;
else
mpeg2_mc
=
mpeg2_mc_c
;
}
#define avg2(a,b) ((a+b+1)>>1)
#define avg4(a,b,c,d) ((a+b+c+d+2)>>2)
#define predict_o(i) (ref[i])
#define predict_x(i) (avg2 (ref[i], ref[i+1]))
#define predict_y(i) (avg2 (ref[i], (ref+stride)[i]))
#define predict_xy(i) (avg4 (ref[i], ref[i+1], \
(ref+stride)[i], (ref+stride)[i+1]))
#define put(predictor,i) dest[i] = predictor (i)
#define avg(predictor,i) dest[i] = avg2 (predictor (i), dest[i])
/* mc function template */
#define MC_FUNC(op,xy) \
static void MC_##op##_##xy##_16_c (uint8_t * dest, const uint8_t * ref, \
const int stride, int height) \
{ \
do { \
op (predict_##xy, 0); \
op (predict_##xy, 1); \
op (predict_##xy, 2); \
op (predict_##xy, 3); \
op (predict_##xy, 4); \
op (predict_##xy, 5); \
op (predict_##xy, 6); \
op (predict_##xy, 7); \
op (predict_##xy, 8); \
op (predict_##xy, 9); \
op (predict_##xy, 10); \
op (predict_##xy, 11); \
op (predict_##xy, 12); \
op (predict_##xy, 13); \
op (predict_##xy, 14); \
op (predict_##xy, 15); \
ref += stride; \
dest += stride; \
} while (--height); \
} \
static void MC_##op##_##xy##_8_c (uint8_t * dest, const uint8_t * ref, \
const int stride, int height) \
{ \
do { \
op (predict_##xy, 0); \
op (predict_##xy, 1); \
op (predict_##xy, 2); \
op (predict_##xy, 3); \
op (predict_##xy, 4); \
op (predict_##xy, 5); \
op (predict_##xy, 6); \
op (predict_##xy, 7); \
ref += stride; \
dest += stride; \
} while (--height); \
}
/* definitions of the actual mc functions */
MC_FUNC
(
put
,
o
)
MC_FUNC
(
avg
,
o
)
MC_FUNC
(
put
,
x
)
MC_FUNC
(
avg
,
x
)
MC_FUNC
(
put
,
y
)
MC_FUNC
(
avg
,
y
)
MC_FUNC
(
put
,
xy
)
MC_FUNC
(
avg
,
xy
)
MPEG2_MC_EXTERN
(
c
)
modules/codec/xvmc/motion_comp_mmx.c
deleted
100644 → 0
View file @
a2180073
/* $Id$
* motion_comp_mmx.c
* 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.
* 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
*/
#include "config.h"
#include <inttypes.h>
#include "mpeg2.h"
#include "attributes.h"
#include "mpeg2_internal.h"
#include "mmx.h"
#define CPU_MMXEXT 0
#define CPU_3DNOW 1
/* MMX code - needs a rewrite */
/*
* Motion Compensation frequently needs to average values using the
* formula (x+y+1)>>1. Both MMXEXT and 3Dnow include one instruction
* to compute this, but it's been left out of classic MMX.
*
* We need to be careful of overflows when doing this computation.
* Rather than unpacking data to 16-bits, which reduces parallelism,
* we use the following formulas:
*
* (x+y)>>1 == (x&y)+((x^y)>>1)
* (x+y+1)>>1 == (x|y)-((x^y)>>1)
*/
/* some rounding constants */
static
mmx_t
mask1
=
{
0xfefefefefefefefeLL
};
static
mmx_t
round4
=
{
0x0002000200020002LL
};
/*
* This code should probably be compiled with loop unrolling
* (ie, -funroll-loops in gcc)becuase some of the loops
* use a small static number of iterations. This was written
* with the assumption the compiler knows best about when
* unrolling will help
*/
static
inline
void
mmx_zero_reg
()
{
/* load 0 into mm0 */
pxor_r2r
(
mm0
,
mm0
);
}
static
inline
void
mmx_average_2_U8
(
uint8_t
*
dest
,
const
uint8_t
*
src1
,
const
uint8_t
*
src2
)
{
/* *dest = (*src1 + *src2 + 1)/ 2; */
movq_m2r
(
*
src1
,
mm1
);
/* load 8 src1 bytes */
movq_r2r
(
mm1
,
mm2
);
/* copy 8 src1 bytes */
movq_m2r
(
*
src2
,
mm3
);
/* load 8 src2 bytes */
movq_r2r
(
mm3
,
mm4
);
/* copy 8 src2 bytes */
pxor_r2r
(
mm1
,
mm3
);
/* xor src1 and src2 */
pand_m2r
(
mask1
,
mm3
);
/* mask lower bits */
psrlq_i2r
(
1
,
mm3
);
/* /2 */
por_r2r
(
mm2
,
mm4
);
/* or src1 and src2 */
psubb_r2r
(
mm3
,
mm4
);
/* subtract subresults */
movq_r2m
(
mm4
,
*
dest
);
/* store result in dest */
}
static
inline
void
mmx_interp_average_2_U8
(
uint8_t
*
dest
,
const
uint8_t
*
src1
,
const
uint8_t
*
src2
)
{
/* *dest = (*dest + (*src1 + *src2 + 1)/ 2 + 1)/ 2; */
movq_m2r
(
*
dest
,
mm1
);
/* load 8 dest bytes */
movq_r2r
(
mm1
,
mm2
);
/* copy 8 dest bytes */
movq_m2r
(
*
src1
,
mm3
);
/* load 8 src1 bytes */
movq_r2r
(
mm3
,
mm4
);
/* copy 8 src1 bytes */
movq_m2r
(
*
src2
,
mm5
);
/* load 8 src2 bytes */
movq_r2r
(
mm5
,
mm6
);
/* copy 8 src2 bytes */
pxor_r2r
(
mm3
,
mm5
);
/* xor src1 and src2 */
pand_m2r
(
mask1
,
mm5
);
/* mask lower bits */
psrlq_i2r
(
1
,
mm5
);
/* /2 */
por_r2r
(
mm4
,
mm6
);
/* or src1 and src2 */
psubb_r2r
(
mm5
,
mm6
);
/* subtract subresults */
movq_r2r
(
mm6
,
mm5
);
/* copy subresult */
pxor_r2r
(
mm1
,
mm5
);
/* xor srcavg and dest */
pand_m2r
(
mask1
,
mm5
);
/* mask lower bits */
psrlq_i2r
(
1
,
mm5
);
/* /2 */
por_r2r
(
mm2
,
mm6
);
/* or srcavg and dest */
psubb_r2r
(
mm5
,
mm6
);
/* subtract subresults */
movq_r2m
(
mm6
,
*
dest
);
/* store result in dest */
}
static
inline
void
mmx_average_4_U8
(
uint8_t
*
dest
,
const
uint8_t
*
src1
,
const
uint8_t
*
src2
,
const
uint8_t
*
src3
,
const
uint8_t
*
src4
)
{
/* *dest = (*src1 + *src2 + *src3 + *src4 + 2)/ 4; */
movq_m2r
(
*
src1
,
mm1
);
/* load 8 src1 bytes */
movq_r2r
(
mm1
,
mm2
);
/* copy 8 src1 bytes */
punpcklbw_r2r
(
mm0
,
mm1
);
/* unpack low src1 bytes */
punpckhbw_r2r
(
mm0
,
mm2
);
/* unpack high src1 bytes */
movq_m2r
(
*
src2
,
mm3
);
/* load 8 src2 bytes */
movq_r2r
(
mm3
,
mm4
);
/* copy 8 src2 bytes */
punpcklbw_r2r
(
mm0
,
mm3
);
/* unpack low src2 bytes */
punpckhbw_r2r
(
mm0
,
mm4
);
/* unpack high src2 bytes */
paddw_r2r
(
mm3
,
mm1
);
/* add lows */
paddw_r2r
(
mm4
,
mm2
);
/* add highs */
/* now have partials in mm1 and mm2 */
movq_m2r
(
*
src3
,
mm3
);
/* load 8 src3 bytes */
movq_r2r
(
mm3
,
mm4
);
/* copy 8 src3 bytes */
punpcklbw_r2r
(
mm0
,
mm3
);
/* unpack low src3 bytes */
punpckhbw_r2r
(
mm0
,
mm4
);
/* unpack high src3 bytes */
paddw_r2r
(
mm3
,
mm1
);
/* add lows */
paddw_r2r
(
mm4
,
mm2
);
/* add highs */
movq_m2r
(
*
src4
,
mm5
);
/* load 8 src4 bytes */
movq_r2r
(
mm5
,
mm6
);
/* copy 8 src4 bytes */
punpcklbw_r2r
(
mm0
,
mm5
);
/* unpack low src4 bytes */
punpckhbw_r2r
(
mm0
,
mm6
);
/* unpack high src4 bytes */
paddw_r2r
(
mm5
,
mm1
);
/* add lows */
paddw_r2r
(
mm6
,
mm2
);
/* add highs */
/* now have subtotal in mm1 and mm2 */
paddw_m2r
(
round4
,
mm1
);
psraw_i2r
(
2
,
mm1
);
/* /4 */
paddw_m2r
(
round4
,
mm2
);
psraw_i2r
(
2
,
mm2
);
/* /4 */
packuswb_r2r
(
mm2
,
mm1
);
/* pack (w/ saturation) */
movq_r2m
(
mm1
,
*
dest
);
/* store result in dest */
}
static
inline
void
mmx_interp_average_4_U8
(
uint8_t
*
dest
,
const
uint8_t
*
src1
,
const
uint8_t
*
src2
,
const
uint8_t
*
src3
,
const
uint8_t
*
src4
)
{
/* *dest = (*dest + (*src1 + *src2 + *src3 + *src4 + 2)/ 4 + 1)/ 2; */
movq_m2r
(
*
src1
,
mm1
);
/* load 8 src1 bytes */
movq_r2r
(
mm1
,
mm2
);
/* copy 8 src1 bytes */
punpcklbw_r2r
(
mm0
,
mm1
);
/* unpack low src1 bytes */
punpckhbw_r2r
(
mm0
,
mm2
);
/* unpack high src1 bytes */
movq_m2r
(
*
src2
,
mm3
);
/* load 8 src2 bytes */
movq_r2r
(
mm3
,
mm4
);
/* copy 8 src2 bytes */
punpcklbw_r2r
(
mm0
,
mm3
);
/* unpack low src2 bytes */
punpckhbw_r2r
(
mm0
,
mm4
);
/* unpack high src2 bytes */
paddw_r2r
(
mm3
,
mm1
);
/* add lows */
paddw_r2r
(
mm4
,
mm2
);
/* add highs */
/* now have partials in mm1 and mm2 */
movq_m2r
(
*
src3
,
mm3
);
/* load 8 src3 bytes */
movq_r2r
(
mm3
,
mm4
);
/* copy 8 src3 bytes */
punpcklbw_r2r
(
mm0
,
mm3
);
/* unpack low src3 bytes */
punpckhbw_r2r
(
mm0
,
mm4
);
/* unpack high src3 bytes */
paddw_r2r
(
mm3
,
mm1
);
/* add lows */
paddw_r2r
(
mm4
,
mm2
);
/* add highs */
movq_m2r
(
*
src4
,
mm5
);
/* load 8 src4 bytes */
movq_r2r
(
mm5
,
mm6
);
/* copy 8 src4 bytes */
punpcklbw_r2r
(
mm0
,
mm5
);
/* unpack low src4 bytes */
punpckhbw_r2r
(
mm0
,
mm6
);
/* unpack high src4 bytes */
paddw_r2r
(
mm5
,
mm1
);
/* add lows */
paddw_r2r
(
mm6
,
mm2
);
/* add highs */
paddw_m2r
(
round4
,
mm1
);
psraw_i2r
(
2
,
mm1
);
/* /4 */
paddw_m2r
(
round4
,
mm2
);
psraw_i2r
(
2
,
mm2
);
/* /4 */
/* now have subtotal/4 in mm1 and mm2 */
movq_m2r
(
*
dest
,
mm3
);
/* load 8 dest bytes */
movq_r2r
(
mm3
,
mm4
);
/* copy 8 dest bytes */
packuswb_r2r
(
mm2
,
mm1
);
/* pack (w/ saturation) */
movq_r2r
(
mm1
,
mm2
);
/* copy subresult */
pxor_r2r
(
mm1
,
mm3
);
/* xor srcavg and dest */
pand_m2r
(
mask1
,
mm3
);
/* mask lower bits */
psrlq_i2r
(
1
,
mm3
);
/* /2 */
por_r2r
(
mm2
,
mm4
);
/* or srcavg and dest */
psubb_r2r
(
mm3
,
mm4
);
/* subtract subresults */
movq_r2m
(
mm4
,
*
dest
);
/* store result in dest */
}
/*-----------------------------------------------------------------------*/
static
inline
void
MC_avg_mmx
(
const
int
width
,
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
mmx_zero_reg
();
do
{
mmx_average_2_U8
(
dest
,
dest
,
ref
);
if
(
width
==
16
)
mmx_average_2_U8
(
dest
+
8
,
dest
+
8
,
ref
+
8
);
dest
+=
stride
;
ref
+=
stride
;
}
while
(
--
height
);
}
static
void
MC_avg_o_16_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg_mmx
(
16
,
height
,
dest
,
ref
,
stride
);
}
static
void
MC_avg_o_8_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg_mmx
(
8
,
height
,
dest
,
ref
,
stride
);
}
/*-----------------------------------------------------------------------*/
static
inline
void
MC_put_mmx
(
const
int
width
,
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
mmx_zero_reg
();
do
{
movq_m2r
(
*
ref
,
mm1
);
/* load 8 ref bytes */
movq_r2m
(
mm1
,
*
dest
);
/* store 8 bytes at curr */
if
(
width
==
16
)
{
movq_m2r
(
*
(
ref
+
8
),
mm1
);
/* load 8 ref bytes */
movq_r2m
(
mm1
,
*
(
dest
+
8
));
/* store 8 bytes at curr */
}
dest
+=
stride
;
ref
+=
stride
;
}
while
(
--
height
);
}
static
void
MC_put_o_16_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put_mmx
(
16
,
height
,
dest
,
ref
,
stride
);
}
static
void
MC_put_o_8_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put_mmx
(
8
,
height
,
dest
,
ref
,
stride
);
}
/*-----------------------------------------------------------------------*/
/* Half pixel interpolation in the x direction */
static
inline
void
MC_avg_x_mmx
(
const
int
width
,
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
mmx_zero_reg
();
do
{
mmx_interp_average_2_U8
(
dest
,
ref
,
ref
+
1
);
if
(
width
==
16
)
mmx_interp_average_2_U8
(
dest
+
8
,
ref
+
8
,
ref
+
9
);
dest
+=
stride
;
ref
+=
stride
;
}
while
(
--
height
);
}
static
void
MC_avg_x_16_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg_x_mmx
(
16
,
height
,
dest
,
ref
,
stride
);
}
static
void
MC_avg_x_8_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg_x_mmx
(
8
,
height
,
dest
,
ref
,
stride
);
}
/*-----------------------------------------------------------------------*/
static
inline
void
MC_put_x_mmx
(
const
int
width
,
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
mmx_zero_reg
();
do
{
mmx_average_2_U8
(
dest
,
ref
,
ref
+
1
);
if
(
width
==
16
)
mmx_average_2_U8
(
dest
+
8
,
ref
+
8
,
ref
+
9
);
dest
+=
stride
;
ref
+=
stride
;
}
while
(
--
height
);
}
static
void
MC_put_x_16_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put_x_mmx
(
16
,
height
,
dest
,
ref
,
stride
);
}
static
void
MC_put_x_8_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put_x_mmx
(
8
,
height
,
dest
,
ref
,
stride
);
}
/*-----------------------------------------------------------------------*/
static
inline
void
MC_avg_xy_mmx
(
const
int
width
,
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
const
uint8_t
*
ref_next
=
ref
+
stride
;
mmx_zero_reg
();
do
{
mmx_interp_average_4_U8
(
dest
,
ref
,
ref
+
1
,
ref_next
,
ref_next
+
1
);
if
(
width
==
16
)
mmx_interp_average_4_U8
(
dest
+
8
,
ref
+
8
,
ref
+
9
,
ref_next
+
8
,
ref_next
+
9
);
dest
+=
stride
;
ref
+=
stride
;
ref_next
+=
stride
;
}
while
(
--
height
);
}
static
void
MC_avg_xy_16_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg_xy_mmx
(
16
,
height
,
dest
,
ref
,
stride
);
}
static
void
MC_avg_xy_8_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg_xy_mmx
(
8
,
height
,
dest
,
ref
,
stride
);
}
/*-----------------------------------------------------------------------*/
static
inline
void
MC_put_xy_mmx
(
const
int
width
,
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
const
uint8_t
*
ref_next
=
ref
+
stride
;
mmx_zero_reg
();
do
{
mmx_average_4_U8
(
dest
,
ref
,
ref
+
1
,
ref_next
,
ref_next
+
1
);
if
(
width
==
16
)
mmx_average_4_U8
(
dest
+
8
,
ref
+
8
,
ref
+
9
,
ref_next
+
8
,
ref_next
+
9
);
dest
+=
stride
;
ref
+=
stride
;
ref_next
+=
stride
;
}
while
(
--
height
);
}
static
void
MC_put_xy_16_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put_xy_mmx
(
16
,
height
,
dest
,
ref
,
stride
);
}
static
void
MC_put_xy_8_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put_xy_mmx
(
8
,
height
,
dest
,
ref
,
stride
);
}
/*-----------------------------------------------------------------------*/
static
inline
void
MC_avg_y_mmx
(
const
int
width
,
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
const
uint8_t
*
ref_next
=
ref
+
stride
;
mmx_zero_reg
();
do
{
mmx_interp_average_2_U8
(
dest
,
ref
,
ref_next
);
if
(
width
==
16
)
mmx_interp_average_2_U8
(
dest
+
8
,
ref
+
8
,
ref_next
+
8
);
dest
+=
stride
;
ref
+=
stride
;
ref_next
+=
stride
;
}
while
(
--
height
);
}
static
void
MC_avg_y_16_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg_y_mmx
(
16
,
height
,
dest
,
ref
,
stride
);
}
static
void
MC_avg_y_8_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg_y_mmx
(
8
,
height
,
dest
,
ref
,
stride
);
}
/*-----------------------------------------------------------------------*/
static
inline
void
MC_put_y_mmx
(
const
int
width
,
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
const
uint8_t
*
ref_next
=
ref
+
stride
;
mmx_zero_reg
();
do
{
mmx_average_2_U8
(
dest
,
ref
,
ref_next
);
if
(
width
==
16
)
mmx_average_2_U8
(
dest
+
8
,
ref
+
8
,
ref_next
+
8
);
dest
+=
stride
;
ref
+=
stride
;
ref_next
+=
stride
;
}
while
(
--
height
);
}
static
void
MC_put_y_16_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put_y_mmx
(
16
,
height
,
dest
,
ref
,
stride
);
}
static
void
MC_put_y_8_mmx
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put_y_mmx
(
8
,
height
,
dest
,
ref
,
stride
);
}
MPEG2_MC_EXTERN
(
mmx
)
/* CPU_MMXEXT/CPU_3DNOW adaptation layer */
#define pavg_r2r(src,dest) \
do { \
if (cpu == CPU_MMXEXT) \
pavgb_r2r (src, dest); \
else \
pavgusb_r2r (src, dest); \
} while (0)
#define pavg_m2r(src,dest) \
do { \
if (cpu == CPU_MMXEXT) \
pavgb_m2r (src, dest); \
else \
pavgusb_m2r (src, dest); \
} while (0)
/* CPU_MMXEXT code */
static
inline
void
MC_put1_8
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
movq_r2m
(
mm0
,
*
dest
);
ref
+=
stride
;
dest
+=
stride
;
}
while
(
--
height
);
}
static
inline
void
MC_put1_16
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
movq_m2r
(
*
(
ref
+
8
),
mm1
);
ref
+=
stride
;
movq_r2m
(
mm0
,
*
dest
);
movq_r2m
(
mm1
,
*
(
dest
+
8
));
dest
+=
stride
;
}
while
(
--
height
);
}
static
inline
void
MC_avg1_8
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
cpu
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
pavg_m2r
(
*
dest
,
mm0
);
ref
+=
stride
;
movq_r2m
(
mm0
,
*
dest
);
dest
+=
stride
;
}
while
(
--
height
);
}
static
inline
void
MC_avg1_16
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
cpu
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
movq_m2r
(
*
(
ref
+
8
),
mm1
);
pavg_m2r
(
*
dest
,
mm0
);
pavg_m2r
(
*
(
dest
+
8
),
mm1
);
movq_r2m
(
mm0
,
*
dest
);
ref
+=
stride
;
movq_r2m
(
mm1
,
*
(
dest
+
8
));
dest
+=
stride
;
}
while
(
--
height
);
}
static
inline
void
MC_put2_8
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
offset
,
const
int
cpu
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
pavg_m2r
(
*
(
ref
+
offset
),
mm0
);
ref
+=
stride
;
movq_r2m
(
mm0
,
*
dest
);
dest
+=
stride
;
}
while
(
--
height
);
}
static
inline
void
MC_put2_16
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
offset
,
const
int
cpu
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
movq_m2r
(
*
(
ref
+
8
),
mm1
);
pavg_m2r
(
*
(
ref
+
offset
),
mm0
);
pavg_m2r
(
*
(
ref
+
offset
+
8
),
mm1
);
movq_r2m
(
mm0
,
*
dest
);
ref
+=
stride
;
movq_r2m
(
mm1
,
*
(
dest
+
8
));
dest
+=
stride
;
}
while
(
--
height
);
}
static
inline
void
MC_avg2_8
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
offset
,
const
int
cpu
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
pavg_m2r
(
*
(
ref
+
offset
),
mm0
);
pavg_m2r
(
*
dest
,
mm0
);
ref
+=
stride
;
movq_r2m
(
mm0
,
*
dest
);
dest
+=
stride
;
}
while
(
--
height
);
}
static
inline
void
MC_avg2_16
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
offset
,
const
int
cpu
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
movq_m2r
(
*
(
ref
+
8
),
mm1
);
pavg_m2r
(
*
(
ref
+
offset
),
mm0
);
pavg_m2r
(
*
(
ref
+
offset
+
8
),
mm1
);
pavg_m2r
(
*
dest
,
mm0
);
pavg_m2r
(
*
(
dest
+
8
),
mm1
);
ref
+=
stride
;
movq_r2m
(
mm0
,
*
dest
);
movq_r2m
(
mm1
,
*
(
dest
+
8
));
dest
+=
stride
;
}
while
(
--
height
);
}
static
mmx_t
mask_one
=
{
0x0101010101010101LL
};
static
inline
void
MC_put4_8
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
cpu
)
{
movq_m2r
(
*
ref
,
mm0
);
movq_m2r
(
*
(
ref
+
1
),
mm1
);
movq_r2r
(
mm0
,
mm7
);
pxor_r2r
(
mm1
,
mm7
);
pavg_r2r
(
mm1
,
mm0
);
ref
+=
stride
;
do
{
movq_m2r
(
*
ref
,
mm2
);
movq_r2r
(
mm0
,
mm5
);
movq_m2r
(
*
(
ref
+
1
),
mm3
);
movq_r2r
(
mm2
,
mm6
);
pxor_r2r
(
mm3
,
mm6
);
pavg_r2r
(
mm3
,
mm2
);
por_r2r
(
mm6
,
mm7
);
pxor_r2r
(
mm2
,
mm5
);
pand_r2r
(
mm5
,
mm7
);
pavg_r2r
(
mm2
,
mm0
);
pand_m2r
(
mask_one
,
mm7
);
psubusb_r2r
(
mm7
,
mm0
);
ref
+=
stride
;
movq_r2m
(
mm0
,
*
dest
);
dest
+=
stride
;
movq_r2r
(
mm6
,
mm7
);
/* unroll ! */
movq_r2r
(
mm2
,
mm0
);
/* unroll ! */
}
while
(
--
height
);
}
static
inline
void
MC_put4_16
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
cpu
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
movq_m2r
(
*
(
ref
+
stride
+
1
),
mm1
);
movq_r2r
(
mm0
,
mm7
);
movq_m2r
(
*
(
ref
+
1
),
mm2
);
pxor_r2r
(
mm1
,
mm7
);
movq_m2r
(
*
(
ref
+
stride
),
mm3
);
movq_r2r
(
mm2
,
mm6
);
pxor_r2r
(
mm3
,
mm6
);
pavg_r2r
(
mm1
,
mm0
);
pavg_r2r
(
mm3
,
mm2
);
por_r2r
(
mm6
,
mm7
);
movq_r2r
(
mm0
,
mm6
);
pxor_r2r
(
mm2
,
mm6
);
pand_r2r
(
mm6
,
mm7
);
pand_m2r
(
mask_one
,
mm7
);
pavg_r2r
(
mm2
,
mm0
);
psubusb_r2r
(
mm7
,
mm0
);
movq_r2m
(
mm0
,
*
dest
);
movq_m2r
(
*
(
ref
+
8
),
mm0
);
movq_m2r
(
*
(
ref
+
stride
+
9
),
mm1
);
movq_r2r
(
mm0
,
mm7
);
movq_m2r
(
*
(
ref
+
9
),
mm2
);
pxor_r2r
(
mm1
,
mm7
);
movq_m2r
(
*
(
ref
+
stride
+
8
),
mm3
);
movq_r2r
(
mm2
,
mm6
);
pxor_r2r
(
mm3
,
mm6
);
pavg_r2r
(
mm1
,
mm0
);
pavg_r2r
(
mm3
,
mm2
);
por_r2r
(
mm6
,
mm7
);
movq_r2r
(
mm0
,
mm6
);
pxor_r2r
(
mm2
,
mm6
);
pand_r2r
(
mm6
,
mm7
);
pand_m2r
(
mask_one
,
mm7
);
pavg_r2r
(
mm2
,
mm0
);
psubusb_r2r
(
mm7
,
mm0
);
ref
+=
stride
;
movq_r2m
(
mm0
,
*
(
dest
+
8
));
dest
+=
stride
;
}
while
(
--
height
);
}
static
inline
void
MC_avg4_8
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
cpu
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
movq_m2r
(
*
(
ref
+
stride
+
1
),
mm1
);
movq_r2r
(
mm0
,
mm7
);
movq_m2r
(
*
(
ref
+
1
),
mm2
);
pxor_r2r
(
mm1
,
mm7
);
movq_m2r
(
*
(
ref
+
stride
),
mm3
);
movq_r2r
(
mm2
,
mm6
);
pxor_r2r
(
mm3
,
mm6
);
pavg_r2r
(
mm1
,
mm0
);
pavg_r2r
(
mm3
,
mm2
);
por_r2r
(
mm6
,
mm7
);
movq_r2r
(
mm0
,
mm6
);
pxor_r2r
(
mm2
,
mm6
);
pand_r2r
(
mm6
,
mm7
);
pand_m2r
(
mask_one
,
mm7
);
pavg_r2r
(
mm2
,
mm0
);
psubusb_r2r
(
mm7
,
mm0
);
movq_m2r
(
*
dest
,
mm1
);
pavg_r2r
(
mm1
,
mm0
);
ref
+=
stride
;
movq_r2m
(
mm0
,
*
dest
);
dest
+=
stride
;
}
while
(
--
height
);
}
static
inline
void
MC_avg4_16
(
int
height
,
uint8_t
*
dest
,
const
uint8_t
*
ref
,
const
int
stride
,
const
int
cpu
)
{
do
{
movq_m2r
(
*
ref
,
mm0
);
movq_m2r
(
*
(
ref
+
stride
+
1
),
mm1
);
movq_r2r
(
mm0
,
mm7
);
movq_m2r
(
*
(
ref
+
1
),
mm2
);
pxor_r2r
(
mm1
,
mm7
);
movq_m2r
(
*
(
ref
+
stride
),
mm3
);
movq_r2r
(
mm2
,
mm6
);
pxor_r2r
(
mm3
,
mm6
);
pavg_r2r
(
mm1
,
mm0
);
pavg_r2r
(
mm3
,
mm2
);
por_r2r
(
mm6
,
mm7
);
movq_r2r
(
mm0
,
mm6
);
pxor_r2r
(
mm2
,
mm6
);
pand_r2r
(
mm6
,
mm7
);
pand_m2r
(
mask_one
,
mm7
);
pavg_r2r
(
mm2
,
mm0
);
psubusb_r2r
(
mm7
,
mm0
);
movq_m2r
(
*
dest
,
mm1
);
pavg_r2r
(
mm1
,
mm0
);
movq_r2m
(
mm0
,
*
dest
);
movq_m2r
(
*
(
ref
+
8
),
mm0
);
movq_m2r
(
*
(
ref
+
stride
+
9
),
mm1
);
movq_r2r
(
mm0
,
mm7
);
movq_m2r
(
*
(
ref
+
9
),
mm2
);
pxor_r2r
(
mm1
,
mm7
);
movq_m2r
(
*
(
ref
+
stride
+
8
),
mm3
);
movq_r2r
(
mm2
,
mm6
);
pxor_r2r
(
mm3
,
mm6
);
pavg_r2r
(
mm1
,
mm0
);
pavg_r2r
(
mm3
,
mm2
);
por_r2r
(
mm6
,
mm7
);
movq_r2r
(
mm0
,
mm6
);
pxor_r2r
(
mm2
,
mm6
);
pand_r2r
(
mm6
,
mm7
);
pand_m2r
(
mask_one
,
mm7
);
pavg_r2r
(
mm2
,
mm0
);
psubusb_r2r
(
mm7
,
mm0
);
movq_m2r
(
*
(
dest
+
8
),
mm1
);
pavg_r2r
(
mm1
,
mm0
);
ref
+=
stride
;
movq_r2m
(
mm0
,
*
(
dest
+
8
));
dest
+=
stride
;
}
while
(
--
height
);
}
static
void
MC_avg_o_16_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg1_16
(
height
,
dest
,
ref
,
stride
,
CPU_MMXEXT
);
}
static
void
MC_avg_o_8_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg1_8
(
height
,
dest
,
ref
,
stride
,
CPU_MMXEXT
);
}
static
void
MC_put_o_16_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put1_16
(
height
,
dest
,
ref
,
stride
);
}
static
void
MC_put_o_8_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put1_8
(
height
,
dest
,
ref
,
stride
);
}
static
void
MC_avg_x_16_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg2_16
(
height
,
dest
,
ref
,
stride
,
1
,
CPU_MMXEXT
);
}
static
void
MC_avg_x_8_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg2_8
(
height
,
dest
,
ref
,
stride
,
1
,
CPU_MMXEXT
);
}
static
void
MC_put_x_16_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put2_16
(
height
,
dest
,
ref
,
stride
,
1
,
CPU_MMXEXT
);
}
static
void
MC_put_x_8_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put2_8
(
height
,
dest
,
ref
,
stride
,
1
,
CPU_MMXEXT
);
}
static
void
MC_avg_y_16_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg2_16
(
height
,
dest
,
ref
,
stride
,
stride
,
CPU_MMXEXT
);
}
static
void
MC_avg_y_8_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg2_8
(
height
,
dest
,
ref
,
stride
,
stride
,
CPU_MMXEXT
);
}
static
void
MC_put_y_16_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put2_16
(
height
,
dest
,
ref
,
stride
,
stride
,
CPU_MMXEXT
);
}
static
void
MC_put_y_8_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put2_8
(
height
,
dest
,
ref
,
stride
,
stride
,
CPU_MMXEXT
);
}
static
void
MC_avg_xy_16_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg4_16
(
height
,
dest
,
ref
,
stride
,
CPU_MMXEXT
);
}
static
void
MC_avg_xy_8_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg4_8
(
height
,
dest
,
ref
,
stride
,
CPU_MMXEXT
);
}
static
void
MC_put_xy_16_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put4_16
(
height
,
dest
,
ref
,
stride
,
CPU_MMXEXT
);
}
static
void
MC_put_xy_8_mmxext
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put4_8
(
height
,
dest
,
ref
,
stride
,
CPU_MMXEXT
);
}
MPEG2_MC_EXTERN
(
mmxext
)
static
void
MC_avg_o_16_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg1_16
(
height
,
dest
,
ref
,
stride
,
CPU_3DNOW
);
}
static
void
MC_avg_o_8_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg1_8
(
height
,
dest
,
ref
,
stride
,
CPU_3DNOW
);
}
static
void
MC_put_o_16_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put1_16
(
height
,
dest
,
ref
,
stride
);
}
static
void
MC_put_o_8_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put1_8
(
height
,
dest
,
ref
,
stride
);
}
static
void
MC_avg_x_16_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg2_16
(
height
,
dest
,
ref
,
stride
,
1
,
CPU_3DNOW
);
}
static
void
MC_avg_x_8_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg2_8
(
height
,
dest
,
ref
,
stride
,
1
,
CPU_3DNOW
);
}
static
void
MC_put_x_16_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put2_16
(
height
,
dest
,
ref
,
stride
,
1
,
CPU_3DNOW
);
}
static
void
MC_put_x_8_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put2_8
(
height
,
dest
,
ref
,
stride
,
1
,
CPU_3DNOW
);
}
static
void
MC_avg_y_16_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg2_16
(
height
,
dest
,
ref
,
stride
,
stride
,
CPU_3DNOW
);
}
static
void
MC_avg_y_8_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg2_8
(
height
,
dest
,
ref
,
stride
,
stride
,
CPU_3DNOW
);
}
static
void
MC_put_y_16_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put2_16
(
height
,
dest
,
ref
,
stride
,
stride
,
CPU_3DNOW
);
}
static
void
MC_put_y_8_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put2_8
(
height
,
dest
,
ref
,
stride
,
stride
,
CPU_3DNOW
);
}
static
void
MC_avg_xy_16_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg4_16
(
height
,
dest
,
ref
,
stride
,
CPU_3DNOW
);
}
static
void
MC_avg_xy_8_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_avg4_8
(
height
,
dest
,
ref
,
stride
,
CPU_3DNOW
);
}
static
void
MC_put_xy_16_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put4_16
(
height
,
dest
,
ref
,
stride
,
CPU_3DNOW
);
}
static
void
MC_put_xy_8_3dnow
(
uint8_t
*
dest
,
const
uint8_t
*
ref
,
int
stride
,
int
height
)
{
MC_put4_8
(
height
,
dest
,
ref
,
stride
,
CPU_3DNOW
);
}
MPEG2_MC_EXTERN
(
3
dnow
)
modules/codec/xvmc/mpeg2.h
deleted
100644 → 0
View file @
a2180073
/* $Id$
* mpeg2.h
* 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.
* 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 MPEG2_H
#define MPEG2_H
#define MPEG2_VERSION(a,b,c) (((a)<<16)|((b)<<8)|(c))
#define MPEG2_RELEASE MPEG2_VERSION (0, 4, 0)
/* 0.4.0 */
#define SEQ_FLAG_MPEG2 1
#define SEQ_FLAG_CONSTRAINED_PARAMETERS 2
#define SEQ_FLAG_PROGRESSIVE_SEQUENCE 4
#define SEQ_FLAG_LOW_DELAY 8
#define SEQ_FLAG_COLOUR_DESCRIPTION 16
#define SEQ_MASK_VIDEO_FORMAT 0xe0
#define SEQ_VIDEO_FORMAT_COMPONENT 0
#define SEQ_VIDEO_FORMAT_PAL 0x20
#define SEQ_VIDEO_FORMAT_NTSC 0x40
#define SEQ_VIDEO_FORMAT_SECAM 0x60
#define SEQ_VIDEO_FORMAT_MAC 0x80
#define SEQ_VIDEO_FORMAT_UNSPECIFIED 0xa0
typedef
struct
mpeg2_sequence_s
{
unsigned
int
width
,
height
;
unsigned
int
chroma_width
,
chroma_height
;
unsigned
int
byte_rate
;
unsigned
int
vbv_buffer_size
;
uint32_t
flags
;
unsigned
int
picture_width
,
picture_height
;
unsigned
int
display_width
,
display_height
;
unsigned
int
pixel_width
,
pixel_height
;
unsigned
int
frame_period
;
uint8_t
profile_level_id
;
uint8_t
colour_primaries
;
uint8_t
transfer_characteristics
;
uint8_t
matrix_coefficients
;
int
aspect_ratio_information
;
}
mpeg2_sequence_t
;
#define GOP_FLAG_DROP_FRAME 1
#define GOP_FLAG_BROKEN_LINK 2
#define GOP_FLAG_CLOSED_GOP 4
typedef
struct
mpeg2_gop_s
{
uint8_t
hours
;
uint8_t
minutes
;
uint8_t
seconds
;
uint8_t
pictures
;
uint32_t
flags
;
}
mpeg2_gop_t
;
#define PIC_MASK_CODING_TYPE 7
#define PIC_FLAG_CODING_TYPE_I 1
#define PIC_FLAG_CODING_TYPE_P 2
#define PIC_FLAG_CODING_TYPE_B 3
#define PIC_FLAG_CODING_TYPE_D 4
#define PIC_FLAG_TOP_FIELD_FIRST 8
#define PIC_FLAG_PROGRESSIVE_FRAME 16
#define PIC_FLAG_COMPOSITE_DISPLAY 32
#define PIC_FLAG_SKIP 64
#define PIC_FLAG_TAGS 128
#define PIC_MASK_COMPOSITE_DISPLAY 0xfffff000
typedef
struct
mpeg2_picture_s
{
unsigned
int
temporal_reference
;
unsigned
int
nb_fields
;
uint32_t
tag
,
tag2
;
uint32_t
flags
;
struct
{
int
x
,
y
;
}
display_offset
[
3
];
}
mpeg2_picture_t
;
typedef
struct
mpeg2_fbuf_s
{
uint8_t
*
buf
[
3
];
void
*
id
;
}
mpeg2_fbuf_t
;
typedef
struct
mpeg2_info_s
{
const
mpeg2_sequence_t
*
sequence
;
const
mpeg2_gop_t
*
gop
;
const
mpeg2_picture_t
*
current_picture
;
const
mpeg2_picture_t
*
current_picture_2nd
;
const
mpeg2_fbuf_t
*
current_fbuf
;
const
mpeg2_picture_t
*
display_picture
;
const
mpeg2_picture_t
*
display_picture_2nd
;
const
mpeg2_fbuf_t
*
display_fbuf
;
const
mpeg2_fbuf_t
*
discard_fbuf
;
const
uint8_t
*
user_data
;
unsigned
int
user_data_len
;
}
mpeg2_info_t
;
typedef
struct
mpeg2dec_s
mpeg2dec_t
;
typedef
struct
mpeg2_decoder_s
mpeg2_decoder_t
;
typedef
enum
{
STATE_BUFFER
=
0
,
STATE_SEQUENCE
=
1
,
STATE_SEQUENCE_REPEATED
=
2
,
STATE_GOP
=
3
,
STATE_PICTURE
=
4
,
STATE_SLICE_1ST
=
5
,
STATE_PICTURE_2ND
=
6
,
STATE_SLICE
=
7
,
STATE_END
=
8
,
STATE_INVALID
=
9
,
STATE_INVALID_END
=
10
}
mpeg2_state_t
;
typedef
struct
mpeg2_convert_init_s
{
unsigned
int
id_size
;
unsigned
int
buf_size
[
3
];
void
(
*
start
)
(
void
*
id
,
const
mpeg2_fbuf_t
*
fbuf
,
const
mpeg2_picture_t
*
picture
,
const
mpeg2_gop_t
*
gop
);
void
(
*
copy
)
(
void
*
id
,
uint8_t
*
const
*
src
,
unsigned
int
v_offset
);
}
mpeg2_convert_init_t
;
typedef
enum
{
MPEG2_CONVERT_SET
=
0
,
MPEG2_CONVERT_STRIDE
=
1
,
MPEG2_CONVERT_START
=
2
}
mpeg2_convert_stage_t
;
typedef
int
mpeg2_convert_t
(
int
stage
,
void
*
id
,
const
mpeg2_sequence_t
*
sequence
,
int
stride
,
uint32_t
accel
,
void
*
arg
,
mpeg2_convert_init_t
*
result
);
int
mpeg2_convert
(
mpeg2dec_t
*
mpeg2dec
,
mpeg2_convert_t
convert
,
void
*
arg
);
int
mpeg2_stride
(
mpeg2dec_t
*
mpeg2dec
,
int
stride
);
void
mpeg2_set_buf
(
mpeg2dec_t
*
mpeg2dec
,
uint8_t
*
buf
[
3
],
void
*
id
);
void
mpeg2_custom_fbuf
(
mpeg2dec_t
*
mpeg2dec
,
int
custom_fbuf
);
#define MPEG2_ACCEL_X86_MMX 1
#define MPEG2_ACCEL_X86_3DNOW 2
#define MPEG2_ACCEL_X86_MMXEXT 4
#define MPEG2_ACCEL_PPC_ALTIVEC 1
#define MPEG2_ACCEL_ALPHA 1
#define MPEG2_ACCEL_ALPHA_MVI 2
#define MPEG2_ACCEL_SPARC_VIS 1
#define MPEG2_ACCEL_SPARC_VIS2 2
#define MPEG2_ACCEL_DETECT 0x80000000
uint32_t
mpeg2_accel
(
uint32_t
accel
);
mpeg2dec_t
*
mpeg2_init
(
void
);
const
mpeg2_info_t
*
mpeg2_info
(
mpeg2dec_t
*
mpeg2dec
);
void
mpeg2_close
(
mpeg2dec_t
*
mpeg2dec
);
void
mpeg2_buffer
(
mpeg2dec_t
*
mpeg2dec
,
uint8_t
*
start
,
uint8_t
*
end
);
int
mpeg2_getpos
(
mpeg2dec_t
*
mpeg2dec
);
mpeg2_state_t
mpeg2_parse
(
mpeg2dec_t
*
mpeg2dec
);
void
mpeg2_reset
(
mpeg2dec_t
*
mpeg2dec
,
int
full_reset
);
void
mpeg2_skip
(
mpeg2dec_t
*
mpeg2dec
,
int
skip
);
void
mpeg2_slice_region
(
mpeg2dec_t
*
mpeg2dec
,
int
start
,
int
end
);
void
mpeg2_tag_picture
(
mpeg2dec_t
*
mpeg2dec
,
uint32_t
tag
,
uint32_t
tag2
);
void
mpeg2_init_fbuf
(
mpeg2_decoder_t
*
decoder
,
uint8_t
*
current_fbuf
[
3
],
uint8_t
*
forward_fbuf
[
3
],
uint8_t
*
backward_fbuf
[
3
]);
typedef
enum
{
MPEG2_ALLOC_MPEG2DEC
=
0
,
MPEG2_ALLOC_CHUNK
=
1
,
MPEG2_ALLOC_YUV
=
2
,
MPEG2_ALLOC_CONVERT_ID
=
3
,
MPEG2_ALLOC_CONVERTED
=
4
}
mpeg2_alloc_t
;
void
*
mpeg2_malloc
(
unsigned
size
,
mpeg2_alloc_t
reason
);
void
mpeg2_free
(
void
*
buf
);
void
mpeg2_malloc_hooks
(
void
*
malloc
(
unsigned
,
mpeg2_alloc_t
),
int
free
(
void
*
));
#endif
/* MPEG2_H */
modules/codec/xvmc/slice.c
deleted
100644 → 0
View file @
a2180073
/* $Id$
* slice.c
* Copyright (C) 2000-2003 Michel Lespinasse <walken@zoy.org>
* Copyright (C) 2003 Peter Gubanov <peter@elecard.net.ru>
* 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
*/
#include "xxmc-config.h"
#include <inttypes.h>
#include "mpeg2.h"
#include "attributes.h"
#include "mpeg2_internal.h"
extern
mpeg2_mc_t
mpeg2_mc
;
extern
void
(
*
mpeg2_cpu_state_save
)
(
cpu_state_t
*
state
);
extern
void
(
*
mpeg2_cpu_state_restore
)
(
cpu_state_t
*
state
);
#include "vlc.h"
static
inline
int
get_motion_delta
(
mpeg2_decoder_t
*
const
decoder
,
const
int
f_code
)
{
#define bit_buf (decoder->bitstream_buf)
#define bits (decoder->bitstream_bits)
#define bit_ptr (decoder->bitstream_ptr)
int
delta
;
int
sign
;
const
MVtab
*
tab
;
if
(
bit_buf
&
0x80000000
)
{
DUMPBITS
(
bit_buf
,
bits
,
1
);
return
0
;
}
else
if
(
bit_buf
>=
0x0c000000
)
{
tab
=
MV_4
+
UBITS
(
bit_buf
,
4
);
delta
=
(
tab
->
delta
<<
f_code
)
+
1
;
bits
+=
tab
->
len
+
f_code
+
1
;
bit_buf
<<=
tab
->
len
;
sign
=
SBITS
(
bit_buf
,
1
);
bit_buf
<<=
1
;
if
(
f_code
)
delta
+=
UBITS
(
bit_buf
,
f_code
);
bit_buf
<<=
f_code
;
return
(
delta
^
sign
)
-
sign
;
}
else
{
tab
=
MV_10
+
UBITS
(
bit_buf
,
10
);
delta
=
(
tab
->
delta
<<
f_code
)
+
1
;
bits
+=
tab
->
len
+
1
;
bit_buf
<<=
tab
->
len
;
sign
=
SBITS
(
bit_buf
,
1
);
bit_buf
<<=
1
;
if
(
f_code
)
{
NEEDBITS
(
bit_buf
,
bits
,
bit_ptr
);
delta
+=
UBITS
(
bit_buf
,
f_code
);
DUMPBITS
(
bit_buf
,
bits
,
f_code
);
}
return
(
delta
^
sign
)
-
sign
;
}
#undef bit_buf
#undef bits
#undef bit_ptr
}
static
inline
int
bound_motion_vector
(
const
int
vector
,
const
int
f_code
)
{
return
((
int32_t
)
vector
<<
(
27
-
f_code
))
>>
(
27
-
f_code
);
}
static
inline
int
get_dmv
(
mpeg2_decoder_t
*
const
decoder
)
{
#define bit_buf (decoder->bitstream_buf)
#define bits (decoder->bitstream_bits)
#define bit_ptr (decoder->bitstream_ptr)
const
DMVtab
*
tab
;
tab
=
DMV_2
+
UBITS
(
bit_buf
,
2
);
DUMPBITS
(
bit_buf
,
bits
,
tab
->
len
);
return
tab
->
dmv
;
#undef bit_buf
#undef bits
#undef bit_ptr
}
#define MOTION_420(table,ref,motion_x,motion_y,size,y) \
pos_x = 2 * decoder->offset + motion_x; \
pos_y = 2 * decoder->v_offset + motion_y + 2 * y; \
if (unlikely (pos_x > decoder->limit_x)) { \
pos_x = ((int)pos_x < 0) ? 0 : decoder->limit_x; \
motion_x = pos_x - 2 * decoder->offset; \
} \
if (unlikely (pos_y > decoder->limit_y_ ## size)) { \
pos_y = ((int)pos_y < 0) ? 0 : decoder->limit_y_ ## size; \
motion_y = pos_y - 2 * decoder->v_offset - 2 * y; \
} \
xy_half = ((pos_y & 1) << 1) | (pos_x & 1); \
table[xy_half] (decoder->dest[0] + y * decoder->stride + decoder->offset, \
ref[0] + (pos_x >> 1) + (pos_y >> 1) * decoder->stride, \
decoder->stride, size); \
motion_x /= 2; motion_y /= 2; \
xy_half = ((motion_y & 1) << 1) | (motion_x & 1); \
offset = (((decoder->offset + motion_x) >> 1) + \
((((decoder->v_offset + motion_y) >> 1) + y/2) * \
decoder->uv_stride)); \
table[4+xy_half] (decoder->dest[1] + y/2 * decoder->uv_stride + \
(decoder->offset >> 1), ref[1] + offset, \
decoder->uv_stride, size/2); \
table[4+xy_half] (decoder->dest[2] + y/2 * decoder->uv_stride + \
(decoder->offset >> 1), ref[2] + offset, \
decoder->uv_stride, size/2)
#define MOTION_FIELD_420(table,ref,motion_x,motion_y,dest_field,op,src_field) \
pos_x = 2 * decoder->offset + motion_x; \
pos_y = decoder->v_offset + motion_y; \
if (unlikely (pos_x > decoder->limit_x)) { \
pos_x = ((int)pos_x < 0) ? 0 : decoder->limit_x; \
motion_x = pos_x - 2 * decoder->offset; \
} \
if (unlikely (pos_y > decoder->limit_y)) { \
pos_y = ((int)pos_y < 0) ? 0 : decoder->limit_y; \
motion_y = pos_y - decoder->v_offset; \
} \
xy_half = ((pos_y & 1) << 1) | (pos_x & 1); \
table[xy_half] (decoder->dest[0] + dest_field * decoder->stride + \
decoder->offset, \
(ref[0] + (pos_x >> 1) + \
((pos_y op) + src_field) * decoder->stride), \
2 * decoder->stride, 8); \
motion_x /= 2; motion_y /= 2; \
xy_half = ((motion_y & 1) << 1) | (motion_x & 1); \
offset = (((decoder->offset + motion_x) >> 1) + \
(((decoder->v_offset >> 1) + (motion_y op) + src_field) * \
decoder->uv_stride)); \
table[4+xy_half] (decoder->dest[1] + dest_field * decoder->uv_stride + \
(decoder->offset >> 1), ref[1] + offset, \
2 * decoder->uv_stride, 4); \
table[4+xy_half] (decoder->dest[2] + dest_field * decoder->uv_stride + \
(decoder->offset >> 1), ref[2] + offset, \
2 * decoder->uv_stride, 4)
#define MOTION_DMV_420(table,ref,motion_x,motion_y) \
pos_x = 2 * decoder->offset + motion_x; \
pos_y = decoder->v_offset + motion_y; \
if (unlikely (pos_x > decoder->limit_x)) { \
pos_x = ((int)pos_x < 0) ? 0 : decoder->limit_x; \
motion_x = pos_x - 2 * decoder->offset; \
} \
if (unlikely (pos_y > decoder->limit_y)) { \
pos_y = ((int)pos_y < 0) ? 0 : decoder->limit_y; \
motion_y = pos_y - decoder->v_offset; \
} \
xy_half = ((pos_y & 1) << 1) | (pos_x & 1); \
offset = (pos_x >> 1) + (pos_y & ~1) * decoder->stride; \
table[xy_half] (decoder->dest[0] + decoder->offset, \
ref[0] + offset, 2 * decoder->stride, 8); \
table[xy_half] (decoder->dest[0] + decoder->stride + decoder->offset, \
ref[0] + decoder->stride + offset, \
2 * decoder->stride, 8); \
motion_x /= 2; motion_y /= 2; \
xy_half = ((motion_y & 1) << 1) | (motion_x & 1); \
offset = (((decoder->offset + motion_x) >> 1) + \
(((decoder->v_offset >> 1) + (motion_y & ~1)) * \
decoder->uv_stride)); \
table[4+xy_half] (decoder->dest[1] + (decoder->offset >> 1), \
ref[1] + offset, 2 * decoder->uv_stride, 4); \
table[4+xy_half] (decoder->dest[1] + decoder->uv_stride + \
(decoder->offset >> 1), \
ref[1] + decoder->uv_stride + offset, \
2 * decoder->uv_stride, 4); \
table[4+xy_half] (decoder->dest[2] + (decoder->offset >> 1), \
ref[2] + offset, 2 * decoder->uv_stride, 4); \
table[4+xy_half] (decoder->dest[2] + decoder->uv_stride + \
(decoder->offset >> 1), \
ref[2] + decoder->uv_stride + offset, \
2 * decoder->uv_stride, 4)
#define MOTION_ZERO_420(table,ref) \
table[0] (decoder->dest[0] + decoder->offset, \
(ref[0] + decoder->offset + \
decoder->v_offset * decoder->stride), decoder->stride, 16); \
offset = ((decoder->offset >> 1) + \
(decoder->v_offset >> 1) * decoder->uv_stride); \
table[4] (decoder->dest[1] + (decoder->offset >> 1), \
ref[1] + offset, decoder->uv_stride, 8); \
table[4] (decoder->dest[2] + (decoder->offset >> 1), \
ref[2] + offset, decoder->uv_stride, 8)
#define MOTION_422(table,ref,motion_x,motion_y,size,y) \
pos_x = 2 * decoder->offset + motion_x; \
pos_y = 2 * decoder->v_offset + motion_y + 2 * y; \
if (unlikely (pos_x > decoder->limit_x)) { \
pos_x = ((int)pos_x < 0) ? 0 : decoder->limit_x; \
motion_x = pos_x - 2 * decoder->offset; \
} \
if (unlikely (pos_y > decoder->limit_y_ ## size)) { \
pos_y = ((int)pos_y < 0) ? 0 : decoder->limit_y_ ## size; \
motion_y = pos_y - 2 * decoder->v_offset - 2 * y; \
} \
xy_half = ((pos_y & 1) << 1) | (pos_x & 1); \
offset = (pos_x >> 1) + (pos_y >> 1) * decoder->stride; \
table[xy_half] (decoder->dest[0] + y * decoder->stride + decoder->offset, \
ref[0] + offset, decoder->stride, size); \
offset = (offset + (motion_x & (motion_x < 0))) >> 1; \
motion_x /= 2; \
xy_half = ((pos_y & 1) << 1) | (motion_x & 1); \
table[4+xy_half] (decoder->dest[1] + y * decoder->uv_stride + \
(decoder->offset >> 1), ref[1] + offset, \
decoder->uv_stride, size); \
table[4+xy_half] (decoder->dest[2] + y * decoder->uv_stride + \
(decoder->offset >> 1), ref[2] + offset, \
decoder->uv_stride, size)
#define MOTION_FIELD_422(table,ref,motion_x,motion_y,dest_field,op,src_field) \
pos_x = 2 * decoder->offset + motion_x; \
pos_y = decoder->v_offset + motion_y; \
if (unlikely (pos_x > decoder->limit_x)) { \
pos_x = ((int)pos_x < 0) ? 0 : decoder->limit_x; \
motion_x = pos_x - 2 * decoder->offset; \
} \
if (unlikely (pos_y > decoder->limit_y)) { \
pos_y = ((int)pos_y < 0) ? 0 : decoder->limit_y; \
motion_y = pos_y - decoder->v_offset; \
} \
xy_half = ((pos_y & 1) << 1) | (pos_x & 1); \
offset = (pos_x >> 1) + ((pos_y op) + src_field) * decoder->stride; \
table[xy_half] (decoder->dest[0] + dest_field * decoder->stride + \
decoder->offset, ref[0] + offset, \
2 * decoder->stride, 8); \
offset = (offset + (motion_x & (motion_x < 0))) >> 1; \
motion_x /= 2; \
xy_half = ((pos_y & 1) << 1) | (motion_x & 1); \
table[4+xy_half] (decoder->dest[1] + dest_field * decoder->uv_stride + \
(decoder->offset >> 1), ref[1] + offset, \
2 * decoder->uv_stride, 8); \
table[4+xy_half] (decoder->dest[2] + dest_field * decoder->uv_stride + \
(decoder->offset >> 1), ref[2] + offset, \
2 * decoder->uv_stride, 8)
#define MOTION_DMV_422(table,ref,motion_x,motion_y) \
pos_x = 2 * decoder->offset + motion_x; \
pos_y = decoder->v_offset + motion_y; \
if (unlikely (pos_x > decoder->limit_x)) { \
pos_x = ((int)pos_x < 0) ? 0 : decoder->limit_x; \
motion_x = pos_x - 2 * decoder->offset; \
} \
if (unlikely (pos_y > decoder->limit_y)) { \
pos_y = ((int)pos_y < 0) ? 0 : decoder->limit_y; \
motion_y = pos_y - decoder->v_offset; \
} \
xy_half = ((pos_y & 1) << 1) | (pos_x & 1); \
offset = (pos_x >> 1) + (pos_y & ~1) * decoder->stride; \
table[xy_half] (decoder->dest[0] + decoder->offset, \
ref[0] + offset, 2 * decoder->stride, 8); \
table[xy_half] (decoder->dest[0] + decoder->stride + decoder->offset, \
ref[0] + decoder->stride + offset, \
2 * decoder->stride, 8); \
offset = (offset + (motion_x & (motion_x < 0))) >> 1; \
motion_x /= 2; \
xy_half = ((pos_y & 1) << 1) | (motion_x & 1); \
table[4+xy_half] (decoder->dest[1] + (decoder->offset >> 1), \
ref[1] + offset, 2 * decoder->uv_stride, 8); \
table[4+xy_half] (decoder->dest[1] + decoder->uv_stride + \
(decoder->offset >> 1), \
ref[1] + decoder->uv_stride + offset, \
2 * decoder->uv_stride, 8); \
table[4+xy_half] (decoder->dest[2] + (decoder->offset >> 1), \
ref[2] + offset, 2 * decoder->uv_stride, 8); \
table[4+xy_half] (decoder->dest[2] + decoder->uv_stride + \
(decoder->offset >> 1), \
ref[2] + decoder->uv_stride + offset, \
2 * decoder->uv_stride, 8)
#define MOTION_ZERO_422(table,ref) \
offset = decoder->offset + decoder->v_offset * decoder->stride; \
table[0] (decoder->dest[0] + decoder->offset, \
ref[0] + offset, decoder->stride, 16); \
offset >>= 1; \
table[4] (decoder->dest[1] + (decoder->offset >> 1), \
ref[1] + offset, decoder->uv_stride, 16); \
table[4] (decoder->dest[2] + (decoder->offset >> 1), \
ref[2] + offset, decoder->uv_stride, 16)
#define MOTION_444(table,ref,motion_x,motion_y,size,y) \
pos_x = 2 * decoder->offset + motion_x; \
pos_y = 2 * decoder->v_offset + motion_y + 2 * y; \
if (unlikely (pos_x > decoder->limit_x)) { \
pos_x = ((int)pos_x < 0) ? 0 : decoder->limit_x; \
motion_x = pos_x - 2 * decoder->offset; \
} \
if (unlikely (pos_y > decoder->limit_y_ ## size)) { \
pos_y = ((int)pos_y < 0) ? 0 : decoder->limit_y_ ## size; \
motion_y = pos_y - 2 * decoder->v_offset - 2 * y; \
} \
xy_half = ((pos_y & 1) << 1) | (pos_x & 1); \
offset = (pos_x >> 1) + (pos_y >> 1) * decoder->stride; \
table[xy_half] (decoder->dest[0] + y * decoder->stride + decoder->offset, \
ref[0] + offset, decoder->stride, size); \
table[xy_half] (decoder->dest[1] + y * decoder->stride + decoder->offset, \
ref[1] + offset, decoder->stride, size); \
table[xy_half] (decoder->dest[2] + y * decoder->stride + decoder->offset, \
ref[2] + offset, decoder->stride, size)
#define MOTION_FIELD_444(table,ref,motion_x,motion_y,dest_field,op,src_field) \
pos_x = 2 * decoder->offset + motion_x; \
pos_y = decoder->v_offset + motion_y; \
if (unlikely (pos_x > decoder->limit_x)) { \
pos_x = ((int)pos_x < 0) ? 0 : decoder->limit_x; \
motion_x = pos_x - 2 * decoder->offset; \
} \
if (unlikely (pos_y > decoder->limit_y)) { \
pos_y = ((int)pos_y < 0) ? 0 : decoder->limit_y; \
motion_y = pos_y - decoder->v_offset; \
} \
xy_half = ((pos_y & 1) << 1) | (pos_x & 1); \
offset = (pos_x >> 1) + ((pos_y op) + src_field) * decoder->stride; \
table[xy_half] (decoder->dest[0] + dest_field * decoder->stride + \
decoder->offset, ref[0] + offset, \
2 * decoder->stride, 8); \
table[xy_half] (decoder->dest[1] + dest_field * decoder->stride + \
decoder->offset, ref[1] + offset, \
2 * decoder->stride, 8); \
table[xy_half] (decoder->dest[2] + dest_field * decoder->stride + \
decoder->offset, ref[2] + offset, \
2 * decoder->stride, 8)
#define MOTION_DMV_444(table,ref,motion_x,motion_y) \
pos_x = 2 * decoder->offset + motion_x; \
pos_y = decoder->v_offset + motion_y; \
if (unlikely (pos_x > decoder->limit_x)) { \
pos_x = ((int)pos_x < 0) ? 0 : decoder->limit_x; \
motion_x = pos_x - 2 * decoder->offset; \
} \
if (unlikely (pos_y > decoder->limit_y)) { \
pos_y = ((int)pos_y < 0) ? 0 : decoder->limit_y; \
motion_y = pos_y - decoder->v_offset; \
} \
xy_half = ((pos_y & 1) << 1) | (pos_x & 1); \
offset = (pos_x >> 1) + (pos_y & ~1) * decoder->stride; \
table[xy_half] (decoder->dest[0] + decoder->offset, \
ref[0] + offset, 2 * decoder->stride, 8); \
table[xy_half] (decoder->dest[0] + decoder->stride + decoder->offset, \
ref[0] + decoder->stride + offset, \
2 * decoder->stride, 8); \
table[xy_half] (decoder->dest[1] + decoder->offset, \
ref[1] + offset, 2 * decoder->stride, 8); \
table[xy_half] (decoder->dest[1] + decoder->stride + decoder->offset, \
ref[1] + decoder->stride + offset, \
2 * decoder->stride, 8); \
table[xy_half] (decoder->dest[2] + decoder->offset, \
ref[2] + offset, 2 * decoder->stride, 8); \
table[xy_half] (decoder->dest[2] + decoder->stride + decoder->offset, \
ref[2] + decoder->stride + offset, \
2 * decoder->stride, 8)
#define MOTION_ZERO_444(table,ref) \
offset = decoder->offset + decoder->v_offset * decoder->stride; \
table[0] (decoder->dest[0] + decoder->offset, \
ref[0] + offset, decoder->stride, 16); \
table[4] (decoder->dest[1] + decoder->offset, \
ref[1] + offset, decoder->stride, 16); \
table[4] (decoder->dest[2] + (decoder->offset >> 1), \
ref[2] + offset, decoder->stride, 16)
#define bit_buf (decoder->bitstream_buf)
#define bits (decoder->bitstream_bits)
#define bit_ptr (decoder->bitstream_ptr)
static
void
motion_mp1
(
mpeg2_decoder_t
*
const
decoder
,
motion_t
*
const
motion
,
mpeg2_mc_fct
*
const
*
const
table
)
{
int
motion_x
,
motion_y
;
unsigned
int
pos_x
,
pos_y
,
xy_half
,
offset
;
NEEDBITS
(
bit_buf
,
bits
,
bit_ptr
);
motion_x
=
(
motion
->
pmv
[
0
][
0
]
+
(
get_motion_delta
(
decoder
,
motion
->
f_code
[
0
]
)
<<
motion
->
f_code
[
1
]));
motion_x
=
bound_motion_vector
(
motion_x
,
motion
->
f_code
[
0
]
+
motion
->
f_code
[
1
]);
motion
->
pmv
[
0
][
0
]
=
motion_x
;
NEEDBITS
(
bit_buf
,
bits
,
bit_ptr
);
motion_y
=
(
motion
->
pmv
[
0
][
1
]
+
(
get_motion_delta
(
decoder
,
motion
->
f_code
[
0
])
<<
motion
->
f_code
[
1
]));
motion_y
=
bound_motion_vector
(
motion_y
,
motion
->
f_code
[
0
]
+
motion
->
f_code
[
1
]);
motion
->
pmv
[
0
][
1
]
=
motion_y
;
MOTION_420
(
table
,
motion
->
ref
[
0
],
motion_x
,
motion_y
,
16
,
0
);
}
#define MOTION_FUNCTIONS(FORMAT,MOTION,MOTION_FIELD,MOTION_DMV,MOTION_ZERO) \
\
static void motion_fr_frame_##FORMAT (mpeg2_decoder_t * const decoder, \
motion_t * const motion, \
mpeg2_mc_fct * const * const table) \
{ \
int motion_x, motion_y; \
unsigned int pos_x, pos_y, xy_half, offset; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
motion_x = motion->pmv[0][0] + get_motion_delta (decoder, \
motion->f_code[0]); \
motion_x = bound_motion_vector (motion_x, motion->f_code[0]); \
motion->pmv[1][0] = motion->pmv[0][0] = motion_x; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
motion_y = motion->pmv[0][1] + get_motion_delta (decoder, \
motion->f_code[1]); \
motion_y = bound_motion_vector (motion_y, motion->f_code[1]); \
motion->pmv[1][1] = motion->pmv[0][1] = motion_y; \
\
MOTION (table, motion->ref[0], motion_x, motion_y, 16, 0); \
} \
\
static void motion_fr_field_##FORMAT (mpeg2_decoder_t * const decoder, \
motion_t * const motion, \
mpeg2_mc_fct * const * const table) \
{ \
int motion_x, motion_y, field; \
unsigned int pos_x, pos_y, xy_half, offset; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
field = UBITS (bit_buf, 1); \
DUMPBITS (bit_buf, bits, 1); \
\
motion_x = motion->pmv[0][0] + get_motion_delta (decoder, \
motion->f_code[0]); \
motion_x = bound_motion_vector (motion_x, motion->f_code[0]); \
motion->pmv[0][0] = motion_x; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
motion_y = ((motion->pmv[0][1] >> 1) + \
get_motion_delta (decoder, motion->f_code[1])); \
/* motion_y = bound_motion_vector (motion_y, motion->f_code[1]); */
\
motion->pmv[0][1] = motion_y << 1; \
\
MOTION_FIELD (table, motion->ref[0], motion_x, motion_y, 0, & ~1, field); \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
field = UBITS (bit_buf, 1); \
DUMPBITS (bit_buf, bits, 1); \
\
motion_x = motion->pmv[1][0] + get_motion_delta (decoder, \
motion->f_code[0]); \
motion_x = bound_motion_vector (motion_x, motion->f_code[0]); \
motion->pmv[1][0] = motion_x; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
motion_y = ((motion->pmv[1][1] >> 1) + \
get_motion_delta (decoder, motion->f_code[1])); \
/* motion_y = bound_motion_vector (motion_y, motion->f_code[1]); */
\
motion->pmv[1][1] = motion_y << 1; \
\
MOTION_FIELD (table, motion->ref[0], motion_x, motion_y, 1, & ~1, field); \
} \
\
static void motion_fr_dmv_##FORMAT (mpeg2_decoder_t * const decoder, \
motion_t * const motion, \
mpeg2_mc_fct * const * const table) \
{ \
int motion_x, motion_y, dmv_x, dmv_y, m, other_x, other_y; \
unsigned int pos_x, pos_y, xy_half, offset; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
motion_x = motion->pmv[0][0] + get_motion_delta (decoder, \
motion->f_code[0]); \
motion_x = bound_motion_vector (motion_x, motion->f_code[0]); \
motion->pmv[1][0] = motion->pmv[0][0] = motion_x; \
NEEDBITS (bit_buf, bits, bit_ptr); \
dmv_x = get_dmv (decoder); \
\
motion_y = ((motion->pmv[0][1] >> 1) + \
get_motion_delta (decoder, motion->f_code[1])); \
/* motion_y = bound_motion_vector (motion_y, motion->f_code[1]); */
\
motion->pmv[1][1] = motion->pmv[0][1] = motion_y << 1; \
dmv_y = get_dmv (decoder); \
\
m = decoder->top_field_first ? 1 : 3; \
other_x = ((motion_x * m + (motion_x > 0)) >> 1) + dmv_x; \
other_y = ((motion_y * m + (motion_y > 0)) >> 1) + dmv_y - 1; \
MOTION_FIELD (mpeg2_mc.put, motion->ref[0], other_x, other_y, 0, | 1, 0); \
\
m = decoder->top_field_first ? 3 : 1; \
other_x = ((motion_x * m + (motion_x > 0)) >> 1) + dmv_x; \
other_y = ((motion_y * m + (motion_y > 0)) >> 1) + dmv_y + 1; \
MOTION_FIELD (mpeg2_mc.put, motion->ref[0], other_x, other_y, 1, & ~1, 0);\
\
MOTION_DMV (mpeg2_mc.avg, motion->ref[0], motion_x, motion_y); \
} \
\
static void motion_reuse_##FORMAT (mpeg2_decoder_t * const decoder, \
motion_t * const motion, \
mpeg2_mc_fct * const * const table) \
{ \
int motion_x, motion_y; \
unsigned int pos_x, pos_y, xy_half, offset; \
\
motion_x = motion->pmv[0][0]; \
motion_y = motion->pmv[0][1]; \
\
MOTION (table, motion->ref[0], motion_x, motion_y, 16, 0); \
} \
\
static void motion_zero_##FORMAT (mpeg2_decoder_t * const decoder, \
motion_t * const motion, \
mpeg2_mc_fct * const * const table) \
{ \
unsigned int offset; \
\
motion->pmv[0][0] = motion->pmv[0][1] = 0; \
motion->pmv[1][0] = motion->pmv[1][1] = 0; \
\
MOTION_ZERO (table, motion->ref[0]); \
} \
\
static void motion_fi_field_##FORMAT (mpeg2_decoder_t * const decoder, \
motion_t * const motion, \
mpeg2_mc_fct * const * const table) \
{ \
int motion_x, motion_y; \
uint8_t ** ref_field; \
unsigned int pos_x, pos_y, xy_half, offset; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
ref_field = motion->ref2[UBITS (bit_buf, 1)]; \
DUMPBITS (bit_buf, bits, 1); \
\
motion_x = motion->pmv[0][0] + get_motion_delta (decoder, \
motion->f_code[0]); \
motion_x = bound_motion_vector (motion_x, motion->f_code[0]); \
motion->pmv[1][0] = motion->pmv[0][0] = motion_x; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
motion_y = motion->pmv[0][1] + get_motion_delta (decoder, \
motion->f_code[1]); \
motion_y = bound_motion_vector (motion_y, motion->f_code[1]); \
motion->pmv[1][1] = motion->pmv[0][1] = motion_y; \
\
MOTION (table, ref_field, motion_x, motion_y, 16, 0); \
} \
\
static void motion_fi_16x8_##FORMAT (mpeg2_decoder_t * const decoder, \
motion_t * const motion, \
mpeg2_mc_fct * const * const table) \
{ \
int motion_x, motion_y; \
uint8_t ** ref_field; \
unsigned int pos_x, pos_y, xy_half, offset; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
ref_field = motion->ref2[UBITS (bit_buf, 1)]; \
DUMPBITS (bit_buf, bits, 1); \
\
motion_x = motion->pmv[0][0] + get_motion_delta (decoder, \
motion->f_code[0]); \
motion_x = bound_motion_vector (motion_x, motion->f_code[0]); \
motion->pmv[0][0] = motion_x; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
motion_y = motion->pmv[0][1] + get_motion_delta (decoder, \
motion->f_code[1]); \
motion_y = bound_motion_vector (motion_y, motion->f_code[1]); \
motion->pmv[0][1] = motion_y; \
\
MOTION (table, ref_field, motion_x, motion_y, 8, 0); \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
ref_field = motion->ref2[UBITS (bit_buf, 1)]; \
DUMPBITS (bit_buf, bits, 1); \
\
motion_x = motion->pmv[1][0] + get_motion_delta (decoder, \
motion->f_code[0]); \
motion_x = bound_motion_vector (motion_x, motion->f_code[0]); \
motion->pmv[1][0] = motion_x; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
motion_y = motion->pmv[1][1] + get_motion_delta (decoder, \
motion->f_code[1]); \
motion_y = bound_motion_vector (motion_y, motion->f_code[1]); \
motion->pmv[1][1] = motion_y; \
\
MOTION (table, ref_field, motion_x, motion_y, 8, 8); \
} \
\
static void motion_fi_dmv_##FORMAT (mpeg2_decoder_t * const decoder, \
motion_t * const motion, \
mpeg2_mc_fct * const * const table) \
{ \
int motion_x, motion_y, other_x, other_y; \
unsigned int pos_x, pos_y, xy_half, offset; \
\
NEEDBITS (bit_buf, bits, bit_ptr); \
motion_x = motion->pmv[0][0] + get_motion_delta (decoder, \
motion->f_code[0]); \
motion_x = bound_motion_vector (motion_x, motion->f_code[0]); \
motion->pmv[1][0] = motion->pmv[0][0] = motion_x; \
NEEDBITS (bit_buf, bits, bit_ptr); \
other_x = ((motion_x + (motion_x > 0)) >> 1) + get_dmv (decoder); \
\
motion_y = motion->pmv[0][1] + get_motion_delta (decoder, \
motion->f_code[1]); \
motion_y = bound_motion_vector (motion_y, motion->f_code[1]); \
motion->pmv[1][1] = motion->pmv[0][1] = motion_y; \
other_y = (((motion_y + (motion_y > 0)) >> 1) + get_dmv (decoder) + \
decoder->dmv_offset); \
\
MOTION (mpeg2_mc.put, motion->ref[0], motion_x, motion_y, 16, 0); \
MOTION (mpeg2_mc.avg, motion->ref[1], other_x, other_y, 16, 0); \
} \
MOTION_FUNCTIONS
(
420
,
MOTION_420
,
MOTION_FIELD_420
,
MOTION_DMV_420
,
MOTION_ZERO_420
)
MOTION_FUNCTIONS
(
422
,
MOTION_422
,
MOTION_FIELD_422
,
MOTION_DMV_422
,
MOTION_ZERO_422
)
MOTION_FUNCTIONS
(
444
,
MOTION_444
,
MOTION_FIELD_444
,
MOTION_DMV_444
,
MOTION_ZERO_444
)
/* like motion_frame, but parsing without actual motion compensation */
static
void
motion_fr_conceal
(
mpeg2_decoder_t
*
const
decoder
)
{
int
tmp
;
NEEDBITS
(
bit_buf
,
bits
,
bit_ptr
);
tmp
=
(
decoder
->
f_motion
.
pmv
[
0
][
0
]
+
get_motion_delta
(
decoder
,
decoder
->
f_motion
.
f_code
[
0
]));
tmp
=
bound_motion_vector
(
tmp
,
decoder
->
f_motion
.
f_code
[
0
]);
decoder
->
f_motion
.
pmv
[
1
][
0
]
=
decoder
->
f_motion
.
pmv
[
0
][
0
]
=
tmp
;
NEEDBITS
(
bit_buf
,
bits
,
bit_ptr
);
tmp
=
(
decoder
->
f_motion
.
pmv
[
0
][
1
]
+
get_motion_delta
(
decoder
,
decoder
->
f_motion
.
f_code
[
1
]));
tmp
=
bound_motion_vector
(
tmp
,
decoder
->
f_motion
.
f_code
[
1
]);
decoder
->
f_motion
.
pmv
[
1
][
1
]
=
decoder
->
f_motion
.
pmv
[
0
][
1
]
=
tmp
;
DUMPBITS
(
bit_buf
,
bits
,
1
);
/* remove marker_bit */
}
static
void
motion_fi_conceal
(
mpeg2_decoder_t
*
const
decoder
)
{
int
tmp
;
NEEDBITS
(
bit_buf
,
bits
,
bit_ptr
);
DUMPBITS
(
bit_buf
,
bits
,
1
);
/* remove field_select */
tmp
=
(
decoder
->
f_motion
.
pmv
[
0
][
0
]
+
get_motion_delta
(
decoder
,
decoder
->
f_motion
.
f_code
[
0
]));
tmp
=
bound_motion_vector
(
tmp
,
decoder
->
f_motion
.
f_code
[
0
]);
decoder
->
f_motion
.
pmv
[
1
][
0
]
=
decoder
->
f_motion
.
pmv
[
0
][
0
]
=
tmp
;
NEEDBITS
(
bit_buf
,
bits
,
bit_ptr
);
tmp
=
(
decoder
->
f_motion
.
pmv
[
0
][
1
]
+
get_motion_delta
(
decoder
,
decoder
->
f_motion
.
f_code
[
1
]));
tmp
=
bound_motion_vector
(
tmp
,
decoder
->
f_motion
.
f_code
[
1
]);
decoder
->
f_motion
.
pmv
[
1
][
1
]
=
decoder
->
f_motion
.
pmv
[
0
][
1
]
=
tmp
;
DUMPBITS
(
bit_buf
,
bits
,
1
);
/* remove marker_bit */
}
#undef bit_buf
#undef bits
#undef bit_ptr
#define MOTION_CALL(routine,direction) \
do { \
if ((direction) & MACROBLOCK_MOTION_FORWARD) \
routine (decoder, &(decoder->f_motion), mpeg2_mc.put); \
if ((direction) & MACROBLOCK_MOTION_BACKWARD) \
routine (decoder, &(decoder->b_motion), \
((direction) & MACROBLOCK_MOTION_FORWARD ? \
mpeg2_mc.avg : mpeg2_mc.put)); \
} while (0)
#define NEXT_MACROBLOCK \
do { \
decoder->offset += 16; \
if (decoder->offset == decoder->width) { \
do {
/* just so we can use the break statement */
\
if (decoder->convert) { \
decoder->convert (decoder->convert_id, decoder->dest, \
decoder->v_offset); \
if (decoder->coding_type == B_TYPE) \
break; \
} \
decoder->dest[0] += decoder->slice_stride; \
decoder->dest[1] += decoder->slice_uv_stride; \
decoder->dest[2] += decoder->slice_uv_stride; \
} while (0); \
decoder->v_offset += 16; \
if (decoder->v_offset > decoder->limit_y) { \
if (mpeg2_cpu_state_restore) \
mpeg2_cpu_state_restore (&cpu_state); \
return; \
} \
decoder->offset = 0; \
} \
} while (0)
void
mpeg2_init_fbuf
(
mpeg2_decoder_t
*
decoder
,
uint8_t
*
current_fbuf
[
3
],
uint8_t
*
forward_fbuf
[
3
],
uint8_t
*
backward_fbuf
[
3
])
{
int
offset
,
stride
,
height
,
bottom_field
;
stride
=
decoder
->
stride_frame
;
bottom_field
=
(
decoder
->
picture_structure
==
BOTTOM_FIELD
);
offset
=
bottom_field
?
stride
:
0
;
height
=
decoder
->
height
;
decoder
->
picture_dest
[
0
]
=
current_fbuf
[
0
]
+
offset
;
decoder
->
picture_dest
[
1
]
=
current_fbuf
[
1
]
+
(
offset
>>
1
);
decoder
->
picture_dest
[
2
]
=
current_fbuf
[
2
]
+
(
offset
>>
1
);
decoder
->
f_motion
.
ref
[
0
][
0
]
=
forward_fbuf
[
0
]
+
offset
;
decoder
->
f_motion
.
ref
[
0
][
1
]
=
forward_fbuf
[
1
]
+
(
offset
>>
1
);
decoder
->
f_motion
.
ref
[
0
][
2
]
=
forward_fbuf
[
2
]
+
(
offset
>>
1
);
decoder
->
b_motion
.
ref
[
0
][
0
]
=
backward_fbuf
[
0
]
+
offset
;
decoder
->
b_motion
.
ref
[
0
][
1
]
=
backward_fbuf
[
1
]
+
(
offset
>>
1
);
decoder
->
b_motion
.
ref
[
0
][
2
]
=
backward_fbuf
[
2
]
+
(
offset
>>
1
);
if
(
decoder
->
picture_structure
!=
FRAME_PICTURE
)
{
decoder
->
dmv_offset
=
bottom_field
?
1
:
-
1
;
decoder
->
f_motion
.
ref2
[
0
]
=
decoder
->
f_motion
.
ref
[
bottom_field
];
decoder
->
f_motion
.
ref2
[
1
]
=
decoder
->
f_motion
.
ref
[
!
bottom_field
];
decoder
->
b_motion
.
ref2
[
0
]
=
decoder
->
b_motion
.
ref
[
bottom_field
];
decoder
->
b_motion
.
ref2
[
1
]
=
decoder
->
b_motion
.
ref
[
!
bottom_field
];
offset
=
stride
-
offset
;
if
(
decoder
->
second_field
&&
(
decoder
->
coding_type
!=
B_TYPE
)
)
forward_fbuf
=
current_fbuf
;
decoder
->
f_motion
.
ref
[
1
][
0
]
=
forward_fbuf
[
0
]
+
offset
;
decoder
->
f_motion
.
ref
[
1
][
1
]
=
forward_fbuf
[
1
]
+
(
offset
>>
1
);
decoder
->
f_motion
.
ref
[
1
][
2
]
=
forward_fbuf
[
2
]
+
(
offset
>>
1
);
decoder
->
b_motion
.
ref
[
1
][
0
]
=
backward_fbuf
[
0
]
+
offset
;
decoder
->
b_motion
.
ref
[
1
][
1
]
=
backward_fbuf
[
1
]
+
(
offset
>>
1
);
decoder
->
b_motion
.
ref
[
1
][
2
]
=
backward_fbuf
[
2
]
+
(
offset
>>
1
);
stride
<<=
1
;
height
>>=
1
;
}
decoder
->
stride
=
stride
;
decoder
->
uv_stride
=
stride
>>
1
;
decoder
->
slice_stride
=
16
*
stride
;
decoder
->
slice_uv_stride
=
decoder
->
slice_stride
>>
(
2
-
decoder
->
chroma_format
);
decoder
->
limit_x
=
2
*
decoder
->
width
-
32
;
decoder
->
limit_y_16
=
2
*
height
-
32
;
decoder
->
limit_y_8
=
2
*
height
-
16
;
decoder
->
limit_y
=
height
-
16
;
if
(
decoder
->
mpeg1
)
{
decoder
->
motion_parser
[
0
]
=
motion_zero_420
;
decoder
->
motion_parser
[
MC_FRAME
]
=
motion_mp1
;
decoder
->
motion_parser
[
4
]
=
motion_reuse_420
;
}
else
if
(
decoder
->
picture_structure
==
FRAME_PICTURE
)
{
if
(
decoder
->
chroma_format
==
0
)
{
decoder
->
motion_parser
[
0
]
=
motion_zero_420
;
decoder
->
motion_parser
[
MC_FIELD
]
=
motion_fr_field_420
;
decoder
->
motion_parser
[
MC_FRAME
]
=
motion_fr_frame_420
;
decoder
->
motion_parser
[
MC_DMV
]
=
motion_fr_dmv_420
;
decoder
->
motion_parser
[
4
]
=
motion_reuse_420
;
}
else
if
(
decoder
->
chroma_format
==
1
)
{
decoder
->
motion_parser
[
0
]
=
motion_zero_422
;
decoder
->
motion_parser
[
MC_FIELD
]
=
motion_fr_field_422
;
decoder
->
motion_parser
[
MC_FRAME
]
=
motion_fr_frame_422
;
decoder
->
motion_parser
[
MC_DMV
]
=
motion_fr_dmv_422
;
decoder
->
motion_parser
[
4
]
=
motion_reuse_422
;
}
else
{
decoder
->
motion_parser
[
0
]
=
motion_zero_444
;
decoder
->
motion_parser
[
MC_FIELD
]
=
motion_fr_field_444
;
decoder
->
motion_parser
[
MC_FRAME
]
=
motion_fr_frame_444
;
decoder
->
motion_parser
[
MC_DMV
]
=
motion_fr_dmv_444
;
decoder
->
motion_parser
[
4
]
=
motion_reuse_444
;
}
}
else
{
if
(
decoder
->
chroma_format
==
0
)
{
decoder
->
motion_parser
[
0
]
=
motion_zero_420
;
decoder
->
motion_parser
[
MC_FIELD
]
=
motion_fi_field_420
;
decoder
->
motion_parser
[
MC_16X8
]
=
motion_fi_16x8_420
;
decoder
->
motion_parser
[
MC_DMV
]
=
motion_fi_dmv_420
;
decoder
->
motion_parser
[
4
]
=
motion_reuse_420
;
}
else
if
(
decoder
->
chroma_format
==
1
)
{
decoder
->
motion_parser
[
0
]
=
motion_zero_422
;
decoder
->
motion_parser
[
MC_FIELD
]
=
motion_fi_field_422
;
decoder
->
motion_parser
[
MC_16X8
]
=
motion_fi_16x8_422
;
decoder
->
motion_parser
[
MC_DMV
]
=
motion_fi_dmv_422
;
decoder
->
motion_parser
[
4
]
=
motion_reuse_422
;
}
else
{
decoder
->
motion_parser
[
0
]
=
motion_zero_444
;
decoder
->
motion_parser
[
MC_FIELD
]
=
motion_fi_field_444
;
decoder
->
motion_parser
[
MC_16X8
]
=
motion_fi_16x8_444
;
decoder
->
motion_parser
[
MC_DMV
]
=
motion_fi_dmv_444
;
decoder
->
motion_parser
[
4
]
=
motion_reuse_444
;
}
}
}
modules/codec/xvmc/slice_xvmc_vld.c
deleted
100644 → 0
View file @
a2180073
/* $Id$
* Copyright (c) 2004 The Unichrome project. All rights reserved.
*
* This program 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, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTIES OR REPRESENTATIONS; 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.
*
*
*/
#ifdef HAVE_CONFIG_H
# include "config.h"
#endif
#include <vlc_common.h>
#include <vlc_vout.h>
#include <vlc_codec.h>
#include "mpeg2.h"
#include "mpeg2_internal.h"
#include "xvmc_vld.h"
static
uint8_t
zig_zag_scan
[
64
]
ATTR_ALIGN
(
16
)
=
{
/* Zig-Zag scan pattern */
0
,
1
,
8
,
16
,
9
,
2
,
3
,
10
,
17
,
24
,
32
,
25
,
18
,
11
,
4
,
5
,
12
,
19
,
26
,
33
,
40
,
48
,
41
,
34
,
27
,
20
,
13
,
6
,
7
,
14
,
21
,
28
,
35
,
42
,
49
,
56
,
57
,
50
,
43
,
36
,
29
,
22
,
15
,
23
,
30
,
37
,
44
,
51
,
58
,
59
,
52
,
45
,
38
,
31
,
39
,
46
,
53
,
60
,
61
,
54
,
47
,
55
,
62
,
63
};
static
uint8_t
alternate_scan
[
64
]
ATTR_ALIGN
(
16
)
=
{
/* Alternate scan pattern */
0
,
8
,
16
,
24
,
1
,
9
,
2
,
10
,
17
,
25
,
32
,
40
,
48
,
56
,
57
,
49
,
41
,
33
,
26
,
18
,
3
,
11
,
4
,
12
,
19
,
27
,
34
,
42
,
50
,
58
,
35
,
43
,
51
,
59
,
20
,
28
,
5
,
13
,
6
,
14
,
21
,
29
,
36
,
44
,
52
,
60
,
37
,
45
,
53
,
61
,
22
,
30
,
7
,
15
,
23
,
31
,
38
,
46
,
54
,
62
,
39
,
47
,
55
,
63
};
void
mpeg2_xxmc_choose_coding
(
decoder_t
*
p_dec
,
mpeg2_decoder_t
*
const
decoder
,
picture_t
*
picture
,
double
aspect_ratio
,
int
flags
)
{
if
(
picture
)
{
//vlc_fourcc_t decoder_format = picture->format.i_chroma;
//if (decoder_format == VLC_FOURCC('X','x','M','C')) {
vlc_xxmc_t
*
xxmc
=
(
vlc_xxmc_t
*
)
picture
->
p_data
;
/*
* Make a request for acceleration type and mpeg coding from
* the output plugin.
*/
xxmc
->
fallback_format
=
VLC_FOURCC
(
'Y'
,
'V'
,
'1'
,
'2'
);
xxmc
->
acceleration
=
VLC_XVMC_ACCEL_VLD
;
//| VLC_XVMC_ACCEL_IDCT| VLC_XVMC_ACCEL_MOCOMP ;
//msg_Dbg(p_dec, "mpeg2_xxmc_choose_coding 2");
/*
* Standard MOCOMP / IDCT XvMC implementation for interlaced streams
* is buggy. The bug is inherited from the old XvMC driver. Don't use it until
* it has been fixed. (A volunteer ?)
*/
//if ( decoder->picture_structure != 3 ) {
//xxmc->acceleration &= ~( VLC_XVMC_ACCEL_IDCT | VLC_XVMC_ACCEL_MOCOMP );
//}
xxmc
->
mpeg
=
(
decoder
->
mpeg1
)
?
VLC_XVMC_MPEG_1
:
VLC_XVMC_MPEG_2
;
xxmc
->
proc_xxmc_update_frame
(
picture
,
decoder
->
width
,
decoder
->
height
,
aspect_ratio
,
VLC_IMGFMT_XXMC
,
flags
);
//}
}
}
void
mpeg2_xxmc_slice
(
mpeg2dec_t
*
mpeg2dec
,
picture_t
*
picture
,
int
code
,
uint8_t
*
buffer
,
int
size
)
{
mpeg2_decoder_t
*
const
decoder
=
&
(
mpeg2dec
->
decoder
);
picture
=
(
picture_t
*
)
mpeg2dec
->
fbuf
[
0
]
->
id
;
vlc_xxmc_t
*
xxmc
=
(
vlc_xxmc_t
*
)
picture
->
p_data
;
vlc_vld_frame_t
*
vft
=
&
xxmc
->
vld_frame
;
unsigned
mb_frame_height
;
int
i
;
const
uint8_t
*
scan_pattern
;
if
(
1
==
code
)
{
//mpeg2_skip(mpeg2dec, 1);
//frame->bad_frame = 1;
/*
* Check that first field went through OK. Otherwise,
* indicate bad frame.
*/
if
(
decoder
->
second_field
)
{
mpeg2dec
->
xvmc_last_slice_code
=
(
xxmc
->
decoded
)
?
0
:
-
1
;
xxmc
->
decoded
=
0
;
}
else
{
mpeg2dec
->
xvmc_last_slice_code
=
0
;
}
mb_frame_height
=
//(!(decoder->mpeg1) && (decoder->progressive_sequence)) ?
//2*((decoder->height+31) >> 5) :
(
decoder
->
height
+
15
)
>>
4
;
mpeg2dec
->
xxmc_mb_pic_height
=
(
decoder
->
picture_structure
==
FRAME_PICTURE
)
?
mb_frame_height
:
mb_frame_height
>>
1
;
if
(
decoder
->
mpeg1
)
{
vft
->
mv_ranges
[
0
][
0
]
=
decoder
->
b_motion
.
f_code
[
0
];
vft
->
mv_ranges
[
0
][
1
]
=
decoder
->
b_motion
.
f_code
[
0
];
vft
->
mv_ranges
[
1
][
0
]
=
decoder
->
f_motion
.
f_code
[
0
];
vft
->
mv_ranges
[
1
][
1
]
=
decoder
->
f_motion
.
f_code
[
0
];
}
else
{
vft
->
mv_ranges
[
0
][
0
]
=
decoder
->
b_motion
.
f_code
[
0
];
vft
->
mv_ranges
[
0
][
1
]
=
decoder
->
b_motion
.
f_code
[
1
];
vft
->
mv_ranges
[
1
][
0
]
=
decoder
->
f_motion
.
f_code
[
0
];
vft
->
mv_ranges
[
1
][
1
]
=
decoder
->
f_motion
.
f_code
[
1
];
}
vft
->
picture_structure
=
decoder
->
picture_structure
;
vft
->
picture_coding_type
=
decoder
->
coding_type
;
vft
->
mpeg_coding
=
(
decoder
->
mpeg1
)
?
0
:
1
;
vft
->
progressive_sequence
=
decoder
->
progressive_sequence
;
vft
->
scan
=
(
decoder
->
scan
==
mpeg2_scan_alt
);
vft
->
pred_dct_frame
=
decoder
->
frame_pred_frame_dct
;
vft
->
concealment_motion_vectors
=
decoder
->
concealment_motion_vectors
;
vft
->
q_scale_type
=
decoder
->
q_scale_type
;
vft
->
intra_vlc_format
=
decoder
->
intra_vlc_format
;
vft
->
intra_dc_precision
=
7
-
decoder
->
intra_dc_precision
;
vft
->
second_field
=
decoder
->
second_field
;
/*
* Translation of libmpeg2's Q-matrix layout to VLD XvMC's.
* Errors here will give
* blocky artifacts and sometimes wrong colors.
*/
scan_pattern
=
(
vft
->
scan
)
?
alternate_scan
:
zig_zag_scan
;
if
(
(
vft
->
load_intra_quantizer_matrix
=
decoder
->
load_intra_quantizer_matrix
)
)
{
for
(
i
=
0
;
i
<
64
;
++
i
)
{
vft
->
intra_quantizer_matrix
[
scan_pattern
[
i
]]
=
mpeg2dec
->
quantizer_matrix
[
0
][
decoder
->
scan
[
i
]];
}
}
if
(
(
vft
->
load_non_intra_quantizer_matrix
=
decoder
->
load_non_intra_quantizer_matrix
)
)
{
for
(
i
=
0
;
i
<
64
;
++
i
)
{
vft
->
non_intra_quantizer_matrix
[
scan_pattern
[
i
]]
=
mpeg2dec
->
quantizer_matrix
[
1
][
decoder
->
scan
[
i
]];
}
}
decoder
->
load_intra_quantizer_matrix
=
0
;
decoder
->
load_non_intra_quantizer_matrix
=
0
;
vft
->
forward_reference_picture
=
(
picture_t
*
)
mpeg2dec
->
ptr_forward_ref_picture
;
vft
->
backward_reference_picture
=
(
picture_t
*
)
mpeg2dec
->
ptr_backward_ref_picture
;
#if 0
printf("\nSLICE DATA !!!! size=%d", size-4);
int i=0;
if ( vft->forward_reference_picture != NULL && ((vlc_xxmc_t *)
vft->forward_reference_picture->p_data)->slice_data_size > 10)
{
printf("\nFORWARD SLICE DATA !!!! size=%d\n", ((vlc_xxmc_t *)
vft->forward_reference_picture->p_data)->slice_data_size);
for (i=0;i<10;i++)
{
printf("%d ", *(((vlc_xxmc_t *) vft->forward_reference_picture->p_data)->slice_data+i));
}
printf("\nFORWARD SLICE DATA END!!!!\n");
}
if ( vft->backward_reference_picture != NULL && ((vlc_xxmc_t *)
vft->backward_reference_picture->p_data)->slice_data_size > 10)
{
printf("\nBACKWARD SLICE DATA !!!! size=%d\n", ((vlc_xxmc_t *)
vft->backward_reference_picture->p_data)->slice_data_size);
for (i=0;i<10;i++)
{
printf("%d ", *(((vlc_xxmc_t *) vft->backward_reference_picture->p_data)->slice_data+i));
}
printf("\nBACKWARD SLICE DATA END!!!!\n");
}
#endif
xxmc
->
proc_xxmc_begin
(
picture
);
if
(
xxmc
->
result
!=
0
)
{
/* "mpeg2_xxmc_slice begin failed" */
/* xmc->proc_xxmc_flushsync( picture ); */
xxmc
->
proc_xxmc_flush
(
picture
);
mpeg2dec
->
xvmc_last_slice_code
=-
1
;
}
}
if
(
((
code
==
mpeg2dec
->
xvmc_last_slice_code
+
1
||
code
==
mpeg2dec
->
xvmc_last_slice_code
))
&&
(
unsigned
int
)
code
<=
mpeg2dec
->
xxmc_mb_pic_height
)
{
/*
* Send this slice to the output plugin. May stall for a long
* time in proc_slice;
*/
//mpeg2_skip(mpeg2dec, 1);
//frame->bad_frame = 1;
//size = mpeg2dec->chunk_ptr-mpeg2dec->chunk_start;
xxmc
->
slice_data_size
=
size
;
//mpeg2dec->buf_end - mpeg2dec->buf_start;
xxmc
->
slice_data
=
mpeg2dec
->
chunk_start
;
//buffer;
xxmc
->
slice_code
=
code
;
xxmc
->
proc_xxmc_slice
(
picture
);
if
(
xxmc
->
result
!=
0
)
{
//xxmc->proc_xxmc_flushsync( picture );
xxmc
->
proc_xxmc_flush
(
picture
);
mpeg2dec
->
xvmc_last_slice_code
=-
1
;
return
;
}
if
(
(
unsigned
int
)
code
==
mpeg2dec
->
xxmc_mb_pic_height
)
{
/*
* We've encountered the last slice of this frame.
* Release the decoder for a new frame and, if all
* went well, tell libmpeg2 that we are ready.
*/
mpeg2_xxmc_vld_frame_complete
(
mpeg2dec
,
picture
,
code
);
return
;
}
else
if
(
code
==
mpeg2dec
->
xvmc_last_slice_code
+
1
)
{
//xxmc->proc_xxmc_flush( picture );
/*
* Keep track of slices.
*/
mpeg2dec
->
xvmc_last_slice_code
++
;
}
}
else
{
/*
* An error has occurred.
*/
//printf("VLD XvMC: Slice error: code=%d\tlast slice code=%d\tmb_pic_height=%d\n", code, mpeg2dec->xvmc_last_slice_code,mpeg2dec->xxmc_mb_pic_height);
mpeg2dec
->
xvmc_last_slice_code
=
-
1
;
xxmc
->
proc_xxmc_flush
(
picture
);
return
;
}
}
void
mpeg2_xxmc_vld_frame_complete
(
mpeg2dec_t
*
mpeg2dec
,
picture_t
*
picture
,
int
code
)
{
vlc_xxmc_t
*
xxmc
=
(
vlc_xxmc_t
*
)
picture
->
p_data
;
vlc_vld_frame_t
*
vft
=
&
xxmc
->
vld_frame
;
if
(
xxmc
->
decoded
)
return
;
if
(
mpeg2dec
->
xvmc_last_slice_code
>=
1
)
{
xxmc
->
proc_xxmc_flush
(
picture
);
if
(
xxmc
->
result
)
{
mpeg2dec
->
xvmc_last_slice_code
=-
1
;
return
;
}
xxmc
->
decoded
=
1
;
mpeg2dec
->
xvmc_last_slice_code
++
;
if
(
vft
->
picture_structure
==
3
||
vft
->
second_field
)
{
if
(
xxmc
->
result
==
0
)
mpeg2_skip
(
mpeg2dec
,
0
);
//frame->bad_frame = 0;
}
}
}
modules/codec/xvmc/vlc.h
deleted
100644 → 0
View file @
a2180073
/* $Id$
* vlc.h
* 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.
* 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
*/
#define GETWORD(bit_buf,shift,bit_ptr) \
do { \
bit_buf |= ((bit_ptr[0] << 8) | bit_ptr[1]) << (shift); \
bit_ptr += 2; \
} while (0)
static
inline
void
bitstream_init
(
mpeg2_decoder_t
*
decoder
,
const
uint8_t
*
start
)
{
decoder
->
bitstream_buf
=
(
start
[
0
]
<<
24
)
|
(
start
[
1
]
<<
16
)
|
(
start
[
2
]
<<
8
)
|
start
[
3
];
decoder
->
bitstream_ptr
=
start
+
4
;
decoder
->
bitstream_bits
=
-
16
;
}
/* make sure that there are at least 16 valid bits in bit_buf */
#define NEEDBITS(bit_buf,bits,bit_ptr) \
do { \
if (unlikely (bits > 0)) { \
GETWORD (bit_buf, bits, bit_ptr); \
bits -= 16; \
} \
} while (0)
/* remove num valid bits from bit_buf */
#define DUMPBITS(bit_buf,bits,num) \
do { \
bit_buf <<= (num); \
bits += (num); \
} while (0)
/* take num bits from the high part of bit_buf and zero extend them */
#define UBITS(bit_buf,num) (((uint32_t)(bit_buf)) >> (32 - (num)))
/* take num bits from the high part of bit_buf and sign extend them */
#define SBITS(bit_buf,num) (((int32_t)(bit_buf)) >> (32 - (num)))
typedef
struct
{
uint8_t
modes
;
uint8_t
len
;
}
MBtab
;
typedef
struct
{
uint8_t
delta
;
uint8_t
len
;
}
MVtab
;
typedef
struct
{
int8_t
dmv
;
uint8_t
len
;
}
DMVtab
;
typedef
struct
{
uint8_t
cbp
;
uint8_t
len
;
}
CBPtab
;
typedef
struct
{
uint8_t
size
;
uint8_t
len
;
}
DCtab
;
typedef
struct
{
uint8_t
run
;
uint8_t
level
;
uint8_t
len
;
}
DCTtab
;
typedef
struct
{
uint8_t
mba
;
uint8_t
len
;
}
MBAtab
;
#define INTRA MACROBLOCK_INTRA
#define QUANT MACROBLOCK_QUANT
static
const
MBtab
MB_I
[]
=
{
{
INTRA
|
QUANT
,
2
},
{
INTRA
,
1
}
};
#define MC MACROBLOCK_MOTION_FORWARD
#define CODED MACROBLOCK_PATTERN
static
const
MBtab
MB_P
[]
=
{
{
INTRA
|
QUANT
,
6
},
{
CODED
|
QUANT
,
5
},
{
MC
|
CODED
|
QUANT
,
5
},
{
INTRA
,
5
},
{
MC
,
3
},
{
MC
,
3
},
{
MC
,
3
},
{
MC
,
3
},
{
CODED
,
2
},
{
CODED
,
2
},
{
CODED
,
2
},
{
CODED
,
2
},
{
CODED
,
2
},
{
CODED
,
2
},
{
CODED
,
2
},
{
CODED
,
2
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
},
{
MC
|
CODED
,
1
}
};
#define FWD MACROBLOCK_MOTION_FORWARD
#define BWD MACROBLOCK_MOTION_BACKWARD
#define INTER MACROBLOCK_MOTION_FORWARD|MACROBLOCK_MOTION_BACKWARD
static
const
MBtab
MB_B
[]
=
{
{
0
,
0
},
{
INTRA
|
QUANT
,
6
},
{
BWD
|
CODED
|
QUANT
,
6
},
{
FWD
|
CODED
|
QUANT
,
6
},
{
INTER
|
CODED
|
QUANT
,
5
},
{
INTER
|
CODED
|
QUANT
,
5
},
{
INTRA
,
5
},
{
INTRA
,
5
},
{
FWD
,
4
},
{
FWD
,
4
},
{
FWD
,
4
},
{
FWD
,
4
},
{
FWD
|
CODED
,
4
},
{
FWD
|
CODED
,
4
},
{
FWD
|
CODED
,
4
},
{
FWD
|
CODED
,
4
},
{
BWD
,
3
},
{
BWD
,
3
},
{
BWD
,
3
},
{
BWD
,
3
},
{
BWD
,
3
},
{
BWD
,
3
},
{
BWD
,
3
},
{
BWD
,
3
},
{
BWD
|
CODED
,
3
},
{
BWD
|
CODED
,
3
},
{
BWD
|
CODED
,
3
},
{
BWD
|
CODED
,
3
},
{
BWD
|
CODED
,
3
},
{
BWD
|
CODED
,
3
},
{
BWD
|
CODED
,
3
},
{
BWD
|
CODED
,
3
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
},
{
INTER
|
CODED
,
2
}
};
#undef INTRA
#undef QUANT
#undef MC
#undef CODED
#undef FWD
#undef BWD
#undef INTER
static
const
MVtab
MV_4
[]
=
{
{
3
,
6
},
{
2
,
4
},
{
1
,
3
},
{
1
,
3
},
{
0
,
2
},
{
0
,
2
},
{
0
,
2
},
{
0
,
2
}
};
static
const
MVtab
MV_10
[]
=
{
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
0
,
10
},
{
15
,
10
},
{
14
,
10
},
{
13
,
10
},
{
12
,
10
},
{
11
,
10
},
{
10
,
10
},
{
9
,
9
},
{
9
,
9
},
{
8
,
9
},
{
8
,
9
},
{
7
,
9
},
{
7
,
9
},
{
6
,
7
},
{
6
,
7
},
{
6
,
7
},
{
6
,
7
},
{
6
,
7
},
{
6
,
7
},
{
6
,
7
},
{
6
,
7
},
{
5
,
7
},
{
5
,
7
},
{
5
,
7
},
{
5
,
7
},
{
5
,
7
},
{
5
,
7
},
{
5
,
7
},
{
5
,
7
},
{
4
,
7
},
{
4
,
7
},
{
4
,
7
},
{
4
,
7
},
{
4
,
7
},
{
4
,
7
},
{
4
,
7
},
{
4
,
7
}
};
static
const
DMVtab
DMV_2
[]
=
{
{
0
,
1
},
{
0
,
1
},
{
1
,
2
},
{
-
1
,
2
}
};
static
const
CBPtab
CBP_7
[]
=
{
{
0x11
,
7
},
{
0x12
,
7
},
{
0x14
,
7
},
{
0x18
,
7
},
{
0x21
,
7
},
{
0x22
,
7
},
{
0x24
,
7
},
{
0x28
,
7
},
{
0x3f
,
6
},
{
0x3f
,
6
},
{
0x30
,
6
},
{
0x30
,
6
},
{
0x09
,
6
},
{
0x09
,
6
},
{
0x06
,
6
},
{
0x06
,
6
},
{
0x1f
,
5
},
{
0x1f
,
5
},
{
0x1f
,
5
},
{
0x1f
,
5
},
{
0x10
,
5
},
{
0x10
,
5
},
{
0x10
,
5
},
{
0x10
,
5
},
{
0x2f
,
5
},
{
0x2f
,
5
},
{
0x2f
,
5
},
{
0x2f
,
5
},
{
0x20
,
5
},
{
0x20
,
5
},
{
0x20
,
5
},
{
0x20
,
5
},
{
0x07
,
5
},
{
0x07
,
5
},
{
0x07
,
5
},
{
0x07
,
5
},
{
0x0b
,
5
},
{
0x0b
,
5
},
{
0x0b
,
5
},
{
0x0b
,
5
},
{
0x0d
,
5
},
{
0x0d
,
5
},
{
0x0d
,
5
},
{
0x0d
,
5
},
{
0x0e
,
5
},
{
0x0e
,
5
},
{
0x0e
,
5
},
{
0x0e
,
5
},
{
0x05
,
5
},
{
0x05
,
5
},
{
0x05
,
5
},
{
0x05
,
5
},
{
0x0a
,
5
},
{
0x0a
,
5
},
{
0x0a
,
5
},
{
0x0a
,
5
},
{
0x03
,
5
},
{
0x03
,
5
},
{
0x03
,
5
},
{
0x03
,
5
},
{
0x0c
,
5
},
{
0x0c
,
5
},
{
0x0c
,
5
},
{
0x0c
,
5
},
{
0x01
,
4
},
{
0x01
,
4
},
{
0x01
,
4
},
{
0x01
,
4
},
{
0x01
,
4
},
{
0x01
,
4
},
{
0x01
,
4
},
{
0x01
,
4
},
{
0x02
,
4
},
{
0x02
,
4
},
{
0x02
,
4
},
{
0x02
,
4
},
{
0x02
,
4
},
{
0x02
,
4
},
{
0x02
,
4
},
{
0x02
,
4
},
{
0x04
,
4
},
{
0x04
,
4
},
{
0x04
,
4
},
{
0x04
,
4
},
{
0x04
,
4
},
{
0x04
,
4
},
{
0x04
,
4
},
{
0x04
,
4
},
{
0x08
,
4
},
{
0x08
,
4
},
{
0x08
,
4
},
{
0x08
,
4
},
{
0x08
,
4
},
{
0x08
,
4
},
{
0x08
,
4
},
{
0x08
,
4
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
},
{
0x0f
,
3
}
};
static
const
CBPtab
CBP_9
[]
=
{
{
0
,
0
},
{
0x00
,
9
},
{
0x39
,
9
},
{
0x36
,
9
},
{
0x37
,
9
},
{
0x3b
,
9
},
{
0x3d
,
9
},
{
0x3e
,
9
},
{
0x17
,
8
},
{
0x17
,
8
},
{
0x1b
,
8
},
{
0x1b
,
8
},
{
0x1d
,
8
},
{
0x1d
,
8
},
{
0x1e
,
8
},
{
0x1e
,
8
},
{
0x27
,
8
},
{
0x27
,
8
},
{
0x2b
,
8
},
{
0x2b
,
8
},
{
0x2d
,
8
},
{
0x2d
,
8
},
{
0x2e
,
8
},
{
0x2e
,
8
},
{
0x19
,
8
},
{
0x19
,
8
},
{
0x16
,
8
},
{
0x16
,
8
},
{
0x29
,
8
},
{
0x29
,
8
},
{
0x26
,
8
},
{
0x26
,
8
},
{
0x35
,
8
},
{
0x35
,
8
},
{
0x3a
,
8
},
{
0x3a
,
8
},
{
0x33
,
8
},
{
0x33
,
8
},
{
0x3c
,
8
},
{
0x3c
,
8
},
{
0x15
,
8
},
{
0x15
,
8
},
{
0x1a
,
8
},
{
0x1a
,
8
},
{
0x13
,
8
},
{
0x13
,
8
},
{
0x1c
,
8
},
{
0x1c
,
8
},
{
0x25
,
8
},
{
0x25
,
8
},
{
0x2a
,
8
},
{
0x2a
,
8
},
{
0x23
,
8
},
{
0x23
,
8
},
{
0x2c
,
8
},
{
0x2c
,
8
},
{
0x31
,
8
},
{
0x31
,
8
},
{
0x32
,
8
},
{
0x32
,
8
},
{
0x34
,
8
},
{
0x34
,
8
},
{
0x38
,
8
},
{
0x38
,
8
}
};
static
const
DCtab
DC_lum_5
[]
=
{
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
0
,
3
},
{
0
,
3
},
{
0
,
3
},
{
0
,
3
},
{
3
,
3
},
{
3
,
3
},
{
3
,
3
},
{
3
,
3
},
{
4
,
3
},
{
4
,
3
},
{
4
,
3
},
{
4
,
3
},
{
5
,
4
},
{
5
,
4
},
{
6
,
5
}
};
static
const
DCtab
DC_chrom_5
[]
=
{
{
0
,
2
},
{
0
,
2
},
{
0
,
2
},
{
0
,
2
},
{
0
,
2
},
{
0
,
2
},
{
0
,
2
},
{
0
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
1
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
2
,
2
},
{
3
,
3
},
{
3
,
3
},
{
3
,
3
},
{
3
,
3
},
{
4
,
4
},
{
4
,
4
},
{
5
,
5
}
};
static
const
DCtab
DC_long
[]
=
{
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
6
,
5
},
{
7
,
6
},
{
7
,
6
},
{
7
,
6
},
{
7
,
6
},
{
7
,
6
},
{
7
,
6
},
{
7
,
6
},
{
7
,
6
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
9
,
8
},
{
9
,
8
},
{
10
,
9
},
{
11
,
9
}
};
static
const
DCTtab
DCT_16
[]
=
{
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
129
,
0
,
0
},
{
2
,
18
,
0
},
{
2
,
17
,
0
},
{
2
,
16
,
0
},
{
2
,
15
,
0
},
{
7
,
3
,
0
},
{
17
,
2
,
0
},
{
16
,
2
,
0
},
{
15
,
2
,
0
},
{
14
,
2
,
0
},
{
13
,
2
,
0
},
{
12
,
2
,
0
},
{
32
,
1
,
0
},
{
31
,
1
,
0
},
{
30
,
1
,
0
},
{
29
,
1
,
0
},
{
28
,
1
,
0
}
};
static
const
DCTtab
DCT_15
[]
=
{
{
1
,
40
,
15
},
{
1
,
39
,
15
},
{
1
,
38
,
15
},
{
1
,
37
,
15
},
{
1
,
36
,
15
},
{
1
,
35
,
15
},
{
1
,
34
,
15
},
{
1
,
33
,
15
},
{
1
,
32
,
15
},
{
2
,
14
,
15
},
{
2
,
13
,
15
},
{
2
,
12
,
15
},
{
2
,
11
,
15
},
{
2
,
10
,
15
},
{
2
,
9
,
15
},
{
2
,
8
,
15
},
{
1
,
31
,
14
},
{
1
,
31
,
14
},
{
1
,
30
,
14
},
{
1
,
30
,
14
},
{
1
,
29
,
14
},
{
1
,
29
,
14
},
{
1
,
28
,
14
},
{
1
,
28
,
14
},
{
1
,
27
,
14
},
{
1
,
27
,
14
},
{
1
,
26
,
14
},
{
1
,
26
,
14
},
{
1
,
25
,
14
},
{
1
,
25
,
14
},
{
1
,
24
,
14
},
{
1
,
24
,
14
},
{
1
,
23
,
14
},
{
1
,
23
,
14
},
{
1
,
22
,
14
},
{
1
,
22
,
14
},
{
1
,
21
,
14
},
{
1
,
21
,
14
},
{
1
,
20
,
14
},
{
1
,
20
,
14
},
{
1
,
19
,
14
},
{
1
,
19
,
14
},
{
1
,
18
,
14
},
{
1
,
18
,
14
},
{
1
,
17
,
14
},
{
1
,
17
,
14
},
{
1
,
16
,
14
},
{
1
,
16
,
14
}
};
static
const
DCTtab
DCT_13
[]
=
{
{
11
,
2
,
13
},
{
10
,
2
,
13
},
{
6
,
3
,
13
},
{
4
,
4
,
13
},
{
3
,
5
,
13
},
{
2
,
7
,
13
},
{
2
,
6
,
13
},
{
1
,
15
,
13
},
{
1
,
14
,
13
},
{
1
,
13
,
13
},
{
1
,
12
,
13
},
{
27
,
1
,
13
},
{
26
,
1
,
13
},
{
25
,
1
,
13
},
{
24
,
1
,
13
},
{
23
,
1
,
13
},
{
1
,
11
,
12
},
{
1
,
11
,
12
},
{
9
,
2
,
12
},
{
9
,
2
,
12
},
{
5
,
3
,
12
},
{
5
,
3
,
12
},
{
1
,
10
,
12
},
{
1
,
10
,
12
},
{
3
,
4
,
12
},
{
3
,
4
,
12
},
{
8
,
2
,
12
},
{
8
,
2
,
12
},
{
22
,
1
,
12
},
{
22
,
1
,
12
},
{
21
,
1
,
12
},
{
21
,
1
,
12
},
{
1
,
9
,
12
},
{
1
,
9
,
12
},
{
20
,
1
,
12
},
{
20
,
1
,
12
},
{
19
,
1
,
12
},
{
19
,
1
,
12
},
{
2
,
5
,
12
},
{
2
,
5
,
12
},
{
4
,
3
,
12
},
{
4
,
3
,
12
},
{
1
,
8
,
12
},
{
1
,
8
,
12
},
{
7
,
2
,
12
},
{
7
,
2
,
12
},
{
18
,
1
,
12
},
{
18
,
1
,
12
}
};
static
const
DCTtab
DCT_B14_10
[]
=
{
{
17
,
1
,
10
},
{
6
,
2
,
10
},
{
1
,
7
,
10
},
{
3
,
3
,
10
},
{
2
,
4
,
10
},
{
16
,
1
,
10
},
{
15
,
1
,
10
},
{
5
,
2
,
10
}
};
static
const
DCTtab
DCT_B14_8
[]
=
{
{
65
,
0
,
6
},
{
65
,
0
,
6
},
{
65
,
0
,
6
},
{
65
,
0
,
6
},
{
3
,
2
,
7
},
{
3
,
2
,
7
},
{
10
,
1
,
7
},
{
10
,
1
,
7
},
{
1
,
4
,
7
},
{
1
,
4
,
7
},
{
9
,
1
,
7
},
{
9
,
1
,
7
},
{
8
,
1
,
6
},
{
8
,
1
,
6
},
{
8
,
1
,
6
},
{
8
,
1
,
6
},
{
7
,
1
,
6
},
{
7
,
1
,
6
},
{
7
,
1
,
6
},
{
7
,
1
,
6
},
{
2
,
2
,
6
},
{
2
,
2
,
6
},
{
2
,
2
,
6
},
{
2
,
2
,
6
},
{
6
,
1
,
6
},
{
6
,
1
,
6
},
{
6
,
1
,
6
},
{
6
,
1
,
6
},
{
14
,
1
,
8
},
{
1
,
6
,
8
},
{
13
,
1
,
8
},
{
12
,
1
,
8
},
{
4
,
2
,
8
},
{
2
,
3
,
8
},
{
1
,
5
,
8
},
{
11
,
1
,
8
}
};
static
const
DCTtab
DCT_B14AC_5
[]
=
{
{
1
,
3
,
5
},
{
5
,
1
,
5
},
{
4
,
1
,
5
},
{
1
,
2
,
4
},
{
1
,
2
,
4
},
{
3
,
1
,
4
},
{
3
,
1
,
4
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
129
,
0
,
2
},
{
129
,
0
,
2
},
{
129
,
0
,
2
},
{
129
,
0
,
2
},
{
129
,
0
,
2
},
{
129
,
0
,
2
},
{
129
,
0
,
2
},
{
129
,
0
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
}
};
static
const
DCTtab
DCT_B14DC_5
[]
=
{
{
1
,
3
,
5
},
{
5
,
1
,
5
},
{
4
,
1
,
5
},
{
1
,
2
,
4
},
{
1
,
2
,
4
},
{
3
,
1
,
4
},
{
3
,
1
,
4
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
},
{
1
,
1
,
1
}
};
static
const
DCTtab
DCT_B15_10
[]
=
{
{
6
,
2
,
9
},
{
6
,
2
,
9
},
{
15
,
1
,
9
},
{
15
,
1
,
9
},
{
3
,
4
,
10
},
{
17
,
1
,
10
},
{
16
,
1
,
9
},
{
16
,
1
,
9
}
};
static
const
DCTtab
DCT_B15_8
[]
=
{
{
65
,
0
,
6
},
{
65
,
0
,
6
},
{
65
,
0
,
6
},
{
65
,
0
,
6
},
{
8
,
1
,
7
},
{
8
,
1
,
7
},
{
9
,
1
,
7
},
{
9
,
1
,
7
},
{
7
,
1
,
7
},
{
7
,
1
,
7
},
{
3
,
2
,
7
},
{
3
,
2
,
7
},
{
1
,
7
,
6
},
{
1
,
7
,
6
},
{
1
,
7
,
6
},
{
1
,
7
,
6
},
{
1
,
6
,
6
},
{
1
,
6
,
6
},
{
1
,
6
,
6
},
{
1
,
6
,
6
},
{
5
,
1
,
6
},
{
5
,
1
,
6
},
{
5
,
1
,
6
},
{
5
,
1
,
6
},
{
6
,
1
,
6
},
{
6
,
1
,
6
},
{
6
,
1
,
6
},
{
6
,
1
,
6
},
{
2
,
5
,
8
},
{
12
,
1
,
8
},
{
1
,
11
,
8
},
{
1
,
10
,
8
},
{
14
,
1
,
8
},
{
13
,
1
,
8
},
{
4
,
2
,
8
},
{
2
,
4
,
8
},
{
3
,
1
,
5
},
{
3
,
1
,
5
},
{
3
,
1
,
5
},
{
3
,
1
,
5
},
{
3
,
1
,
5
},
{
3
,
1
,
5
},
{
3
,
1
,
5
},
{
3
,
1
,
5
},
{
2
,
2
,
5
},
{
2
,
2
,
5
},
{
2
,
2
,
5
},
{
2
,
2
,
5
},
{
2
,
2
,
5
},
{
2
,
2
,
5
},
{
2
,
2
,
5
},
{
2
,
2
,
5
},
{
4
,
1
,
5
},
{
4
,
1
,
5
},
{
4
,
1
,
5
},
{
4
,
1
,
5
},
{
4
,
1
,
5
},
{
4
,
1
,
5
},
{
4
,
1
,
5
},
{
4
,
1
,
5
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
2
,
1
,
3
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
129
,
0
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
3
,
4
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
1
,
2
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
2
,
3
},
{
1
,
4
,
5
},
{
1
,
4
,
5
},
{
1
,
4
,
5
},
{
1
,
4
,
5
},
{
1
,
4
,
5
},
{
1
,
4
,
5
},
{
1
,
4
,
5
},
{
1
,
4
,
5
},
{
1
,
5
,
5
},
{
1
,
5
,
5
},
{
1
,
5
,
5
},
{
1
,
5
,
5
},
{
1
,
5
,
5
},
{
1
,
5
,
5
},
{
1
,
5
,
5
},
{
1
,
5
,
5
},
{
10
,
1
,
7
},
{
10
,
1
,
7
},
{
2
,
3
,
7
},
{
2
,
3
,
7
},
{
11
,
1
,
7
},
{
11
,
1
,
7
},
{
1
,
8
,
7
},
{
1
,
8
,
7
},
{
1
,
9
,
7
},
{
1
,
9
,
7
},
{
1
,
12
,
8
},
{
1
,
13
,
8
},
{
3
,
3
,
8
},
{
5
,
2
,
8
},
{
1
,
14
,
8
},
{
1
,
15
,
8
}
};
static
const
MBAtab
MBA_5
[]
=
{
{
6
,
5
},
{
5
,
5
},
{
4
,
4
},
{
4
,
4
},
{
3
,
4
},
{
3
,
4
},
{
2
,
3
},
{
2
,
3
},
{
2
,
3
},
{
2
,
3
},
{
1
,
3
},
{
1
,
3
},
{
1
,
3
},
{
1
,
3
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
},
{
0
,
1
}
};
static
const
MBAtab
MBA_11
[]
=
{
{
32
,
11
},
{
31
,
11
},
{
30
,
11
},
{
29
,
11
},
{
28
,
11
},
{
27
,
11
},
{
26
,
11
},
{
25
,
11
},
{
24
,
11
},
{
23
,
11
},
{
22
,
11
},
{
21
,
11
},
{
20
,
10
},
{
20
,
10
},
{
19
,
10
},
{
19
,
10
},
{
18
,
10
},
{
18
,
10
},
{
17
,
10
},
{
17
,
10
},
{
16
,
10
},
{
16
,
10
},
{
15
,
10
},
{
15
,
10
},
{
14
,
8
},
{
14
,
8
},
{
14
,
8
},
{
14
,
8
},
{
14
,
8
},
{
14
,
8
},
{
14
,
8
},
{
14
,
8
},
{
13
,
8
},
{
13
,
8
},
{
13
,
8
},
{
13
,
8
},
{
13
,
8
},
{
13
,
8
},
{
13
,
8
},
{
13
,
8
},
{
12
,
8
},
{
12
,
8
},
{
12
,
8
},
{
12
,
8
},
{
12
,
8
},
{
12
,
8
},
{
12
,
8
},
{
12
,
8
},
{
11
,
8
},
{
11
,
8
},
{
11
,
8
},
{
11
,
8
},
{
11
,
8
},
{
11
,
8
},
{
11
,
8
},
{
11
,
8
},
{
10
,
8
},
{
10
,
8
},
{
10
,
8
},
{
10
,
8
},
{
10
,
8
},
{
10
,
8
},
{
10
,
8
},
{
10
,
8
},
{
9
,
8
},
{
9
,
8
},
{
9
,
8
},
{
9
,
8
},
{
9
,
8
},
{
9
,
8
},
{
9
,
8
},
{
9
,
8
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
8
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
},
{
7
,
7
}
};
modules/codec/xvmc/xvmc_vld.h
deleted
100644 → 0
View file @
a2180073
/* $Id$
* Copyright (c) 2004 The Unichrome project. All rights reserved.
*
* This program 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, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTIES OR REPRESENTATIONS; 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 _XVMC_VLD_H
#define _XVMC_VLD_H
#include "accel_xvmc.h"
//#include "xvmc.h"
extern
void
mpeg2_xxmc_slice
(
mpeg2dec_t
*
mpeg2dec
,
picture_t
*
picture
,
int
code
,
uint8_t
*
buffer
,
int
size
);
extern
void
mpeg2_xxmc_choose_coding
(
decoder_t
*
p_dec
,
mpeg2_decoder_t
*
const
decoder
,
picture_t
*
picture
,
double
aspect_ratio
,
int
flags
);
extern
void
mpeg2_xxmc_vld_frame_complete
(
mpeg2dec_t
*
mpeg2dec
,
picture_t
*
picture
,
int
code
);
#endif
modules/codec/xvmc/xxmc-config.h
deleted
100644 → 0
View file @
a2180073
/* include/config.h. Generated by configure. */
/* include/config.h.in. Generated from configure.in by autoheader. */
/* autodetect accelerations */
#define ACCEL_DETECT
/* alpha architecture */
/* #undef ARCH_ALPHA */
/* ppc architecture */
/* #undef ARCH_PPC */
/* sparc architecture */
/* #undef ARCH_SPARC */
/* x86 architecture */
#define ARCH_X86
/* maximum supported data alignment */
#define ATTRIBUTE_ALIGNED_MAX 64
/* debug mode configuration */
/* #undef DEBUG */
/* Define to 1 if you have the <altivec.h> header file. */
/* #undef HAVE_ALTIVEC_H */
/* Define if you have the `__builtin_expect' function. */
#define HAVE_BUILTIN_EXPECT
/* Define to 1 if you have the <dlfcn.h> header file. */
#define HAVE_DLFCN_H 1
/* Define to 1 if you have the `ftime' function. */
#define HAVE_FTIME 1
/* Define to 1 if you have the `gettimeofday' function. */
#define HAVE_GETTIMEOFDAY 1
/* Define to 1 if you have the <inttypes.h> header file. */
#define HAVE_INTTYPES_H 1
/* Define to 1 if you have the <io.h> header file. */
/* #undef HAVE_IO_H */
/* Define to 1 if you have the <memory.h> header file. */
#define HAVE_MEMORY_H 1
/* Define to 1 if you have the <stdint.h> header file. */
#define HAVE_STDINT_H 1
/* Define to 1 if you have the <stdlib.h> header file. */
#define HAVE_STDLIB_H 1
/* Define to 1 if you have the <strings.h> header file. */
#define HAVE_STRINGS_H 1
/* Define to 1 if you have the <string.h> header file. */
#define HAVE_STRING_H 1
/* Define to 1 if the system has the type `struct timeval'. */
#define HAVE_STRUCT_TIMEVAL 1
/* Define to 1 if you have the <sys/stat.h> header file. */
#define HAVE_SYS_STAT_H 1
/* Define to 1 if you have the <sys/timeb.h> header file. */
#define HAVE_SYS_TIMEB_H 1
/* Define to 1 if you have the <sys/time.h> header file. */
#define HAVE_SYS_TIME_H 1
/* Define to 1 if you have the <sys/types.h> header file. */
#define HAVE_SYS_TYPES_H 1
/* Define to 1 if you have the <time.h> header file. */
#define HAVE_TIME_H 1
/* Define to 1 if you have the <unistd.h> header file. */
#define HAVE_UNISTD_H 1
/* libvo DirectX support */
/* #undef LIBVO_DX */
/* libvo SDL support */
/* #undef LIBVO_SDL */
/* libvo X11 support */
#define LIBVO_X11
/* libvo Xv support */
#define LIBVO_XV
/* mpeg2dec profiling */
/* #undef MPEG2DEC_GPROF */
/* Name of package */
/*#define PACKAGE "mpeg2dec"*/
/* Define to the address where bug reports for this package should be sent. */
/*#define PACKAGE_BUGREPORT ""*/
/* Define to the full name of this package. */
/*#define PACKAGE_NAME ""*/
/* Define to the full name and version of this package. */
/*#define PACKAGE_STRING ""*/
/* Define to the one symbol short name of this package. */
/*#define PACKAGE_TARNAME ""*/
/* Define to the version of this package. */
/*#define PACKAGE_VERSION ""*/
/* Define as the return type of signal handlers (`int' or `void'). */
#define RETSIGTYPE void
/* The size of a `char', as computed by sizeof. */
/* #undef SIZEOF_CHAR */
/* The size of a `int', as computed by sizeof. */
/* #undef SIZEOF_INT */
/* The size of a `long', as computed by sizeof. */
/* #undef SIZEOF_LONG */
/* The size of a `short', as computed by sizeof. */
/* #undef SIZEOF_SHORT */
/* The size of a `void*', as computed by sizeof. */
/* #undef SIZEOF_VOIDP */
/* Define to 1 if you have the ANSI C header files. */
#define STDC_HEADERS 1
/* Define to 1 if you can safely include both <sys/time.h> and <time.h>. */
#define TIME_WITH_SYS_TIME 1
/* Version number of package */
/* #define VERSION "0.4.0" */
/* Define to 1 if your processor stores words with the most significant byte
first (like Motorola and SPARC, unlike Intel and VAX). */
/* #undef WORDS_BIGENDIAN */
/* Define to 1 if the X Window System is missing or not being used. */
/* #undef X_DISPLAY_MISSING */
/* Number of bits in a file offset, on hosts where this is settable. */
#define _FILE_OFFSET_BITS 64
/* Define for large files, on AIX-style hosts. */
/* #undef _LARGE_FILES */
/* Define to empty if `const' does not conform to ANSI C. */
/* #undef const */
/* Define to `__inline__' or `__inline' if that's what the C compiler
calls it, or to nothing if 'inline' is not supported under any name. */
#ifndef __cplusplus
#define inline __attribute__ ((__always_inline__))
#endif
/* Define as `__restrict' if that's what the C compiler calls it, or to
nothing if it is not supported. */
#define restrict __restrict__
/* Define to `unsigned' if <sys/types.h> does not define. */
/* #undef size_t */
/* Define to empty if the keyword `volatile' does not work. Warning: valid
code using `volatile' can become incorrect without. Disable with care. */
/* #undef volatile */
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment