From e611b132f9b8abe35b362e5870b74bce94a1e58e Mon Sep 17 00:00:00 2001 From: Adam Date: Sat, 16 May 2020 20:51:50 -0700 Subject: initial commit --- private/crt32/iostream/filebuf1.cxx | 231 ++++++++++++++++++++++++++++++++++++ 1 file changed, 231 insertions(+) create mode 100644 private/crt32/iostream/filebuf1.cxx (limited to 'private/crt32/iostream/filebuf1.cxx') diff --git a/private/crt32/iostream/filebuf1.cxx b/private/crt32/iostream/filebuf1.cxx new file mode 100644 index 000000000..6079d69e2 --- /dev/null +++ b/private/crt32/iostream/filebuf1.cxx @@ -0,0 +1,231 @@ +/*** +*filebuf1.cxx - non-core filebuf member functions. +* +* Copyright (c) 1991-1992, Microsoft Corporation. All rights reserved. +* +*Purpose: +* Contains optional member functions for filebuf class. +* +*Revision History: +* 09-21-91 KRS Created. Split off from fstream.cxx. +* 10-24-91 KRS C700 #4909: Typo/logic bug in setmode(). +* 11-06-91 KRS Add support for share mode in open(). Use _sopen(). +* 08-19-92 KRS Use _SH_DENYNO for default mode for NT. +* 03-02-93 SKS Avoid setting _O_TRUNC when noreplace is specified +* +*******************************************************************************/ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#pragma hdrstop + +#include + +/*** +*filebuf* filebuf::attach(filedesc fd) - filebuf attach function +* +*Purpose: +* filebuf attach() member function. Attach filebuf object to the +* given file descriptor previously obtained from _open() or _sopen(). +* +*Entry: +* fd = file descriptor. +* +*Exit: +* Returns this pointer or NULL if error. +* +*Exceptions: +* Returns NULL if fd = -1. +* +*******************************************************************************/ +filebuf* filebuf::attach(filedesc fd) +{ + if (x_fd!=-1) + return NULL; // error if already attached + + lock(); + x_fd = fd; + if ((fd!=-1) && (!unbuffered()) && (!ebuf())) + { + char * sbuf = new char[BUFSIZ]; + if (!sbuf) + { + unbuffered(1); + } + else + { + streambuf::setb(sbuf,sbuf+BUFSIZ,1); + } + } + unlock(); + return this; +} + +/*** +*filebuf* filebuf::open(const char* name, int mode, int share) - filebuf open +* +*Purpose: +* filebuf open() member function. Open a file and attach to filebuf +* object. +* +*Entry: +* name = file name string. +* mode = open mode: Combination of ios:: in, out, binary, nocreate, app, +* ate, noreplace and trunc. See spec. for details on behavior. +* share = share mode (optional). sh_compat, sh_none, sh_read, sh_write. +* +*Exit: +* Returns this pointer or NULL if error. +* +*Exceptions: +* Returns NULL if filebuf is already attached to an open file, or if +* invalid mode options, or if call to _sopen or filebuf::seekoff() fails. +* +*******************************************************************************/ +filebuf* filebuf::open(const char* name, int mode, int share) +{ + int dos_mode; + int smode; + if (x_fd!=-1) + return NULL; // error if already open +// translate mode argument + dos_mode = (mode & ios::binary) ? O_BINARY : O_TEXT; + if (!(mode & ios::nocreate)) + dos_mode |= O_CREAT; + if (mode & ios::noreplace) + dos_mode |= O_EXCL; + if (mode & ios::app) + { + mode |= ios::out; + dos_mode |= O_APPEND; + } + if (mode & ios::trunc) + { + mode |= ios::out; // IMPLIED + dos_mode |= O_TRUNC; + } + if (mode & ios::out) + { + if (mode & ios::in) + { + dos_mode |= O_RDWR; + } + else + { + dos_mode |= O_WRONLY; + } + // CONSIDER: a bit weaker treatment than in spec. + if (!(mode & (ios::in|ios::app|ios::ate|ios::noreplace))) + { + mode |= ios::trunc; // IMPLIED + dos_mode |= O_TRUNC; + } + } + else if (mode & ios::in) + dos_mode |= O_RDONLY; + else + return NULL; // error if not ios:in or ios::out + + smode = _SH_DENYNO; // default for NT + share &= (sh_read|sh_write|sh_none); // ignore other bits + if (share) // optimization openprot serves as default + { + switch (share) + { +/* case 03000 : Reserved for sh_compat */ + +// case sh_none : + case 04000 : + smode = _SH_DENYRW; + break; +// case sh_read : + case 05000 : + smode = _SH_DENYWR; + break; +// case sh_write : + case 06000 : + smode = _SH_DENYRD; + break; +// case (sh_read|sh_write) : + case 07000 : + smode = _SH_DENYNO; + break; + default : // unrecognized value same as default + break; + }; + } + + x_fd = _sopen(name, dos_mode, smode, S_IREAD|S_IWRITE); + if (x_fd==-1) + return NULL; + lock(); + x_fOpened = 1; + if ((!unbuffered()) && (!ebuf())) + { + char * sbuf = new char[BUFSIZ]; + if (!sbuf) + { + unbuffered(1); + } + else + { + streambuf::setb(sbuf,sbuf+BUFSIZ,1); + } + } + if (mode & ios::ate) + if (seekoff(0,ios::end,mode)==EOF) + { + close(); + unlock(); + return NULL; + } + unlock(); + return this; +} + +/*** +*int filebuf::setmode(int mode) - filebuf setmode function +* +*Purpose: +* filebuf setmode() member function. Set binary or text access mode. +* Calls _setmode(). +* +* MS-specific extension. +* +*Entry: +* mode = filebuf::binary or filebuf::text. +* +*Exit: +* Returns previous mode, or -1 error. +* +*Exceptions: +* Return -1 (EOF) if invalid argument or _setmode fails. +* +*******************************************************************************/ +int filebuf::setmode(int mode) +{ + int retval; + if ((mode!=filebuf::binary) && (mode!=filebuf::text)) + return -1; + + lock(); + if ((x_fd==-1) || (sync()==EOF)) + { + retval = -1; + } + else + { + retval = _setmode(x_fd,mode); + } + + unlock(); + return retval; +} -- cgit v1.2.3