diff options
author | Benjamin Sugars <bsugars@canoe.ca> | 2001-05-02 06:53:11 -0400 |
---|---|---|
committer | Jarkko Hietaniemi <jhi@iki.fi> | 2001-05-02 15:21:08 +0000 |
commit | 09bf542c87dffb276bec96e979ba5437e7fc39b1 (patch) | |
tree | 1330d0bd902cbd162c1ec65fdf1d7a67b94407f7 /ext | |
parent | eea3e08689220c9a779c03d0f6b6668e3cb6d7fb (diff) | |
download | perl-09bf542c87dffb276bec96e979ba5437e7fc39b1.tar.gz |
Re: [PATCH] Allow appending on a PerlIO::Scalar
Message-ID: <Pine.LNX.4.21.0105021041380.1652-100000@marmot.rim.canoe.ca>
p4raw-id: //depot/perl@9959
Diffstat (limited to 'ext')
-rw-r--r-- | ext/PerlIO/Scalar/Scalar.xs | 35 |
1 files changed, 31 insertions, 4 deletions
diff --git a/ext/PerlIO/Scalar/Scalar.xs b/ext/PerlIO/Scalar/Scalar.xs index f22193e31d..9e9412ab0f 100644 --- a/ext/PerlIO/Scalar/Scalar.xs +++ b/ext/PerlIO/Scalar/Scalar.xs @@ -17,6 +17,7 @@ IV PerlIOScalar_pushed(PerlIO *f, const char *mode, SV *arg) { dTHX; + IV code; PerlIOScalar *s = PerlIOSelf(f,PerlIOScalar); /* If called (normally) via open() then arg is ref to scalar we are using, otherwise arg (from binmode presumably) is either NULL @@ -38,11 +39,12 @@ PerlIOScalar_pushed(PerlIO *f, const char *mode, SV *arg) s->var = newSVpvn("",0); } sv_upgrade(s->var,SVt_PV); - if (strnEQ(mode,"a",1)) + code = PerlIOBase_pushed(f,mode,Nullsv); + if ((PerlIOBase(f)->flags) & PERLIO_F_APPEND) s->posn = SvCUR(SvRV(arg)); else s->posn = 0; - return PerlIOBase_pushed(f,mode,Nullsv); + return code; } IV @@ -123,9 +125,34 @@ PerlIOScalar_write(PerlIO *f, const void *vbuf, Size_t count) { if (PerlIOBase(f)->flags & PERLIO_F_CANWRITE) { - return PerlIOScalar_unread(f,vbuf,count); + dTHX; + Off_t offset; + PerlIOScalar *s = PerlIOSelf(f,PerlIOScalar); + SV *sv = s->var; + char *dst; + if ((PerlIOBase(f)->flags) & PERLIO_F_APPEND) + { + dst = SvGROW(sv,SvCUR(sv)+count); + offset = SvCUR(sv); + s->posn = offset+count; + } + else + { + if ((s->posn+count) > SvCUR(sv)) + dst = SvGROW(sv,s->posn+count); + else + dst = SvPV_nolen(sv); + offset = s->posn; + s->posn += count; + } + Move(vbuf,dst+offset,count,char); + if (s->posn > SvCUR(sv)) + SvCUR_set(sv,s->posn); + SvPOK_on(s->var); + return count; } - return 0; + else + return 0; } IV |