1bf215546Sopenharmony_ci/************************************************************************** 2bf215546Sopenharmony_ci * 3bf215546Sopenharmony_ci * Copyright 2013 Advanced Micro Devices, Inc. 4bf215546Sopenharmony_ci * All Rights Reserved. 5bf215546Sopenharmony_ci * 6bf215546Sopenharmony_ci * Permission is hereby granted, free of charge, to any person obtaining a 7bf215546Sopenharmony_ci * copy of this software and associated documentation files (the 8bf215546Sopenharmony_ci * "Software"), to deal in the Software without restriction, including 9bf215546Sopenharmony_ci * without limitation the rights to use, copy, modify, merge, publish, 10bf215546Sopenharmony_ci * distribute, sub license, and/or sell copies of the Software, and to 11bf215546Sopenharmony_ci * permit persons to whom the Software is furnished to do so, subject to 12bf215546Sopenharmony_ci * the following conditions: 13bf215546Sopenharmony_ci * 14bf215546Sopenharmony_ci * The above copyright notice and this permission notice (including the 15bf215546Sopenharmony_ci * next paragraph) shall be included in all copies or substantial portions 16bf215546Sopenharmony_ci * of the Software. 17bf215546Sopenharmony_ci * 18bf215546Sopenharmony_ci * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 19bf215546Sopenharmony_ci * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 20bf215546Sopenharmony_ci * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. 21bf215546Sopenharmony_ci * IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR 22bf215546Sopenharmony_ci * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 23bf215546Sopenharmony_ci * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 24bf215546Sopenharmony_ci * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 25bf215546Sopenharmony_ci * 26bf215546Sopenharmony_ci **************************************************************************/ 27bf215546Sopenharmony_ci 28bf215546Sopenharmony_ci#include "pipe/p_video_codec.h" 29bf215546Sopenharmony_ci#include "radeon_vce.h" 30bf215546Sopenharmony_ci#include "radeon_video.h" 31bf215546Sopenharmony_ci#include "si_pipe.h" 32bf215546Sopenharmony_ci#include "util/u_memory.h" 33bf215546Sopenharmony_ci#include "util/u_video.h" 34bf215546Sopenharmony_ci#include "vl/vl_video_buffer.h" 35bf215546Sopenharmony_ci 36bf215546Sopenharmony_ci#include <stdio.h> 37bf215546Sopenharmony_ci 38bf215546Sopenharmony_cistatic void rate_control(struct rvce_encoder *enc) 39bf215546Sopenharmony_ci{ 40bf215546Sopenharmony_ci RVCE_BEGIN(0x04000005); // rate control 41bf215546Sopenharmony_ci RVCE_CS(enc->pic.rate_ctrl[0].rate_ctrl_method); // encRateControlMethod 42bf215546Sopenharmony_ci RVCE_CS(enc->pic.rate_ctrl[0].target_bitrate); // encRateControlTargetBitRate 43bf215546Sopenharmony_ci RVCE_CS(enc->pic.rate_ctrl[0].peak_bitrate); // encRateControlPeakBitRate 44bf215546Sopenharmony_ci RVCE_CS(enc->pic.rate_ctrl[0].frame_rate_num); // encRateControlFrameRateNum 45bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encGOPSize 46bf215546Sopenharmony_ci RVCE_CS(enc->pic.quant_i_frames); // encQP_I 47bf215546Sopenharmony_ci RVCE_CS(enc->pic.quant_p_frames); // encQP_P 48bf215546Sopenharmony_ci RVCE_CS(enc->pic.quant_b_frames); // encQP_B 49bf215546Sopenharmony_ci RVCE_CS(enc->pic.rate_ctrl[0].vbv_buffer_size); // encVBVBufferSize 50bf215546Sopenharmony_ci RVCE_CS(enc->pic.rate_ctrl[0].frame_rate_den); // encRateControlFrameRateDen 51bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encVBVBufferLevel 52bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encMaxAUSize 53bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encQPInitialMode 54bf215546Sopenharmony_ci RVCE_CS(enc->pic.rate_ctrl[0].target_bits_picture); // encTargetBitsPerPicture 55bf215546Sopenharmony_ci RVCE_CS(enc->pic.rate_ctrl[0].peak_bits_picture_integer); // encPeakBitsPerPictureInteger 56bf215546Sopenharmony_ci RVCE_CS(enc->pic.rate_ctrl[0].peak_bits_picture_fraction); // encPeakBitsPerPictureFractional 57bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encMinQP 58bf215546Sopenharmony_ci RVCE_CS(0x00000033); // encMaxQP 59bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encSkipFrameEnable 60bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encFillerDataEnable 61bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encEnforceHRD 62bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encBPicsDeltaQP 63bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encReferenceBPicsDeltaQP 64bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encRateControlReInitDisable 65bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encLCVBRInitQPFlag 66bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encLCVBRSATDBasedNonlinearBitBudgetFlag 67bf215546Sopenharmony_ci RVCE_END(); 68bf215546Sopenharmony_ci} 69bf215546Sopenharmony_ci 70bf215546Sopenharmony_cistatic void encode(struct rvce_encoder *enc) 71bf215546Sopenharmony_ci{ 72bf215546Sopenharmony_ci signed luma_offset, chroma_offset, bs_offset; 73bf215546Sopenharmony_ci unsigned dep, bs_idx = enc->bs_idx++; 74bf215546Sopenharmony_ci int i; 75bf215546Sopenharmony_ci 76bf215546Sopenharmony_ci if (enc->dual_inst) { 77bf215546Sopenharmony_ci if (bs_idx == 0) 78bf215546Sopenharmony_ci dep = 1; 79bf215546Sopenharmony_ci else if (enc->pic.picture_type == PIPE_H2645_ENC_PICTURE_TYPE_IDR) 80bf215546Sopenharmony_ci dep = 0; 81bf215546Sopenharmony_ci else 82bf215546Sopenharmony_ci dep = 2; 83bf215546Sopenharmony_ci } else 84bf215546Sopenharmony_ci dep = 0; 85bf215546Sopenharmony_ci 86bf215546Sopenharmony_ci enc->task_info(enc, 0x00000003, dep, 0, bs_idx); 87bf215546Sopenharmony_ci 88bf215546Sopenharmony_ci RVCE_BEGIN(0x05000001); // context buffer 89bf215546Sopenharmony_ci RVCE_READWRITE(enc->cpb.res->buf, enc->cpb.res->domains, 0); // encodeContextAddressHi/Lo 90bf215546Sopenharmony_ci RVCE_END(); 91bf215546Sopenharmony_ci 92bf215546Sopenharmony_ci bs_offset = -(signed)(bs_idx * enc->bs_size); 93bf215546Sopenharmony_ci 94bf215546Sopenharmony_ci RVCE_BEGIN(0x05000004); // video bitstream buffer 95bf215546Sopenharmony_ci RVCE_WRITE(enc->bs_handle, RADEON_DOMAIN_GTT, bs_offset); // videoBitstreamRingAddressHi/Lo 96bf215546Sopenharmony_ci RVCE_CS(enc->bs_size); // videoBitstreamRingSize 97bf215546Sopenharmony_ci RVCE_END(); 98bf215546Sopenharmony_ci 99bf215546Sopenharmony_ci if (enc->dual_pipe) { 100bf215546Sopenharmony_ci unsigned aux_offset = 101bf215546Sopenharmony_ci enc->cpb.res->buf->size - RVCE_MAX_AUX_BUFFER_NUM * RVCE_MAX_BITSTREAM_OUTPUT_ROW_SIZE * 2; 102bf215546Sopenharmony_ci RVCE_BEGIN(0x05000002); // auxiliary buffer 103bf215546Sopenharmony_ci for (i = 0; i < 8; ++i) { 104bf215546Sopenharmony_ci RVCE_CS(aux_offset); 105bf215546Sopenharmony_ci aux_offset += RVCE_MAX_BITSTREAM_OUTPUT_ROW_SIZE; 106bf215546Sopenharmony_ci } 107bf215546Sopenharmony_ci for (i = 0; i < 8; ++i) 108bf215546Sopenharmony_ci RVCE_CS(RVCE_MAX_BITSTREAM_OUTPUT_ROW_SIZE); 109bf215546Sopenharmony_ci RVCE_END(); 110bf215546Sopenharmony_ci } 111bf215546Sopenharmony_ci 112bf215546Sopenharmony_ci RVCE_BEGIN(0x03000001); // encode 113bf215546Sopenharmony_ci RVCE_CS(enc->pic.frame_num ? 0x0 : 0x11); // insertHeaders 114bf215546Sopenharmony_ci RVCE_CS(0x00000000); // pictureStructure 115bf215546Sopenharmony_ci RVCE_CS(enc->bs_size); // allowedMaxBitstreamSize 116bf215546Sopenharmony_ci RVCE_CS(0x00000000); // forceRefreshMap 117bf215546Sopenharmony_ci RVCE_CS(0x00000000); // insertAUD 118bf215546Sopenharmony_ci RVCE_CS(0x00000000); // endOfSequence 119bf215546Sopenharmony_ci RVCE_CS(0x00000000); // endOfStream 120bf215546Sopenharmony_ci RVCE_READ(enc->handle, RADEON_DOMAIN_VRAM, 121bf215546Sopenharmony_ci (uint64_t)enc->luma->u.legacy.level[0].offset_256B * 256); // inputPictureLumaAddressHi/Lo 122bf215546Sopenharmony_ci RVCE_READ(enc->handle, RADEON_DOMAIN_VRAM, 123bf215546Sopenharmony_ci (uint64_t)enc->chroma->u.legacy.level[0].offset_256B * 256); // inputPictureChromaAddressHi/Lo 124bf215546Sopenharmony_ci RVCE_CS(align(enc->luma->u.legacy.level[0].nblk_y, 16)); // encInputFrameYPitch 125bf215546Sopenharmony_ci RVCE_CS(enc->luma->u.legacy.level[0].nblk_x * enc->luma->bpe); // encInputPicLumaPitch 126bf215546Sopenharmony_ci RVCE_CS(enc->chroma->u.legacy.level[0].nblk_x * enc->chroma->bpe); // encInputPicChromaPitch 127bf215546Sopenharmony_ci if (enc->dual_pipe) 128bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encInputPic(Addr|Array)Mode,encDisable(TwoPipeMode|MBOffloading) 129bf215546Sopenharmony_ci else 130bf215546Sopenharmony_ci RVCE_CS(0x00010000); // encInputPic(Addr|Array)Mode,encDisable(TwoPipeMode|MBOffloading) 131bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encInputPicTileConfig 132bf215546Sopenharmony_ci RVCE_CS(enc->pic.picture_type); // encPicType 133bf215546Sopenharmony_ci RVCE_CS(enc->pic.picture_type == PIPE_H2645_ENC_PICTURE_TYPE_IDR);// encIdrFlag 134bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encIdrPicId 135bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encMGSKeyPic 136bf215546Sopenharmony_ci RVCE_CS(!enc->pic.not_referenced); // encReferenceFlag 137bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encTemporalLayerIndex 138bf215546Sopenharmony_ci RVCE_CS(0x00000000); // num_ref_idx_active_override_flag 139bf215546Sopenharmony_ci RVCE_CS(0x00000000); // num_ref_idx_l0_active_minus1 140bf215546Sopenharmony_ci RVCE_CS(0x00000000); // num_ref_idx_l1_active_minus1 141bf215546Sopenharmony_ci 142bf215546Sopenharmony_ci i = enc->pic.frame_num - enc->pic.ref_idx_l0_list[0]; 143bf215546Sopenharmony_ci if (i > 1 && enc->pic.picture_type == PIPE_H2645_ENC_PICTURE_TYPE_P) { 144bf215546Sopenharmony_ci RVCE_CS(0x00000001); // encRefListModificationOp 145bf215546Sopenharmony_ci RVCE_CS(i - 1); // encRefListModificationNum 146bf215546Sopenharmony_ci } else { 147bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encRefListModificationOp 148bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encRefListModificationNum 149bf215546Sopenharmony_ci } 150bf215546Sopenharmony_ci 151bf215546Sopenharmony_ci for (i = 0; i < 3; ++i) { 152bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encRefListModificationOp 153bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encRefListModificationNum 154bf215546Sopenharmony_ci } 155bf215546Sopenharmony_ci for (i = 0; i < 4; ++i) { 156bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encDecodedPictureMarkingOp 157bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encDecodedPictureMarkingNum 158bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encDecodedPictureMarkingIdx 159bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encDecodedRefBasePictureMarkingOp 160bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encDecodedRefBasePictureMarkingNum 161bf215546Sopenharmony_ci } 162bf215546Sopenharmony_ci 163bf215546Sopenharmony_ci // encReferencePictureL0[0] 164bf215546Sopenharmony_ci RVCE_CS(0x00000000); // pictureStructure 165bf215546Sopenharmony_ci if (enc->pic.picture_type == PIPE_H2645_ENC_PICTURE_TYPE_P || 166bf215546Sopenharmony_ci enc->pic.picture_type == PIPE_H2645_ENC_PICTURE_TYPE_B) { 167bf215546Sopenharmony_ci struct rvce_cpb_slot *l0 = si_l0_slot(enc); 168bf215546Sopenharmony_ci si_vce_frame_offset(enc, l0, &luma_offset, &chroma_offset); 169bf215546Sopenharmony_ci RVCE_CS(l0->picture_type); // encPicType 170bf215546Sopenharmony_ci RVCE_CS(l0->frame_num); // frameNumber 171bf215546Sopenharmony_ci RVCE_CS(l0->pic_order_cnt); // pictureOrderCount 172bf215546Sopenharmony_ci RVCE_CS(luma_offset); // lumaOffset 173bf215546Sopenharmony_ci RVCE_CS(chroma_offset); // chromaOffset 174bf215546Sopenharmony_ci } else { 175bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encPicType 176bf215546Sopenharmony_ci RVCE_CS(0x00000000); // frameNumber 177bf215546Sopenharmony_ci RVCE_CS(0x00000000); // pictureOrderCount 178bf215546Sopenharmony_ci RVCE_CS(0xffffffff); // lumaOffset 179bf215546Sopenharmony_ci RVCE_CS(0xffffffff); // chromaOffset 180bf215546Sopenharmony_ci } 181bf215546Sopenharmony_ci 182bf215546Sopenharmony_ci // encReferencePictureL0[1] 183bf215546Sopenharmony_ci RVCE_CS(0x00000000); // pictureStructure 184bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encPicType 185bf215546Sopenharmony_ci RVCE_CS(0x00000000); // frameNumber 186bf215546Sopenharmony_ci RVCE_CS(0x00000000); // pictureOrderCount 187bf215546Sopenharmony_ci RVCE_CS(0xffffffff); // lumaOffset 188bf215546Sopenharmony_ci RVCE_CS(0xffffffff); // chromaOffset 189bf215546Sopenharmony_ci 190bf215546Sopenharmony_ci // encReferencePictureL1[0] 191bf215546Sopenharmony_ci RVCE_CS(0x00000000); // pictureStructure 192bf215546Sopenharmony_ci if (enc->pic.picture_type == PIPE_H2645_ENC_PICTURE_TYPE_B) { 193bf215546Sopenharmony_ci struct rvce_cpb_slot *l1 = si_l1_slot(enc); 194bf215546Sopenharmony_ci si_vce_frame_offset(enc, l1, &luma_offset, &chroma_offset); 195bf215546Sopenharmony_ci RVCE_CS(l1->picture_type); // encPicType 196bf215546Sopenharmony_ci RVCE_CS(l1->frame_num); // frameNumber 197bf215546Sopenharmony_ci RVCE_CS(l1->pic_order_cnt); // pictureOrderCount 198bf215546Sopenharmony_ci RVCE_CS(luma_offset); // lumaOffset 199bf215546Sopenharmony_ci RVCE_CS(chroma_offset); // chromaOffset 200bf215546Sopenharmony_ci } else { 201bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encPicType 202bf215546Sopenharmony_ci RVCE_CS(0x00000000); // frameNumber 203bf215546Sopenharmony_ci RVCE_CS(0x00000000); // pictureOrderCount 204bf215546Sopenharmony_ci RVCE_CS(0xffffffff); // lumaOffset 205bf215546Sopenharmony_ci RVCE_CS(0xffffffff); // chromaOffset 206bf215546Sopenharmony_ci } 207bf215546Sopenharmony_ci 208bf215546Sopenharmony_ci si_vce_frame_offset(enc, si_current_slot(enc), &luma_offset, &chroma_offset); 209bf215546Sopenharmony_ci RVCE_CS(luma_offset); // encReconstructedLumaOffset 210bf215546Sopenharmony_ci RVCE_CS(chroma_offset); // encReconstructedChromaOffset 211bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encColocBufferOffset 212bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encReconstructedRefBasePictureLumaOffset 213bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encReconstructedRefBasePictureChromaOffset 214bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encReferenceRefBasePictureLumaOffset 215bf215546Sopenharmony_ci RVCE_CS(0x00000000); // encReferenceRefBasePictureChromaOffset 216bf215546Sopenharmony_ci RVCE_CS(0x00000000); // pictureCount 217bf215546Sopenharmony_ci RVCE_CS(enc->pic.frame_num); // frameNumber 218bf215546Sopenharmony_ci RVCE_CS(enc->pic.pic_order_cnt); // pictureOrderCount 219bf215546Sopenharmony_ci RVCE_CS(0x00000000); // numIPicRemainInRCGOP 220bf215546Sopenharmony_ci RVCE_CS(0x00000000); // numPPicRemainInRCGOP 221bf215546Sopenharmony_ci RVCE_CS(0x00000000); // numBPicRemainInRCGOP 222bf215546Sopenharmony_ci RVCE_CS(0x00000000); // numIRPicRemainInRCGOP 223bf215546Sopenharmony_ci RVCE_CS(0x00000000); // enableIntraRefresh 224bf215546Sopenharmony_ci RVCE_END(); 225bf215546Sopenharmony_ci} 226bf215546Sopenharmony_ci 227bf215546Sopenharmony_civoid si_vce_50_get_param(struct rvce_encoder *enc, struct pipe_h264_enc_picture_desc *pic) 228bf215546Sopenharmony_ci{ 229bf215546Sopenharmony_ci} 230bf215546Sopenharmony_ci 231bf215546Sopenharmony_civoid si_vce_50_init(struct rvce_encoder *enc) 232bf215546Sopenharmony_ci{ 233bf215546Sopenharmony_ci si_vce_40_2_2_init(enc); 234bf215546Sopenharmony_ci 235bf215546Sopenharmony_ci /* only the two below are different */ 236bf215546Sopenharmony_ci enc->rate_control = rate_control; 237bf215546Sopenharmony_ci enc->encode = encode; 238bf215546Sopenharmony_ci enc->si_get_pic_param = si_vce_50_get_param; 239bf215546Sopenharmony_ci} 240