Skip to content

Commit eaec188

Browse files
committed
These generate a sourcefile in libdwarf (dwarf_lname_version.c)
that enables DWARF6 language version access. The generated source is not yet used. modified: src/bin/buildDW_LNAME/buildlname.c modified: src/bin/buildDW_LNAME/dwarf_lname_data.h modified: src/bin/checkDW_LANG/checklangname.c A new generated source which will replace a function in dwarf_query.c new file: src/lib/libdwarf/dwarf_lname_version.c
1 parent 26eba0c commit eaec188

File tree

4 files changed

+383
-98
lines changed

4 files changed

+383
-98
lines changed

src/bin/buildDW_LNAME/buildlname.c

Lines changed: 213 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,16 @@ All rights reserved.
44
55
This software file is hereby placed in the public domain.
66
For use by anyone for any purpose.
7+
8+
This code is not in libdwarf itself, it simply checks
9+
some information in dwarf.h and emits source file
10+
into the libdwarf source directory (which code
11+
gets compiled into libdwarf)
712
*/
813

14+
#include <config.h> /* for PACKAGE_VERSION */
915
#include <stdio.h> /* FILE fclose() fopen() fprintf() printf() */
10-
#include <stdlib.h> /* exit() getenv() */
16+
#include <stdlib.h> /* exit() getenv() qsort() */
1117
#include <string.h> /* strcmp() strcpy() strncmp() strlen() */
1218

1319
#include "dwarf.h"
@@ -18,10 +24,13 @@ static char *input_name = 0;
1824
static char pathbuf[BUFSIZ];
1925
static char buffer[BUFSIZ];
2026

27+
/* This for the output into dwarf_lname_version.c */
28+
static char outpath[BUFSIZ];
29+
2130
#define FALSE 0
2231
#define TRUE 1
2332

24-
static unsigned tcount = sizeof(lnsix) / sizeof(lnsix[0]);
33+
static unsigned int tcount = sizeof(lnsix) / sizeof(lnsix[0]);
2534
static unsigned int touchcounts[sizeof(lnsix) / sizeof(lnsix[0])];
2635

2736
static void
@@ -39,53 +48,53 @@ safe_strcpy(char *targ,char *src,unsigned targlen, unsigned srclen)
3948
static void
4049
validatetouchcount(char *curdefname,unsigned long v)
4150
{
42-
if (v >= tcount) {
43-
printf("ERROR: For LNAME id 0x%04lx there is "
44-
"No count available, limit is %x. Something wrong!\n",
45-
v,tcount);
46-
exit(EXIT_FAILURE);
47-
}
48-
if (touchcounts[v]) {
49-
printf("ERROR: For LNAME id 0x%04lx we are double "
50-
"counting at count 0x%x . Something wrong!\n",
51-
v,touchcounts[v]);
52-
exit(EXIT_FAILURE);
53-
}
54-
++touchcounts[v];
55-
if (lnsix[v].ln_value != v) {
56-
printf("ERROR: For LNAME id 0x%04lx not at the "
57-
"correct entry vs "
58-
" ln_value 0x%04x\n",
59-
v,lnsix[v].ln_value);
60-
exit(EXIT_FAILURE);
61-
}
62-
if (strcmp(curdefname,lnsix[v].ln_name)) {
63-
printf("ERROR: For LNAME id 0x%04lx we find the"
64-
" wrong string! name %s lnsixname %s \n",
65-
v, curdefname,lnsix[v].ln_name);
66-
exit(EXIT_FAILURE);
67-
}
51+
if (v >= tcount) {
52+
printf("ERROR: For LNAME id 0x%04lx there is "
53+
"No count available, limit is %x. Something wrong!\n",
54+
v,tcount);
55+
exit(EXIT_FAILURE);
56+
}
57+
if (touchcounts[v]) {
58+
printf("ERROR: For LNAME id 0x%04lx we are double "
59+
"counting at count 0x%x . Something wrong!\n",
60+
v,touchcounts[v]);
61+
exit(EXIT_FAILURE);
62+
}
63+
++touchcounts[v];
64+
if (lnsix[v].ln_value != v) {
65+
printf("ERROR: For LNAME id 0x%04lx not at the "
66+
"correct entry vs "
67+
" ln_value 0x%04x\n",
68+
v,lnsix[v].ln_value);
69+
exit(EXIT_FAILURE);
70+
}
71+
if (strcmp(curdefname,lnsix[v].ln_name)) {
72+
printf("ERROR: For LNAME id 0x%04lx we find the"
73+
" wrong string! name %s lnsixname %s \n",
74+
v, curdefname,lnsix[v].ln_name);
75+
exit(EXIT_FAILURE);
76+
}
6877
}
78+
6979
static void
70-
validatefinaltouchcount()
80+
validatefinaltouchcount(void)
7181
{
72-
unsigned long i = 1;
73-
/* Skip [0], it is not real, just a placeholder.
74-
0 is not a valid LNAME id */
75-
for( ; i < tcount; ++i) {
76-
if (touchcounts[i] != 1) {
77-
printf(" ERROR: an entry in the LNAMES list "
78-
" with DW_LNAME id 0x%04lx has touchcount"
79-
" %u which indicates an error comparing "
80-
" dwarf.h and the lnsix table here.\n",
81-
i,touchcounts[i]);
82+
unsigned long i = 1;
83+
/* Skip [0], it is not real, just a placeholder.
84+
0 is not a valid LNAME id */
85+
for ( ; i < tcount; ++i) {
86+
if (touchcounts[i] != 1) {
87+
printf(" ERROR: an entry in the LNAMES list "
88+
" with DW_LNAME id 0x%04lx has touchcount"
89+
" %u which indicates an error comparing "
90+
" dwarf.h and the lnsix table here.\n",
91+
i,touchcounts[i]);
8292
exit(EXIT_FAILURE);
83-
}
84-
}
93+
}
94+
}
8595
}
8696

