Beispiel #1
0
void
sh_css_sp_init_pipeline(struct sh_css_pipeline *me,
			enum ia_css_pipe_id id,
			uint8_t pipe_num,
			bool preview_mode,
			bool low_light,
			bool xnr,
			bool two_ppc,
			bool continuous,
			bool offline,
			bool input_needs_raw_binning,
			enum sh_css_pipe_config_override copy_ovrd,
			enum ia_css_input_mode input_mode,
			const mipi_port_ID_t port_id)
{
	/* Get first stage */
	struct sh_css_pipeline_stage *stage;
	struct sh_css_binary	     *first_binary = me->stages->binary;
	unsigned num;

	enum ia_css_pipe_id pipe_id = id;
	unsigned int thread_id;
	uint8_t if_config_index;

	if (input_mode == IA_CSS_INPUT_MODE_SENSOR
		|| input_mode == IA_CSS_INPUT_MODE_BUFFERED_SENSOR) {
		if_config_index  = (uint8_t) (port_id - MIPI_PORT0_ID);
	} else if (input_mode == IA_CSS_INPUT_MODE_MEMORY){
		if_config_index = SH_CSS_IF_CONFIG_NOT_NEEDED;
	} else if_config_index = 0x0;

	sh_css_query_sp_thread_id(pipe_num, &thread_id);
	memset(&sh_css_sp_group.pipe[thread_id], 0, sizeof(struct sh_css_sp_pipeline));

	/* Count stages */
	for (stage = me->stages, num = 0; stage; stage = stage->next, num++) {
		stage->stage_num = num;
		sh_css_debug_pipe_graph_dump_stage(stage, id);
	}
	me->num_stages = num;

	if (first_binary != NULL) {
	/* Init pipeline data */
		sh_css_sp_init_group(two_ppc, first_binary->input_format, offline, if_config_index);
	/* for Capture, do we need to add more modes like */
		if (continuous &&
			(first_binary->info->mode == SH_CSS_BINARY_MODE_PREVIEW ||
			 first_binary->info->mode == SH_CSS_BINARY_MODE_PRIMARY)) {
#if 0
			sh_css_sp_start_raw_copy(first_binary, first_args->cc_frame,
				two_ppc, input_needs_raw_binning,
				copy_ovrd);
			sh_css_debug_pipe_graph_dump_sp_raw_copy(first_args->cc_frame);
#endif
		}
	} /* if (first_binary != NULL) */

	/* Init stage data */
	sh_css_init_host2sp_frame_data();

	sh_css_sp_group.pipe[thread_id].num_stages = 0;
	sh_css_sp_group.pipe[thread_id].pipe_id = pipe_id;
	sh_css_sp_group.pipe[thread_id].thread_id = thread_id;
	sh_css_sp_group.pipe[thread_id].pipe_num = pipe_num;
	sh_css_sp_group.pipe[thread_id].input_system_mode
						= (uint32_t)input_mode;
	sh_css_sp_group.pipe[thread_id].port_id = port_id;
	sh_css_sp_group.pipe[thread_id].dvs_frame_delay = (uint32_t)me->dvs_frame_delay;
	
	/* TODO: next indicates from which queues parameters need to be
		 sampled, needs checking/improvement */
	if (sh_css_pipe_uses_params(me)) {
		sh_css_sp_group.pipe[thread_id].pipe_config =
			SH_CSS_PIPE_CONFIG_SAMPLE_PARAMS << thread_id;
	}

	/* For continuous use-cases, SP copy is responsible for sampling the
	 * parameters */
	if (continuous)
		sh_css_sp_group.pipe[thread_id].pipe_config = 0;

	for (stage = me->stages, num = 0; stage; stage = stage->next, num++) {
		sh_css_sp_group.pipe[thread_id].num_stages++;
		if (is_sp_stage(stage)) {
			sp_init_sp_stage(stage, pipe_num, two_ppc, input_needs_raw_binning,
				copy_ovrd, if_config_index);
		} else {
			sp_init_stage(stage, pipe_num, num, preview_mode,
					low_light, xnr, if_config_index);
		}

		store_sp_stage_data(pipe_id, pipe_num, num);
	}
	store_sp_group_data();

}
Beispiel #2
0
static enum sh_css_err
sh_css_sp_init_stage(struct sh_css_binary *binary,
		    const char *binary_name,
		    const struct sh_css_blob_info *blob_info,
		    const struct sh_css_binary_args *args,
		    enum sh_css_pipe_id id,
		    unsigned stage,
		    bool preview_mode,
		    bool low_light,
		    bool xnr,
		    unsigned irq_buf_flags,
		    const struct sh_css_hmm_isp_interface *isp_mem_if)
{
	const struct sh_css_binary_info *info = binary->info;
	enum sh_css_err err = sh_css_success;
	int i;

	enum sh_css_pipe_id pipe_id = id;
	unsigned int thread_id;
	bool continuous = sh_css_continuous_is_enabled();
	{
		/**
		 * Clear sh_css_sp_stage for easy debugging.
		 * program_input_circuit must be saved as it is set outside
		 * this function.
		 */
		unsigned int program_input_circuit;
		program_input_circuit = sh_css_sp_stage.program_input_circuit;
		memset(&sh_css_sp_stage, 0, sizeof(sh_css_sp_stage));
		sh_css_sp_stage.program_input_circuit = program_input_circuit;
	}

	sh_css_query_sp_thread_id(pipe_id, &thread_id);
	sh_css_sp_group.pipe[thread_id].num_stages++;

	if (info == NULL) {
		sh_css_sp_group.pipe[thread_id].sp_stage_addr[stage] = mmgr_NULL;
		return sh_css_success;
	}

	sh_css_sp_stage.deinterleaved = stage == 0 &&
					sh_css_continuous_is_enabled();

	/*
	 * TODO: Make the Host dynamically determine
	 * the stage type.
	 */
	sh_css_sp_stage.stage_type = SH_CSS_ISP_STAGE_TYPE;
	sh_css_sp_stage.num		= stage;
	sh_css_sp_stage.isp_online	= binary && binary->online;
	sh_css_sp_stage.isp_copy_vf     = args->copy_vf;
	sh_css_sp_stage.isp_copy_output = args->copy_output;
	/* These flags wil be set from the css top level */
	sh_css_sp_stage.irq_buf_flags   = irq_buf_flags;

	/* Copy the frame infos first, to be overwritten by the frames,
	   if these are present.
	*/
	sh_css_frame_info_to_sp(&sh_css_sp_stage.frames.in.info,
				&binary->in_frame_info);
	sh_css_frame_info_to_sp(&sh_css_sp_stage.frames.out.info,
				&binary->out_frame_info);
	sh_css_frame_info_to_sp(&sh_css_sp_stage.frames.internal_frame_info,
				&binary->internal_frame_info);
	sh_css_sp_stage.dvs_envelope.width    = binary->dvs_envelope.width;
	sh_css_sp_stage.dvs_envelope.height   = binary->dvs_envelope.height;
	sh_css_sp_stage.isp_deci_log_factor   = binary->deci_factor_log2;
	sh_css_sp_stage.isp_vf_downscale_bits = binary->vf_downscale_log2;

	sh_css_sp_stage.sp_enable_xnr = xnr;
/*	sh_css_sp_stage.uds.extra_vectors   = info->uds.extra_vectors; */ /* task 3340 */
	sh_css_sp_stage.xmem_bin_addr = info->xmem_addr;
	sh_css_sp_stage.xmem_map_addr = sh_css_params_ddr_address_map();
	sh_css_sp_stage.anr	      = low_light;
	sh_css_isp_stage.blob_info = *blob_info;
	sh_css_stage_write_binary_info((struct sh_css_binary_info *)info);
	memcpy(sh_css_isp_stage.binary_name, binary_name,
		strlen(binary_name)+1);
	memcpy(&sh_css_isp_stage.mem_interface, isp_mem_if,
		sizeof(sh_css_isp_stage.mem_interface));

#if 0
	{
		struct sh_css_vector motion;
		struct sh_css_zoom zoom;

		sh_css_get_zoom(&zoom);
		sh_css_get_dis_motion(&motion);

		sh_css_update_uds_and_crop_info(binary->info,
					&binary->in_frame_info,
					&binary->out_frame_info,
					&binary->dvs_envelope,
					preview_mode,
					&zoom,
					&motion,
					&sh_css_sp_stage.uds,
					&sh_css_sp_stage.sp_out_crop_pos);
	}
#else
	/**
	 * Even when a stage does not need uds and does not params,
	 * sp_uds_init() seems to be called (needs further investigation)
	 * This function can not deal with dx, dy = {0, 0}
	 */
	(void)preview_mode;
#if 0
	sh_css_sp_stage.uds =
		(struct sh_css_uds_info){HRT_GDC_N, HRT_GDC_N, 0, 0};
#endif

#endif

	sh_css_params_set_current_binary(binary);

	/* Clean static frame info before we update it */
	/*
	 * TODO: Initialize the static frame data with
	 * "sh_css_frame_null".
	 */
	for (i = 0; i < SH_CSS_NUM_FRAME_IDS; i++)
		/* Here, we do not initialize it to zero for now */
		/* to be able to recognize non-updated elements  */
		sh_css_sp_stage.frames.static_frame_data[i] = -1;

	err = sh_css_sp_write_frame_pointers(args, pipe_id, stage);
	if (err != sh_css_success)
		return err;

	if (continuous &&  binary->info->enable.raw_binning) {
		/* TODO: Remove this after preview output decimation is fixed
		 * by configuring out&vf info fiels properly */
		sh_css_sp_stage.frames.out.info.padded_width
			<<= binary->vf_downscale_log2;
		sh_css_sp_stage.frames.out.info.width
			<<= binary->vf_downscale_log2;
		sh_css_sp_stage.frames.out.info.height
			<<= binary->vf_downscale_log2;
	}

	store_sp_stage_data(pipe_id, stage);

	return sh_css_success;
}

