hc
2024-12-19 9370bb92b2d16684ee45cf24e879c93c509162da
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
/*
 * Copyright 2015 Rockchip Electronics Co. LTD
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
#ifndef __MPI_ENC_H__
#define __MPI_ENC_H__
 
#ifdef __cplusplus
extern "C" {
#endif
 
#if defined(_WIN32)
#include "vld.h"
#endif
 
#define MODULE_TAG "mpi_enc"
 
#include <assert.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <rockchip/rk_mpi.h>
 
//#include "mpp_env.h"
//#include "mpp_mem.h"
//#include "printf.h"
//#include "mpp_time.h"
#include "mpp_common.h"
#if USE_RK_AISERVER
#include "mpp_osd.h"
#endif
 
//#include "utils.h"
#define BIT(n)  (1<<(n))
 
#define MAX_FILE_NAME_LENGTH        256
#define RK_MPP_VERSION_DEFAULT 1
#define RK_MPP_USE_FULL_RANGE 0
#define RK_MPP_H264_FORCE_IDR_COUNT 5
#define RK_MPP_H264_FORCE_IDR_PERIOD 5 //must >=1
#define RK_MPP_ENC_TEST_NATIVE 0
#define RK_MPP_USE_ZERO_COPY 1
 
#if RK_MPP_USE_ZERO_COPY
#if !RK_MPP_ENC_TEST_NATIVE
#define RK_MPP_USE_UVC_VIDEO_BUFFER
#endif
extern struct uvc_encode uvc_enc;
#endif
#define RK_MPP_DYNAMIC_DEBUG_ON 1 //release version can set to 0
#define RK_MPP_RANGE_DEBUG_ON 1 //release version can set to 0
 
#define RK_MPP_DYNAMIC_DEBUG_OUT_CHECK "/tmp/uvc_enc_out"
#define RK_MPP_DYNAMIC_DEBUG_IN_CHECK "/tmp/uvc_enc_in" //open it will lower the fps
#define RK_MPP_RANGE_DEBUG_IN_CHECK "/tmp/uvc_range_in"
#define RK_MPP_OUT_LEN_DEBUG_CHECK "/tmp/uvc_out_len"
#define RK_MPP_CLOSE_FRM_LOSS_DEBUG_CHECK "/tmp/uvc_frm_loss"
 
#define RK_MPP_ENABLE_UVC_H265 "/tmp/use_encodec_h265"
 
#define RK_MPP_DEBUG_OUT_FILE "/uvc_enc_out.bin"
#define RK_MPP_DEBUG_IN_FILE "/uvc_enc_in.bin"
 
#define RK_MPP_ENC_CFG_ORIGINAL_PATH "/etc/mpp_enc_cfg.conf"
#define RK_MPP_ENC_CFG_MODIFY_PATH "/data/mpp_enc_cfg.conf"
 
#ifdef USE_ARM64
#define RK_MPP_MJPEG_FPS_CONTROL 0
#else
#define RK_MPP_MJPEG_FPS_CONTROL 1
#endif
 
//#define DEBUG_OUTPUT 1
#if RK_MPP_ENC_TEST_NATIVE
extern struct uvc_encode uvc_enc;
extern int uvc_encode_init(struct uvc_encode *e, int width, int height, int fcc, int h265, unsigned int fps);
#define TEST_ENC_TPYE V4L2_PIX_FMT_H264 //V4L2_PIX_FMT_MJPEG
#endif
#define MPP_ENC_CFG_MIN_FPS 0 // 0 means use host set fps
#define MPP_ENC_CFG_MAX_FPS 100
 
#define MPP_ENC_CFG_MIN_BPS 2 * 1000
#define MPP_ENC_CFG_MAX_BPS 98 * 1000 * 1000
#define MPP_ENC_MJPEG_CFG_MAX_BPS 150 * 1024 * 1024
#define MPP_ENC_CFG_H264_DEFAULT_PROFILE 100
#define MPP_ENC_CFG_H264_DEFAULT_LEVEL 40
#define MPP_ENC_MJPEG_FRC_USE_MPP 0
 
//**********for simple frc************//
#define MJPEG_FRC_BPS_MAX 150*1024*1024
#define MJPEG_FRC_BPS_MIN 100*1024*1024
#define MJPEG_FRC_BPS_PER_STEP 1*1024*1024
 
#define MJPEG_FRC_QUANT_MAX 10
#define MJPEG_FRC_QUANT_MIN 6
 
#define MJPEG_FRC_QFACTOR_MAX 99
#define MJPEG_FRC_QFACTOR_MIN 70
 
