aboutsummaryrefslogtreecommitdiffstats
path: root/scripts/dtc/srcpos.c
diff options
context:
space:
mode:
authorJohn Bonesio <bones@secretlab.ca>2010-11-17 18:28:20 -0500
committerGrant Likely <grant.likely@secretlab.ca>2011-01-03 18:02:49 -0500
commit658f29a51e9830e620bb9a1ce3534b318a38bfeb (patch)
treee6cc7cd9b9e17d97308619fd8516b77bcc038114 /scripts/dtc/srcpos.c
parentcd1e65044d4473cca9a01bae7b7938f065044a4b (diff)
of/flattree: Update dtc to current mainline.
Pull in recent changes from the main dtc repository. These changes primarily allow multiple device trees to be declared which are merged by dtc. This feature allows us to include a basic dts file and then provide more information for the specific system through the merging functionality. Changes pulled from git://git.jdl.com/software/dtc.git commit id: 37c0b6a0, "dtc: Add code to make diffing trees easier" Signed-off-by: John Bonesio <bones@secretlab.ca> Signed-off-by: Grant Likely <grant.likely@secretlab.ca>
Diffstat (limited to 'scripts/dtc/srcpos.c')
-rw-r--r--scripts/dtc/srcpos.c258
1 files changed, 195 insertions, 63 deletions
diff --git a/scripts/dtc/srcpos.c b/scripts/dtc/srcpos.c
index 9641b7628b4d..2dbc874288ca 100644
--- a/scripts/dtc/srcpos.c
+++ b/scripts/dtc/srcpos.c
@@ -17,100 +17,232 @@
17 * USA 17 * USA
18 */ 18 */
19 19
20#define _GNU_SOURCE
21
22#include <stdio.h>
23
20#include "dtc.h" 24#include "dtc.h"
21#include "srcpos.h" 25#include "srcpos.h"
22 26
23/*
24 * Like yylineno, this is the current open file pos.
25 */
26 27
27struct dtc_file *srcpos_file; 28static char *dirname(const char *path)
29{
30 const char *slash = strrchr(path, '/');
31
32 if (slash) {
33 int len = slash - path;
34 char *dir = xmalloc(len + 1);
35
36 memcpy(dir, path, len);
37 dir[len] = '\0';
38 return dir;
39 }
40 return NULL;
41}
42
43struct srcfile_state *current_srcfile; /* = NULL */
28 44
29static int dtc_open_one(struct dtc_file *file, 45/* Detect infinite include recursion. */
30 const char *search, 46#define MAX_SRCFILE_DEPTH (100)
31 const char *fname) 47static int srcfile_depth; /* = 0 */
48
49FILE *srcfile_relative_open(const char *fname, char **fullnamep)
32{ 50{
51 FILE *f;
33 char *fullname; 52 char *fullname;
34 53
35 if (search) { 54 if (streq(fname, "-")) {
36 fullname = xmalloc(strlen(search) + strlen(fname) + 2); 55 f = stdin;
37 56 fullname = xstrdup("<stdin>");
38 strcpy(fullname, search);
39 strcat(fullname, "/");
40 strcat(fullname, fname);
41 } else { 57 } else {
42 fullname = strdup(fname); 58 if (!current_srcfile || !current_srcfile->dir
59 || (fname[0] == '/'))
60 fullname = xstrdup(fname);
61 else
62 fullname = join_path(current_srcfile->dir, fname);
63
64 f = fopen(fullname, "r");
65 if (!f)
66 die("Couldn't open \"%s\": %s\n", fname,
67 strerror(errno));
43 } 68 }
44 69
45 file->file = fopen(fullname, "r"); 70 if (fullnamep)
46 if (!file->file) { 71 *fullnamep = fullname;
72 else
47 free(fullname); 73 free(fullname);
48 return 0;
49 }
50 74
51 file->name = fullname; 75 return f;
52 return 1;
53} 76}
54 77
78void srcfile_push(const char *fname)
79{
80 struct srcfile_state *srcfile;
81
82 if (srcfile_depth++ >= MAX_SRCFILE_DEPTH)
83 die("Includes nested too deeply");
84
85 srcfile = xmalloc(sizeof(*srcfile));
86
87 srcfile->f = srcfile_relative_open(fname, &srcfile->name);
88 srcfile->dir = dirname(srcfile->name);
89 srcfile->prev = current_srcfile;
90
91 srcfile->lineno = 1;
92 srcfile->colno = 1;
93
94 current_srcfile = srcfile;
95}
55 96
56struct dtc_file *dtc_open_file(const char *fname, 97int srcfile_pop(void)
57 const struct search_path *search)
58{ 98{
59 static const struct search_path default_search = { NULL, NULL, NULL }; 99 struct srcfile_state *srcfile = current_srcfile;
60 100
61 struct dtc_file *file; 101 assert(srcfile);
62 const char *slash;
63 102
64 file = xmalloc(sizeof(struct dtc_file)); 103 current_srcfile = srcfile->prev;
65 104
66 slash = strrchr(fname, '/'); 105 if (fclose(srcfile->f))
67 if (slash) { 106 die("Error closing \"%s\": %s\n", srcfile->name,
68 char *dir = xmalloc(slash - fname + 1); 107 strerror(errno));
69 108
70 memcpy(dir, fname, slash - fname); 109 /* FIXME: We allow the srcfile_state structure to leak,
71 dir[slash - fname] = 0; 110 * because it could still be referenced from a location
72 file->dir = dir; 111 * variable being carried through the parser somewhere. To
73 } else { 112 * fix this we could either allocate all the files from a
74 file->dir = NULL; 113 * table, or use a pool allocator. */
75 }
76 114
77 if (streq(fname, "-")) { 115 return current_srcfile ? 1 : 0;
78 file->name = "stdin"; 116}
79 file->file = stdin;
80 return file;
81 }
82 117
83 if (fname[0] == '/') { 118/*
84 file->file = fopen(fname, "r"); 119 * The empty source position.
85 if (!file->file) 120 */
86 goto fail;
87 121
88 file->name = strdup(fname); 122struct srcpos srcpos_empty = {
89 return file; 123 .first_line = 0,
90 } 124 .first_column = 0,
125 .last_line = 0,
126 .last_column = 0,
127 .file = NULL,
128};
91 129
92 if (!search) 130#define TAB_SIZE 8
93 search = &default_search;
94 131
95 while (search) { 132void srcpos_update(struct srcpos *pos, const char *text, int len)
96 if (dtc_open_one(file, search->dir, fname)) 133{
97 return file; 134 int i;
135
136 pos->file = current_srcfile;
137
138 pos->first_line = current_srcfile->lineno;
139 pos->first_column = current_srcfile->colno;
140
141 for (i = 0; i < len; i++)
142 if (text[i] == '\n') {
143 current_srcfile->lineno++;
144 current_srcfile->colno = 1;
145 } else if (text[i] == '\t') {
146 current_srcfile->colno =
147 ALIGN(current_srcfile->colno, TAB_SIZE);
148 } else {
149 current_srcfile->colno++;
150 }
151
152 pos->last_line = current_srcfile->lineno;
153 pos->last_column = current_srcfile->colno;
154}
98 155
99 if (errno != ENOENT) 156struct srcpos *
100 goto fail; 157srcpos_copy(struct srcpos *pos)
158{
159 struct srcpos *pos_new;
101 160
102 search = search->next; 161 pos_new = xmalloc(sizeof(struct srcpos));
103 } 162 memcpy(pos_new, pos, sizeof(struct srcpos));
163
164 return pos_new;
165}
166
167
168
169void
170srcpos_dump(struct srcpos *pos)
171{
172 printf("file : \"%s\"\n",
173 pos->file ? (char *) pos->file : "<no file>");
174 printf("first_line : %d\n", pos->first_line);
175 printf("first_column: %d\n", pos->first_column);
176 printf("last_line : %d\n", pos->last_line);
177 printf("last_column : %d\n", pos->last_column);
178 printf("file : %s\n", pos->file->name);
179}
104 180
105fail: 181
106 die("Couldn't open \"%s\": %s\n", fname, strerror(errno)); 182char *
183srcpos_string(struct srcpos *pos)
184{
185 const char *fname = "<no-file>";
186 char *pos_str;
187 int rc;
188
189 if (pos)
190 fname = pos->file->name;
191
192
193 if (pos->first_line != pos->last_line)
194 rc = asprintf(&pos_str, "%s:%d.%d-%d.%d", fname,
195 pos->first_line, pos->first_column,
196 pos->last_line, pos->last_column);
197 else if (pos->first_column != pos->last_column)
198 rc = asprintf(&pos_str, "%s:%d.%d-%d", fname,
199 pos->first_line, pos->first_column,
200 pos->last_column);
201 else
202 rc = asprintf(&pos_str, "%s:%d.%d", fname,
203 pos->first_line, pos->first_column);
204
205 if (rc == -1)
206 die("Couldn't allocate in srcpos string");
207
208 return pos_str;
209}
210
211void
212srcpos_verror(struct srcpos *pos, char const *fmt, va_list va)
213{
214 const char *srcstr;
215
216 srcstr = srcpos_string(pos);
217
218 fprintf(stdout, "Error: %s ", srcstr);
219 vfprintf(stdout, fmt, va);
220 fprintf(stdout, "\n");
107} 221}
108 222
109void dtc_close_file(struct dtc_file *file) 223void
224srcpos_error(struct srcpos *pos, char const *fmt, ...)
110{ 225{
111 if (fclose(file->file)) 226 va_list va;
112 die("Error closing \"%s\": %s\n", file->name, strerror(errno)); 227
228 va_start(va, fmt);
229 srcpos_verror(pos, fmt, va);
230 va_end(va);
231}
232
233
234void
235srcpos_warn(struct srcpos *pos, char const *fmt, ...)
236{
237 const char *srcstr;
238 va_list va;
239 va_start(va, fmt);
240
241 srcstr = srcpos_string(pos);
242
243 fprintf(stderr, "Warning: %s ", srcstr);
244 vfprintf(stderr, fmt, va);
245 fprintf(stderr, "\n");
113 246
114 free(file->dir); 247 va_end(va);
115 free(file);
116} 248}