sensord: merge tizen 2.3 sensord into tizen branch
[platform/core/system/sensord.git] / src / accel / accel_sensor.cpp
1 /*
2  * sensord
3  *
4  * Copyright (c) 2014 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 <common.h>
21 #include <sf_common.h>
22
23 #include <accel_sensor.h>
24 #include <sensor_plugin_loader.h>
25 #include <algorithm>
26
27 using std::bind1st;
28 using std::mem_fun;
29
30 #define GRAVITY 9.80665
31 #define G_TO_MG 1000
32
33 #define RAW_DATA_TO_G_UNIT(X) (((float)(X))/((float)G_TO_MG))
34 #define RAW_DATA_TO_METRE_PER_SECOND_SQUARED_UNIT(X) (GRAVITY * (RAW_DATA_TO_G_UNIT(X)))
35
36 #define SENSOR_NAME "ACCELEROMETER_SENSOR"
37
38 accel_sensor::accel_sensor()
39 : m_sensor_hal(NULL)
40 , m_interval(POLL_1HZ_MS)
41 {
42         m_name = string(SENSOR_NAME);
43
44         vector<unsigned int> supported_events = {
45                 ACCELEROMETER_EVENT_RAW_DATA_REPORT_ON_TIME,
46                 ACCELEROMETER_EVENT_UNPROCESSED_DATA_REPORT_ON_TIME,
47         };
48
49         for_each(supported_events.begin(), supported_events.end(),
50                 bind1st(mem_fun(&sensor_base::register_supported_event), this));
51
52         physical_sensor::set_poller(accel_sensor::working, this);
53 }
54
55 accel_sensor::~accel_sensor()
56 {
57         INFO("accel_sensor is destroyed!\n");
58 }
59
60 bool accel_sensor::init()
61 {
62         m_sensor_hal = sensor_plugin_loader::get_instance().get_sensor_hal(ACCELEROMETER_SENSOR);
63
64         if (!m_sensor_hal) {
65                 ERR("cannot load sensor_hal[%s]", sensor_base::get_name());
66                 return false;
67         }
68
69         sensor_properties_s properties;
70
71         if (m_sensor_hal->get_properties(properties) == false) {
72                 ERR("sensor->get_properties() is failed!\n");
73                 return false;
74         }
75
76         m_raw_data_unit = properties.resolution / GRAVITY * G_TO_MG;
77
78         INFO("m_raw_data_unit accel : [%f]\n", m_raw_data_unit);
79
80         INFO("%s is created!\n", sensor_base::get_name());
81         return true;
82 }
83
84 sensor_type_t accel_sensor::get_type(void)
85 {
86         return ACCELEROMETER_SENSOR;
87 }
88
89 bool accel_sensor::working(void *inst)
90 {
91         accel_sensor *sensor = (accel_sensor*)inst;
92         return sensor->process_event();
93 }
94
95 bool accel_sensor::process_event(void)
96 {
97         sensor_event_t base_event;
98
99         if (!m_sensor_hal->is_data_ready(true))
100                 return true;
101
102         m_sensor_hal->get_sensor_data(base_event.data);
103
104         AUTOLOCK(m_mutex);
105         AUTOLOCK(m_client_info_mutex);
106
107         if (get_client_cnt(ACCELEROMETER_EVENT_UNPROCESSED_DATA_REPORT_ON_TIME)) {
108                 base_event.sensor_id = get_id();
109                 base_event.event_type = ACCELEROMETER_EVENT_UNPROCESSED_DATA_REPORT_ON_TIME;
110                 push(base_event);
111         }
112
113         if (get_client_cnt(ACCELEROMETER_EVENT_RAW_DATA_REPORT_ON_TIME)) {
114                 base_event.sensor_id = get_id();
115                 base_event.event_type = ACCELEROMETER_EVENT_RAW_DATA_REPORT_ON_TIME;
116                 raw_to_base(base_event.data);
117                 push(base_event);
118         }
119
120         return true;
121 }
122
123 bool accel_sensor::on_start(void)
124 {
125         if (!m_sensor_hal->enable()) {
126                 ERR("m_sensor_hal start fail\n");
127                 return false;
128         }
129
130         return start_poll();
131 }
132
133 bool accel_sensor::on_stop(void)
134 {
135         if (!m_sensor_hal->disable()) {
136                 ERR("m_sensor_hal stop fail\n");
137                 return false;
138         }
139
140         return stop_poll();
141 }
142
143 bool accel_sensor::get_properties(sensor_properties_s &properties)
144 {
145         return m_sensor_hal->get_properties(properties);
146 }
147
148 int accel_sensor::get_sensor_data(unsigned int type, sensor_data_t &data)
149 {
150         if (m_sensor_hal->get_sensor_data(data) < 0) {
151                 ERR("Failed to get sensor data");
152                 return -1;
153         }
154
155         if (type == ACCELEROMETER_BASE_DATA_SET) {
156                 raw_to_base(data);
157         } else {
158                 ERR("Does not support type: 0x%x", type);
159                 return -1;
160         }
161
162         return 0;
163 }
164
165 bool accel_sensor::set_interval(unsigned long interval)
166 {
167         AUTOLOCK(m_mutex);
168
169         m_interval = interval;
170
171         INFO("Polling interval is set to %dms", interval);
172
173         return m_sensor_hal->set_interval(interval);
174 }
175
176 void accel_sensor::raw_to_base(sensor_data_t &data)
177 {
178         data.value_count = 3;
179         data.values[0] = RAW_DATA_TO_METRE_PER_SECOND_SQUARED_UNIT(data.values[0] * m_raw_data_unit);
180         data.values[1] = RAW_DATA_TO_METRE_PER_SECOND_SQUARED_UNIT(data.values[1] * m_raw_data_unit);
181         data.values[2] = RAW_DATA_TO_METRE_PER_SECOND_SQUARED_UNIT(data.values[2] * m_raw_data_unit);
182 }
183
184 extern "C" sensor_module* create(void)
185 {
186         accel_sensor *sensor;
187
188         try {
189                 sensor = new(std::nothrow) accel_sensor;
190         } catch (int err) {
191                 ERR("Failed to create module, err: %d, cause: %s", err, strerror(err));
192                 return NULL;
193         }
194
195         sensor_module *module = new(std::nothrow) sensor_module;
196         retvm_if(!module || !sensor, NULL, "Failed to allocate memory");
197
198         module->sensors.push_back(sensor);
199         return module;
200 }