0d129151d28fd00093b6f3a15b200961baa4df78
[platform/core/system/sensord.git] / src / server / sensor_loader.cpp
1 /*
2  * sensord
3  *
4  * Copyright (c) 2013 Samsung Electronics Co., Ltd.
5  *
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
9  *
10  * http://www.apache.org/licenses/LICENSE-2.0
11  *
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.
17  *
18  */
19
20 #include <dlfcn.h>
21 #include <dirent.h>
22 #include <sensor_common.h>
23 #include <sensor_loader.h>
24 #include <sensor_hal.h>
25 #include <sensor_base.h>
26 #include <sensor_log.h>
27 #include <physical_sensor.h>
28 #include <virtual_sensor.h>
29 #include <external_sensor.h>
30 #include <unordered_set>
31 #include <algorithm>
32 #include <memory>
33
34 #include <hrm_sensor.h>
35
36 #ifdef ENABLE_AUTO_ROTATION
37 #include <auto_rotation_sensor.h>
38 #endif
39 #ifdef ENABLE_GRAVITY
40 #include <gravity_sensor.h>
41 #endif
42 #ifdef ENABLE_LINEAR_ACCEL
43 #include <linear_accel_sensor.h>
44 #endif
45 #ifdef ENABLE_ORIENTATION
46 #include <orientation_sensor.h>
47 #endif
48 #ifdef ENABLE_ROTATION_VECTOR
49 #include <rotation_vector_sensor.h>
50 #endif
51
52 using std::vector;
53 using std::string;
54
55 #define DEVICE_HAL_DIR_PATH "/usr/lib/sensor"
56
57 sensor_loader::sensor_loader()
58 {
59 }
60
61 sensor_loader::~sensor_loader()
62 {
63         sensor_device_map_t::iterator it_device;
64         std::vector<void *>::iterator it_handle;
65
66         for (it_device = m_active_devices.begin(); it_device != m_active_devices.end();)
67                 it_device = m_active_devices.erase(it_device);
68
69         for (it_handle = m_handles.begin(); it_handle != m_handles.end(); ++it_handle)
70                 dlclose(*it_handle);
71
72         m_handles.clear();
73 }
74
75 sensor_loader& sensor_loader::get_instance(void)
76 {
77         static sensor_loader inst;
78         return inst;
79 }
80
81 bool sensor_loader::load(void)
82 {
83         std::vector<string> device_hal_paths;
84         std::vector<string> unique_device_hal_paths;
85
86         get_paths_from_dir(string(DEVICE_HAL_DIR_PATH), device_hal_paths);
87
88         std::unordered_set<string> s;
89         auto unique = [&s](vector<string> &paths, const string &path) {
90                 if (s.insert(path).second)
91                         paths.push_back(path);
92         };
93
94         for_each(device_hal_paths.begin(), device_hal_paths.end(),
95                 [&](const string &path) {
96                         unique(unique_device_hal_paths, path);
97                 }
98         );
99
100         for_each(unique_device_hal_paths.begin(), unique_device_hal_paths.end(),
101                 [&](const string &path) {
102                         void *handle;
103                         load_sensor_devices(path, handle);
104                         m_handles.push_back(handle);
105                 }
106         );
107
108         create_sensors();
109         show_sensor_info();
110
111         return true;
112 }
113
114 bool sensor_loader::load_sensor_devices(const string &path, void* &handle)
115 {
116         sensor_device_t *_devices = NULL;
117         sensor_device *device = NULL;
118         const sensor_info_t *infos;
119
120         _I("load device: [%s]", path.c_str());
121
122         void *_handle = dlopen(path.c_str(), RTLD_NOW);
123         if (!_handle) {
124                 _E("Failed to dlopen(%s), dlerror : %s", path.c_str(), dlerror());
125                 return false;
126         }
127
128         dlerror();
129
130         /* TODO: The out-param of the create function should be const */
131         create_t create_devices = (create_t) dlsym(_handle, "create");
132         if (!create_devices) {
133                 _E("Failed to find symbols in %s", path.c_str());
134                 dlclose(_handle);
135                 return false;
136         }
137
138         int device_size = create_devices(&_devices);
139         if (!_devices) {
140                 _E("Failed to create devices, path is %s\n", path.c_str());
141                 dlclose(_handle);
142                 return false;
143         }
144
145         for (int i = 0; i < device_size; ++i) {
146                 device = static_cast<sensor_device *>(_devices[i]);
147                 std::shared_ptr<sensor_device> device_ptr(device);
148
149                 int info_size = device_ptr->get_sensors(&infos);
150                 for (int j = 0; j < info_size; ++j)
151                         m_devices[&infos[j]] = device_ptr;
152         }
153
154         handle = _handle;
155
156         return true;
157 }
158
159 void sensor_loader::create_sensors(void)
160 {
161         /* HRM sensors need SENSOR_PERMISSION_BIO */
162         create_physical_sensors<hrm_sensor>(HRM_RAW_SENSOR);
163         create_physical_sensors<hrm_sensor>(HRM_SENSOR);
164         create_physical_sensors<hrm_sensor>(HRM_LED_GREEN_SENSOR);
165         create_physical_sensors<hrm_sensor>(HRM_LED_IR_SENSOR);
166         create_physical_sensors<hrm_sensor>(HRM_LED_RED_SENSOR);
167
168         create_physical_sensors<physical_sensor>(UNKNOWN_SENSOR);
169
170 #ifdef ENABLE_AUTO_ROTATION
171         create_virtual_sensors<auto_rotation_sensor>("Auto Rotation");
172 #endif
173 #ifdef ENABLE_ROTATION_VECTOR
174         create_virtual_sensors<rotation_vector_sensor>("Rotation Vector");
175 #endif
176 #ifdef ENABLE_GRAVITY
177         create_virtual_sensors<gravity_sensor>("Gravity");
178 #endif
179 #ifdef ENABLE_LINEAR_ACCEL
180         create_virtual_sensors<linear_accel_sensor>("Linear Accel");
181 #endif
182 #ifdef ENABLE_ORIENTATION
183         create_virtual_sensors<orientation_sensor>("Orientation");
184 #endif
185 }
186
187 template<typename _sensor>
188 void sensor_loader::create_physical_sensors(sensor_type_t type)
189 {
190         int32_t index;
191         const sensor_info_t *info;
192         physical_sensor *sensor;
193         sensor_device *device;
194
195         sensor_device_map_t::iterator it;
196
197         for (it = m_devices.begin(); it != m_devices.end(); ++it) {
198                 info = it->first;
199                 device = it->second.get();
200
201                 if (type != UNKNOWN_SENSOR) {
202                         if (type != (sensor_type_t)(info->type))
203                                 continue;
204                 }
205
206                 sensor = dynamic_cast<physical_sensor *>(create_sensor<_sensor>());
207
208                 if (!sensor) {
209                         _E("Memory allocation failed[%s]", info->name);
210                         return;
211                 }
212
213                 sensor_type_t _type = (sensor_type_t)info->type;
214                 index = (int32_t)m_sensors.count(_type);
215
216                 sensor->set_id(((int64_t)_type << SENSOR_TYPE_SHIFT) | index);
217                 sensor->set_sensor_info(info);
218                 sensor->set_sensor_device(device);
219
220                 std::shared_ptr<sensor_base> sensor_ptr(sensor);
221                 m_sensors.insert(std::make_pair(_type, sensor_ptr));
222
223                 m_active_devices[it->first] = it->second;
224                 m_devices.erase(it->first);
225
226                 _I("created [%s] sensor", sensor->get_name());
227         }
228 }
229
230 template <typename _sensor>
231 void sensor_loader::create_virtual_sensors(const char *name)
232 {
233         int32_t index;
234         sensor_type_t type;
235         virtual_sensor *instance;
236
237         instance = dynamic_cast<virtual_sensor *>(create_sensor<_sensor>());
238         if (!instance) {
239                 _E("Memory allocation failed[%s]", name);
240                 return;
241         }
242
243         if (!instance->init()) {
244                 _E("Failed to init %s", name);
245                 delete instance;
246                 return;
247         }
248
249         std::shared_ptr<sensor_base> sensor(instance);
250         type = sensor->get_type();
251         index = (int32_t)(m_sensors.count(type));
252
253         sensor->set_id((int64_t)type << SENSOR_TYPE_SHIFT | index);
254
255         m_sensors.insert(std::make_pair(type, sensor));
256
257         _I("created [%s] sensor", sensor->get_name());
258 }
259
260 template <typename _sensor>
261 void sensor_loader::create_external_sensors(const char *name)
262 {
263         int32_t index;
264         sensor_type_t type;
265         external_sensor *instance;
266
267         instance = dynamic_cast<external_sensor *>(create_sensor<_sensor>());
268         if (!instance) {
269                 _E("Memory allocation failed[%s]", name);
270                 return;
271         }
272
273         std::shared_ptr<sensor_base> sensor(instance);
274         type = sensor->get_type();
275         index = (int32_t)(m_sensors.count(type));
276
277         sensor->set_id((int64_t)type << SENSOR_TYPE_SHIFT | index);
278
279         m_sensors.insert(std::make_pair(type, sensor));
280
281         _I("created [%s] sensor", sensor->get_name());
282 }
283
284 template <typename _sensor>
285 sensor_base* sensor_loader::create_sensor(void)
286 {
287         sensor_base *instance = NULL;
288
289         try {
290                 instance = new _sensor;
291         } catch (std::exception &e) {
292                 _E("Failed to create sensor, exception: %s", e.what());
293                 return NULL;
294         } catch (int err) {
295                 _ERRNO(errno, _E, "Failed to create sensor");
296                 return NULL;
297         }
298
299         return instance;
300 }
301
302 void sensor_loader::show_sensor_info(void)
303 {
304         _I("========== Loaded sensor information ==========\n");
305
306         int index = 0;
307
308         auto it = m_sensors.begin();
309
310         while (it != m_sensors.end()) {
311                 sensor_base *sensor = it->second.get();
312
313                 sensor_info info;
314                 sensor->get_sensor_info(info);
315                 _I("No:%d [%s]\n", ++index, sensor->get_name());
316                 info.show();
317                 it++;
318         }
319
320         _I("===============================================\n");
321 }
322
323 bool sensor_loader::get_paths_from_dir(const string &dir_path, vector<string> &hal_paths)
324 {
325         DIR *dir = NULL;
326         struct dirent dir_entry;
327         struct dirent *result;
328         string name;
329         int ret;
330
331         dir = opendir(dir_path.c_str());
332
333         if (!dir) {
334                 _E("Failed to open dir: %s", dir_path.c_str());
335                 return false;
336         }
337
338         while (true) {
339                 ret = readdir_r(dir, &dir_entry, &result);
340
341                 if (ret != 0)
342                         continue;
343
344                 if (result == NULL)
345                         break;
346
347                 name = string(dir_entry.d_name);
348
349                 if (name == "." || name == "..")
350                         continue;
351
352                 hal_paths.push_back(dir_path + "/" + name);
353         }
354
355         closedir(dir);
356         return true;
357 }
358
359 sensor_base* sensor_loader::get_sensor(sensor_type_t type)
360 {
361         auto it = m_sensors.find(type);
362
363         if (it == m_sensors.end())
364                 return NULL;
365
366         return it->second.get();
367 }
368
369 sensor_base* sensor_loader::get_sensor(sensor_id_t id)
370 {
371         vector<sensor_base *> sensors;
372
373         sensor_type_t type = static_cast<sensor_type_t>(id >> SENSOR_TYPE_SHIFT);
374         unsigned int index = (id & SENSOR_INDEX_MASK);
375
376         sensors = get_sensors(type);
377
378         if (index >= sensors.size())
379                 return NULL;
380
381         return sensors[index];
382 }
383
384 vector<sensor_type_t> sensor_loader::get_sensor_types(void)
385 {
386         vector<sensor_type_t> sensor_types;
387
388         auto it = m_sensors.begin();
389
390         while (it != m_sensors.end()) {
391                 sensor_types.push_back((sensor_type_t)(it->first));
392                 it = m_sensors.upper_bound(it->first);
393         }
394
395         return sensor_types;
396 }
397
398 vector<sensor_base *> sensor_loader::get_sensors(sensor_type_t type)
399 {
400         vector<sensor_base *> sensor_list;
401         std::pair<sensor_map_t::iterator, sensor_map_t::iterator> ret;
402
403         if ((int)(type) == (int)SENSOR_DEVICE_ALL)
404                 ret = std::make_pair(m_sensors.begin(), m_sensors.end());
405         else
406                 ret = m_sensors.equal_range(type);
407
408         for (auto it = ret.first; it != ret.second; ++it)
409                 sensor_list.push_back(it->second.get());
410
411         return sensor_list;
412 }
413
414 vector<sensor_base *> sensor_loader::get_virtual_sensors(void)
415 {
416         vector<sensor_base *> virtual_list;
417         sensor_base* sensor;
418
419         for (auto it = m_sensors.begin(); it != m_sensors.end(); ++it) {
420                 sensor = it->second.get();
421
422                 if (!sensor || !sensor->is_virtual())
423                         continue;
424
425                 virtual_list.push_back(sensor);
426         }
427
428         return virtual_list;
429 }