2008-05-15 08:39:12 +02:00
|
|
|
/*
|
|
|
|
* (C) Copyright David Gibson <dwg@au1.ibm.com>, IBM Corporation. 2005, 2008.
|
|
|
|
*
|
|
|
|
* This program is free software; you can redistribute it and/or
|
|
|
|
* modify it under the terms of the GNU General Public License as
|
|
|
|
* published by the Free Software Foundation; either version 2 of the
|
|
|
|
* License, or (at your option) any later version.
|
|
|
|
*
|
|
|
|
* This program is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
|
|
* General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU General Public License
|
|
|
|
* along with this program; if not, write to the Free Software
|
|
|
|
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
|
|
|
|
* USA
|
|
|
|
*/
|
|
|
|
|
2008-11-07 01:45:48 +01:00
|
|
|
%option noyywrap nounput noinput
|
2008-05-15 08:39:12 +02:00
|
|
|
|
|
|
|
%x INCLUDE
|
|
|
|
%x BYTESTRING
|
|
|
|
%x PROPNODENAME
|
|
|
|
|
|
|
|
PROPNODECHAR [a-zA-Z0-9,._+*#?@-]
|
|
|
|
PATHCHAR ({PROPNODECHAR}|[/])
|
|
|
|
LABEL [a-zA-Z_][a-zA-Z0-9_]*
|
dtc: Clean up lexing of include files
Currently we scan the /include/ directive as two tokens, the
"/include/" keyword itself, then the string giving the file name to
include. We use a special scanner state to keep the two linked
together, and use the scanner state stack to keep track of the
original state while we're parsing the two /include/ tokens.
This does mean that we need to enable the 'stack' option in flex,
which results in a not-easily-suppressed warning from the flex
boilerplate code. This is mildly irritating.
However, this two-token scanning of the /include/ directive also has
some extremely strange edge cases, because there are a variety of
tokens recognized in all scanner states, including INCLUDE. For
example the following strange dts file:
/include/ /dts-v1/;
/ {
/* ... */
};
Will be processed successfully with the /include/ being effectively
ignored: the '/dts-v1/' and ';' are recognized even in INCLUDE state,
then the ';' transitions us to PROPNODENAME state, throwing away
INCLUDE, and the previous state is never popped off the stack. Or
for another example this construct:
foo /include/ = "somefile.dts"
will be parsed as though it were:
foo = /include/ "somefile.dts"
Again, the '=' is scanned without leaving INCLUDE state, then the next
string triggers the include logic.
And finally, we use a different regexp for the string with the
included filename than the normal string regexpt, which is also
potentially weird.
This patch, therefore, cleans up the lexical handling of the /include/
directive. Instead of the INCLUDE state, we instead scan the whole
include directive, both keyword and filename as a single token. This
does mean a bit more complexity in extracting the filename out of
yytext, but I think it's worth it to avoid the strageness described
above. It also means it's no longer possible to put a comment between
the /include/ and the filename, but I'm really not very worried about
breaking files using such a strange construct.
2008-06-26 09:08:57 +02:00
|
|
|
STRING \"([^\\"]|\\.)*\"
|
|
|
|
WS [[:space:]]
|
|
|
|
COMMENT "/*"([^*]|\*+[^*/])*\*+"/"
|
|
|
|
LINECOMMENT "//".*\n
|
|
|
|
GAP ({WS}|{COMMENT}|{LINECOMMENT})*
|
2008-05-15 08:39:12 +02:00
|
|
|
|
|
|
|
%{
|
dtc: Address an assortment of portability problems
I've recently worked with a FreeBSD developer, getting dtc and libfdt
working on FreeBSD. This showed up a number of portability problems
in the dtc package which this patch addresses. Changes are as
follows:
- the parent_offset and supernode_atdepth_offset testcases
used the glibc extension functions strchrnul() and strndupa(). Those
are removed, using slightly longer coding with standard C functions
instead.
- some other testcases had a #define _GNU_SOURCE for no
particular reason. This is removed.
- run_tests.sh has bash specific constructs removed, and the
interpreter changed to /bin/sh. This apparently now runs fine on
FreeBSD's /bin/sh, and I've also tested it with both ash and dash.
- convert-dtsv0-lexer.l has some extra #includes added. These
must have been included indirectly with Linux and glibc, but aren't on
FreeBSD.
- the endian handling functions in libfdt_env.h, based on
endian.h and byteswap.h are replaced with some portable open-coded
versions. Unfortunately, these result in fairly crappy code when
compiled, but as far as I can determine there doesn't seem to be any
POSIX, SUS or de facto standard way of determining endianness at
compile time, nor standard names for byteswapping functions.
- some more endian handling, from testdata.h using the
problematic endian.h is simply removed, since it wasn't actually being
used anyway.
Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
2008-06-26 03:03:49 +02:00
|
|
|
#include <string.h>
|
|
|
|
#include <stdlib.h>
|
2008-05-15 08:39:12 +02:00
|
|
|
#include <stdarg.h>
|
dtc: Address an assortment of portability problems
I've recently worked with a FreeBSD developer, getting dtc and libfdt
working on FreeBSD. This showed up a number of portability problems
in the dtc package which this patch addresses. Changes are as
follows:
- the parent_offset and supernode_atdepth_offset testcases
used the glibc extension functions strchrnul() and strndupa(). Those
are removed, using slightly longer coding with standard C functions
instead.
- some other testcases had a #define _GNU_SOURCE for no
particular reason. This is removed.
- run_tests.sh has bash specific constructs removed, and the
interpreter changed to /bin/sh. This apparently now runs fine on
FreeBSD's /bin/sh, and I've also tested it with both ash and dash.
- convert-dtsv0-lexer.l has some extra #includes added. These
must have been included indirectly with Linux and glibc, but aren't on
FreeBSD.
- the endian handling functions in libfdt_env.h, based on
endian.h and byteswap.h are replaced with some portable open-coded
versions. Unfortunately, these result in fairly crappy code when
compiled, but as far as I can determine there doesn't seem to be any
POSIX, SUS or de facto standard way of determining endianness at
compile time, nor standard names for byteswapping functions.
- some more endian handling, from testdata.h using the
problematic endian.h is simply removed, since it wasn't actually being
used anyway.
Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
2008-06-26 03:03:49 +02:00
|
|
|
|
|
|
|
#include <errno.h>
|
2008-05-15 08:39:12 +02:00
|
|
|
#include <assert.h>
|
|
|
|
#include <fnmatch.h>
|
dtc: Address an assortment of portability problems
I've recently worked with a FreeBSD developer, getting dtc and libfdt
working on FreeBSD. This showed up a number of portability problems
in the dtc package which this patch addresses. Changes are as
follows:
- the parent_offset and supernode_atdepth_offset testcases
used the glibc extension functions strchrnul() and strndupa(). Those
are removed, using slightly longer coding with standard C functions
instead.
- some other testcases had a #define _GNU_SOURCE for no
particular reason. This is removed.
- run_tests.sh has bash specific constructs removed, and the
interpreter changed to /bin/sh. This apparently now runs fine on
FreeBSD's /bin/sh, and I've also tested it with both ash and dash.
- convert-dtsv0-lexer.l has some extra #includes added. These
must have been included indirectly with Linux and glibc, but aren't on
FreeBSD.
- the endian handling functions in libfdt_env.h, based on
endian.h and byteswap.h are replaced with some portable open-coded
versions. Unfortunately, these result in fairly crappy code when
compiled, but as far as I can determine there doesn't seem to be any
POSIX, SUS or de facto standard way of determining endianness at
compile time, nor standard names for byteswapping functions.
- some more endian handling, from testdata.h using the
problematic endian.h is simply removed, since it wasn't actually being
used anyway.
Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
2008-06-26 03:03:49 +02:00
|
|
|
|
2008-05-15 08:39:12 +02:00
|
|
|
#include "srcpos.h"
|
2008-10-03 18:12:33 +02:00
|
|
|
#include "util.h"
|
2008-05-15 08:39:12 +02:00
|
|
|
|
|
|
|
static int v1_tagged; /* = 0 */
|
|
|
|
static int cbase = 16;
|
|
|
|
static int saw_hyphen; /* = 0 */
|
|
|
|
static unsigned long long last_val;
|
|
|
|
static char *last_name; /* = NULL */
|
|
|
|
|
|
|
|
#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
|
|
|
|
|
|
|
|
const struct {
|
|
|
|
const char *pattern;
|
|
|
|
int obase, width;
|
|
|
|
} guess_table[] = {
|
|
|
|
{ "*-frequency", 10, 0 },
|
|
|
|
{ "num-*", 10, 0 },
|
|
|
|
{ "#*-cells", 10, 0 },
|
|
|
|
{ "*cache-line-size", 10, 0 },
|
|
|
|
{ "*cache-block-size", 10, 0 },
|
|
|
|
{ "*cache-size", 10, 0 },
|
|
|
|
{ "*cache-sets", 10, 0 },
|
|
|
|
{ "cell-index", 10, 0 },
|
|
|
|
{ "bank-width", 10, 0 },
|
|
|
|
{ "*-fifo-size", 10, 0 },
|
|
|
|
{ "*-frame-size", 10, 0 },
|
|
|
|
{ "*-channel", 10, 0 },
|
|
|
|
{ "current-speed", 10, 0 },
|
|
|
|
{ "phy-map", 16, 8 },
|
|
|
|
{ "dcr-reg", 16, 3 },
|
|
|
|
{ "reg", 16, 8 },
|
|
|
|
{ "ranges", 16, 8},
|
|
|
|
};
|
|
|
|
%}
|
|
|
|
|
|
|
|
%%
|
dtc: Clean up lexing of include files
Currently we scan the /include/ directive as two tokens, the
"/include/" keyword itself, then the string giving the file name to
include. We use a special scanner state to keep the two linked
together, and use the scanner state stack to keep track of the
original state while we're parsing the two /include/ tokens.
This does mean that we need to enable the 'stack' option in flex,
which results in a not-easily-suppressed warning from the flex
boilerplate code. This is mildly irritating.
However, this two-token scanning of the /include/ directive also has
some extremely strange edge cases, because there are a variety of
tokens recognized in all scanner states, including INCLUDE. For
example the following strange dts file:
/include/ /dts-v1/;
/ {
/* ... */
};
Will be processed successfully with the /include/ being effectively
ignored: the '/dts-v1/' and ';' are recognized even in INCLUDE state,
then the ';' transitions us to PROPNODENAME state, throwing away
INCLUDE, and the previous state is never popped off the stack. Or
for another example this construct:
foo /include/ = "somefile.dts"
will be parsed as though it were:
foo = /include/ "somefile.dts"
Again, the '=' is scanned without leaving INCLUDE state, then the next
string triggers the include logic.
And finally, we use a different regexp for the string with the
included filename than the normal string regexpt, which is also
potentially weird.
This patch, therefore, cleans up the lexical handling of the /include/
directive. Instead of the INCLUDE state, we instead scan the whole
include directive, both keyword and filename as a single token. This
does mean a bit more complexity in extracting the filename out of
yytext, but I think it's worth it to avoid the strageness described
above. It also means it's no longer possible to put a comment between
the /include/ and the filename, but I'm really not very worried about
breaking files using such a strange construct.
2008-06-26 09:08:57 +02:00
|
|
|
<*>"/include/"{GAP}{STRING} ECHO;
|
2008-05-15 08:39:12 +02:00
|
|
|
|
|
|
|
<*>\"([^\\"]|\\.)*\" ECHO;
|
|
|
|
|
|
|
|
<*>"/dts-v1/" {
|
|
|
|
die("Input dts file is already version 1\n");
|
|
|
|
}
|
|
|
|
|
|
|
|
<*>"/memreserve/" {
|
|
|
|
if (!v1_tagged) {
|
|
|
|
fprintf(yyout, "/dts-v1/;\n\n");
|
|
|
|
v1_tagged = 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
ECHO;
|
|
|
|
BEGIN(INITIAL);
|
|
|
|
}
|
|
|
|
|
|
|
|
<*>{LABEL}: ECHO;
|
|
|
|
|
|
|
|
<INITIAL>[bodh]# {
|
|
|
|
if (*yytext == 'b')
|
|
|
|
cbase = 2;
|
|
|
|
else if (*yytext == 'o')
|
|
|
|
cbase = 8;
|
|
|
|
else if (*yytext == 'd')
|
|
|
|
cbase = 10;
|
|
|
|
else
|
|
|
|
cbase = 16;
|
|
|
|
}
|
|
|
|
|
|
|
|
<INITIAL>[0-9a-fA-F]+ {
|
|
|
|
unsigned long long val;
|
|
|
|
int obase = 16, width = 0;
|
|
|
|
int i;
|
|
|
|
|
|
|
|
val = strtoull(yytext, NULL, cbase);
|
|
|
|
|
|
|
|
if (saw_hyphen)
|
|
|
|
val = val - last_val + 1;
|
|
|
|
|
|
|
|
if (last_name) {
|
|
|
|
for (i = 0; i < ARRAY_SIZE(guess_table); i++)
|
|
|
|
if (fnmatch(guess_table[i].pattern,
|
|
|
|
last_name, 0) == 0) {
|
|
|
|
obase = guess_table[i].obase;
|
|
|
|
width = guess_table[i].width;
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
obase = 16;
|
|
|
|
width = 16;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (cbase != 16)
|
|
|
|
obase = cbase;
|
|
|
|
|
|
|
|
switch (obase) {
|
|
|
|
case 2:
|
|
|
|
case 16:
|
|
|
|
fprintf(yyout, "0x%0*llx", width, val);
|
|
|
|
break;
|
|
|
|
case 8:
|
|
|
|
fprintf(yyout, "0%0*llo", width, val);
|
|
|
|
break;
|
|
|
|
case 10:
|
|
|
|
fprintf(yyout, "%*llu", width, val);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
cbase = 16;
|
|
|
|
last_val = val;
|
|
|
|
saw_hyphen = 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
\&{LABEL} ECHO;
|
|
|
|
|
|
|
|
"&{/"{PATHCHAR}+\} ECHO;
|
|
|
|
|
|
|
|
<INITIAL>"&/"{PATHCHAR}+ fprintf(yyout, "&{/%s}", yytext + 2);
|
|
|
|
|
|
|
|
<BYTESTRING>[0-9a-fA-F]{2} ECHO;
|
|
|
|
|
|
|
|
<BYTESTRING>"]" {
|
|
|
|
ECHO;
|
|
|
|
BEGIN(INITIAL);
|
|
|
|
}
|
|
|
|
|
|
|
|
<PROPNODENAME>{PROPNODECHAR}+ {
|
|
|
|
ECHO;
|
2008-10-03 18:12:33 +02:00
|
|
|
last_name = xstrdup(yytext);
|
2008-05-15 08:39:12 +02:00
|
|
|
BEGIN(INITIAL);
|
|
|
|
}
|
|
|
|
|
dtc: Clean up lexing of include files
Currently we scan the /include/ directive as two tokens, the
"/include/" keyword itself, then the string giving the file name to
include. We use a special scanner state to keep the two linked
together, and use the scanner state stack to keep track of the
original state while we're parsing the two /include/ tokens.
This does mean that we need to enable the 'stack' option in flex,
which results in a not-easily-suppressed warning from the flex
boilerplate code. This is mildly irritating.
However, this two-token scanning of the /include/ directive also has
some extremely strange edge cases, because there are a variety of
tokens recognized in all scanner states, including INCLUDE. For
example the following strange dts file:
/include/ /dts-v1/;
/ {
/* ... */
};
Will be processed successfully with the /include/ being effectively
ignored: the '/dts-v1/' and ';' are recognized even in INCLUDE state,
then the ';' transitions us to PROPNODENAME state, throwing away
INCLUDE, and the previous state is never popped off the stack. Or
for another example this construct:
foo /include/ = "somefile.dts"
will be parsed as though it were:
foo = /include/ "somefile.dts"
Again, the '=' is scanned without leaving INCLUDE state, then the next
string triggers the include logic.
And finally, we use a different regexp for the string with the
included filename than the normal string regexpt, which is also
potentially weird.
This patch, therefore, cleans up the lexical handling of the /include/
directive. Instead of the INCLUDE state, we instead scan the whole
include directive, both keyword and filename as a single token. This
does mean a bit more complexity in extracting the filename out of
yytext, but I think it's worth it to avoid the strageness described
above. It also means it's no longer possible to put a comment between
the /include/ and the filename, but I'm really not very worried about
breaking files using such a strange construct.
2008-06-26 09:08:57 +02:00
|
|
|
<*>{GAP} ECHO;
|
2008-05-15 08:39:12 +02:00
|
|
|
|
|
|
|
<*>- { /* Hack to convert old style memreserves */
|
|
|
|
saw_hyphen = 1;
|
|
|
|
fprintf(yyout, " ");
|
|
|
|
}
|
|
|
|
|
|
|
|
<*>. {
|
|
|
|
if (!v1_tagged) {
|
|
|
|
fprintf(yyout, "/dts-v1/;\n\n");
|
|
|
|
v1_tagged = 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
ECHO;
|
|
|
|
if (yytext[0] == '[') {
|
|
|
|
BEGIN(BYTESTRING);
|
|
|
|
}
|
|
|
|
if ((yytext[0] == '{')
|
|
|
|
|| (yytext[0] == ';')) {
|
|
|
|
BEGIN(PROPNODENAME);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
%%
|
|
|
|
static void usage(void)
|
|
|
|
{
|
|
|
|
fprintf(stderr, "convert-dtsv0 <v0 dts file>...\n");
|
|
|
|
exit(3);
|
|
|
|
}
|
|
|
|
|
|
|
|
static void convert_file(const char *fname)
|
|
|
|
{
|
|
|
|
const char suffix[] = "v1";
|
|
|
|
int len = strlen(fname);
|
|
|
|
char *newname;
|
|
|
|
|
|
|
|
newname = xmalloc(len + sizeof(suffix));
|
|
|
|
memcpy(newname, fname, len);
|
|
|
|
memcpy(newname + len, suffix, sizeof(suffix));
|
|
|
|
|
|
|
|
srcpos_file = dtc_open_file(fname, NULL);
|
|
|
|
yyin = srcpos_file->file;
|
|
|
|
|
|
|
|
yyout = fopen(newname, "w");
|
|
|
|
if (!yyout)
|
|
|
|
die("Couldn't open output file %s: %s\n",
|
|
|
|
newname, strerror(errno));
|
|
|
|
|
|
|
|
while(yylex())
|
|
|
|
;
|
|
|
|
}
|
|
|
|
|
|
|
|
int main(int argc, char *argv[])
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
|
|
|
if (argc < 2)
|
|
|
|
usage();
|
|
|
|
|
|
|
|
for (i = 1; i < argc; i++) {
|
|
|
|
fprintf(stderr, "Converting %s from dts v0 to dts v1\n", argv[i]);
|
|
|
|
convert_file(argv[i]);
|
|
|
|
}
|
|
|
|
|
|
|
|
exit(0);
|
|
|
|
}
|