1 /*
2 * Copyright (C) 2018 Knowles Electronics
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 #define LOG_TAG "oslo_iaxxx_sensor_control"
18
19 #include "oslo_iaxxx_sensor_control.h"
20
21 #include <log/log.h>
22
23 #include "cvq_ioctl.h"
24 #include <linux/mfd/adnc/iaxxx-module.h>
25
26 #define IAXXX_DEV_NODE "/dev/iaxxx-module-celldrv"
27
iaxxx_sensor_mgr_init(void)28 struct ia_sensor_mgr *iaxxx_sensor_mgr_init(void) {
29 struct ia_sensor_mgr *smd = NULL;
30
31 smd = (struct ia_sensor_mgr *)malloc(sizeof(struct ia_sensor_mgr));
32 if (NULL == smd) {
33 ALOGE("%s: ERROR Failed to allocated memory for ia_sensor_mgr", __func__);
34 return NULL;
35 }
36
37 if ((smd->dev_node = fopen(IAXXX_DEV_NODE, "rw")) == NULL) {
38 ALOGE("%s: ERROR file %s open for write error: %s\n", __func__, IAXXX_DEV_NODE,
39 strerror(errno));
40 free(smd);
41 return NULL;
42 }
43
44 return smd;
45 }
46
iaxxx_sensor_mgr_deinit(struct ia_sensor_mgr * smd)47 int iaxxx_sensor_mgr_deinit(struct ia_sensor_mgr *smd) {
48 if (smd == NULL) {
49 ALOGE("%s: ERROR: Invalid handle to ia_sensor_mgr", __func__);
50 return -1;
51 }
52
53 if (smd->dev_node) {
54 fclose(smd->dev_node);
55 }
56
57 free(smd);
58
59 return 0;
60 }
61
oslo_driver_set_param(struct ia_sensor_mgr * smd,int param_id,float param_val)62 void oslo_driver_set_param(struct ia_sensor_mgr *smd, int param_id, float param_val) {
63 int err = 0;
64 struct iaxxx_sensor_param sp;
65
66 if (NULL == smd) {
67 ALOGE("%s: NULL handle passed", __func__);
68 return;
69 }
70
71 sp.inst_id = 0;
72 sp.block_id = 0;
73
74 sp.param_id = param_id;
75 sp.param_val = param_val;
76
77 ALOGD("Set sensor param 0x%X with value %f", param_id, param_val);
78 fprintf(stdout, "Set sensor param 0x%X with value %f\n", param_id, param_val);
79
80 err = ioctl(fileno(smd->dev_node), MODULE_SENSOR_SET_PARAM, (unsigned long)&sp);
81 if (-1 == err) {
82 ALOGE("%s: ERROR: MODULE_SENSOR_SET_PARAM IOCTL failed with error %d(%s)", __func__, errno,
83 strerror(errno));
84 return;
85 }
86 }
87
oslo_driver_get_param(struct ia_sensor_mgr * smd,int param_id)88 uint32_t oslo_driver_get_param(struct ia_sensor_mgr *smd, int param_id) {
89 struct iaxxx_sensor_param sp;
90 int err = 0;
91 ALOGD("Get param - param_id 0x%X", param_id);
92
93 if (NULL == smd) {
94 ALOGE("%s: NULL handle passed", __func__);
95 return 0;
96 }
97
98 sp.inst_id = 0;
99 sp.block_id = 0;
100
101 sp.param_id = param_id;
102 sp.param_val = 0;
103 err = ioctl(fileno(smd->dev_node), MODULE_SENSOR_GET_PARAM, (unsigned long)&sp);
104 if (-1 == err) {
105 ALOGE("%s: ERROR: MODULE_SENSOR_GET_PARAM IOCTL failed with error %d(%s)", __func__, errno,
106 strerror(errno));
107 return 0;
108 } else {
109 ALOGD("Value of param 0x%X is %u", sp.param_id, sp.param_val);
110 fprintf(stdout, "Value of param 0x%X is %u\n", sp.param_id, sp.param_val);
111 }
112
113 return sp.param_val;
114 }
115
oslo_driver_set_param_blk(struct ia_sensor_mgr * smd,uint32_t param_blk_id,const void * blk_data,uint32_t blk_size)116 size_t oslo_driver_set_param_blk(struct ia_sensor_mgr *smd, uint32_t param_blk_id,
117 const void *blk_data, uint32_t blk_size) {
118 size_t bytes_written = 0;
119 struct iaxxx_sensor_param_blk spb;
120 int err;
121
122 if (NULL == smd) {
123 ALOGE("%s: NULL handle passed", __func__);
124 return 0;
125 }
126
127 spb.inst_id = 0;
128 spb.block_id = 0;
129 spb.param_blk_id = param_blk_id;
130
131 spb.blk_data = (uintptr_t)blk_data;
132 spb.blk_size = MIN(blk_size, SENSOR_MAX_PARAMBLK_SIZE);
133
134 ALOGD("Set sensor param blk with size %d", blk_size);
135
136 err = ioctl(fileno(smd->dev_node), MODULE_SENSOR_WRITE_PARAM_BLK, (unsigned long)&spb);
137 if (-1 == err) {
138 ALOGE("%s: ERROR: MODULE_SENSOR_WRITE_PARAM_BLK failed with error %d(%s)", __func__, errno,
139 strerror(errno));
140 } else {
141 bytes_written = spb.blk_size;
142 }
143
144 return bytes_written;
145 }
146
oslo_driver_get_stats(struct ia_sensor_mgr * smd,struct iaxxx_sensor_mode_stats stats[])147 int oslo_driver_get_stats(struct ia_sensor_mgr *smd, struct iaxxx_sensor_mode_stats stats[]) {
148 int rc = 0;
149
150 if (NULL == smd || NULL == stats) {
151 ALOGE("%s: NULL argument passed", __func__);
152 return -EINVAL;
153 }
154
155 rc = ioctl(fileno(smd->dev_node), IAXXX_SENSOR_MODE_STATS, (unsigned long)stats);
156 if (rc != 0) {
157 ALOGE("%s: ERROR: IAXXX_SENSOR_MODE_STATS failed with error %d(%s)", __func__, errno,
158 strerror(errno));
159 }
160
161 return rc;
162 }
163
oslo_plugin_set_param(int param_id,uint32_t param_val)164 void oslo_plugin_set_param(int param_id, uint32_t param_val) {
165 struct iaxxx_odsp_hw *ioh = NULL;
166 int err = 0;
167
168 ioh = iaxxx_odsp_init();
169 if (ioh == NULL) {
170 ALOGE("ERROR: Failed to init odsp HAL");
171 return;
172 }
173
174 err = iaxxx_odsp_plugin_set_parameter(ioh, SENSOR_INSTANCE_ID, param_id, param_val,
175 IAXXX_HMD_BLOCK_ID);
176 if (err != 0) {
177 ALOGE("Failed to set param_id %d with error %d", param_id, err);
178 } else {
179 ALOGD("Set param_id %d with value %" PRIu32, param_id, param_val);
180 }
181
182 if (ioh) {
183 err = iaxxx_odsp_deinit(ioh);
184 if (err != 0) {
185 ALOGE("Failed to deinit the odsp HAL");
186 }
187 }
188 }
189
oslo_plugin_get_param(int param_id)190 uint32_t oslo_plugin_get_param(int param_id) {
191 struct iaxxx_odsp_hw *ioh = NULL;
192 int err = 0;
193 uint32_t param_val;
194
195 ioh = iaxxx_odsp_init();
196 if (ioh == NULL) {
197 ALOGE("ERROR: Failed to init odsp HAL");
198 return 0;
199 }
200
201 err = iaxxx_odsp_plugin_get_parameter(ioh, SENSOR_INSTANCE_ID, param_id, IAXXX_HMD_BLOCK_ID,
202 ¶m_val);
203 if (err != 0) {
204 ALOGE("Failed to get param_id %u with error %d", param_id, err);
205 } else {
206 ALOGD("Value of param 0x%X is %u", param_id, param_val);
207 fprintf(stdout, "Value of param 0x%X is %u\n", param_id, param_val);
208 }
209
210 if (ioh) {
211 err = iaxxx_odsp_deinit(ioh);
212 if (err != 0) {
213 ALOGE("Failed to deinit the odsp HAL");
214 }
215 }
216
217 return param_val;
218 }
219