build/stlport/src/details/fstream_unistd.cpp

changeset 0
6474c204b198
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/build/stlport/src/details/fstream_unistd.cpp	Wed Dec 31 06:09:35 2014 +0100
     1.3 @@ -0,0 +1,347 @@
     1.4 +/*
     1.5 + * Copyright (c) 1999
     1.6 + * Silicon Graphics Computer Systems, Inc.
     1.7 + *
     1.8 + * Copyright (c) 1999
     1.9 + * Boris Fomitchev
    1.10 + *
    1.11 + * This material is provided "as is", with absolutely no warranty expressed
    1.12 + * or implied. Any use is at your own risk.
    1.13 + *
    1.14 + * Permission to use or copy this software for any purpose is hereby granted
    1.15 + * without fee, provided the above notices are retained on all copies.
    1.16 + * Permission to modify the code and to distribute modified code is granted,
    1.17 + * provided the above notices are retained, and a notice that the code was
    1.18 + * modified is included with the above copyright notice.
    1.19 + *
    1.20 + */
    1.21 +
    1.22 +#if defined  (__SUNPPRO_CC)  && !defined (_STLP_NO_NEW_C_HEADERS)
    1.23 +#  include <time.h>
    1.24 +// For sunpro, it chokes if time.h is included through stat.h
    1.25 +#endif
    1.26 +
    1.27 +#include <fstream>
    1.28 +
    1.29 +#ifdef __CYGWIN__
    1.30 +#  define __int64 long long
    1.31 +#endif
    1.32 +
    1.33 +extern "C" {
    1.34 +// open/close/read/write
    1.35 +#include <sys/stat.h>           // For stat
    1.36 +#if !defined (_CRAY) && ! defined (__EMX__)
    1.37 +#  include <sys/mman.h>           // For mmap
    1.38 +#endif
    1.39 +
    1.40 +//  on HP-UX 11, this one contradicts with pthread.h on pthread_atfork, unless we unset this
    1.41 +#if defined (__hpux) && defined (__GNUC__)
    1.42 +#  undef _INCLUDE_POSIX1C_SOURCE
    1.43 +#endif
    1.44 +
    1.45 +#include <unistd.h>
    1.46 +#include <fcntl.h>
    1.47 +}
    1.48 +
    1.49 +#ifdef __APPLE__
    1.50 +#  include <sys/sysctl.h>
    1.51 +#endif
    1.52 +
    1.53 +const _STLP_fd INVALID_STLP_FD = -1;
    1.54 +
    1.55 +#ifndef O_ACCMODE
    1.56 +#  define O_ACCMODE (O_RDONLY|O_WRONLY|O_RDWR)
    1.57 +#endif
    1.58 +
    1.59 +// Compare with streamoff definition in stl/char_traits.h!
    1.60 +#if defined (_STLP_USE_DEFAULT_FILE_OFFSET) || \
    1.61 +    (!defined(_LARGEFILE_SOURCE) && !defined (_LARGEFILE64_SOURCE))
    1.62 +#  define FSTAT fstat
    1.63 +#  define STAT  stat
    1.64 +#  define LSEEK lseek
    1.65 +#  define MMAP  mmap
    1.66 +#  define OPEN  open
    1.67 +#else
    1.68 +#  define FSTAT fstat64
    1.69 +#  define STAT  stat64
    1.70 +#  define LSEEK lseek64
    1.71 +#  define MMAP  mmap64
    1.72 +#  define OPEN  open64
    1.73 +#endif
    1.74 +
    1.75 +#ifndef MAP_FAILED /* MMAP failure return code */
    1.76 +#  define MAP_FAILED -1
    1.77 +#endif
    1.78 +
    1.79 +_STLP_BEGIN_NAMESPACE
    1.80 +
    1.81 +static ios_base::openmode flag_to_openmode(int mode)
    1.82 +{
    1.83 +  ios_base::openmode ret = ios_base::__default_mode;
    1.84 +
    1.85 +  switch ( mode & O_ACCMODE ) {
    1.86 +    case O_RDONLY:
    1.87 +      ret = ios_base::in;
    1.88 +      break;
    1.89 +    case O_WRONLY:
    1.90 +      ret = ios_base::out;
    1.91 +      break;
    1.92 +    case O_RDWR:
    1.93 +      ret = ios_base::in | ios_base::out;
    1.94 +      break;
    1.95 +  }
    1.96 +
    1.97 +  if ( mode & O_APPEND )
    1.98 +    ret |= ios_base::app;
    1.99 +
   1.100 +  return ret;
   1.101 +}
   1.102 +
   1.103 +_STLP_MOVE_TO_PRIV_NAMESPACE
   1.104 +
   1.105 +// Helper functions for _Filebuf_base.
   1.106 +
   1.107 +static bool __is_regular_file(_STLP_fd fd) {
   1.108 +  struct STAT buf;
   1.109 +  return FSTAT(fd, &buf) == 0 && S_ISREG(buf.st_mode);
   1.110 +}
   1.111 +
   1.112 +// Number of characters in the file.
   1.113 +static streamoff __file_size(_STLP_fd fd) {
   1.114 +  streamoff ret = 0;
   1.115 +
   1.116 +  struct STAT buf;
   1.117 +  if (FSTAT(fd, &buf) == 0 && S_ISREG(buf.st_mode))
   1.118 +    ret = buf.st_size > 0 ? buf.st_size : 0;
   1.119 +
   1.120 +  return ret;
   1.121 +}
   1.122 +
   1.123 +_STLP_MOVE_TO_STD_NAMESPACE
   1.124 +
   1.125 +size_t _Filebuf_base::_M_page_size = 4096;
   1.126 +
   1.127 +_Filebuf_base::_Filebuf_base()
   1.128 +  : _M_file_id(INVALID_STLP_FD),
   1.129 +    _M_openmode(0),
   1.130 +    _M_is_open(false),
   1.131 +    _M_should_close(false)
   1.132 +{}
   1.133 +
   1.134 +void _Filebuf_base::_S_initialize()
   1.135 +{
   1.136 +#if defined (__APPLE__)
   1.137 +  int mib[2];
   1.138 +  size_t pagesize, len;
   1.139 +  mib[0] = CTL_HW;
   1.140 +  mib[1] = HW_PAGESIZE;
   1.141 +  len = sizeof(pagesize);
   1.142 +  sysctl(mib, 2, &pagesize, &len, NULL, 0);
   1.143 +  _M_page_size = pagesize;
   1.144 +#elif defined (__DJGPP) && defined (_CRAY)
   1.145 +  _M_page_size = BUFSIZ;
   1.146 +#else
   1.147 +  _M_page_size = sysconf(_SC_PAGESIZE);
   1.148 +#endif
   1.149 +}
   1.150 +
   1.151 +// Return the size of the file.  This is a wrapper for stat.
   1.152 +// Returns zero if the size cannot be determined or is ill-defined.
   1.153 +streamoff _Filebuf_base::_M_file_size()
   1.154 +{
   1.155 +  return _STLP_PRIV __file_size(_M_file_id);
   1.156 +}
   1.157 +
   1.158 +bool _Filebuf_base::_M_open(const char* name, ios_base::openmode openmode,
   1.159 +                            long permission)
   1.160 +{
   1.161 +  _STLP_fd file_no;
   1.162 +
   1.163 +  if (_M_is_open)
   1.164 +    return false;
   1.165 +
   1.166 +  int flags = 0;
   1.167 +
   1.168 +  // Unix makes no distinction between text and binary files.
   1.169 +  switch ( openmode & (~ios_base::ate & ~ios_base::binary) ) {
   1.170 +    case ios_base::out:
   1.171 +    case ios_base::out | ios_base::trunc:
   1.172 +      flags = O_WRONLY | O_CREAT | O_TRUNC;
   1.173 +      break;
   1.174 +    case ios_base::app:
   1.175 +    case ios_base::out | ios_base::app:
   1.176 +      flags = O_WRONLY | O_CREAT | O_APPEND;
   1.177 +      break;
   1.178 +    case ios_base::in:
   1.179 +      flags = O_RDONLY;
   1.180 +      permission = 0;             // Irrelevant unless we're writing.
   1.181 +      break;
   1.182 +    case ios_base::in | ios_base::out:
   1.183 +      flags = O_RDWR;
   1.184 +      break;
   1.185 +    case ios_base::in | ios_base::out | ios_base::trunc:
   1.186 +      flags = O_RDWR | O_CREAT | O_TRUNC;
   1.187 +      break;
   1.188 +    case ios_base::in | ios_base::app:
   1.189 +    case ios_base::in | ios_base::out | ios_base::app:
   1.190 +      flags = O_RDWR | O_CREAT | O_APPEND;
   1.191 +      break;
   1.192 +    default:                      // The above are the only combinations of
   1.193 +      return false;               // flags allowed by the C++ standard.
   1.194 +  }
   1.195 +
   1.196 +  file_no = OPEN(name, flags, permission);
   1.197 +
   1.198 +  if (file_no < 0)
   1.199 +    return false;
   1.200 +
   1.201 +  _M_is_open = true;
   1.202 +
   1.203 +  if ((openmode & (ios_base::ate | ios_base::app)) && (LSEEK(file_no, 0, SEEK_END) == -1)) {
   1.204 +    _M_is_open = false;
   1.205 +  }
   1.206 +
   1.207 +  _M_file_id = file_no;
   1.208 +  _M_should_close = _M_is_open;
   1.209 +  _M_openmode = openmode;
   1.210 +
   1.211 +  if (_M_is_open)
   1.212 +    _M_regular_file = _STLP_PRIV __is_regular_file(_M_file_id);
   1.213 +
   1.214 +  return (_M_is_open != 0);
   1.215 +}
   1.216 +
   1.217 +
   1.218 +bool _Filebuf_base::_M_open(const char* name, ios_base::openmode openmode)
   1.219 +{
   1.220 +  // This doesn't really grant everyone in the world read/write
   1.221 +  // access.  On Unix, file-creation system calls always clear
   1.222 +  // bits that are set in the umask from the permissions flag.
   1.223 +  return this->_M_open(name, openmode, S_IRUSR | S_IWUSR | S_IRGRP |
   1.224 +                                       S_IWGRP | S_IROTH | S_IWOTH);
   1.225 +}
   1.226 +
   1.227 +// Associated the filebuf with a file descriptor pointing to an already-
   1.228 +// open file.  Mode is set to be consistent with the way that the file
   1.229 +// was opened.
   1.230 +bool _Filebuf_base::_M_open(int file_no, ios_base::openmode)
   1.231 +{
   1.232 +  if (_M_is_open || file_no < 0)
   1.233 +    return false;
   1.234 +
   1.235 +  int mode = fcntl(file_no, F_GETFL);
   1.236 +
   1.237 +  if (mode == -1)
   1.238 +    return false;
   1.239 +
   1.240 +  _M_openmode = flag_to_openmode(mode);
   1.241 +  _M_file_id = file_no;
   1.242 +
   1.243 +  _M_is_open = true;
   1.244 +  _M_should_close = false;
   1.245 +  _M_regular_file = _STLP_PRIV __is_regular_file(_M_file_id);
   1.246 +  return true;
   1.247 +}
   1.248 +
   1.249 +bool _Filebuf_base::_M_close()
   1.250 +{
   1.251 +  if (!_M_is_open)
   1.252 +    return false;
   1.253 +
   1.254 +  bool ok = _M_should_close ? (close(_M_file_id) == 0) : true;
   1.255 +
   1.256 +  _M_is_open = _M_should_close = false;
   1.257 +  _M_openmode = 0;
   1.258 +  return ok;
   1.259 +}
   1.260 +
   1.261 +// Read up to n characters into a buffer.  Return value is number of
   1.262 +// characters read.
   1.263 +ptrdiff_t _Filebuf_base::_M_read(char* buf, ptrdiff_t n)
   1.264 +{
   1.265 +  return read(_M_file_id, buf, n);
   1.266 +}
   1.267 +
   1.268 +// Write n characters from a buffer.  Return value: true if we managed
   1.269 +// to write the entire buffer, false if we didn't.
   1.270 +bool _Filebuf_base::_M_write(char* buf, ptrdiff_t n)
   1.271 +{
   1.272 +  for (;;) {
   1.273 +    ptrdiff_t written = write(_M_file_id, buf, n);
   1.274 +
   1.275 +    if (n == written) {
   1.276 +      return true;
   1.277 +    }
   1.278 +
   1.279 +    if (written > 0 && written < n) {
   1.280 +      n -= written;
   1.281 +      buf += written;
   1.282 +    } else {
   1.283 +      return false;
   1.284 +    }
   1.285 +  }
   1.286 +}
   1.287 +
   1.288 +// Wrapper for lseek or the like.
   1.289 +streamoff _Filebuf_base::_M_seek(streamoff offset, ios_base::seekdir dir)
   1.290 +{
   1.291 +  int whence;
   1.292 +
   1.293 +  switch ( dir ) {
   1.294 +    case ios_base::beg:
   1.295 +      if (offset < 0 /* || offset > _M_file_size() */ )
   1.296 +        return streamoff(-1);
   1.297 +      whence = SEEK_SET;
   1.298 +      break;
   1.299 +    case ios_base::cur:
   1.300 +      whence = SEEK_CUR;
   1.301 +      break;
   1.302 +    case ios_base::end:
   1.303 +      if (/* offset > 0 || */  -offset > _M_file_size() )
   1.304 +        return streamoff(-1);
   1.305 +      whence = SEEK_END;
   1.306 +      break;
   1.307 +    default:
   1.308 +      return streamoff(-1);
   1.309 +  }
   1.310 +
   1.311 +  return LSEEK(_M_file_id, offset, whence);
   1.312 +}
   1.313 +
   1.314 +// Attempts to memory-map len bytes of the current file, starting
   1.315 +// at position offset.  Precondition: offset is a multiple of the
   1.316 +// page size.  Postcondition: return value is a null pointer if the
   1.317 +// memory mapping failed.  Otherwise the return value is a pointer to
   1.318 +// the memory-mapped file and the file position is set to offset.
   1.319 +void* _Filebuf_base::_M_mmap(streamoff offset, streamoff len)
   1.320 +{
   1.321 +  void* base;
   1.322 +#if !defined (__DJGPP) && !defined (_CRAY)
   1.323 +  base = MMAP(0, len, PROT_READ, MAP_PRIVATE, _M_file_id, offset);
   1.324 +  if (base != (void*)MAP_FAILED) {
   1.325 +    if (LSEEK(_M_file_id, offset + len, SEEK_SET) < 0) {
   1.326 +      this->_M_unmap(base, len);
   1.327 +      base = 0;
   1.328 +    }
   1.329 +  } else
   1.330 +    base =0;
   1.331 +#else
   1.332 +  _STLP_MARK_PARAMETER_AS_UNUSED(&offset)
   1.333 +  _STLP_MARK_PARAMETER_AS_UNUSED(&len)
   1.334 +  base = 0;
   1.335 +#endif
   1.336 +  return base;
   1.337 +}
   1.338 +
   1.339 +void _Filebuf_base::_M_unmap(void* base, streamoff len)
   1.340 +{
   1.341 +  // precondition : there is a valid mapping at the moment
   1.342 +#if !defined (__DJGPP) && !defined (_CRAY)
   1.343 +  munmap((char*)base, len);
   1.344 +#else
   1.345 +  _STLP_MARK_PARAMETER_AS_UNUSED(&len)
   1.346 +  _STLP_MARK_PARAMETER_AS_UNUSED(base)
   1.347 +#endif
   1.348 +}
   1.349 +
   1.350 +_STLP_END_NAMESPACE

mercurial