xref: /freebsd/usr.sbin/bluetooth/ath3kfw/ath3k_fw.c (revision 21a4258d89a4e27632cfd87e5ad6e8538a6e77a2)
1 /*-
2  * Copyright (c) 2013 Adrian Chadd <adrian@freebsd.org>
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer,
10  *    without modification.
11  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
12  *    similar to the "NO WARRANTY" disclaimer below ("Disclaimer") and any
13  *    redistribution must be conditioned upon including a substantially
14  *    similar Disclaimer requirement for further binary redistribution.
15  *
16  * NO WARRANTY
17  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19  * LIMITED TO, THE IMPLIED WARRANTIES OF NONINFRINGEMENT, MERCHANTIBILITY
20  * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
21  * THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY,
22  * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
25  * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
27  * THE POSSIBILITY OF SUCH DAMAGES.
28  *
29  * $FreeBSD$
30  */
31 
32 #include <stdio.h>
33 #include <stdlib.h>
34 #include <unistd.h>
35 #include <errno.h>
36 #include <string.h>
37 #include <err.h>
38 #include <fcntl.h>
39 #include <sys/types.h>
40 #include <sys/stat.h>
41 
42 #include "ath3k_fw.h"
43 #include "ath3k_dbg.h"
44 
45 int
46 ath3k_fw_read(struct ath3k_firmware *fw, const char *fwname)
47 {
48 	int fd;
49 	struct stat sb;
50 	unsigned char *buf;
51 	ssize_t r;
52 	int i;
53 
54 	fd = open(fwname, O_RDONLY);
55 	if (fd < 0) {
56 		warn("%s: open: %s", __func__, fwname);
57 		return (0);
58 	}
59 
60 	if (fstat(fd, &sb) != 0) {
61 		warn("%s: stat: %s", __func__, fwname);
62 		close(fd);
63 		return (0);
64 	}
65 
66 	buf = calloc(1, sb.st_size);
67 	if (buf == NULL) {
68 		warn("%s: calloc", __func__);
69 		close(fd);
70 		return (0);
71 	}
72 
73 	i = 0;
74 	/* XXX handle partial reads */
75 	r = read(fd, buf, sb.st_size);
76 	if (r < 0) {
77 		warn("%s: read", __func__);
78 		free(buf);
79 		close(fd);
80 		return (0);
81 	}
82 
83 	if (r != sb.st_size) {
84 		fprintf(stderr, "%s: read len %d != file size %d\n",
85 		    __func__,
86 		    (int) r,
87 		    (int) sb.st_size);
88 		free(buf);
89 		close(fd);
90 		return (0);
91 	}
92 
93 	/* We have everything, so! */
94 
95 	bzero(fw, sizeof(*fw));
96 
97 	fw->fwname = strdup(fwname);
98 	fw->len = sb.st_size;
99 	fw->size = sb.st_size;
100 	fw->buf = buf;
101 
102 	close(fd);
103 	return (1);
104 }
105 
106 void
107 ath3k_fw_free(struct ath3k_firmware *fw)
108 {
109 	if (fw->fwname)
110 		free(fw->fwname);
111 	if (fw->buf)
112 		free(fw->buf);
113 	bzero(fw, sizeof(*fw));
114 }
115