#define MPP_FRC_WAIT_TIME_MS 2
#define MPP_FRC_WAIT_TIME_US (MPP_FRC_WAIT_TIME_MS * 1000)
#define MPP_FRC_WAIT_COUNT_MIN (18 / MPP_FRC_WAIT_TIME_MS) // in high resolution, the frame rate is not enough to lower this
#define MPP_MJPEG_HIGH_FPS_FRC_WAIT_COUNT_MIN (6 / MPP_FRC_WAIT_TIME_MS) // in high resolution, the frame rate is not enough to lower this
 
#define MPP_FRC_UP_FRM_SET_INIT 1000
#define MPP_FRC_UP_FRM_SET_MIN  MPP_FRC_UP_FRM_SET_INIT
#define MPP_FRC_UP_FRM_SET_MAX 0x40000000
 
#define MPP_FRC_WAIT_COUNT_OFFSET 5 // bit rate control is too low to increase this
 
//***************ROI*********************//
#define MPP_ENC_ROI_ENABLE 1
#define UPALIGNTO(value, align) ((value + align - 1) & (~(align - 1)))
#define UPALIGNTO16(value) UPALIGNTO(value, 16)
#define VALUE_SCOPE_CHECK(X, MIN, MAX) assert((X >= MIN) && (X <= MAX))
 
typedef struct  {
    uint16_t x;            /**< horizontal position of top left corner */
    uint16_t y;            /**< vertical position of top left corner */
    uint16_t w;            /**< width of ROI rectangle */
    uint16_t h;            /**< height of ROI rectangle */
    uint16_t intra;        /**< flag of forced intra macroblock */
    int16_t quality;      /**<  qp of macroblock */
    uint16_t qp_area_idx;  /**< qp min max area select*/
    uint8_t  area_map_en;  /**< enable area map */
    uint8_t  abs_qp_en;    /**< absolute qp enable flag*/
} EncROIRegion;
 
//***************GOP MODE*********************//
typedef enum {
  GOP_MODE_NORMALP = 0, // normal p mode
  GOP_MODE_TSVC2,       // tsvc: 2 layer
  GOP_MODE_TSVC3,       // tsvc: 3 layer
  GOP_MODE_TSVC4,       // tsvc: 4 layer
  GOP_MODE_SMARTP,      // smart p mode
} MpiEncGopMode;
 
//************************************//
 
enum SIMPLE_FRC_MODE
{
    FRC_OFF = 0,
    FRC_ONLY_LOW,
    FRC_BOTH_UP_LOW,
};
 
//**********************//
 
typedef struct
{
    MppCodingType   type;
    RK_U32          width;
    RK_U32          height;
    MppFrameFormat  format;
    RK_U32          debug;
    RK_U32          num_frames;
    RK_U32          fps;
    RK_U32          have_output;
} MpiEncTestCmd;
typedef struct
{
    RK_U32 init;
    RK_U32 max;
    RK_U32 min;
    RK_U32 step;
    RK_U32 max_i_qp;
    RK_U32 min_i_qp;
 
} MpiEncQqCfg;
/********************do not change the order below*******************/
#define MPP_ENC_CFG_CHANGE_BIT(x) (1 << x)
#define MPP_STREAM_SAVE_DIR_LEN 32
typedef struct
{
    RK_U32 change;
    RK_U32 fbc;
    RK_U32 split_mode;// 1
    RK_U32 split_arg;// 2
    RK_U32 force_idr_count; // 3
    RK_U32 force_idr_period;// 4
    RK_U32 frc_fps;// 5
    enum SIMPLE_FRC_MODE frc_mode; // 6
    MppEncRotationCfg rotation;// 7
    RK_U32 enc_time;
    RK_U32 try_count;
} MpiEncCommonCfg;
 
typedef struct
{
    RK_U32 change;
    RK_U32 frc_quant; //
    RK_S32 frc_qfactor;  //
    RK_U32 frc_bps;
 
    RK_U32 quant; //bit0      1- 10 default:7
    MppFrameColorRange range; // bit1   full:MPP_FRAME_RANGE_JPEG  limit:MPP_FRAME_RANGE_MPEG;
    RK_U32 qfactor; // bit2   0-99  priprity option this. set 0 is close this and set use quant
    RK_S32 qfactor_min;  // 3
    RK_S32 qfactor_max;  // 4
    RK_U32 gop;  // 5
    MppEncRcMode rc_mode; // 6
    RK_U32 bps; // 7
    RK_U32 framerate; // 8
    RK_U32 enc_mode; //enc_mode no have change bit   0:mean auto select 1:close the mjpeg_frc 2: use mjpeg_frc
    RK_U32 qfactor_frc_min;
    MppEncSeiMode sei;  // 11
} MpiEncMjpegCfg;
 
