forked from KolibriOS/kolibrios
Fplay: update
git-svn-id: svn://kolibrios.org@6658 a494cfbc-eb01-0410-851d-a64ba20cac60
This commit is contained in:
parent
587cdc9c87
commit
47d330f439
@ -16,13 +16,11 @@ LIB_DIR:= $(SDK_DIR)/lib
|
|||||||
INCLUDES= -I. -I$(SDK_DIR)/sources/newlib/libc/include -I$(SDK_DIR)/sources/ffmpeg/ffmpeg-2.8
|
INCLUDES= -I. -I$(SDK_DIR)/sources/newlib/libc/include -I$(SDK_DIR)/sources/ffmpeg/ffmpeg-2.8
|
||||||
INCLUDES+=-I$(SDK_DIR)/sources/freetype/include -I$(SDK_DIR)/sources/vaapi/libva-1.6.2
|
INCLUDES+=-I$(SDK_DIR)/sources/freetype/include -I$(SDK_DIR)/sources/vaapi/libva-1.6.2
|
||||||
|
|
||||||
DEFINES= -DDEBUG=1 -DHAVE_VAAPI -DPACKAGE_NAME=\"Fplay-vaapi\"
|
DEFINES= -DDEBUG=1 -D_GNU_SOURCE -DHAVE_VAAPI -DPACKAGE_NAME=\"Fplay-vaapi\"
|
||||||
LIBS:= -lavdevice.dll -lavformat.dll -lavcodec.dll -lavutil.dll -lswscale.dll
|
LIBS:= -lavdevice.dll -lavformat.dll -lavcodec.dll -lavutil.dll -lswscale.dll
|
||||||
LIBS+= -lswresample.dll -lsound -lpixlib3 -lfreetype.dll -lva.dll -lgcc -lc.dll -lapp
|
LIBS+= -lswresample.dll -lsound -lpixlib3 -lfreetype.dll -lva.dll -lgcc -lc.dll
|
||||||
|
|
||||||
LIBPATH:= -L$(LIB_DIR) -L/home/autobuild/tools/win32/mingw32/lib
|
LDFLAGS = -static --subsystem native --stack 0x200000 -Map fplay.map -Tapp-dynamic.lds --image-base 0
|
||||||
|
|
||||||
LDFLAGS = -static -nostdlib --stack 0x200000 -Map fplay.map -T$(SDK_DIR)/sources/newlib/app.lds --image-base 0
|
|
||||||
|
|
||||||
SOURCES = opendial.asm \
|
SOURCES = opendial.asm \
|
||||||
audio.c \
|
audio.c \
|
||||||
@ -46,7 +44,7 @@ OBJECTS = $(patsubst %.asm, %.o, $(patsubst %.c, %.o, $(SOURCES)))
|
|||||||
all:$(NAME)
|
all:$(NAME)
|
||||||
|
|
||||||
$(NAME): $(OBJECTS) Makefile
|
$(NAME): $(OBJECTS) Makefile
|
||||||
$(LD) $(LDFLAGS) $(LIBPATH) --subsystem native -o $@ $(OBJECTS) $(LIBS)
|
$(LD) $(LDFLAGS) -o $@ $(OBJECTS) $(LIBS)
|
||||||
kos32-objcopy $@ -O binary
|
kos32-objcopy $@ -O binary
|
||||||
|
|
||||||
%.o : %.c Makefile
|
%.o : %.c Makefile
|
||||||
|
@ -14,6 +14,27 @@
|
|||||||
#include "sound.h"
|
#include "sound.h"
|
||||||
#include "fplay.h"
|
#include "fplay.h"
|
||||||
|
|
||||||
|
static struct decoder ffmpeg_decoder;
|
||||||
|
static struct decoder* init_ffmpeg_decoder(vst_t *vst);
|
||||||
|
|
||||||
|
static decoder_init_fn* decoders[] = {
|
||||||
|
init_va_decoder,
|
||||||
|
init_ffmpeg_decoder,
|
||||||
|
NULL
|
||||||
|
};
|
||||||
|
|
||||||
|
static void fini_ffmpeg_decoder(vst_t *vst)
|
||||||
|
{
|
||||||
|
av_frame_free(&vst->decoder->Frame);
|
||||||
|
|
||||||
|
for(int i = 0; i < vst->decoder->nframes; i++)
|
||||||
|
{
|
||||||
|
vframe_t *vframe;
|
||||||
|
vframe = &vst->decoder->vframes[i];
|
||||||
|
avpicture_free(&vframe->picture);
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
static struct decoder* init_ffmpeg_decoder(vst_t *vst)
|
static struct decoder* init_ffmpeg_decoder(vst_t *vst)
|
||||||
{
|
{
|
||||||
AVCodecContext *vCtx = vst->vCtx;
|
AVCodecContext *vCtx = vst->vCtx;
|
||||||
@ -21,9 +42,7 @@ static struct decoder* init_ffmpeg_decoder(vst_t *vst)
|
|||||||
vframe_t *vframe;
|
vframe_t *vframe;
|
||||||
int i, ret;
|
int i, ret;
|
||||||
|
|
||||||
decoder = calloc(1, sizeof(struct decoder));
|
decoder = &ffmpeg_decoder;
|
||||||
if(decoder == NULL)
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
decoder->Frame = av_frame_alloc();
|
decoder->Frame = av_frame_alloc();
|
||||||
if(decoder->Frame == NULL)
|
if(decoder->Frame == NULL)
|
||||||
@ -42,8 +61,6 @@ static struct decoder* init_ffmpeg_decoder(vst_t *vst)
|
|||||||
|
|
||||||
vframe->format = vCtx->pix_fmt;
|
vframe->format = vCtx->pix_fmt;
|
||||||
vframe->index = i;
|
vframe->index = i;
|
||||||
vframe->pts = 0;
|
|
||||||
vframe->ready = 0;
|
|
||||||
list_add_tail(&vframe->list, &vst->input_list);
|
list_add_tail(&vframe->list, &vst->input_list);
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -59,7 +76,8 @@ static struct decoder* init_ffmpeg_decoder(vst_t *vst)
|
|||||||
decoder->width = vCtx->width;
|
decoder->width = vCtx->width;
|
||||||
decoder->height = vCtx->height;
|
decoder->height = vCtx->height;
|
||||||
decoder->codec_id = vCtx->codec_id;
|
decoder->codec_id = vCtx->codec_id;
|
||||||
|
decoder->profile = vCtx->profile;
|
||||||
|
decoder->fini = fini_ffmpeg_decoder;
|
||||||
return decoder;
|
return decoder;
|
||||||
|
|
||||||
err_1:
|
err_1:
|
||||||
@ -68,60 +86,10 @@ err_1:
|
|||||||
vframe = &decoder->vframes[i];
|
vframe = &decoder->vframes[i];
|
||||||
avpicture_free(&vframe->picture);
|
avpicture_free(&vframe->picture);
|
||||||
};
|
};
|
||||||
av_frame_free(&decoder->Frame);
|
|
||||||
err_0:
|
err_0:
|
||||||
free(decoder);
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
int init_video_decoder(vst_t *vst)
|
|
||||||
{
|
|
||||||
AVCodecContext *vCtx = vst->vCtx;
|
|
||||||
|
|
||||||
vst->vCodec = avcodec_find_decoder(vCtx->codec_id);
|
|
||||||
|
|
||||||
if(vst->vCodec == NULL)
|
|
||||||
{
|
|
||||||
printf("Unsupported codec with id %d for input stream %d\n",
|
|
||||||
vst->vCtx->codec_id, vst->vStream);
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
vst->decoder = va_init_decoder(vst);
|
|
||||||
if(vst->decoder == NULL)
|
|
||||||
vst->decoder = init_ffmpeg_decoder(vst);
|
|
||||||
|
|
||||||
if(vst->decoder != NULL)
|
|
||||||
{
|
|
||||||
printf("%dx%d %s %s%s decoder\n",
|
|
||||||
vst->decoder->width, vst->decoder->height,
|
|
||||||
av_get_pix_fmt_name(vst->decoder->pix_fmt),
|
|
||||||
vst->decoder->is_hw == 0 ? "ffmpeg ":"vaapi ",
|
|
||||||
vst->decoder->name);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
};
|
|
||||||
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void fini_video_decoder(vst_t *vst)
|
|
||||||
{
|
|
||||||
avcodec_close(vst->vCtx);
|
|
||||||
|
|
||||||
if(vst->decoder->is_hw != 0)
|
|
||||||
return;
|
|
||||||
|
|
||||||
for(int i = 0; i < vst->decoder->nframes; i++)
|
|
||||||
{
|
|
||||||
vframe_t *vframe;
|
|
||||||
vframe = &vst->decoder->vframes[i];
|
|
||||||
avpicture_free(&vframe->picture);
|
|
||||||
};
|
|
||||||
av_frame_free(&vst->decoder->Frame);
|
|
||||||
free(vst->decoder);
|
|
||||||
};
|
|
||||||
|
|
||||||
static vframe_t *get_input_frame(vst_t *vst)
|
static vframe_t *get_input_frame(vst_t *vst)
|
||||||
{
|
{
|
||||||
vframe_t *vframe = NULL;
|
vframe_t *vframe = NULL;
|
||||||
@ -230,3 +198,36 @@ int decode_video(vst_t* vst)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int init_video_decoder(vst_t *vst)
|
||||||
|
{
|
||||||
|
decoder_init_fn **init_fn;
|
||||||
|
AVCodecContext *vCtx = vst->vCtx;
|
||||||
|
int i;
|
||||||
|
|
||||||
|
vst->vCodec = avcodec_find_decoder(vCtx->codec_id);
|
||||||
|
|
||||||
|
if(vst->vCodec == NULL)
|
||||||
|
{
|
||||||
|
printf("Unsupported codec with id %d for input stream %d\n",
|
||||||
|
vst->vCtx->codec_id, vst->vStream);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
for(init_fn = decoders; init_fn != NULL; init_fn++)
|
||||||
|
{
|
||||||
|
vst->decoder = (*init_fn)(vst);
|
||||||
|
if(vst->decoder != NULL)
|
||||||
|
{
|
||||||
|
printf("%dx%d %s %s%s decoder\n",
|
||||||
|
vst->decoder->width, vst->decoder->height,
|
||||||
|
av_get_pix_fmt_name(vst->decoder->pix_fmt),
|
||||||
|
vst->decoder->is_hw == 0 ? "ffmpeg ":"vaapi ",
|
||||||
|
vst->decoder->name);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
@ -30,8 +30,7 @@ int64_t rewind_pos;
|
|||||||
|
|
||||||
int64_t stream_duration;
|
int64_t stream_duration;
|
||||||
|
|
||||||
int threads_running = DECODER_THREAD;
|
volatile int threads_running = DECODER_THREAD;
|
||||||
|
|
||||||
|
|
||||||
int main( int argc, char *argv[])
|
int main( int argc, char *argv[])
|
||||||
{
|
{
|
||||||
@ -113,7 +112,6 @@ int main( int argc, char *argv[])
|
|||||||
return -1; // Didn't find a video stream
|
return -1; // Didn't find a video stream
|
||||||
};
|
};
|
||||||
|
|
||||||
// __asm__ __volatile__("int3");
|
|
||||||
|
|
||||||
INIT_LIST_HEAD(&vst.input_list);
|
INIT_LIST_HEAD(&vst.input_list);
|
||||||
INIT_LIST_HEAD(&vst.output_list);
|
INIT_LIST_HEAD(&vst.output_list);
|
||||||
@ -127,6 +125,8 @@ int main( int argc, char *argv[])
|
|||||||
vst.vCtx = vst.fCtx->streams[vst.vStream]->codec;
|
vst.vCtx = vst.fCtx->streams[vst.vStream]->codec;
|
||||||
vst.aCtx = vst.fCtx->streams[vst.aStream]->codec;
|
vst.aCtx = vst.fCtx->streams[vst.aStream]->codec;
|
||||||
|
|
||||||
|
// __asm__ __volatile__("int3");
|
||||||
|
|
||||||
if(init_video_decoder(&vst) != 0 )
|
if(init_video_decoder(&vst) != 0 )
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
@ -193,7 +193,9 @@ int main( int argc, char *argv[])
|
|||||||
if(astream.lock.handle)
|
if(astream.lock.handle)
|
||||||
mutex_destroy(&astream.lock);
|
mutex_destroy(&astream.lock);
|
||||||
|
|
||||||
fini_video_decoder(&vst);
|
vst.decoder->fini(&vst);
|
||||||
|
avcodec_close(vst.vCtx);
|
||||||
|
|
||||||
mutex_destroy(&vst.q_video.lock);
|
mutex_destroy(&vst.q_video.lock);
|
||||||
mutex_destroy(&vst.q_audio.lock);
|
mutex_destroy(&vst.q_audio.lock);
|
||||||
mutex_destroy(&vst.decoder_lock);
|
mutex_destroy(&vst.decoder_lock);
|
||||||
|
@ -114,18 +114,23 @@ struct decoder
|
|||||||
{
|
{
|
||||||
const char *name;
|
const char *name;
|
||||||
enum AVCodecID codec_id;
|
enum AVCodecID codec_id;
|
||||||
|
int profile;
|
||||||
enum AVPixelFormat pix_fmt;
|
enum AVPixelFormat pix_fmt;
|
||||||
int width;
|
int width;
|
||||||
int height;
|
int height;
|
||||||
AVFrame *Frame;
|
AVFrame *Frame;
|
||||||
vframe_t *active_frame;
|
vframe_t *active_frame;
|
||||||
void *hwctx;
|
|
||||||
int is_hw:1;
|
|
||||||
int frame_reorder:1;
|
|
||||||
int nframes;
|
|
||||||
vframe_t vframes[16];
|
vframe_t vframes[16];
|
||||||
|
int nframes;
|
||||||
|
int is_hw:1;
|
||||||
|
int has_surfaces:1;
|
||||||
|
int frame_reorder:1;
|
||||||
|
void (*fini)(vst_t *vst);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
typedef struct decoder* decoder_init_fn(vst_t *vst);
|
||||||
|
struct decoder* init_va_decoder(vst_t *vst);
|
||||||
|
|
||||||
struct vstate
|
struct vstate
|
||||||
{
|
{
|
||||||
AVFormatContext *fCtx; /* format context */
|
AVFormatContext *fCtx; /* format context */
|
||||||
@ -133,8 +138,6 @@ struct vstate
|
|||||||
AVCodecContext *aCtx; /* audio decoder context */
|
AVCodecContext *aCtx; /* audio decoder context */
|
||||||
AVCodec *vCodec; /* video codec */
|
AVCodec *vCodec; /* video codec */
|
||||||
AVCodec *aCodec; /* audio codec */
|
AVCodec *aCodec; /* audio codec */
|
||||||
enum AVCodecID codec_id;
|
|
||||||
int codec_profile;
|
|
||||||
char *input_file;
|
char *input_file;
|
||||||
char *input_name;
|
char *input_name;
|
||||||
int vStream; /* video stream index */
|
int vStream; /* video stream index */
|
||||||
@ -152,6 +155,7 @@ struct vstate
|
|||||||
mutex_t output_lock;
|
mutex_t output_lock;
|
||||||
struct list_head input_list;
|
struct list_head input_list;
|
||||||
struct list_head output_list;
|
struct list_head output_list;
|
||||||
|
struct list_head destructor_list;
|
||||||
|
|
||||||
struct decoder *decoder;
|
struct decoder *decoder;
|
||||||
int snd_format;
|
int snd_format;
|
||||||
@ -168,7 +172,7 @@ struct vstate
|
|||||||
#define AUDIO_THREAD 2
|
#define AUDIO_THREAD 2
|
||||||
#define VIDEO_THREAD 4
|
#define VIDEO_THREAD 4
|
||||||
|
|
||||||
extern int threads_running;
|
extern volatile int threads_running;
|
||||||
extern astream_t astream;
|
extern astream_t astream;
|
||||||
|
|
||||||
render_t *create_render(vst_t *vst, window_t *win, uint32_t flags);
|
render_t *create_render(vst_t *vst, window_t *win, uint32_t flags);
|
||||||
@ -217,3 +221,4 @@ char *get_moviefile();
|
|||||||
#define LEAVE() printf("leave %s\n",__FUNCTION__)
|
#define LEAVE() printf("leave %s\n",__FUNCTION__)
|
||||||
#define FAIL() printf("fail %s\n",__FUNCTION__)
|
#define FAIL() printf("fail %s\n",__FUNCTION__)
|
||||||
|
|
||||||
|
|
||||||
|
@ -1,8 +1,9 @@
|
|||||||
|
#include <sys/types.h>
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <libavcodec/avcodec.h>
|
#include <libavcodec/avcodec.h>
|
||||||
#include <libavformat/avformat.h>
|
#include <libavformat/avformat.h>
|
||||||
#include <libswscale/swscale.h>
|
#include <libswscale/swscale.h>
|
||||||
|
#include <unistd.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
#include "winlib/winlib.h"
|
#include "winlib/winlib.h"
|
||||||
|
@ -37,11 +37,19 @@ struct hw_profile
|
|||||||
#undef ARRAY_ELEMS
|
#undef ARRAY_ELEMS
|
||||||
#define ARRAY_ELEMS(a) (sizeof(a) / sizeof((a)[0]))
|
#define ARRAY_ELEMS(a) (sizeof(a) / sizeof((a)[0]))
|
||||||
|
|
||||||
|
struct va_decoder
|
||||||
|
{
|
||||||
|
struct decoder decoder;
|
||||||
|
VADisplay dpy;
|
||||||
|
void *hwctx;
|
||||||
|
VASurfaceID v_surface_id[16];
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct va_decoder va_decoder;
|
||||||
|
|
||||||
static int drm_fd = 0;
|
static int drm_fd = 0;
|
||||||
static struct vaapi_context *v_context;
|
static struct vaapi_context *v_context;
|
||||||
|
|
||||||
static VASurfaceID v_surface_id[16];
|
|
||||||
|
|
||||||
#define HAS_HEVC VA_CHECK_VERSION(0, 38, 0)
|
#define HAS_HEVC VA_CHECK_VERSION(0, 38, 0)
|
||||||
#define HAS_VP9 (VA_CHECK_VERSION(0, 38, 1) && defined(FF_PROFILE_VP9_0))
|
#define HAS_VP9 (VA_CHECK_VERSION(0, 38, 1) && defined(FF_PROFILE_VP9_0))
|
||||||
|
|
||||||
@ -281,6 +289,7 @@ static int vaapi_init_decoder(vst_t *vst,VAProfile profile,
|
|||||||
unsigned int picture_height)
|
unsigned int picture_height)
|
||||||
{
|
{
|
||||||
struct vaapi_context* const vaapi = v_context;
|
struct vaapi_context* const vaapi = v_context;
|
||||||
|
struct va_decoder *hw_decoder = (struct va_decoder*)vst->decoder;
|
||||||
VAConfigAttrib attrib;
|
VAConfigAttrib attrib;
|
||||||
VAConfigID config_id = VA_INVALID_ID;
|
VAConfigID config_id = VA_INVALID_ID;
|
||||||
VAContextID context_id = VA_INVALID_ID;
|
VAContextID context_id = VA_INVALID_ID;
|
||||||
@ -309,9 +318,19 @@ ENTER();
|
|||||||
return -1;
|
return -1;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if (vaapi->context_id != VA_INVALID_ID)
|
||||||
|
vaDestroyContext(vaapi->display, vaapi->context_id);
|
||||||
|
|
||||||
|
if (hw_decoder->decoder.has_surfaces)
|
||||||
|
{
|
||||||
|
vaDestroySurfaces(vaapi->display,hw_decoder->v_surface_id,hw_decoder->decoder.nframes);
|
||||||
|
hw_decoder->decoder.has_surfaces = 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (vaapi->config_id != VA_INVALID_ID)
|
if (vaapi->config_id != VA_INVALID_ID)
|
||||||
vaDestroyConfig(vaapi->display, vaapi->config_id);
|
vaDestroyConfig(vaapi->display, vaapi->config_id);
|
||||||
|
|
||||||
|
|
||||||
attrib.type = VAConfigAttribRTFormat;
|
attrib.type = VAConfigAttribRTFormat;
|
||||||
|
|
||||||
printf("vaGetConfigAttributes\n");
|
printf("vaGetConfigAttributes\n");
|
||||||
@ -341,17 +360,20 @@ ENTER();
|
|||||||
|
|
||||||
printf("vaCreateSurfaces %dx%d\n",picture_width,picture_height);
|
printf("vaCreateSurfaces %dx%d\n",picture_width,picture_height);
|
||||||
status = vaCreateSurfaces(vaapi->display, VA_RT_FORMAT_YUV420, picture_width, picture_height,
|
status = vaCreateSurfaces(vaapi->display, VA_RT_FORMAT_YUV420, picture_width, picture_height,
|
||||||
v_surface_id,vst->decoder->nframes,NULL,0);
|
hw_decoder->v_surface_id,hw_decoder->decoder.nframes,NULL,0);
|
||||||
if (!vaapi_check_status(status, "vaCreateSurfaces()"))
|
if (!vaapi_check_status(status, "vaCreateSurfaces()"))
|
||||||
{
|
{
|
||||||
FAIL();
|
FAIL();
|
||||||
return -1;
|
return -1;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
hw_decoder->decoder.has_surfaces = 1;
|
||||||
|
|
||||||
{
|
{
|
||||||
VAImage vaimage;
|
VAImage vaimage;
|
||||||
VABufferInfo info = {0};
|
VABufferInfo info = {0};
|
||||||
|
|
||||||
vaDeriveImage(vaapi->display,v_surface_id[0],&vaimage);
|
vaDeriveImage(vaapi->display,hw_decoder->v_surface_id[0],&vaimage);
|
||||||
printf("vaDeriveImage: %x fourcc: %x\n"
|
printf("vaDeriveImage: %x fourcc: %x\n"
|
||||||
"offset0: %d pitch0: %d\n"
|
"offset0: %d pitch0: %d\n"
|
||||||
"offset1: %d pitch1: %d\n"
|
"offset1: %d pitch1: %d\n"
|
||||||
@ -376,7 +398,7 @@ ENTER();
|
|||||||
status = vaCreateContext(vaapi->display, config_id,
|
status = vaCreateContext(vaapi->display, config_id,
|
||||||
picture_width, picture_height,
|
picture_width, picture_height,
|
||||||
VA_PROGRESSIVE,
|
VA_PROGRESSIVE,
|
||||||
v_surface_id, vst->decoder->nframes,
|
hw_decoder->v_surface_id, vst->decoder->nframes,
|
||||||
&context_id);
|
&context_id);
|
||||||
if (!vaapi_check_status(status, "vaCreateContext()"))
|
if (!vaapi_check_status(status, "vaCreateContext()"))
|
||||||
{
|
{
|
||||||
@ -395,24 +417,19 @@ static enum PixelFormat get_format(struct AVCodecContext *avctx,
|
|||||||
const enum AVPixelFormat *fmt)
|
const enum AVPixelFormat *fmt)
|
||||||
{
|
{
|
||||||
vst_t *vst = (vst_t*)avctx->opaque;
|
vst_t *vst = (vst_t*)avctx->opaque;
|
||||||
|
struct va_decoder* hw_decoder = (struct va_decoder*)vst->decoder;
|
||||||
|
struct decoder* decoder = &hw_decoder->decoder;
|
||||||
VAProfile profile = avctx->profile;
|
VAProfile profile = avctx->profile;
|
||||||
enum AVCodecID codec = avctx->codec_id;
|
enum AVCodecID codec = avctx->codec_id;
|
||||||
|
|
||||||
if (codec == AV_CODEC_ID_H264)
|
if(avctx->hwaccel_context != NULL)
|
||||||
{
|
{
|
||||||
if(profile == FF_PROFILE_H264_BASELINE)
|
if(decoder->codec_id != avctx->codec_id ||
|
||||||
profile = FF_PROFILE_H264_CONSTRAINED_BASELINE;
|
decoder->profile != avctx->profile)
|
||||||
};
|
|
||||||
|
|
||||||
if(avctx->hwaccel_context != NULL &&
|
|
||||||
(vst->codec_id != codec ||
|
|
||||||
vst->codec_profile != profile))
|
|
||||||
{
|
{
|
||||||
struct decoder* decoder = vst->decoder;
|
|
||||||
|
|
||||||
printf("\n%s codec changed!!!\n"
|
printf("\n%s codec changed!!!\n"
|
||||||
"old id %d profile %x new id %d profile %x\n",
|
"old id %d profile %x new id %d profile %x\n",
|
||||||
__FUNCTION__, vst->codec_id, vst->codec_profile,
|
__FUNCTION__, decoder->codec_id, decoder->profile,
|
||||||
codec, profile);
|
codec, profile);
|
||||||
|
|
||||||
for(int i = 0; i < decoder->nframes; i++)
|
for(int i = 0; i < decoder->nframes; i++)
|
||||||
@ -421,6 +438,15 @@ static enum PixelFormat get_format(struct AVCodecContext *avctx,
|
|||||||
vframe->format = AV_PIX_FMT_NONE;
|
vframe->format = AV_PIX_FMT_NONE;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
return AV_PIX_FMT_VAAPI_VLD;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (codec == AV_CODEC_ID_H264)
|
||||||
|
{
|
||||||
|
if(profile == FF_PROFILE_H264_BASELINE)
|
||||||
|
profile = FF_PROFILE_H264_CONSTRAINED_BASELINE;
|
||||||
|
};
|
||||||
|
|
||||||
printf("\n%s codec %d profile %x\n", __FUNCTION__,avctx->codec_id, avctx->profile);
|
printf("\n%s codec %d profile %x\n", __FUNCTION__,avctx->codec_id, avctx->profile);
|
||||||
|
|
||||||
@ -438,8 +464,6 @@ static enum PixelFormat get_format(struct AVCodecContext *avctx,
|
|||||||
if (vaapi_init_decoder(vst, profile, VAEntrypointVLD, avctx->width, avctx->height) == 0)
|
if (vaapi_init_decoder(vst, profile, VAEntrypointVLD, avctx->width, avctx->height) == 0)
|
||||||
{
|
{
|
||||||
avctx->hwaccel_context = v_context;
|
avctx->hwaccel_context = v_context;
|
||||||
vst->codec_id = codec;
|
|
||||||
vst->codec_profile = profile;
|
|
||||||
printf("%s format: %x\n",__FUNCTION__, fmt[i]);
|
printf("%s format: %x\n",__FUNCTION__, fmt[i]);
|
||||||
return fmt[i];
|
return fmt[i];
|
||||||
}
|
}
|
||||||
@ -466,9 +490,10 @@ static int get_buffer2(AVCodecContext *avctx, AVFrame *pic, int flags)
|
|||||||
{
|
{
|
||||||
static struct av_surface avsurface;
|
static struct av_surface avsurface;
|
||||||
vst_t *vst = (vst_t*)avctx->opaque;
|
vst_t *vst = (vst_t*)avctx->opaque;
|
||||||
|
struct va_decoder* hw_decoder = (struct va_decoder*)vst->decoder;
|
||||||
void *surface;
|
void *surface;
|
||||||
|
|
||||||
surface = (void *)(uintptr_t)v_surface_id[vst->decoder->active_frame->index];
|
surface = (void *)(uintptr_t)hw_decoder->v_surface_id[vst->decoder->active_frame->index];
|
||||||
|
|
||||||
pic->data[3] = surface;
|
pic->data[3] = surface;
|
||||||
|
|
||||||
@ -547,18 +572,25 @@ enum wl_drm_format {
|
|||||||
void va_create_planar(vst_t *vst, vframe_t *vframe)
|
void va_create_planar(vst_t *vst, vframe_t *vframe)
|
||||||
{
|
{
|
||||||
struct vaapi_context* const vaapi = v_context;
|
struct vaapi_context* const vaapi = v_context;
|
||||||
|
struct va_decoder* hw_decoder = (struct va_decoder*)vst->decoder;
|
||||||
VABufferInfo info = {0};
|
VABufferInfo info = {0};
|
||||||
|
|
||||||
VAImage vaimage;
|
VAImage vaimage;
|
||||||
VAStatus status;
|
VAStatus status;
|
||||||
planar_t *planar;
|
planar_t *planar;
|
||||||
|
|
||||||
vaSyncSurface(vaapi->display,v_surface_id[vframe->index]);
|
vaSyncSurface(vaapi->display,hw_decoder->v_surface_id[vframe->index]);
|
||||||
|
|
||||||
if(vframe->format != AV_PIX_FMT_NONE)
|
if(vframe->format != AV_PIX_FMT_NONE)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
status = vaDeriveImage(vaapi->display,v_surface_id[vframe->index],&vaimage);
|
if(vframe->planar != NULL)
|
||||||
|
{
|
||||||
|
pxDestroyPlanar(vframe->planar);
|
||||||
|
vframe->planar = NULL;
|
||||||
|
};
|
||||||
|
|
||||||
|
status = vaDeriveImage(vaapi->display,hw_decoder->v_surface_id[vframe->index],&vaimage);
|
||||||
if (!vaapi_check_status(status, "vaDeriveImage()"))
|
if (!vaapi_check_status(status, "vaDeriveImage()"))
|
||||||
{
|
{
|
||||||
FAIL();
|
FAIL();
|
||||||
@ -687,29 +719,57 @@ err_0:
|
|||||||
return profile;
|
return profile;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct decoder* va_init_decoder(vst_t *vst)
|
static void fini_va_decoder(vst_t *vst)
|
||||||
|
{
|
||||||
|
struct vaapi_context* const vaapi = v_context;
|
||||||
|
struct va_decoder *hw_decoder = (struct va_decoder*)vst->decoder;
|
||||||
|
ENTER();
|
||||||
|
for(int i = 0; i < hw_decoder->decoder.nframes; i++)
|
||||||
|
{
|
||||||
|
vframe_t *vframe = &hw_decoder->decoder.vframes[i];
|
||||||
|
if(vframe->planar != NULL)
|
||||||
|
{
|
||||||
|
printf("destroy planar %d\n", i);
|
||||||
|
pxDestroyPlanar(vframe->planar);
|
||||||
|
vframe->planar = NULL;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
av_frame_free(&hw_decoder->decoder.Frame);
|
||||||
|
|
||||||
|
if (vaapi->context_id != VA_INVALID_ID)
|
||||||
|
vaDestroyContext(vaapi->display, vaapi->context_id);
|
||||||
|
|
||||||
|
if (hw_decoder->decoder.has_surfaces)
|
||||||
|
vaDestroySurfaces(vaapi->display,hw_decoder->v_surface_id,hw_decoder->decoder.nframes);
|
||||||
|
|
||||||
|
if (vaapi->config_id != VA_INVALID_ID)
|
||||||
|
vaDestroyConfig(vaapi->display, vaapi->config_id);
|
||||||
|
|
||||||
|
vaTerminate(hw_decoder->dpy);
|
||||||
|
LEAVE();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
struct decoder* init_va_decoder(vst_t *vst)
|
||||||
{
|
{
|
||||||
AVCodecContext *vCtx = vst->vCtx;
|
AVCodecContext *vCtx = vst->vCtx;
|
||||||
struct decoder *decoder;
|
struct va_decoder *hw_decoder = &va_decoder;
|
||||||
VADisplay dpy;
|
struct decoder *decoder = &hw_decoder->decoder;
|
||||||
|
|
||||||
drm_fd = get_service("DISPLAY");
|
drm_fd = get_service("DISPLAY");
|
||||||
if (drm_fd == 0)
|
if (drm_fd == 0)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
dpy = vaGetDisplayDRM(drm_fd);
|
hw_decoder->dpy = vaGetDisplayDRM(drm_fd);
|
||||||
if (dpy == NULL)
|
if (hw_decoder->dpy == NULL)
|
||||||
goto err_0;
|
goto err_0;
|
||||||
|
|
||||||
decoder = calloc(1, sizeof(struct decoder));
|
hw_decoder->hwctx = vaapi_init(hw_decoder->dpy);
|
||||||
if(decoder == NULL)
|
if(hw_decoder->hwctx == NULL)
|
||||||
goto err_0;
|
|
||||||
|
|
||||||
decoder->hwctx = vaapi_init(dpy);
|
|
||||||
if(decoder->hwctx == NULL)
|
|
||||||
goto err_1;
|
goto err_1;
|
||||||
|
|
||||||
if(get_profile(dpy, vCtx->codec_id) == VAProfileNone)
|
if(get_profile(hw_decoder->dpy, vCtx->codec_id) == VAProfileNone)
|
||||||
goto err_1;
|
goto err_1;
|
||||||
|
|
||||||
decoder->Frame = av_frame_alloc();
|
decoder->Frame = av_frame_alloc();
|
||||||
@ -728,8 +788,6 @@ struct decoder* va_init_decoder(vst_t *vst)
|
|||||||
vframe->format = AV_PIX_FMT_NONE;
|
vframe->format = AV_PIX_FMT_NONE;
|
||||||
vframe->is_hw_pic = 1;
|
vframe->is_hw_pic = 1;
|
||||||
vframe->index = i;
|
vframe->index = i;
|
||||||
vframe->pts = 0;
|
|
||||||
vframe->ready = 0;
|
|
||||||
list_add_tail(&vframe->list, &vst->input_list);
|
list_add_tail(&vframe->list, &vst->input_list);
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -747,19 +805,20 @@ struct decoder* va_init_decoder(vst_t *vst)
|
|||||||
|
|
||||||
decoder->name = vst->vCodec->name;
|
decoder->name = vst->vCodec->name;
|
||||||
decoder->codec_id = vCtx->codec_id;
|
decoder->codec_id = vCtx->codec_id;
|
||||||
|
decoder->profile = vCtx->profile;
|
||||||
decoder->pix_fmt = vCtx->pix_fmt;
|
decoder->pix_fmt = vCtx->pix_fmt;
|
||||||
decoder->width = vCtx->width;
|
decoder->width = vCtx->width;
|
||||||
decoder->height = vCtx->height;
|
decoder->height = vCtx->height;
|
||||||
decoder->is_hw = 1;
|
decoder->is_hw = 1;
|
||||||
decoder->frame_reorder = 1;
|
decoder->frame_reorder = 1;
|
||||||
|
decoder->fini = fini_va_decoder;
|
||||||
|
|
||||||
return decoder;
|
return (struct decoder*)decoder;
|
||||||
|
|
||||||
err_2:
|
err_2:
|
||||||
av_frame_free(&decoder->Frame);
|
av_frame_free(&decoder->Frame);
|
||||||
err_1:
|
err_1:
|
||||||
vaTerminate(dpy);
|
vaTerminate(hw_decoder->dpy);
|
||||||
free(decoder);
|
|
||||||
err_0:
|
err_0:
|
||||||
drm_fd = 0;
|
drm_fd = 0;
|
||||||
return NULL;
|
return NULL;
|
||||||
|
@ -134,7 +134,7 @@ int draw_frame(window_t *win)
|
|||||||
int frame_proc(ctrl_t *ctrl, uint32_t msg, uint32_t arg1, uint32_t arg2)
|
int frame_proc(ctrl_t *ctrl, uint32_t msg, uint32_t arg1, uint32_t arg2)
|
||||||
{
|
{
|
||||||
static pos_t spos;
|
static pos_t spos;
|
||||||
static track_mode;
|
static int track_mode;
|
||||||
|
|
||||||
uint32_t cursor;
|
uint32_t cursor;
|
||||||
ctrl_t *child;
|
ctrl_t *child;
|
||||||
|
Loading…
Reference in New Issue
Block a user