87-
88-
/* Writes a complete new function
97+
/* Writes a complete new function
8998
int dwarf_language_version_data(..)
9099
in
91100
dwarf_lname_version.c
@@ -94,22 +103,173 @@ validatefinaltouchcount()
94103
that function.
95104
96105
We avoid anything in the new source file
97-
representing date or time as we want
106+
representing date or time as we want
98107
re-running this (if no changes in dwarf_lname_data.h)
99108
outputs bit-for-bit identical dwarf_lname_version.c .
100109
*/
101110

111+
#if 0 /* debug dump function */
112+
static void
113+
dump_table(void)
114+
{
115+
unsigned i = 0;
116+
117+
printf("lnsix table\n");
118+
for ( ; i < tcount; ++i) {
119+
struct lnsix_s * e = &lnsix[i];
120+
printf("[ %2u] %-16s, %s,0x%04u,%u,%s;\n",
121+
i,
122+
e->ln_informal,
123+
e->ln_name,
124+
e->ln_value,
125+
e->ln_low_bound,
126+
e->ln_vscheme);
127+
}
128+
fflush(stdout);
129+
}
130+
#endif /* debug dump function */
131+
132+
static int
133+
qcompar(const void *lh_i,const void *rh_i)
134+
{
135+
const struct lnsix_s *lh = 0;
136+
const struct lnsix_s *rh = 0;
137+
int res = 0;
138+
int res1 = 0;
139+
int res2 = 0;
140+
141+
lh = lh_i;
142+
rh = rh_i;
143+
res=strcmp(lh->ln_vscheme,rh->ln_vscheme);
144+
if (res) {
145+
return res;
146+
}
147+
res1= lh->ln_low_bound - rh->ln_low_bound;
148+
if (res1) {
149+
return res1;
150+
}
151+
res2=strcmp(lh->ln_name,rh->ln_name);
152+
return res2;
153+
}
154+
155+
static int
156+
same_switch_part(struct lnsix_s *lh,struct lnsix_s *rh) {
157+
if (strcmp(lh->ln_vscheme,rh->ln_vscheme)) {
158+
return FALSE;
159+
}
160+
if (lh->ln_low_bound != rh->ln_low_bound) {
161+
return FALSE;
162+
}
163+
return TRUE;
164+
}
165+
166+
static void
167+
print_return_values(FILE *outfile,struct lnsix_s *cur)
168+
{
169+
fprintf(outfile," *dw_default_lower_bound = %u;\n",
170+
cur->ln_low_bound);
171+
if (!strcmp(cur->ln_vscheme,"")) {
172+
fprintf(outfile," *dw_version_scheme = 0;\n");
173+
} else {
174+
fprintf(outfile," *dw_version_scheme = \"%s\";\n",
175+
cur->ln_vscheme);
176+
}
177+
fprintf(outfile,
178+
" return DW_DLV_OK;\n");
179+
}
102180