typedef struct
{
    RK_U32 change;
    RK_U32 gop; //0
    RK_U32 gop_normal; //0
    MppEncRcMode rc_mode;
    RK_U32 framerate; ////simple to set.
    MppFrameColorRange range; // full: MPP_FRAME_RANGE_JPEG  limit:MPP_FRAME_RANGE_MPEG;
    MppEncHeaderMode head_each_idr;
    MppEncSeiMode sei;//5
    MpiEncQqCfg qp;//6-9
    RK_U32 profile;//10
    RK_U32 cabac_en;
    RK_U32 cabac_idc;
    RK_U32 trans_8x8;//
    RK_U32 level;
    RK_U32 bps;//15
    RK_U32 idr_bps;//16
    RK_U32 vi_len;//17
    MpiEncGopMode gop_mode; //18
} MpiEncH264Cfg;
 
typedef struct
{
    RK_U32 change;
    RK_U32 gop; //0
    RK_U32 gop_normal; //0
    MppEncRcMode rc_mode;
    RK_U32 framerate;
    MppFrameColorRange range; //full: MPP_FRAME_RANGE_JPEG  limit:MPP_FRAME_RANGE_MPEG;
    MppEncHeaderMode head_each_idr;
    MppEncSeiMode sei;//5
    MpiEncQqCfg qp;//6-11
    RK_U32 bps;//12
    RK_U32 idr_bps;//13
    RK_U32 vi_len;//14
    MpiEncGopMode gop_mode; // 15
} MpiEncH265Cfg;
 
#if MPP_ENC_OSD_ENABLE
#define MPP_ENC_OSD_IMAGE_PATH_LEN 32
typedef struct
{
    bool set_ok;
    bool enable; //dynamic on/off set this
    enum OSD_REGION_TYPE type;
    RK_U32 start_x;
    RK_U32 start_y;
    char image_path[MPP_ENC_OSD_IMAGE_PATH_LEN];//*image_path;//
 
// for mjpeg rga osd
    RK_U32 width;
    RK_U32 height;
    int rga_osd_fd;
    unsigned int handle; // for drm handle
    uint8_t *buffer;
    int drm_size;
// for mjpeg rga osd
} MpiEncOSDCfg;
 
#endif
 
/***************************o not change the order above**************************************/
typedef struct MppBuffNode
{
    MppFrame frame;
    MppPacket packet;
    MppBuffer buf;
    MppBuffer pkt_buf_out;
    int buf_fd;
    bool init;
} MppBuffInfo;
 
#define IN_BUF_COUNT_MAX 10
#define OUT_BUF_COUNT_MAX 3
 
#if RK_MPP_MJPEG_FPS_CONTROL
#define MJPEG_FPS_CONTROL_V2 1
#endif
 
typedef struct
{
#if RK_MPP_MJPEG_FPS_CONTROL
    void *fps_handle;
#endif
    RK_U32 fps;
    RK_U32 loss_frm;
    RK_U32 continuous_frm;
    RK_U32 frc_up_frm_set;
    bool set_frc_low;
    bool fps_ctr_enable;
    MpiEncCommonCfg common_cfg;
    MpiEncMjpegCfg mjpeg_cfg;
    MpiEncH264Cfg h264_cfg;
    MpiEncH265Cfg h265_cfg;
 
    // global flow control flag
    RK_U32 frm_eos;
    RK_U32 pkt_eos;
    RK_U32 frame_count;
    RK_U64 stream_size;
#if RK_MPP_RANGE_DEBUG_ON
#define RANGE_PATH_MAX_LEN 128
    FILE *fp_range_path;
    FILE *fp_range_file;
    char *range_path;
#endif
    // src and dst
    FILE *fp_input;
    FILE *fp_output;
    char streamin_save_dir[MPP_STREAM_SAVE_DIR_LEN];
    char streamout_save_dir[MPP_STREAM_SAVE_DIR_LEN];
 
    // base flow context
    MppCtx ctx;
    MppApi *mpi;
    RK_U32 use_legacy_cfg;
    MppEncCfg cfg;
    MppEncPrepCfg prep_cfg;
    MppEncRcCfg rc_cfg;
    MppEncCodecCfg codec_cfg;
    MppEncSliceSplit split_cfg;
#if MPP_ENC_OSD_ENABLE
    /*
    * osd idx size range from 16x16 bytes(pixels) to hor_stride*ver_stride(bytes).
    * for general use, 1/8 Y buffer is enough.
    */
    MppEncOSDPltCfg osd_plt_cfg;
    MppEncOSDPlt     osd_plt;
    MppEncOSDData    osd_data;
    MppBuffer osd_idx_buf;
    size_t osd_idx_size;
    RK_U32 osd_count;
    bool osd_enable;
    bool osd_plt_user;
    bool osd_index_enable[OSD_REGIONS_CNT];
    MpiEncOSDCfg osd_cfg[OSD_REGIONS_CNT];
    RK_U32 plt_table[PALETTE_TABLE_LEN]; //ayuv map
    int rga_osd_drm_fd;
#endif
#if MPP_ENC_ROI_ENABLE
    RK_U32 roi_enable;
    RK_U32 roi_number;
    MppEncROIRegion *roi_region;
    MppEncROICfg     roi_cfg;
#endif
    // input / output
    MppBuffer frm_buf;
    MppEncSeiMode sei_mode;
    MppEncHeaderMode header_mode;
 
    // paramter for resource malloc
    RK_U32 width;
    RK_U32 height;
    RK_U32 hor_stride;
    RK_U32 ver_stride;
    MppFrameFormat fmt;
    MppCodingType type;
    RK_S32 num_frames;
    RK_S32 loop_times;
 
    // resources
    size_t header_size;
    size_t frame_size;
    /* NOTE: packet buffer may overflow */
    size_t packet_size;
 
    RK_U32 split_mode;
    RK_U32 split_arg;
 
    RK_U32 user_data_enable;
 
    // rate control runtime parameter
    RK_S32 gop;
    RK_S32 fps_in_flex;
    RK_S32 fps_in_den;
    RK_S32 fps_in_num;
    RK_S32 fps_out_flex;
    RK_S32 fps_out_den;
    RK_S32 fps_out_num;
    RK_S32 bps;
 
    MppFrame frame;
    MppPacket packet;
    void *enc_data;
    size_t enc_len;
    RK_U32 enc_version;
    RK_U32 h2645_frm_count;
#if RK_MPP_USE_ZERO_COPY
    MppBufferGroup pkt_grp;
    MppBuffer pkt_buf;
#endif
    pthread_t check_cfg_change_hd;
 
    int cfg_notify_fd;
    int cfg_notify_wd;
    MppBuffInfo out_buff_info[OUT_BUF_COUNT_MAX];
    MppBuffInfo in_buff_info[IN_BUF_COUNT_MAX];
    int yuv_rotation_drm_fd;
    int yuv_rotation_fd;
    unsigned int yuv_rotation_handle; // for drm handle
    int yuv_rotation_drm_size;
    MppEncUserData user_data;
} MpiEncTestData;
 
