2 * A simple firmware helper program.
4 * Copyright 2005 Red Hat, Inc.
6 * This software may be freely redistributed under the terms of the GNU
9 * You should have received a copy of the GNU General Public License
10 * along with this program; if not, write to the Free Software
11 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24 #include "../../udev_utils.h"
25 #include "../../logging.h"
27 #define FIRMWARE_PATH "/lib/firmware"
31 void log_message(int priority, const char *format, ...)
34 static int udev_log = -1;
39 value = getenv("UDEV_LOG");
41 udev_log = log_priority(value);
46 if (priority > udev_log)
49 va_start(args, format);
50 vsyslog(priority, format, args);
55 /* Set the 'loading' attribute for a firmware device.
56 * 1 == currently loading
60 static int set_loading(const char *device, int value) {
61 char loading_path[PATH_SIZE];
65 snprintf(loading_path, sizeof(loading_path), "/sys/%s/loading", device);
66 loading_path[sizeof(loading_path)-1] = '\0';
67 f = fopen(loading_path, "w");
70 rc = fprintf(f, "%d", value);
77 int main(int argc, char **argv) {
78 char *devpath, *firmware, *action, *driver;
79 char fw_path[PATH_SIZE];
80 char data_path[PATH_SIZE];
83 size_t fw_buffer_size;
87 logging_init("firmware_helper");
89 driver = getenv("PHYSDEVDRIVER");
92 devpath = getenv("DEVPATH");
93 firmware = getenv("FIRMWARE");
94 action = getenv("ACTION");
95 if (!devpath || !firmware || !action || strcmp(action,"add") != 0) {
96 err("missing devpath, action or firmware");
100 dbg("try to load firmware '%s' for '%s'", firmware, devpath);
101 set_loading(devpath, 1);
103 snprintf(fw_path, sizeof(fw_path), "%s/%s", FIRMWARE_PATH, firmware);
104 fw_path[sizeof(fw_path)-1] = '\0';
105 if (file_map(fw_path, &fw_buffer, &fw_buffer_size) != 0 || fw_buffer_size == 0) {
106 err("could not load firmware '%s' for '%s'", fw_path, devpath);
111 snprintf(data_path, sizeof(data_path), "/sys/%s/data", devpath);
112 data_path[sizeof(data_path)-1] = '\0';
113 fw_fd = open(data_path, O_RDWR);
120 while (count < fw_buffer_size) {
123 c = write(fw_fd, fw_buffer+count, fw_buffer_size);
133 file_unmap(fw_buffer, fw_buffer_size);
134 set_loading(devpath, 0);
135 info("loaded '%s' for device '%s'", fw_path, devpath);
141 file_unmap(fw_buffer, fw_buffer_size);
142 set_loading(devpath, -1);
144 err("error loading '%s' for device '%s' with driver '%s'", fw_path, devpath, driver);