static enum sh_css_err
sp_init_stage(struct sh_css_pipeline_stage *stage,
		    enum sh_css_pipe_id id,
		    unsigned stage_num,
		    bool preview_mode,
	      bool low_light,
	      bool xnr)
{
	struct sh_css_binary *binary = stage->binary;
	const struct sh_css_fw_info *firmware = stage->firmware;
	const struct sh_css_binary_args *args = &stage->args;
	const unsigned char *binary_name;
	const struct sh_css_binary_info *info = NULL;
	struct sh_css_binary tmp_binary;
	const struct sh_css_blob_info *blob_info;
	struct sh_css_hmm_isp_interface isp_mem_if[SH_CSS_NUM_ISP_MEMORIES];
	const struct sh_css_hmm_isp_interface *mem_if = isp_mem_if;
	enum sh_css_pipe_id pipe_id = id;

	memset(isp_mem_if, 0, sizeof(isp_mem_if));

	if (binary) {
		info = binary->info;
		binary_name =
			(const unsigned char *)(info->blob->name);
		blob_info = &info->blob->header.blob;
	} else {
		info = &firmware->info.isp;
		sh_css_fill_binary_info(info, false, false,
			    SH_CSS_INPUT_FORMAT_RAW_10,
			    args->in_frame  ? &args->in_frame->info  : NULL,
			    args->out_frame ? &args->out_frame->info : NULL,
			    args->out_vf_frame ? &args->out_vf_frame->info
						: NULL,
			    &tmp_binary,
			    false);
		binary = &tmp_binary;
		binary->info = info;
		binary_name = SH_CSS_EXT_ISP_PROG_NAME(firmware);
		blob_info = &firmware->blob;
		mem_if = firmware->memory_interface;
	}

	sh_css_dtrace(SH_DBG_TRACE,
		"sp_init_stage(): load binary: %s\n", binary_name);
#ifdef __KERNEL__
	printk(KERN_ERR "load binary: %s\n", binary_name);
#endif

	sh_css_sp_init_stage(binary,
			     (const char *)binary_name,
			     blob_info,
			     args,
			     pipe_id,
			     stage_num,
			     preview_mode,
			     low_light,
			     xnr,
				stage->irq_buf_flags,
				mem_if);
	return sh_css_success;
}