typedef struct MPP_ENC_INFO {
    int fd;
    size_t size;
    RK_U32 pts;
    RK_U32 seq;
} MPP_ENC_INFO_DEF;
 
MPP_RET mpi_enc_test_init(MpiEncTestCmd *cmd, MpiEncTestData **data);
MPP_RET mpi_enc_test_run(MpiEncTestData **data, MPP_ENC_INFO_DEF *info);
MPP_RET mpi_enc_test_deinit(MpiEncTestData **data);
MPP_RET mpi_enc_inbuf_deinit(MpiEncTestData *data);
void mpi_enc_cmd_config(MpiEncTestCmd *cmd, int width, int height, int fcc, int h265, unsigned int fps);
void mpi_enc_cmd_config_mjpg(MpiEncTestCmd *cmd, int width, int height);
void mpi_enc_cmd_config_h264(MpiEncTestCmd *cmd, int width, int height);
void mpi_enc_set_format(MppFrameFormat format);
int mpi_enc_get_h264_extra(MpiEncTestData *p, void *buffer, size_t *size);
RK_S32 mpi_get_env_u32(const char *name, RK_U32 *value, RK_U32 default_value);
MPP_RET mpp_enc_cfg_set_s32(MppEncCfg cfg, const char *name, RK_S32 val);
MPP_RET mpp_enc_cfg_set_u32(MppEncCfg cfg, const char *name, RK_U32 val);
MPP_RET mpp_enc_cfg_set_s64(MppEncCfg cfg, const char *name, RK_S64 val);
MPP_RET mpp_enc_cfg_set_u64(MppEncCfg cfg, const char *name, RK_U64 val);
MPP_RET mpp_enc_cfg_set_ptr(MppEncCfg cfg, const char *name, void *val);
MPP_RET mpp_enc_cfg_get_s32(MppEncCfg cfg, const char *name, RK_S32 *val);
MPP_RET mpp_enc_cfg_get_u32(MppEncCfg cfg, const char *name, RK_U32 *val);
MPP_RET mpp_enc_cfg_get_s64(MppEncCfg cfg, const char *name, RK_S64 *val);
MPP_RET mpp_enc_cfg_get_u64(MppEncCfg cfg, const char *name, RK_U64 *val);
 
#ifdef RK_MPP_USE_UVC_VIDEO_BUFFER
struct uvc_buffer *uvc_buffer_write_get(int id);
void uvc_buffer_read_set(int id, struct uvc_buffer *buf);
void uvc_user_lock();
void uvc_user_unlock();
struct uvc_buffer *uvc_buffer_write_get_nolock(int id);
void uvc_buffer_read_set_nolock(int id, struct uvc_buffer *buf);
 
#endif
#ifdef __cplusplus
}
#endif
 
#endif