Release Version 0.4.6.

This commit is contained in:
Johns 2012-02-02 23:32:51 +01:00
parent ab4e89132e
commit 00cafd18ed
3 changed files with 133 additions and 15 deletions

View File

@ -1,7 +1,8 @@
User johns User johns
Date: Date: Thu Feb 2 23:29:35 CET 2012
Release Version 0.4.6 Release Version 0.4.6
Warn only on the first duplicated frame in sequence.
Increase audio buffer, if bigger audio delay is used. Increase audio buffer, if bigger audio delay is used.
Makes SkipLines configure in setup menu. Makes SkipLines configure in setup menu.
Auto-crop only enabled with normal 4:3 display mode. Auto-crop only enabled with normal 4:3 display mode.

View File

@ -42,7 +42,7 @@ extern "C"
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
static const char *const VERSION = "0.4.5"; static const char *const VERSION = "0.4.6";
static const char *const DESCRIPTION = static const char *const DESCRIPTION =
trNOOP("A software and GPU emulated HD device"); trNOOP("A software and GPU emulated HD device");

127
video.c
View File

@ -1465,14 +1465,14 @@ static void VaapiDestroySurfaces(VaapiDecoder * decoder)
if (vaDestroySurfaces(decoder->VaDisplay, decoder->SurfacesFree, if (vaDestroySurfaces(decoder->VaDisplay, decoder->SurfacesFree,
decoder->SurfaceFreeN) decoder->SurfaceFreeN)
!= VA_STATUS_SUCCESS) { != VA_STATUS_SUCCESS) {
Error("video/vaapi: can't destroy %d surfaces\n", Error(_("video/vaapi: can't destroy %d surfaces\n"),
decoder->SurfaceFreeN); decoder->SurfaceFreeN);
} }
decoder->SurfaceFreeN = 0; decoder->SurfaceFreeN = 0;
if (vaDestroySurfaces(decoder->VaDisplay, decoder->SurfacesUsed, if (vaDestroySurfaces(decoder->VaDisplay, decoder->SurfacesUsed,
decoder->SurfaceUsedN) decoder->SurfaceUsedN)
!= VA_STATUS_SUCCESS) { != VA_STATUS_SUCCESS) {
Error("video/vaapi: can't destroy %d surfaces\n", Error(_("video/vaapi: can't destroy %d surfaces\n"),
decoder->SurfaceUsedN); decoder->SurfaceUsedN);
} }
decoder->SurfaceUsedN = 0; decoder->SurfaceUsedN = 0;
@ -1506,7 +1506,7 @@ static VASurfaceID VaapiGetSurface(VaapiDecoder * decoder)
} }
// surface still in use, try next // surface still in use, try next
if (status != VASurfaceReady) { if (status != VASurfaceReady) {
Debug("video/vaapi: surface %#010x not ready: %d\n", surface, Debug(3, "video/vaapi: surface %#010x not ready: %d\n", surface,
status); status);
if (!VaapiBuggyVdpau || i < 1) { if (!VaapiBuggyVdpau || i < 1) {
continue; continue;
@ -1839,6 +1839,111 @@ static void VaapiDelDecoder(VaapiDecoder * decoder)
free(decoder); free(decoder);
} }
static VAProfile VaapiFindProfile(const VAProfile * profiles, unsigned n,
VAProfile profile);
static VAEntrypoint VaapiFindEntrypoint(const VAEntrypoint * entrypoints,
unsigned n, VAEntrypoint entrypoint);
///
/// 1080i
///
static void Vaapi1080i(void)
{
VAProfile profiles[vaMaxNumProfiles(VaDisplay)];
int profile_n;
VAEntrypoint entrypoints[vaMaxNumEntrypoints(VaDisplay)];
int entrypoint_n;
int p;
int e;
VAConfigAttrib attrib;
VAConfigID config_id;
VAContextID context_id;
VASurfaceID surfaces[32];
int n;
uint32_t start_tick;
uint32_t tick;
p = -1;
e = -1;
// prepare va-api profiles
if (vaQueryConfigProfiles(VaDisplay, profiles, &profile_n)) {
Error(_("codec: vaQueryConfigProfiles failed"));
return;
}
// check profile
p = VaapiFindProfile(profiles, profile_n, VAProfileH264High);
if (p == -1) {
Debug(3, "\tno profile found\n");
return;
}
// prepare va-api entry points
if (vaQueryConfigEntrypoints(VaDisplay, p, entrypoints, &entrypoint_n)) {
Error(_("codec: vaQueryConfigEntrypoints failed"));
return;
}
e = VaapiFindEntrypoint(entrypoints, entrypoint_n, VAEntrypointVLD);
if (e == -1) {
Warning(_("codec: unsupported: slow path\n"));
return;
}
memset(&attrib, 0, sizeof(attrib));
attrib.type = VAConfigAttribRTFormat;
attrib.value = VA_RT_FORMAT_YUV420;
// create a configuration for the decode pipeline
if (vaCreateConfig(VaDisplay, p, e, &attrib, 1, &config_id)) {
Error(_("codec: can't create config"));
return;
}
if (vaCreateSurfaces(VaDisplay, 1920, 1080, VA_RT_FORMAT_YUV420, 32,
surfaces) != VA_STATUS_SUCCESS) {
Error(_("video/vaapi: can't create surfaces\n"));
return;
}
// bind surfaces to context
if (vaCreateContext(VaDisplay, config_id, 1920, 1080, VA_PROGRESSIVE,
surfaces, 32, &context_id)) {
Error(_("codec: can't create context"));
return;
}
start_tick = GetMsTicks();
for (n = 1; n < 10000; ++n) {
if (vaPutSurface(VaDisplay, surfaces[0], VideoWindow,
// decoder src
0, 0, 1920, 1080,
// video dst
0, 0, 1920, 1080, NULL, 0, VA_TOP_FIELD | VA_CLEAR_DRAWABLE)
!= VA_STATUS_SUCCESS) {
Error(_("video/vaapi: vaPutSurface failed\n"));
}
if (vaPutSurface(VaDisplay, surfaces[0], VideoWindow,
// decoder src
0, 0, 1920, 1080,
// video dst
0, 0, 1920, 1080, NULL, 0, VA_BOTTOM_FIELD | VA_CLEAR_DRAWABLE)
!= VA_STATUS_SUCCESS) {
Error(_("video/vaapi: vaPutSurface failed\n"));
}
tick = GetMsTicks();
if (!(n % 100)) {
fprintf(stderr, "%d ms / frame\n", (tick - start_tick) / n);
}
}
// destory the stuff.
if (vaDestroyContext(VaDisplay, context_id) != VA_STATUS_SUCCESS) {
Error(_("video/vaapi: can't destroy context!\n"));
}
if (vaDestroySurfaces(VaDisplay, surfaces, 32) != VA_STATUS_SUCCESS) {
Error(_("video/vaapi: can't destroy surfaces\n"));
}
if (vaDestroyConfig(VaDisplay, config_id) != VA_STATUS_SUCCESS) {
Error(_("video/vaapi: can't destroy config!\n"));
}
printf("done\n");
}
/// ///
/// VA-API setup. /// VA-API setup.
/// ///
@ -1909,7 +2014,9 @@ static int VaapiInit(const char *display_name)
// check the chroma format // check the chroma format
// //
attr.type = VAConfigAttribRTFormat attr.flags = VA_DISPLAY_ATTRIB_GETTABLE; attr.type = VAConfigAttribRTFormat attr.flags = VA_DISPLAY_ATTRIB_GETTABLE;
Vaapi1080i();
#endif #endif
return 1; return 1;
} }
@ -3719,13 +3826,18 @@ static void VaapiAdvanceFrame(void)
} }
// debug duplicate frames // debug duplicate frames
} else if (filled == 1) { } else if (filled == 1) {
static int last_warned_frame;
++decoder->FramesDuped; ++decoder->FramesDuped;
decoder->DropNextFrame = 0; decoder->DropNextFrame = 0;
// FIXME: don't warn after stream start // FIXME: don't warn after stream start, don't warn during pause
if (last_warned_frame != decoder->FrameCounter) {
Warning(_ Warning(_
("video: display buffer empty, duping frame (%d/%d) %d\n"), ("video: display buffer empty, duping frame (%d/%d) %d\n"),
decoder->FramesDuped, decoder->FrameCounter, decoder->FramesDuped, decoder->FrameCounter,
atomic_read(&VideoPacketsFilled)); atomic_read(&VideoPacketsFilled));
}
last_warned_frame = decoder->FrameCounter;
if (!(decoder->FramesDisplayed % 300)) { if (!(decoder->FramesDisplayed % 300)) {
VaapiPrintFrames(decoder); VaapiPrintFrames(decoder);
} }
@ -6652,14 +6764,19 @@ static void VdpauAdvanceFrame(void)
// need 4 frames for interlaced // need 4 frames for interlaced
filled = atomic_read(&decoder->SurfacesFilled); filled = atomic_read(&decoder->SurfacesFilled);
if (filled <= 1 + 2 * decoder->Interlaced) { if (filled <= 1 + 2 * decoder->Interlaced) {
static int last_warned_frame;
// keep use of last surface // keep use of last surface
++decoder->FramesDuped; ++decoder->FramesDuped;
decoder->DropNextFrame = 0; decoder->DropNextFrame = 0;
// FIXME: don't warn after stream start // FIXME: don't warn after stream start, don't warn during pause
if (last_warned_frame != decoder->FrameCounter) {
Warning(_ Warning(_
("video: display buffer empty, duping frame (%d/%d) %d\n"), ("video: display buffer empty, duping frame (%d/%d) %d\n"),
decoder->FramesDuped, decoder->FrameCounter, decoder->FramesDuped, decoder->FrameCounter,
atomic_read(&VideoPacketsFilled)); atomic_read(&VideoPacketsFilled));
}
last_warned_frame = decoder->FrameCounter;
if (!(decoder->FramesDisplayed % 300)) { if (!(decoder->FramesDisplayed % 300)) {
VdpauPrintFrames(decoder); VdpauPrintFrames(decoder);
} }