181+
static struct lnsix_s zerosix;
103182
static void
104-
write_new_query_function(char *path)
183+
print_table_entries(FILE *outfile)
105184
{
106-
107-
printf("Query function not complete. %s\n",path);
185+
/* The zero entry is not relevant, a placeholder. */
186+
unsigned i = 1;
187+
signed int sublist_start = -1;
188+
struct lnsix_s sublist_entry;
189+
struct lnsix_s *cur = 0;
190+
unsigned k = 0;
191+
192+
sublist_entry = zerosix;
193+
for ( ;i < tcount; ++i) {
194+
if (sublist_start < 0) {
195+
sublist_entry = lnsix[i];
196+
sublist_start = i;
197+
continue;
198+
}
199+
cur = &lnsix[i];
200+
if (same_switch_part(&sublist_entry,cur)) {
201+
continue;
202+
}
203+
/* now print switch cases */
204+
for (k = sublist_start; k < i; ++k) {
205+
fprintf(outfile," case %s:\n",
206+
lnsix[k].ln_name);
207+
}
208+
print_return_values(outfile,&sublist_entry);
209+
sublist_start = i;
210+
sublist_entry = lnsix[i];
211+
}
212+
for (k = sublist_start; k < i; ++k) {
213+
fprintf(outfile," case %s:\n",
214+
lnsix[k].ln_name);
215+
}
216+
print_return_values(outfile,&sublist_entry);
217+
fprintf(outfile," default:\n");
218+
fprintf(outfile," break;\n");
108219
}
220+
221+
static void
222+
write_new_query_function(FILE *outfile)
223+
{
224+
qsort(&lnsix[0],tcount,sizeof(struct lnsix_s), qcompar);
225+
fprintf(outfile,"/* Generated code, do not edit. */\n");
226+
fprintf(outfile,"/* Generated for source version %s */\n",
227+
PACKAGE_VERSION);
228+
fprintf(outfile, "\n");
229+
fprintf(outfile, "#include \"dwarf.h\"\n");
230+
fprintf(outfile, "#include \"libdwarf.h\"\n");
231+
232+
fprintf(outfile, "int\n");
233+
fprintf(outfile, "dwarf_language_version_data(\n");
234+
fprintf(outfile, " Dwarf_Unsigned dw_lname,\n");
235+
fprintf(outfile, " int *dw_default_lower_bound,\n");
236+
fprintf(outfile, " const char **dw_version_scheme)\n");
237+
238+
fprintf(outfile, "{\n");
239+
fprintf(outfile, " switch(dw_lname) {\n");
240+
print_table_entries(outfile);
241+
fprintf(outfile, " }\n");
242+
fprintf(outfile, " return DW_DLV_NO_ENTRY;\n");
243+
/* insert the details here. */
244+
fprintf(outfile, "}\n");
245+
}
246+
static void
247+
setup_new_query_function(char *path)
248+
{
249+
FILE *outfile = 0;
250+
size_t pathlen = strlen(path);
251+
char *outsuffix = "/src/lib/libdwarf/dwarf_lname_version.c";
252+
253+
safe_strcpy(outpath,path,(unsigned)sizeof(outpath),
254+
(unsigned)pathlen);
255+
safe_strcpy(outpath+pathlen,outsuffix,
256+
(unsigned)sizeof(outpath)-(unsigned)pathlen,
257+
(unsigned)strlen(outsuffix));
258+
outfile = fopen(outpath,"w");
259+
if (!outfile) {
260+
printf("ERROR building dwarf_lname_version.c FAILED."
261+
"Unable to open %s for output\n",outpath);
262+
exit(EXIT_FAILURE);
263+
}
264+
write_new_query_function(outfile);
265+
fclose(outfile);
266+
}
267+
109268
/* Issue error message and exit there is a mismatch,
110-
this should never fail.
269+
this should never fail.
111270
It verifies that dwarf.h DW_LNAME values match
112-
exactly the LNAME values in dwarf_lname_data.h*/
271+
exactly the LNAME values in dwarf_lname_data.h */
272+
113273
static void
114274
check_if_lname_complete(char *path)
115275
{
@@ -199,7 +359,7 @@ check_if_lname_complete(char *path)
199359
lastvalue = v;
200360
validatetouchcount(curdefname,v);
201361
continue;
202-
}
362+
}
203363
if (lastvalue == v) {
204364
printf("define line %u: DW_LNAME number value "
205365
" 0x%lx duplicated.\n",
@@ -254,7 +414,7 @@ int main(int argc, char**argv)
254414
exit(EXIT_FAILURE);
255415

256416
}
257-
safe_strcpy(pathbuf,path,sizeof(pathbuf),len);
417+
safe_strcpy(pathbuf,path,(unsigned)sizeof(pathbuf),(unsigned)len);
258418
{
259419
size_t remaining = sizeof(pathbuf) -len -1;
260420
size_t tailpathlen = strlen(tailpath);
@@ -266,12 +426,12 @@ int main(int argc, char**argv)
266426
}
267427
/* Notice tailpath has a leading / */
268428
safe_strcpy(pathbuf+len,(char *)tailpath,
269-
remaining,tailpathlen);
429+
(unsigned)remaining,(unsigned)tailpathlen);
270430
}
271431
input_name = pathbuf;
272432

273433
check_if_lname_complete(pathbuf);
274-
write_new_query_function(pathbuf);
434+
setup_new_query_function(path);
275435

276436
return 0;
277437
}

0 commit comments

Comments
 (0)