2 * Copyright 2009-2010, Colin Günther, coling@gmx.de.
3 * All Rights Reserved. Distributed under the terms of the MIT License.
8 #include <posix/sys/mman.h>
10 #include <compat/sys/param.h>
11 #include <compat/sys/firmware.h>
12 #include <compat/sys/haiku-module.h>
17 #include <FindDirectory.h>
18 #include <StorageDefs.h>
19 #include <SupportDefs.h>
24 #define MAX_FBSD_FIRMWARE_NAME_CHARS 64
25 // For strndup, beeing cautious in kernel code is a good thing.
26 // NB: This constant doesn't exist in FreeBSD.
30 getHaikuFirmwareName(const char* fbsdFirmwareName
,
31 const char* unknownFirmwareName
)
35 if (__haiku_firmware_name_map
== NULL
)
36 return unknownFirmwareName
;
38 for (i
= 0; i
< __haiku_firmware_parts_count
; i
++) {
39 if (strcmp(__haiku_firmware_name_map
[i
][0], fbsdFirmwareName
) == 0)
40 return __haiku_firmware_name_map
[i
][1];
42 return unknownFirmwareName
;
46 const struct firmware
*
47 firmware_get(const char* fbsdFirmwareName
)
49 char* fbsdFirmwareNameCopy
= NULL
;
50 int fileDescriptor
= -1;
51 struct firmware
* firmware
= NULL
;
52 int32 firmwareFileSize
;
53 char* firmwarePath
= NULL
;
54 const char* haikuFirmwareName
= NULL
;
55 ssize_t readCount
= 0;
56 directory_which checkDirs
[] = { B_SYSTEM_NONPACKAGED_DATA_DIRECTORY
,
57 B_SYSTEM_DATA_DIRECTORY
};
59 = sizeof(checkDirs
) / sizeof(checkDirs
[0]);
62 haikuFirmwareName
= getHaikuFirmwareName(fbsdFirmwareName
,
65 firmwarePath
= (char*)malloc(B_PATH_NAME_LENGTH
);
66 if (firmwarePath
== NULL
)
70 for (; i
< numCheckDirs
; i
++) {
71 if (find_directory(checkDirs
[i
], -1, false, firmwarePath
,
72 B_PATH_NAME_LENGTH
) != B_OK
) {
76 strlcat(firmwarePath
, "/firmware/", B_PATH_NAME_LENGTH
);
77 strlcat(firmwarePath
, gDriverName
, B_PATH_NAME_LENGTH
);
78 strlcat(firmwarePath
, "/", B_PATH_NAME_LENGTH
);
79 strlcat(firmwarePath
, haikuFirmwareName
, B_PATH_NAME_LENGTH
);
81 fileDescriptor
= open(firmwarePath
, B_READ_ONLY
);
82 if (fileDescriptor
>= 0)
86 if (fileDescriptor
< 0)
89 firmwareFileSize
= lseek(fileDescriptor
, 0, SEEK_END
);
90 if (firmwareFileSize
== -1)
93 lseek(fileDescriptor
, 0, SEEK_SET
);
95 fbsdFirmwareNameCopy
= strndup(fbsdFirmwareName
,
96 MAX_FBSD_FIRMWARE_NAME_CHARS
);
97 if (fbsdFirmwareNameCopy
== NULL
)
100 firmware
= (struct firmware
*)malloc(sizeof(struct firmware
));
101 if (firmware
== NULL
)
104 firmware
->data
= malloc(firmwareFileSize
);
105 if (firmware
->data
== NULL
)
108 readCount
= read(fileDescriptor
, (void*)firmware
->data
, firmwareFileSize
);
109 if (readCount
== -1 || readCount
< firmwareFileSize
) {
110 free((void*)firmware
->data
);
114 firmware
->datasize
= firmwareFileSize
;
115 firmware
->name
= fbsdFirmwareNameCopy
;
116 firmware
->version
= __haiku_firmware_version
;
118 close(fileDescriptor
);
125 if (fbsdFirmwareNameCopy
)
126 free(fbsdFirmwareNameCopy
);
129 if (fileDescriptor
>= 0)
130 close(fileDescriptor
);
136 firmware_put(const struct firmware
* firmware
, int flags
)
138 if (firmware
== NULL
)
142 free((void*)firmware
->data
);
144 free((void*)firmware
->name
);
145 free((void*)firmware
);