tizen 2.3 release
[framework/system/deviced.git] / src / gpio / gpio.c
1 /*
2  * deviced
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 <stdlib.h>
21 #include <sys/stat.h>
22 #include <unistd.h>
23 #include <errno.h>
24 #include <fcntl.h>
25 #include <dirent.h>
26 #include <stdbool.h>
27
28 #include "core/log.h"
29 #include "core/common.h"
30 #include "core/devices.h"
31 #include "core/edbus-handler.h"
32 #include "core/list.h"
33 #include "gpio.h"
34
35 static dd_list *gpio_head;
36
37 static const struct gpio_device default_gpio = {
38         .name = "default-gpio",
39 };
40
41 void register_gpio_device(const struct gpio_device *gpio)
42 {
43         DD_LIST_APPEND(gpio_head, (void*)gpio);
44 }
45
46 void unregister_gpio_device(const struct gpio_device *gpio)
47 {
48         DD_LIST_REMOVE(gpio_head, (void*)gpio);
49 }
50
51 int check_default_gpio_device(const struct gpio_device *gpio)
52 {
53         return (gpio == &default_gpio);
54 }
55
56 const struct gpio_device *find_gpio_device(const char *name)
57 {
58         dd_list *elem;
59         const struct gpio_device *gpio;
60
61         DD_LIST_FOREACH(gpio_head, elem, gpio) {
62                 if (!strcmp(gpio->name, name))
63                         return gpio;
64         }
65
66         gpio = &default_gpio;
67         return gpio;
68 }
69
70 static DBusMessage *check_gpio_status(E_DBus_Object *obj, DBusMessage *msg)
71 {
72         DBusMessageIter iter;
73         DBusMessage *reply;
74         const struct gpio_device *gpio;
75         char *name;
76         int ret;
77         int status = GPIO_DEVICE_UNKNOWN;
78
79         ret = dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &name,
80                         DBUS_TYPE_INVALID);
81         if (!ret) {
82                 status = -EBADMSG;
83                 goto out;
84         }
85
86         gpio = find_gpio_device(name);
87         if (check_default_gpio_device(gpio))
88                 goto out;
89         status = gpio->status();
90                 _D("%s %d", name, status);
91 out:
92         reply = dbus_message_new_method_return(msg);
93         dbus_message_iter_init_append(reply, &iter);
94         dbus_message_iter_append_basic(&iter, DBUS_TYPE_INT32, &status);
95         return reply;
96 }
97
98 static const struct edbus_method edbus_methods[] = {
99         { "GetStatus",          "s", "i", check_gpio_status },
100 };
101
102 static void gpio_init(void *data)
103 {
104         struct gpio_device *gpio;
105         dd_list *elem;
106         int ret;
107
108         DD_LIST_FOREACH(gpio_head, elem, gpio) {
109                 gpio->init();
110                 gpio->status();
111         }
112
113         ret = register_edbus_method(DEVICED_PATH_GPIO, edbus_methods, ARRAY_SIZE(edbus_methods));
114         if (ret < 0)
115                 _E("fail to init edbus method(%d)", ret);
116 }
117
118 const struct device_ops gpio_device_ops = {
119         .priority = DEVICE_PRIORITY_NORMAL,
120         .name     = "gpio",
121         .init     = gpio_init,
122 };
123
124 DEVICE_OPS_REGISTER(&gpio_device_ops)