source: trunk/mkstructinfo.awk @ 891

Last change on this file since 891 was 891, checked in by moo, 3 years ago

fix #275: struct parser for one line struct definition

  • Property svn:eol-style set to native
File size: 3.8 KB
RevLine 
[52]1#! /usr/bin/awk -f
[1]2# vim:ts=4:sw=4
3BEGIN {
4    brace = 0;
[187]5    incomment = 0;
[1]6    buffer_len = 0;
7}
[837]8function printstruct(structname) {
9    printf "define(`ELEMENTSOF_%s', `%s')\n", structname, ELEMENTSOF[structname];
10    printf "define(`COUNTOF_%s', `%s')\n", structname, COUNTOF[structname];
11    printf "define(`SIZEOF_%s', `(  %s  )')\n", structname, SIZEOF[structname];
12}
[891]13function countBrace(text,  len, i, char, braceCount) {
14    len = length(text);
15    braceCount = 0;
16    for (i = 1; i <= len; ++i) {
17        char = substr(text, i, 1);
18        if (char == "{") {
19            braceCount = braceCount + 1;
20        }
21        else if (char == "}") {
22            braceCount = braceCount - 1;
23        }
24    }
25    return braceCount;
26}
[187]27
28# multiline comment handling
29{
30    # removes one line comment
31    gsub(/\/\*(.+?)\*\//, " ");
32}
33/\*\// {
34    if (incomment) {
35        sub(/.*\*\//, "");
36        incomment = 0;
37    }
38}
39incomment {
40    next;
41}
42/\/\*/ {
43    sub(/\/\*.*/, "");
44    incomment = 1;
45    # fall through
46}
47
48# skip file/line mark here to be faster
[169]49/^#/ {
50    next;
51}
[187]52
[1]53/^}.*;/ {
54    if (instruct) {
55        sub(";", "");
[837]56        structname = instruct;
57        if (structname == 1 && $2) {
58            structname = $2;
[1]59        }
[837]60        if (structname in typedefs) {
61            structname = typedefs[structname];
[1]62        }
[42]63        sizeinfo = "";
[1]64        elms = "";
65        for (i = 0; i in buffer; i ++) {
[42]66            if (i) {
67                sizeinfo = sizeinfo " + ";
68            }
[837]69            sizeinfo = sizeinfo "sizeof(((" structname "*)NULL)->" buffer[i] ")";
[4]70
[42]71            if (i == 0) {
[719]72                elms = "\"" buffer[i] "\"";
[4]73            }
74            else {
[719]75                elms = elms "," "\"" buffer[i] "\"";
[4]76            }
[1]77        }
[837]78        ELEMENTSOF[structname] = elms;
79        COUNTOF[structname]    = i;
80        SIZEOF[structname]     = sizeinfo;
81        printstruct(structname);
[1]82        print "\n";
[23]83        for (i in buffer) {
84            delete buffer[i];
85        }
[1]86        buffer_len = 0;
87        instruct = 0;
88    }
89    next;
90}
91
[891]92/.[{}]/ {
93    brace += countBrace($0);
[1]94}
95
96{
97    if (brace == 1 && instruct) {
[187]98        gsub(/(^[\t ]+|[\t ]+$)/, ""); # trim whitespaces
[1]99        sub(/.*[{}]/, "");
[42]100        gsub(/\[[^\]]+\]/, ""); # ignore [...]
101        gsub(/:[0-9]+/, ""); # ignore struct bit
102        if (match($0, /^[^(]*\([ ]*\*([^)]+)\)/)) {
103            sub(/ +/, "")
104            sub(/^[^(]*\(\*/, "");
105            sub(/\).*/, "");
106            # function pointer
107            buffer[buffer_len] = $0;
[1]108            buffer_len ++;
109        }
110        else {
[187]111            # process normal variables
112
[42]113            # ignore any ()s
114            while (gsub(/(\([^)]*\))/, "")) {
[1]115            }
[42]116            if (match($0, /[()]/)) {
117                next;
118            }
[169]119            # unsigned int *a,  b; int c;
[42]120            gsub(/[*]/, " ");
[169]121            # unsigned int a,  b; int c;
[42]122            gsub(/ +/, " ");
[169]123            # unsigned int a, b; int c;
[42]124            gsub(/ *[,;]/, ";");
[169]125            # unsigned int a; b; int c;
[42]126            if (!match($0, /;/)) {
127                next;
128            }
[187]129            # print "=DEBUG=" $0 "==";
[42]130            split($0, chunks, ";");
[169]131            # [unsigned int a, b, c]
132
133            for (i = 1; i in chunks; i ++) {
[42]134                if (chunks[i] == "") {
135                    delete chunks[i];
136                    continue;
137                }
138                split(chunks[i], pieces, " ");
[169]139                # [unsigned, int, a]
140                # [b]
141                # [c]
[42]142
[169]143                last_piece = "";
144                for (j = 1; j in pieces; j ++) {
[42]145                    last_piece = pieces[j];
[169]146                    delete pieces[j];
[42]147                }
148                if (last_piece == "") {
[187]149                    # print "=ERROR=" chunks[i] "==";
150                    delete chunks[i];
151                    continue;
[42]152                }
[169]153                # a
154                # b
155                # c
156
[42]157                buffer[buffer_len] = last_piece;
[1]158                buffer_len ++;
[169]159                delete chunks[i]
[1]160            }
[169]161            last_piece = "";
[1]162        }
163        next;
164    }
165}
166
167/^typedef struct [^{]*;/ {
168    sub(";", "");
[837]169    typename=$3;
170    newtypename=$4;
171    typedefs[typename] = newtypename;
172    if (ELEMENTSOF[typename]) {
173        ELEMENTSOF[newtypename] = ELEMENTSOF[typename];
174        COUNTOF[newtypename]    = COUNTOF[typename];
175        sub(/.*/, SIZEOF[typename]);
176        gsub(typename, newtypename);
177        SIZEOF[newtypename]     = $0;
178        printstruct(newtypename);
179    }
[1]180    next;
181}
[187]182/^typedef struct .*\{[^}]*$/ {
[891]183    brace = countBrace($0);
184    if (brace > 0) {
185        instruct = 1;
186    }
187    else {
188        brace = 0;
189        instruct = 0;
190    }
191
192    for (i in buffer) {
193        delete buffer[i];
194    }
[1]195    next;
196}
197
[891]198/^struct .*\{.*/ {
199    brace = countBrace($0);
200    if (brace > 0) {
201        instruct = $2;
202    }
203    else {
204        brace = 0;
205        instruct = 0;
206    }
207
208    for (i in buffer) {
209        delete buffer[i];
210    }
[1]211    next;
212}
Note: See TracBrowser for help on using the repository browser.