void
sh_css_sp_init_pipeline(struct sh_css_pipeline *me,
			enum sh_css_pipe_id id,
			bool preview_mode,
			bool low_light,
			bool xnr,
			bool two_ppc,
			bool continuous,
			bool offline,
			bool input_needs_raw_binning,
			enum sh_css_pipe_config_override copy_ovrd)
{
	/* Get first stage */
	struct sh_css_pipeline_stage *stage;
	struct sh_css_binary	     *first_binary = me->stages->binary;
	struct sh_css_binary_args    *first_args   = &me->stages->args;
	unsigned num;

	enum sh_css_pipe_id pipe_id = id;
	unsigned int thread_id;

	sh_css_query_sp_thread_id(pipe_id, &thread_id);
	memset(&sh_css_sp_group.pipe[thread_id], 0, sizeof(struct sh_css_sp_pipeline));

	/* Count stages */
	for (stage = me->stages, num = 0; stage; stage = stage->next, num++) {
		stage->stage_num = num;
		sh_css_debug_pipe_graph_dump_stage(stage, id);
	}
	me->num_stages = num;

	if (first_binary != NULL) {
	/* Init pipeline data */
		sh_css_sp_init_group(two_ppc, first_binary->input_format, offline);
	/* for Capture, do we need to add more modes like */
		if (continuous &&
			(first_binary->info->mode == SH_CSS_BINARY_MODE_PREVIEW ||
			 first_binary->info->mode == SH_CSS_BINARY_MODE_PRIMARY)) {
#if 0
			sh_css_queue_buffer(SH_CSS_COPY_PIPELINE,
				SH_CSS_BUFFER_TYPE_OUTPUT_FRAME,
				(void *)first_args->cc_frame);
#endif
			sh_css_sp_start_raw_copy(first_binary, first_args->cc_frame,
				two_ppc, input_needs_raw_binning,
				copy_ovrd);

			sh_css_debug_pipe_graph_dump_sp_raw_copy(first_args->cc_frame);
		}
	} /* if (first_binary != NULL) */

