4 * Copyright (c) 2014 Samsung Electronics Co., Ltd.
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
10 * http://www.apache.org/licenses/LICENSE-2.0
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
23 #include <sys/ioctl.h>
25 #include <linux/input.h>
27 #include <proxi_sensor_hal.h>
28 #include <iio_common.h>
31 using config::CConfig;
33 #define INITIAL_VALUE -1
34 #define INITIAL_TIME 0
36 #define SENSOR_TYPE_PROXI "PROXI"
37 #define ELEMENT_NAME "NAME"
38 #define ELEMENT_VENDOR "VENDOR"
39 #define ATTR_VALUE "value"
41 #define INPUT_NAME "proximity_sensor"
44 #define ENABLE_VAL true
45 #define DISABLE_VAL false
47 proxi_sensor_hal::proxi_sensor_hal()
48 : m_state(PROXIMITY_STATE_FAR)
49 , m_node_handle(INITIAL_VALUE)
50 , m_fired_time(INITIAL_TIME)
51 , m_sensorhub_supported(false)
57 ERR("check_hw_node() fail");
61 CConfig &config = CConfig::get_instance();
63 if (!config.get(SENSOR_TYPE_PROXI, m_model_id, ELEMENT_VENDOR, m_vendor))
65 ERR("[VENDOR] is empty");
69 INFO("m_vendor = %s", m_vendor.c_str());
71 if (!config.get(SENSOR_TYPE_PROXI, m_model_id, ELEMENT_NAME, m_chip_name))
73 ERR("[NAME] is empty");
77 INFO("m_chip_name = %s", m_chip_name.c_str());
79 fd = open(m_event_resource.c_str(), NO_FLAG);
82 ERR("Could not open event resource");
86 ret = ioctl(fd, IOCTL_IIO_EVENT_FD, &m_event_fd);
90 if ((ret == -1) || (m_event_fd == -1))
92 ERR("Failed to retrieve event fd");
96 INFO("proxi_sensor_hal is created!");
99 proxi_sensor_hal::~proxi_sensor_hal()
102 INFO("proxi_sensor_hal is destroyed!");
105 string proxi_sensor_hal::get_model_id(void)
110 sensor_type_t proxi_sensor_hal::get_type(void)
112 return PROXIMITY_SENSOR;
115 bool proxi_sensor_hal::enable_resource(bool enable)
117 update_sysfs_num(m_enable_resource.c_str(), enable);
121 bool proxi_sensor_hal::enable(void)
125 enable_resource(ENABLE_VAL);
128 INFO("Proximity sensor real starting");
132 bool proxi_sensor_hal::disable(void)
136 enable_resource(DISABLE_VAL);
138 INFO("Proximity sensor real stopping");
142 bool proxi_sensor_hal::update_value(bool wait)
144 iio_event_t proxi_event;
145 fd_set readfds, exceptfds;
149 FD_SET(m_event_fd, &readfds);
150 FD_SET(m_event_fd, &exceptfds);
153 ret = select(m_event_fd + 1, &readfds, NULL, &exceptfds, NULL);
157 ERR("select error:%s m_event_fd:d", strerror(errno), m_event_fd);
162 DBG("select timeout");
166 if (FD_ISSET(m_event_fd, &exceptfds))
168 ERR("select exception occurred!");
172 if (FD_ISSET(m_event_fd, &readfds))
174 INFO("proximity event detection!");
175 int len = read(m_event_fd, &proxi_event, sizeof(proxi_event));
179 DBG("Error in read(m_event_fd):%s.", strerror(errno));
184 ev_data.num = proxi_event.event_id;
185 if (ev_data.bytes[CH_TYPE] == PROXIMITY_TYPE)
187 AUTOLOCK(m_value_mutex);
189 temp = GET_DIR_VAL(ev_data.bytes[DIRECTION]);
190 if (temp == PROXIMITY_NODE_STATE_FAR)
192 INFO("PROXIMITY_STATE_FAR state occurred");
193 m_state = PROXIMITY_STATE_FAR;
195 else if (temp == PROXIMITY_NODE_STATE_NEAR)
197 INFO("PROXIMITY_STATE_NEAR state occurred");
198 m_state = PROXIMITY_STATE_NEAR;
202 ERR("PROXIMITY_STATE Unknown: %d", proxi_event.event_id);
206 m_fired_time = proxi_event.timestamp;
210 ERR("No proximity event data available to read");
217 bool proxi_sensor_hal::is_data_ready(bool wait)
220 ret = update_value(wait);
224 int proxi_sensor_hal::get_sensor_data(sensor_data_t &data)
226 AUTOLOCK(m_value_mutex);
227 data.data_accuracy = SENSOR_ACCURACY_UNDEFINED;
228 data.data_unit_idx = SENSOR_UNIT_STATE_ON_OFF;
229 data.timestamp = m_fired_time;
231 data.values[0] = (float)(m_state);
235 bool proxi_sensor_hal::get_properties(sensor_properties_t &properties)
237 properties.sensor_unit_idx = SENSOR_UNIT_STATE_ON_OFF;
238 properties.sensor_min_range = 0;
239 properties.sensor_max_range = 1;
240 snprintf(properties.sensor_name, sizeof(properties.sensor_name), "%s", m_chip_name.c_str());
241 snprintf(properties.sensor_vendor, sizeof(properties.sensor_vendor), "%s", m_vendor.c_str());
242 properties.sensor_resolution = 1;
246 bool proxi_sensor_hal::is_sensorhub_supported(void)
251 bool proxi_sensor_hal::check_hw_node(void)
256 DIR *main_dir = NULL;
257 struct dirent *dir_entry = NULL;
258 bool find_node = false;
260 INFO("======================start check_hw_node=============================");
262 m_sensorhub_supported = is_sensorhub_supported();
263 main_dir = opendir(IIO_DIR);
267 ERR("Could not open IIO directory\n");
273 dir_entry = readdir(main_dir);
274 if(dir_entry == NULL)
277 if ((strncasecmp(dir_entry->d_name , ".", 1 ) != 0) && (strncasecmp(dir_entry->d_name , "..", 2 ) != 0) && (dir_entry->d_ino != 0))
279 file_name = string(IIO_DIR) + string(dir_entry->d_name) + string(NAME_NODE);
281 ifstream infile(file_name.c_str());
288 if (strncmp(dir_entry->d_name, IIO_DEV_BASE_NAME, IIO_DEV_STR_LEN) == 0)
290 if (CConfig::get_instance().is_supported(SENSOR_TYPE_PROXI, hw_name) == true)
292 m_name = m_model_id = hw_name;
293 m_proxi_dir = string(dir_entry->d_name);
294 m_enable_resource = string(IIO_DIR) + m_proxi_dir + string(EVENT_DIR) + string(EVENT_EN_NODE);
295 m_event_resource = string(DEV_DIR) + m_proxi_dir;
297 INFO("m_enable_resource = %s", m_enable_resource.c_str());
298 INFO("m_model_id = %s", m_model_id.c_str());
299 INFO("m_proxi_dir = %s", m_proxi_dir.c_str());
300 INFO("m_event_resource = %s", m_event_resource.c_str());
313 extern "C" void *create(void)
315 proxi_sensor_hal *inst;
319 inst = new proxi_sensor_hal();
323 ERR("Failed to create proxi_sensor_hal class, errno : %d, errstr : %s", err, strerror(err));
330 extern "C" void destroy(void *inst)
332 delete (proxi_sensor_hal *)inst;