def _get_param(self): container = av.open(self._stream_name) stream = [s for s in container.streams if s.type == 'video'] if len(stream) == 0: # The stream is not video acl_log.log_error("%s has no video stream" % (self._stream_name)) return const.FAILED ret, profile = self._get_profile(stream) if ret: acl_log.log_error("%s is not annex-b format, decode failed" % (self._stream_name)) return const.FAILED video_context = container.streams.video[0].codec_context codec_id_name = video_context.name ret, self._entype = self._get_entype(codec_id_name, profile) if ret: return const.FAILED self._width = video_context.width self._height = video_context.height acl_log.log_info("Get %s infomation: width %d, height %d, profile %d, " "codec %s, entype %d" % (self._stream_name, self._width, self._height, profile, codec_id_name, self._entype)) container.close() return const.SUCCESS
def _pyav_vdec(self): frame = 0 video = av.open(self._stream_name) stream = [s for s in video.streams if s.type == 'video'] acl_log.log_info("Start decode %s frames" % (self._stream_name)) for packet in video.demux([stream[0]]): # Get frame data from packet and copy to dvpp frame_data, data_size = self._prepare_frame_data(packet) if data_size == 0: # Last packet size is 0, no frame to decode anymore break if self._vdec.process(frame_data, data_size, [self._channel_id, frame]): acl_log.log_error("Dvpp vdec deocde frame %d failed, " "stop decode" % (frame)) self._status = DECODE_STATUS_ERROR break frame += 1 # The status chang to stop when app stop decode if self._status != DECODE_STATUS_RUNNING: acl_log.log_info("Decode status change to %d, stop decode" % (self._status)) break
def create_threads(detector): config = configparser.ConfigParser() config.read(FACE_DETEC_CONF) video_decoders = [] for item in config['videostream']: preprocesser = Preprocess(config['videostream'][item], len(video_decoders), MODEL_WIDTH, MODEL_HEIGHT) video_decoders.append(preprocesser) rtsp_num = len(video_decoders) if rtsp_num == 0: log_error("No video stream name or addr configuration in ", FACE_DETEC_CONF) return None, None postprocessor = Postprocess(detector) display_channel = int(config['display']['channel']) if (display_channel is None) or (display_channel >= rtsp_num): log_info("No video to display, display configuration: ", config['display']['channel']) else: video_decoders[display_channel].set_display(True) ret = postprocessor.create_presenter_channel(FACE_DETEC_CONF) if ret == False: log_error("Create presenter channel failed") return None, None return video_decoders, postprocessor
def read(self, no_wait=False): """Read decoded frame no_wait: Get image without wait. If set this arg True, and return image is None, should call is_finished() method to confirm decode finish or failed Returns: 1. const.SUCCESS, not None: get image success 2. const.SUCCESS, None: all frames decoded and be token off 3. const.FAILED, None: Has frame not decoded, but no image decoded, it means decode video failed """ image = None ret = const.SUCCESS # received eos frame and all received frame decode complete if no_wait or self.is_finished(): try: image = self._frame_queue.get_nowait() except: acl_log.log_info("No decode frame in queue anymore") else: try: image = self._frame_queue.get(timeout=READ_TIMEOUT) except: ret = const.FAILED acl_log.log_error("Read channel id %d frame timeout, " "receive frame %d, decoded %d" % (self._channel_id, self._decode_cnt, self._decode_complete_cnt)) return ret, image
def _open(self): # Get frame width, height, encode type by pyav if self._get_param(): acl_log.log_error("Decode %s failed for get stream " "parameters error" % (self._stream_name)) return # Create decode thread and prepare to decode self._decode_thread_id, ret = acl.util.start_thread( self._decode_thread_entry, []) if ret: acl_log.log_error("Create %s decode thread failed, error %d" % (self._stream_name, ret)) return # Wait decode thread decode ready for i in range(0, WAIT_READY_MAX): if self._status == DECODE_STATUS_INIT: time.sleep(WAIT_INTERVAL) if self._status == DECODE_STATUS_READY: self._is_opened = True acl_log.log_info("Ready to decode %s..." % (self._stream_name)) else: acl_log.log_error("Open %s failed for wait ready timeout" % (self._stream_name)) return
def __del__(self): self.open_status.value = STATUS_EXITING log_info("Presenter channel close...") self._send_heart_beat_message() if STATUS_OK == self._wait_open_status(STATUS_EXITTED): log_info("Presenter channel closed") else: log_error("Presenter channel close failed for presenter agent no response")
def _wait_open_status(self, listen_status): ret = STATUS_ERROR for i in range(0, 100): time.sleep(0.1) if self.open_status.value == listen_status: log_info("Open status is %d now" % (listen_status)) ret = STATUS_OK break return ret
def close(self): """Close channel""" if self.open_status == dtype.STATUS_EXITTED: return log_info("Presenter channel close...") eos = dtype.FinishMsg("exit") self.send_message(eos) while self.agent_msg_queue.qsize() > 0: time.sleep(0.001) self.open_status = dtype.STATUS_EXITTED
def _cb_thread_func(self, args_list): context, ret = acl.rt.create_context(0) if ret != 0: log_info("[INFO] cb_thread_func acl.rt.create_context ret=", ret) return while self.callback_run_flag is True: ret = acl.rt.process_report(1000) ret = acl.rt.destroy_context(context) log_info("[INFO] cb_thread_func acl.rt.destroy_context ret=", ret) self._is_thread_exit = True
def close(self): if self.open_status == STATUS_EXITTED: return log_info("Presenter channel close...") eos = FinishMsg("exit") self.send_message(eos) while self.agent_msg_queue.qsize() > 0: self._release_send_success_data() time.sleep(0.001) self.open_status = STATUS_EXITTED
def process(self, image): ret = acl.media.dvpp_set_pic_desc_data(self.dvpp_pic_desc, image.data()) ret = acl.media.dvpp_set_pic_desc_size(self.dvpp_pic_desc, image.size) log_info("[INFO] set pic desc size") # send frame ret = acl.media.venc_send_frame(self.venc_channel_desc, self.dvpp_pic_desc, 0, self.frame_config, None) utils.check_ret("acl.media.venc_send_frame", ret)
def get_channel_config(config_file): config = configparser.ConfigParser() config.read(config_file) presenter_server_ip = config['baseconf']['presenter_server_ip'] port = int(config['baseconf']['presenter_server_port']) channel_name = config['baseconf']['channel_name'] content_type = int(config['baseconf']['content_type']) log_info("presenter server ip %s, port %d, channel name %s, " "type %d" % (presenter_server_ip, port, channel_name, content_type)) return presenter_server_ip, port, channel_name, content_type
def _init_resource(self): if self._is_inited: return self.venc_channel_desc = acl.media.venc_create_channel_desc() utils.check_none("acl.media.venc_create_channel_desc", self.venc_channel_desc) self._cb_thread_id, ret = acl.util.start_thread( self._cb_thread_func, []) utils.check_ret("acl.util.start_thread", ret) log_info("[INFO] start_thread", self._cb_thread_id, ret) self._set_channel_desc() log_info("[INFO] set venc channel desc") ret = acl.media.venc_create_channel(self.venc_channel_desc) utils.check_ret("acl.media.venc_create_channel", ret) self.frame_config = acl.media.venc_create_frame_config() utils.check_none("acl.media.venc_create_frame_config", self.frame_config) log_info("[INFO] create_frame_config") # set picture description self.dvpp_pic_desc = acl.media.dvpp_create_pic_desc() utils.check_none("acl.media.dvpp_create_pic_desc", self.dvpp_pic_desc) self._set_frame_config(self.frame_config, 0, 0) log_info("[INFO] set frame config") self._get_frame_config(self.frame_config) self._is_inited = True
def finish(self): if self._is_fin: return self._set_frame_config(self.frame_config, 1, 0) # send eos frame log_info("[INFO] venc send frame eos") ret = acl.media.venc_send_frame(self.venc_channel_desc, 0, 0, self.frame_config, None) log_info("[INFO] acl.media.venc_send_frame ret=", ret) self._set_eos_stream_desc() self._thread_join() self._is_fin = True
def _thread_exit(self): self._status = STATUS_PREPROC_EXIT log_info("Channel %d thread exit..."%(self._channel)) if self._dvpp != None: del self._dvpp self._dvpp = None if self._cap != None: del self._cap self._cap = None if self._context != None: acl.rt.destroy_context(self._context) self._context = None log_info("Channel %d thread exit ok"%(self._channel))
def _start(self): thread_id, ret = acl.util.start_thread(self._thread_entry, []) utils.check_ret("acl.util.start_thread", ret) log_info("Start sub thread ok, wait init...") while self._status == STATUS_PREPROC_INIT: time.sleep(0.001) log_info("Status changed to ", self._status) while self._start == STATUS_PREPROC_RUNNING: if self._image_queue.qsize() > 0: break time.sleep(0.001) return self._status != STATUS_PREPROC_ERROR
def _thread_entry(self, args_list): self._context, ret = acl.rt.create_context(0) utils.check_ret("acl.rt.create_context", ret) ret = True while ret: data = self._data_queue.get() if isinstance(data, DetectData): ret = self._process_detect_data(data.detect_results, data.frame_data) elif isinstance(data, str): log_info("Post process thread exit") self._exit = True ret = False else: log_error("post process thread receive unkonow data")
def destroy(self): """ dvpp resource release """ if self._is_destroyed: return if self._resize_config: acl.media.dvpp_destroy_resize_config(self._resize_config) if self._dvpp_channel_desc: acl.media.dvpp_destroy_channel(self._dvpp_channel_desc) acl.media.dvpp_destroy_channel_desc(self._dvpp_channel_desc) if self._jpege_config: acl.media.dvpp_destroy_jpege_config(self._jpege_config) self._is_destroyed = True resource_list.unregister(self) log_info("dvpp resource release success")
def _init_resource(self): log_info("Init model resource start...") if not os.path.isfile(self._model_path): log_error("model_path failed, please check. model_path=%s" % self._model_path) return const.FAILED self._model_id, ret = acl.mdl.load_from_file(self._model_path) utils.check_ret("acl.mdl.load_from_file", ret) self._model_desc = acl.mdl.create_desc() ret = acl.mdl.get_desc(self._model_desc, self._model_id) utils.check_ret("acl.mdl.get_desc", ret) #get outputs num of model self._output_size = acl.mdl.get_num_outputs(self._model_desc) #create output dataset self._gen_output_dataset(self._output_size) #recode input data address,if need malloc memory,the memory will be reuseable self._init_input_buffer() log_info("Init model resource success") return const.SUCCESS
def destroy(self): """ release resource of model inference Args: null Returns: null """ if self._is_destroyed: return self._release_dataset(self._output_dataset, free_memory=True) if self._model_id: ret = acl.mdl.unload(self._model_id) if ret != const.ACL_ERROR_NONE: log_info("acl.mdl.unload error:", ret) if self._model_desc: ret = acl.mdl.destroy_desc(self._model_desc) if ret != const.ACL_ERROR_NONE: log_info("acl.mdl.destroy_desc error:", ret) self._is_destroyed = True resource_list.unregister(self) log_info("Model release source success")
def main(): #初始化acl acl_resource = AclResource() acl_resource.init() #创建一个检测网络实例,当前使用vgg_ssd网络.当更换检测网络时,在此实例化新的网络 detector = VggSsd(acl_resource, MODEL_PATH, MODEL_WIDTH, MODEL_HEIGHT) video_decoders, postprocessor = create_threads(detector) if video_decoders is None: log_error("Please check the configuration in %s is valid" % (FACE_DETEC_CONF)) return while True: all_process_fin = True for decoder in video_decoders: ret, data = decoder.get_data() if ret == False: log_info("Read data ret ", ret) continue if data: detect_results = detector.execute(data) postprocessor.process(data, detect_results) all_process_fin = False if all_process_fin: log_info("all video decoder finish") break postprocessor.exit() log_info("sample execute end")
def _prepare_frame_data(self, packet): in_frame_np = np.frombuffer(packet.to_bytes(), np.byte) size = in_frame_np.size if size == 0: # Last frame data is empty acl_log.log_info("Pyav decode finish") self._status = DECODE_STATUS_PYAV_FINISH return None, 0 in_frame_ptr = acl.util.numpy_to_ptr(in_frame_np) policy = const.ACL_MEMCPY_DEVICE_TO_DEVICE if self._run_mode == const.ACL_HOST: policy = const.ACL_MEMCPY_HOST_TO_DEVICE ret = acl.rt.memcpy(self._input_buffer, size, in_frame_ptr, size, policy) if ret: acl_log.log_error("Copy data to dvpp failed, policy %d, error %d" % (policy, ret)) self._status = DECODE_STATUS_ERROR return None, 0 return self._input_buffer, size
def _thread_entry(self, args_list): self._context, ret = acl.rt.create_context(0) utils.check_ret("acl.rt.create_context", ret) self._cap = video.AclVideo(self._stream_name) self._dvpp = Dvpp() self._status = STATUS_PREPROC_RUNNING frame_cnt = 0 while self._status == STATUS_PREPROC_RUNNING: ret, image = self._cap.read() if ret or (image is None): if ret == const.VIDEO_DECODE_FINISH: log_info("Video %s decode finish"%(self._stream_name)) self._status = STATUS_PREPROC_EXIT else: log_info("Video %s decode failed"%(self._stream_name)) self._status = STATUS_PREPROC_ERROR break if (int(frame_cnt) % 5 == 0): self._process_frame(image) time.sleep(0.0) self._thread_exit()
def _gen_output_dataset(self, ouput_num): log_info("[Model] create model output dataset:") dataset = acl.mdl.create_dataset() for i in range(ouput_num): #malloc device memory for output size = acl.mdl.get_output_size_by_index(self._model_desc, i) buf, ret = acl.rt.malloc(size, const.ACL_MEM_MALLOC_NORMAL_ONLY) utils.check_ret("acl.rt.malloc", ret) #crate oputput data buffer dataset_buffer = acl.create_data_buffer(buf, size) _, ret = acl.mdl.add_dataset_buffer(dataset, dataset_buffer) log_info("malloc output %d, size %d" % (i, size)) if ret: acl.rt.free(buf) acl.destroy_data_buffer(dataset_buffer) utils.check_ret("acl.destroy_data_buffer", ret) self._output_dataset = dataset log_info("Create model output dataset success")
def StartPresenterAgent(msg_queue, server_ip, port, open_status, data_respone_counter): """Startup presenter agent""" agent = PresenterAgent(server_ip, port) ret = agent.connect_server() if ret: log_error("Connect server failed, ret =", ret) return open_status.value = datatype.STATUS_CONNECTED while True: data = msg_queue.get() if data is None: continue if isinstance(data, datatype.FinishMsg): log_info("Receive presenter agent exit notification, queue size ", msg_queue.qsize()) time.sleep(0.1) agent.exit() break agent.socket.send_msg(data) msg_name, msg_body = agent.socket.recv_msg() if (msg_name is None) or (msg_body is None): log_error("Recv invalid message, message name ", msg_name) continue if ((open_status.value == datatype.STATUS_CONNECTED) and pm.is_open_channel_response(msg_name)): log_info("Received open channel respone") open_status.value = datatype.STATUS_OPENED agent.start_heard_beat_thread() log_info("presenter agent change connect_status to ", open_status.value) if ((open_status.value == datatype.STATUS_OPENED) and pm.is_image_frame_response(msg_name)): data_respone_counter.value += 1
def _callback_func(self, input_pic_desc, output_stream_desc, user_data): if output_stream_desc == 0: log_info("[INFO] [venc] output_stream_desc is null") return stream_data = acl.media.dvpp_get_stream_desc_data(output_stream_desc) if stream_data is None: log_info( "[INFO] [venc] acl.media.dvpp_get_stream_desc_data is none") return ret = acl.media.dvpp_get_stream_desc_ret_code(output_stream_desc) if ret == 0: stream_data_size = acl.media.dvpp_get_stream_desc_size( output_stream_desc) log_info("[INFO] [venc] stream_data size", stream_data_size) # stream memcpy d2h np_data = np.zeros(stream_data_size, dtype=np.byte) np_data_ptr = acl.util.numpy_to_ptr(np_data) ret = acl.rt.memcpy(np_data_ptr, stream_data_size, stream_data, stream_data_size, const.ACL_MEMCPY_DEVICE_TO_DEVICE) with open(self._filename, 'ab') as f: f.write(np_data)
def close(self): """Close camera""" log_info("Close camera ", self._id) libatlas.CloseCameraEx(self._id)
self.callback_run_flag = False while self._is_thread_exit == False: time.sleep(0.01) ret = acl.util.stop_thread(self._cb_thread_id) log_info("[INFO] stop_thread", ret) if __name__ == '__main__': ret = acl.init("") utils.check_ret("acl.init", ret) ret = acl.rt.set_device(DEVICE_ID) utils.check_ret("acl.rt.set_device", ret) run_mode, ret = acl.rt.get_run_mode() utils.check_ret("acl.rt.get_run_mode", ret) venc_handel = AclVenc() venc_cnt = 16 while venc_cnt: # load file image = AclImage(VENC_FILE_PATH, 1280, 720) image = image.copy_to_dvpp() venc_handel.process(image) venc_cnt -= 1 log_info("process end") venc_handel.finish() ret = acl.rt.reset_device(DEVICE_ID) utils.check_ret("acl.rt.reset_device", ret) ret = acl.finalize() utils.check_ret("acl.finalize", ret)
def _thread_join(self): self.callback_run_flag = False while self._is_thread_exit == False: time.sleep(0.01) ret = acl.util.stop_thread(self._cb_thread_id) log_info("[INFO] stop_thread", ret)