]> git.karo-electronics.de Git - karo-tx-linux.git/blob - drivers/staging/greybus/manifest.c
greybus: Random spell fixes
[karo-tx-linux.git] / drivers / staging / greybus / manifest.c
1 /*
2  * Greybus module manifest parsing
3  *
4  * Copyright 2014 Google Inc.
5  *
6  * Released under the GPLv2 only.
7  */
8
9 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
10
11 #include <linux/err.h>
12
13 #include "greybus.h"
14
15 /*
16  * We scan the manifest once to identify where all the descriptors
17  * are.  The result is a list of these manifest_desc structures.  We
18  * then pick through them for what we're looking for (starting with
19  * the module descriptor).  As each is processed we remove it from
20  * the list.  When we're done the list should (probably) be empty.
21  */
22 struct manifest_desc {
23         struct list_head                links;
24
25         size_t                          size;
26         void                            *data;
27         enum greybus_descriptor_type    type;
28 };
29
30 static LIST_HEAD(manifest_descs);
31
32 static void release_manifest_descriptor(struct manifest_desc *descriptor)
33 {
34         list_del(&descriptor->links);
35         kfree(descriptor);
36 }
37
38 static void release_manifest_descriptors(void)
39 {
40         struct manifest_desc *descriptor;
41         struct manifest_desc *next;
42
43         list_for_each_entry_safe(descriptor, next, &manifest_descs, links)
44                 release_manifest_descriptor(descriptor);
45 }
46
47 /*
48  * Validate the given descriptor.  Its reported size must fit within
49  * the number of bytes remaining, and it must have a recognized
50  * type.  Check that the reported size is at least as big as what
51  * we expect to see.  (It could be bigger, perhaps for a new version
52  * of the format.)
53  *
54  * Returns the number of bytes consumed by the descriptor, or a
55  * negative errno.
56  */
57 static int identify_descriptor(struct greybus_descriptor *desc, size_t size)
58 {
59         struct greybus_descriptor_header *desc_header = &desc->header;
60         struct manifest_desc *descriptor;
61         int desc_size;
62         size_t expected_size;
63
64         if (size < sizeof(*desc_header)) {
65                 pr_err("manifest too small\n");
66                 return -EINVAL;         /* Must at least have header */
67         }
68
69         desc_size = (int)le16_to_cpu(desc_header->size);
70         if ((size_t)desc_size > size) {
71                 pr_err("descriptor too big\n");
72                 return -EINVAL;
73         }
74
75         switch (desc_header->type) {
76         case GREYBUS_TYPE_MODULE:
77                 if (desc_size < sizeof(struct greybus_descriptor_module)) {
78                         pr_err("module descriptor too small (%u)\n",
79                                 desc_size);
80                         return -EINVAL;
81                 }
82                 break;
83         case GREYBUS_TYPE_STRING:
84                 expected_size = sizeof(*desc_header);
85                 expected_size += sizeof(struct greybus_descriptor_string);
86                 expected_size += (size_t)desc->string.length;
87                 if (desc_size < expected_size) {
88                         pr_err("string descriptor too small (%u)\n",
89                                 desc_size);
90                         return -EINVAL;
91                 }
92                 break;
93         case GREYBUS_TYPE_INTERFACE:
94                 break;
95         case GREYBUS_TYPE_CPORT:
96                 if (desc_size < sizeof(struct greybus_descriptor_cport)) {
97                         pr_err("cport descriptor too small (%u)\n",
98                                 desc_size);
99                         return -EINVAL;
100                 }
101                 break;
102         case GREYBUS_TYPE_CLASS:
103                 pr_warn("class descriptor found (ignoring)\n");
104                 break;
105         case GREYBUS_TYPE_INVALID:
106         default:
107                 pr_err("invalid descriptor type (%hhu)\n", desc_header->type);
108                 return -EINVAL;
109         }
110
111         descriptor = kzalloc(sizeof(*descriptor), GFP_KERNEL);
112         if (!descriptor)
113                 return -ENOMEM;
114
115         descriptor->size = desc_size;
116         descriptor->data = (u8 *)desc + sizeof(*desc_header);
117         descriptor->type = desc_header->type;
118         list_add_tail(&descriptor->links, &manifest_descs);
119
120         return desc_size;
121 }
122
123 /*
124  * Find the string descriptor having the given id, validate it, and
125  * allocate a duplicate copy of it.  The duplicate has an extra byte
126  * which guarantees the returned string is NUL-terminated.
127  *
128  * String index 0 is valid (it represents "no string"), and for
129  * that a null pointer is returned.
130  *
131  * Otherwise returns a pointer to a newly-allocated copy of the
132  * descriptor string, or an error-coded pointer on failure.
133  */
134 static char *gb_string_get(u8 string_id)
135 {
136         struct greybus_descriptor_string *desc_string;
137         struct manifest_desc *descriptor;
138         bool found = false;
139         char *string;
140
141         /* A zero string id means no string (but no error) */
142         if (!string_id)
143                 return NULL;
144
145         list_for_each_entry(descriptor, &manifest_descs, links) {
146
147                 if (descriptor->type != GREYBUS_TYPE_STRING)
148                         continue;
149
150                 desc_string = descriptor->data;
151                 if (desc_string->id == string_id) {
152                         found = true;
153                         break;
154                 }
155         }
156         if (!found)
157                 return ERR_PTR(-ENOENT);
158
159         /* Allocate an extra byte so we can guarantee it's NUL-terminated */
160         string = kmemdup(&desc_string->string, (size_t)desc_string->length + 1,
161                                 GFP_KERNEL);
162         if (!string)
163                 return ERR_PTR(-ENOMEM);
164         string[desc_string->length] = '\0';
165
166         /* Ok we've used this string, so we're done with it */
167         release_manifest_descriptor(descriptor);
168
169         return string;
170 }
171
172 /*
173  * Find cport descriptors in the manifest and set up data structures
174  * for the functions that use them.  Returns the number of interfaces
175  * set up for the given module, or 0 if there is an error.
176  */
177 static u32 gb_manifest_parse_cports(struct gb_interface *interface)
178 {
179         u32 count = 0;
180
181         while (true) {
182                 struct manifest_desc *descriptor;
183                 struct greybus_descriptor_cport *desc_cport;
184                 u8 protocol_id;
185                 u16 cport_id;
186                 bool found = false;
187
188                 /* Find a cport descriptor */
189                 list_for_each_entry(descriptor, &manifest_descs, links) {
190                         if (descriptor->type == GREYBUS_TYPE_CPORT) {
191                                 desc_cport = descriptor->data;
192                                 if (desc_cport->interface == interface->id) {
193                                         found = true;
194                                         break;
195                                 }
196                         }
197                 }
198                 if (!found)
199                         break;
200
201                 /* Found one.  Set up its function structure */
202                 protocol_id = desc_cport->protocol_id;
203                 cport_id = le16_to_cpu(desc_cport->id);
204                 if (!gb_connection_create(interface, cport_id, protocol_id))
205                         return 0;       /* Error */
206
207                 count++;
208                 /* Release the cport descriptor */
209                 release_manifest_descriptor(descriptor);
210         }
211
212         return count;
213 }
214
215 /*
216  * Find interface descriptors in the manifest and set up their data
217  * structures.  Returns the number of interfaces set up for the
218  * given module.
219  */
220 static u32 gb_manifest_parse_interfaces(struct gb_module *gmod)
221 {
222         u32 count = 0;
223
224         while (true) {
225                 struct manifest_desc *descriptor;
226                 struct greybus_descriptor_interface *desc_interface;
227                 struct gb_interface *interface;
228                 bool found = false;
229
230                 /* Find an interface descriptor */
231                 list_for_each_entry(descriptor, &manifest_descs, links) {
232                         if (descriptor->type == GREYBUS_TYPE_INTERFACE) {
233                                 found = true;
234                                 break;
235                         }
236                 }
237                 if (!found)
238                         break;
239
240                 /* Found one.  Set up its interface structure*/
241                 desc_interface = descriptor->data;
242                 interface = gb_interface_create(gmod, desc_interface->id);
243                 if (!interface)
244                         return 0;       /* Error */
245
246                 /* Now go set up this interface's functions and cports */
247                 if (!gb_manifest_parse_cports(interface))
248                         return 0;       /* Error parsing cports */
249
250                 count++;
251
252                 /* Done with this interface descriptor */
253                 release_manifest_descriptor(descriptor);
254         }
255
256         return count;
257 }
258
259 static bool gb_manifest_parse_module(struct gb_module *gmod,
260                                         struct manifest_desc *module_desc)
261 {
262         struct greybus_descriptor_module *desc_module = module_desc->data;
263
264         /* Handle the strings first--they can fail */
265         gmod->vendor_string = gb_string_get(desc_module->vendor_stringid);
266         if (IS_ERR(gmod->vendor_string))
267                 return false;
268
269         gmod->product_string = gb_string_get(desc_module->product_stringid);
270         if (IS_ERR(gmod->product_string)) {
271                 goto out_free_vendor_string;
272         }
273
274         gmod->vendor = le16_to_cpu(desc_module->vendor);
275         gmod->product = le16_to_cpu(desc_module->product);
276         gmod->version = le16_to_cpu(desc_module->version);
277         gmod->unique_id = le64_to_cpu(desc_module->unique_id);
278
279         /* Release the module descriptor, now that we're done with it */
280         release_manifest_descriptor(module_desc);
281
282         /* A module must have at least one interface descriptor */
283         if (!gb_manifest_parse_interfaces(gmod)) {
284                 pr_err("manifest interface descriptors not valid\n");
285                 goto out_err;
286         }
287
288         return true;
289 out_err:
290         kfree(gmod->product_string);
291         gmod->product_string = NULL;
292 out_free_vendor_string:
293         kfree(gmod->vendor_string);
294         gmod->vendor_string = NULL;
295
296         return false;
297 }
298
299 /*
300  * Parse a buffer containing a module manifest.
301  *
302  * If we find anything wrong with the content/format of the buffer
303  * we reject it.
304  *
305  * The first requirement is that the manifest's version is
306  * one we can parse.
307  *
308  * We make an initial pass through the buffer and identify all of
309  * the descriptors it contains, keeping track for each its type
310  * and the location size of its data in the buffer.
311  *
312  * Next we scan the descriptors, looking for a module descriptor;
313  * there must be exactly one of those.  When found, we record the
314  * information it contains, and then remove that descriptor (and any
315  * string descriptors it refers to) from further consideration.
316  *
317  * After that we look for the module's interfaces--there must be at
318  * least one of those.
319  *
320  * Returns true if parsing was successful, false otherwise.
321  */
322 bool gb_manifest_parse(struct gb_module *gmod, void *data, size_t size)
323 {
324         struct greybus_manifest *manifest;
325         struct greybus_manifest_header *header;
326         struct greybus_descriptor *desc;
327         struct manifest_desc *descriptor;
328         struct manifest_desc *module_desc = NULL;
329         u16 manifest_size;
330         u32 found = 0;
331         bool result;
332
333         /* Manifest descriptor list should be empty here */
334         if (WARN_ON(!list_empty(&manifest_descs)))
335                 return false;
336
337         /* we have to have at _least_ the manifest header */
338         if (size <= sizeof(manifest->header)) {
339                 pr_err("short manifest (%zu)\n", size);
340                 return false;
341         }
342
343         /* Make sure the size is right */
344         manifest = data;
345         header = &manifest->header;
346         manifest_size = le16_to_cpu(header->size);
347         if (manifest_size != size) {
348                 pr_err("manifest size mismatch %zu != %hu\n",
349                         size, manifest_size);
350                 return false;
351         }
352
353         /* Validate major/minor number */
354         if (header->version_major > GREYBUS_VERSION_MAJOR) {
355                 pr_err("manifest version too new (%hhu.%hhu > %hhu.%hhu)\n",
356                         header->version_major, header->version_minor,
357                         GREYBUS_VERSION_MAJOR, GREYBUS_VERSION_MINOR);
358                 return false;
359         }
360
361         /* OK, find all the descriptors */
362         desc = (struct greybus_descriptor *)(header + 1);
363         size -= sizeof(*header);
364         while (size) {
365                 int desc_size;
366
367                 desc_size = identify_descriptor(desc, size);
368                 if (desc_size <= 0) {
369                         if (!desc_size)
370                                 pr_err("zero-sized manifest descriptor\n");
371                         result = false;
372                         goto out;
373                 }
374                 desc = (struct greybus_descriptor *)((char *)desc + desc_size);
375                 size -= desc_size;
376         }
377
378         /* There must be a single module descriptor */
379         list_for_each_entry(descriptor, &manifest_descs, links) {
380                 if (descriptor->type == GREYBUS_TYPE_MODULE)
381                         if (!found++)
382                                 module_desc = descriptor;
383         }
384         if (found != 1) {
385                 pr_err("manifest must have 1 module descriptor (%u found)\n",
386                         found);
387                 result = false;
388                 goto out;
389         }
390
391         /* Parse the module manifest, starting with the module descriptor */
392         result = gb_manifest_parse_module(gmod, module_desc);
393
394         /*
395          * We really should have no remaining descriptors, but we
396          * don't know what newer format manifests might leave.
397          */
398         if (result && !list_empty(&manifest_descs))
399                 pr_info("excess descriptors in module manifest\n");
400 out:
401         release_manifest_descriptors();
402
403         return result;
404 }