blob: 133e796e72f8c3004e573918fab0669f0d071b0e [file] [log] [blame]
San Mehatdc266072009-05-06 11:16:52 -07001/*
2 * Copyright (C) 2008 The Android Open Source Project
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#include <stdio.h>
San Mehat48765672009-05-20 15:28:43 -070017#include <stdlib.h>
San Mehatdc266072009-05-06 11:16:52 -070018#include <string.h>
19#include <fcntl.h>
20#include <unistd.h>
21#include <malloc.h>
22#include <errno.h>
23#include <sys/types.h>
24#include <sys/stat.h>
25#include <unistd.h>
26
27#define LOG_TAG "Controller"
28
29#include <cutils/log.h>
30
31#include "Controller.h"
32
33extern "C" int init_module(void *, unsigned int, const char *);
34extern "C" int delete_module(const char *, unsigned int);
35
San Mehat48765672009-05-20 15:28:43 -070036Controller::Controller(const char *name, const char *prefix) {
San Mehatdc266072009-05-06 11:16:52 -070037 mName = name;
San Mehat48765672009-05-20 15:28:43 -070038 mPropertyPrefix = prefix;
39 mProperties = new PropertyCollection();
40
41 mEnabled = false;
42 registerProperty("enable");
San Mehatdc266072009-05-06 11:16:52 -070043}
44
45int Controller::start() {
46 return 0;
47}
48
49int Controller::stop() {
50 return 0;
51}
52
San Mehat48765672009-05-20 15:28:43 -070053const PropertyCollection & Controller::getProperties() {
54 return *mProperties;
55}
56
57int Controller::setProperty(const char *name, char *value) {
58 if (!strcmp(name, "enable")) {
59 int en = atoi(value);
60 int rc;
61
62 rc = (en ? enable() : disable());
63
64 if (!rc)
65 mEnabled = en;
66
67 return rc;
68 }
69
70 errno = ENOENT;
71 return -1;
72}
73
74const char *Controller::getProperty(const char *name, char *buffer, size_t maxsize) {
75 if (!strcmp(name, "enable")) {
76 snprintf(buffer, maxsize, "%d", mEnabled);
77 return buffer;
78 }
79
80 errno = ENOENT;
81 return NULL;
82}
83
84int Controller::registerProperty(const char *name) {
85 PropertyCollection::iterator it;
86
87 for (it = mProperties->begin(); it != mProperties->end(); ++it) {
88 if (!strcmp(name, (*it))) {
89 errno = EADDRINUSE;
90 LOGE("Failed to register property (%s)", strerror(errno));
91 return -1;
92 }
93 }
94
95 mProperties->push_back(name);
96 return 0;
97}
98
99int Controller::unregisterProperty(const char *name) {
100 PropertyCollection::iterator it;
101
102 for (it = mProperties->begin(); it != mProperties->end(); ++it) {
103 if (!strcmp(name, (*it))) {
104 mProperties->erase(it);
105 return 0;
106 }
107 }
108 errno = ENOENT;
109 return -1;
110}
111
San Mehatdc266072009-05-06 11:16:52 -0700112int Controller::loadKernelModule(char *modpath, const char *args) {
113 void *module;
114 unsigned int size;
115
San Mehatdc266072009-05-06 11:16:52 -0700116 module = loadFile(modpath, &size);
117 if (!module) {
118 errno = -EIO;
119 return -1;
120 }
121
122 int rc = init_module(module, size, args);
123 free (module);
124 return rc;
125}
126
127int Controller::unloadKernelModule(const char *modtag) {
128 int rc = -1;
129 int retries = 10;
130
San Mehatdc266072009-05-06 11:16:52 -0700131 while (retries--) {
132 rc = delete_module(modtag, O_NONBLOCK | O_EXCL);
133 if (rc < 0 && errno == EAGAIN)
134 usleep(1000*500);
135 else
136 break;
137 }
138
139 if (rc != 0) {
140 LOGW("Unable to unload kernel driver '%s' (%s)", modtag,
141 strerror(errno));
142 }
143 return rc;
144}
145
146bool Controller::isKernelModuleLoaded(const char *modtag) {
147 FILE *fp = fopen("/proc/modules", "r");
148
149 if (!fp) {
150 LOGE("Unable to open /proc/modules (%s)", strerror(errno));
151 return false;
152 }
153
154 char line[255];
155 while(fgets(line, sizeof(line), fp)) {
156 char *endTag = strchr(line, ' ');
157
158 if (!endTag) {
159 LOGW("Unable to find tag for line '%s'", line);
160 continue;
161 }
162 if (!strncmp(line, modtag, (endTag - line))) {
163 fclose(fp);
164 return true;
165 }
166 }
167
168 fclose(fp);
169 return false;
170}
171
San Mehatdc266072009-05-06 11:16:52 -0700172void *Controller::loadFile(char *filename, unsigned int *_size)
173{
174 int ret, fd;
175 struct stat sb;
176 ssize_t size;
177 void *buffer = NULL;
178
179 /* open the file */
180 fd = open(filename, O_RDONLY);
181 if (fd < 0)
182 return NULL;
183
184 /* find out how big it is */
185 if (fstat(fd, &sb) < 0)
186 goto bail;
187 size = sb.st_size;
188
189 /* allocate memory for it to be read into */
190 buffer = malloc(size);
191 if (!buffer)
192 goto bail;
193
194 /* slurp it into our buffer */
195 ret = read(fd, buffer, size);
196 if (ret != size)
197 goto bail;
198
199 /* let the caller know how big it is */
200 *_size = size;
201
202bail:
203 close(fd);
204 return buffer;
205}