Feature: add FFMessageQueue

pull/221/head
xufuji456 2 years ago
parent 6ce7f8e6b3
commit acc42e49d5
  1. 141
      app/src/main/cpp/ffplayer/FFMessageQueue.cpp
  2. 96
      app/src/main/cpp/ffplayer/FFMessageQueue.h
  3. 91
      app/src/main/cpp/ffplayer/ffplay_define.h
  4. 2
      app/src/main/cpp/ffplayer/queue/FrameQueue.h

@ -1,65 +1,8 @@
//
// Created by xu fulong on 2022/9/24.
//
#ifndef FFMSG_QUEUE_H #include "FFMessageQueue.h"
#define FFMSG_QUEUE_H
#include <mutex>
#include <libavutil/mem.h>
/**************** msg define begin ***************/
#define FFP_MSG_FLUSH 0
#define FFP_MSG_ERROR 100
#define FFP_MSG_PREPARED 200
#define FFP_MSG_COMPLETED 300
#define FFP_MSG_VIDEO_SIZE_CHANGED 400
#define FFP_MSG_SAR_CHANGED 401
#define FFP_MSG_VIDEO_RENDERING_START 402
#define FFP_MSG_AUDIO_RENDERING_START 403
#define FFP_MSG_VIDEO_ROTATION_CHANGED 404
#define FFP_MSG_AUDIO_DECODED_START 405
#define FFP_MSG_VIDEO_DECODED_START 406
#define FFP_MSG_OPEN_INPUT 407
#define FFP_MSG_FIND_STREAM_INFO 408
#define FFP_MSG_COMPONENT_OPEN 409
#define FFP_MSG_VIDEO_SEEK_RENDERING_START 410
#define FFP_MSG_AUDIO_SEEK_RENDERING_START 411
#define FFP_MSG_BUFFERING_START 500
#define FFP_MSG_BUFFERING_END 501
#define FFP_MSG_BUFFERING_UPDATE 502
#define FFP_MSG_BUFFERING_BYTES_UPDATE 503
#define FFP_MSG_BUFFERING_TIME_UPDATE 504
#define FFP_MSG_SEEK_COMPLETE 600
#define FFP_MSG_PLAYBACK_STATE_CHANGED 700
#define FFP_MSG_TIMED_TEXT 800
#define FFP_MSG_VIDEO_DECODER_OPEN 900
#define FFP_REQ_START 1001
#define FFP_REQ_PAUSE 1002
#define FFP_REQ_SEEK 1003
/**************** msg define end *****************/
typedef struct AVMessage {
int what;
int arg1;
int arg2;
void *obj;
void (*free_l)(void *obj);
struct AVMessage *next;
} AVMessage;
typedef struct MessageQueue {
AVMessage *first_msg, *last_msg;
int nb_messages;
int abort_request;
std::mutex mutex;
std::condition_variable cond;
AVMessage *recycle_msg;
int recycle_count;
int alloc_count;
} MessageQueue;
inline static void msg_free(AVMessage *msg) { inline static void msg_free(AVMessage *msg) {
if (!msg || !msg->obj) if (!msg || !msg->obj)
@ -113,36 +56,22 @@ inline static void msg_init_msg(AVMessage *msg) {
memset(msg, 0, sizeof(AVMessage)); memset(msg, 0, sizeof(AVMessage));
} }
inline static void msg_queue_put_notify1(MessageQueue *q, int what) { void FFMessageQueue::init() {
AVMessage msg; memset(q, 0, sizeof(MessageQueue));
msg_init_msg(&msg); q->abort_request = 1;
msg.what = what;
msg_queue_put(q, &msg);
} }
inline static void msg_queue_put_notify2(MessageQueue *q, int what, int arg1) { void FFMessageQueue::start() {
AVMessage msg; std::lock_guard<std::mutex> lock(q->mutex);
msg_init_msg(&msg); q->abort_request = 0;
msg.what = what;
msg.arg1 = arg1;
msg_queue_put(q, &msg);
}
inline static void msg_queue_put_notify3(MessageQueue *q, int what, int arg1, int arg2) {
AVMessage msg; AVMessage msg;
msg_init_msg(&msg); msg_init_msg(&msg);
msg.what = what; msg.what = FFP_MSG_FLUSH;
msg.arg1 = arg1; msg_queue_put_private(q, &msg);
msg.arg2 = arg2;
msg_queue_put(q, &msg);
}
inline static void msg_queue_init(MessageQueue *q) {
memset(q, 0, sizeof(MessageQueue));
q->abort_request = 1;
} }
inline static void msg_queue_flush(MessageQueue *q) { void FFMessageQueue::flush() {
AVMessage *msg, *msg1; AVMessage *msg, *msg1;
std::lock_guard<std::mutex> lock(q->mutex); std::lock_guard<std::mutex> lock(q->mutex);
@ -156,23 +85,31 @@ inline static void msg_queue_flush(MessageQueue *q) {
q->nb_messages = 0; q->nb_messages = 0;
} }
inline static void msg_queue_abort(MessageQueue *q) { void FFMessageQueue::sendMessage1(int what) {
std::unique_lock<std::mutex> lock(q->mutex); AVMessage msg;
q->abort_request = 1; msg_init_msg(&msg);
q->cond.notify_all(); msg.what = what;
msg_queue_put(q, &msg);
} }
inline static void msg_queue_start(MessageQueue *q) { void FFMessageQueue::sendMessage2(int what, int arg1) {
std::lock_guard<std::mutex> lock(q->mutex); AVMessage msg;
q->abort_request = 0; msg_init_msg(&msg);
msg.what = what;
msg.arg1 = arg1;
msg_queue_put(q, &msg);
}
void FFMessageQueue::sendMessage3(int what, int arg1, int arg2) {
AVMessage msg; AVMessage msg;
msg_init_msg(&msg); msg_init_msg(&msg);
msg.what = FFP_MSG_FLUSH; msg.what = what;
msg_queue_put_private(q, &msg); msg.arg1 = arg1;
msg.arg2 = arg2;
msg_queue_put(q, &msg);
} }
inline static int msg_queue_get(MessageQueue *q, AVMessage *msg, int block) { int FFMessageQueue::get(AVMessage *msg, int block) {
AVMessage *msg1; AVMessage *msg1;
int ret; int ret;
@ -207,7 +144,7 @@ inline static int msg_queue_get(MessageQueue *q, AVMessage *msg, int block) {
return ret; return ret;
} }
inline static void msg_queue_remove(MessageQueue *q, int what) { void FFMessageQueue::remove(int what) {
AVMessage **p_msg, *msg, *last_msg; AVMessage **p_msg, *msg, *last_msg;
std::lock_guard<std::mutex> lock(q->mutex); std::lock_guard<std::mutex> lock(q->mutex);
@ -238,8 +175,14 @@ inline static void msg_queue_remove(MessageQueue *q, int what) {
} }
} }
inline static void msg_queue_destroy(MessageQueue *q) { void FFMessageQueue::abort() {
msg_queue_flush(q); std::unique_lock<std::mutex> lock(q->mutex);
q->abort_request = 1;
q->cond.notify_all();
}
void FFMessageQueue::destroy() {
flush();
std::lock_guard<std::mutex> lock(q->mutex); std::lock_guard<std::mutex> lock(q->mutex);
while(q->recycle_msg) { while(q->recycle_msg) {
@ -249,6 +192,4 @@ inline static void msg_queue_destroy(MessageQueue *q) {
msg_free(msg); msg_free(msg);
av_freep(&msg); av_freep(&msg);
} }
} }
#endif // FFMSG_QUEUE_H

@ -0,0 +1,96 @@
//
// Created by xu fulong on 2022/9/24.
//
#ifndef FFMPEGANDROID_FFMESSAGEQUEUE_H
#define FFMPEGANDROID_FFMESSAGEQUEUE_H
#include <mutex>
#include <libavutil/mem.h>
/**************** msg define begin ***************/
#define FFP_MSG_FLUSH 0
#define FFP_MSG_ERROR 100
#define FFP_MSG_PREPARED 200
#define FFP_MSG_COMPLETED 300
#define FFP_MSG_VIDEO_SIZE_CHANGED 400
#define FFP_MSG_SAR_CHANGED 401
#define FFP_MSG_VIDEO_RENDERING_START 402
#define FFP_MSG_AUDIO_RENDERING_START 403
#define FFP_MSG_VIDEO_ROTATION_CHANGED 404
#define FFP_MSG_AUDIO_DECODED_START 405
#define FFP_MSG_VIDEO_DECODED_START 406
#define FFP_MSG_OPEN_INPUT 407
#define FFP_MSG_FIND_STREAM_INFO 408
#define FFP_MSG_COMPONENT_OPEN 409
#define FFP_MSG_VIDEO_SEEK_RENDERING_START 410
#define FFP_MSG_AUDIO_SEEK_RENDERING_START 411
#define FFP_MSG_BUFFERING_START 500
#define FFP_MSG_BUFFERING_END 501
#define FFP_MSG_BUFFERING_UPDATE 502
#define FFP_MSG_BUFFERING_BYTES_UPDATE 503
#define FFP_MSG_BUFFERING_TIME_UPDATE 504
#define FFP_MSG_SEEK_COMPLETE 600
#define FFP_MSG_PLAYBACK_STATE_CHANGED 700
#define FFP_MSG_TIMED_TEXT 800
#define FFP_MSG_VIDEO_DECODER_OPEN 900
#define FFP_REQ_START 1001
#define FFP_REQ_PAUSE 1002
#define FFP_REQ_SEEK 1003
/**************** msg define end *****************/
typedef struct AVMessage {
int what;
int arg1;
int arg2;
void *obj;
void (*free_l)(void *obj);
struct AVMessage *next;
} AVMessage;
typedef struct MessageQueue {
AVMessage *first_msg, *last_msg;
int nb_messages;
int abort_request;
std::mutex mutex;
std::condition_variable cond;
AVMessage *recycle_msg;
int recycle_count;
int alloc_count;
} MessageQueue;
class FFMessageQueue {
private:
MessageQueue *q;
public:
void init();
void start();
void flush();
void sendMessage1(int what);
void sendMessage2(int what, int arg1);
void sendMessage3(int what, int arg1, int arg2);
int get(AVMessage *msg, int block);
void remove(int what);
void abort();
void destroy();
};
#endif //FFMPEGANDROID_FFMESSAGEQUEUE_H

@ -5,8 +5,97 @@
#ifndef FFMPEGANDROID_FFPLAY_DEFINE_H #ifndef FFMPEGANDROID_FFPLAY_DEFINE_H
#define FFMPEGANDROID_FFPLAY_DEFINE_H #define FFMPEGANDROID_FFPLAY_DEFINE_H
#define PACKET_QUEUE_SIZE 16 #include <mutex>
#include "FFMessageQueue.h"
#ifdef __cplusplus
extern "C" {
#endif
#include <libavformat/avformat.h>
#ifdef __cplusplus
}
#endif
#define PACKET_QUEUE_SIZE 16
#define FRAME_QUEUE_SIZE 16 #define FRAME_QUEUE_SIZE 16
#define VIDEO_QUEUE_SIZE 5
#define SAMPLE_QUEUE_SIZE 9
#define MAX_QUEUE_SIZE (15 * 1024 * 1024)
#define MIN_FRAMES 25
#define AUDIO_MIN_BUFFER_SIZE 512
#define AUDIO_MAX_CALLBACKS_PER_SEC 30
#define REFRESH_RATE 0.01
#define AV_SYNC_THRESHOLD_MIN 0.04
#define AV_SYNC_THRESHOLD_MAX 0.1
#define AV_SYNC_FRAMEDUP_THRESHOLD 0.1
#define AV_NOSYNC_THRESHOLD 10.0
#define EXTERNAL_CLOCK_MIN_FRAMES 2
#define EXTERNAL_CLOCK_MAX_FRAMES 10
#define EXTERNAL_CLOCK_SPEED_MIN 0.900
#define EXTERNAL_CLOCK_SPEED_MAX 1.010
#define EXTERNAL_CLOCK_SPEED_STEP 0.001
struct AVDictionary {
int count;
AVDictionaryEntry *elements;
};
typedef enum {
AV_SYNC_AUDIO, // 同步到音频时钟
AV_SYNC_VIDEO, // 同步到视频时钟
AV_SYNC_EXTERNAL, // 同步到外部时钟
} SyncType;
class PlayerParams {
public:
std::mutex mutex;
MessageQueue *messageQueue;
int64_t videoDuration;
AVInputFormat *iformat;
const char *url;
int64_t offset;
const char *headers;
const char *audioCodecName;
const char *videoCodecName;
int abortRequest;
int pauseRequest;
SyncType syncType;
int64_t startTime;
int64_t duration;
int realTime;
int infiniteBuffer;
int audioDisable;
int videoDisable;
int displayDisable;
int fast;
int genpts;
int lowres;
float playbackRate;
float playbackPitch;
int seekByBytes;
int seekRequest;
int seekFlags;
int64_t seekPos;
int64_t seekRel;
int autoExit;
int loop;
int mute;
int reorderVideoPts;
};
#endif //FFMPEGANDROID_FFPLAY_DEFINE_H #endif //FFMPEGANDROID_FFPLAY_DEFINE_H

@ -3,7 +3,7 @@
#define FFMPEGANDROID_FRAMEQUEUE_H #define FFMPEGANDROID_FRAMEQUEUE_H
#include <mutex> #include <mutex>
#include "ffplayer/ffplay_define.h" #include "ffplay_define.h"
extern "C" { extern "C" {
#include "libavcodec/avcodec.h" #include "libavcodec/avcodec.h"

Loading…
Cancel
Save