过程"/>
sensor 上电过程
2023年08月14日17:17:44 更新
以 i2c 举例
void xxx_start_hw_detect_sequence(sns_sensor *const this)
{/**-----------------Register and Open COM Port-------------------------*/if (NULL == state->common_port_info.port_handle){rv = state->scp_service->api->sns_scp_register_com_port(&state->common_port_info_config,&state->common_port_info.port_handle);if (rv == SNS_RC_SUCCESS){rv = state->scp_service->api->sns_scp_open(state->common_port_info.port_handle);}}/**---------------------Register Power Rails --------------------------*/if (sns_suid_lookup_get(&state->common.suid_lookup_data, "timer", NULL)&& NULL == state->pwr_rail_service&& rv == SNS_RC_SUCCESS){rv = stk3a6x_register_power_rail(this);/**---------------------Turn Power Rails ON----------------------------*/state->common.rail_config.rail_vote = state->common.registry_rail_on_state;if (rv == SNS_RC_SUCCESS){rv = state->pwr_rail_service->api->sns_vote_power_rail_update(state->pwr_rail_service,this,&state->common.rail_config,NULL);}/**-------------Create a Timer stream for Power Rail ON timeout.---------*/if (rv == SNS_RC_SUCCESS){stk3a6x_start_power_rail_timer(this,sns_convert_ns_to_ticks(STK3A6X_OFF_TO_IDLE_MS * 1000 * 1000),STK3A6X_POWER_RAIL_PENDING_INIT);}}
}
1:注册 COM Port
sns_scp_register_com_port
函数路径:
sns_sync_com_port_service.c
SNS_SECTION(".text.sns") sns_rc sns_scp_register_com_port(sns_com_port_config const *com_config,sns_sync_com_port_handle **port_handle)
{// 已经打开过了,就不在重复打开 if(NULL != *port_handle){sns_scp_deregister_com_port(port_handle);}// 分配空间。 port_priv_handle = sns_malloc(SNS_HEAP_ISLAND, sizeof(sns_com_port_priv_handle));
// sensor 驱动传过去的 一些参数.主要是从 registery 读取出来的数据。sns_memscpy(&port_priv_handle->com_config,sizeof(sns_com_port_config),com_config,sizeof(sns_com_port_config));
// 只是赋值了 bus_info .其他的后续再来看下 port_priv_handle->bus_info.bus_type = com_config->bus_type;port_priv_handle->bus_info.power_on = false;port_priv_handle->bus_info.opened = false;/** bus_info::bus_config shall be allocated by bus specific* implementation.*/*port_handle = (sns_sync_com_port_handle *)port_priv_handle;return SNS_RC_SUCCESS;
}
2: sns_scp_open
port_handle 是第一步分配的内存,并对 bus_type 进行了些赋值
SNS_SECTION(".text.sns") sns_rc sns_scp_open(sns_sync_com_port_handle *port_handle){sns_com_port_priv_handle *priv_handle = (sns_com_port_priv_handle *)port_handle;sns_bus_info *bus_info = &priv_handle->bus_info;sns_rc return_code = SNS_RC_SUCCESS;
// 打开过,就不要在打开了if(bus_info->opened == true){return SNS_RC_SUCCESS;}
// return_code = scp_port_apis[bus_info->bus_type]->sns_scp_open(port_handle);else{bus_info->opened = true;bus_info->power_on = true;}return return_code;
}
看下这个 scp_port_apis[bus_info->bus_type]->sns_scp_open(port_handle);
跑到 sns_com_port_i2c.c
sns_open_i2c 函数中,最后还是通过这个函数
sns_open_i2c_internal来实现的 .
static sns_rc sns_open_i2c_internal(sns_sync_com_port_handle *port_handle)
{sns_com_port_priv_handle *priv_handle = (sns_com_port_priv_handle *)port_handle;sns_bus_info *bus_info = &priv_handle->bus_info;sns_com_port_config *com_config = &priv_handle->com_config;// malloc 空间bus_info->bus_config = sns_malloc( SNS_HEAP_ISLAND, sizeof(sns_i2c_info) );i2c_info = (sns_i2c_info *)bus_info->bus_config;
//以请求的 i2c 速度打开 clk 资源.sns_result =sns_i2c_setup_clk_resources(com_config->bus_type,(i2c_instance)(com_config->bus_instance),com_config->max_bus_speed_KHz,NULL);
// clk 设置完成,接下来 open i2c.result = i2c_open( (i2c_instance)(com_config->bus_instance),&i2c_info->i2c_handle);// i2c 上电 result = i2c_power_on( i2c_info->i2c_handle );// log . 可以查看 哪个 sensor 上电成功.SNS_PRINTF( LOW, sns_fw_printf, "i2c_open success. hndl:%p instance:%u type:%u addr:0x%x",i2c_info->i2c_handle, com_config->bus_instance, com_config->bus_type, com_config->slave_control );return SNS_RC_SUCCESS;
}
i2c 协议的一些上电大概就是这个流程, 其他协议应该也差不多.
普通的 gpio 口怎么上电呢? 比如 有些 sensor vdd 时序是有上电时序要求的.
再来继续看 Register Power Rails
应该是 注册 vdd/vddio
把这段代码 贴过来,看下
// 注册了个 定时器if (sns_suid_lookup_get(&state->common.suid_lookup_data, "timer", NULL)&& NULL == state->pwr_rail_service&& rv == SNS_RC_SUCCESS){rv = stk3a6x_register_power_rail(this);/**---------------------Turn Power Rails ON----------------------------*/state->common.rail_config.rail_vote = state->common.registry_rail_on_state;if (rv == SNS_RC_SUCCESS){rv = state->pwr_rail_service->api->sns_vote_power_rail_update(state->pwr_rail_service,this,&state->common.rail_config,NULL);}/**-------------Create a Timer stream for Power Rail ON timeout.---------*/if (rv == SNS_RC_SUCCESS){stk3a6x_start_power_rail_timer(this,sns_convert_ns_to_ticks(STK3A6X_OFF_TO_IDLE_MS * 1000 * 1000),STK3A6X_POWER_RAIL_PENDING_INIT);}}
看下 stk3a6x_register_power_rail
static sns_rc stk3a6x_register_power_rail(sns_sensor *const this)
{/** OFF state.* Must be used when there are no active Sensors Instances.*/state->common.rail_config.rail_vote = SNS_RAIL_OFF;if (NULL == state->pwr_rail_service){state->pwr_rail_service =(sns_pwr_rail_service*)smgr->get_service(smgr, SNS_POWER_RAIL_SERVICE);state->pwr_rail_service->api->sns_register_power_rails(state->pwr_rail_service,&state->common.rail_config);}if (NULL == state->pwr_rail_service){rv = SNS_RC_FAILED;}return rv;
}rail_config 这些之类的 就是 json 设置的 这些
"num_rail":{ "type": "int", "ver": "0","data": " " },"rail_on_state":{ "type": "int", "ver": "0","data": "2"},"vddio_rail":{ "type": "str", "ver": "0","data": "/pmic/client/sensor_vddio" },
ok ,我们看下这个注册函数.有解释的.
大概理解下:
为物理的 sensor 供电的. 一般有一个或者多个. 从这可以看出,这不就是 vdd/vddio 这一类的东西嘛
这些东西应该定义在 non-volatile registry 。 是的,我们设置了 json文件,最后解析在 persist 分区中。最后从 registry 取出我们设置的数据. 当然这个只能初始化一次,上电过程不可能多次上电.
/*** Register power rails for a physical sensor.** All physical sensors typically have one or more power rails* that supply power to the sensor hardware. Power rail* configuration for all sensors shall be defined in the* non-volatile registry. After the sensor driver fetches rail* information from the registry, it shall register all rails* using this API. Rail registration must happen only once for* any rail.* * @param[i] this Power rail service reference.* @param[i] rail_config Rail config being registered.** @return* SNS_RC_INVALID_VALUE - input rail config is invalid* SNS_RC_SUCCESS - rail registration successful*/sns_rc (*sns_register_power_rails)(sns_pwr_rail_service* this,sns_rail_config const* rail_config);
我们大致看下 这个函数的实现
SNS_SECTION(".text.sns") sns_rc sns_register_power_rails(sns_pwr_rail_service *this,sns_rail_config const* rail_config)
{SNS_ISLAND_EXIT();return sns_register_power_rails_internal(this,rail_config);
}
//
static sns_rc __attribute__ ((noinline))
sns_register_power_rails_internal(sns_pwr_rail_service *this,sns_rail_config const* rail_config)
{// 获取 锁 sns_osa_lock_acquire(pwr_rail_service.rail_mgr_lock);else{// 有几路 供电.for(i = 0; i< rail_config->num_of_rails; i++){rc = sns_pwr_rail_init(&rail_config->rails[i]);// if even a single rail init fails then return immediately.if(rc != SNS_RC_SUCCESS){break;}}}// 释放 锁sns_osa_lock_release(pwr_rail_service.rail_mgr_lock);return rc;
}// 假设 只有 vdd 供电,简单点
// 现在 看下 sns_pwr_rail_init
static sns_rc __attribute__ ((noinline))
sns_pwr_rail_init(sns_rail_name const* rail)
{
// 这名字也不是随便取的,可以参照下这个函数if(!sns_rail_name_is_valid(rail)){return SNS_RC_INVALID_VALUE;}// Init default state for rail.pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].state = SNS_RAIL_OFF;// Copy Rail name.sns_strlcpy(pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].name.name,rail->name,RAIL_NAME_STRING_SIZE_MAX);// Init client list for rail.sns_isafe_list_init(&pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].client_item_list);// Get NPA handle for rail. Not to be done for dummy railif((0 != strncmp(DUMMY_SENSOR_VDD, pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].name.name,sizeof(DUMMY_SENSOR_VDD))) &&(0 != strncmp(SNS_PWR_RAIL_VDD, pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].name.name,sizeof(SNS_PWR_RAIL_VDD)))){pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].rail_npa_handle =npa_create_sync_client(pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].name.name,"Sensors",NPA_CLIENT_REQUIRED);if (NULL == pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].rail_npa_handle){SNS_SPRINTF(ERROR, sns_fw_printf, "Could not initialize power rail: %s",pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].name.name);}}else{pwr_rail_service.rails[pwr_rail_service.num_rails_initialized].rail_npa_handle = NULL;}// Increment number of initialized rails.pwr_rail_service.num_rails_initialized++;return SNS_RC_SUCCESS;
}
下班时间到了,只能到后续有时间在写了…
继续 2023年08月15日10:04:14 更新
/**
- Define a dummy rail for OEMs that use external rails for their sensors.
- Dummy rail config is required so island mode block/unblock logic still
- works for those OEMs.
*/
#define DUMMY_SENSOR_VDD “/pmic/client/dummy_vdd”
#define SNS_PWR_RAIL_VDD “/see/rail/eLDO”
不太清楚这两个有啥区别??
可以使用外部供电. 比如下面这样.
没有使用 dsp 的pmic ,用了AP 那边的 pmic, 在 linux kernel 对这个口进行输出高电平,这个 sensor 就能进行供电了。
OK ,注册完成。接下来应该就是上电。
继续回到 xxx_start_hw_detect_sequence
/**---------------------Turn Power Rails ON----------------------------*/// json 中设置 的 rail_on_state 。 就是启动转态 LPM/NPM 这种state->common.rail_config.rail_vote = state->common.registry_rail_on_state;
// if (rv == SNS_RC_SUCCESS){rv = state->pwr_rail_service->api->sns_vote_power_rail_update(state->pwr_rail_service,this,&state->common.rail_config,NULL);}
看下是 怎么 power on 的
重点是这个函数 sns_vote_power_rail_update
sns_pwr_rail_service.c
/*** Vote for a power rail status change.** Each physical sensor driver uses this API to turn it's* sensors power rails ON when there is an active client* request. It is also the driver's responsibility to vote for* power rails OFF when all clients requests are disabled (i.e.* there are no Sensors Instances present)*/
/*看注释的话: 1: 客户端上电请求2: 下电请求,会有多个下电请求,用 投票方法决定哪个下电。 不知道上电需不需要?? 没太看懂 3: sensor instance 不会有这个动作发生。
*/
// 实际实现在这里.
static sns_rc __attribute__ ((noinline))
sns_vote_power_rail_update_internal(sns_pwr_rail_service *this,struct sns_sensor const* sensor,sns_rail_config const* rails_config,sns_time* rail_on_timestamp)
{for(i = 0; i < rails_config->num_of_rails; i++){// 判断是否注册了。 rail_is_registered = sns_rail_is_registered(&rails_config->rails[i], &rail_index);// 我们设置的状态是 SNS_RAIL_OFF . 这个是移除 pwr_rail_client if(rails_config->rail_vote == SNS_RAIL_OFF){sns_remove_pwr_rail_client(sensor, rail_index);}else{sns_add_pwr_rail_client(sensor, rails_config->rail_vote, rail_index);}// Update the power rail state. Not required for dummy railif(0 != strncmp(DUMMY_SENSOR_VDD, pwr_rail_service.rails[rail_index].name.name, sizeof(DUMMY_SENSOR_VDD))){sns_update_power_rail_state(rail_index);}// 主要是为了获取硬件初始化的多长时间./** There can be more than one rail that a client wants to* turn ON. Using max operation to get timestamp of rail that* was turned ON most recently so that the client can know* exactly how long it needs until HW is available. */on_timestamp = SNS_MAX(on_timestamp, sns_get_rail_on_timestamp(rail_index));}return rc;
}
接下来最重要的就是: sns_update_power_rail_state
Parses client info for the rail and chooses best state.
static void __attribute__ ((noinline))
sns_update_power_rail_state(uint8_t rail_index)
{for(;NULL != sns_isafe_list_iter_curr(&iter);sns_isafe_list_iter_advance(&iter)){item = (sns_client_item*)sns_isafe_list_iter_get_curr_data(&iter);// Search for the highest vote in rail's client list.new_state = SNS_MAX(new_state, item->vote);if (SNS_RAIL_ON_LPM == item->vote){lpm_client_count++;}}
// LPM > 1. 新的状态进行赋值 SNS_RAIL_ON_NPM . if (MAX_LPM_CLIENTS_PER_RAIL < lpm_client_count){new_state = SNS_RAIL_ON_NPM;}// 进去if(new_state != pwr_rail_service.rails[rail_index].state){/* state new_state action* ----------------------------------------------------------------------* OFF LPM/NPM change right away. Update on_timestamp.* LPM NPM change right away. Update on_timestamp.* NPM/LPM OFF change right away. Clear on_timestamp.* NPM LPM change right away. No change to on_timestamp.*/
// 没有跑进去,不管if (SNS_VDDIO_PWR_RAIL_ALWAYS_ON == 0x1){if ((new_state == SNS_RAIL_OFF)&& (0 == strncmp(PMIC_NPA_GROUP_ID_SENSOR_VDDIO, pwr_rail_service.rails[rail_index].name.name, sizeof(PMIC_NPA_GROUP_ID_SENSOR_VDDIO)))){if (0== sns_isafe_list_iter_len(&iter)) {new_state = SNS_RAIL_ON_LPM;}else return;}}if(0 == strncmp(SNS_PWR_RAIL_VDD, pwr_rail_service.rails[rail_index].name.name, sizeof(SNS_PWR_RAIL_VDD))){
#ifdef SNS_GPIO_FOR_EXTERNAL_LDOsns_write_gpio(SNS_GPIO_FOR_EXTERNAL_LDO, 1, SNS_GPIO_DRIVE_STRENGTH_2_MILLI_AMP, SNS_GPIO_PULL_TYPE_PULL_UP,(SNS_RAIL_OFF != new_state)?SNS_GPIO_STATE_HIGH:SNS_GPIO_STATE_LOW);
#endif}else{// 向 NPA 发送 power_on 请求.pmic_rail_state = (new_state == SNS_RAIL_OFF) ?PMIC_NPA_MODE_ID_SENSOR_POWER_OFF :((new_state == SNS_RAIL_ON_LPM) ?PMIC_NPA_MODE_ID_SENSOR_LPM :PMIC_NPA_MODE_ID_SENSOR_POWER_ON);if (NULL != pwr_rail_service.rails[rail_index].rail_npa_handle){npa_issue_required_request(pwr_rail_service.rails[rail_index].rail_npa_handle,pmic_rail_state);SNS_SPRINTF(HIGH, sns_fw_printf, "sensor power rail: %s, state: %d",(char*)pwr_rail_service.rails[rail_index].name.name,pmic_rail_state);}}pwr_rail_service.rails[rail_index].state = new_state; // 更新状态}
}
new_state:是我们sensor 那边 传进去的状态
pwr_rail_service.rails[rail_index].state : 这个初始值 不太确定是多少,从哪里传过来的. 后面在去看下
这个不是很确定
转态发送了改变, 才会进行相应的动作.
从 log 中可以看到打印:
sensor power rail: /pmic/client/sensor_vdd, state: 2
sensor power rail: /pmic/client/sensor_vddio, state: 2
sensor power rail: /pmic/client/sensor_vdd_2, state: 2
sensor power rail: /pmic/client/sensor_vddio_2, state: 2
我们设置的 rail_on_state 是2, 没毛病。 这样就 power on 了.
这个是等待的时间。
个人认为是 等待 dsp 那边稳定后,再来读取 sensor id 。
/**-------------Create a Timer stream for Power Rail ON timeout.---------*/if (rv == SNS_RC_SUCCESS){stk3a6x_start_power_rail_timer(this,sns_convert_ns_to_ticks(STK3A6X_OFF_TO_IDLE_MS * 1000 * 1000),STK3A6X_POWER_RAIL_PENDING_INIT);}
我们看下这个写法:
void stk3a6x_start_power_rail_timer(sns_sensor *const this,sns_time timeout_ticks,stk3a6x_power_rail_pending_state pwr_rail_pend_state)
{req_payload.timeout_period = timeout_ticks;if (NULL == state->timer_stream){sns_service_manager *smgr = this->cb->get_service_manager(this);sns_stream_service *stream_svc = (sns_stream_service*)smgr->get_service(smgr, SNS_STREAM_SERVICE);sns_sensor_uid suid;sns_suid_lookup_get(&state->common.suid_lookup_data, "timer", &suid);stream_svc->api->create_sensor_stream(stream_svc, this, suid,&state->timer_stream);}req_len = pb_encode_request(buffer, sizeof(buffer), &req_payload,sns_timer_sensor_config_fields, NULL);if (req_len > 0 && NULL != state->timer_stream){sns_request timer_req ={.message_id = SNS_TIMER_MSGID_SNS_TIMER_SENSOR_CONFIG,.request = buffer, .request_len = req_len};state->timer_stream->api->send_request(state->timer_stream, &timer_req);state->power_rail_pend_state = pwr_rail_pend_state;}
}
看到只是发了个 消息: SNS_TIMER_MSGID_SNS_TIMER_SENSOR_CONFIG
state->power_rail_pend_state = pwr_rail_pend_state; 这句是在发送之后进行赋值的,并没有发送出去.
进入 sns_timer_sensor.c
SNS_SECTION(".text.sns")
static sns_sensor_instance*
sns_timer_set_client_request(sns_sensor *const this,sns_request const *curr_req,sns_request const *new_req,bool remove) {else if( SNS_TIMER_MSGID_SNS_TIMER_SENSOR_CONFIG == new_req->message_id &&sns_timer_get_decoded_req(new_req, &decoded_request, &decoded_payload) ){// 加入到 timer 链表当中去.this->instance_api->set_client_config(timer_inst, &inst_req);sns_isafe_list_item_init(&new_inst_state->periodic_entry, timer_inst);rc = sns_timer_sensor_record_entry(state, timer_inst, true);// Generate timer registration eventif(!pb_send_event(timer_inst, sns_timer_sensor_reg_event_fields,&(new_inst_state->client_config), sns_get_system_time(),SNS_TIMER_MSGID_SNS_TIMER_SENSOR_REG_EVENT, NULL)){SNS_PRINTF(ERROR, sns_fw_printf, "Timer registration event failure");}}}
可以看到 最后发送 SNS_TIMER_MSGID_SNS_TIMER_SENSOR_REG_EVENT
这个可以看到, 没有什么用. sensor 当中没有对这个做处理
我们看下 timer 时间到了 怎么处理的
SNS_SECTION(".text.sns")
static sns_rc
sns_timer_inst_generate_event(sns_sensor_instance *const timer_inst,sns_sensor *const timer_sensor,sns_time system_time)
{timer_event.timeout_time = sensor_state->ro_buffer.timeout_event.timestamp;timer_event.requested_timeout_time = state->trigger_time;// 发送 SNS_TIMER_MSGID_SNS_TIMER_SENSOR_EVENT message 的消息if(!pb_send_event(timer_inst, sns_timer_sensor_event_fields, &timer_event,system_time, SNS_TIMER_MSGID_SNS_TIMER_SENSOR_EVENT,NULL)){}
#ifdef SNS_TIMER_ENABLE_DEBUGSNS_PRINTF(LOW, sns_fw_printf, "Timer sent event for %x, tout %x, now %x",(uint32_t)timer_inst, (uint32_t)state->trigger_time,(uint32_t)system_time );
#endifreturn SNS_RC_SUCCESS;
}
可以看到,时间到了,会发送 SNS_TIMER_MSGID_SNS_TIMER_SENSOR_EVENT 的消息。
接下来,我们在回到 sensor 的驱动中
sns_stk3a6x_sensor_island.c
sns_rc stk3a6x_sensor_notify_event(sns_sensor *const this)
{
// 处理 timer event /**----------------------Handle a Timer Sensor event.-------------------*/if (NULL != state->timer_stream){event = state->timer_stream->api->peek_input(state->timer_stream);while (NULL != event){pb_istream_t stream = pb_istream_from_buffer((pb_byte_t*)event->event,event->event_len);// timer 定时器,时间到了,发来的消息 SNS_TIMER_MSGID_SNS_TIMER_SENSOR_EVENTif (SNS_TIMER_MSGID_SNS_TIMER_SENSOR_EVENT == event->message_id){if (pb_decode(&stream, sns_timer_sensor_event_fields, &timer_event)){ // 注册的时候设置的 STK3A6X_POWER_RAIL_PENDING_INIT if (state->power_rail_pend_state == STK3A6X_POWER_RAIL_PENDING_INIT){/**-------------------Read and Confirm WHO-AM-I------------------------*/state->island_service->api->sensor_island_exit(state->island_service, this);state->common.hw_is_present = stk3a6x_discover_hw(this);if (state->common.hw_is_present){stk3a6x_publish_available(this);stk3a6x_update_sibling_sensors(this);} state->power_rail_pend_state = STK3A6X_POWER_RAIL_PENDING_NONE;}}event = state->timer_stream->api->get_next_input(state->timer_stream);}/** Free up timer stream if not needed anymore */if (state->power_rail_pend_state == STK3A6X_POWER_RAIL_PENDING_NONE){sns_sensor_util_remove_sensor_stream(this, &state->timer_stream);}}}
总结下这个函数:
stk3a6x_start_power_rail_timer(this,
sns_convert_ns_to_ticks(STK3A6X_OFF_TO_IDLE_MS * 1000 * 1000),
STK3A6X_POWER_RAIL_PENDING_INIT);
power rail 等 STK3A6X_OFF_TO_IDLE_MS 的时间 ,在来继续处理
init 完成后,接下来就是读取 id
bool stk3a6x_discover_hw(sns_sensor *const this)
{/**-------------------Read and Confirm WHO-AM-I------------------------*/rv = stk3a6x_get_who_am_i(state->scp_service, state->common_port_info.port_handle,&buffer[0]);STK3A6X_PRINTF(ERROR, this, "STK3A6X rv:%d,buffer[0]:0x%X",rv, buffer[0]);if ((rv == SNS_RC_SUCCESS) && (stk3a6x_check_pid(buffer[0]) == true)){// Reset Sensor only if an inatance is not alreadly running// 像是有什么故障,所以要 reset sensor if (NULL == sns_sensor_util_get_shared_instance(this)){rv = stk3a6x_reset_device(state->scp_service, state->common_port_info.port_handle,(STK3A6X_ALS_OC | STK3A6X_ALS_STRM | STK3A6X_PS_OC | STK3A6X_PS_STRM));}if (rv == SNS_RC_SUCCESS){hw_is_present = true;}}state->common.who_am_i = buffer[0];/**------------------Power Down and Close COM Port--------------------*/state->scp_service->api->sns_scp_update_bus_power(state->common_port_info.port_handle,false);state->scp_service->api->sns_scp_close(state->common_port_info.port_handle);state->scp_service->api->sns_scp_deregister_com_port(&state->common_port_info.port_handle);/**----------------------Turn Power Rail OFF--------------------------*/state->common.rail_config.rail_vote = SNS_RAIL_OFF;state->pwr_rail_service->api->sns_vote_power_rail_update(state->pwr_rail_service,this,&state->common.rail_config,NULL);return hw_is_present;
}
关闭了 com port / power done . 不知道 等传输数据的时候,还要打开这些吗??
读取到了id ,找到了硬件,publish 属性上去…
if (state->common.hw_is_present)
{
stk3a6x_publish_available(this);
stk3a6x_update_sibling_sensors(this);
}
现在 有个 sensor vdd 上电时序有要求,改哪里呢?
蓝色是 vdd , 如果要增加蓝色 vdd 的低电平的时间,要怎么改??
更多推荐
sensor 上电过程
发布评论