#include "MutliSourceVideoProcess.h" #ifdef _MSC_VER #include #include #include "../putText.h" #endif #include #include #include #include #include #include "../FFNvDecoder/logger.hpp" #include "CropImg.h" // #define AUTHORIZATION //#define DQ_AUTHORIZATION #ifdef DQ_AUTHORIZATION #include "license_validator.h" #ifdef _MSC_VER #define productSN "2AC69C4638EF46c884BD2BF132FF41D9" //��ǧ����-������ȨID #else #define productSN "683E9D5E56474da5A4C2D3EA9A00568E" //��ǧ����-������ȨID #endif #endif #ifdef AUTHORIZATION #include "authority.h" #ifdef _MSC_VER #define productSN "4ACFCBE67EF645AB8F0B4CFCDD1926F1" //WINDOWS�����Ʒϵ�к� #else #define productSN "4FD45501D5104F0C8C4BE530FC872F46" //LINUX�����Ʒϵ�к� //#define productSN "7CF8B4797F9E441686145BED07F662DE" //LINUX�����Ʒϵ�к� #endif #endif #define AUTH_LICENSE "sy_va_sub_sdk_2023" static int TaskID = 0; static long long get_cur_time_ms(){ chrono::time_point tpMicro = chrono::time_point_cast(chrono::system_clock::now()); return tpMicro.time_since_epoch().count(); } void check_thread(void* handle); static void algorthim_process_thread(void* arg) { CMutliSourceVideoProcess* _this=(CMutliSourceVideoProcess*)arg; if(_this != nullptr){ _this->algorthim_process(); } else { LOG_ERROR("算法处理线程启动失败 !"); } } //std::ofstream g_os("./cudaMem.txt", std::ofstream::out | std::ofstream::trunc); CMutliSourceVideoProcess::CMutliSourceVideoProcess() { } CMutliSourceVideoProcess::~CMutliSourceVideoProcess() { //��־����ʼ�� //DxUninitializeLog(); } int CMutliSourceVideoProcess::FinishProcessThread() { if (thrd_status == 0) { m_bExit = true; thrd.join(); thrd_status = -1; } m_bProcessExit = true; ProcessThread.join(); //waiting thread finish m_vptProcess.release(); m_snaphot_helper.snapshot_helper_release(); return 1; } /* AI_LOG_LEVEL_CLOSE = -1, // 关闭日志 AI_LOG_LEVEL_TRACE = 0, // 跟踪变量 AI_LOG_LEVEL_DEBUG = 1, // 调试日志 AI_LOG_LEVEL_INFO = 2, // 普通日志信息 (如:无关紧要的信息输出) AI_LOG_LEVEL_WARNING = 3, // 警告日志通知,模块一切正常(如:重要流程通知) AI_LOG_LEVEL_ERROR = 4, // 重要日志,如结果和严重错误 */ int CMutliSourceVideoProcess::InitAlgorthim(mvpt_param vptParam, VIDEO_OBJECT_INFO_CALLBACK tObjInfoCallbackFunc, VIDEO_FINISH_CALLBACK tFinishCallbackFunc) { set_default_logger(LogLevel(1), "multi_source_process", "logs/main.log", 64 * 1024 * 1024, 30); // checkGpuMem(); licence_status = -1; thrd_status = -1; //SetUnhandledExceptionFilter(CustomExceptionCrashHandler); int ret = SUCCESS; /*DxLogConfig sCfg = { 0 }; sCfg.serviceID = vptParam.serviceID; sCfg.limitSize = vptParam.limitSize; strcpy(sCfg.name, vptParam.name); strcpy(sCfg.path, vptParam.path); DxInitializeLog(&sCfg);*/ /*printf("=====================��ȨERROR==================\n"); printf("=====================��ȨERROR==================\n"); printf("=====================��ȨERROR==================\n");*/ #ifdef AUTHORIZATION #ifdef _WIN32 if (SUCCESS == (ret = sy_licence(productSN))) #elif __linux__ char wtime[15]; memset(wtime, 0, 15); char * time = wtime; ret = sy_licence(productSN, &time); if (SUCCESS == ret) #endif #else // ret = license_check(vptParam.auth_license, productSN);// sy_time_check(2022, 2); ret = strcmp(AUTH_LICENSE, vptParam.auth_license); if (ret == SUCCESS) #endif { cuInit(0); int device_count = 0; cuDeviceGetCount(&device_count); if (vptParam.gpuid >= device_count) { printf("\nGPU_ID PARAM WRONG, gpuid: %d device_count: %d\n", vptParam.gpuid, device_count); return GPUID_PARAM_ERROR; } CUdevice dev = 0; size_t memSize = 0; dev = vptParam.gpuid; CUresult rlt = CUDA_SUCCESS; rlt = cuDeviceTotalMem(&memSize, dev); gpu_total_memory = (float)memSize / (1024 * 1024); if (gpu_total_memory < 9000) //8G�Դ棬С�ڴ淽�� section_batch_size = 10; else section_batch_size = 20; if(vptParam.skip_frame > 0){ // 默认值为5 skip_frame_ = vptParam.skip_frame; } mgpuid = vptParam.gpuid; ret = m_vptProcess.init(mgpuid, section_batch_size); if (0 != ret) return ret; viewTaskID = -1; TaskinPlay = 0; TotalTask = 0; taskFinishCallbackFunc = nullptr; if (tFinishCallbackFunc != nullptr) taskFinishCallbackFunc = std::bind(tFinishCallbackFunc, this, std::placeholders::_1); taskObjInfoCallbackFunc = nullptr; if (tObjInfoCallbackFunc != nullptr) taskObjInfoCallbackFunc = std::bind(tObjInfoCallbackFunc, this, std::placeholders::_1); m_hp_analysis_config = vptParam.hp_analysis_config; m_hcp_analysis_config = vptParam.hcp_analysis_config; m_vehicle_analysis_config = vptParam.vehicle_analysis_config; m_hf_recg_config = vptParam.hf_recg_config; m_hcf_recg_config = vptParam.hcf_recg_config; m_vcf_recg_config = vptParam.vcf_recg_config; m_face_det_config = vptParam.face_det_config; m_snaphot_helper.snapshot_helper_init(vptParam.gpuid, gpu_total_memory, vptParam.vrdbpath, vptParam.auth_license, vptParam.wait_framecount, m_hp_analysis_config, \ m_hcp_analysis_config, m_vehicle_analysis_config, m_vehicle_recg_config, m_vehicle_plate_det_recg_config, m_hf_recg_config, m_hcf_recg_config, m_vcf_recg_config, m_face_det_config); m_bProcessExit = false; ProcessThread = std::thread(algorthim_process_thread, this); if (ret == SUCCESS) //�ɹ� { licence_status = 0; #ifdef AUTHORIZATION m_bExit = false; thrd = std::thread(check_thread, this); #endif thrd_status = 0; } } else { return AUTHOR_ERROR; } /* #ifdef AUTHORIZATION #ifdef __linux__ if (wtime) { delete[] wtime; wtime = NULL; } #endif #endif */ // debug by zsh return ret; } void CMutliSourceVideoProcess::FinishDecode(const int taskID) { for (int i = 0; i < tasks.size(); i++) { if (tasks[i].taskID == taskID && tasks[taskID].taskTcuvid != NULL) { tasks[taskID].taskState == FINISH; tasks[taskID].taskTcuvid->DxCloseDecoder(); delete tasks[taskID].taskTcuvid; tasks[taskID].taskTcuvid = NULL; printf("-----------------------finish task: %d-----------------------\n", taskID); break; } } } void CMutliSourceVideoProcess::FinishTask(const int taskID) { for (int i = 0; i < tasks.size(); i++) { if (tasks[i].taskID == taskID) { //printf("first begin finish\n"); if (tasks[i].taskState == PLAY) TaskinPlay--; tasks[i].taskState = FINISH; tasks[i].taskFileSource = nullptr; tasks[i].taskObjCallbackFunc = nullptr; tasks[i].taskRealTimeCallbackFunc = nullptr; m_snaphot_helper.finish_task_ss_analysis(taskID); if (tasks[i].folderName) { delete tasks[i].folderName; tasks[i].folderName = nullptr; } if (tasks[i].folderNameLittle) { delete tasks[i].folderNameLittle; tasks[i].folderNameLittle = nullptr; } tasks[i].frameImage.release(); m_vptProcess.FinishTaskTracker(taskID); if (viewTaskID == taskID) viewTaskID = -1; break; } } } void CMutliSourceVideoProcess::PauseTask(const int taskID) { for (int i = 0; i < tasks.size(); i++) { if (tasks[i].taskID == taskID) { if (tasks[i].taskState == PLAY) TaskinPlay--; tasks[i].taskState = PAUSE; m_vptProcess.PauseTaskTracker(taskID); tasks[i].taskTcuvid->PauseDecoder(); if (viewTaskID == taskID) viewTaskID = -1; printf("-----------------------pasue task: %d-----------------------\n", taskID); break; } } } void CMutliSourceVideoProcess::RestartTask(const int taskID) { for (int i = 0; i < tasks.size(); i++) { if (tasks[i].taskID == taskID) { tasks[i].taskState = PLAY; TaskinPlay++; m_vptProcess.RestartTaskTraker(taskID); tasks[i].taskTcuvid->ResumeDecoder(); printf("-----------------------restart task: %d-----------------------\n", taskID); break; } } } //ʵʱ�鿴�ӿ� �ɿ���һ·��ʵʱ�鿴������·�ķ������OSD��Ȼ�󽫻���ͨ���ص��������ظ��û� void CMutliSourceVideoProcess::ViewTask(const int taskID) { if (tasks.size() > taskID && tasks[taskID].taskState == PLAY) { viewTaskID = taskID; printf("-----------------------view task: %d-----------------------\n", taskID); } else printf("Only can view playing task!"); } //����ʵʱ�鿴�ӿڣ��ر�ʵʱ����ķ��� void CMutliSourceVideoProcess::FinishViewTask() { viewTaskID = -1; printf("-----------------------finish view task-----------------------\n"); } bool CMutliSourceVideoProcess::AddTask(task_param tparam) //debug by zsh { const char* videoFileName = tparam.video_filename; const char* resultFolderLittle = tparam.result_folder_little; const char* resultFolder = tparam.result_folder; const char* resultFolderface = tparam.result_folder_face; VIDEO_OBJECT_SNAPSHOT_CALLBACK objCallbackFunc = tparam.obj_snapshot_callback_func; VIDEO_REALTIME_CALLBACK realTimeCallbackFunc = tparam.rt_view_callback_func; std::lock_guard l(_tx_add_task); using std::placeholders::_1; Task new_task = {}; new_task.taskID = TotalTask; new_task.taskFileSource = videoFileName; memcpy(new_task.task_min_boxsize, tparam.minBoxsize, sizeof(sy_rect)* DETECTTYPE); DxConfig cfg = { 0 }; cfg.devId = mgpuid; cfg.forceTcp = false; cfg.decMode = tparam.decMode; cfg.name = std::to_string(new_task.taskID); new_task.taskTcuvid = new DxDecoderWrap(&cfg); if (NULL == new_task.taskTcuvid) { printf("Add New DxDecoder Failed!"); AddTaskSucFlag = -1; return false; } if (new_task.taskTcuvid->DxOpenDecoder(new_task.taskFileSource, skip_frame_) != 0) { cout << "Add Task Failed! Please check you video file name!" << endl; delete new_task.taskTcuvid; new_task.taskTcuvid = NULL; AddTaskSucFlag = -1; return false; } int total_frame = new_task.taskTcuvid->DxGetFrameCount(); int width = 0; int height = 0; new_task.taskTcuvid->DxGetResolution(width, height); LOG_INFO("[{}] - finish add codec. w:{} h:{} total_frame:{}", cfg.name.c_str(), width, height, total_frame); new_task.frameImage = cv::Mat::zeros(height, width, CV_8UC3); new_task.taskState = PLAY; new_task.taskFrameCount = 0; new_task.taskLastFrameCount = 0; new_task.taskObjCallbackFunc = nullptr; if (objCallbackFunc != nullptr) new_task.taskObjCallbackFunc = std::bind(objCallbackFunc, this, std::placeholders::_1); new_task.taskRealTimeCallbackFunc = nullptr; if (realTimeCallbackFunc != nullptr) new_task.taskRealTimeCallbackFunc = std::bind(realTimeCallbackFunc, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3); new_task.taskTotalFrameCount = total_frame; if (resultFolderLittle == NULL) { new_task.folderNameLittle = NULL; } else { new_task.folderNameLittle = new char[strlen(resultFolderLittle) + 2]{}; strcpy(new_task.folderNameLittle, resultFolderLittle); int length = strlen(new_task.folderNameLittle); if (new_task.folderNameLittle[length - 1] != '\\' && new_task.folderNameLittle[length - 1] != '/') { new_task.folderNameLittle[length] = '/'; new_task.folderNameLittle[length + 1] = '\0'; } CreateResultFolder(new_task.folderNameLittle, ""); } if (resultFolder == NULL) { new_task.folderName = NULL; } else { new_task.folderName = new char[strlen(resultFolder) + 2]{}; strcpy(new_task.folderName, resultFolder); int length = strlen(new_task.folderName); if (new_task.folderName[length - 1] != '\\' && new_task.folderName[length - 1] != '/') { new_task.folderName[length] = '/'; new_task.folderName[length + 1] = '\0'; } CreateResultFolder(new_task.folderName, ""); } if (resultFolderface == NULL) { new_task.folderNameFace = NULL; } else { new_task.folderNameFace = new char[strlen(resultFolderface) + 2]{}; strcpy(new_task.folderNameFace, resultFolderface); int length = strlen(new_task.folderNameFace); if (new_task.folderNameFace[length - 1] != '\\' && new_task.folderNameFace[length - 1] != '/') { new_task.folderNameFace[length] = '/'; new_task.folderNameFace[length + 1] = '\0'; } CreateResultFolder(new_task.folderNameFace, ""); } TASK_INFO new_task_info = {}; new_task_info.image_folder = new_task.folderName; new_task_info.snapshot_folder = new_task.folderNameLittle; new_task_info.snapshot_folder_face = new_task.folderNameFace; new_task_info.task_total_framecount = new_task.taskTotalFrameCount; new_task_info._on_image_display = tparam.on_image_display; new_task_info.jpeg_quality_ = tparam.jpeg_quality; //debug by zsh new_task_info.obj_callback = new_task.taskObjCallbackFunc; m_snaphot_helper.add_task_info(new_task.taskID, new_task_info); TotalTask++; TaskinPlay++; tasks.push_back(new_task); m_vptProcess.AddTaskTracker(new_task.taskID, width, height); AddTaskSucFlag = 1; LOG_INFO("add task: {}", new_task.taskID); return true; } int CMutliSourceVideoProcess::AddOperator(task_param tparam) { { // printf("add first task in operator queue\n"); std::unique_lock l(taskMutex); AddTaskSucFlag = 0; Operator newOper; newOper.changeTaskID = 0; newOper.changeTaskOperator = ADDTASK; strcpy(newOper.videoFileName, tparam.video_filename); strcpy(newOper.resultFolderLittleName, tparam.result_folder_little); strcpy(newOper.resultFolderName, tparam.result_folder); strcpy(newOper.result_folder_face, tparam.result_folder_face); newOper.on_image_display = tparam.on_image_display; newOper.jpeg_quality = tparam.jpeg_quality; newOper.decMode = tparam.decMode; newOper.taskObjCallbackFunc = tparam.obj_snapshot_callback_func; newOper.taskRealTimeCallbackFunc = tparam.rt_view_callback_func; memcpy(newOper.minBoxsize, tparam.minBoxsize, sizeof(sy_rect)* DETECTTYPE); TaskOperatorQ.push_back(newOper); taskCondVar.wait_for(l, std::chrono::seconds(20)); } int addRes = -1; int newTaskID = TaskID++; if (AddTaskSucFlag == 1) { addRes = newTaskID; } else if (AddTaskSucFlag == -1) { addRes = -1; TaskID--; } else if (AddTaskSucFlag == 0) { Operator newOper = TaskOperatorQ.back(); if (strcmp(newOper.videoFileName, tparam.video_filename) == 0) { TaskOperatorQ.pop_back(); } cout << "Failed Add New Task! Algorithm Process Error! " << endl; } return addRes; } int CMutliSourceVideoProcess::get_task_progress(int taskid, double &progress) { int ret = 0; for (auto &item : tasks) { if (item.taskID == taskid) { progress = (double)item.taskFrameCount / (double)item.taskTotalFrameCount; return 0; } } return -1; } void CMutliSourceVideoProcess::AddOperator(int taskID, int taskOper) { if (taskOper > 0 && taskOper < 4) { Operator newOper = {}; newOper.changeTaskID = taskID; newOper.changeTaskOperator = TaskOperator(taskOper); //TaskOperatorQ.push(newOper); TaskOperatorQ.push_back(newOper); } } void CMutliSourceVideoProcess::OperatorTask() { while (!TaskOperatorQ.empty()) { Operator newOperator = TaskOperatorQ.front(); TaskOperatorQ.pop_front(); switch (newOperator.changeTaskOperator) { case ADDTASK: { task_param tparam; strcpy(tparam.video_filename, newOperator.videoFileName); strcpy(tparam.result_folder_little, newOperator.resultFolderLittleName); strcpy(tparam.result_folder, newOperator.resultFolderName); strcpy(tparam.result_folder_face, newOperator.result_folder_face); tparam.on_image_display = newOperator.on_image_display; tparam.jpeg_quality = newOperator.jpeg_quality; memcpy(tparam.minBoxsize, newOperator.minBoxsize, sizeof(sy_rect)* DETECTTYPE); tparam.obj_snapshot_callback_func = newOperator.taskObjCallbackFunc; tparam.rt_view_callback_func = newOperator.taskRealTimeCallbackFunc; tparam.decMode = newOperator.decMode; AddTask(tparam); } break; case PAUSETASK: PauseTask(newOperator.changeTaskID); break; case RESTARTTASK: RestartTask(newOperator.changeTaskID); break; case FINISHTASK: FinishTask(newOperator.changeTaskID); break; default: break; } } } //#define LOG_INFO void CMutliSourceVideoProcess::callTaskObjInfoCallbackFunc(int objCount, VPT_ObjInfo *obj, int taskFrameCount, int taskId) { if (objCount == 0) { video_object_info newObjInfo; newObjInfo.task_id = taskId; newObjInfo.task_frame_count = taskFrameCount; newObjInfo.object_id = -1; newObjInfo.left = 0; newObjInfo.right = 0; newObjInfo.top = 0; newObjInfo.bottom = 0; newObjInfo.index = 0; newObjInfo.confidence = 0; if (taskObjInfoCallbackFunc != nullptr) taskObjInfoCallbackFunc(&newObjInfo); } else { for (int c = 0; c < objCount; c++) { OBJ_KEY newObj = { taskId, obj[c].id }; video_object_info newObjInfo; newObjInfo.task_id = taskId; newObjInfo.task_frame_count = taskFrameCount; newObjInfo.object_id = obj[c].id; newObjInfo.left = obj[c].left; newObjInfo.right = obj[c].right; newObjInfo.top = obj[c].top; newObjInfo.bottom = obj[c].bottom; int index = m_snaphot_helper.getIndexByKey(newObj); if(index < 0) { newObjInfo.index = obj[c].index; } else { newObjInfo.index = index; } newObjInfo.confidence = obj[c].confidence; if (taskObjInfoCallbackFunc != nullptr) { taskObjInfoCallbackFunc(&newObjInfo); } } } } void CMutliSourceVideoProcess::algorthim_process() { set k; int count = 0; DxGPUFrame frame = {}; cudaSetDevice(mgpuid); int total_count = 0; long long begintime1 =get_cur_time_ms(); int process_times = 0; long long last_time = get_cur_time_ms(); while (!m_bProcessExit) { if (licence_status <= -3) { printf("authority failed!\n"); break; } double time_val, time_val_p = 0; { std::lock_guard l(taskMutex); OperatorTask(); } taskCondVar.notify_all(); int curTaskSize = tasks.size(); count = 0; static int ncount = 0; map> finishTaskDeleteObj; int curPlayTaskCount = 0; for (int i = 0; i < curTaskSize; i++) { if ((tasks[i].taskState == PLAY || tasks[i].taskState == DECODEERROR)) { if (!tasks[i].taskTcuvid->DxDecoderIsRun()) { cudaError_t cudaStatus = cudaGetLastError(); if (cudaStatus != cudaSuccess) { printf("begin finish last error: %s\n", cudaGetErrorString(cudaStatus)); } cout << "***************** Task " << i << " is Finished *****************" << endl; tasks[i].taskState = FINISH; FinishTask(tasks[i].taskID); tasks[i].taskTcuvid->DxCloseDecoder(); delete tasks[i].taskTcuvid; tasks[i].taskTcuvid = NULL; m_snaphot_helper.waitSaveAnalysisInfo(tasks[i].taskID); //回调通知上层任务结束 if (taskFinishCallbackFunc != nullptr) { std::lock_guard l(m_snaphot_helper.callback_tx); taskFinishCallbackFunc(tasks[i].taskID); } TaskinPlay--; } } if (tasks[i].taskState == FINISH) count++; } //�������������FINISH״̬ if (count >= tasks.size()) //have no decode video, break { { std::lock_guard l(taskMutex); //�ж���������ȴ������Ƿ����µ��������� if (HasNewTask()) { continue; } else { continue; } } } //��ǰû��PLAY������ ѭ���ȴ� curPlayTaskCount = TaskinPlay; if (curPlayTaskCount <= 0) { Sleep(30); continue; } k.clear(); TaskinPlayID.clear(); //��ȡ�������� getdata_flag: for (int i = 0; i < curTaskSize; i++) { if (k.find(i) == k.end() && tasks[i].taskState == PLAY && tasks[i].taskTcuvid->DxDecoderIsRun()) { if(tasks[i].taskTcuvid->DxLockFrame(tasks[i].task_algorithm_data) == 0) { k.insert(i); TaskinPlayID.insert(tasks[i].taskID); } } else if (k.find(i) == k.end() && tasks[i].taskState == PLAY && !tasks[i].taskTcuvid->DxDecoderIsRun()) { tasks[i].taskState = DECODEERROR; curPlayTaskCount--; m_vptProcess.FinishTaskTracker(tasks[i].taskID); } } if (curPlayTaskCount <= 0) { Sleep(30); continue; } //��û�л�ȡ������·���Ľ������� ѭ���ȴ� if (k.size() < curPlayTaskCount) { std::this_thread::sleep_for(std::chrono::milliseconds(1)); goto getdata_flag; } #ifdef LOG_INFO2 long long gather_data_time = get_cur_time_ms(); std::cout << "gather_data time_using: " << gather_data_time - last_time << std::endl; #endif cudaDeviceSynchronize(); int cur_batch_size = 0; cur_batch_size = section_batch_size; if (0) { if (section_batch_size == 20) cur_batch_size = section_batch_size; else { if (curPlayTaskCount <= 2 * section_batch_size) cur_batch_size = section_batch_size; else if (curPlayTaskCount >= 2 * MAX_BATCH) cur_batch_size = MAX_BATCH; else cur_batch_size = curPlayTaskCount / 2 + (curPlayTaskCount % 2); } } long long start_time_vpt = get_cur_time_ms(); set::iterator iter = TaskinPlayID.begin(); int task_in_play_size = TaskinPlayID.size(); vector> deleteObjectID(task_in_play_size); vector batch_img(task_in_play_size); vector> unUsedResult(task_in_play_size); vector VPTResult(task_in_play_size); vector vec_frameIndex; for (size_t i = 0; i < TaskinPlayID.size(); i++) { DxGPUFrame task_algorithm_data = tasks[*iter].task_algorithm_data; int w = task_algorithm_data.width; int h = task_algorithm_data.height; int npitch = task_algorithm_data.size; batch_img[i].set_data(w, h, 3, (unsigned char *)task_algorithm_data.frame); vec_frameIndex.push_back(task_algorithm_data.timestamp); iter++; } int flag = m_vptProcess.process(batch_img.data(), batch_img.size(), vec_frameIndex, VPTResult, deleteObjectID, unUsedResult); #ifdef LOG_INFO2 std::cout << "VPT_Process_GPU time_using: " << get_cur_time_ms() - start_time_vpt << std::endl; #endif long long result_analysis_time = get_cur_time_ms(); iter = TaskinPlayID.begin(); for (int i = 0; i < curPlayTaskCount; i++) { Task task = tasks[*iter]; task.taskFrameCount = task.task_algorithm_data.timestamp; //若该路任务当前帧未检测到目标,返回ID为-1的目标表明未检测到目标 if (VPTResult[i].objCount == 0) { callTaskObjInfoCallbackFunc(0, nullptr, task.taskFrameCount, *iter); } //实时查看模块,若存在实时查看,把当前视频画面cp回内存 bool view = false; int frameHeight = task.task_algorithm_data.height; int frameWidth = task.task_algorithm_data.width; if (*iter == viewTaskID) { cudaMemcpy(task.frameImage.data, task.task_algorithm_data.frame, 3 * frameWidth * frameHeight * sizeof(unsigned char), cudaMemcpyDeviceToHost); view = true; } //跟踪帧也需要返回跟踪的结果 if (task.taskLastFrameCount > 0) { vector OneUnUsedResult = unUsedResult[i]; if (OneUnUsedResult.size() == 0) { callTaskObjInfoCallbackFunc(0, nullptr, task.taskLastFrameCount + 1, *iter); } for (int k = 0; k < OneUnUsedResult.size(); ++k) { if (OneUnUsedResult[k].objCount == 0) { callTaskObjInfoCallbackFunc(0, nullptr, task.taskLastFrameCount + k + 1, *iter); } else { //cout << "OneUnUsedResult.size = " << OneUnUsedResult.size() << " k=" << k << " OneUnUsedResult[k].objCount = " << OneUnUsedResult[k].objCount << endl; callTaskObjInfoCallbackFunc(OneUnUsedResult[k].objCount, OneUnUsedResult[k].obj, task.taskLastFrameCount + k + 1, *iter); } } } task.taskLastFrameCount = task.taskFrameCount; unsigned char* snapshot_image_data[MAX_OBJ_COUNT]{}; int snapshot_left[MAX_OBJ_COUNT]{}; int snapshot_right[MAX_OBJ_COUNT]{}; int snapshot_top[MAX_OBJ_COUNT]{}; int snapshot_bottom[MAX_OBJ_COUNT]{}; int snapshot_dst_width[MAX_OBJ_COUNT]{}; int snapshot_dst_height[MAX_OBJ_COUNT]{}; int copy_obj_count = 0; //用于记录该路有多少个目标需要进行显存图像的更新 vector human_idx; //用于记录快照数组中那些是人脸 vector human_obj_keys; callTaskObjInfoCallbackFunc(VPTResult[i].objCount, VPTResult[i].obj, task.taskFrameCount, *iter); for (int c = 0; c < VPTResult[i].objCount; c++) { VPT_ObjInfo obj = VPTResult[i].obj[c]; OBJ_KEY newObj = { (*iter), obj.id }; //实时查看模块 绘制目标框到画面上 if (view) { int index = m_snaphot_helper.getIndexByKey(newObj); if(index < 0) { index = obj.index; } //cout << "---- vew ---- "; int p1 = obj.left - 10 > 0 ? obj.left - 10 : 0; int p2 = obj.top - 15 > 0 ? obj.top - 15 : 0; cv::rectangle(task.frameImage, Rect(obj.left, obj.top, obj.right - obj.left, obj.bottom - obj.top), Scalar(158, 52, 254), 3, 1, 0); #ifdef _MSC_VER string resss = "" + to_string(index) + " " + ObjTypes[index]; putTextZH(task.frameImage, resss.c_str(), { p1, p2 }, Scalar(20, 255, 20), 14, "Arial"); #else string resss = "" + to_string(obj.id) + " " + ObjTypesEnglish[obj.index]; cv::putText(task.frameImage, resss.c_str(), cv::Point(p1, p2), cv::FONT_HERSHEY_COMPLEX, 2, Scalar(20, 255, 20), 2, 8, 0); #endif } CropInfo crop_info = m_snaphot_helper.cacheSnapShotInfo(newObj, obj, task); if(crop_info.bCrop){ snapshot_image_data[copy_obj_count] = crop_info.snapshot_image_data; snapshot_left[copy_obj_count] = crop_info.snapshot_left; snapshot_top[copy_obj_count] = crop_info.snapshot_top; snapshot_right[copy_obj_count] = crop_info.snapshot_right; snapshot_bottom[copy_obj_count] = crop_info.snapshot_bottom; snapshot_dst_width[copy_obj_count] = crop_info.snapshot_dst_width; snapshot_dst_height[copy_obj_count] = crop_info.snapshot_dst_height; int index = m_snaphot_helper.getIndexByKey(newObj); if(0 == index) { human_idx.push_back(copy_obj_count); human_obj_keys.emplace_back(newObj); } copy_obj_count++; } } //若待抠图的快照数不为0 则进行批量抠图 if (0 != copy_obj_count) { PartMemResizeBatch((unsigned char*)task.task_algorithm_data.frame, frameWidth, frameHeight, snapshot_image_data, copy_obj_count, snapshot_left, snapshot_top, snapshot_right, snapshot_bottom, snapshot_dst_width, snapshot_dst_height, 0, 0, 0, 1, 1, 1); //最新刚添加的人脸检测模块,针对存在的行人快照进行人脸检测+人脸快照框的优选 if (m_face_det_config == SY_CONFIG_OPEN && !human_idx.empty()) { //需要做人脸检测 int human_count = human_idx.size(); sy_img human_img[human_count]; sy_point ori_points[human_count]; for (int idx = 0; idx < human_count; idx++) { int ii = human_idx[idx]; human_img[idx].set_data(snapshot_dst_width[ii], snapshot_dst_height[ii], 3, snapshot_image_data[ii]); ori_points[idx].x_ = (snapshot_right[ii] - snapshot_left[ii]); ori_points[idx].y_ = (snapshot_bottom[ii] - snapshot_top[ii]); } m_snaphot_helper.cacheFaceSnapshotInfo(human_img, human_count, ori_points, human_idx, human_obj_keys, snapshot_left, snapshot_top, task); } } //实时查看 绘制目标轨迹 回调函数返回 if (view) { m_vptProcess.DrawTracker(*iter, &task.frameImage); if (task.taskRealTimeCallbackFunc != nullptr) task.taskRealTimeCallbackFunc(task.frameImage.data, task.frameImage.rows, task.frameImage.cols); } // tasks[*iter].taskFrameCount += skip_frame_; iter++; } #ifdef LOG_INFO2 long long result_analysis_time2 = get_cur_time_ms(); cout << "result_analysis time_using:" << result_analysis_time2 - result_analysis_time << endl; #endif long long second_analysis_time = get_cur_time_ms(); auto task_iter = TaskinPlayID.begin(); for (int i = 0; i < curPlayTaskCount; i++) { for (int j = 0; j < deleteObjectID[i].size(); j++) { OBJ_KEY deleteObj = { *task_iter, deleteObjectID[i][j] }; m_snaphot_helper.SaveResultInFile(deleteObj); } task_iter++; } for (auto task_id: TaskinPlayID) { cudaFree(tasks[task_id].task_algorithm_data.frame); tasks[task_id].task_algorithm_data.frame = nullptr; } m_snaphot_helper.object_attri_analysis(); cudaError_t cudaStatus = cudaGetLastError(); if (cudaStatus != cudaSuccess) { LOG_ERROR("object_attri_analysis last error: {}", cudaGetErrorString(cudaStatus)); } #ifdef LOG_INFO2 long long second_analysis_time2 = get_cur_time_ms(); cout << "second_analysis time_using:" << second_analysis_time2 - second_analysis_time << endl; #endif ++total_count; ++ncount; #ifdef LOG_INFO2 last_time = get_cur_time_ms(); cout << "process time_using:" << last_time - gather_data_time << endl; cout << endl; #endif } m_snaphot_helper.clearSnapshotInfo(); long long costTime1 = get_cur_time_ms() - begintime1; LOG_INFO("Process Thread is Finished. total frame cost time = {} ms, process times: {}", costTime1, process_times); } int CMutliSourceVideoProcess::GetRuningNb() { int no = 0; for(int i=0; i < tasks.size(); i++){ if(tasks[i].taskState == PLAY){ no ++; } } return no; } #ifdef AUTHORIZATION void check_thread(void* handle) { int res = -1; #ifndef _MSC_VER char wtime[15]; memset(wtime, 0, 15); char * time = wtime; #endif CMutliSourceVideoProcess *_this = (CMutliSourceVideoProcess *)handle; while (!_this->m_bExit) { //printf("xxx check status on process...\n"); #ifdef _MSC_VER res = sy_licence(productSN); #else res = sy_licence(productSN, &time); //printf("--------------wtime in thread: %s, status: %d\n", wtime, licence_status); #endif if (res < 0) { _this->licence_status = _this->licence_status - 1; printf("CMutliSourceVideoProcess licence error, ret: %d \n", res); } else { if (_this->licence_status < 0) { _this->licence_status = 0; } } std::this_thread::sleep_for(std::chrono::seconds(300)); } } #endif