OpenCores
URL https://opencores.org/ocsvn/open8_urisc/open8_urisc/trunk

Subversion Repositories open8_urisc

[/] [open8_urisc/] [trunk/] [gnu/] [binutils/] [bfd/] [cache.c] - Blame information for rev 62

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 14 khays
/* BFD library -- caching of file descriptors.
2
 
3
   Copyright 1990, 1991, 1992, 1993, 1994, 1996, 2000, 2001, 2002,
4
   2003, 2004, 2005, 2007, 2008, 2009 Free Software Foundation, Inc.
5
 
6
   Hacked by Steve Chamberlain of Cygnus Support (steve@cygnus.com).
7
 
8
   This file is part of BFD, the Binary File Descriptor library.
9
 
10
   This program is free software; you can redistribute it and/or modify
11
   it under the terms of the GNU General Public License as published by
12
   the Free Software Foundation; either version 3 of the License, or
13
   (at your option) any later version.
14
 
15
   This program is distributed in the hope that it will be useful,
16
   but WITHOUT ANY WARRANTY; without even the implied warranty of
17
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18
   GNU General Public License for more details.
19
 
20
   You should have received a copy of the GNU General Public License
21
   along with this program; if not, write to the Free Software
22
   Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
23
   MA 02110-1301, USA.  */
24
 
25
/*
26
SECTION
27
        File caching
28
 
29
        The file caching mechanism is embedded within BFD and allows
30
        the application to open as many BFDs as it wants without
31
        regard to the underlying operating system's file descriptor
32
        limit (often as low as 20 open files).  The module in
33
        <<cache.c>> maintains a least recently used list of
34
        <<BFD_CACHE_MAX_OPEN>> files, and exports the name
35
        <<bfd_cache_lookup>>, which runs around and makes sure that
36
        the required BFD is open. If not, then it chooses a file to
37
        close, closes it and opens the one wanted, returning its file
38
        handle.
39
 
40
SUBSECTION
41
        Caching functions
42
*/
43
 
44
#include "sysdep.h"
45
#include "bfd.h"
46
#include "libbfd.h"
47
#include "libiberty.h"
48
 
49
#ifdef HAVE_MMAP
50
#include <sys/mman.h>
51
#endif
52
 
53
/* In some cases we can optimize cache operation when reopening files.
54
   For instance, a flush is entirely unnecessary if the file is already
55
   closed, so a flush would use CACHE_NO_OPEN.  Similarly, a seek using
56
   SEEK_SET or SEEK_END need not first seek to the current position.
57
   For stat we ignore seek errors, just in case the file has changed
58
   while we weren't looking.  If it has, then it's possible that the
59
   file is shorter and we don't want a seek error to prevent us doing
60
   the stat.  */
61
enum cache_flag {
62
  CACHE_NORMAL = 0,
63
  CACHE_NO_OPEN = 1,
64
  CACHE_NO_SEEK = 2,
65
  CACHE_NO_SEEK_ERROR = 4
66
};
67
 
68
/* The maximum number of files which the cache will keep open at
69
   one time.  */
70
 
71
#define BFD_CACHE_MAX_OPEN 10
72
 
73
/* The number of BFD files we have open.  */
74
 
75
static int open_files;
76
 
77
/* Zero, or a pointer to the topmost BFD on the chain.  This is
78
   used by the <<bfd_cache_lookup>> macro in @file{libbfd.h} to
79
   determine when it can avoid a function call.  */
80
 
81
static bfd *bfd_last_cache = NULL;
82
 
83
/* Insert a BFD into the cache.  */
84
 
85
static void
86
insert (bfd *abfd)
87
{
88
  if (bfd_last_cache == NULL)
89
    {
90
      abfd->lru_next = abfd;
91
      abfd->lru_prev = abfd;
92
    }
93
  else
94
    {
95
      abfd->lru_next = bfd_last_cache;
96
      abfd->lru_prev = bfd_last_cache->lru_prev;
97
      abfd->lru_prev->lru_next = abfd;
98
      abfd->lru_next->lru_prev = abfd;
99
    }
100
  bfd_last_cache = abfd;
101
}
102
 
103
/* Remove a BFD from the cache.  */
104
 
