]> Git Repo - J-u-boot.git/blob - lib/binman.c
usb: gadget: dwc3: Convert interrupt handling to usb_gadget_generic_ops
[J-u-boot.git] / lib / binman.c
1 // SPDX-License-Identifier: Intel
2 /*
3  * Access to binman information at runtime
4  *
5  * Copyright 2019 Google LLC
6  * Written by Simon Glass <[email protected]>
7  */
8
9 #include <binman.h>
10 #include <dm.h>
11 #include <log.h>
12 #include <malloc.h>
13 #include <mapmem.h>
14
15 /**
16  * struct binman_info - Information needed by the binman library
17  *
18  * @image: Node describing the image we are running from
19  * @rom_offset: Offset from an image_pos to the memory-mapped address, or
20  *      ROM_OFFSET_NONE if the ROM is not memory-mapped. Can be positive or
21  *      negative
22  */
23 struct binman_info {
24         ofnode image;
25         int rom_offset;
26 };
27
28 #define ROM_OFFSET_NONE         (-1)
29
30 static struct binman_info *binman;
31
32 /**
33  * find_image_node() - Find the top-level binman node
34  *
35  * Finds the binman node which can be used to load entries. The correct node
36  * depends on whether multiple-images is in use.
37  *
38  * @nodep: Returns the node found, on success
39  * Return: 0 if OK, , -EINVAL if there is no /binman node, -ECHILD if multiple
40  * images are being used but the first image is not available
41  */
42 static int find_image_node(ofnode *nodep)
43 {
44         ofnode node;
45
46         node = ofnode_path("/binman");
47         if (!ofnode_valid(node))
48                 return log_msg_ret("binman node", -EINVAL);
49         if (ofnode_read_bool(node, "multiple-images")) {
50                 node = ofnode_first_subnode(node);
51
52                 if (!ofnode_valid(node))
53                         return log_msg_ret("first image", -ECHILD);
54         }
55         *nodep = node;
56
57         return 0;
58 }
59
60 static int binman_entry_find_internal(ofnode node, const char *name,
61                                       struct binman_entry *entry)
62 {
63         int ret;
64
65         if (!ofnode_valid(node))
66                 node = binman->image;
67         node = ofnode_find_subnode(node, name);
68         if (!ofnode_valid(node))
69                 return log_msg_ret("node", -ENOENT);
70
71         ret = ofnode_read_u32(node, "image-pos", &entry->image_pos);
72         if (ret)
73                 return log_msg_ret("image-pos", ret);
74         ret = ofnode_read_u32(node, "size", &entry->size);
75         if (ret)
76                 return log_msg_ret("size", ret);
77
78         return 0;
79 }
80
81 int binman_entry_find(const char *name, struct binman_entry *entry)
82 {
83         return binman_entry_find_internal(binman->image, name, entry);
84 }
85
86 int binman_entry_map(ofnode parent, const char *name, void **bufp, int *sizep)
87 {
88         struct binman_entry entry;
89         int ret;
90
91         if (binman->rom_offset == ROM_OFFSET_NONE)
92                 return -EPERM;
93         ret = binman_entry_find_internal(parent, name, &entry);
94         if (ret)
95                 return log_msg_ret("entry", ret);
96         if (sizep)
97                 *sizep = entry.size;
98         *bufp = map_sysmem(entry.image_pos + binman->rom_offset, entry.size);
99
100         return 0;
101 }
102
103 ofnode binman_section_find_node(const char *name)
104 {
105         return ofnode_find_subnode(binman->image, name);
106 }
107
108 void binman_set_rom_offset(int rom_offset)
109 {
110         binman->rom_offset = rom_offset;
111 }
112
113 int binman_get_rom_offset(void)
114 {
115         return binman->rom_offset;
116 }
117
118 int binman_select_subnode(const char *name)
119 {
120         ofnode node;
121         int ret;
122
123         ret = find_image_node(&node);
124         if (ret)
125                 return log_msg_ret("main", -ENOENT);
126         node = ofnode_find_subnode(node, name);
127         if (!ofnode_valid(node))
128                 return log_msg_ret("node", -ENOENT);
129         binman->image = node;
130         log_info("binman: Selected image subnode '%s'\n",
131                  ofnode_get_name(binman->image));
132
133         return 0;
134 }
135
136 int binman_init(void)
137 {
138         int ret;
139
140         binman = malloc(sizeof(struct binman_info));
141         if (!binman)
142                 return log_msg_ret("space for binman", -ENOMEM);
143         ret = find_image_node(&binman->image);
144         if (ret)
145                 return log_msg_ret("node", -ENOENT);
146         binman_set_rom_offset(ROM_OFFSET_NONE);
147         log_debug("binman: Selected image node '%s'\n",
148                   ofnode_get_name(binman->image));
149
150         return 0;
151 }
This page took 0.035496 seconds and 4 git commands to generate.