Annotation of GNUtools/libg++/libio/iostream.cc, revision 1.1

1.1     ! root        1: /* This is part of libio/iostream, providing -*- C++ -*- input/output.
        !             2: Copyright (C) 1993 Free Software Foundation
        !             3: 
        !             4: This file is part of the GNU IO Library.  This library is free
        !             5: software; you can redistribute it and/or modify it under the
        !             6: terms of the GNU General Public License as published by the
        !             7: Free Software Foundation; either version 2, or (at your option)
        !             8: any later version.
        !             9: 
        !            10: This library is distributed in the hope that it will be useful,
        !            11: but WITHOUT ANY WARRANTY; without even the implied warranty of
        !            12: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
        !            13: GNU General Public License for more details.
        !            14: 
        !            15: You should have received a copy of the GNU General Public License
        !            16: along with GNU CC; see the file COPYING.  If not, write to
        !            17: the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
        !            18: 
        !            19: As a special exception, if you link this library with files
        !            20: compiled with a GNU compiler to produce an executable, this does not cause
        !            21: the resulting executable to be covered by the GNU General Public License.
        !            22: This exception does not however invalidate any other reasons why
        !            23: the executable file might be covered by the GNU General Public License. */
        !            24: 
        !            25: /* Written by Per Bothner ([email protected]). */
        !            26: 
        !            27: #ifdef __GNUC__
        !            28: #pragma implementation
        !            29: #endif
        !            30: #define _STREAM_COMPAT
        !            31: #include <iostream.h>
        !            32: #include "libioP.h"
        !            33: extern "C" {
        !            34: #include <stdio.h>  /* Needed for sprintf */
        !            35: }
        !            36: extern "C" {
        !            37: #include <ctype.h>
        !            38: }
        !            39: extern "C" {
        !            40: #include <string.h>
        !            41: }
        !            42: extern "C" {
        !            43: #include <limits.h>
        !            44: }
        !            45: #include "floatio.h"
        !            46: 
        !            47: #define        BUF             (MAXEXP+MAXFRACT+1)     /* + decimal point */
        !            48: 
        !            49: //#define isspace(ch) ((ch)==' ' || (ch)=='\t' || (ch)=='\n')
        !            50: 
        !            51: istream::istream(streambuf *sb, ostream* tied) : ios(sb, tied)
        !            52: {
        !            53:     _flags |= ios::dont_close;
        !            54:     _gcount = 0;
        !            55: }
        !            56: 
        !            57: int skip_ws(streambuf* sb)
        !            58: {
        !            59:     int ch;
        !            60:     for (;;) {
        !            61:        ch = sb->sbumpc();
        !            62:        if (ch == EOF || !isspace(ch))
        !            63:            return ch;
        !            64:     }
        !            65: }
        !            66: 
        !            67: istream& istream::get(char& c)
        !            68: {
        !            69:     if (ipfx1()) {
        !            70:        int ch = _strbuf->sbumpc();
        !            71:        if (ch == EOF) {
        !            72:          set(ios::eofbit|ios::failbit);
        !            73:          _gcount = 0;
        !            74:        }
        !            75:        else {
        !            76:          c = (char)ch;
        !            77:          _gcount = 1;
        !            78:        }
        !            79:     }
        !            80:     return *this;
        !            81: }
        !            82: 
        !            83: int istream::peek()
        !            84: {
        !            85:   if (!good())
        !            86:     return EOF;
        !            87:   if (_tie && rdbuf()->in_avail() == 0)
        !            88:     _tie->flush();
        !            89:   int ch = _strbuf->sgetc();
        !            90:   if (ch == EOF)
        !            91:     set(ios::eofbit);
        !            92:   return ch;
        !            93: }
        !            94: 
        !            95: istream& istream::ignore(int n /* = 1 */, int delim /* = EOF */)
        !            96: {
        !            97:     if (ipfx1()) {
        !            98:        register streambuf* sb = _strbuf;
        !            99:        if (delim == EOF) {
        !           100:            _gcount = sb->ignore(n);
        !           101:            return *this;
        !           102:        }
        !           103:        _gcount = 0;
        !           104:        for (;;) {
        !           105: #if 0
        !           106:            if (n != MAXINT) // FIXME
        !           107: #endif
        !           108:            if (--n < 0)
        !           109:                break;
        !           110:            int ch = sb->sbumpc();
        !           111:            if (ch == EOF) {
        !           112:                set(ios::eofbit|ios::failbit);
        !           113:                break;
        !           114:            }
        !           115:            _gcount++;
        !           116:            if (ch == delim)
        !           117:                break;
        !           118:        }
        !           119:     }
        !           120:     return *this;
        !           121: }
        !           122: 
        !           123: istream& istream::read(char *s, int n)
        !           124: {
        !           125:     if (ipfx1()) {
        !           126:        _gcount = _strbuf->sgetn(s, n);
        !           127:        if (_gcount != n)
        !           128:            set(ios::failbit);
        !           129:     }
        !           130:     return *this;
        !           131: }
        !           132: 
        !           133: istream& istream::seekg(streampos pos)
        !           134: {
        !           135:     pos = _strbuf->sseekpos(pos, ios::in);
        !           136:     if (pos == streampos(EOF))
        !           137:        set(ios::badbit);
        !           138:     return *this;
        !           139: }
        !           140: 
        !           141: istream& istream::seekg(streamoff off, _seek_dir dir)
        !           142: {
        !           143:   streampos pos
        !           144:     = _IO_seekoff (_strbuf, off,
        !           145:                   (_IO_seekflags)
        !           146:                   ((int)dir | _IO_seek_not_out | _IO_seek_pos_ignored));
        !           147:   if (pos == streampos(EOF))
        !           148:     set(ios::badbit);
        !           149:   return *this;
        !           150: }
        !           151: 
        !           152: streampos istream::tellg()
        !           153: {
        !           154: #if 0
        !           155:     streampos pos = _strbuf->sseekoff(0, ios::cur, ios::in);
        !           156: #else
        !           157:     streampos pos
        !           158:       = _IO_seekoff (_strbuf, 0,
        !           159:                     (_IO_seekflags)(_IO_seek_cur | _IO_seek_not_out));
        !           160: #endif
        !           161:     if (pos == streampos(EOF))
        !           162:        set(ios::badbit);
        !           163:     return pos;
        !           164: }
        !           165: 
        !           166: istream& istream::operator>>(char& c)
        !           167: {
        !           168:     if (ipfx0()) {
        !           169:        int ch = _strbuf->sbumpc();
        !           170:        if (ch == EOF)
        !           171:            set(ios::eofbit|ios::failbit);
        !           172:        else
        !           173:            c = (char)ch;
        !           174:     }
        !           175:     return *this;
        !           176: }
        !           177: 
        !           178: istream& istream::operator>>(char* ptr)
        !           179: {
        !           180:   register char *p = ptr;
        !           181:   int w = width(0);
        !           182:   if (ipfx0()) {
        !           183:     register streambuf* sb = _strbuf;
        !           184:     for (;;)
        !           185:       {
        !           186:        int ch = sb->sbumpc();
        !           187:        if (ch == EOF)
        !           188:          {
        !           189:            set(p == ptr ? (ios::eofbit|ios::failbit) : (ios::eofbit));
        !           190:            break;
        !           191:          }
        !           192:        else if (isspace(ch))
        !           193:          {
        !           194:            sb->sputbackc(ch);
        !           195:            break;
        !           196:          }
        !           197:        else if (w == 1)
        !           198:          {
        !           199:            set(ios::failbit);
        !           200:            sb->sputbackc(ch);
        !           201:            break;
        !           202:          }
        !           203:        else *p++ = ch;
        !           204:        w--;
        !           205:       }
        !           206:   }
        !           207:   *p = '\0';
        !           208:   return *this;
        !           209: }
        !           210: 
        !           211: #if defined(__GNUC__) && !defined(__STRICT_ANSI__)
        !           212: #define LONGEST long long
        !           213: #else
        !           214: #define LONGEST long
        !           215: #endif
        !           216: 
        !           217: static int read_int(istream& stream, unsigned LONGEST& val, int& neg)
        !           218: {
        !           219:     if (!stream.ipfx0())
        !           220:       return 0;
        !           221:     register streambuf* sb = stream.rdbuf();
        !           222:     int base = 10;
        !           223:     int ndigits = 0;
        !           224:     register int ch = skip_ws(sb);
        !           225:     if (ch == EOF)
        !           226:        goto eof_fail;
        !           227:     neg = 0;
        !           228:     if (ch == '+') {
        !           229:        ch = skip_ws(sb);
        !           230:     }
        !           231:     else if (ch == '-') {
        !           232:        neg = 1;
        !           233:        ch = skip_ws(sb);
        !           234:     }
        !           235:     if (ch == EOF) goto eof_fail;
        !           236:     if (!(stream.flags() & ios::basefield)) {
        !           237:        if (ch == '0') {
        !           238:            ch = sb->sbumpc();
        !           239:            if (ch == EOF) {
        !           240:                val = 0;
        !           241:                return 1;
        !           242:            }
        !           243:            if (ch == 'x' || ch == 'X') {
        !           244:                base = 16;
        !           245:                ch = sb->sbumpc();
        !           246:                if (ch == EOF) goto eof_fail;
        !           247:            }
        !           248:            else {
        !           249:                sb->sputbackc(ch);
        !           250:                base = 8;
        !           251:                ch = '0';
        !           252:            }
        !           253:        }
        !           254:     }
        !           255:     else if ((stream.flags() & ios::basefield) == ios::hex)
        !           256:        base = 16;
        !           257:     else if ((stream.flags() & ios::basefield) == ios::oct)
        !           258:        base = 8;
        !           259:     val = 0;
        !           260:     for (;;) {
        !           261:        if (ch == EOF)
        !           262:            break;
        !           263:        int digit;
        !           264:        if (ch >= '0' && ch <= '9')
        !           265:            digit = ch - '0';
        !           266:        else if (ch >= 'A' && ch <= 'F')
        !           267:            digit = ch - 'A' + 10;
        !           268:        else if (ch >= 'a' && ch <= 'f')
        !           269:            digit = ch - 'a' + 10;
        !           270:        else
        !           271:            digit = 999;
        !           272:        if (digit >= base) {
        !           273:            sb->sputbackc(ch);
        !           274:            if (ndigits == 0)
        !           275:                goto fail;
        !           276:            else
        !           277:                return 1;
        !           278:        }
        !           279:        ndigits++;
        !           280:        val = base * val + digit;
        !           281:        ch = sb->sbumpc();
        !           282:     }
        !           283:     return 1;
        !           284:   fail:
        !           285:     stream.set(ios::failbit);
        !           286:     return 0;
        !           287:   eof_fail:
        !           288:     stream.set(ios::failbit|ios::eofbit);
        !           289:     return 0;
        !           290: }
        !           291: 
        !           292: #define READ_INT(TYPE) \
        !           293: istream& istream::operator>>(TYPE& i)\
        !           294: {\
        !           295:     unsigned LONGEST val; int neg;\
        !           296:     if (read_int(*this, val, neg)) {\
        !           297:        if (neg) val = -val;\
        !           298:        i = (TYPE)val;\
        !           299:     }\
        !           300:     return *this;\
        !           301: }
        !           302: 
        !           303: READ_INT(short)
        !           304: READ_INT(unsigned short)
        !           305: READ_INT(int)
        !           306: READ_INT(unsigned int)
        !           307: READ_INT(long)
        !           308: READ_INT(unsigned long)
        !           309: #if defined(__GNUC__) && !defined(__STRICT_ANSI__)
        !           310: READ_INT(long long)
        !           311: READ_INT(unsigned long long)
        !           312: #endif
        !           313: 
        !           314: istream& istream::operator>>(double& x)
        !           315: {
        !           316:     if (ipfx0())
        !           317:        scan("%lg", &x);
        !           318:     return *this;
        !           319: }
        !           320: 
        !           321: istream& istream::operator>>(float& x)
        !           322: {
        !           323:     if (ipfx0())
        !           324:        scan("%g", &x);
        !           325:     return *this;
        !           326: }
        !           327: 
        !           328: istream& istream::operator>>(register streambuf* sbuf)
        !           329: {
        !           330:     if (ipfx0()) {
        !           331:        register streambuf* inbuf = rdbuf();
        !           332:        // FIXME: Should optimize!
        !           333:        for (;;) {
        !           334:            register int ch = inbuf->sbumpc();
        !           335:            if (ch == EOF) {
        !           336:                set(ios::eofbit);
        !           337:                break;
        !           338:            }
        !           339:            if (sbuf->sputc(ch) == EOF) {
        !           340:                set(ios::failbit);
        !           341:                break;
        !           342:            }
        !           343:        }
        !           344:     }
        !           345:     return *this;
        !           346: }
        !           347: 
        !           348: ostream& ostream::operator<<(char c)
        !           349: {
        !           350:     if (opfx()) {
        !           351: #if 1
        !           352:        // This is what the cfront implementation does.
        !           353:        if (_strbuf->sputc(c) == EOF)
        !           354:          goto failed;
        !           355: #else
        !           356:        // This is what cfront documentation and current ANSI drafts say.
        !           357:        int w = width(0);
        !           358:        char fill_char = fill();
        !           359:        register int padding = w > 0 ? w - 1 : 0;
        !           360:        register streambuf *sb = _strbuf;
        !           361:        if (!(flags() & ios::left) && padding) // Default adjustment.
        !           362:            if (_IO_padn(sb, fill_char, padding) < padding)
        !           363:              goto failed;
        !           364:        if (sb->sputc(c) == EOF)
        !           365:          goto failed;
        !           366:        if (flags() & ios::left && padding) // Left adjustment.
        !           367:            if (_IO_padn(sb, fill_char, padding) < padding)
        !           368:              goto failed;
        !           369: #endif
        !           370:        osfx();
        !           371:     }
        !           372:     return *this;
        !           373:   failed:
        !           374:     set(ios::badbit);
        !           375:     osfx();
        !           376:     return *this;
        !           377: }
        !           378: 
        !           379: /* Write VAL on STREAM.
        !           380:    If SIGN<0, val is the absolute value of a negative number.
        !           381:    If SIGN>0, val is a signed non-negative number.
        !           382:    If SIGN==0, val is unsigned. */
        !           383: 
        !           384: static void write_int(ostream& stream, unsigned LONGEST val, int sign)
        !           385: {
        !           386: #define WRITE_BUF_SIZE (10 + sizeof(unsigned LONGEST) * 3)
        !           387:     char buf[WRITE_BUF_SIZE];
        !           388:     register char *buf_ptr = buf+WRITE_BUF_SIZE; // End of buf.
        !           389:     char *show_base = "";
        !           390:     int show_base_len = 0;
        !           391:     int show_pos = 0; // If 1, print a '+'.
        !           392: 
        !           393:     // Now do the actual conversion, placing the result at the *end* of buf.
        !           394:     // Note that we use separate code for decimal, octal, and hex,
        !           395:     // so we can divide by optimizable constants.
        !           396:     if ((stream.flags() & ios::basefield) == ios::oct) { // Octal
        !           397:        do {
        !           398:            *--buf_ptr = (val & 7) + '0';
        !           399:            val = val >> 3;
        !           400:        } while (val != 0);
        !           401:        if ((stream.flags() & ios::showbase) && (val != 0))
        !           402:            *--buf_ptr = '0';
        !           403:     }
        !           404:     else if ((stream.flags() & ios::basefield) == ios::hex) { // Hex
        !           405:        char *xdigs = (stream.flags() & ios::uppercase) ? "0123456789ABCDEF0X"
        !           406:            : "0123456789abcdef0x";
        !           407:        do {
        !           408:            *--buf_ptr = xdigs[val & 15];
        !           409:            val = val >> 4;
        !           410:        } while (val != 0);
        !           411:        if ((stream.flags() & ios::showbase) && (val != 0)) {
        !           412:            show_base = xdigs + 16; // Either "0X" or "0x".
        !           413:            show_base_len = 2;
        !           414:        }
        !           415:     }
        !           416:     else { // Decimal
        !           417: #if defined(__GNUC__) && !defined(__STRICT_ANSI__)
        !           418:        // Optimization:  Only use long long when we need to.
        !           419:        while (val > UINT_MAX) {
        !           420:            *--buf_ptr = (val % 10) + '0';
        !           421:            val /= 10;
        !           422:        }
        !           423:        // Use more efficient (int) arithmetic for the rest.
        !           424:        register unsigned int ival = (unsigned int)val;
        !           425: #else
        !           426:        register unsigned LONGEST ival = val;
        !           427: #endif
        !           428:        do {
        !           429:            *--buf_ptr = (ival % 10) + '0';
        !           430:            ival /= 10;
        !           431:        } while (ival != 0);
        !           432:        if (sign > 0 && (stream.flags() & ios::showpos))
        !           433:            show_pos=1;
        !           434:     }
        !           435: 
        !           436:     int buf_len = buf+WRITE_BUF_SIZE - buf_ptr;
        !           437:     int w = stream.width(0);
        !           438: 
        !           439:     // Calculate padding.
        !           440:     int len = buf_len+show_pos;
        !           441:     if (sign < 0) len++;
        !           442:     len += show_base_len;
        !           443:     int padding = len > w ? 0 : w - len;
        !           444: 
        !           445:     // Do actual output.
        !           446:     register streambuf* sbuf = stream.rdbuf();
        !           447:     ios::fmtflags pad_kind =
        !           448:        stream.flags() & (ios::left|ios::right|ios::internal);
        !           449:     char fill_char = stream.fill();
        !           450:     if (padding > 0
        !           451:        && pad_kind != (ios::fmtflags)ios::left
        !           452:        && pad_kind != (ios::fmtflags)ios::internal) // Default (right) adjust.
        !           453:        if (_IO_padn(sbuf, fill_char, padding) < padding)
        !           454:          goto failed;
        !           455:     if (sign < 0 || show_pos)
        !           456:       {
        !           457:        char ch = sign < 0 ? '-' : '+';
        !           458:        if (sbuf->sputc(ch) < 0)
        !           459:          goto failed;
        !           460:       }
        !           461:     if (show_base_len)
        !           462:        if (_IO_sputn(sbuf, show_base, show_base_len) <= 0)
        !           463:          goto failed;
        !           464:     if (pad_kind == (ios::fmtflags)ios::internal && padding > 0)
        !           465:       if (_IO_padn(sbuf, fill_char, padding) < padding)
        !           466:        goto failed;
        !           467:     if (_IO_sputn (sbuf, buf_ptr, buf_len) != buf_len)
        !           468:       goto failed;
        !           469:     if (pad_kind == (ios::fmtflags)ios::left && padding > 0) // Left adjustment
        !           470:       if (_IO_padn(sbuf, fill_char, padding) < padding)
        !           471:        goto failed;
        !           472:     stream.osfx();
        !           473:     return;
        !           474:   failed:
        !           475:     stream.set(ios::badbit);
        !           476:     stream.osfx();
        !           477: }
        !           478: 
        !           479: ostream& ostream::operator<<(int n)
        !           480: {
        !           481:     if (opfx()) {
        !           482:        int sign = 1;
        !           483:        if (n < 0 && (flags() & (ios::oct|ios::hex)) == 0)
        !           484:            n = -n, sign = -1;
        !           485:        write_int(*this, n, sign);
        !           486:     }
        !           487:     return *this;
        !           488: }
        !           489: 
        !           490: ostream& ostream::operator<<(unsigned int n)
        !           491: {
        !           492:     if (opfx())
        !           493:        write_int(*this, n, 0);
        !           494:     return *this;
        !           495: }
        !           496: 
        !           497: 
        !           498: ostream& ostream::operator<<(long n)
        !           499: {
        !           500:     if (opfx()) {
        !           501:        int sign = 1;
        !           502:        unsigned int abs_n = (unsigned)n;
        !           503:        if (n < 0 && (flags() & (ios::oct|ios::hex)) == 0)
        !           504:            abs_n = -((unsigned)n), sign = -1;
        !           505:        write_int(*this, abs_n, sign);
        !           506:     }
        !           507:     return *this;
        !           508: }
        !           509: 
        !           510: ostream& ostream::operator<<(unsigned long n)
        !           511: {
        !           512:     if (opfx())
        !           513:        write_int(*this, n, 0);
        !           514:     return *this;
        !           515: }
        !           516: 
        !           517: #if defined(__GNUC__) && !defined(__STRICT_ANSI__)
        !           518: ostream& ostream::operator<<(long long n)
        !           519: {
        !           520:     if (opfx()) {
        !           521:        int sign = 1;
        !           522:        unsigned long long abs_n = (unsigned long long)n;
        !           523:        if (n < 0 && (flags() & (ios::oct|ios::hex)) == 0)
        !           524:            abs_n = -((unsigned long long)n), sign = -1;
        !           525:        write_int(*this, abs_n, sign);
        !           526:     }
        !           527:     return *this;
        !           528: }
        !           529: 
        !           530: 
        !           531: ostream& ostream::operator<<(unsigned long long n)
        !           532: {
        !           533:     if (opfx())
        !           534:        write_int(*this, n, 0);
        !           535:     return *this;
        !           536: }
        !           537: #endif /*__GNUC__*/
        !           538: 
        !           539: ostream& ostream::operator<<(double n)
        !           540: {
        !           541:     if (opfx()) {
        !           542:        // Uses __cvt_double (renamed from static cvt), in Chris Torek's
        !           543:        // stdio implementation.  The setup code uses the same logic
        !           544:        // as in __vsbprintf.C (also based on Torek's code).
        !           545:        int format_char;
        !           546: #if 0
        !           547:        if (flags() ios::showpos) sign = '+';
        !           548: #endif
        !           549:        if ((flags() & ios::floatfield) == ios::fixed)
        !           550:            format_char = 'f';
        !           551:        else if ((flags() & ios::floatfield) == ios::scientific)
        !           552:            format_char = flags() & ios::uppercase ? 'E' : 'e';
        !           553:        else
        !           554:            format_char = flags() & ios::uppercase ? 'G' : 'g';
        !           555: 
        !           556:        int fpprec = 0; // 'Extra' (suppressed) floating precision.
        !           557:        int prec = precision();
        !           558:        if (prec > MAXFRACT) {
        !           559:            if (flags() & (ios::fixed|ios::scientific) & ios::showpos)
        !           560:                fpprec = prec - MAXFRACT;
        !           561:            prec = MAXFRACT;
        !           562:        }
        !           563:        else if (prec <= 0 && !(flags() & ios::fixed))
        !           564:          prec = 6; /* default */
        !           565: 
        !           566:        // Do actual conversion.
        !           567: #ifdef USE_DTOA
        !           568:        if (_IO_outfloat(n, rdbuf(), format_char, width(0),
        !           569:                       prec, flags(), 0, fill()) < 0)
        !           570:            set(ios::badbit|ios::failbit); // ??
        !           571: #else
        !           572:        int negative;
        !           573:        char buf[BUF];
        !           574:        int sign = '\0';
        !           575:        char *cp = buf;
        !           576:        *cp = 0;
        !           577:        int size = __cvt_double(n, prec,
        !           578:                                flags() & ios::showpoint ? 0x80 : 0,
        !           579:                                &negative,
        !           580:                                format_char, cp, buf + sizeof(buf));
        !           581:        if (negative) sign = '-';
        !           582:        if (*cp == 0)
        !           583:            cp++;
        !           584: 
        !           585:        // Calculate padding.
        !           586:        int fieldsize = size + fpprec;
        !           587:        if (sign) fieldsize++;
        !           588:        int padding = 0;
        !           589:        int w = width(0);
        !           590:        if (fieldsize < w)
        !           591:            padding = w - fieldsize;
        !           592: 
        !           593:        // Do actual output.
        !           594:        register streambuf* sbuf = rdbuf();
        !           595:        register i;
        !           596:        char fill_char = fill();
        !           597:        ios::fmtflags pad_kind =
        !           598:            flags() & (ios::left|ios::right|ios::internal);
        !           599:        if (pad_kind != (ios::fmtflags)ios::left // Default (right) adjust.
        !           600:            && pad_kind != (ios::fmtflags)ios::internal)
        !           601:            for (i = padding; --i >= 0; ) sbuf->sputc(fill_char);
        !           602:        if (sign)
        !           603:            sbuf->sputc(sign);
        !           604:        if (pad_kind == (ios::fmtflags)ios::internal)
        !           605:            for (i = padding; --i >= 0; ) sbuf->sputc(fill_char);
        !           606:        
        !           607:        // Emit the actual concented field, followed by extra zeros.
        !           608:        _IO_sputn (sbuf, cp, size);
        !           609:        for (i = fpprec; --i >= 0; ) sbuf->sputc('0');
        !           610: 
        !           611:        if (pad_kind == (ios::fmtflags)ios::left) // Left adjustment
        !           612:            for (i = padding; --i >= 0; ) sbuf->sputc(fill_char);
        !           613: #endif
        !           614:        osfx();
        !           615:     }
        !           616:     return *this;
        !           617: }
        !           618: 
        !           619: ostream& ostream::operator<<(const char *s)
        !           620: {
        !           621:   if (opfx())
        !           622:     {
        !           623:       if (s == NULL)
        !           624:        s = "(null)";
        !           625:       int len = strlen(s);
        !           626:       int w = width(0);
        !           627: // FIXME: Should we: if (w && len>w) len = w;
        !           628:       char fill_char = fill();
        !           629:       register streambuf *sbuf = rdbuf();
        !           630:       register int padding = w > len ? w - len : 0;
        !           631:       if (!(flags() & ios::left) && padding > 0) // Default adjustment.
        !           632:        if (_IO_padn(sbuf, fill_char, padding) != padding)
        !           633:          goto failed;
        !           634:       if (_IO_sputn (sbuf, s, len) != len)
        !           635:        goto failed;
        !           636:       if (flags() & ios::left && padding > 0) // Left adjustment.
        !           637:        if (_IO_padn(sbuf, fill_char, padding) != padding)
        !           638:          goto failed;
        !           639:       osfx();
        !           640:     }
        !           641:   return *this;
        !           642:  failed:
        !           643:   set(ios::badbit);
        !           644:   osfx();
        !           645:   return *this;
        !           646: }
        !           647: 
        !           648: #if 0
        !           649: ostream& ostream::operator<<(const void *p)
        !           650: { Is in osform.cc, to avoid pulling in all of _IO_vfprintf by this file. */ }
        !           651: #endif
        !           652: 
        !           653: ostream& ostream::operator<<(register streambuf* sbuf)
        !           654: {
        !           655:   if (opfx())
        !           656:     {
        !           657:       char buffer[_IO_BUFSIZ];
        !           658:       register streambuf* outbuf = _strbuf;
        !           659:       for (;;)
        !           660:        {
        !           661:          _IO_size_t count = _IO_sgetn(sbuf, buffer, _IO_BUFSIZ);
        !           662:          if (count <= 0)
        !           663:            break;
        !           664:          if (_IO_sputn(outbuf, buffer, count) != count)
        !           665:            {
        !           666:              set(ios::badbit);
        !           667:              break;
        !           668:            }
        !           669:        }
        !           670:       osfx();
        !           671:     }
        !           672:   return *this;
        !           673: }
        !           674: 
        !           675: ostream::ostream(streambuf* sb, ostream* tied) : ios(sb, tied)
        !           676: {
        !           677:     _flags |= ios::dont_close;
        !           678: }
        !           679: 
        !           680: ostream& ostream::seekp(streampos pos)
        !           681: {
        !           682:     pos = _strbuf->sseekpos(pos, ios::out);
        !           683:     if (pos == streampos(EOF))
        !           684:        set(ios::badbit);
        !           685:     return *this;
        !           686: }
        !           687: 
        !           688: ostream& ostream::seekp(streamoff off, _seek_dir dir)
        !           689: {
        !           690:   streampos pos
        !           691:     = _IO_seekoff (_strbuf, off,
        !           692:                   (_IO_seekflags)
        !           693:                   ((int)dir | _IO_seek_not_in | _IO_seek_pos_ignored));
        !           694:   if (pos == streampos(EOF))
        !           695:     set(ios::badbit);
        !           696:   return *this;
        !           697: }
        !           698: 
        !           699: streampos ostream::tellp()
        !           700: {
        !           701: #if 1
        !           702:     streampos pos
        !           703:       = _IO_seekoff (_strbuf, 0,
        !           704:                     (_IO_seekflags)(_IO_seek_cur | _IO_seek_not_in));
        !           705: #else
        !           706:     streampos pos = _strbuf->sseekoff(0, ios::cur, ios::out);
        !           707: #endif
        !           708:     if (pos == streampos(EOF))
        !           709:        set(ios::badbit);
        !           710:     return pos;
        !           711: }
        !           712: 
        !           713: ostream& ostream::flush()
        !           714: {
        !           715:     if (_strbuf->_jumps->__sync(_strbuf))
        !           716:        set(ios::badbit);
        !           717:     return *this;
        !           718: }
        !           719: 
        !           720: ostream& flush(ostream& outs)
        !           721: {
        !           722:   return outs.flush();
        !           723: }
        !           724: 
        !           725: istream& ws(istream& ins)
        !           726: {
        !           727:     if (ins.ipfx1()) {
        !           728:        int ch = skip_ws(ins._strbuf);
        !           729:        if (ch == EOF)
        !           730:            ins.set(ios::eofbit);
        !           731:        else
        !           732:            ins._strbuf->sputbackc(ch);
        !           733:     }
        !           734:     return ins;
        !           735: }
        !           736: 
        !           737: // Skip white-space.  Return 0 on failure (EOF), or 1 on success.
        !           738: // Differs from ws() manipulator in that failbit is set on EOF.
        !           739: // Called by ipfx() and ipfx0() if needed.
        !           740: 
        !           741: int istream::_skip_ws()
        !           742: {
        !           743:     int ch = skip_ws(_strbuf);
        !           744:     if (ch == EOF) {
        !           745:        set(ios::eofbit|ios::failbit);
        !           746:        return 0;
        !           747:     }
        !           748:     else {
        !           749:        _strbuf->sputbackc(ch);
        !           750:        return 1;
        !           751:     }
        !           752: }
        !           753: 
        !           754: ostream& ends(ostream& outs)
        !           755: {
        !           756:     outs.put('\0');
        !           757:     return outs;
        !           758: }
        !           759: 
        !           760: ostream& endl(ostream& outs)
        !           761: {
        !           762:     return flush(outs.put('\n'));
        !           763: }
        !           764: 
        !           765: ostream& ostream::write(const char *s, int n)
        !           766: {
        !           767:     if (opfx()) {
        !           768:        if (_IO_sputn(_strbuf, s, n) != n)
        !           769:            set(ios::failbit);
        !           770:     }
        !           771:     return *this;
        !           772: }
        !           773: 
        !           774: void ostream::do_osfx()
        !           775: {
        !           776:     if (flags() & ios::unitbuf)
        !           777:        flush();
        !           778:     if (flags() & ios::stdio) {
        !           779:        fflush(stdout);
        !           780:        fflush(stderr);
        !           781:     }
        !           782: }
        !           783: 
        !           784: iostream::iostream(streambuf* sb, ostream* tied) : ios(sb, tied)
        !           785: {
        !           786:   _flags |= ios::dont_close;
        !           787: }
        !           788: 
        !           789: // NOTE: extension for compatibility with old libg++.
        !           790: // Not really compatible with fistream::close().
        !           791: #ifdef _STREAM_COMPAT
        !           792: void ios::close()
        !           793: {
        !           794:   if (!(_flags & (unsigned int)ios::dont_close))
        !           795:     delete rdbuf();
        !           796:   else if (_strbuf->_flags & _IO_IS_FILEBUF)
        !           797:     ((struct filebuf*)rdbuf())->close();
        !           798:   else if (_strbuf != NULL)
        !           799:     rdbuf()->sync();
        !           800:   _flags |= ios::dont_close;
        !           801:   _strbuf = NULL;
        !           802:   _state = badbit;
        !           803: }
        !           804: 
        !           805: int istream::skip(int i)
        !           806: {
        !           807:     int old = (_flags & ios::skipws) != 0;
        !           808:     if (i)
        !           809:        _flags |= ios::skipws;
        !           810:     else
        !           811:        _flags &= ~ios::skipws;
        !           812:     return old;
        !           813: }
        !           814: #endif

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.