Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
[submodule "aom"]
path = aom
url = https://aomedia.googlesource.com/aom
[submodule "libvpx"]
path = libvpx
url = https://chromium.googlesource.com/webm/libvpx
1 change: 1 addition & 0 deletions aom
Submodule aom added at d032a4
1 change: 1 addition & 0 deletions libvpx
Submodule libvpx added at c686f3
2 changes: 1 addition & 1 deletion meson.build
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
project('LibMebo', 'c',
project('LibMebo', ['c' , 'cpp'],
version : '0.1.0.1',
meson_version : '>= 0.49',
default_options: [ 'warning_level=2',
Expand Down
205 changes: 205 additions & 0 deletions src/Handlers/AV1RateControlHandler.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,205 @@
#include "AV1RateControlHandler.hpp"
#include <dlfcn.h>
#include <iostream>
#include <cstring>

#include "../../aom/av1/ratectrl_rtc.h"

Libmebo_brc_AV1::Libmebo_brc_AV1(LibMeboBrcAlgorithmID algo_id)
: Libmebo_brc(LIBMEBO_CODEC_AV1, algo_id), handle(nullptr),
ptrCreateAV1Controller(nullptr) {
enc_params_libmebo.num_sl = 1;
enc_params_libmebo.num_tl = 1;
enc_params_libmebo.bitrate = 288; // in kbps.
enc_params_libmebo.dynamic_rate_change = 0;
enc_params_libmebo.framecount = 100;
enc_params_libmebo.framerate = 60;
enc_params_libmebo.width = 320;
enc_params_libmebo.height = 160;
enc_params_libmebo.id = static_cast<unsigned int>(LIBMEBO_CODEC_AV1);
enc_params_libmebo.preset = 0;
enc_params_libmebo.buf_optimal_sz = 600;
}

Libmebo_brc_AV1::~Libmebo_brc_AV1() {
if (handle) {
dlclose(handle);
}
}
#define av1aom_zero(dest) memset(&(dest), 0, sizeof(dest))
AomAV1RateControlRtcConfig *config;
void *controller;

int Libmebo_brc_AV1::InitSymbolsFromLiray() {
char path[] = "/home/pradeep4/Documents/pradeep/libmebo_push/libmebo/aom/build/libaom_av1_rc.so"; // this needs to be at config time.
handle = dlopen(path, RTLD_LAZY);
if (!handle) {
return kMainHandleLibError;
}

ptrCreateAV1Controller =
(createAV1Controller_t)dlsym(handle, "av1_ratecontrol_rtc_create");
if (!ptrCreateAV1Controller) {
return kAv1CreateSymbLoadError;
}
ptrInitConfigFunc = (InitRateControlConfigFunc)dlsym(
handle, "av1_ratecontrol_rtc_init_ratecontrol_config");

if (!ptrInitConfigFunc) {
return kAV1RateCtrlInitConfigSymbLoadError;
}
ptrUpdateRateControl_AV1 =
(UpdateRateControl_AV1_t)dlsym(handle, "av1_ratecontrol_rtc_update");
if (!ptrUpdateRateControl_AV1) {
return kUpdateRateControlSymbLoadError;
}
ptrComputeQP_AV1 =
(ComputeQP_AV1_t)dlsym(handle, "av1_ratecontrol_rtc_compute_qp");
if (!ptrComputeQP_AV1) {
return kCompueQPSymbLoadError;
}
ptrPostEncodeUpdate_AV1 = (PostEncodeUpdate_AV1_t)dlsym(
handle, "av1_ratecontrol_rtc_post_encode_update");
if (!ptrPostEncodeUpdate_AV1) {
return kPostEncodeSymbLoadError;
}
ptrGetQP_AV1 = (GetQP_AV1_t)dlsym(handle, "av1_ratecontrol_rtc_get_qp");
if (!ptrGetQP_AV1) {
return kGetQpSymbLoadError;
}
ptrGetLoopfilterLevel_AV1 = (GetLoopfilterLevel_AV1_t)dlsym(
handle, "av1_ratecontrol_rtc_get_loop_filter_level");
if (!ptrGetLoopfilterLevel_AV1) {
return kGetLoopFilterSymbError;
}
return kNoError;
}

LibMeboRateController *
Libmebo_brc_AV1::init(LibMeboRateController *libmebo_rc,
LibMeboRateControllerConfig *libmebo_rc_config) {
int result = InitSymbolsFromLiray();
if (result != kNoError) {
return nullptr;
}
libmebo_rc = Libmebo_brc::init(libmebo_rc, libmebo_rc_config);

memset (&config, 0, sizeof(config));
ptrInitConfigFunc(config);

if (config == nullptr)
return nullptr;

constexpr int kMinQP = 10;
constexpr int kMaxQP = 56;
config->width = 640;
config->height = 480;
config->is_screen = false;
// third_party/webrtc/modules/video_coding/codecs/av1/libaom_av1_encoder.cc
config->max_quantizer = kMaxQP;
config->min_quantizer = kMinQP;

config->buf_initial_sz = 600;
config->buf_optimal_sz = 500;
config->target_bandwidth = 800000 / 1000;
config->buf_sz = 1000;
config->undershoot_pct = 25;
config->overshoot_pct = 50;
config->max_intra_bitrate_pct = 300;
config->max_inter_bitrate_pct = 50;
config->framerate = 60;
av1aom_zero(config->layer_target_bitrate);
config->layer_target_bitrate[0] = (config->target_bandwidth);
av1aom_zero(config->ts_rate_decimator);
config->ts_rate_decimator[0] = 1;
config->aq_mode = 1;
av1aom_zero(config->max_quantizers);
av1aom_zero(config->min_quantizers);
av1aom_zero(config->scaling_factor_num);
av1aom_zero(config->scaling_factor_den);
config->ss_number_layers = 1;
config->ts_number_layers = 1;
config->max_quantizers[0] = kMaxQP;
config->min_quantizers[0] = kMinQP;
config->scaling_factor_num[0] = 1;
config->scaling_factor_den[0] = 1;
config->frame_drop_thresh = 30;
config->max_consec_drop_ms = 8;

controller = ptrCreateAV1Controller(*config);
if (controller == nullptr)
return nullptr;
return libmebo_rc;
}

LibMeboStatus
Libmebo_brc_AV1::update_config(LibMeboRateController *rc,
LibMeboRateControllerConfig *rc_config) {
LibMeboStatus status = LIBMEBO_STATUS_SUCCESS;

if (!rc || !rc_config)
return LIBMEBO_STATUS_ERROR;

ptrUpdateRateControl_AV1(controller, *config);

return status;
}

LibMeboStatus Libmebo_brc_AV1::post_encode_update(LibMeboRateController *rc,
uint64_t encoded_frame_size) {
LibMeboStatus status = LIBMEBO_STATUS_SUCCESS;

if (!rc)
return LIBMEBO_STATUS_ERROR;

ptrPostEncodeUpdate_AV1(controller, encoded_frame_size);

return status;
}

LibMeboStatus
Libmebo_brc_AV1::compute_qp(LibMeboRateController *rc,
LibMeboRCFrameParams *rc_frame_params) {

LibMeboStatus status = LIBMEBO_STATUS_SUCCESS;

if (!rc)
return LIBMEBO_STATUS_ERROR;
aom::AV1FrameParamsRTC frame_params_aom;

if (rc_frame_params->frame_type == LIBMEBO_KEY_FRAME)
frame_params_aom.frame_type = kKeyFrame;
else
frame_params_aom.frame_type = kInterFrame;

ptrComputeQP_AV1(controller, frame_params_aom);
return status;
}

LibMeboStatus Libmebo_brc_AV1::get_qp(LibMeboRateController *rc, int *qp) {
LibMeboStatus status = LIBMEBO_STATUS_SUCCESS;

if (!rc)
return LIBMEBO_STATUS_ERROR;

*qp = ptrGetQP_AV1(controller);
return status;
}

LibMeboStatus Libmebo_brc_AV1::get_loop_filter_level(LibMeboRateController *rc,
int *filter_level) {
LibMeboStatus status = LIBMEBO_STATUS_SUCCESS;
if (!rc)
return LIBMEBO_STATUS_ERROR;

AomAV1LoopfilterLevel loop_filter_level;

loop_filter_level = ptrGetLoopfilterLevel_AV1(controller);

filter_level[0] = loop_filter_level.filter_level[0];
filter_level[1] = loop_filter_level.filter_level[1];
filter_level[2] = loop_filter_level.filter_level_u;
filter_level[3] = loop_filter_level.filter_level_v;

return status;
}
66 changes: 66 additions & 0 deletions src/Handlers/AV1RateControlHandler.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
#pragma once
#include <memory>

extern "C" {
#include "../lib/libmebo.hpp"
}
#include "../../aom/av1/ratectrl_rtc.h"
#include "LibMeboControlHandler.hpp"

typedef enum ErrorsLoadingSymbols {
kNoError = 0,
kMainHandleLibError = -1,
kAv1CreateSymbLoadError = -2,
kAV1RateCtrlInitConfigSymbLoadError = -3,
kUpdateRateControlSymbLoadError = -4,
kCompueQPSymbLoadError = -5,
kPostEncodeSymbLoadError = -6,
kGetQpSymbLoadError = -7,
kGetLoopFilterSymbError = -8,
} ErrosLibmeboSymbols;

class Libmebo_brc_AV1 : public Libmebo_brc {
public:
Libmebo_brc_AV1(LibMeboBrcAlgorithmID algo_id);
virtual ~Libmebo_brc_AV1() override;
LibMeboRateController *init(LibMeboRateController *rc,
LibMeboRateControllerConfig *rc_config) override;
LibMeboStatus update_config(LibMeboRateController *rc,
LibMeboRateControllerConfig *rc_cfg) override;
LibMeboStatus post_encode_update(LibMeboRateController *rc,
uint64_t encoded_frame_size) override;
LibMeboStatus compute_qp(LibMeboRateController *rc,
LibMeboRCFrameParams *rc_frame_params) override;
LibMeboStatus get_qp(LibMeboRateController *rc, int *qp) override;
LibMeboStatus get_loop_filter_level(LibMeboRateController *rc,
int *filter_level) override;
int InitSymbolsFromLiray();

private:
typedef void *BrcCodecEnginePtr;
BrcCodecEnginePtr brc_codec_handler;
// std::unique_ptr <aom::AV1RateControlRTC> av1_rc_rtc_;
void *handle;
typedef AomAV1RateControlRtcConfig *(*create_av1_rate_control_config_t)();
typedef void *(*createAV1Controller_t)(const AomAV1RateControlRtcConfig &rc_cfg);
typedef bool (*UpdateRateControl_AV1_t)(void *controller, const AomAV1RateControlRtcConfig &rc_cfg);
typedef int (*GetQP_AV1_t)(void *controller);
typedef FrameDropDecision (*ComputeQP_AV1_t)(void *controller, const AomAV1FrameParamsRTC &frame_params);
typedef AomAV1LoopfilterLevel (*GetLoopfilterLevel_AV1_t)(void *controller);
typedef void (*PostEncodeUpdate_AV1_t)(void *controller, uint64_t encoded_frame_size);
typedef bool (*GetSegmentationData_AV1_t)(void *controller, AomAV1SegmentationData *segmentation_data);
typedef AomAV1CdefInfo (*GetCdefInfo_AV1_t)(void *controller);


typedef void (*InitRateControlConfigFunc)(struct AomAV1RateControlRtcConfig *config);
create_av1_rate_control_config_t create_av1_ratecontrol_config;
createAV1Controller_t ptrCreateAV1Controller;
UpdateRateControl_AV1_t ptrUpdateRateControl_AV1;
GetQP_AV1_t ptrGetQP_AV1;
ComputeQP_AV1_t ptrComputeQP_AV1;
GetLoopfilterLevel_AV1_t ptrGetLoopfilterLevel_AV1;
PostEncodeUpdate_AV1_t ptrPostEncodeUpdate_AV1;
GetSegmentationData_AV1_t ptrGetSegmentationData_AV1;
GetCdefInfo_AV1_t ptrGetCdefInfo_AV1;
InitRateControlConfigFunc ptrInitConfigFunc;
};
Loading