1 /* ----------------------------------------------------------------------- *
3 * Copyright 1996-2014 The NASM Authors - All Rights Reserved
4 * See the file AUTHORS included with the NASM distribution for
5 * the specific copyright holders.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following
11 * * Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * * Redistributions in binary form must reproduce the above
14 * copyright notice, this list of conditions and the following
15 * disclaimer in the documentation and/or other materials provided
16 * with the distribution.
18 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
19 * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
20 * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
21 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
22 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
23 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
25 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
26 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
28 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
29 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
30 * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 * ----------------------------------------------------------------------- */
35 * rdlib.c - routines for manipulating RDOFF libraries (.rdl)
48 /* See Texinfo documentation about new RDOFF libraries format */
52 char *rdl_errors
[5] = {
53 "no error", "could not open file", "invalid file structure",
54 "file contains modules of an unsupported RDOFF version",
58 int rdl_verify(const char *filename
)
64 static char lastverified
[256];
65 static int lastresult
= -1;
67 if (lastresult
!= -1 && !strcmp(filename
, lastverified
))
70 fp
= fopen(filename
, "rb");
71 strcpy(lastverified
, filename
);
74 return (rdl_error
= lastresult
= 1);
79 while (fread(buf
+ i
, 1, 1, fp
) == 1 && i
< 257 && buf
[i
])
86 * A special module, eg a signature block or a directory.
87 * Format of such a module is defined to be:
88 * six char type identifier
89 * int32_t count bytes content
91 * so we can handle it uniformaly with RDOFF2 modules.
93 nasm_read(buf
, 6, fp
);
95 /* Currently, nothing useful to do with signature block.. */
97 nasm_read(buf
, 6, fp
);
99 if (strncmp(buf
, "RDOFF", 5)) {
101 return rdl_error
= lastresult
= 2;
102 } else if (buf
[5] != '2') {
104 return rdl_error
= lastresult
= 3;
107 nasm_read(&length
, 4, fp
);
108 fseek(fp
, length
, SEEK_CUR
); /* skip over the module */
111 return lastresult
= 0; /* library in correct format */
114 int rdl_open(struct librarynode
*lib
, const char *name
)
116 int i
= rdl_verify(name
);
121 lib
->name
= nasm_strdup(name
);
127 int rdl_searchlib(struct librarynode
*lib
, const char *label
, rdffile
* f
)
139 lib
->fp
= fopen(lib
->name
, "rb");
148 while (!feof(lib
->fp
)) {
150 * read the module name from the file, and prepend
151 * the library name and '.' to it.
153 strcpy(buf
, lib
->name
);
155 i
= strlen(lib
->name
);
158 while (fread(buf
+ i
, 1, 1, lib
->fp
) == 1 && i
< 512 && buf
[i
])
165 if (!strcmp(buf
+ t
, ".dir")) { /* skip over directory */
166 nasm_read(&l
, 4, lib
->fp
);
167 fseek(lib
->fp
, l
, SEEK_CUR
);
171 * open the RDOFF module
173 if (rdfopenhere(f
, lib
->fp
, &lib
->referenced
, buf
)) {
174 rdl_error
= 16 * rdf_errno
;
178 * read in the header, and scan for exported symbols
180 hdr
= nasm_malloc(f
->header_len
);
181 rdfloadseg(f
, RDOFF_HEADER
, hdr
);
183 while ((r
= rdfgetheaderrec(f
))) {
184 if (r
->type
!= 3) /* not an export */
187 if (!strcmp(r
->e
.label
, label
)) { /* match! */
188 nasm_free(hdr
); /* reset to 'just open' */
189 f
->header_loc
= NULL
; /* state... */
195 /* find start of next module... */
198 fseek(lib
->fp
, i
, SEEK_SET
);
202 * close the file if nobody else is using it
205 if (!lib
->referenced
) {
212 int rdl_openmodule(struct librarynode
*lib
, int moduleno
, rdffile
* f
)
221 lib
->fp
= fopen(lib
->name
, "rb");
224 return (rdl_error
= 1);
230 while (!feof(lib
->fp
)) {
231 strcpy(buf
, lib
->name
);
235 while (fread(buf
+ i
, 1, 1, lib
->fp
) == 1 && i
< 512 && buf
[i
])
241 if (buf
[t
] != '.') /* special module - not counted in the numbering */
242 cmod
++; /* of RDOFF modules - must be referred to by name */
244 if (cmod
== moduleno
) {
246 rdfopenhere(f
, lib
->fp
, &lib
->referenced
, buf
);
248 if (!lib
->referenced
) {
255 nasm_read(buf
, 6, lib
->fp
);
259 } else if (strncmp(buf
, "RDOFF", 5)) {
260 if (!--lib
->referenced
) {
264 return rdl_error
= 2;
265 } else if (buf
[5] != '2') {
266 if (!--lib
->referenced
) {
270 return rdl_error
= 3;
273 nasm_read(&length
, 4, lib
->fp
);
274 fseek(lib
->fp
, length
, SEEK_CUR
); /* skip over the module */
276 if (!--lib
->referenced
) {
280 return rdl_error
= 4; /* module not found */
283 void rdl_perror(const char *apname
, const char *filename
)
286 rdfperror(apname
, filename
);
288 fprintf(stderr
, "%s:%s:%s\n", apname
, filename
,
289 rdl_errors
[rdl_error
]);