105
static void
106
snip (bfd *abfd)
107
{
108
  abfd->lru_prev->lru_next = abfd->lru_next;
109
  abfd->lru_next->lru_prev = abfd->lru_prev;
110
  if (abfd == bfd_last_cache)
111
    {
112
      bfd_last_cache = abfd->lru_next;
113
      if (abfd == bfd_last_cache)
114
        bfd_last_cache = NULL;
115
    }
116
}
117
 
118
/* Close a BFD and remove it from the cache.  */
119
 
120
static bfd_boolean
121
bfd_cache_delete (bfd *abfd)
122
{
123
  bfd_boolean ret;
124
 
125
  if (fclose ((FILE *) abfd->iostream) == 0)
126
    ret = TRUE;
127
  else
128
    {
129
      ret = FALSE;
130
      bfd_set_error (bfd_error_system_call);
131
    }
132
 
133
  snip (abfd);
134
 
135
  abfd->iostream = NULL;
136
  --open_files;
137
 
138
  return ret;
139
}
140
 
141
/* We need to open a new file, and the cache is full.  Find the least
142
   recently used cacheable BFD and close it.  */
143
 
144
static bfd_boolean
145
close_one (void)
146
{
147
  register bfd *to_kill;
148
 
149
  if (bfd_last_cache == NULL)
150
    to_kill = NULL;
151
  else
152
    {
153
      for (to_kill = bfd_last_cache->lru_prev;
154
           ! to_kill->cacheable;
155
           to_kill = to_kill->lru_prev)
156
        {
157
          if (to_kill == bfd_last_cache)
158
            {
159
              to_kill = NULL;
160
              break;
161
            }
162
        }
163
    }
164
 
165
  if (to_kill == NULL)
166
    {
167
      /* There are no open cacheable BFD's.  */
168
      return TRUE;
169
    }
170
 
171
  to_kill->where = real_ftell ((FILE *) to_kill->iostream);
172
 
173
  return bfd_cache_delete (to_kill);
174
}
175
 
176
/* Check to see if the required BFD is the same as the last one
177
   looked up. If so, then it can use the stream in the BFD with
178
   impunity, since it can't have changed since the last lookup;
179
   otherwise, it has to perform the complicated lookup function.  */
180
 
181
#define bfd_cache_lookup(x, flag) \
182
  ((x) == bfd_last_cache                        \
183
   ? (FILE *) (bfd_last_cache->iostream)        \
184
   : bfd_cache_lookup_worker (x, flag))
185
 
186
/* Called when the macro <<bfd_cache_lookup>> fails to find a
187
   quick answer.  Find a file descriptor for @var{abfd}.  If
188
   necessary, it open it.  If there are already more than
189
   <<BFD_CACHE_MAX_OPEN>> files open, it tries to close one first, to
190
   avoid running out of file descriptors.  It will return NULL
191
   if it is unable to (re)open the @var{abfd}.  */
192
 
193
static FILE *
194
bfd_cache_lookup_worker (bfd *abfd, enum cache_flag flag)
195
{
196
  bfd *orig_bfd = abfd;
197
  if ((abfd->flags & BFD_IN_MEMORY) != 0)
198
    abort ();
199
 
200
  if (abfd->my_archive)
201
    abfd = abfd->my_archive;
202
 
203
  if (abfd->iostream != NULL)
204
    {
205
      /* Move the file to the start of the cache.  */
206
      if (abfd != bfd_last_cache)
207
        {
208
          snip (abfd);
209
          insert (abfd);
210
        }
211
      return (FILE *) abfd->iostream;
212
    }
213
 
214
  if (flag & CACHE_NO_OPEN)
215
    return NULL;
216
 
217
  if (bfd_open_file (abfd) == NULL)
218
    ;
219
  else if (!(flag & CACHE_NO_SEEK)
220
           && real_fseek ((FILE *) abfd->iostream, abfd->where, SEEK_SET) != 0
221
           && !(flag & CACHE_NO_SEEK_ERROR))
222
    bfd_set_error (bfd_error_system_call);
223
  else
224
    return (FILE *) abfd->iostream;
225
 
226
  (*_bfd_error_handler) (_("reopening %B: %s\n"),
227
                         orig_bfd, bfd_errmsg (bfd_get_error ()));
228
  return NULL;
229
}
230
 
231
static file_ptr
232
cache_btell (struct bfd *abfd)
233
{
234
  FILE *f = bfd_cache_lookup (abfd, CACHE_NO_OPEN);
235
  if (f == NULL)
236
    return abfd->where;
237
  return real_ftell (f);
238
}
239
 
240
static int
241
cache_bseek (struct bfd *abfd, file_ptr offset, int whence)
242
{
243
  FILE *f = bfd_cache_lookup (abfd, whence != SEEK_CUR ? CACHE_NO_SEEK : CACHE_NORMAL);
244
  if (f == NULL)
245
    return -1;
246
  return real_fseek (f, offset, whence);
247
}
248
 
249
/* Note that archive entries don't have streams; they share their parent's.
250
   This allows someone to play with the iostream behind BFD's back.
251
 
252
   Also, note that the origin pointer points to the beginning of a file's
253
   contents (0 for non-archive elements).  For archive entries this is the
254
   first octet in the file, NOT the beginning of the archive header.  */
255
 
256
static file_ptr
257
cache_bread_1 (struct bfd *abfd, void *buf, file_ptr nbytes)
258
{
259
  FILE *f;
260
  file_ptr nread;
261
  /* FIXME - this looks like an optimization, but it's really to cover
262
     up for a feature of some OSs (not solaris - sigh) that
263
     ld/pe-dll.c takes advantage of (apparently) when it creates BFDs
264
     internally and tries to link against them.  BFD seems to be smart
265
     enough to realize there are no symbol records in the "file" that
266
     doesn't exist but attempts to read them anyway.  On Solaris,
267
     attempting to read zero bytes from a NULL file results in a core
268
     dump, but on other platforms it just returns zero bytes read.
269
     This makes it to something reasonable. - DJ */
270
  if (nbytes == 0)
271
    return 0;
272
 
273
  f = bfd_cache_lookup (abfd, CACHE_NORMAL);
274
  if (f == NULL)
275
    return 0;
276
 
277
#if defined (__VAX) && defined (VMS)
278
  /* Apparently fread on Vax VMS does not keep the record length
279
     information.  */
280
  nread = read (fileno (f), buf, nbytes);
281
  /* Set bfd_error if we did not read as much data as we expected.  If
282
     the read failed due to an error set the bfd_error_system_call,
283
     else set bfd_error_file_truncated.  */
284
  if (nread == (file_ptr)-1)
285
    {
286
      bfd_set_error (bfd_error_system_call);
287
      return -1;
288
    }
289
#else
290
  nread = fread (buf, 1, nbytes, f);
291
  /* Set bfd_error if we did not read as much data as we expected.  If
292
     the read failed due to an error set the bfd_error_system_call,
293
     else set bfd_error_file_truncated.  */
294
  if (nread < nbytes && ferror (f))
295
    {
296
      bfd_set_error (bfd_error_system_call);
297
      return -1;
298
    }
299
#endif
300
  if (nread < nbytes)
301
    /* This may or may not be an error, but in case the calling code
302
       bails out because of it, set the right error code.  */
303
    bfd_set_error (bfd_error_file_truncated);
304
  return nread;
305
}
306
 
307
static file_ptr
308
cache_bread (struct bfd *abfd, void *buf, file_ptr nbytes)
309
{
310
  file_ptr nread = 0;
311
 
312
  /* Some filesystems are unable to handle reads that are too large
313
     (for instance, NetApp shares with oplocks turned off).  To avoid
314
     hitting this limitation, we read the buffer in chunks of 8MB max.  */
315
  while (nread < nbytes)
316
    {
317
      const file_ptr max_chunk_size = 0x800000;
318
      file_ptr chunk_size = nbytes - nread;
319
      file_ptr chunk_nread;
320
 
321
      if (chunk_size > max_chunk_size)
322
        chunk_size = max_chunk_size;
323
 
324
      chunk_nread = cache_bread_1 (abfd, (char *) buf + nread, chunk_size);
325
 
326
      /* Update the nread count.
327
 
328
         We just have to be careful of the case when cache_bread_1 returns
329
         a negative count:  If this is our first read, then set nread to
330
         that negative count in order to return that negative value to the
331
         caller.  Otherwise, don't add it to our total count, or we would
332
         end up returning a smaller number of bytes read than we actually
333
         did.  */
334
      if (nread == 0 || chunk_nread > 0)
335
        nread += chunk_nread;
336
 
337
      if (chunk_nread < chunk_size)
338
        break;
339
    }
340
 
341
  return nread;
342
}
343
 
344
static file_ptr
345
cache_bwrite (struct bfd *abfd, const void *where, file_ptr nbytes)
346
{
347
  file_ptr nwrite;
348
  FILE *f = bfd_cache_lookup (abfd, CACHE_NORMAL);
349
 
350
  if (f == NULL)
351
    return 0;
352
  nwrite = fwrite (where, 1, nbytes, f);
353
  if (nwrite < nbytes && ferror (f))
354
    {
355
      bfd_set_error (bfd_error_system_call);
356
      return -1;
357
    }
358
  return nwrite;
359
}
360
 
361
static int
362
cache_bclose (struct bfd *abfd)
363
{
364
  return bfd_cache_close (abfd);
365
}
366
 
367
static int
368
cache_bflush (struct bfd *abfd)
369
{
370
  int sts;
371
  FILE *f = bfd_cache_lookup (abfd, CACHE_NO_OPEN);
372
 
373
  if (f == NULL)
374
    return 0;
375
  sts = fflush (f);
376
  if (sts < 0)
377
    bfd_set_error (bfd_error_system_call);
378
  return sts;
379
}
380
 
381
static int
382
cache_bstat (struct bfd *abfd, struct stat *sb)
383
{
384
  int sts;
385
  FILE *f = bfd_cache_lookup (abfd, CACHE_NO_SEEK_ERROR);
386
 
387
  if (f == NULL)
388
    return -1;
389
  sts = fstat (fileno (f), sb);
390
  if (sts < 0)
391
    bfd_set_error (bfd_error_system_call);
392
  return sts;
393
}
394
 
395
static void *
396
cache_bmmap (struct bfd *abfd ATTRIBUTE_UNUSED,
397
             void *addr ATTRIBUTE_UNUSED,
398
             bfd_size_type len ATTRIBUTE_UNUSED,
399
             int prot ATTRIBUTE_UNUSED,
400
             int flags ATTRIBUTE_UNUSED,
401
             file_ptr offset ATTRIBUTE_UNUSED)
402
{
403
  void *ret = (void *) -1;
404
 
405
  if ((abfd->flags & BFD_IN_MEMORY) != 0)
406
    abort ();
407
#ifdef HAVE_MMAP
408
  else
409
    {
410
      FILE *f = bfd_cache_lookup (abfd, CACHE_NO_SEEK_ERROR);
411
      if (f == NULL)
412
        return ret;
413
 
414
      ret = mmap (addr, len, prot, flags, fileno (f), offset);
415
      if (ret == (void *) -1)
416
        bfd_set_error (bfd_error_system_call);
417
    }
418
#endif
419
 
420
  return ret;
421
}
422
 
423
static const struct bfd_iovec cache_iovec =
424
{
425
  &cache_bread, &cache_bwrite, &cache_btell, &cache_bseek,
426
  &cache_bclose, &cache_bflush, &cache_bstat, &cache_bmmap
427
};
428
 
429
/*
430
INTERNAL_FUNCTION
431
        bfd_cache_init
432
 
433
SYNOPSIS
434
        bfd_boolean bfd_cache_init (bfd *abfd);
435
 
436
DESCRIPTION
437
        Add a newly opened BFD to the cache.
438
*/
439
 
440
bfd_boolean
441
bfd_cache_init (bfd *abfd)
442
{
443
  BFD_ASSERT (abfd->iostream != NULL);
444
  if (open_files >= BFD_CACHE_MAX_OPEN)
445
    {
446
      if (! close_one ())
447
        return FALSE;
448
    }
449
  abfd->iovec = &cache_iovec;
450
  insert (abfd);
451
  ++open_files;
452
  return TRUE;
453
}
454
 
455
/*
456
INTERNAL_FUNCTION
457
        bfd_cache_close
458
 
459
SYNOPSIS
460
        bfd_boolean bfd_cache_close (bfd *abfd);
461
 
462
DESCRIPTION
463
        Remove the BFD @var{abfd} from the cache. If the attached file is open,
464
        then close it too.
465
 
466
RETURNS
467
        <<FALSE>> is returned if closing the file fails, <<TRUE>> is
468
        returned if all is well.
469
*/
470
 
471
bfd_boolean
472
bfd_cache_close (bfd *abfd)
473
{
474
  if (abfd->iovec != &cache_iovec)
475
    return TRUE;
476
 
477
  if (abfd->iostream == NULL)
478
    /* Previously closed.  */
479
    return TRUE;
480
 
481
  return bfd_cache_delete (abfd);
482
}
483
 
484
/*
485
FUNCTION
486
        bfd_cache_close_all
487
 
488
SYNOPSIS
489
        bfd_boolean bfd_cache_close_all (void);
490
 
491
DESCRIPTION
492
        Remove all BFDs from the cache. If the attached file is open,
493
        then close it too.
494
 
495
RETURNS
496
        <<FALSE>> is returned if closing one of the file fails, <<TRUE>> is
497
        returned if all is well.
498
*/
499
 
500
bfd_boolean
501
bfd_cache_close_all ()
502
{
503
  bfd_boolean ret = TRUE;
504
 
505
  while (bfd_last_cache != NULL)
506
    ret &= bfd_cache_close (bfd_last_cache);
507
 
508
  return ret;
509
}
510
 
511
/*
512
INTERNAL_FUNCTION
513
        bfd_open_file
514
 
515
SYNOPSIS
516
        FILE* bfd_open_file (bfd *abfd);
517
 
518
DESCRIPTION
519
        Call the OS to open a file for @var{abfd}.  Return the <<FILE *>>
520
        (possibly <<NULL>>) that results from this operation.  Set up the
521
        BFD so that future accesses know the file is open. If the <<FILE *>>
522
        returned is <<NULL>>, then it won't have been put in the
523
        cache, so it won't have to be removed from it.
524
*/
525
 
526
FILE *
527
bfd_open_file (bfd *abfd)
528
{
529
  abfd->cacheable = TRUE;       /* Allow it to be closed later.  */
530
 
531
  if (open_files >= BFD_CACHE_MAX_OPEN)
532
    {
533
      if (! close_one ())
534
        return NULL;
535
    }
536
 
537
  switch (abfd->direction)
538
    {
539
    case read_direction:
540
    case no_direction:
541
      abfd->iostream = (PTR) real_fopen (abfd->filename, FOPEN_RB);
542
      break;
543
    case both_direction:
544
    case write_direction:
545
      if (abfd->opened_once)
546
        {
547
          abfd->iostream = (PTR) real_fopen (abfd->filename, FOPEN_RUB);
548
          if (abfd->iostream == NULL)
549
            abfd->iostream = (PTR) real_fopen (abfd->filename, FOPEN_WUB);
550
        }
551
      else
552
        {
553
          /* Create the file.
554
 
555
             Some operating systems won't let us overwrite a running
556
             binary.  For them, we want to unlink the file first.
557
 
558
             However, gcc 2.95 will create temporary files using
559
             O_EXCL and tight permissions to prevent other users from
560
             substituting other .o files during the compilation.  gcc
561
             will then tell the assembler to use the newly created
562
             file as an output file.  If we unlink the file here, we
563
             open a brief window when another user could still
564
             substitute a file.
565
 
566
             So we unlink the output file if and only if it has
567
             non-zero size.  */
568
#ifndef __MSDOS__
569
          /* Don't do this for MSDOS: it doesn't care about overwriting
570
             a running binary, but if this file is already open by
571
             another BFD, we will be in deep trouble if we delete an
572
             open file.  In fact, objdump does just that if invoked with
573
             the --info option.  */
574
          struct stat s;
575
 
576
          if (stat (abfd->filename, &s) == 0 && s.st_size != 0)
577
            unlink_if_ordinary (abfd->filename);
578
#endif
579
          abfd->iostream = (PTR) real_fopen (abfd->filename, FOPEN_WUB);
580
          abfd->opened_once = TRUE;
581
        }
582
      break;
583
    }
584
 
585
  if (abfd->iostream == NULL)
586
    bfd_set_error (bfd_error_system_call);
587
  else
588
    {
589
      if (! bfd_cache_init (abfd))
590
        return NULL;
591
    }
592
 
593
  return (FILE *) abfd->iostream;
594
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.