#include #include #include #include #include #ifdef _WIN32 #include "Winsock2.h" #pragma comment(lib, "ws2_32.lib") #endif #ifdef __linux__ #include "arpa/inet.h" #endif #include "../interface/FFNvDecoderManager.h" #include "../interface/utiltools.hpp" #define MIN_RTP_PORT 10000 #define MAX_RTP_PORT 60000 // ȡ MIN_RTP_PORT(10000)~MAX_RTP_PORT(60000)֮�������˿�(ż���������������˿ڿ���) int allocRtpPort() { static int s_rtpPort = MIN_RTP_PORT; if (MIN_RTP_PORT == s_rtpPort) { srand((unsigned int)time(NULL)); s_rtpPort = MIN_RTP_PORT + (rand() % MIN_RTP_PORT); } if (s_rtpPort % 2) ++s_rtpPort; while (true) { s_rtpPort += 2; s_rtpPort = s_rtpPort >= MAX_RTP_PORT ? MIN_RTP_PORT : s_rtpPort; int i = 0; for (; i < 2; i++) { sockaddr_in sRecvAddr; int s = socket(AF_INET, SOCK_DGRAM, 0); sRecvAddr.sin_family = AF_INET; sRecvAddr.sin_addr.s_addr = htonl(INADDR_ANY); sRecvAddr.sin_port = htons(s_rtpPort + i); int nResult = bind(s, (sockaddr *)&sRecvAddr, sizeof(sRecvAddr)); if (nResult != 0) { break; } nResult = close(s); if (nResult != 0) { printf("closesocket failed:%d\n", nResult); break; } } if (i == 2) break; } return s_rtpPort; } unsigned char *pHwRgb[2] = {nullptr, nullptr}; int sum1 = 0; int sum2 = 0; string data_home = "/mnt/data/cmhu/tmp/"; /** * 注意: gpuFrame 在解码器设置的显卡上,后续操作要十分注意这一点,尤其是多线程情况 * */ void postDecoded(const void * userPtr, DeviceRgbMemory* devFrame){ AbstractDecoder* decoder = (AbstractDecoder*)userPtr; if (decoder!= nullptr) { // cout << "decode name: " << decoder->getName() << endl; // const char* gpu_pixfmt = av_get_pix_fmt_name((AVPixelFormat)gpuFrame->format); // cout << "pixfmt: " << gpu_pixfmt << endl; // cout << "keyframe: " << gpuFrame->key_frame << " width: " << gpuFrame->width << " height: "<< gpuFrame->height << endl; // cout << "decode successed ✿✿ヽ(°▽°)ノ✿ " << endl; int sum = sum1; if (decoder->getName() == "dec0") { sum1 ++ ; sum = sum1; } else if (decoder->getName() == "dec2") { sum2 ++ ; sum = sum2; } } } long start_time = 0; long end_time = 0; bool count_flag = false; int count = 0; int count_std = 100; static int sum = 0; unsigned char *pHwData = nullptr; void postDecoded0(const void * userPtr, DeviceRgbMemory* devFrame){ // std::this_thread::sleep_for(std::chrono::milliseconds(30000)); AbstractDecoder* decoder = (AbstractDecoder*)userPtr; if (decoder!= nullptr) { // cout << "decode name: " << decoder->getName() << endl; if (decoder->getName() == "dec") { if (! count_flag) { count_flag = true; count = 0; end_time = start_time = UtilTools::get_cur_time_ms(); } count++; sum ++ ; if (count >= count_std) { // end_time = UtilTools::get_cur_time_ms(); // long time_using = end_time - start_time; // double time_per_frame = double(time_using)/count_std ; // cout << count_std << "帧用时:" << time_using << "ms 每帧用时:" << time_per_frame << "ms" << endl; cout << decoder->getName() << " keyframe: " << devFrame->isKeyFrame() << " width: " << devFrame->getWidth() << " height: "<< devFrame->getHeight() << endl; // cout << gpuFrame->pts << endl; count_flag = false; } // cout << "帧数:" << sum << endl; } } } void decode_finished_cbk(const void* userPtr){ cout << "当前时间戳: " << UtilTools::get_cur_time_ms() << endl; } bool decode_request_stream_cbk(const char* deviceId){ cout << "需在此请求流" << endl; return true; } // string test_uri = "rtmp://192.168.10.56:1935/objecteye/1"; // string test_uri = "/home/cmhu/data/output_800x480.mp4"; // string test_uri = "/home/cmhu/data/output_1920x1080.mp4"; // string test_uri = "rtsp://176.10.0.2:8554/stream"; // string test_uri = "/mnt/f/fiss/test_data/h265.mp4"; // string test_uri = "rtsp://176.10.0.4:8554/stream"; string test_uri = "rtsp://admin:admin@123456@192.168.60.176:554/cam/realmonitor?channel=1&subtype=0"; void createDecode(int index, const char* gpu_id){ FFNvDecoderManager* pDecManager = FFNvDecoderManager::getInstance(); MgrDecConfig config; config.name = "dec" + to_string(index); config.cfg.uri = test_uri; config.cfg.post_decoded_cbk = postDecoded; config.cfg.decode_finished_cbk = decode_finished_cbk; config.cfg.force_tcp = true; config.dec_type = DECODER_TYPE_FFMPEG; config.cfg.gpuid = gpu_id; // if (index % 2 == 0) // { // config.cfg.gpuid = "0"; // } // else // { // config.cfg.gpuid = "0"; // } AbstractDecoder* decoder = pDecManager->createDecoder(config); if (!decoder) { return ; } pDecManager->setPostDecArg(config.name, decoder); pDecManager->setFinishedDecArg(config.name, decoder); pDecManager->startDecodeByName(config.name); } void createGB28181Decode(int index, char* gpu_id, int port){ FFNvDecoderManager* pDecManager = FFNvDecoderManager::getInstance(); MgrDecConfig config; config.name = "dec" + to_string(index); config.cfg.uri = config.name; config.cfg.post_decoded_cbk = postDecoded; config.cfg.decode_finished_cbk = decode_finished_cbk; config.cfg.request_stream_cbk = decode_request_stream_cbk; config.cfg.force_tcp = true; config.dec_type = DECODER_TYPE_GB28181; config.cfg.port = port;//allocRtpPort(); config.cfg.gpuid = gpu_id; AbstractDecoder* decoder = pDecManager->createDecoder(config); if (!decoder) { return ; } pDecManager->setPostDecArg(config.name, decoder); pDecManager->setFinishedDecArg(config.name, decoder); pDecManager->startDecodeByName(config.name); } void createDvppDecoder(int index, char* devId, int channelId){ FFNvDecoderManager* pDecManager = FFNvDecoderManager::getInstance(); MgrDecConfig config; config.name = "dec" + to_string(index); config.cfg.uri = test_uri; config.cfg.post_decoded_cbk = postDecoded; config.cfg.decode_finished_cbk = decode_finished_cbk; config.cfg.force_tcp = true; config.dec_type = DECODER_TYPE_DVPP; config.cfg.gpuid = devId; AbstractDecoder* decoder = pDecManager->createDecoder(config); if (!decoder) { return ; } pDecManager->setPostDecArg(config.name, decoder); pDecManager->setFinishedDecArg(config.name, decoder); pDecManager->startDecodeByName(config.name); } void logFF(void *, int level, const char *fmt, va_list ap) { vfprintf(stdout, fmt, ap); } int main(int argc, char* argv[]){ test_uri = argv[1]; char* gpuid = argv[2]; int port = atoi(argv[3]); cout << test_uri << " gpu_id:" << gpuid << " port:" << port << endl; // av_log_set_callback(&logFF); // CheckCUDAProperty(atoi(gpuid)); pthread_t m_decode_thread; pthread_create(&m_decode_thread,0, [](void* arg) { // cudaSetDevice(atoi(gpuid)); while (true) { std::this_thread::sleep_for(std::chrono::minutes(1)); FFNvDecoderManager* pDecManager = FFNvDecoderManager::getInstance(); int count = pDecManager->count(); cout << "当前时间:" << UtilTools::get_cur_time_ms() << " 当前运行路数: " << pDecManager->count() << endl; } return (void*)0; } ,nullptr); FFNvDecoderManager* pDecManager = FFNvDecoderManager::getInstance(); int i = 0; createDvppDecoder(i, gpuid, 0); i++; while (true) { int ch = getchar(); if (ch == 'q') { break; } switch (ch) { case 'f': case 'F': createDecode(i, gpuid); i++; break; case 'g': case 'G': createGB28181Decode(i, gpuid, port); i++; break; case 'd': case 'D': createDvppDecoder(i, gpuid, 0); i++; break; case 'r': case 'R': pDecManager->resumeDecoder("dec0"); break; case 'p': case 'P': pDecManager->pauseDecoder("dec0"); break; case 'c': case 'C': i--; pDecManager->closeDecoderByName("dec" + to_string(i)); break; case 'i': case 'I': { int w,h; pDecManager->getResolution("dec0", w,h); printf( "%s : %dx%d\n", "dec0" , w,h ); } break; default: break; } /* code */ } cout << "总共帧数:" << sum << endl; pDecManager->closeAllDecoder(); }