mirror of
https://github.com/BobTheBlinker/android_kernel_motorola_sm6375.git
synced 2026-10-23 21:19:04 -04:00
cam: Add actuator standalone diver for vibrator.
-To eliminate the resonance noise during system vibrator vibrating, set actuator to specified DAC position(480 on DW9714), then the resonance noise can be obviously improved. To achieve the conbination between vibrator and camera AF actuator,we implemnte: - Actuator separately control during camera power off. - Actuator policy to avoid vibrating disturb normal camera AF. port from (CR),fix berlna wide camera resonance noise issue. -Port from (CR): cam/actuator: Add CCI access lock to avoid conflicts. Usually actuator initial setting will execute power down reset(PD), actuator can't respond CCI access for a while after PD. Add lock to avoid access actuator while PD operation. -Port from (CR): cam/actuator: Create separate work queue for park lens. Park lens may cost more than 100ms for different camera modules, create seperate work queue for actuator to avoid park lens operation block system_wq too long. -Port from (CR): cam/actautor: Optimizing park lens for vibrating. Move lens to noise reduction postion after camera exited. -Port from (CR): cam/actuator: Avoid error releasing CCI/regulator. Avoid unbalanced aquire/release of CCI/regulator when actuator init failed. Due to when CCI init for vibrator failed, regulators had been released. -For new baseline sm8350,compile this standalone actuator diver into camera.ko Change-Id: If77d10badfb4147c467ebae238f4e6af317d466f Signed-off-by: wangshuo18 <wangshuo18@lenovo.com> Reviewed-on: https://gerrit.mot.com/1906964 SLTApproved: Slta Waiver SME-Granted: SME Approvals Granted Tested-by: Jira Key Reviewed-by: Dawei Wang <wangdw10@motorola.com> Reviewed-by: Darong Huang <huangdra@motorola.com> Reviewed-by: Long Cheng <chengl1@motorola.com> Reviewed-by: Xu Ji <jixu@motorola.com> Reviewed-by: Jian Zhang <zhangjo@motorola.com> Reviewed-by: Zhuoran Xu <xuzr3@motorola.com> Reviewed-by: Bolei Shang <shangbl1@lenovo.com> Reviewed-by: Zhenxin Xi <xizx@motorola.com> Submit-Approved: Jira Key
This commit is contained in:
parent
09fc695550
commit
68f7e5cb86
10 changed files with 1252 additions and 1 deletions
|
|
@ -172,6 +172,12 @@ camera-$(CONFIG_SPECTRA_SENSOR) += \
|
|||
cam_sensor_module/cam_sensor_utils/cam_sensor_util.o \
|
||||
cam_sensor_module/cam_res_mgr/cam_res_mgr.o
|
||||
|
||||
ifneq (,$(filter $(CONFIG_AF_NOISE_ELIMINATION), y m))
|
||||
camera-$(CONFIG_SPECTRA_SENSOR) += \
|
||||
cam_sensor_module/cam_actuator/mot_actuator.o \
|
||||
cam_sensor_module/cam_actuator/mot_actuator_policy.o
|
||||
endif
|
||||
|
||||
camera-$(CONFIG_LEDS_QPNP_FLASH_V2) += \
|
||||
cam_sensor_module/cam_flash/cam_flash_dev.o \
|
||||
cam_sensor_module/cam_flash/cam_flash_core.o \
|
||||
|
|
|
|||
|
|
@ -10,6 +10,9 @@
|
|||
#include "cam_trace.h"
|
||||
#include "cam_common_util.h"
|
||||
#include "cam_packet_util.h"
|
||||
#ifdef CONFIG_AF_NOISE_ELIMINATION
|
||||
#include "mot_actuator_policy.h"
|
||||
#endif
|
||||
|
||||
int32_t cam_actuator_construct_default_power_setting(
|
||||
struct cam_sensor_power_ctrl_t *power_info)
|
||||
|
|
@ -259,7 +262,13 @@ int32_t cam_actuator_apply_settings(struct cam_actuator_ctrl_t *a_ctrl,
|
|||
CAM_ERR(CAM_ACTUATOR, " Invalid settings");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_AF_NOISE_ELIMINATION
|
||||
/*Usually actuator initial setting will execute power down reset(PD), actuator can't respond
|
||||
CCI access for a while after PD. Add lock to avoid access actuator while PD operation.*/
|
||||
if (a_ctrl->is_multi_user_supported) {
|
||||
mot_actuator_lock();
|
||||
}
|
||||
#endif
|
||||
list_for_each_entry(i2c_list,
|
||||
&(i2c_set->list_head), list) {
|
||||
rc = cam_actuator_i2c_modes_util(
|
||||
|
|
@ -276,6 +285,14 @@ int32_t cam_actuator_apply_settings(struct cam_actuator_ctrl_t *a_ctrl,
|
|||
}
|
||||
}
|
||||
|
||||
#ifdef CONFIG_AF_NOISE_ELIMINATION
|
||||
/*Usually actuator initial setting will execute power down reset(PD), actuator can't respond
|
||||
CCI access for a while after PD. Add lock to avoid access actuator while PD operation.*/
|
||||
if (a_ctrl->is_multi_user_supported) {
|
||||
mot_actuator_unlock();
|
||||
}
|
||||
#endif
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
|
@ -582,6 +599,13 @@ int32_t cam_actuator_i2c_pkt_parse(struct cam_actuator_ctrl_t *a_ctrl,
|
|||
}
|
||||
}
|
||||
|
||||
#ifdef CONFIG_AF_NOISE_ELIMINATION
|
||||
if (a_ctrl->cam_act_state == CAM_ACTUATOR_ACQUIRE &&
|
||||
a_ctrl->is_multi_user_supported == true) {
|
||||
mot_actuator_get(ACTUATOR_CLIENT_CAMERA);
|
||||
}
|
||||
#endif
|
||||
|
||||
if (a_ctrl->cam_act_state == CAM_ACTUATOR_ACQUIRE) {
|
||||
rc = cam_actuator_power_up(a_ctrl);
|
||||
if (rc < 0) {
|
||||
|
|
@ -595,6 +619,7 @@ int32_t cam_actuator_i2c_pkt_parse(struct cam_actuator_ctrl_t *a_ctrl,
|
|||
rc = cam_actuator_apply_settings(a_ctrl,
|
||||
&a_ctrl->i2c_data.init_settings);
|
||||
if (rc < 0) {
|
||||
delete_request(&a_ctrl->i2c_data.init_settings);
|
||||
CAM_ERR(CAM_ACTUATOR, "Cannot apply Init settings");
|
||||
goto end;
|
||||
}
|
||||
|
|
@ -890,6 +915,11 @@ int32_t cam_actuator_driver_cmd(struct cam_actuator_ctrl_t *a_ctrl,
|
|||
}
|
||||
|
||||
if (a_ctrl->cam_act_state == CAM_ACTUATOR_CONFIG) {
|
||||
#ifdef CONFIG_AF_NOISE_ELIMINATION
|
||||
if (a_ctrl->is_multi_user_supported == true) {
|
||||
mot_actuator_put(ACTUATOR_CLIENT_CAMERA);
|
||||
}
|
||||
#endif
|
||||
rc = cam_actuator_power_down(a_ctrl);
|
||||
if (rc < 0) {
|
||||
CAM_ERR(CAM_ACTUATOR,
|
||||
|
|
|
|||
|
|
@ -115,6 +115,9 @@ struct cam_actuator_ctrl_t {
|
|||
struct cam_actuator_query_cap act_info;
|
||||
struct actuator_intf_params bridge_intf;
|
||||
uint32_t last_flush_req;
|
||||
#ifdef CONFIG_AF_NOISE_ELIMINATION
|
||||
bool is_multi_user_supported;
|
||||
#endif
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -34,6 +34,15 @@ int32_t cam_actuator_parse_dt(struct cam_actuator_ctrl_t *a_ctrl,
|
|||
|
||||
of_node = soc_info->dev->of_node;
|
||||
|
||||
#ifdef CONFIG_AF_NOISE_ELIMINATION
|
||||
if (!of_property_read_bool(of_node, "multi-user-support")) {
|
||||
a_ctrl->is_multi_user_supported = false;
|
||||
} else {
|
||||
a_ctrl->is_multi_user_supported = true;
|
||||
}
|
||||
CAM_DBG(CAM_ACTUATOR, "multi-user-support %d", a_ctrl->is_multi_user_supported);
|
||||
#endif
|
||||
|
||||
if (a_ctrl->io_master_info.master_type == CCI_MASTER) {
|
||||
rc = of_property_read_u32(of_node, "cci-master",
|
||||
&(a_ctrl->cci_i2c_master));
|
||||
|
|
|
|||
1032
drivers/cam_sensor_module/cam_actuator/mot_actuator.c
Normal file
1032
drivers/cam_sensor_module/cam_actuator/mot_actuator.c
Normal file
File diff suppressed because it is too large
Load diff
35
drivers/cam_sensor_module/cam_actuator/mot_actuator.h
Normal file
35
drivers/cam_sensor_module/cam_actuator/mot_actuator.h
Normal file
|
|
@ -0,0 +1,35 @@
|
|||
#ifndef __MOT_ACTUATOR_H__
|
||||
#define __MOT_ACTUATOR_H__
|
||||
|
||||
#include <linux/ioctl.h>
|
||||
#include <linux/videodev2.h>
|
||||
#define MOT_ACTUATOR_NAME "mot_actuator"
|
||||
|
||||
#define MOT_ACTUATOR_READ \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 50, int)
|
||||
#define MOT_ACTUATOR_READ32 \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 50, int)
|
||||
|
||||
#define MOT_ACTUATOR_WRITE \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 51, int)
|
||||
#define MOT_ACTUATOR_WRITE32 \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 51, int)
|
||||
|
||||
#define MOT_ACTUATOR_INIT \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 52, int)
|
||||
#define MOT_ACTUATOR_INIT32 \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 52, int)
|
||||
|
||||
#define MOT_ACTUATOR_RELEASE \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 53, int)
|
||||
#define MOT_ACTUATOR_RELEASE32 \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 53, int)
|
||||
|
||||
#define MOT_ACTUATOR_EXIT \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 54, int)
|
||||
#define MOT_ACTUATOR_EXIT32 \
|
||||
_IOWR('X', BASE_VIDIOC_PRIVATE + 54, int)
|
||||
|
||||
int mot_actuator_driver_init(void);
|
||||
void mot_actuator_driver_exit(void);
|
||||
#endif /*__MOT_ACTUATOR_H__*/
|
||||
113
drivers/cam_sensor_module/cam_actuator/mot_actuator_policy.c
Normal file
113
drivers/cam_sensor_module/cam_actuator/mot_actuator_policy.c
Normal file
|
|
@ -0,0 +1,113 @@
|
|||
/*
|
||||
* Copyright (C) 2020 Motorola Mobility LLC.
|
||||
*
|
||||
* This software is licensed under the terms of the GNU General Public
|
||||
* License version 2, as published by the Free Software Foundation, and
|
||||
* may be copied, distributed, and modified under those terms.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
*/
|
||||
#include <linux/module.h>
|
||||
#include <linux/types.h>
|
||||
#include "cam_debug_util.h"
|
||||
#include "mot_actuator_policy.h"
|
||||
|
||||
extern int mot_actuator_on_vibrate_start(void);
|
||||
extern int mot_actuator_on_vibrate_stop(void);
|
||||
|
||||
static atomic_t mot_actuator_ref_count = ATOMIC_INIT(0);
|
||||
static unsigned long mot_actuator_consumers = ATOMIC_INIT(0);
|
||||
static struct mutex actuator_res_lock = __MUTEX_INITIALIZER(actuator_res_lock);
|
||||
|
||||
int mot_actuator_get(mot_actuator_client user)
|
||||
{
|
||||
if (user <= ACTUATOR_CLIENT_INVALID || user >= ACTUATOR_CLIENT_MAX) {
|
||||
CAM_ERR(CAM_ACTUATOR, "INVALID CLIENT!!!");
|
||||
return 0;
|
||||
}
|
||||
|
||||
CAM_DBG(CAM_ACTUATOR, "Obtain actuator from: %d", user);
|
||||
|
||||
test_and_set_bit(user, &mot_actuator_consumers);
|
||||
|
||||
return atomic_add_return(1, &mot_actuator_ref_count);
|
||||
}
|
||||
EXPORT_SYMBOL(mot_actuator_get);
|
||||
|
||||
int mot_actuator_put(mot_actuator_client user)
|
||||
{
|
||||
unsigned long consumers = 0;
|
||||
if (user <= ACTUATOR_CLIENT_INVALID || user >= ACTUATOR_CLIENT_MAX) {
|
||||
CAM_ERR(CAM_ACTUATOR, "INVALID CLIENT!!!");
|
||||
return 0;
|
||||
}
|
||||
|
||||
CAM_DBG(CAM_ACTUATOR, "Release actuator from: %d", user);
|
||||
|
||||
test_and_clear_bit(user, &mot_actuator_consumers);
|
||||
|
||||
consumers = mot_actuator_get_consumers();
|
||||
if (((consumers & CLINET_VIBRATOR_MASK) == CLINET_VIBRATOR_MASK) &&
|
||||
(user != ACTUATOR_CLIENT_VIBRATOR)) {
|
||||
//If only vibrator noise eliminator exists, move lens to required position
|
||||
CAM_DBG(CAM_ACTUATOR, "Set actuator pos for vibrator");
|
||||
mot_actuator_on_vibrate_start();
|
||||
if ((mot_actuator_get_consumers() & CLINET_VIBRATOR_MASK) == 0) {
|
||||
mot_actuator_on_vibrate_stop();
|
||||
}
|
||||
}
|
||||
|
||||
return atomic_sub_return(1, &mot_actuator_ref_count);
|
||||
}
|
||||
EXPORT_SYMBOL(mot_actuator_put);
|
||||
|
||||
int mot_actuator_get_ref_count(void)
|
||||
{
|
||||
return atomic_read(&mot_actuator_ref_count);
|
||||
}
|
||||
EXPORT_SYMBOL(mot_actuator_get_ref_count);
|
||||
|
||||
unsigned int mot_actuator_get_consumers(void)
|
||||
{
|
||||
return mot_actuator_consumers;
|
||||
}
|
||||
EXPORT_SYMBOL(mot_actuator_get_consumers);
|
||||
|
||||
void mot_actuator_lock(void)
|
||||
{
|
||||
mutex_lock(&actuator_res_lock);
|
||||
}
|
||||
EXPORT_SYMBOL(mot_actuator_lock);
|
||||
|
||||
void mot_actuator_unlock(void)
|
||||
{
|
||||
mutex_unlock(&actuator_res_lock);
|
||||
}
|
||||
EXPORT_SYMBOL(mot_actuator_unlock);
|
||||
|
||||
ssize_t mot_actuator_dump(char *buf)
|
||||
{
|
||||
int item_len = 0;
|
||||
unsigned int consumers = mot_actuator_get_consumers();
|
||||
|
||||
item_len += sprintf(buf+item_len, "refCount: %d\n", mot_actuator_get_ref_count());
|
||||
item_len += sprintf(buf+item_len, "Consumers (0x%x):\n", consumers);
|
||||
|
||||
if (consumers & CLINET_CAMERA_MASK) {
|
||||
item_len += sprintf(buf+item_len, "camera");
|
||||
}
|
||||
|
||||
if (consumers & CLINET_VIBRATOR_MASK) {
|
||||
item_len += sprintf(buf+item_len, " vibrator");
|
||||
}
|
||||
|
||||
item_len += sprintf(buf+item_len, "\n");
|
||||
|
||||
CAM_DBG(CAM_ACTUATOR, "ref cnt:%d, consumers:0x%x", mot_actuator_get_ref_count(), mot_actuator_get_consumers());
|
||||
return item_len;
|
||||
}
|
||||
EXPORT_SYMBOL(mot_actuator_dump);
|
||||
20
drivers/cam_sensor_module/cam_actuator/mot_actuator_policy.h
Normal file
20
drivers/cam_sensor_module/cam_actuator/mot_actuator_policy.h
Normal file
|
|
@ -0,0 +1,20 @@
|
|||
#ifndef __MOT_ACTUATOR_POLICY_H__
|
||||
#define __MOT_ACTUATOR_POLICY_H__
|
||||
|
||||
typedef enum {
|
||||
ACTUATOR_CLIENT_INVALID,
|
||||
ACTUATOR_CLIENT_CAMERA,
|
||||
ACTUATOR_CLIENT_VIBRATOR,
|
||||
ACTUATOR_CLIENT_MAX
|
||||
} mot_actuator_client;
|
||||
|
||||
#define CLINET_CAMERA_MASK (0x01 << ACTUATOR_CLIENT_CAMERA)
|
||||
#define CLINET_VIBRATOR_MASK (0x01 << ACTUATOR_CLIENT_VIBRATOR)
|
||||
|
||||
int mot_actuator_get(mot_actuator_client user);
|
||||
int mot_actuator_put(mot_actuator_client user);
|
||||
void mot_actuator_lock(void);
|
||||
void mot_actuator_unlock(void);
|
||||
ssize_t mot_actuator_dump(char *buf);
|
||||
unsigned int mot_actuator_get_consumers(void);
|
||||
#endif /*__MOT_ACTUATOR_POLICY_H__*/
|
||||
|
|
@ -20,6 +20,7 @@
|
|||
#include "cam_cci_dev.h"
|
||||
#include "cam_sensor_dev.h"
|
||||
#include "cam_actuator_dev.h"
|
||||
#include "mot_actuator.h"
|
||||
#include "cam_csiphy_dev.h"
|
||||
#include "cam_eeprom_dev.h"
|
||||
#include "cam_ois_dev.h"
|
||||
|
|
@ -105,6 +106,7 @@ static const struct camera_submodule_component camera_sensor[] = {
|
|||
{&cam_cci_init_module, &cam_cci_exit_module},
|
||||
{&cam_csiphy_init_module, &cam_csiphy_exit_module},
|
||||
{&cam_actuator_driver_init, &cam_actuator_driver_exit},
|
||||
{&mot_actuator_driver_init, &mot_actuator_driver_exit},
|
||||
{&cam_sensor_driver_init, &cam_sensor_driver_exit},
|
||||
{&cam_eeprom_driver_init, &cam_eeprom_driver_exit},
|
||||
{&cam_ois_driver_init, &cam_ois_driver_exit},
|
||||
|
|
|
|||
|
|
@ -32,6 +32,7 @@
|
|||
#define CAM_CUSTOM_DEVICE_TYPE (CAM_DEVICE_TYPE_BASE + 14)
|
||||
#define CAM_OPE_DEVICE_TYPE (CAM_DEVICE_TYPE_BASE + 15)
|
||||
#define CAM_TFE_DEVICE_TYPE (CAM_DEVICE_TYPE_BASE + 16)
|
||||
#define CAM_MOT_ACTUATOR_TYPE (CAM_DEVICE_TYPE_BASE + 17)
|
||||
|
||||
/* cam_req_mgr hdl info */
|
||||
#define CAM_REQ_MGR_HDL_IDX_POS 8
|
||||
|
|
|
|||
Loading…
Reference in a new issue