1/* 2 * Copyright (c) 2023 Shenzhen Kaihong Digital Industry Development Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16#include <fstream> 17#include <functional> 18#include <getopt.h> 19#include <stdio.h> 20#include <stdlib.h> 21#include <string.h> 22#include <unistd.h> 23#include "codec_factory.h" 24#include "common/sharing_log.h" 25#include "frame.h" 26#include "media_frame_pipeline.h" 27 28using namespace OHOS::Sharing; 29 30char *gInFile = nullptr; 31char *gOutFile = nullptr; 32int gType = -1; // 0 for decode, 1 for encode 33 34void ShowUsage(char *exe) 35{ 36 SHARING_LOGD("usage:\n%{public}s -t <type> -i <in file> -o <out file>", exe); 37 SHARING_LOGD("\t-t 0: decode G.711, 1: encode G.711, 2:decode AAC-ADTS"); 38 SHARING_LOGD("\t-i in file"); 39 SHARING_LOGD("\t-o out file"); 40} 41 42int ParseParam(int argc, char *argv[]) 43{ 44 int ret; 45 46 while ((ret = getopt(argc, argv, ":t:i:o:")) != -1) { 47 switch (ret) { 48 case ('t'): 49 gType = atoi(optarg); 50 break; 51 case ('i'): 52 gInFile = optarg; 53 break; 54 case ('o'): 55 gOutFile = optarg; 56 break; 57 case ':': 58 SHARING_LOGD("option [-%c] requires an argument.", static_cast<char>(optopt)); 59 break; 60 case '?': 61 SHARING_LOGD("unknown option: %c.", static_cast<char>(optopt)); 62 break; 63 default: 64 break; 65 } 66 } 67 68 if ((gType > 2 || gType < 0) || gInFile == nullptr || gOutFile == nullptr) { 69 SHARING_LOGD("param error"); 70 ShowUsage(argv[0]); 71 return -1; 72 } 73 74 return 0; 75} 76 77class RawDataReceiver : public FrameDestination { 78public: 79 RawDataReceiver(std::fstream &fd) : fd_(fd) {} 80 ~RawDataReceiver() = default; 81 void OnFrame(const Frame::Ptr &frame) override 82 { 83 fd_.write((char *)frame->Data(), frame->Size()); 84 SHARING_LOGD("write data(%{public}p) len(%{public}d)", frame->Data(), frame->Size()); 85 } 86 87private: 88 std::fstream &fd_; 89}; 90 91void DecodeG711(char *data, int length, std::fstream &fd) 92{ 93 std::shared_ptr<AudioDecoder> decoder = CodecFactory::CreateAudioDecoder(CODEC_G711A); 94 if (!decoder) { 95 return; 96 } 97 decoder->Init(); 98 99 auto rawReceiver = std::make_shared<RawDataReceiver>(fd); 100 101 decoder->AddAudioDestination(rawReceiver); 102 auto g711Frame = FrameImpl::Create(); 103 g711Frame->codecId_ = CODEC_G711A; 104 char *p = data; 105 for (int i = 0; i < length / 160; i++) { 106 SHARING_LOGD("for i(%{public}d)", i); 107 g711Frame->Clear(); 108 g711Frame->Assign(p, 160); 109 decoder->OnFrame(g711Frame); 110 p += 160; 111 } 112 SHARING_LOGD("decodeG711 line(%{public}d).", __LINE__); 113} 114 115void DecodeAAC(char *data, int length, std::fstream &fd) 116{ 117 std::shared_ptr<AudioDecoder> decoder = CodecFactory::CreateAudioDecoder(OHOS::Sharing::CODEC_AAC); 118 if (!decoder) { 119 return; 120 } 121 decoder->Init(); 122 123 auto rawReceiver = std::make_shared<RawDataReceiver>(fd); 124 125 decoder->AddAudioDestination(rawReceiver); 126 auto aacFrame = FrameImpl::Create(); 127 aacFrame->codecId_ = CODEC_AAC; 128 char *p = data; 129 for (int i = 0; i < length / 2048; i++) { 130 SHARING_LOGD("for i(%{public}d)", i); 131 aacFrame->Clear(); 132 aacFrame->Assign(p, 2048); 133 decoder->OnFrame(aacFrame); 134 p += 2048; 135 } 136 SHARING_LOGD("decodeAAC line(%{public}d).", __LINE__); 137} 138 139void EncodeG711(char *data, int length, std::fstream &fd) 140{ 141 std::shared_ptr<AudioEncoder> encoder = CodecFactory::CreateAudioEncoder(CODEC_G711A); 142 if (!encoder) { 143 return; 144 } 145 encoder->Init(); 146 147 auto rawReceiver = std::make_shared<RawDataReceiver>(fd); 148 149 encoder->AddAudioDestination(rawReceiver); 150 151 auto pcmFrame = FrameImpl::Create(); 152 pcmFrame->codecId_ = CODEC_PCM; 153 char *p = data; 154 for (int i = 0; i < length / 320; i++) { 155 SHARING_LOGD("for i(%{public}d)", i); 156 pcmFrame->Clear(); 157 pcmFrame->Assign(p, 320); 158 encoder->OnFrame(pcmFrame); 159 p += 320; 160 } 161 SHARING_LOGD("decodeG711 line(%{public}d).", __LINE__); 162} 163 164int main(int argc, char *argv[]) 165{ 166 SHARING_LOGD("hello codec_demo."); 167 if (ParseParam(argc, argv) != 0) { 168 return -1; 169 } 170 171 std::fstream infile(gInFile, std::ios::in | std::ios_base::binary); 172 if (!infile.is_open()) { 173 SHARING_LOGD("failed to open file"); 174 return -1; 175 } 176 177 std::fstream outfile(gOutFile, std::ios::out | std::ios_base::binary); 178 if (!outfile.is_open()) { 179 SHARING_LOGD("failed to open file"); 180 return -1; 181 } 182 183 infile.seekg(0, std::ios::end); 184 int size = infile.tellg(); 185 infile.seekg(0, std::ios::beg); 186 187 char *content = new char[size]; 188 infile.read(content, size); 189 SHARING_LOGD("size %{public}d.", size); 190 infile.close(); 191 if (gType == 0) { 192 DecodeG711(content, size, outfile); 193 } else if (gType == 1) { 194 EncodeG711(content, size, outfile); 195 } else if (gType == 2) { 196 DecodeAAC(content, size, outfile); 197 } 198 199 outfile.close(); 200 delete[] content; 201} 202