PNG  IHDRX cHRMz&u0`:pQ<bKGD pHYsodtIME MeqIDATxw]Wug^Qd˶ 6`!N:!@xI~)%7%@Bh&`lnjVF29gΨ4E$|>cɚ{gk= %,a KX%,a KX%,a KX%,a KX%,a KX%,a KX%, b` ǟzeאfp]<!SJmɤY޲ڿ,%c ~ع9VH.!Ͳz&QynֺTkRR.BLHi٪:l;@(!MԴ=žI,:o&N'Kù\vRmJ雵֫AWic H@" !: Cé||]k-Ha oݜ:y F())u]aG7*JV@J415p=sZH!=!DRʯvɱh~V\}v/GKY$n]"X"}t@ xS76^[bw4dsce)2dU0 CkMa-U5tvLƀ~mlMwfGE/-]7XAƟ`׮g ewxwC4\[~7@O-Q( a*XGƒ{ ՟}$_y3tĐƤatgvێi|K=uVyrŲlLӪuܿzwk$m87k( `múcE)"@rK( z4$D; 2kW=Xb$V[Ru819קR~qloѱDyįݎ*mxw]y5e4K@ЃI0A D@"BDk_)N\8͜9dz"fK0zɿvM /.:2O{ Nb=M=7>??Zuo32 DLD@D| &+֎C #B8ַ`bOb $D#ͮҪtx]%`ES`Ru[=¾!@Od37LJ0!OIR4m]GZRJu$‡c=%~s@6SKy?CeIh:[vR@Lh | (BhAMy=݃  G"'wzn޺~8ԽSh ~T*A:xR[ܹ?X[uKL_=fDȊ؂p0}7=D$Ekq!/t.*2ʼnDbŞ}DijYaȲ(""6HA;:LzxQ‘(SQQ}*PL*fc\s `/d'QXW, e`#kPGZuŞuO{{wm[&NBTiiI0bukcA9<4@SӊH*؎4U/'2U5.(9JuDfrޱtycU%j(:RUbArLֺN)udA':uGQN"-"Is.*+k@ `Ojs@yU/ H:l;@yyTn}_yw!VkRJ4P)~y#)r,D =ě"Q]ci'%HI4ZL0"MJy 8A{ aN<8D"1#IJi >XjX֔#@>-{vN!8tRݻ^)N_╗FJEk]CT՟ YP:_|H1@ CBk]yKYp|og?*dGvzنzӴzjֺNkC~AbZƷ`.H)=!QͷVTT(| u78y֮}|[8-Vjp%2JPk[}ԉaH8Wpqhwr:vWª<}l77_~{s۴V+RCģ%WRZ\AqHifɤL36: #F:p]Bq/z{0CU6ݳEv_^k7'>sq*+kH%a`0ԣisqにtү04gVgW΂iJiS'3w.w}l6MC2uԯ|>JF5`fV5m`Y**Db1FKNttu]4ccsQNnex/87+}xaUW9y>ͯ骵G{䩓Գ3+vU}~jJ.NFRD7<aJDB1#ҳgSb,+CS?/ VG J?|?,2#M9}B)MiE+G`-wo߫V`fio(}S^4e~V4bHOYb"b#E)dda:'?}׮4繏`{7Z"uny-?ǹ;0MKx{:_pÚmFמ:F " .LFQLG)Q8qN q¯¯3wOvxDb\. BKD9_NN &L:4D{mm o^tֽ:q!ƥ}K+<"m78N< ywsard5+вz~mnG)=}lYݧNj'QJS{S :UYS-952?&O-:W}(!6Mk4+>A>j+i|<<|;ر^߉=HE|V#F)Emm#}/"y GII웻Jі94+v뾧xu~5C95~ūH>c@덉pʃ1/4-A2G%7>m;–Y,cyyaln" ?ƻ!ʪ<{~h~i y.zZB̃/,雋SiC/JFMmBH&&FAbϓO^tubbb_hZ{_QZ-sύodFgO(6]TJA˯#`۶ɟ( %$&+V'~hiYy>922 Wp74Zkq+Ovn錄c>8~GqܲcWꂎz@"1A.}T)uiW4="jJ2W7mU/N0gcqܗOO}?9/wìXžΏ0 >֩(V^Rh32!Hj5`;O28؇2#ݕf3 ?sJd8NJ@7O0 b־?lldщ̡&|9C.8RTWwxWy46ah嘦mh٤&l zCy!PY?: CJyв]dm4ǜҐR޻RլhX{FƯanшQI@x' ao(kUUuxW_Ñ줮[w8 FRJ(8˼)_mQ _!RJhm=!cVmm ?sFOnll6Qk}alY}; "baӌ~M0w,Ggw2W:G/k2%R,_=u`WU R.9T"v,<\Ik޽/2110Ӿxc0gyC&Ny޽JҢrV6N ``یeA16"J³+Rj*;BϜkZPJaÍ<Jyw:NP8/D$ 011z֊Ⱳ3ι֘k1V_"h!JPIΣ'ɜ* aEAd:ݺ>y<}Lp&PlRfTb1]o .2EW\ͮ]38؋rTJsǏP@芎sF\> P^+dYJLbJ C-xϐn> ι$nj,;Ǖa FU *择|h ~izť3ᤓ`K'-f tL7JK+vf2)V'-sFuB4i+m+@My=O҈0"|Yxoj,3]:cо3 $#uŘ%Y"y죯LebqtҢVzq¼X)~>4L׶m~[1_k?kxֺQ`\ |ٛY4Ѯr!)N9{56(iNq}O()Em]=F&u?$HypWUeB\k]JɩSع9 Zqg4ZĊo oMcjZBU]B\TUd34ݝ~:7ڶSUsB0Z3srx 7`:5xcx !qZA!;%͚7&P H<WL!džOb5kF)xor^aujƍ7 Ǡ8/p^(L>ὴ-B,{ۇWzֺ^k]3\EE@7>lYBȝR.oHnXO/}sB|.i@ɥDB4tcm,@ӣgdtJ!lH$_vN166L__'Z)y&kH;:,Y7=J 9cG) V\hjiE;gya~%ks_nC~Er er)muuMg2;֫R)Md) ,¶ 2-wr#F7<-BBn~_(o=KO㭇[Xv eN_SMgSҐ BS헃D%g_N:/pe -wkG*9yYSZS.9cREL !k}<4_Xs#FmҶ:7R$i,fi!~' # !6/S6y@kZkZcX)%5V4P]VGYq%H1!;e1MV<!ϐHO021Dp= HMs~~a)ަu7G^];git!Frl]H/L$=AeUvZE4P\.,xi {-~p?2b#amXAHq)MWǾI_r`S Hz&|{ +ʖ_= (YS(_g0a03M`I&'9vl?MM+m~}*xT۲(fY*V4x@29s{DaY"toGNTO+xCAO~4Ϳ;p`Ѫ:>Ҵ7K 3}+0 387x\)a"/E>qpWB=1 ¨"MP(\xp߫́A3+J] n[ʼnӼaTbZUWb={~2ooKױӰp(CS\S筐R*JغV&&"FA}J>G֐p1ٸbk7 ŘH$JoN <8s^yk_[;gy-;߉DV{c B yce% aJhDȶ 2IdйIB/^n0tNtџdcKj4϶v~- CBcgqx9= PJ) dMsjpYB] GD4RDWX +h{y`,3ꊕ$`zj*N^TP4L:Iz9~6s) Ga:?y*J~?OrMwP\](21sZUD ?ܟQ5Q%ggW6QdO+\@ ̪X'GxN @'4=ˋ+*VwN ne_|(/BDfj5(Dq<*tNt1х!MV.C0 32b#?n0pzj#!38}޴o1KovCJ`8ŗ_"]] rDUy޲@ Ȗ-;xџ'^Y`zEd?0„ DAL18IS]VGq\4o !swV7ˣι%4FѮ~}6)OgS[~Q vcYbL!wG3 7띸*E Pql8=jT\꘿I(z<[6OrR8ºC~ډ]=rNl[g|v TMTղb-o}OrP^Q]<98S¤!k)G(Vkwyqyr޽Nv`N/e p/~NAOk \I:G6]4+K;j$R:Mi #*[AȚT,ʰ,;N{HZTGMoּy) ]%dHء9Պ䠬|<45,\=[bƟ8QXeB3- &dҩ^{>/86bXmZ]]yޚN[(WAHL$YAgDKp=5GHjU&99v簪C0vygln*P)9^͞}lMuiH!̍#DoRBn9l@ xA/_v=ȺT{7Yt2N"4!YN`ae >Q<XMydEB`VU}u]嫇.%e^ánE87Mu\t`cP=AD/G)sI"@MP;)]%fH9'FNsj1pVhY&9=0pfuJ&gޤx+k:!r˭wkl03׼Ku C &ѓYt{.O.zҏ z}/tf_wEp2gvX)GN#I ݭ߽v/ .& и(ZF{e"=V!{zW`, ]+LGz"(UJp|j( #V4, 8B 0 9OkRrlɱl94)'VH9=9W|>PS['G(*I1==C<5"Pg+x'K5EMd؞Af8lG ?D FtoB[je?{k3zQ vZ;%Ɠ,]E>KZ+T/ EJxOZ1i #T<@ I}q9/t'zi(EMqw`mYkU6;[t4DPeckeM;H}_g pMww}k6#H㶏+b8雡Sxp)&C $@'b,fPߑt$RbJ'vznuS ~8='72_`{q纶|Q)Xk}cPz9p7O:'|G~8wx(a 0QCko|0ASD>Ip=4Q, d|F8RcU"/KM opKle M3#i0c%<7׿p&pZq[TR"BpqauIp$ 8~Ĩ!8Սx\ւdT>>Z40ks7 z2IQ}ItԀ<-%S⍤};zIb$I 5K}Q͙D8UguWE$Jh )cu4N tZl+[]M4k8֦Zeq֮M7uIqG 1==tLtR,ƜSrHYt&QP윯Lg' I,3@P'}'R˪e/%-Auv·ñ\> vDJzlӾNv5:|K/Jb6KI9)Zh*ZAi`?S {aiVDԲuy5W7pWeQJk֤#5&V<̺@/GH?^τZL|IJNvI:'P=Ϛt"¨=cud S Q.Ki0 !cJy;LJR;G{BJy޺[^8fK6)=yʊ+(k|&xQ2`L?Ȓ2@Mf 0C`6-%pKpm')c$׻K5[J*U[/#hH!6acB JA _|uMvDyk y)6OPYjœ50VT K}cǻP[ $:]4MEA.y)|B)cf-A?(e|lɉ#P9V)[9t.EiQPDѠ3ϴ;E:+Օ t ȥ~|_N2,ZJLt4! %ա]u {+=p.GhNcŞQI?Nd'yeh n7zi1DB)1S | S#ًZs2|Ɛy$F SxeX{7Vl.Src3E℃Q>b6G ўYCmtկ~=K0f(=LrAS GN'ɹ9<\!a`)֕y[uՍ[09` 9 +57ts6}b4{oqd+J5fa/,97J#6yν99mRWxJyѡyu_TJc`~W>l^q#Ts#2"nD1%fS)FU w{ܯ R{ ˎ󅃏џDsZSQS;LV;7 Od1&1n$ N /.q3~eNɪ]E#oM~}v֯FڦwyZ=<<>Xo稯lfMFV6p02|*=tV!c~]fa5Y^Q_WN|Vs 0ҘދU97OI'N2'8N֭fgg-}V%y]U4 峧p*91#9U kCac_AFңĪy뚇Y_AiuYyTTYЗ-(!JFLt›17uTozc. S;7A&&<ԋ5y;Ro+:' *eYJkWR[@F %SHWP 72k4 qLd'J "zB6{AC0ƁA6U.'F3:Ȅ(9ΜL;D]m8ڥ9}dU "v!;*13Rg^fJyShyy5auA?ɩGHRjo^]׽S)Fm\toy 4WQS@mE#%5ʈfFYDX ~D5Ϡ9tE9So_aU4?Ѽm%&c{n>.KW1Tlb}:j uGi(JgcYj0qn+>) %\!4{LaJso d||u//P_y7iRJ߬nHOy) l+@$($VFIQ9%EeKʈU. ia&FY̒mZ=)+qqoQn >L!qCiDB;Y<%} OgBxB!ØuG)WG9y(Ą{_yesuZmZZey'Wg#C~1Cev@0D $a@˲(.._GimA:uyw֬%;@!JkQVM_Ow:P.s\)ot- ˹"`B,e CRtaEUP<0'}r3[>?G8xU~Nqu;Wm8\RIkբ^5@k+5(By'L&'gBJ3ݶ!/㮻w҅ yqPWUg<e"Qy*167΃sJ\oz]T*UQ<\FԎ`HaNmڜ6DysCask8wP8y9``GJ9lF\G g's Nn͵MLN֪u$| /|7=]O)6s !ĴAKh]q_ap $HH'\1jB^s\|- W1:=6lJBqjY^LsPk""`]w)󭃈,(HC ?䔨Y$Sʣ{4Z+0NvQkhol6C.婧/u]FwiVjZka&%6\F*Ny#8O,22+|Db~d ~Çwc N:FuuCe&oZ(l;@ee-+Wn`44AMK➝2BRՈt7g*1gph9N) *"TF*R(#'88pm=}X]u[i7bEc|\~EMn}P瘊J)K.0i1M6=7'_\kaZ(Th{K*GJyytw"IO-PWJk)..axӝ47"89Cc7ĐBiZx 7m!fy|ϿF9CbȩV 9V-՛^pV̌ɄS#Bv4-@]Vxt-Z, &ֺ*diؠ2^VXbs֔Ìl.jQ]Y[47gj=幽ex)A0ip׳ W2[ᎇhuE^~q흙L} #-b۸oFJ_QP3r6jr+"nfzRJTUqoaۍ /$d8Mx'ݓ= OՃ| )$2mcM*cЙj}f };n YG w0Ia!1Q.oYfr]DyISaP}"dIӗթO67jqR ҊƐƈaɤGG|h;t]䗖oSv|iZqX)oalv;۩meEJ\!8=$4QU4Xo&VEĊ YS^E#d,yX_> ۘ-e\ "Wa6uLĜZi`aD9.% w~mB(02G[6y.773a7 /=o7D)$Z 66 $bY^\CuP. (x'"J60׿Y:Oi;F{w佩b+\Yi`TDWa~|VH)8q/=9!g߆2Y)?ND)%?Ǐ`k/sn:;O299yB=a[Ng 3˲N}vLNy;*?x?~L&=xyӴ~}q{qE*IQ^^ͧvü{Huu=R|>JyUlZV, B~/YF!Y\u_ݼF{_C)LD]m {H 0ihhadd nUkf3oٺCvE\)QJi+֥@tDJkB$1!Đr0XQ|q?d2) Ӣ_}qv-< FŊ߫%roppVBwü~JidY4:}L6M7f٬F "?71<2#?Jyy4뷢<_a7_=Q E=S1И/9{+93֮E{ǂw{))?maÆm(uLE#lïZ  ~d];+]h j?!|$F}*"4(v'8s<ŏUkm7^7no1w2ؗ}TrͿEk>p'8OB7d7R(A 9.*Mi^ͳ; eeUwS+C)uO@ =Sy]` }l8^ZzRXj[^iUɺ$tj))<sbDJfg=Pk_{xaKo1:-uyG0M ԃ\0Lvuy'ȱc2Ji AdyVgVh!{]/&}}ċJ#%d !+87<;qN޼Nفl|1N:8ya  8}k¾+-$4FiZYÔXk*I&'@iI99)HSh4+2G:tGhS^繿 Kتm0 вDk}֚+QT4;sC}rՅE,8CX-e~>G&'9xpW,%Fh,Ry56Y–hW-(v_,? ; qrBk4-V7HQ;ˇ^Gv1JVV%,ik;D_W!))+BoS4QsTM;gt+ndS-~:11Sgv!0qRVh!"Ȋ(̦Yl.]PQWgٳE'`%W1{ndΗBk|Ž7ʒR~,lnoa&:ü$ 3<a[CBݮwt"o\ePJ=Hz"_c^Z.#ˆ*x z̝grY]tdkP*:97YľXyBkD4N.C_[;F9`8& !AMO c `@BA& Ost\-\NX+Xp < !bj3C&QL+*&kAQ=04}cC!9~820G'PC9xa!w&bo_1 Sw"ܱ V )Yl3+ס2KoXOx]"`^WOy :3GO0g;%Yv㐫(R/r (s } u B &FeYZh0y> =2<Ϟc/ -u= c&׭,.0"g"7 6T!vl#sc>{u/Oh Bᾈ)۴74]x7 gMӒ"d]U)}" v4co[ ɡs 5Gg=XR14?5A}D "b{0$L .\4y{_fe:kVS\\O]c^W52LSBDM! C3Dhr̦RtArx4&agaN3Cf<Ԉp4~ B'"1@.b_/xQ} _߃҉/gٓ2Qkqp0շpZ2fԫYz< 4L.Cyυι1t@鎫Fe sYfsF}^ V}N<_`p)alٶ "(XEAVZ<)2},:Ir*#m_YӼ R%a||EƼIJ,,+f"96r/}0jE/)s)cjW#w'Sʯ5<66lj$a~3Kʛy 2:cZ:Yh))+a߭K::N,Q F'qB]={.]h85C9cr=}*rk?vwV렵ٸW Rs%}rNAkDv|uFLBkWY YkX מ|)1!$#3%y?pF<@<Rr0}: }\J [5FRxY<9"SQdE(Q*Qʻ)q1E0B_O24[U'],lOb ]~WjHޏTQ5Syu wq)xnw8~)c 쫬gٲߠ H% k5dƝk> kEj,0% b"vi2Wس_CuK)K{n|>t{P1򨾜j>'kEkƗBg*H%'_aY6Bn!TL&ɌOb{c`'d^{t\i^[uɐ[}q0lM˕G:‚4kb祔c^:?bpg… +37stH:0}en6x˟%/<]BL&* 5&fK9Mq)/iyqtA%kUe[ڛKN]Ě^,"`/ s[EQQm?|XJ߅92m]G.E΃ח U*Cn.j_)Tѧj̿30ڇ!A0=͜ar I3$C^-9#|pk!)?7.x9 @OO;WƝZBFU keZ75F6Tc6"ZȚs2y/1 ʵ:u4xa`C>6Rb/Yм)^=+~uRd`/|_8xbB0?Ft||Z\##|K 0>>zxv8۴吅q 8ĥ)"6>~\8:qM}#͚'ĉ#p\׶ l#bA?)|g g9|8jP(cr,BwV (WliVxxᡁ@0Okn;ɥh$_ckCgriv}>=wGzβ KkBɛ[˪ !J)h&k2%07δt}!d<9;I&0wV/ v 0<H}L&8ob%Hi|޶o&h1L|u֦y~󛱢8fٲUsւ)0oiFx2}X[zVYr_;N(w]_4B@OanC?gĦx>мgx>ΛToZoOMp>40>V Oy V9iq!4 LN,ˢu{jsz]|"R޻&'ƚ{53ўFu(<٪9:΋]B;)B>1::8;~)Yt|0(pw2N%&X,URBK)3\zz&}ax4;ǟ(tLNg{N|Ǽ\G#C9g$^\}p?556]/RP.90 k,U8/u776s ʪ_01چ|\N 0VV*3H鴃J7iI!wG_^ypl}r*jɤSR 5QN@ iZ#1ٰy;_\3\BQQ x:WJv츟ٯ$"@6 S#qe딇(/P( Dy~TOϻ<4:-+F`0||;Xl-"uw$Цi󼕝mKʩorz"mϺ$F:~E'ҐvD\y?Rr8_He@ e~O,T.(ފR*cY^m|cVR[8 JҡSm!ΆԨb)RHG{?MpqrmN>߶Y)\p,d#xۆWY*,l6]v0h15M˙MS8+EdI='LBJIH7_9{Caз*Lq,dt >+~ّeʏ?xԕ4bBAŚjﵫ!'\Ը$WNvKO}ӽmSşذqsOy?\[,d@'73'j%kOe`1.g2"e =YIzS2|zŐƄa\U,dP;jhhhaxǶ?КZ՚.q SE+XrbOu%\GتX(H,N^~]JyEZQKceTQ]VGYqnah;y$cQahT&QPZ*iZ8UQQM.qo/T\7X"u?Mttl2Xq(IoW{R^ ux*SYJ! 4S.Jy~ BROS[V|žKNɛP(L6V^|cR7i7nZW1Fd@ Ara{詑|(T*dN]Ko?s=@ |_EvF]׍kR)eBJc" MUUbY6`~V޴dJKß&~'d3i WWWWWW
Current Directory: /usr/share/perl5/vendor_perl/IO
Viewing File: /usr/share/perl5/vendor_perl/IO/String.pm
package IO::String; # Copyright 1998-2005 Gisle Aas. # # This library is free software; you can redistribute it and/or # modify it under the same terms as Perl itself. require 5.005_03; use strict; use vars qw($VERSION $DEBUG $IO_CONSTANTS); $VERSION = "1.08"; # $Date: 2005/12/05 12:00:47 $ use Symbol (); sub new { my $class = shift; my $self = bless Symbol::gensym(), ref($class) || $class; tie *$self, $self; $self->open(@_); return $self; } sub open { my $self = shift; return $self->new(@_) unless ref($self); if (@_) { my $bufref = ref($_[0]) ? $_[0] : \$_[0]; $$bufref = "" unless defined $$bufref; *$self->{buf} = $bufref; } else { my $buf = ""; *$self->{buf} = \$buf; } *$self->{pos} = 0; *$self->{lno} = 0; return $self; } sub pad { my $self = shift; my $old = *$self->{pad}; *$self->{pad} = substr($_[0], 0, 1) if @_; return "\0" unless defined($old) && length($old); return $old; } sub dump { require Data::Dumper; my $self = shift; print Data::Dumper->Dump([$self], ['*self']); print Data::Dumper->Dump([*$self{HASH}], ['$self{HASH}']); return; } sub TIEHANDLE { print "TIEHANDLE @_\n" if $DEBUG; return $_[0] if ref($_[0]); my $class = shift; my $self = bless Symbol::gensym(), $class; $self->open(@_); return $self; } sub DESTROY { print "DESTROY @_\n" if $DEBUG; } sub close { my $self = shift; delete *$self->{buf}; delete *$self->{pos}; delete *$self->{lno}; undef *$self if $] eq "5.008"; # workaround for some bug return 1; } sub opened { my $self = shift; return defined *$self->{buf}; } sub binmode { my $self = shift; return 1 unless @_; # XXX don't know much about layers yet :-( return 0; } sub getc { my $self = shift; my $buf; return $buf if $self->read($buf, 1); return undef; } sub ungetc { my $self = shift; $self->setpos($self->getpos() - 1); return 1; } sub eof { my $self = shift; return length(${*$self->{buf}}) <= *$self->{pos}; } sub print { my $self = shift; if (defined $\) { if (defined $,) { $self->write(join($,, @_).$\); } else { $self->write(join("",@_).$\); } } else { if (defined $,) { $self->write(join($,, @_)); } else { $self->write(join("",@_)); } } return 1; } *printflush = \*print; sub printf { my $self = shift; print "PRINTF(@_)\n" if $DEBUG; my $fmt = shift; $self->write(sprintf($fmt, @_)); return 1; } my($SEEK_SET, $SEEK_CUR, $SEEK_END); sub _init_seek_constants { if ($IO_CONSTANTS) { require IO::Handle; $SEEK_SET = &IO::Handle::SEEK_SET; $SEEK_CUR = &IO::Handle::SEEK_CUR; $SEEK_END = &IO::Handle::SEEK_END; } else { $SEEK_SET = 0; $SEEK_CUR = 1; $SEEK_END = 2; } } sub seek { my($self,$off,$whence) = @_; my $buf = *$self->{buf} || return 0; my $len = length($$buf); my $pos = *$self->{pos}; _init_seek_constants() unless defined $SEEK_SET; if ($whence == $SEEK_SET) { $pos = $off } elsif ($whence == $SEEK_CUR) { $pos += $off } elsif ($whence == $SEEK_END) { $pos = $len + $off } else { die "Bad whence ($whence)" } print "SEEK(POS=$pos,OFF=$off,LEN=$len)\n" if $DEBUG; $pos = 0 if $pos < 0; $self->truncate($pos) if $pos > $len; # extend file *$self->{pos} = $pos; return 1; } sub pos { my $self = shift; my $old = *$self->{pos}; if (@_) { my $pos = shift || 0; my $buf = *$self->{buf}; my $len = $buf ? length($$buf) : 0; $pos = $len if $pos > $len; *$self->{pos} = $pos; } return $old; } sub getpos { shift->pos; } *sysseek = \&seek; *setpos = \&pos; *tell = \&getpos; sub getline { my $self = shift; my $buf = *$self->{buf} || return; my $len = length($$buf); my $pos = *$self->{pos}; return if $pos >= $len; unless (defined $/) { # slurp *$self->{pos} = $len; return substr($$buf, $pos); } unless (length $/) { # paragraph mode # XXX slow&lazy implementation using getc() my $para = ""; my $eol = 0; my $c; while (defined($c = $self->getc)) { if ($c eq "\n") { $eol++; next if $eol > 2; } elsif ($eol > 1) { $self->ungetc($c); last; } else { $eol = 0; } $para .= $c; } return $para; # XXX wantarray } my $idx = index($$buf,$/,$pos); if ($idx < 0) { # return rest of it *$self->{pos} = $len; $. = ++ *$self->{lno}; return substr($$buf, $pos); } $len = $idx - $pos + length($/); *$self->{pos} += $len; $. = ++ *$self->{lno}; return substr($$buf, $pos, $len); } sub getlines { die "getlines() called in scalar context\n" unless wantarray; my $self = shift; my($line, @lines); push(@lines, $line) while defined($line = $self->getline); return @lines; } sub READLINE { goto &getlines if wantarray; goto &getline; } sub input_line_number { my $self = shift; my $old = *$self->{lno}; *$self->{lno} = shift if @_; return $old; } sub truncate { my $self = shift; my $len = shift || 0; my $buf = *$self->{buf}; if (length($$buf) >= $len) { substr($$buf, $len) = ''; *$self->{pos} = $len if $len < *$self->{pos}; } else { $$buf .= ($self->pad x ($len - length($$buf))); } return 1; } sub read { my $self = shift; my $buf = *$self->{buf}; return undef unless $buf; my $pos = *$self->{pos}; my $rem = length($$buf) - $pos; my $len = $_[1]; $len = $rem if $len > $rem; return undef if $len < 0; if (@_ > 2) { # read offset substr($_[0],$_[2]) = substr($$buf, $pos, $len); } else { $_[0] = substr($$buf, $pos, $len); } *$self->{pos} += $len; return $len; } sub write { my $self = shift; my $buf = *$self->{buf}; return unless $buf; my $pos = *$self->{pos}; my $slen = length($_[0]); my $len = $slen; my $off = 0; if (@_ > 1) { $len = $_[1] if $_[1] < $len; if (@_ > 2) { $off = $_[2] || 0; die "Offset outside string" if $off > $slen; if ($off < 0) { $off += $slen; die "Offset outside string" if $off < 0; } my $rem = $slen - $off; $len = $rem if $rem < $len; } } substr($$buf, $pos, $len) = substr($_[0], $off, $len); *$self->{pos} += $len; return $len; } *sysread = \&read; *syswrite = \&write; sub stat { my $self = shift; return unless $self->opened; return 1 unless wantarray; my $len = length ${*$self->{buf}}; return ( undef, undef, # dev, ino 0666, # filemode 1, # links $>, # user id $), # group id undef, # device id $len, # size undef, # atime undef, # mtime undef, # ctime 512, # blksize int(($len+511)/512) # blocks ); } sub FILENO { return undef; # XXX perlfunc says this means the file is closed } sub blocking { my $self = shift; my $old = *$self->{blocking} || 0; *$self->{blocking} = shift if @_; return $old; } my $notmuch = sub { return }; *fileno = $notmuch; *error = $notmuch; *clearerr = $notmuch; *sync = $notmuch; *flush = $notmuch; *setbuf = $notmuch; *setvbuf = $notmuch; *untaint = $notmuch; *autoflush = $notmuch; *fcntl = $notmuch; *ioctl = $notmuch; *GETC = \&getc; *PRINT = \&print; *PRINTF = \&printf; *READ = \&read; *WRITE = \&write; *SEEK = \&seek; *TELL = \&getpos; *EOF = \&eof; *CLOSE = \&close; *BINMODE = \&binmode; sub string_ref { my $self = shift; return *$self->{buf}; } *sref = \&string_ref; 1; __END__ =head1 NAME IO::String - Emulate file interface for in-core strings =head1 SYNOPSIS use IO::String; $io = IO::String->new; $io = IO::String->new($var); tie *IO, 'IO::String'; # read data <$io>; $io->getline; read($io, $buf, 100); # write data print $io "string\n"; $io->print(@data); syswrite($io, $buf, 100); select $io; printf "Some text %s\n", $str; # seek $pos = $io->getpos; $io->setpos(0); # rewind $io->seek(-30, -1); seek($io, 0, 0); =head1 DESCRIPTION The C<IO::String> module provides the C<IO::File> interface for in-core strings. An C<IO::String> object can be attached to a string, and makes it possible to use the normal file operations for reading or writing data, as well as for seeking to various locations of the string. This is useful when you want to use a library module that only provides an interface to file handles on data that you have in a string variable. Note that perl-5.8 and better has built-in support for "in memory" files, which are set up by passing a reference instead of a filename to the open() call. The reason for using this module is that it makes the code backwards compatible with older versions of Perl. The C<IO::String> module provides an interface compatible with C<IO::File> as distributed with F<IO-1.20>, but the following methods are not available: new_from_fd, fdopen, format_write, format_page_number, format_lines_per_page, format_lines_left, format_name, format_top_name. The following methods are specific to the C<IO::String> class: =over 4 =item $io = IO::String->new =item $io = IO::String->new( $string ) The constructor returns a newly-created C<IO::String> object. It takes an optional argument, which is the string to read from or write into. If no $string argument is given, then an internal buffer (initially empty) is allocated. The C<IO::String> object returned is tied to itself. This means that you can use most Perl I/O built-ins on it too: readline, <>, getc, print, printf, syswrite, sysread, close. =item $io->open =item $io->open( $string ) Attaches an existing IO::String object to some other $string, or allocates a new internal buffer (if no argument is given). The position is reset to 0. =item $io->string_ref Returns a reference to the string that is attached to the C<IO::String> object. Most useful when you let the C<IO::String> create an internal buffer to write into. =item $io->pad =item $io->pad( $char ) Specifies the padding to use if the string is extended by either the seek() or truncate() methods. It is a single character and defaults to "\0". =item $io->pos =item $io->pos( $newpos ) Yet another interface for reading and setting the current read/write position within the string (the normal getpos/setpos/tell/seek methods are also available). The pos() method always returns the old position, and if you pass it an argument it sets the new position. There is (deliberately) a difference between the setpos() and seek() methods in that seek() extends the string (with the specified padding) if you go to a location past the end, whereas setpos() just snaps back to the end. If truncate() is used to extend the string, then it works as seek(). =back =head1 BUGS In Perl versions < 5.6, the TIEHANDLE interface was incomplete. If you use such a Perl, then seek(), tell(), eof(), fileno(), binmode() will not do anything on an C<IO::String> handle. See L<perltie> for details. =head1 SEE ALSO L<IO::File>, L<IO::Stringy>, L<perlfunc/open> =head1 COPYRIGHT Copyright 1998-2005 Gisle Aas. This library is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut