(root)/
gcc-13.2.0/
gcc/
rust/
metadata/
rust-imports.h
       1  // Copyright 2009 The Go Authors. All rights reserved.
       2  // Use of this source code is governed by a BSD-style
       3  // license that can be found in the LICENSE file.
       4  
       5  #ifndef RUST_IMPORTS_H
       6  #define RUST_IMPORTS_H
       7  
       8  #include "rust-system.h"
       9  #include "rust-location.h"
      10  
      11  namespace Rust {
      12  
      13  extern void
      14  add_search_path (const std::string &path);
      15  
      16  class Import
      17  {
      18  public:
      19    // The Stream class is an interface used to read the data.  The
      20    // caller should instantiate a child of this class.
      21    class Stream
      22    {
      23    public:
      24      Stream ();
      25      virtual ~Stream ();
      26  
      27      // Set the position, for error messages.
      28      void set_pos (int pos) { this->pos_ = pos; }
      29  
      30      // Return whether we have seen an error.
      31      bool saw_error () const { return this->saw_error_; }
      32  
      33      // Record that we've seen an error.
      34      void set_saw_error () { this->saw_error_ = true; }
      35  
      36      // Return the next character (a value from 0 to 0xff) without
      37      // advancing.  Returns -1 at end of stream.
      38      int peek_char ();
      39  
      40      // Look for LENGTH characters, setting *BYTES to point to them.
      41      // Returns false if the bytes are not available.  Does not
      42      // advance.
      43      bool peek (size_t length, const char **bytes)
      44      {
      45        return this->do_peek (length, bytes);
      46      }
      47  
      48      // Return the next character (a value from 0 to 0xff) and advance
      49      // the read position by 1.  Returns -1 at end of stream.
      50      int get_char ()
      51      {
      52        int c = this->peek_char ();
      53        this->advance (1);
      54        return c;
      55      }
      56  
      57      // Return true if at the end of the stream.
      58      bool at_eof () { return this->peek_char () == -1; }
      59  
      60      // Return true if the next bytes match STR.
      61      bool match_c_string (const char *str)
      62      {
      63        return this->match_bytes (str, strlen (str));
      64      }
      65  
      66      // Return true if the next LENGTH bytes match BYTES.
      67      bool match_bytes (const char *bytes, size_t length);
      68  
      69      // Give an error if the next bytes do not match STR.  Advance the
      70      // read position by the length of STR.
      71      void require_c_string (Location location, const char *str)
      72      {
      73        this->require_bytes (location, str, strlen (str));
      74      }
      75  
      76      // Given an error if the next LENGTH bytes do not match BYTES.
      77      // Advance the read position by LENGTH.
      78      void require_bytes (Location, const char *bytes, size_t length);
      79  
      80      // Advance the read position by SKIP bytes.
      81      void advance (size_t skip)
      82      {
      83        this->do_advance (skip);
      84        this->pos_ += skip;
      85      }
      86  
      87      // Return the current read position.  This returns int because it
      88      // is more convenient in error reporting.  FIXME.
      89      int pos () { return static_cast<int> (this->pos_); }
      90  
      91      // This function should set *BYTES to point to a buffer holding
      92      // the LENGTH bytes at the current read position.  It should
      93      // return false if the bytes are not available.  This should not
      94      // change the current read position.
      95      virtual bool do_peek (size_t length, const char **bytes) = 0;
      96  
      97      // This function should advance the current read position LENGTH
      98      // bytes.
      99      virtual void do_advance (size_t skip) = 0;
     100  
     101    private:
     102      // The current read position.
     103      size_t pos_;
     104      // True if we've seen an error reading from this stream.
     105      bool saw_error_;
     106    };
     107  
     108    // Find import data.  This searches the file system for FILENAME and
     109    // returns a pointer to a Stream object to read the data that it
     110    // exports.  LOCATION is the location of the import statement.
     111    // RELATIVE_IMPORT_PATH is used as a prefix for a relative import.
     112    static Stream *open_package (const std::string &filename, Location location,
     113  			       const std::string &relative_import_path);
     114  
     115    // Constructor.
     116    Import (Stream *, Location);
     117  
     118    // The location of the import statement.
     119    Location location () const { return this->location_; }
     120  
     121    // Return the next character.
     122    int peek_char () { return this->stream_->peek_char (); }
     123  
     124    // Return the next character and advance.
     125    int get_char () { return this->stream_->get_char (); }
     126  
     127    // Read LENGTH characters into *OUT and advance past them.  On
     128    // EOF reports an error and sets *OUT to an empty string.
     129    void read (size_t length, std::string *out);
     130  
     131    // Return true at the end of the stream.
     132    bool at_eof () { return this->stream_->at_eof (); }
     133  
     134    // Return whether the next bytes match STR.
     135    bool match_c_string (const char *str)
     136    {
     137      return this->stream_->match_c_string (str);
     138    }
     139  
     140    // Require that the next bytes match STR.
     141    void require_c_string (const char *str)
     142    {
     143      this->stream_->require_c_string (this->location_, str);
     144    }
     145  
     146    // Advance the stream SKIP bytes.
     147    void advance (size_t skip) { this->stream_->advance (skip); }
     148  
     149    // Stream position, for error reporting.
     150    int pos () { return this->stream_->pos (); }
     151  
     152    // Clear the stream when it is no longer accessible.
     153    void clear_stream () { this->stream_ = NULL; }
     154  
     155  private:
     156    static Stream *try_package_in_directory (const std::string &, Location);
     157  
     158    static int try_suffixes (std::string *);
     159  
     160    static Stream *find_export_data (const std::string &filename, int fd,
     161  				   Location);
     162  
     163    static Stream *find_object_export_data (const std::string &filename, int fd,
     164  					  off_t offset, Location);
     165  
     166    static bool is_archive_magic (const char *);
     167  
     168    static Stream *find_archive_export_data (const std::string &filename, int fd,
     169  					   Location);
     170  
     171    // The stream from which to read import data.
     172    Stream *stream_;
     173    // The location of the import statement we are processing.
     174    Location location_;
     175  };
     176  
     177  // Read import data from a string.
     178  
     179  class Stream_from_string : public Import::Stream
     180  {
     181  public:
     182    Stream_from_string (const std::string &str) : str_ (str), pos_ (0) {}
     183  
     184    bool do_peek (size_t length, const char **bytes)
     185    {
     186      if (this->pos_ + length > this->str_.length ())
     187        return false;
     188      *bytes = this->str_.data () + this->pos_;
     189      return true;
     190    }
     191  
     192    void do_advance (size_t len) { this->pos_ += len; }
     193  
     194  private:
     195    // The string of data we are reading.
     196    std::string str_;
     197    // The current position within the string.
     198    size_t pos_;
     199  };
     200  
     201  // Read import data from a buffer allocated using malloc.
     202  
     203  class Stream_from_buffer : public Import::Stream
     204  {
     205  public:
     206    Stream_from_buffer (char *buf, size_t length)
     207      : buf_ (buf), length_ (length), pos_ (0)
     208    {}
     209  
     210    ~Stream_from_buffer () { free (this->buf_); }
     211  
     212    bool do_peek (size_t length, const char **bytes)
     213    {
     214      if (this->pos_ + length > this->length_)
     215        return false;
     216      *bytes = this->buf_ + this->pos_;
     217      return true;
     218    }
     219  
     220    void do_advance (size_t len) { this->pos_ += len; }
     221  
     222  private:
     223    // The data we are reading.
     224    char *buf_;
     225    // The length of the buffer.
     226    size_t length_;
     227    // The current position within the buffer.
     228    size_t pos_;
     229  };
     230  
     231  // Read import data from an open file descriptor.
     232  
     233  class Stream_from_file : public Import::Stream
     234  {
     235  public:
     236    Stream_from_file (int fd);
     237  
     238    ~Stream_from_file ();
     239  
     240    bool do_peek (size_t, const char **);
     241  
     242    void do_advance (size_t);
     243  
     244  private:
     245    // No copying.
     246    Stream_from_file (const Stream_from_file &);
     247    Stream_from_file &operator= (const Stream_from_file &);
     248  
     249    // The file descriptor.
     250    int fd_;
     251    // Data read from the file.
     252    std::string data_;
     253  };
     254  
     255  } // namespace Rust
     256  
     257  #endif // RUST_IMPORTS_H