00001 // -*- C++ -*- 00002 00003 //========================================================================== 00004 /** 00005 * @file Read_Buffer.h 00006 * 00007 * Read_Buffer.h,v 4.24 2006/01/16 19:39:07 jwillemsen Exp 00008 * 00009 * @author Douglas C. Schmidt <schmidt@cs.wustl.edu> 00010 * @author Seth Widoff 00011 */ 00012 //========================================================================== 00013 00014 #ifndef ACE_READ_BUFFER_H 00015 #define ACE_READ_BUFFER_H 00016 00017 #include /**/ "ace/pre.h" 00018 00019 #include "ace/ACE_export.h" 00020 00021 #if !defined (ACE_LACKS_PRAGMA_ONCE) 00022 # pragma once 00023 #endif /* ACE_LACKS_PRAGMA_ONCE */ 00024 00025 #include "ace/Global_Macros.h" 00026 #include "ace/os_include/os_stdio.h" 00027 00028 ACE_BEGIN_VERSIONED_NAMESPACE_DECL 00029 00030 class ACE_Allocator; 00031 00032 /** 00033 * @class ACE_Read_Buffer 00034 * 00035 * @brief Efficiently reads an artibrarily large buffer from an input 00036 * stream up to and including a termination character. Also 00037 * performs search/replace on single occurrences a character in 00038 * the buffer using the principles of Integrated Layer 00039 * Processing. 00040 * 00041 * This implementation is optimized to do a single dynamic 00042 * allocation and make only one copy of the data. It uses 00043 * recursion and the run-time stack to accomplish this 00044 * efficiently. 00045 */ 00046 class ACE_Export ACE_Read_Buffer 00047 { 00048 public: 00049 // = Initialization and termination methods. 00050 /// Read from a FILE *. 00051 ACE_Read_Buffer (FILE *fp, 00052 int close_on_delete = 0, 00053 ACE_Allocator * = 0); 00054 00055 #if !defined (ACE_HAS_WINCE) 00056 // Note that ACE_HANDLE = FILE under CE. 00057 00058 /// Read from an open HANDLE. 00059 ACE_Read_Buffer (ACE_HANDLE handle, 00060 int close_on_delete = 0, 00061 ACE_Allocator * = 0); 00062 #endif // ACE_HAS_WINCE 00063 00064 /// Closes the FILE *. 00065 ~ACE_Read_Buffer (void); 00066 00067 /** 00068 * Returns a pointer dynamically allocated with 00069 * <ACE_Allocator::malloc> to data from the input stream up to (and 00070 * including) the <terminator>. If <search> is >= 0 then all 00071 * occurrences of the <search> value are substituted with the 00072 * <replace> value. The last of the byte of data is a 0, so that 00073 * <strlen> can be used on it. The caller is responsible for 00074 * freeing the pointer returned from this method using the 00075 * <ACE_Allocator::free>. 00076 */ 00077 char *read (int terminator = EOF, 00078 int search = '\n', 00079 int replace = '\0'); 00080 00081 /// Returns the number of characters replaced during a <read>. 00082 size_t replaced (void) const; 00083 00084 /// Returns the size of the allocated buffer obtained during a 00085 /// @c read, not including the null terminator. 00086 size_t size (void) const; 00087 00088 /// Returns a pointer to its allocator. 00089 ACE_Allocator *alloc (void) const; 00090 00091 /// Dump the state of the object. 00092 void dump (void) const; 00093 00094 private: 00095 00096 // Disallow copying and assignment... 00097 void operator= (const ACE_Read_Buffer &); 00098 ACE_Read_Buffer (const ACE_Read_Buffer &); 00099 00100 private: 00101 /// Recursive helper method that does the work... 00102 char *rec_read (int term, int search, int replace); 00103 00104 /// The total number of characters in the buffer. 00105 size_t size_; 00106 00107 /// The total number of characters replaced. 00108 size_t occurrences_; 00109 00110 /// The stream we are reading from. 00111 FILE *stream_; 00112 00113 /// Keeps track of whether we should close the FILE in the 00114 /// destructor. 00115 int close_on_delete_; 00116 00117 /// Pointer to the allocator. 00118 ACE_Allocator *allocator_; 00119 00120 }; 00121 00122 ACE_END_VERSIONED_NAMESPACE_DECL 00123 00124 #if defined (__ACE_INLINE__) 00125 # include "ace/Read_Buffer.inl" 00126 #endif /* __ACE_INLINE__ */ 00127 00128 #include /**/ "ace/post.h" 00129 00130 #endif /* ACE_READ_BUFFER_H */