	/* Init stage data */
	sh_css_init_host2sp_frame_data();

	sh_css_sp_group.pipe[thread_id].num_stages = 0;
	sh_css_sp_group.pipe[thread_id].pipe_id = pipe_id;
	/* TODO: next indicates from which queues parameters need to be
		 sampled, needs checking/improvement */
	if (sh_css_pipe_uses_params(me)) {
		sh_css_sp_group.pipe[thread_id].pipe_config =
			SH_CSS_PIPE_CONFIG_SAMPLE_PARAMS << thread_id;
	}

	/* For continuous use-cases, SP copy is responsible for sampling the
	 * parameters */
	if (sh_css_continuous_is_enabled())
		sh_css_sp_group.pipe[thread_id].pipe_config = 0;

	for (stage = me->stages, num = 0; stage; stage = stage->next, num++)
		sp_init_stage(stage, pipe_id, num, preview_mode, low_light, xnr);

	store_sp_group_data();

}

void
sh_css_sp_uninit_pipeline(enum sh_css_pipe_id pipe_id)
{
	unsigned int thread_id;
	sh_css_query_sp_thread_id(pipe_id, &thread_id);
	/*memset(&sh_css_sp_group.pipe[thread_id], 0, sizeof(struct sh_css_sp_pipeline));*/
	sh_css_sp_group.pipe[thread_id].num_stages = 0;
}
void
sh_css_sp_init_pipeline(struct ia_css_pipeline *me,
			enum ia_css_pipe_id id,
			uint8_t pipe_num,
			bool xnr,
			bool two_ppc,
			bool continuous,
			bool offline,
			unsigned int required_bds_factor,
			enum sh_css_pipe_config_override copy_ovrd,
			enum ia_css_input_mode input_mode,
			const struct ia_css_metadata_config *md_config,
			const struct ia_css_metadata_info *md_info
#if !defined(IS_ISP_2500_SYSTEM)
			, const mipi_port_ID_t port_id
#endif
			)
{
	/* Get first stage */
	struct ia_css_pipeline_stage *stage        = NULL;
	struct ia_css_binary	     *first_binary = NULL;
	unsigned num;

	enum ia_css_pipe_id pipe_id = id;
	unsigned int thread_id;
	uint8_t if_config_index, tmp_if_config_index;

	assert(me != NULL);

#if !defined(HAS_NO_INPUT_SYSTEM)
	assert(me->stages != NULL);

	first_binary = me->stages->binary;

	if (input_mode == IA_CSS_INPUT_MODE_SENSOR
		|| input_mode == IA_CSS_INPUT_MODE_BUFFERED_SENSOR) {
			assert (port_id < N_MIPI_PORT_ID);
			if (port_id >= N_MIPI_PORT_ID) /* should not happen but KW does not know */
				return; /* we should be able to return an error */
			if_config_index  = (uint8_t) (port_id - MIPI_PORT0_ID);
	} else if (input_mode == IA_CSS_INPUT_MODE_MEMORY){
		if_config_index = SH_CSS_IF_CONFIG_NOT_NEEDED;
	} else if_config_index = 0x0;
#else
	(void)input_mode;
	if_config_index = SH_CSS_IF_CONFIG_NOT_NEEDED;
#endif

	ia_css_pipeline_get_sp_thread_id(pipe_num, &thread_id);
	memset(&sh_css_sp_group.pipe[thread_id], 0, sizeof(struct sh_css_sp_pipeline));

	/* Count stages */
	for (stage = me->stages, num = 0; stage; stage = stage->next, num++) {
		stage->stage_num = num;
		ia_css_debug_pipe_graph_dump_stage(stage, id);
	}
	me->num_stages = num;

	if (first_binary != NULL) {
	/* Init pipeline data */
		sh_css_sp_init_group(two_ppc, first_binary->input_format, offline, if_config_index);
	} /* if (first_binary != NULL) */

#if defined(USE_INPUT_SYSTEM_VERSION_2401)
	/* Signal the host immediately after start for SP_ISYS_COPY only */
	if ((me->num_stages == 1) && me->stages &&
	    (me->stages->sp_func == IA_CSS_PIPELINE_ISYS_COPY))
		sh_css_sp_group.config.no_isp_sync = true;
#endif

	/* Init stage data */
	sh_css_init_host2sp_frame_data();

	sh_css_sp_group.pipe[thread_id].num_stages = 0;
	sh_css_sp_group.pipe[thread_id].pipe_id = pipe_id;
	sh_css_sp_group.pipe[thread_id].thread_id = thread_id;
	sh_css_sp_group.pipe[thread_id].pipe_num = pipe_num;
	sh_css_sp_group.pipe[thread_id].num_execs = me->num_execs;
	sh_css_sp_group.pipe[thread_id].required_bds_factor = required_bds_factor;
#if !defined(HAS_NO_INPUT_SYSTEM)
	sh_css_sp_group.pipe[thread_id].input_system_mode
						= (uint32_t)input_mode;
	sh_css_sp_group.pipe[thread_id].port_id = port_id;
#endif
	sh_css_sp_group.pipe[thread_id].dvs_frame_delay = (uint32_t)me->dvs_frame_delay;

	/* TODO: next indicates from which queues parameters need to be
		 sampled, needs checking/improvement */
	if (ia_css_pipeline_uses_params(me)) {
		sh_css_sp_group.pipe[thread_id].pipe_config =
			SH_CSS_PIPE_CONFIG_SAMPLE_PARAMS << thread_id;
	}

	/* For continuous use-cases, SP copy is responsible for sampling the
	 * parameters */
	if (continuous)
		sh_css_sp_group.pipe[thread_id].pipe_config = 0;

	sh_css_sp_group.pipe[thread_id].inout_port_config = me->inout_port_config;

#if defined (SH_CSS_ENABLE_METADATA)
	if (md_info != NULL && md_info->size > 0) {
		sh_css_sp_group.pipe[thread_id].metadata.width  = md_info->resolution.width;
		sh_css_sp_group.pipe[thread_id].metadata.height = md_info->resolution.height;
		sh_css_sp_group.pipe[thread_id].metadata.stride = md_info->stride;
		sh_css_sp_group.pipe[thread_id].metadata.size   = md_info->size;
		ia_css_isys_convert_stream_format_to_mipi_format(
				md_config->data_type, MIPI_PREDICTOR_NONE,
				&sh_css_sp_group.pipe[thread_id].metadata.format);
	}
#else
	(void)md_config;
	(void)md_info;
#endif

	ia_css_debug_dtrace(IA_CSS_DEBUG_TRACE_PRIVATE, "sh_css_sp_init_pipeline pipe_id %d port_config %08x\n",pipe_id,sh_css_sp_group.pipe[thread_id].inout_port_config);

	for (stage = me->stages, num = 0; stage; stage = stage->next, num++) {
		sh_css_sp_group.pipe[thread_id].num_stages++;
		if (is_sp_stage(stage)) {
			sp_init_sp_stage(stage, pipe_num, two_ppc,
				copy_ovrd, if_config_index);
		} else {
			if ((stage->stage_num != 0) || SH_CSS_PIPE_PORT_CONFIG_IS_CONTINUOUS(me->inout_port_config))
				tmp_if_config_index = SH_CSS_IF_CONFIG_NOT_NEEDED;
			else
				tmp_if_config_index = if_config_index;
			sp_init_stage(stage, pipe_num,
				      xnr, tmp_if_config_index);
		}

		store_sp_stage_data(pipe_id, pipe_num, num);
	}
	sh_css_sp_group.pipe[thread_id].pipe_config |= (uint32_t)
		(me->acquire_isp_each_stage << IA_CSS_ACQUIRE_ISP_POS);
	store_sp_group_data();

}