This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
remove double typeglob deref (suggested by RonaldWS <ronaldws@aol.com>)
[perl5.git] / pp.c
CommitLineData
a0d0e21e 1/* pp.c
79072805 2 *
9607fc9c 3 * Copyright (c) 1991-1997, Larry Wall
79072805 4 *
a0d0e21e
LW
5 * You may distribute under the terms of either the GNU General Public
6 * License or the Artistic License, as specified in the README file.
79072805 7 *
a0d0e21e
LW
8 */
9
10/*
11 * "It's a big house this, and very peculiar. Always a bit more to discover,
12 * and no knowing what you'll find around a corner. And Elves, sir!" --Samwise
13 */
79072805
LW
14
15#include "EXTERN.h"
16#include "perl.h"
17
36477c24 18/*
ef2d312d
TH
19 * The compiler on Concurrent CX/UX systems has a subtle bug which only
20 * seems to show up when compiling pp.c - it generates the wrong double
21 * precision constant value for (double)UV_MAX when used inline in the body
22 * of the code below, so this makes a static variable up front (which the
23 * compiler seems to get correct) and uses it in place of UV_MAX below.
24 */
25#ifdef CXUX_BROKEN_CONSTANT_CONVERT
26static double UV_MAX_cxux = ((double)UV_MAX);
8ec5e241 27#endif
ef2d312d
TH
28
29/*
36477c24 30 * Types used in bitwise operations.
31 *
32 * Normally we'd just use IV and UV. However, some hardware and
33 * software combinations (e.g. Alpha and current OSF/1) don't have a
34 * floating-point type to use for NV that has adequate bits to fully
35 * hold an IV/UV. (In other words, sizeof(long) == sizeof(double).)
36 *
96e4d5b1 37 * It just so happens that "int" is the right size almost everywhere.
36477c24 38 */
39typedef int IBW;
40typedef unsigned UBW;
41
96e4d5b1 42/*
43 * Mask used after bitwise operations.
44 *
45 * There is at least one realm (Cray word machines) that doesn't
46 * have an integral type (except char) small enough to be represented
47 * in a double without loss; that is, it has no 32-bit type.
48 */
6ee623d5 49#if LONGSIZE > 4 && defined(_CRAY) && !defined(_CRAYMPP)
46fc3d4c 50# define BW_BITS 32
51# define BW_MASK ((1 << BW_BITS) - 1)
52# define BW_SIGN (1 << (BW_BITS - 1))
96e4d5b1 53# define BWi(i) (((i) & BW_SIGN) ? ((i) | ~BW_MASK) : ((i) & BW_MASK))
54# define BWu(u) ((u) & BW_MASK)
55#else
56# define BWi(i) (i)
57# define BWu(u) (u)
58#endif
59
60/*
61 * Offset for integer pack/unpack.
62 *
63 * On architectures where I16 and I32 aren't really 16 and 32 bits,
64 * which for now are all Crays, pack and unpack have to play games.
65 */
66
67/*
68 * These values are required for portability of pack() output.
69 * If they're not right on your machine, then pack() and unpack()
70 * wouldn't work right anyway; you'll need to apply the Cray hack.
71 * (I'd like to check them with #if, but you can't use sizeof() in
dc45a647
MB
72 * the preprocessor.) --???
73 */
74/*
75 The appropriate SHORTSIZE, INTSIZE, LONGSIZE, and LONGLONGSIZE
76 defines are now in config.h. --Andy Dougherty April 1998
96e4d5b1 77 */
78#define SIZE16 2
79#define SIZE32 4
80
81#if BYTEORDER > 0xFFFF && defined(_CRAY) && !defined(_CRAYMPP)
82# if BYTEORDER == 0x12345678
83# define OFF16(p) (char*)(p)
84# define OFF32(p) (char*)(p)
85# else
86# if BYTEORDER == 0x87654321
87# define OFF16(p) ((char*)(p) + (sizeof(U16) - SIZE16))
88# define OFF32(p) ((char*)(p) + (sizeof(U32) - SIZE32))
89# else
90 }}}} bad cray byte order
91# endif
92# endif
93# define COPY16(s,p) (*(p) = 0, Copy(s, OFF16(p), SIZE16, char))
94# define COPY32(s,p) (*(p) = 0, Copy(s, OFF32(p), SIZE32, char))
95# define CAT16(sv,p) sv_catpvn(sv, OFF16(p), SIZE16)
96# define CAT32(sv,p) sv_catpvn(sv, OFF32(p), SIZE32)
97#else
98# define COPY16(s,p) Copy(s, p, SIZE16, char)
99# define COPY32(s,p) Copy(s, p, SIZE32, char)
100# define CAT16(sv,p) sv_catpvn(sv, (char*)(p), SIZE16)
101# define CAT32(sv,p) sv_catpvn(sv, (char*)(p), SIZE32)
102#endif
103
76e3520e 104#ifndef PERL_OBJECT
71be2cbc 105static void doencodes _((SV* sv, char* s, I32 len));
93dc8474
CS
106static SV* refto _((SV* sv));
107static U32 seed _((void));
76e3520e 108#endif
93dc8474 109
a0d0e21e 110/* variations on pp_null */
79072805 111
8ac85365
NIS
112#ifdef I_UNISTD
113#include <unistd.h>
114#endif
dfe9444c
AD
115
116/* XXX I can't imagine anyone who doesn't have this actually _needs_
117 it, since pid_t is an integral type.
118 --AD 2/20/1998
119*/
120#ifdef NEED_GETPID_PROTO
121extern Pid_t getpid (void);
8ac85365
NIS
122#endif
123
93a17b20
LW
124PP(pp_stub)
125{
4e35701f 126 djSP;
54310121 127 if (GIMME_V == G_SCALAR)
3280af22 128 XPUSHs(&PL_sv_undef);
93a17b20
LW
129 RETURN;
130}
131
79072805
LW
132PP(pp_scalar)
133{
134 return NORMAL;
135}
136
137/* Pushy stuff. */
138
93a17b20
LW
139PP(pp_padav)
140{
4e35701f 141 djSP; dTARGET;
533c011a
NIS
142 if (PL_op->op_private & OPpLVAL_INTRO)
143 SAVECLEARSV(PL_curpad[PL_op->op_targ]);
85e6fe83 144 EXTEND(SP, 1);
533c011a 145 if (PL_op->op_flags & OPf_REF) {
85e6fe83 146 PUSHs(TARG);
93a17b20 147 RETURN;
85e6fe83
LW
148 }
149 if (GIMME == G_ARRAY) {
150 I32 maxarg = AvFILL((AV*)TARG) + 1;
151 EXTEND(SP, maxarg);
93965878
NIS
152 if (SvMAGICAL(TARG)) {
153 U32 i;
154 for (i=0; i < maxarg; i++) {
155 SV **svp = av_fetch((AV*)TARG, i, FALSE);
3280af22 156 SP[i+1] = (svp) ? *svp : &PL_sv_undef;
93965878
NIS
157 }
158 }
159 else {
160 Copy(AvARRAY((AV*)TARG), SP+1, maxarg, SV*);
161 }
85e6fe83
LW
162 SP += maxarg;
163 }
164 else {
165 SV* sv = sv_newmortal();
166 I32 maxarg = AvFILL((AV*)TARG) + 1;
167 sv_setiv(sv, maxarg);
168 PUSHs(sv);
169 }
170 RETURN;
93a17b20
LW
171}
172
173PP(pp_padhv)
174{
4e35701f 175 djSP; dTARGET;
54310121 176 I32 gimme;
177
93a17b20 178 XPUSHs(TARG);
533c011a
NIS
179 if (PL_op->op_private & OPpLVAL_INTRO)
180 SAVECLEARSV(PL_curpad[PL_op->op_targ]);
181 if (PL_op->op_flags & OPf_REF)
93a17b20 182 RETURN;
54310121 183 gimme = GIMME_V;
184 if (gimme == G_ARRAY) {
a0d0e21e 185 RETURNOP(do_kv(ARGS));
85e6fe83 186 }
54310121 187 else if (gimme == G_SCALAR) {
85e6fe83 188 SV* sv = sv_newmortal();
46fc3d4c 189 if (HvFILL((HV*)TARG))
190 sv_setpvf(sv, "%ld/%ld",
191 (long)HvFILL((HV*)TARG), (long)HvMAX((HV*)TARG) + 1);
85e6fe83
LW
192 else
193 sv_setiv(sv, 0);
194 SETs(sv);
85e6fe83 195 }
54310121 196 RETURN;
93a17b20
LW
197}
198
ed6116ce
LW
199PP(pp_padany)
200{
201 DIE("NOT IMPL LINE %d",__LINE__);
202}
203
79072805
LW
204/* Translations. */
205
206PP(pp_rv2gv)
207{
4e35701f 208 djSP; dTOPss;
8ec5e241 209
ed6116ce 210 if (SvROK(sv)) {
a0d0e21e 211 wasref:
f5284f61
IZ
212 tryAMAGICunDEREF(to_gv);
213
ed6116ce 214 sv = SvRV(sv);
b1dadf13 215 if (SvTYPE(sv) == SVt_PVIO) {
216 GV *gv = (GV*) sv_newmortal();
217 gv_init(gv, 0, "", 0, 0);
218 GvIOp(gv) = (IO *)sv;
3e3baf6d 219 (void)SvREFCNT_inc(sv);
b1dadf13 220 sv = (SV*) gv;
221 } else if (SvTYPE(sv) != SVt_PVGV)
a0d0e21e 222 DIE("Not a GLOB reference");
79072805
LW
223 }
224 else {
93a17b20 225 if (SvTYPE(sv) != SVt_PVGV) {
748a9306 226 char *sym;
2d8e6c8d 227 STRLEN n_a;
748a9306 228
a0d0e21e
LW
229 if (SvGMAGICAL(sv)) {
230 mg_get(sv);
231 if (SvROK(sv))
232 goto wasref;
233 }
234 if (!SvOK(sv)) {
533c011a
NIS
235 if (PL_op->op_flags & OPf_REF ||
236 PL_op->op_private & HINT_STRICT_REFS)
22c35a8c 237 DIE(PL_no_usym, "a symbol");
599cee73 238 if (ckWARN(WARN_UNINITIALIZED))
22c35a8c 239 warner(WARN_UNINITIALIZED, PL_warn_uninit);
a0d0e21e
LW
240 RETSETUNDEF;
241 }
2d8e6c8d 242 sym = SvPV(sv, n_a);
533c011a 243 if (PL_op->op_private & HINT_STRICT_REFS)
22c35a8c 244 DIE(PL_no_symref, sym, "a symbol");
748a9306 245 sv = (SV*)gv_fetchpv(sym, TRUE, SVt_PVGV);
93a17b20 246 }
79072805 247 }
533c011a
NIS
248 if (PL_op->op_private & OPpLVAL_INTRO)
249 save_gp((GV*)sv, !(PL_op->op_flags & OPf_SPECIAL));
79072805
LW
250 SETs(sv);
251 RETURN;
252}
253
79072805
LW
254PP(pp_rv2sv)
255{
4e35701f 256 djSP; dTOPss;
79072805 257
ed6116ce 258 if (SvROK(sv)) {
a0d0e21e 259 wasref:
f5284f61
IZ
260 tryAMAGICunDEREF(to_sv);
261
ed6116ce 262 sv = SvRV(sv);
79072805
LW
263 switch (SvTYPE(sv)) {
264 case SVt_PVAV:
265 case SVt_PVHV:
266 case SVt_PVCV:
a0d0e21e 267 DIE("Not a SCALAR reference");
79072805
LW
268 }
269 }
270 else {
f12c7020 271 GV *gv = (GV*)sv;
748a9306 272 char *sym;
2d8e6c8d 273 STRLEN n_a;
748a9306 274
463ee0b2 275 if (SvTYPE(gv) != SVt_PVGV) {
a0d0e21e
LW
276 if (SvGMAGICAL(sv)) {
277 mg_get(sv);
278 if (SvROK(sv))
279 goto wasref;
280 }
281 if (!SvOK(sv)) {
533c011a
NIS
282 if (PL_op->op_flags & OPf_REF ||
283 PL_op->op_private & HINT_STRICT_REFS)
22c35a8c 284 DIE(PL_no_usym, "a SCALAR");
599cee73 285 if (ckWARN(WARN_UNINITIALIZED))
22c35a8c 286 warner(WARN_UNINITIALIZED, PL_warn_uninit);
a0d0e21e
LW
287 RETSETUNDEF;
288 }
2d8e6c8d 289 sym = SvPV(sv, n_a);
533c011a 290 if (PL_op->op_private & HINT_STRICT_REFS)
22c35a8c 291 DIE(PL_no_symref, sym, "a SCALAR");
f12c7020 292 gv = (GV*)gv_fetchpv(sym, TRUE, SVt_PV);
463ee0b2
LW
293 }
294 sv = GvSV(gv);
a0d0e21e 295 }
533c011a
NIS
296 if (PL_op->op_flags & OPf_MOD) {
297 if (PL_op->op_private & OPpLVAL_INTRO)
a0d0e21e 298 sv = save_scalar((GV*)TOPs);
533c011a
NIS
299 else if (PL_op->op_private & OPpDEREF)
300 vivify_ref(sv, PL_op->op_private & OPpDEREF);
79072805 301 }
a0d0e21e 302 SETs(sv);
79072805
LW
303 RETURN;
304}
305
306PP(pp_av2arylen)
307{
4e35701f 308 djSP;
79072805
LW
309 AV *av = (AV*)TOPs;
310 SV *sv = AvARYLEN(av);
311 if (!sv) {
312 AvARYLEN(av) = sv = NEWSV(0,0);
313 sv_upgrade(sv, SVt_IV);
314 sv_magic(sv, (SV*)av, '#', Nullch, 0);
315 }
316 SETs(sv);
317 RETURN;
318}
319
a0d0e21e
LW
320PP(pp_pos)
321{
4e35701f 322 djSP; dTARGET; dPOPss;
8ec5e241 323
533c011a 324 if (PL_op->op_flags & OPf_MOD) {
5f05dabc 325 if (SvTYPE(TARG) < SVt_PVLV) {
326 sv_upgrade(TARG, SVt_PVLV);
327 sv_magic(TARG, Nullsv, '.', Nullch, 0);
328 }
329
330 LvTYPE(TARG) = '.';
6ff81951
GS
331 if (LvTARG(TARG) != sv) {
332 if (LvTARG(TARG))
333 SvREFCNT_dec(LvTARG(TARG));
334 LvTARG(TARG) = SvREFCNT_inc(sv);
335 }
a0d0e21e
LW
336 PUSHs(TARG); /* no SvSETMAGIC */
337 RETURN;
338 }
339 else {
8ec5e241 340 MAGIC* mg;
a0d0e21e
LW
341
342 if (SvTYPE(sv) >= SVt_PVMG && SvMAGIC(sv)) {
343 mg = mg_find(sv, 'g');
565764a8 344 if (mg && mg->mg_len >= 0) {
a0ed51b3
LW
345 I32 i = mg->mg_len;
346 if (IN_UTF8)
347 sv_pos_b2u(sv, &i);
348 PUSHi(i + PL_curcop->cop_arybase);
a0d0e21e
LW
349 RETURN;
350 }
351 }
352 RETPUSHUNDEF;
353 }
354}
355
79072805
LW
356PP(pp_rv2cv)
357{
4e35701f 358 djSP;
79072805
LW
359 GV *gv;
360 HV *stash;
8990e307 361
4633a7c4
LW
362 /* We usually try to add a non-existent subroutine in case of AUTOLOAD. */
363 /* (But not in defined().) */
533c011a 364 CV *cv = sv_2cv(TOPs, &stash, &gv, !(PL_op->op_flags & OPf_SPECIAL));
07055b4c
CS
365 if (cv) {
366 if (CvCLONE(cv))
367 cv = (CV*)sv_2mortal((SV*)cv_clone(cv));
368 }
369 else
3280af22 370 cv = (CV*)&PL_sv_undef;
79072805
LW
371 SETs((SV*)cv);
372 RETURN;
373}
374
c07a80fd 375PP(pp_prototype)
376{
4e35701f 377 djSP;
c07a80fd 378 CV *cv;
379 HV *stash;
380 GV *gv;
381 SV *ret;
382
3280af22 383 ret = &PL_sv_undef;
b6c543e3
IZ
384 if (SvPOK(TOPs) && SvCUR(TOPs) >= 7) {
385 char *s = SvPVX(TOPs);
386 if (strnEQ(s, "CORE::", 6)) {
387 int code;
388
389 code = keyword(s + 6, SvCUR(TOPs) - 6);
390 if (code < 0) { /* Overridable. */
391#define MAX_ARGS_OP ((sizeof(I32) - 1) * 2)
392 int i = 0, n = 0, seen_question = 0;
393 I32 oa;
394 char str[ MAX_ARGS_OP * 2 + 2 ]; /* One ';', one '\0' */
395
396 while (i < MAXO) { /* The slow way. */
22c35a8c
GS
397 if (strEQ(s + 6, PL_op_name[i])
398 || strEQ(s + 6, PL_op_desc[i]))
399 {
b6c543e3 400 goto found;
22c35a8c 401 }
b6c543e3
IZ
402 i++;
403 }
404 goto nonesuch; /* Should not happen... */
405 found:
22c35a8c 406 oa = PL_opargs[i] >> OASHIFT;
b6c543e3
IZ
407 while (oa) {
408 if (oa & OA_OPTIONAL) {
409 seen_question = 1;
410 str[n++] = ';';
411 } else if (seen_question)
412 goto set; /* XXXX system, exec */
413 if ((oa & (OA_OPTIONAL - 1)) >= OA_AVREF
414 && (oa & (OA_OPTIONAL - 1)) <= OA_HVREF) {
415 str[n++] = '\\';
416 }
417 /* What to do with R ((un)tie, tied, (sys)read, recv)? */
418 str[n++] = ("?$@@%&*$")[oa & (OA_OPTIONAL - 1)];
419 oa = oa >> 4;
420 }
421 str[n++] = '\0';
422 ret = sv_2mortal(newSVpv(str, n - 1));
423 } else if (code) /* Non-Overridable */
424 goto set;
425 else { /* None such */
426 nonesuch:
427 croak("Cannot find an opnumber for \"%s\"", s+6);
428 }
429 }
430 }
c07a80fd 431 cv = sv_2cv(TOPs, &stash, &gv, FALSE);
5f05dabc 432 if (cv && SvPOK(cv))
433 ret = sv_2mortal(newSVpv(SvPVX(cv), SvCUR(cv)));
b6c543e3 434 set:
c07a80fd 435 SETs(ret);
436 RETURN;
437}
438
a0d0e21e
LW
439PP(pp_anoncode)
440{
4e35701f 441 djSP;
533c011a 442 CV* cv = (CV*)PL_curpad[PL_op->op_targ];
a5f75d66 443 if (CvCLONE(cv))
b355b4e0 444 cv = (CV*)sv_2mortal((SV*)cv_clone(cv));
5f05dabc 445 EXTEND(SP,1);
748a9306 446 PUSHs((SV*)cv);
a0d0e21e
LW
447 RETURN;
448}
449
450PP(pp_srefgen)
79072805 451{
4e35701f 452 djSP;
71be2cbc 453 *SP = refto(*SP);
79072805 454 RETURN;
8ec5e241 455}
a0d0e21e
LW
456
457PP(pp_refgen)
458{
4e35701f 459 djSP; dMARK;
a0d0e21e 460 if (GIMME != G_ARRAY) {
5f0b1d4e
GS
461 if (++MARK <= SP)
462 *MARK = *SP;
463 else
3280af22 464 *MARK = &PL_sv_undef;
5f0b1d4e
GS
465 *MARK = refto(*MARK);
466 SP = MARK;
467 RETURN;
a0d0e21e 468 }
bbce6d69 469 EXTEND_MORTAL(SP - MARK);
71be2cbc 470 while (++MARK <= SP)
471 *MARK = refto(*MARK);
a0d0e21e 472 RETURN;
79072805
LW
473}
474
76e3520e 475STATIC SV*
8ac85365 476refto(SV *sv)
71be2cbc 477{
478 SV* rv;
479
480 if (SvTYPE(sv) == SVt_PVLV && LvTYPE(sv) == 'y') {
481 if (LvTARGLEN(sv))
68dc0745 482 vivify_defelem(sv);
483 if (!(sv = LvTARG(sv)))
3280af22 484 sv = &PL_sv_undef;
71be2cbc 485 }
486 else if (SvPADTMP(sv))
487 sv = newSVsv(sv);
488 else {
489 SvTEMP_off(sv);
490 (void)SvREFCNT_inc(sv);
491 }
492 rv = sv_newmortal();
493 sv_upgrade(rv, SVt_RV);
494 SvRV(rv) = sv;
495 SvROK_on(rv);
496 return rv;
497}
498
79072805
LW
499PP(pp_ref)
500{
4e35701f 501 djSP; dTARGET;
463ee0b2 502 SV *sv;
79072805
LW
503 char *pv;
504
a0d0e21e 505 sv = POPs;
f12c7020 506
507 if (sv && SvGMAGICAL(sv))
8ec5e241 508 mg_get(sv);
f12c7020 509
a0d0e21e 510 if (!sv || !SvROK(sv))
4633a7c4 511 RETPUSHNO;
79072805 512
ed6116ce 513 sv = SvRV(sv);
a0d0e21e 514 pv = sv_reftype(sv,TRUE);
463ee0b2 515 PUSHp(pv, strlen(pv));
79072805
LW
516 RETURN;
517}
518
519PP(pp_bless)
520{
4e35701f 521 djSP;
463ee0b2 522 HV *stash;
79072805 523
463ee0b2 524 if (MAXARG == 1)
3280af22 525 stash = PL_curcop->cop_stash;
7b8d334a
GS
526 else {
527 SV *ssv = POPs;
528 STRLEN len;
529 char *ptr = SvPV(ssv,len);
599cee73
PM
530 if (ckWARN(WARN_UNSAFE) && len == 0)
531 warner(WARN_UNSAFE,
532 "Explicit blessing to '' (assuming package main)");
7b8d334a
GS
533 stash = gv_stashpvn(ptr, len, TRUE);
534 }
a0d0e21e 535
5d3fdfeb 536 (void)sv_bless(TOPs, stash);
79072805
LW
537 RETURN;
538}
539
fb73857a 540PP(pp_gelem)
541{
542 GV *gv;
543 SV *sv;
76e3520e 544 SV *tmpRef;
fb73857a 545 char *elem;
4e35701f 546 djSP;
2d8e6c8d
GS
547 STRLEN n_a;
548
fb73857a 549 sv = POPs;
2d8e6c8d 550 elem = SvPV(sv, n_a);
fb73857a 551 gv = (GV*)POPs;
76e3520e 552 tmpRef = Nullsv;
fb73857a 553 sv = Nullsv;
554 switch (elem ? *elem : '\0')
555 {
556 case 'A':
557 if (strEQ(elem, "ARRAY"))
76e3520e 558 tmpRef = (SV*)GvAV(gv);
fb73857a 559 break;
560 case 'C':
561 if (strEQ(elem, "CODE"))
76e3520e 562 tmpRef = (SV*)GvCVu(gv);
fb73857a 563 break;
564 case 'F':
565 if (strEQ(elem, "FILEHANDLE")) /* XXX deprecate in 5.005 */
76e3520e 566 tmpRef = (SV*)GvIOp(gv);
fb73857a 567 break;
568 case 'G':
569 if (strEQ(elem, "GLOB"))
76e3520e 570 tmpRef = (SV*)gv;
fb73857a 571 break;
572 case 'H':
573 if (strEQ(elem, "HASH"))
76e3520e 574 tmpRef = (SV*)GvHV(gv);
fb73857a 575 break;
576 case 'I':
577 if (strEQ(elem, "IO"))
76e3520e 578 tmpRef = (SV*)GvIOp(gv);
fb73857a 579 break;
580 case 'N':
581 if (strEQ(elem, "NAME"))
582 sv = newSVpv(GvNAME(gv), GvNAMELEN(gv));
583 break;
584 case 'P':
585 if (strEQ(elem, "PACKAGE"))
586 sv = newSVpv(HvNAME(GvSTASH(gv)), 0);
587 break;
588 case 'S':
589 if (strEQ(elem, "SCALAR"))
76e3520e 590 tmpRef = GvSV(gv);
fb73857a 591 break;
592 }
76e3520e
GS
593 if (tmpRef)
594 sv = newRV(tmpRef);
fb73857a 595 if (sv)
596 sv_2mortal(sv);
597 else
3280af22 598 sv = &PL_sv_undef;
fb73857a 599 XPUSHs(sv);
600 RETURN;
601}
602
a0d0e21e 603/* Pattern matching */
79072805 604
a0d0e21e 605PP(pp_study)
79072805 606{
4e35701f 607 djSP; dPOPss;
c277df42 608 register UNOP *unop = cUNOP;
a0d0e21e
LW
609 register unsigned char *s;
610 register I32 pos;
611 register I32 ch;
612 register I32 *sfirst;
613 register I32 *snext;
a0d0e21e
LW
614 STRLEN len;
615
3280af22 616 if (sv == PL_lastscream) {
1e422769 617 if (SvSCREAM(sv))
618 RETPUSHYES;
619 }
c07a80fd 620 else {
3280af22
NIS
621 if (PL_lastscream) {
622 SvSCREAM_off(PL_lastscream);
623 SvREFCNT_dec(PL_lastscream);
c07a80fd 624 }
3280af22 625 PL_lastscream = SvREFCNT_inc(sv);
c07a80fd 626 }
1e422769 627
628 s = (unsigned char*)(SvPV(sv, len));
629 pos = len;
630 if (pos <= 0)
631 RETPUSHNO;
3280af22
NIS
632 if (pos > PL_maxscream) {
633 if (PL_maxscream < 0) {
634 PL_maxscream = pos + 80;
635 New(301, PL_screamfirst, 256, I32);
636 New(302, PL_screamnext, PL_maxscream, I32);
79072805
LW
637 }
638 else {
3280af22
NIS
639 PL_maxscream = pos + pos / 4;
640 Renew(PL_screamnext, PL_maxscream, I32);
79072805 641 }
79072805 642 }
a0d0e21e 643
3280af22
NIS
644 sfirst = PL_screamfirst;
645 snext = PL_screamnext;
a0d0e21e
LW
646
647 if (!sfirst || !snext)
648 DIE("do_study: out of memory");
649
650 for (ch = 256; ch; --ch)
651 *sfirst++ = -1;
652 sfirst -= 256;
653
654 while (--pos >= 0) {
655 ch = s[pos];
656 if (sfirst[ch] >= 0)
657 snext[pos] = sfirst[ch] - pos;
658 else
659 snext[pos] = -pos;
660 sfirst[ch] = pos;
79072805
LW
661 }
662
c07a80fd 663 SvSCREAM_on(sv);
464e2e8a 664 sv_magic(sv, Nullsv, 'g', Nullch, 0); /* piggyback on m//g magic */
1e422769 665 RETPUSHYES;
79072805
LW
666}
667
a0d0e21e 668PP(pp_trans)
79072805 669{
4e35701f 670 djSP; dTARG;
a0d0e21e
LW
671 SV *sv;
672
533c011a 673 if (PL_op->op_flags & OPf_STACKED)
a0d0e21e 674 sv = POPs;
79072805 675 else {
54b9620d 676 sv = DEFSV;
a0d0e21e 677 EXTEND(SP,1);
79072805 678 }
adbc6bb1 679 TARG = sv_newmortal();
4757a243 680 PUSHi(do_trans(sv));
a0d0e21e 681 RETURN;
79072805
LW
682}
683
a0d0e21e 684/* Lvalue operators. */
79072805 685
a0d0e21e
LW
686PP(pp_schop)
687{
4e35701f 688 djSP; dTARGET;
a0d0e21e
LW
689 do_chop(TARG, TOPs);
690 SETTARG;
691 RETURN;
79072805
LW
692}
693
a0d0e21e 694PP(pp_chop)
79072805 695{
4e35701f 696 djSP; dMARK; dTARGET;
a0d0e21e
LW
697 while (SP > MARK)
698 do_chop(TARG, POPs);
699 PUSHTARG;
700 RETURN;
79072805
LW
701}
702
a0d0e21e 703PP(pp_schomp)
79072805 704{
4e35701f 705 djSP; dTARGET;
a0d0e21e
LW
706 SETi(do_chomp(TOPs));
707 RETURN;
79072805
LW
708}
709
a0d0e21e 710PP(pp_chomp)
79072805 711{
4e35701f 712 djSP; dMARK; dTARGET;
a0d0e21e 713 register I32 count = 0;
8ec5e241 714
a0d0e21e
LW
715 while (SP > MARK)
716 count += do_chomp(POPs);
717 PUSHi(count);
718 RETURN;
79072805
LW
719}
720
a0d0e21e 721PP(pp_defined)
463ee0b2 722{
4e35701f 723 djSP;
a0d0e21e
LW
724 register SV* sv;
725
726 sv = POPs;
727 if (!sv || !SvANY(sv))
728 RETPUSHNO;
729 switch (SvTYPE(sv)) {
730 case SVt_PVAV:
6051dbdb 731 if (AvMAX(sv) >= 0 || SvGMAGICAL(sv) || (SvRMAGICAL(sv) && mg_find(sv,'P')))
a0d0e21e
LW
732 RETPUSHYES;
733 break;
734 case SVt_PVHV:
6051dbdb 735 if (HvARRAY(sv) || SvGMAGICAL(sv) || (SvRMAGICAL(sv) && mg_find(sv,'P')))
a0d0e21e
LW
736 RETPUSHYES;
737 break;
738 case SVt_PVCV:
739 if (CvROOT(sv) || CvXSUB(sv))
740 RETPUSHYES;
741 break;
742 default:
743 if (SvGMAGICAL(sv))
744 mg_get(sv);
745 if (SvOK(sv))
746 RETPUSHYES;
747 }
748 RETPUSHNO;
463ee0b2
LW
749}
750
a0d0e21e
LW
751PP(pp_undef)
752{
4e35701f 753 djSP;
a0d0e21e
LW
754 SV *sv;
755
533c011a 756 if (!PL_op->op_private) {
774d564b 757 EXTEND(SP, 1);
a0d0e21e 758 RETPUSHUNDEF;
774d564b 759 }
79072805 760
a0d0e21e
LW
761 sv = POPs;
762 if (!sv)
763 RETPUSHUNDEF;
85e6fe83 764
a0d0e21e 765 if (SvTHINKFIRST(sv)) {
a3f914c5
GS
766 if (SvREADONLY(sv)) {
767 dTHR;
768 if (PL_curcop != &PL_compiling)
769 croak(PL_no_modify);
770 }
a0d0e21e
LW
771 if (SvROK(sv))
772 sv_unref(sv);
85e6fe83
LW
773 }
774
a0d0e21e
LW
775 switch (SvTYPE(sv)) {
776 case SVt_NULL:
777 break;
778 case SVt_PVAV:
779 av_undef((AV*)sv);
780 break;
781 case SVt_PVHV:
782 hv_undef((HV*)sv);
783 break;
784 case SVt_PVCV:
599cee73
PM
785 if (ckWARN(WARN_UNSAFE) && cv_const_sv((CV*)sv))
786 warner(WARN_UNSAFE, "Constant subroutine %s undefined",
54310121 787 CvANON((CV*)sv) ? "(anonymous)" : GvENAME(CvGV((CV*)sv)));
9607fc9c 788 /* FALL THROUGH */
789 case SVt_PVFM:
09280a33
CS
790 { GV* gv = (GV*)SvREFCNT_inc(CvGV((CV*)sv));
791 cv_undef((CV*)sv);
792 CvGV((CV*)sv) = gv; } /* let user-undef'd sub keep its identity */
a0d0e21e 793 break;
8e07c86e 794 case SVt_PVGV:
44a8e56a 795 if (SvFAKE(sv))
3280af22 796 SvSetMagicSV(sv, &PL_sv_undef);
20408e3c
GS
797 else {
798 GP *gp;
799 gp_free((GV*)sv);
800 Newz(602, gp, 1, GP);
801 GvGP(sv) = gp_ref(gp);
802 GvSV(sv) = NEWSV(72,0);
3280af22 803 GvLINE(sv) = PL_curcop->cop_line;
20408e3c
GS
804 GvEGV(sv) = (GV*)sv;
805 GvMULTI_on(sv);
806 }
44a8e56a 807 break;
a0d0e21e 808 default:
1e422769 809 if (SvTYPE(sv) >= SVt_PV && SvPVX(sv) && SvLEN(sv)) {
4633a7c4
LW
810 (void)SvOOK_off(sv);
811 Safefree(SvPVX(sv));
812 SvPV_set(sv, Nullch);
813 SvLEN_set(sv, 0);
a0d0e21e 814 }
4633a7c4
LW
815 (void)SvOK_off(sv);
816 SvSETMAGIC(sv);
79072805 817 }
a0d0e21e
LW
818
819 RETPUSHUNDEF;
79072805
LW
820}
821
a0d0e21e 822PP(pp_predec)
79072805 823{
4e35701f 824 djSP;
68dc0745 825 if (SvREADONLY(TOPs) || SvTYPE(TOPs) > SVt_PVLV)
22c35a8c 826 croak(PL_no_modify);
55497cff 827 if (SvIOK(TOPs) && !SvNOK(TOPs) && !SvPOK(TOPs) &&
828 SvIVX(TOPs) != IV_MIN)
829 {
748a9306 830 --SvIVX(TOPs);
55497cff 831 SvFLAGS(TOPs) &= ~(SVp_NOK|SVp_POK);
748a9306
LW
832 }
833 else
834 sv_dec(TOPs);
a0d0e21e
LW
835 SvSETMAGIC(TOPs);
836 return NORMAL;
837}
79072805 838
a0d0e21e
LW
839PP(pp_postinc)
840{
4e35701f 841 djSP; dTARGET;
68dc0745 842 if (SvREADONLY(TOPs) || SvTYPE(TOPs) > SVt_PVLV)
22c35a8c 843 croak(PL_no_modify);
a0d0e21e 844 sv_setsv(TARG, TOPs);
55497cff 845 if (SvIOK(TOPs) && !SvNOK(TOPs) && !SvPOK(TOPs) &&
846 SvIVX(TOPs) != IV_MAX)
847 {
748a9306 848 ++SvIVX(TOPs);
55497cff 849 SvFLAGS(TOPs) &= ~(SVp_NOK|SVp_POK);
748a9306
LW
850 }
851 else
852 sv_inc(TOPs);
a0d0e21e
LW
853 SvSETMAGIC(TOPs);
854 if (!SvOK(TARG))
855 sv_setiv(TARG, 0);
856 SETs(TARG);
857 return NORMAL;
858}
79072805 859
a0d0e21e
LW
860PP(pp_postdec)
861{
4e35701f 862 djSP; dTARGET;
68dc0745 863 if(SvREADONLY(TOPs) || SvTYPE(TOPs) > SVt_PVLV)
22c35a8c 864 croak(PL_no_modify);
a0d0e21e 865 sv_setsv(TARG, TOPs);
55497cff 866 if (SvIOK(TOPs) && !SvNOK(TOPs) && !SvPOK(TOPs) &&
867 SvIVX(TOPs) != IV_MIN)
868 {
748a9306 869 --SvIVX(TOPs);
55497cff 870 SvFLAGS(TOPs) &= ~(SVp_NOK|SVp_POK);
748a9306
LW
871 }
872 else
873 sv_dec(TOPs);
a0d0e21e
LW
874 SvSETMAGIC(TOPs);
875 SETs(TARG);
876 return NORMAL;
877}
79072805 878
a0d0e21e
LW
879/* Ordinary operators. */
880
881PP(pp_pow)
882{
8ec5e241 883 djSP; dATARGET; tryAMAGICbin(pow,opASSIGN);
a0d0e21e
LW
884 {
885 dPOPTOPnnrl;
886 SETn( pow( left, right) );
887 RETURN;
93a17b20 888 }
a0d0e21e
LW
889}
890
891PP(pp_multiply)
892{
8ec5e241 893 djSP; dATARGET; tryAMAGICbin(mult,opASSIGN);
a0d0e21e
LW
894 {
895 dPOPTOPnnrl;
896 SETn( left * right );
897 RETURN;
79072805 898 }
a0d0e21e
LW
899}
900
901PP(pp_divide)
902{
8ec5e241 903 djSP; dATARGET; tryAMAGICbin(div,opASSIGN);
a0d0e21e 904 {
77676ba1 905 dPOPPOPnnrl;
7a4c00b4 906 double value;
907 if (right == 0.0)
a0d0e21e
LW
908 DIE("Illegal division by zero");
909#ifdef SLOPPYDIVIDE
910 /* insure that 20./5. == 4. */
911 {
7a4c00b4 912 IV k;
913 if ((double)I_V(left) == left &&
914 (double)I_V(right) == right &&
915 (k = I_V(left)/I_V(right))*I_V(right) == I_V(left)) {
a0d0e21e
LW
916 value = k;
917 } else {
7a4c00b4 918 value = left / right;
79072805 919 }
a0d0e21e
LW
920 }
921#else
7a4c00b4 922 value = left / right;
a0d0e21e
LW
923#endif
924 PUSHn( value );
925 RETURN;
79072805 926 }
a0d0e21e
LW
927}
928
929PP(pp_modulo)
930{
76e3520e 931 djSP; dATARGET; tryAMAGICbin(modulo,opASSIGN);
a0d0e21e 932 {
68dc0745 933 UV left;
934 UV right;
beb18505
CS
935 bool left_neg;
936 bool right_neg;
68dc0745 937 UV ans;
a0d0e21e 938
68dc0745 939 if (SvIOK(TOPs) && !SvNOK(TOPs) && !SvPOK(TOPs)) {
940 IV i = SvIVX(POPs);
beb18505 941 right = (right_neg = (i < 0)) ? -i : i;
68dc0745 942 }
943 else {
944 double n = POPn;
beb18505 945 right = U_V((right_neg = (n < 0)) ? -n : n);
68dc0745 946 }
a0d0e21e 947
36477c24 948 if (SvIOK(TOPs) && !SvNOK(TOPs) && !SvPOK(TOPs)) {
68dc0745 949 IV i = SvIVX(POPs);
beb18505 950 left = (left_neg = (i < 0)) ? -i : i;
36477c24 951 }
a0d0e21e 952 else {
68dc0745 953 double n = POPn;
beb18505 954 left = U_V((left_neg = (n < 0)) ? -n : n);
a0d0e21e 955 }
68dc0745 956
957 if (!right)
958 DIE("Illegal modulus zero");
959
960 ans = left % right;
beb18505 961 if ((left_neg != right_neg) && ans)
68dc0745 962 ans = right - ans;
beb18505 963 if (right_neg) {
3e3baf6d
TB
964 /* XXX may warn: unary minus operator applied to unsigned type */
965 /* could change -foo to be (~foo)+1 instead */
4e35701f
NIS
966 if (ans <= ~((UV)IV_MAX)+1)
967 sv_setiv(TARG, ~ans+1);
beb18505
CS
968 else
969 sv_setnv(TARG, -(double)ans);
970 }
971 else
972 sv_setuv(TARG, ans);
973 PUSHTARG;
a0d0e21e 974 RETURN;
79072805 975 }
a0d0e21e 976}
79072805 977
a0d0e21e
LW
978PP(pp_repeat)
979{
4e35701f 980 djSP; dATARGET; tryAMAGICbin(repeat,opASSIGN);
748a9306 981 {
a0d0e21e 982 register I32 count = POPi;
533c011a 983 if (GIMME == G_ARRAY && PL_op->op_private & OPpREPEAT_DOLIST) {
a0d0e21e
LW
984 dMARK;
985 I32 items = SP - MARK;
986 I32 max;
79072805 987
a0d0e21e
LW
988 max = items * count;
989 MEXTEND(MARK, max);
990 if (count > 1) {
991 while (SP > MARK) {
992 if (*SP)
993 SvTEMP_off((*SP));
994 SP--;
79072805 995 }
a0d0e21e
LW
996 MARK++;
997 repeatcpy((char*)(MARK + items), (char*)MARK,
998 items * sizeof(SV*), count - 1);
999 SP += max;
79072805 1000 }
a0d0e21e
LW
1001 else if (count <= 0)
1002 SP -= items;
79072805 1003 }
a0d0e21e
LW
1004 else { /* Note: mark already snarfed by pp_list */
1005 SV *tmpstr;
1006 STRLEN len;
1007
1008 tmpstr = POPs;
1009 if (TARG == tmpstr && SvTHINKFIRST(tmpstr)) {
3280af22 1010 if (SvREADONLY(tmpstr) && PL_curcop != &PL_compiling)
a0d0e21e
LW
1011 DIE("Can't x= to readonly value");
1012 if (SvROK(tmpstr))
1013 sv_unref(tmpstr);
93a17b20 1014 }
a0d0e21e
LW
1015 SvSetSV(TARG, tmpstr);
1016 SvPV_force(TARG, len);
8ebc5c01 1017 if (count != 1) {
1018 if (count < 1)
1019 SvCUR_set(TARG, 0);
1020 else {
1021 SvGROW(TARG, (count * len) + 1);
a0d0e21e 1022 repeatcpy(SvPVX(TARG) + len, SvPVX(TARG), len, count - 1);
8ebc5c01 1023 SvCUR(TARG) *= count;
7a4c00b4 1024 }
a0d0e21e 1025 *SvEND(TARG) = '\0';
a0d0e21e 1026 }
8ebc5c01 1027 (void)SvPOK_only(TARG);
a0d0e21e 1028 PUSHTARG;
79072805 1029 }
a0d0e21e 1030 RETURN;
748a9306 1031 }
a0d0e21e 1032}
79072805 1033
a0d0e21e
LW
1034PP(pp_subtract)
1035{
8ec5e241 1036 djSP; dATARGET; tryAMAGICbin(subtr,opASSIGN);
a0d0e21e 1037 {
7a4c00b4 1038 dPOPTOPnnrl_ul;
a0d0e21e
LW
1039 SETn( left - right );
1040 RETURN;
79072805 1041 }
a0d0e21e 1042}
79072805 1043
a0d0e21e
LW
1044PP(pp_left_shift)
1045{
8ec5e241 1046 djSP; dATARGET; tryAMAGICbin(lshift,opASSIGN);
a0d0e21e 1047 {
36477c24 1048 IBW shift = POPi;
533c011a 1049 if (PL_op->op_private & HINT_INTEGER) {
36477c24 1050 IBW i = TOPi;
46fc3d4c 1051 i = BWi(i) << shift;
96e4d5b1 1052 SETi(BWi(i));
ff68c719 1053 }
1054 else {
36477c24 1055 UBW u = TOPu;
96e4d5b1 1056 u <<= shift;
1057 SETu(BWu(u));
ff68c719 1058 }
55497cff 1059 RETURN;
79072805 1060 }
a0d0e21e 1061}
79072805 1062
a0d0e21e
LW
1063PP(pp_right_shift)
1064{
8ec5e241 1065 djSP; dATARGET; tryAMAGICbin(rshift,opASSIGN);
a0d0e21e 1066 {
36477c24 1067 IBW shift = POPi;
533c011a 1068 if (PL_op->op_private & HINT_INTEGER) {
36477c24 1069 IBW i = TOPi;
46fc3d4c 1070 i = BWi(i) >> shift;
96e4d5b1 1071 SETi(BWi(i));
ff68c719 1072 }
1073 else {
36477c24 1074 UBW u = TOPu;
96e4d5b1 1075 u >>= shift;
1076 SETu(BWu(u));
ff68c719 1077 }
a0d0e21e 1078 RETURN;
93a17b20 1079 }
79072805
LW
1080}
1081
a0d0e21e 1082PP(pp_lt)
79072805 1083{
8ec5e241 1084 djSP; tryAMAGICbinSET(lt,0);
a0d0e21e
LW
1085 {
1086 dPOPnv;
54310121 1087 SETs(boolSV(TOPn < value));
a0d0e21e 1088 RETURN;
79072805 1089 }
a0d0e21e 1090}
79072805 1091
a0d0e21e
LW
1092PP(pp_gt)
1093{
8ec5e241 1094 djSP; tryAMAGICbinSET(gt,0);
a0d0e21e
LW
1095 {
1096 dPOPnv;
54310121 1097 SETs(boolSV(TOPn > value));
a0d0e21e 1098 RETURN;
79072805 1099 }
a0d0e21e
LW
1100}
1101
1102PP(pp_le)
1103{
8ec5e241 1104 djSP; tryAMAGICbinSET(le,0);
a0d0e21e
LW
1105 {
1106 dPOPnv;
54310121 1107 SETs(boolSV(TOPn <= value));
a0d0e21e 1108 RETURN;
79072805 1109 }
a0d0e21e
LW
1110}
1111
1112PP(pp_ge)
1113{
8ec5e241 1114 djSP; tryAMAGICbinSET(ge,0);
a0d0e21e
LW
1115 {
1116 dPOPnv;
54310121 1117 SETs(boolSV(TOPn >= value));
a0d0e21e 1118 RETURN;
79072805 1119 }
a0d0e21e 1120}
79072805 1121
a0d0e21e
LW
1122PP(pp_ne)
1123{
8ec5e241 1124 djSP; tryAMAGICbinSET(ne,0);
a0d0e21e
LW
1125 {
1126 dPOPnv;
54310121 1127 SETs(boolSV(TOPn != value));
a0d0e21e
LW
1128 RETURN;
1129 }
79072805
LW
1130}
1131
a0d0e21e 1132PP(pp_ncmp)
79072805 1133{
8ec5e241 1134 djSP; dTARGET; tryAMAGICbin(ncmp,0);
a0d0e21e
LW
1135 {
1136 dPOPTOPnnrl;
1137 I32 value;
79072805 1138
ff0cee69 1139 if (left == right)
a0d0e21e 1140 value = 0;
a0d0e21e
LW
1141 else if (left < right)
1142 value = -1;
44a8e56a 1143 else if (left > right)
1144 value = 1;
1145 else {
3280af22 1146 SETs(&PL_sv_undef);
44a8e56a 1147 RETURN;
1148 }
a0d0e21e
LW
1149 SETi(value);
1150 RETURN;
79072805 1151 }
a0d0e21e 1152}
79072805 1153
a0d0e21e
LW
1154PP(pp_slt)
1155{
8ec5e241 1156 djSP; tryAMAGICbinSET(slt,0);
a0d0e21e
LW
1157 {
1158 dPOPTOPssrl;
533c011a 1159 int cmp = ((PL_op->op_private & OPpLOCALE)
bbce6d69 1160 ? sv_cmp_locale(left, right)
1161 : sv_cmp(left, right));
54310121 1162 SETs(boolSV(cmp < 0));
a0d0e21e
LW
1163 RETURN;
1164 }
79072805
LW
1165}
1166
a0d0e21e 1167PP(pp_sgt)
79072805 1168{
8ec5e241 1169 djSP; tryAMAGICbinSET(sgt,0);
a0d0e21e
LW
1170 {
1171 dPOPTOPssrl;
533c011a 1172 int cmp = ((PL_op->op_private & OPpLOCALE)
bbce6d69 1173 ? sv_cmp_locale(left, right)
1174 : sv_cmp(left, right));
54310121 1175 SETs(boolSV(cmp > 0));
a0d0e21e
LW
1176 RETURN;
1177 }
1178}
79072805 1179
a0d0e21e
LW
1180PP(pp_sle)
1181{
8ec5e241 1182 djSP; tryAMAGICbinSET(sle,0);
a0d0e21e
LW
1183 {
1184 dPOPTOPssrl;
533c011a 1185 int cmp = ((PL_op->op_private & OPpLOCALE)
bbce6d69 1186 ? sv_cmp_locale(left, right)
1187 : sv_cmp(left, right));
54310121 1188 SETs(boolSV(cmp <= 0));
a0d0e21e 1189 RETURN;
79072805 1190 }
79072805
LW
1191}
1192
a0d0e21e
LW
1193PP(pp_sge)
1194{
8ec5e241 1195 djSP; tryAMAGICbinSET(sge,0);
a0d0e21e
LW
1196 {
1197 dPOPTOPssrl;
533c011a 1198 int cmp = ((PL_op->op_private & OPpLOCALE)
bbce6d69 1199 ? sv_cmp_locale(left, right)
1200 : sv_cmp(left, right));
54310121 1201 SETs(boolSV(cmp >= 0));
a0d0e21e
LW
1202 RETURN;
1203 }
1204}
79072805 1205
36477c24 1206PP(pp_seq)
1207{
8ec5e241 1208 djSP; tryAMAGICbinSET(seq,0);
36477c24 1209 {
1210 dPOPTOPssrl;
54310121 1211 SETs(boolSV(sv_eq(left, right)));
a0d0e21e
LW
1212 RETURN;
1213 }
1214}
79072805 1215
a0d0e21e 1216PP(pp_sne)
79072805 1217{
8ec5e241 1218 djSP; tryAMAGICbinSET(sne,0);
a0d0e21e
LW
1219 {
1220 dPOPTOPssrl;
54310121 1221 SETs(boolSV(!sv_eq(left, right)));
a0d0e21e 1222 RETURN;
463ee0b2 1223 }
79072805
LW
1224}
1225
a0d0e21e 1226PP(pp_scmp)
79072805 1227{
4e35701f 1228 djSP; dTARGET; tryAMAGICbin(scmp,0);
a0d0e21e
LW
1229 {
1230 dPOPTOPssrl;
533c011a 1231 int cmp = ((PL_op->op_private & OPpLOCALE)
bbce6d69 1232 ? sv_cmp_locale(left, right)
1233 : sv_cmp(left, right));
1234 SETi( cmp );
a0d0e21e
LW
1235 RETURN;
1236 }
1237}
79072805 1238
55497cff 1239PP(pp_bit_and)
1240{
8ec5e241 1241 djSP; dATARGET; tryAMAGICbin(band,opASSIGN);
a0d0e21e
LW
1242 {
1243 dPOPTOPssrl;
4633a7c4 1244 if (SvNIOKp(left) || SvNIOKp(right)) {
533c011a 1245 if (PL_op->op_private & HINT_INTEGER) {
8ec5e241 1246 IBW value = SvIV(left) & SvIV(right);
96e4d5b1 1247 SETi(BWi(value));
36477c24 1248 }
1249 else {
8ec5e241 1250 UBW value = SvUV(left) & SvUV(right);
96e4d5b1 1251 SETu(BWu(value));
36477c24 1252 }
a0d0e21e
LW
1253 }
1254 else {
533c011a 1255 do_vop(PL_op->op_type, TARG, left, right);
a0d0e21e
LW
1256 SETTARG;
1257 }
1258 RETURN;
1259 }
1260}
79072805 1261
a0d0e21e
LW
1262PP(pp_bit_xor)
1263{
8ec5e241 1264 djSP; dATARGET; tryAMAGICbin(bxor,opASSIGN);
a0d0e21e
LW
1265 {
1266 dPOPTOPssrl;
4633a7c4 1267 if (SvNIOKp(left) || SvNIOKp(right)) {
533c011a 1268 if (PL_op->op_private & HINT_INTEGER) {
8ec5e241 1269 IBW value = (USE_LEFT(left) ? SvIV(left) : 0) ^ SvIV(right);
96e4d5b1 1270 SETi(BWi(value));
36477c24 1271 }
1272 else {
8ec5e241 1273 UBW value = (USE_LEFT(left) ? SvUV(left) : 0) ^ SvUV(right);
96e4d5b1 1274 SETu(BWu(value));
36477c24 1275 }
a0d0e21e
LW
1276 }
1277 else {
533c011a 1278 do_vop(PL_op->op_type, TARG, left, right);
a0d0e21e
LW
1279 SETTARG;
1280 }
1281 RETURN;
1282 }
1283}
79072805 1284
a0d0e21e
LW
1285PP(pp_bit_or)
1286{
8ec5e241 1287 djSP; dATARGET; tryAMAGICbin(bor,opASSIGN);
a0d0e21e
LW
1288 {
1289 dPOPTOPssrl;
4633a7c4 1290 if (SvNIOKp(left) || SvNIOKp(right)) {
533c011a 1291 if (PL_op->op_private & HINT_INTEGER) {
8ec5e241 1292 IBW value = (USE_LEFT(left) ? SvIV(left) : 0) | SvIV(right);
96e4d5b1 1293 SETi(BWi(value));
36477c24 1294 }
1295 else {
8ec5e241 1296 UBW value = (USE_LEFT(left) ? SvUV(left) : 0) | SvUV(right);
96e4d5b1 1297 SETu(BWu(value));
36477c24 1298 }
a0d0e21e
LW
1299 }
1300 else {
533c011a 1301 do_vop(PL_op->op_type, TARG, left, right);
a0d0e21e
LW
1302 SETTARG;
1303 }
1304 RETURN;
79072805 1305 }
a0d0e21e 1306}
79072805 1307
a0d0e21e
LW
1308PP(pp_negate)
1309{
4e35701f 1310 djSP; dTARGET; tryAMAGICun(neg);
a0d0e21e
LW
1311 {
1312 dTOPss;
4633a7c4
LW
1313 if (SvGMAGICAL(sv))
1314 mg_get(sv);
55497cff 1315 if (SvIOKp(sv) && !SvNOKp(sv) && !SvPOKp(sv) && SvIVX(sv) != IV_MIN)
1316 SETi(-SvIVX(sv));
1317 else if (SvNIOKp(sv))
a0d0e21e 1318 SETn(-SvNV(sv));
4633a7c4 1319 else if (SvPOKp(sv)) {
a0d0e21e
LW
1320 STRLEN len;
1321 char *s = SvPV(sv, len);
bbce6d69 1322 if (isIDFIRST(*s)) {
a0d0e21e
LW
1323 sv_setpvn(TARG, "-", 1);
1324 sv_catsv(TARG, sv);
79072805 1325 }
a0d0e21e
LW
1326 else if (*s == '+' || *s == '-') {
1327 sv_setsv(TARG, sv);
1328 *SvPV_force(TARG, len) = *s == '-' ? '+' : '-';
79072805 1329 }
b86a2fa7 1330 else if (IN_UTF8 && *(U8*)s >= 0xc0 && isIDFIRST_utf8((U8*)s)) {
834a4ddd
LW
1331 sv_setpvn(TARG, "-", 1);
1332 sv_catsv(TARG, sv);
1333 }
79072805 1334 else
a0d0e21e
LW
1335 sv_setnv(TARG, -SvNV(sv));
1336 SETTARG;
79072805 1337 }
4633a7c4
LW
1338 else
1339 SETn(-SvNV(sv));
79072805 1340 }
a0d0e21e 1341 RETURN;
79072805
LW
1342}
1343
a0d0e21e 1344PP(pp_not)
79072805 1345{
a0d0e21e 1346#ifdef OVERLOAD
4e35701f 1347 djSP; tryAMAGICunSET(not);
a0d0e21e 1348#endif /* OVERLOAD */
3280af22 1349 *PL_stack_sp = boolSV(!SvTRUE(*PL_stack_sp));
a0d0e21e 1350 return NORMAL;
79072805
LW
1351}
1352
a0d0e21e 1353PP(pp_complement)
79072805 1354{
8ec5e241 1355 djSP; dTARGET; tryAMAGICun(compl);
a0d0e21e
LW
1356 {
1357 dTOPss;
4633a7c4 1358 if (SvNIOKp(sv)) {
533c011a 1359 if (PL_op->op_private & HINT_INTEGER) {
36477c24 1360 IBW value = ~SvIV(sv);
96e4d5b1 1361 SETi(BWi(value));
36477c24 1362 }
1363 else {
1364 UBW value = ~SvUV(sv);
96e4d5b1 1365 SETu(BWu(value));
36477c24 1366 }
a0d0e21e
LW
1367 }
1368 else {
1369 register char *tmps;
1370 register long *tmpl;
55497cff 1371 register I32 anum;
a0d0e21e
LW
1372 STRLEN len;
1373
1374 SvSetSV(TARG, sv);
1375 tmps = SvPV_force(TARG, len);
1376 anum = len;
1377#ifdef LIBERAL
1378 for ( ; anum && (unsigned long)tmps % sizeof(long); anum--, tmps++)
1379 *tmps = ~*tmps;
1380 tmpl = (long*)tmps;
1381 for ( ; anum >= sizeof(long); anum -= sizeof(long), tmpl++)
1382 *tmpl = ~*tmpl;
1383 tmps = (char*)tmpl;
1384#endif
1385 for ( ; anum > 0; anum--, tmps++)
1386 *tmps = ~*tmps;
1387
1388 SETs(TARG);
1389 }
1390 RETURN;
1391 }
79072805
LW
1392}
1393
a0d0e21e
LW
1394/* integer versions of some of the above */
1395
a0d0e21e 1396PP(pp_i_multiply)
79072805 1397{
8ec5e241 1398 djSP; dATARGET; tryAMAGICbin(mult,opASSIGN);
a0d0e21e
LW
1399 {
1400 dPOPTOPiirl;
1401 SETi( left * right );
1402 RETURN;
1403 }
79072805
LW
1404}
1405
a0d0e21e 1406PP(pp_i_divide)
79072805 1407{
8ec5e241 1408 djSP; dATARGET; tryAMAGICbin(div,opASSIGN);
a0d0e21e
LW
1409 {
1410 dPOPiv;
1411 if (value == 0)
1412 DIE("Illegal division by zero");
1413 value = POPi / value;
1414 PUSHi( value );
1415 RETURN;
1416 }
79072805
LW
1417}
1418
a0d0e21e 1419PP(pp_i_modulo)
79072805 1420{
76e3520e 1421 djSP; dATARGET; tryAMAGICbin(modulo,opASSIGN);
79072805 1422 {
a0d0e21e 1423 dPOPTOPiirl;
aa306039
CS
1424 if (!right)
1425 DIE("Illegal modulus zero");
a0d0e21e
LW
1426 SETi( left % right );
1427 RETURN;
79072805 1428 }
79072805
LW
1429}
1430
a0d0e21e 1431PP(pp_i_add)
79072805 1432{
8ec5e241 1433 djSP; dATARGET; tryAMAGICbin(add,opASSIGN);
a0d0e21e
LW
1434 {
1435 dPOPTOPiirl;
1436 SETi( left + right );
1437 RETURN;
79072805 1438 }
79072805
LW
1439}
1440
a0d0e21e 1441PP(pp_i_subtract)
79072805 1442{
8ec5e241 1443 djSP; dATARGET; tryAMAGICbin(subtr,opASSIGN);
a0d0e21e
LW
1444 {
1445 dPOPTOPiirl;
1446 SETi( left - right );
1447 RETURN;
79072805 1448 }
79072805
LW
1449}
1450
a0d0e21e 1451PP(pp_i_lt)
79072805 1452{
8ec5e241 1453 djSP; tryAMAGICbinSET(lt,0);
a0d0e21e
LW
1454 {
1455 dPOPTOPiirl;
54310121 1456 SETs(boolSV(left < right));
a0d0e21e
LW
1457 RETURN;
1458 }
79072805
LW
1459}
1460
a0d0e21e 1461PP(pp_i_gt)
79072805 1462{
8ec5e241 1463 djSP; tryAMAGICbinSET(gt,0);
a0d0e21e
LW
1464 {
1465 dPOPTOPiirl;
54310121 1466 SETs(boolSV(left > right));
a0d0e21e
LW
1467 RETURN;
1468 }
79072805
LW
1469}
1470
a0d0e21e 1471PP(pp_i_le)
79072805 1472{
8ec5e241 1473 djSP; tryAMAGICbinSET(le,0);
a0d0e21e
LW
1474 {
1475 dPOPTOPiirl;
54310121 1476 SETs(boolSV(left <= right));
a0d0e21e 1477 RETURN;
85e6fe83 1478 }
79072805
LW
1479}
1480
a0d0e21e 1481PP(pp_i_ge)
79072805 1482{
8ec5e241 1483 djSP; tryAMAGICbinSET(ge,0);
a0d0e21e
LW
1484 {
1485 dPOPTOPiirl;
54310121 1486 SETs(boolSV(left >= right));
a0d0e21e
LW
1487 RETURN;
1488 }
79072805
LW
1489}
1490
a0d0e21e 1491PP(pp_i_eq)
79072805 1492{
8ec5e241 1493 djSP; tryAMAGICbinSET(eq,0);
a0d0e21e
LW
1494 {
1495 dPOPTOPiirl;
54310121 1496 SETs(boolSV(left == right));
a0d0e21e
LW
1497 RETURN;
1498 }
79072805
LW
1499}
1500
a0d0e21e 1501PP(pp_i_ne)
79072805 1502{
8ec5e241 1503 djSP; tryAMAGICbinSET(ne,0);
a0d0e21e
LW
1504 {
1505 dPOPTOPiirl;
54310121 1506 SETs(boolSV(left != right));
a0d0e21e
LW
1507 RETURN;
1508 }
79072805
LW
1509}
1510
a0d0e21e 1511PP(pp_i_ncmp)
79072805 1512{
8ec5e241 1513 djSP; dTARGET; tryAMAGICbin(ncmp,0);
a0d0e21e
LW
1514 {
1515 dPOPTOPiirl;
1516 I32 value;
79072805 1517
a0d0e21e 1518 if (left > right)
79072805 1519 value = 1;
a0d0e21e 1520 else if (left < right)
79072805 1521 value = -1;
a0d0e21e 1522 else
79072805 1523 value = 0;
a0d0e21e
LW
1524 SETi(value);
1525 RETURN;
79072805 1526 }
85e6fe83
LW
1527}
1528
1529PP(pp_i_negate)
1530{
4e35701f 1531 djSP; dTARGET; tryAMAGICun(neg);
85e6fe83
LW
1532 SETi(-TOPi);
1533 RETURN;
1534}
1535
79072805
LW
1536/* High falutin' math. */
1537
1538PP(pp_atan2)
1539{
8ec5e241 1540 djSP; dTARGET; tryAMAGICbin(atan2,0);
a0d0e21e
LW
1541 {
1542 dPOPTOPnnrl;
1543 SETn(atan2(left, right));
1544 RETURN;
1545 }
79072805
LW
1546}
1547
1548PP(pp_sin)
1549{
4e35701f 1550 djSP; dTARGET; tryAMAGICun(sin);
a0d0e21e
LW
1551 {
1552 double value;
1553 value = POPn;
1554 value = sin(value);
1555 XPUSHn(value);
1556 RETURN;
1557 }
79072805
LW
1558}
1559
1560PP(pp_cos)
1561{
4e35701f 1562 djSP; dTARGET; tryAMAGICun(cos);
a0d0e21e
LW
1563 {
1564 double value;
1565 value = POPn;
1566 value = cos(value);
1567 XPUSHn(value);
1568 RETURN;
1569 }
79072805
LW
1570}
1571
56cb0a1c
AD
1572/* Support Configure command-line overrides for rand() functions.
1573 After 5.005, perhaps we should replace this by Configure support
1574 for drand48(), random(), or rand(). For 5.005, though, maintain
1575 compatibility by calling rand() but allow the user to override it.
1576 See INSTALL for details. --Andy Dougherty 15 July 1998
1577*/
85ab1d1d
JH
1578/* Now it's after 5.005, and Configure supports drand48() and random(),
1579 in addition to rand(). So the overrides should not be needed any more.
1580 --Jarkko Hietaniemi 27 September 1998
1581 */
1582
1583#ifndef HAS_DRAND48_PROTO
1584extern double drand48 _((void));
56cb0a1c
AD
1585#endif
1586
79072805
LW
1587PP(pp_rand)
1588{
4e35701f 1589 djSP; dTARGET;
79072805
LW
1590 double value;
1591 if (MAXARG < 1)
1592 value = 1.0;
1593 else
1594 value = POPn;
1595 if (value == 0.0)
1596 value = 1.0;
80252599 1597 if (!PL_srand_called) {
85ab1d1d 1598 (void)seedDrand01((Rand_seed_t)seed());
80252599 1599 PL_srand_called = TRUE;
93dc8474 1600 }
85ab1d1d 1601 value *= Drand01();
79072805
LW
1602 XPUSHn(value);
1603 RETURN;
1604}
1605
1606PP(pp_srand)
1607{
4e35701f 1608 djSP;
93dc8474
CS
1609 UV anum;
1610 if (MAXARG < 1)
1611 anum = seed();
79072805 1612 else
93dc8474 1613 anum = POPu;
85ab1d1d 1614 (void)seedDrand01((Rand_seed_t)anum);
80252599 1615 PL_srand_called = TRUE;
79072805
LW
1616 EXTEND(SP, 1);
1617 RETPUSHYES;
1618}
1619
76e3520e 1620STATIC U32
8ac85365 1621seed(void)
93dc8474 1622{
54310121 1623 /*
1624 * This is really just a quick hack which grabs various garbage
1625 * values. It really should be a real hash algorithm which
1626 * spreads the effect of every input bit onto every output bit,
85ab1d1d 1627 * if someone who knows about such things would bother to write it.
54310121 1628 * Might be a good idea to add that function to CORE as well.
85ab1d1d 1629 * No numbers below come from careful analysis or anything here,
54310121 1630 * except they are primes and SEED_C1 > 1E6 to get a full-width
1631 * value from (tv_sec * SEED_C1 + tv_usec). The multipliers should
1632 * probably be bigger too.
1633 */
1634#if RANDBITS > 16
1635# define SEED_C1 1000003
1636#define SEED_C4 73819
1637#else
1638# define SEED_C1 25747
1639#define SEED_C4 20639
1640#endif
1641#define SEED_C2 3
1642#define SEED_C3 269
1643#define SEED_C5 26107
1644
e858de61 1645 dTHR;
73c60299
RS
1646#ifndef PERL_NO_DEV_RANDOM
1647 int fd;
1648#endif
93dc8474 1649 U32 u;
f12c7020 1650#ifdef VMS
1651# include <starlet.h>
43c92808
HF
1652 /* when[] = (low 32 bits, high 32 bits) of time since epoch
1653 * in 100-ns units, typically incremented ever 10 ms. */
93dc8474 1654 unsigned int when[2];
73c60299
RS
1655#else
1656# ifdef HAS_GETTIMEOFDAY
1657 struct timeval when;
1658# else
1659 Time_t when;
1660# endif
1661#endif
1662
1663/* This test is an escape hatch, this symbol isn't set by Configure. */
1664#ifndef PERL_NO_DEV_RANDOM
1665#ifndef PERL_RANDOM_DEVICE
1666 /* /dev/random isn't used by default because reads from it will block
1667 * if there isn't enough entropy available. You can compile with
1668 * PERL_RANDOM_DEVICE to it if you'd prefer Perl to block until there
1669 * is enough real entropy to fill the seed. */
1670# define PERL_RANDOM_DEVICE "/dev/urandom"
1671#endif
1672 fd = PerlLIO_open(PERL_RANDOM_DEVICE, 0);
1673 if (fd != -1) {
1674 if (PerlLIO_read(fd, &u, sizeof u) != sizeof u)
1675 u = 0;
1676 PerlLIO_close(fd);
1677 if (u)
1678 return u;
1679 }
1680#endif
1681
1682#ifdef VMS
93dc8474 1683 _ckvmssts(sys$gettim(when));
54310121 1684 u = (U32)SEED_C1 * when[0] + (U32)SEED_C2 * when[1];
f12c7020 1685#else
5f05dabc 1686# ifdef HAS_GETTIMEOFDAY
93dc8474 1687 gettimeofday(&when,(struct timezone *) 0);
54310121 1688 u = (U32)SEED_C1 * when.tv_sec + (U32)SEED_C2 * when.tv_usec;
f12c7020 1689# else
93dc8474 1690 (void)time(&when);
54310121 1691 u = (U32)SEED_C1 * when;
f12c7020 1692# endif
1693#endif
54310121 1694 u += SEED_C3 * (U32)getpid();
3280af22 1695 u += SEED_C4 * (U32)(UV)PL_stack_sp;
54310121 1696#ifndef PLAN9 /* XXX Plan9 assembler chokes on this; fix needed */
1697 u += SEED_C5 * (U32)(UV)&when;
f12c7020 1698#endif
93dc8474 1699 return u;
79072805
LW
1700}
1701
1702PP(pp_exp)
1703{
4e35701f 1704 djSP; dTARGET; tryAMAGICun(exp);
a0d0e21e
LW
1705 {
1706 double value;
1707 value = POPn;
1708 value = exp(value);
1709 XPUSHn(value);
1710 RETURN;
1711 }
79072805
LW
1712}
1713
1714PP(pp_log)
1715{
4e35701f 1716 djSP; dTARGET; tryAMAGICun(log);
a0d0e21e
LW
1717 {
1718 double value;
1719 value = POPn;
bbce6d69 1720 if (value <= 0.0) {
36477c24 1721 SET_NUMERIC_STANDARD();
2304df62 1722 DIE("Can't take log of %g", value);
bbce6d69 1723 }
a0d0e21e
LW
1724 value = log(value);
1725 XPUSHn(value);
1726 RETURN;
1727 }
79072805
LW
1728}
1729
1730PP(pp_sqrt)
1731{
4e35701f 1732 djSP; dTARGET; tryAMAGICun(sqrt);
a0d0e21e
LW
1733 {
1734 double value;
1735 value = POPn;
bbce6d69 1736 if (value < 0.0) {
36477c24 1737 SET_NUMERIC_STANDARD();
2304df62 1738 DIE("Can't take sqrt of %g", value);
bbce6d69 1739 }
a0d0e21e
LW
1740 value = sqrt(value);
1741 XPUSHn(value);
1742 RETURN;
1743 }
79072805
LW
1744}
1745
1746PP(pp_int)
1747{
4e35701f 1748 djSP; dTARGET;
774d564b 1749 {
1750 double value = TOPn;
1751 IV iv;
1752
1753 if (SvIOKp(TOPs) && !SvNOKp(TOPs) && !SvPOKp(TOPs)) {
1754 iv = SvIVX(TOPs);
1755 SETi(iv);
1756 }
1757 else {
1758 if (value >= 0.0)
1759 (void)modf(value, &value);
1760 else {
1761 (void)modf(-value, &value);
1762 value = -value;
1763 }
1764 iv = I_V(value);
1765 if (iv == value)
1766 SETi(iv);
1767 else
1768 SETn(value);
1769 }
79072805 1770 }
79072805
LW
1771 RETURN;
1772}
1773
463ee0b2
LW
1774PP(pp_abs)
1775{
4e35701f 1776 djSP; dTARGET; tryAMAGICun(abs);
a0d0e21e 1777 {
774d564b 1778 double value = TOPn;
1779 IV iv;
463ee0b2 1780
774d564b 1781 if (SvIOKp(TOPs) && !SvNOKp(TOPs) && !SvPOKp(TOPs) &&
1782 (iv = SvIVX(TOPs)) != IV_MIN) {
1783 if (iv < 0)
1784 iv = -iv;
1785 SETi(iv);
1786 }
1787 else {
1788 if (value < 0.0)
1789 value = -value;
1790 SETn(value);
1791 }
a0d0e21e 1792 }
774d564b 1793 RETURN;
463ee0b2
LW
1794}
1795
79072805
LW
1796PP(pp_hex)
1797{
4e35701f 1798 djSP; dTARGET;
79072805
LW
1799 char *tmps;
1800 I32 argtype;
2d8e6c8d 1801 STRLEN n_a;
79072805 1802
2d8e6c8d 1803 tmps = POPpx;
55497cff 1804 XPUSHu(scan_hex(tmps, 99, &argtype));
79072805
LW
1805 RETURN;
1806}
1807
1808PP(pp_oct)
1809{
4e35701f 1810 djSP; dTARGET;
55497cff 1811 UV value;
79072805
LW
1812 I32 argtype;
1813 char *tmps;
2d8e6c8d 1814 STRLEN n_a;
79072805 1815
2d8e6c8d 1816 tmps = POPpx;
464e2e8a 1817 while (*tmps && isSPACE(*tmps))
1818 tmps++;
1819 if (*tmps == '0')
79072805
LW
1820 tmps++;
1821 if (*tmps == 'x')
464e2e8a 1822 value = scan_hex(++tmps, 99, &argtype);
4f19785b
WSI
1823 else if (*tmps == 'b')
1824 value = scan_bin(++tmps, 99, &argtype);
464e2e8a 1825 else
1826 value = scan_oct(tmps, 99, &argtype);
55497cff 1827 XPUSHu(value);
79072805
LW
1828 RETURN;
1829}
1830
1831/* String stuff. */
1832
1833PP(pp_length)
1834{
4e35701f 1835 djSP; dTARGET;
a0ed51b3
LW
1836
1837 if (IN_UTF8) {
1838 SETi( sv_len_utf8(TOPs) );
1839 RETURN;
1840 }
1841
a0d0e21e 1842 SETi( sv_len(TOPs) );
79072805
LW
1843 RETURN;
1844}
1845
1846PP(pp_substr)
1847{
4e35701f 1848 djSP; dTARGET;
79072805
LW
1849 SV *sv;
1850 I32 len;
463ee0b2 1851 STRLEN curlen;
a0ed51b3 1852 STRLEN utfcurlen;
79072805
LW
1853 I32 pos;
1854 I32 rem;
84902520 1855 I32 fail;
533c011a 1856 I32 lvalue = PL_op->op_flags & OPf_MOD;
79072805 1857 char *tmps;
3280af22 1858 I32 arybase = PL_curcop->cop_arybase;
7b8d334a
GS
1859 char *repl = 0;
1860 STRLEN repl_len;
79072805 1861
20408e3c 1862 SvTAINTED_off(TARG); /* decontaminate */
5d82c453
GA
1863 if (MAXARG > 2) {
1864 if (MAXARG > 3) {
1865 sv = POPs;
1866 repl = SvPV(sv, repl_len);
7b8d334a 1867 }
79072805 1868 len = POPi;
5d82c453 1869 }
84902520 1870 pos = POPi;
79072805 1871 sv = POPs;
849ca7ee 1872 PUTBACK;
a0d0e21e 1873 tmps = SvPV(sv, curlen);
a0ed51b3
LW
1874 if (IN_UTF8) {
1875 utfcurlen = sv_len_utf8(sv);
1876 if (utfcurlen == curlen)
1877 utfcurlen = 0;
1878 else
1879 curlen = utfcurlen;
1880 }
d1c2b58a
LW
1881 else
1882 utfcurlen = 0;
a0ed51b3 1883
84902520
TB
1884 if (pos >= arybase) {
1885 pos -= arybase;
1886 rem = curlen-pos;
1887 fail = rem;
5d82c453
GA
1888 if (MAXARG > 2) {
1889 if (len < 0) {
1890 rem += len;
1891 if (rem < 0)
1892 rem = 0;
1893 }
1894 else if (rem > len)
1895 rem = len;
1896 }
68dc0745 1897 }
84902520 1898 else {
5d82c453
GA
1899 pos += curlen;
1900 if (MAXARG < 3)
1901 rem = curlen;
1902 else if (len >= 0) {
1903 rem = pos+len;
1904 if (rem > (I32)curlen)
1905 rem = curlen;
1906 }
1907 else {
1908 rem = curlen+len;
1909 if (rem < pos)
1910 rem = pos;
1911 }
1912 if (pos < 0)
1913 pos = 0;
1914 fail = rem;
1915 rem -= pos;
84902520
TB
1916 }
1917 if (fail < 0) {
599cee73
PM
1918 if (ckWARN(WARN_SUBSTR) || lvalue || repl)
1919 warner(WARN_SUBSTR, "substr outside of string");
2304df62
AD
1920 RETPUSHUNDEF;
1921 }
79072805 1922 else {
a0ed51b3
LW
1923 if (utfcurlen)
1924 sv_pos_u2b(sv, &pos, &rem);
79072805 1925 tmps += pos;
79072805
LW
1926 sv_setpvn(TARG, tmps, rem);
1927 if (lvalue) { /* it's an lvalue! */
dedeecda 1928 if (!SvGMAGICAL(sv)) {
1929 if (SvROK(sv)) {
2d8e6c8d
GS
1930 STRLEN n_a;
1931 SvPV_force(sv,n_a);
599cee73
PM
1932 if (ckWARN(WARN_SUBSTR))
1933 warner(WARN_SUBSTR,
1934 "Attempt to use reference as lvalue in substr");
dedeecda 1935 }
1936 if (SvOK(sv)) /* is it defined ? */
1937 (void)SvPOK_only(sv);
1938 else
1939 sv_setpvn(sv,"",0); /* avoid lexical reincarnation */
1940 }
5f05dabc 1941
a0d0e21e
LW
1942 if (SvTYPE(TARG) < SVt_PVLV) {
1943 sv_upgrade(TARG, SVt_PVLV);
1944 sv_magic(TARG, Nullsv, 'x', Nullch, 0);
ed6116ce 1945 }
a0d0e21e 1946
5f05dabc 1947 LvTYPE(TARG) = 'x';
6ff81951
GS
1948 if (LvTARG(TARG) != sv) {
1949 if (LvTARG(TARG))
1950 SvREFCNT_dec(LvTARG(TARG));
1951 LvTARG(TARG) = SvREFCNT_inc(sv);
1952 }
a0d0e21e 1953 LvTARGOFF(TARG) = pos;
8ec5e241 1954 LvTARGLEN(TARG) = rem;
79072805 1955 }
5d82c453 1956 else if (repl)
7b8d334a 1957 sv_insert(sv, pos, rem, repl, repl_len);
79072805 1958 }
849ca7ee 1959 SPAGAIN;
79072805
LW
1960 PUSHs(TARG); /* avoid SvSETMAGIC here */
1961 RETURN;
1962}
1963
1964PP(pp_vec)
1965{
4e35701f 1966 djSP; dTARGET;
79072805
LW
1967 register I32 size = POPi;
1968 register I32 offset = POPi;
1969 register SV *src = POPs;
533c011a 1970 I32 lvalue = PL_op->op_flags & OPf_MOD;
463ee0b2
LW
1971 STRLEN srclen;
1972 unsigned char *s = (unsigned char*)SvPV(src, srclen);
79072805
LW
1973 unsigned long retnum;
1974 I32 len;
1975
20408e3c 1976 SvTAINTED_off(TARG); /* decontaminate */
79072805
LW
1977 offset *= size; /* turn into bit offset */
1978 len = (offset + size + 7) / 8;
1979 if (offset < 0 || size < 1)
1980 retnum = 0;
79072805 1981 else {
a0d0e21e
LW
1982 if (lvalue) { /* it's an lvalue! */
1983 if (SvTYPE(TARG) < SVt_PVLV) {
1984 sv_upgrade(TARG, SVt_PVLV);
1985 sv_magic(TARG, Nullsv, 'v', Nullch, 0);
1986 }
1987
1988 LvTYPE(TARG) = 'v';
6ff81951
GS
1989 if (LvTARG(TARG) != src) {
1990 if (LvTARG(TARG))
1991 SvREFCNT_dec(LvTARG(TARG));
1992 LvTARG(TARG) = SvREFCNT_inc(src);
1993 }
8ec5e241
NIS
1994 LvTARGOFF(TARG) = offset;
1995 LvTARGLEN(TARG) = size;
a0d0e21e 1996 }
93a17b20 1997 if (len > srclen) {
a0d0e21e
LW
1998 if (size <= 8)
1999 retnum = 0;
2000 else {
2001 offset >>= 3;
748a9306
LW
2002 if (size == 16) {
2003 if (offset >= srclen)
2004 retnum = 0;
a0d0e21e 2005 else
748a9306
LW
2006 retnum = (unsigned long) s[offset] << 8;
2007 }
2008 else if (size == 32) {
2009 if (offset >= srclen)
2010 retnum = 0;
2011 else if (offset + 1 >= srclen)
a0d0e21e 2012 retnum = (unsigned long) s[offset] << 24;
748a9306
LW
2013 else if (offset + 2 >= srclen)
2014 retnum = ((unsigned long) s[offset] << 24) +
2015 ((unsigned long) s[offset + 1] << 16);
2016 else
2017 retnum = ((unsigned long) s[offset] << 24) +
2018 ((unsigned long) s[offset + 1] << 16) +
2019 (s[offset + 2] << 8);
a0d0e21e
LW
2020 }
2021 }
79072805 2022 }
a0d0e21e 2023 else if (size < 8)
79072805
LW
2024 retnum = (s[offset >> 3] >> (offset & 7)) & ((1 << size) - 1);
2025 else {
2026 offset >>= 3;
2027 if (size == 8)
2028 retnum = s[offset];
2029 else if (size == 16)
2030 retnum = ((unsigned long) s[offset] << 8) + s[offset+1];
2031 else if (size == 32)
2032 retnum = ((unsigned long) s[offset] << 24) +
2033 ((unsigned long) s[offset + 1] << 16) +
2034 (s[offset + 2] << 8) + s[offset+3];
2035 }
79072805
LW
2036 }
2037
deb3007b 2038 sv_setuv(TARG, (UV)retnum);
79072805
LW
2039 PUSHs(TARG);
2040 RETURN;
2041}
2042
2043PP(pp_index)
2044{
4e35701f 2045 djSP; dTARGET;
79072805
LW
2046 SV *big;
2047 SV *little;
2048 I32 offset;
2049 I32 retval;
2050 char *tmps;
2051 char *tmps2;
463ee0b2 2052 STRLEN biglen;
3280af22 2053 I32 arybase = PL_curcop->cop_arybase;
79072805
LW
2054
2055 if (MAXARG < 3)
2056 offset = 0;
2057 else
2058 offset = POPi - arybase;
2059 little = POPs;
2060 big = POPs;
463ee0b2 2061 tmps = SvPV(big, biglen);
a0ed51b3
LW
2062 if (IN_UTF8 && offset > 0)
2063 sv_pos_u2b(big, &offset, 0);
79072805
LW
2064 if (offset < 0)
2065 offset = 0;
93a17b20
LW
2066 else if (offset > biglen)
2067 offset = biglen;
79072805 2068 if (!(tmps2 = fbm_instr((unsigned char*)tmps + offset,
411d5715 2069 (unsigned char*)tmps + biglen, little, 0)))
a0ed51b3 2070 retval = -1;
79072805 2071 else
a0ed51b3
LW
2072 retval = tmps2 - tmps;
2073 if (IN_UTF8 && retval > 0)
2074 sv_pos_b2u(big, &retval);
2075 PUSHi(retval + arybase);
79072805
LW
2076 RETURN;
2077}
2078
2079PP(pp_rindex)
2080{
4e35701f 2081 djSP; dTARGET;
79072805
LW
2082 SV *big;
2083 SV *little;
463ee0b2
LW
2084 STRLEN blen;
2085 STRLEN llen;
79072805
LW
2086 I32 offset;
2087 I32 retval;
2088 char *tmps;
2089 char *tmps2;
3280af22 2090 I32 arybase = PL_curcop->cop_arybase;
79072805 2091
a0d0e21e 2092 if (MAXARG >= 3)
a0ed51b3 2093 offset = POPi;
79072805
LW
2094 little = POPs;
2095 big = POPs;
463ee0b2
LW
2096 tmps2 = SvPV(little, llen);
2097 tmps = SvPV(big, blen);
79072805 2098 if (MAXARG < 3)
463ee0b2 2099 offset = blen;
a0ed51b3
LW
2100 else {
2101 if (IN_UTF8 && offset > 0)
2102 sv_pos_u2b(big, &offset, 0);
2103 offset = offset - arybase + llen;
2104 }
79072805
LW
2105 if (offset < 0)
2106 offset = 0;
463ee0b2
LW
2107 else if (offset > blen)
2108 offset = blen;
79072805 2109 if (!(tmps2 = rninstr(tmps, tmps + offset,
463ee0b2 2110 tmps2, tmps2 + llen)))
a0ed51b3 2111 retval = -1;
79072805 2112 else
a0ed51b3
LW
2113 retval = tmps2 - tmps;
2114 if (IN_UTF8 && retval > 0)
2115 sv_pos_b2u(big, &retval);
2116 PUSHi(retval + arybase);
79072805
LW
2117 RETURN;
2118}
2119
2120PP(pp_sprintf)
2121{
4e35701f 2122 djSP; dMARK; dORIGMARK; dTARGET;
36477c24 2123#ifdef USE_LOCALE_NUMERIC
533c011a 2124 if (PL_op->op_private & OPpLOCALE)
36477c24 2125 SET_NUMERIC_LOCAL();
bbce6d69 2126 else
36477c24 2127 SET_NUMERIC_STANDARD();
2128#endif
79072805 2129 do_sprintf(TARG, SP-MARK, MARK+1);
bbce6d69 2130 TAINT_IF(SvTAINTED(TARG));
79072805
LW
2131 SP = ORIGMARK;
2132 PUSHTARG;
2133 RETURN;
2134}
2135
79072805
LW
2136PP(pp_ord)
2137{
4e35701f 2138 djSP; dTARGET;
bdeef251 2139 UV value;
2d8e6c8d
GS
2140 STRLEN n_a;
2141 U8 *tmps = (U8*)POPpx;
a0ed51b3 2142 I32 retlen;
79072805 2143
a0ed51b3 2144 if (IN_UTF8 && (*tmps & 0x80))
bdeef251 2145 value = utf8_to_uv(tmps, &retlen);
a0ed51b3 2146 else
bdeef251
GA
2147 value = (UV)(*tmps & 255);
2148 XPUSHu(value);
79072805
LW
2149 RETURN;
2150}
2151
463ee0b2
LW
2152PP(pp_chr)
2153{
4e35701f 2154 djSP; dTARGET;
463ee0b2 2155 char *tmps;
3b9be786 2156 U32 value = POPu;
463ee0b2 2157
748a9306 2158 (void)SvUPGRADE(TARG,SVt_PV);
a0ed51b3
LW
2159
2160 if (IN_UTF8 && value >= 128) {
2161 SvGROW(TARG,8);
2162 tmps = SvPVX(TARG);
dfe13c55 2163 tmps = (char*)uv_to_utf8((U8*)tmps, (UV)value);
a0ed51b3
LW
2164 SvCUR_set(TARG, tmps - SvPVX(TARG));
2165 *tmps = '\0';
2166 (void)SvPOK_only(TARG);
2167 XPUSHs(TARG);
2168 RETURN;
2169 }
2170
748a9306 2171 SvGROW(TARG,2);
463ee0b2
LW
2172 SvCUR_set(TARG, 1);
2173 tmps = SvPVX(TARG);
a0ed51b3 2174 *tmps++ = value;
748a9306 2175 *tmps = '\0';
a0d0e21e 2176 (void)SvPOK_only(TARG);
463ee0b2
LW
2177 XPUSHs(TARG);
2178 RETURN;
2179}
2180
79072805
LW
2181PP(pp_crypt)
2182{
4e35701f 2183 djSP; dTARGET; dPOPTOPssrl;
2d8e6c8d 2184 STRLEN n_a;
79072805 2185#ifdef HAS_CRYPT
2d8e6c8d 2186 char *tmps = SvPV(left, n_a);
79072805 2187#ifdef FCRYPT
2d8e6c8d 2188 sv_setpv(TARG, fcrypt(tmps, SvPV(right, n_a)));
79072805 2189#else
2d8e6c8d 2190 sv_setpv(TARG, PerlProc_crypt(tmps, SvPV(right, n_a)));
79072805
LW
2191#endif
2192#else
2193 DIE(
2194 "The crypt() function is unimplemented due to excessive paranoia.");
2195#endif
2196 SETs(TARG);
2197 RETURN;
2198}
2199
2200PP(pp_ucfirst)
2201{
4e35701f 2202 djSP;
79072805 2203 SV *sv = TOPs;
a0ed51b3
LW
2204 register U8 *s;
2205 STRLEN slen;
2206
dfe13c55 2207 if (IN_UTF8 && (s = (U8*)SvPV(sv, slen)) && slen && (*s & 0xc0) == 0xc0) {
a0ed51b3
LW
2208 I32 ulen;
2209 U8 tmpbuf[10];
2210 U8 *tend;
2211 UV uv = utf8_to_uv(s, &ulen);
2212
2213 if (PL_op->op_private & OPpLOCALE) {
2214 TAINT;
2215 SvTAINTED_on(sv);
2216 uv = toTITLE_LC_uni(uv);
2217 }
2218 else
2219 uv = toTITLE_utf8(s);
2220
2221 tend = uv_to_utf8(tmpbuf, uv);
2222
2223 if (!SvPADTMP(sv) || tend - tmpbuf != ulen) {
2224 dTARGET;
dfe13c55
GS
2225 sv_setpvn(TARG, (char*)tmpbuf, tend - tmpbuf);
2226 sv_catpvn(TARG, (char*)(s + ulen), slen - ulen);
a0ed51b3
LW
2227 SETs(TARG);
2228 }
2229 else {
dfe13c55 2230 s = (U8*)SvPV_force(sv, slen);
a0ed51b3
LW
2231 Copy(tmpbuf, s, ulen, U8);
2232 }
2233 RETURN;
2234 }
79072805 2235
ed6116ce 2236 if (!SvPADTMP(sv)) {
79072805
LW
2237 dTARGET;
2238 sv_setsv(TARG, sv);
2239 sv = TARG;
2240 SETs(sv);
2241 }
2d8e6c8d 2242 s = (U8*)SvPV_force(sv, slen);
bbce6d69 2243 if (*s) {
533c011a 2244 if (PL_op->op_private & OPpLOCALE) {
bbce6d69 2245 TAINT;
2246 SvTAINTED_on(sv);
2247 *s = toUPPER_LC(*s);
2248 }
2249 else
2250 *s = toUPPER(*s);
2251 }
79072805
LW
2252
2253 RETURN;
2254}
2255
2256PP(pp_lcfirst)
2257{
4e35701f 2258 djSP;
79072805 2259 SV *sv = TOPs;
a0ed51b3
LW
2260 register U8 *s;
2261 STRLEN slen;
2262
dfe13c55 2263 if (IN_UTF8 && (s = (U8*)SvPV(sv, slen)) && slen && (*s & 0xc0) == 0xc0) {
a0ed51b3
LW
2264 I32 ulen;
2265 U8 tmpbuf[10];
2266 U8 *tend;
2267 UV uv = utf8_to_uv(s, &ulen);
2268
2269 if (PL_op->op_private & OPpLOCALE) {
2270 TAINT;
2271 SvTAINTED_on(sv);
2272 uv = toLOWER_LC_uni(uv);
2273 }
2274 else
2275 uv = toLOWER_utf8(s);
2276
2277 tend = uv_to_utf8(tmpbuf, uv);
2278
2279 if (!SvPADTMP(sv) || tend - tmpbuf != ulen) {
2280 dTARGET;
dfe13c55
GS
2281 sv_setpvn(TARG, (char*)tmpbuf, tend - tmpbuf);
2282 sv_catpvn(TARG, (char*)(s + ulen), slen - ulen);
a0ed51b3
LW
2283 SETs(TARG);
2284 }
2285 else {
dfe13c55 2286 s = (U8*)SvPV_force(sv, slen);
a0ed51b3
LW
2287 Copy(tmpbuf, s, ulen, U8);
2288 }
2289 RETURN;
2290 }
79072805 2291
ed6116ce 2292 if (!SvPADTMP(sv)) {
79072805
LW
2293 dTARGET;
2294 sv_setsv(TARG, sv);
2295 sv = TARG;
2296 SETs(sv);
2297 }
2d8e6c8d 2298 s = (U8*)SvPV_force(sv, slen);
bbce6d69 2299 if (*s) {
533c011a 2300 if (PL_op->op_private & OPpLOCALE) {
bbce6d69 2301 TAINT;
2302 SvTAINTED_on(sv);
2303 *s = toLOWER_LC(*s);
2304 }
2305 else
2306 *s = toLOWER(*s);
2307 }
79072805
LW
2308
2309 SETs(sv);
2310 RETURN;
2311}
2312
2313PP(pp_uc)
2314{
4e35701f 2315 djSP;
79072805 2316 SV *sv = TOPs;
a0ed51b3 2317 register U8 *s;
463ee0b2 2318 STRLEN len;
79072805 2319
a0ed51b3
LW
2320 if (IN_UTF8) {
2321 dTARGET;
2322 I32 ulen;
2323 register U8 *d;
2324 U8 *send;
2325
dfe13c55 2326 s = (U8*)SvPV(sv,len);
a5a20234
LW
2327 if (!len) {
2328 sv_setpvn(TARG, "", 0);
2329 SETs(TARG);
a0ed51b3 2330 RETURN;
a5a20234 2331 }
a0ed51b3
LW
2332
2333 (void)SvUPGRADE(TARG, SVt_PV);
2334 SvGROW(TARG, (len * 2) + 1);
2335 (void)SvPOK_only(TARG);
dfe13c55 2336 d = (U8*)SvPVX(TARG);
a0ed51b3
LW
2337 send = s + len;
2338 if (PL_op->op_private & OPpLOCALE) {
2339 TAINT;
2340 SvTAINTED_on(TARG);
2341 while (s < send) {
2342 d = uv_to_utf8(d, toUPPER_LC_uni( utf8_to_uv(s, &ulen)));
2343 s += ulen;
2344 }
2345 }
2346 else {
2347 while (s < send) {
2348 d = uv_to_utf8(d, toUPPER_utf8( s ));
2349 s += UTF8SKIP(s);
2350 }
2351 }
2352 *d = '\0';
2353 SvCUR_set(TARG, d - (U8*)SvPVX(TARG));
2354 SETs(TARG);
2355 RETURN;
2356 }
2357
ed6116ce 2358 if (!SvPADTMP(sv)) {
79072805
LW
2359 dTARGET;
2360 sv_setsv(TARG, sv);
2361 sv = TARG;
2362 SETs(sv);
2363 }
bbce6d69 2364
dfe13c55 2365 s = (U8*)SvPV_force(sv, len);
bbce6d69 2366 if (len) {
a0ed51b3 2367 register U8 *send = s + len;
bbce6d69 2368
533c011a 2369 if (PL_op->op_private & OPpLOCALE) {
bbce6d69 2370 TAINT;
2371 SvTAINTED_on(sv);
2372 for (; s < send; s++)
2373 *s = toUPPER_LC(*s);
2374 }
2375 else {
2376 for (; s < send; s++)
2377 *s = toUPPER(*s);
2378 }
79072805
LW
2379 }
2380 RETURN;
2381}
2382
2383PP(pp_lc)
2384{
4e35701f 2385 djSP;
79072805 2386 SV *sv = TOPs;
a0ed51b3 2387 register U8 *s;
463ee0b2 2388 STRLEN len;
79072805 2389
a0ed51b3
LW
2390 if (IN_UTF8) {
2391 dTARGET;
2392 I32 ulen;
2393 register U8 *d;
2394 U8 *send;
2395
dfe13c55 2396 s = (U8*)SvPV(sv,len);
a5a20234
LW
2397 if (!len) {
2398 sv_setpvn(TARG, "", 0);
2399 SETs(TARG);
a0ed51b3 2400 RETURN;
a5a20234 2401 }
a0ed51b3
LW
2402
2403 (void)SvUPGRADE(TARG, SVt_PV);
2404 SvGROW(TARG, (len * 2) + 1);
2405 (void)SvPOK_only(TARG);
dfe13c55 2406 d = (U8*)SvPVX(TARG);
a0ed51b3
LW
2407 send = s + len;
2408 if (PL_op->op_private & OPpLOCALE) {
2409 TAINT;
2410 SvTAINTED_on(TARG);
2411 while (s < send) {
2412 d = uv_to_utf8(d, toLOWER_LC_uni( utf8_to_uv(s, &ulen)));
2413 s += ulen;
2414 }
2415 }
2416 else {
2417 while (s < send) {
2418 d = uv_to_utf8(d, toLOWER_utf8(s));
2419 s += UTF8SKIP(s);
2420 }
2421 }
2422 *d = '\0';
2423 SvCUR_set(TARG, d - (U8*)SvPVX(TARG));
2424 SETs(TARG);
2425 RETURN;
2426 }
2427
ed6116ce 2428 if (!SvPADTMP(sv)) {
79072805
LW
2429 dTARGET;
2430 sv_setsv(TARG, sv);
2431 sv = TARG;
2432 SETs(sv);
2433 }
bbce6d69 2434
dfe13c55 2435 s = (U8*)SvPV_force(sv, len);
bbce6d69 2436 if (len) {
a0ed51b3 2437 register U8 *send = s + len;
bbce6d69 2438
533c011a 2439 if (PL_op->op_private & OPpLOCALE) {
bbce6d69 2440 TAINT;
2441 SvTAINTED_on(sv);
2442 for (; s < send; s++)
2443 *s = toLOWER_LC(*s);
2444 }
2445 else {
2446 for (; s < send; s++)
2447 *s = toLOWER(*s);
2448 }
79072805
LW
2449 }
2450 RETURN;
2451}
2452
a0d0e21e 2453PP(pp_quotemeta)
79072805 2454{
4e35701f 2455 djSP; dTARGET;
a0d0e21e
LW
2456 SV *sv = TOPs;
2457 STRLEN len;
2458 register char *s = SvPV(sv,len);
2459 register char *d;
79072805 2460
a0d0e21e
LW
2461 if (len) {
2462 (void)SvUPGRADE(TARG, SVt_PV);
c07a80fd 2463 SvGROW(TARG, (len * 2) + 1);
a0d0e21e 2464 d = SvPVX(TARG);
0dd2cdef
LW
2465 if (IN_UTF8) {
2466 while (len) {
2467 if (*s & 0x80) {
2468 STRLEN ulen = UTF8SKIP(s);
2469 if (ulen > len)
2470 ulen = len;
2471 len -= ulen;
2472 while (ulen--)
2473 *d++ = *s++;
2474 }
2475 else {
2476 if (!isALNUM(*s))
2477 *d++ = '\\';
2478 *d++ = *s++;
2479 len--;
2480 }
2481 }
2482 }
2483 else {
2484 while (len--) {
2485 if (!isALNUM(*s))
2486 *d++ = '\\';
2487 *d++ = *s++;
2488 }
79072805 2489 }
a0d0e21e
LW
2490 *d = '\0';
2491 SvCUR_set(TARG, d - SvPVX(TARG));
2492 (void)SvPOK_only(TARG);
79072805 2493 }
a0d0e21e
LW
2494 else
2495 sv_setpvn(TARG, s, len);
2496 SETs(TARG);
79072805
LW
2497 RETURN;
2498}
2499
a0d0e21e 2500/* Arrays. */
79072805 2501
a0d0e21e 2502PP(pp_aslice)
79072805 2503{
4e35701f 2504 djSP; dMARK; dORIGMARK;
a0d0e21e
LW
2505 register SV** svp;
2506 register AV* av = (AV*)POPs;
533c011a 2507 register I32 lval = PL_op->op_flags & OPf_MOD;
3280af22 2508 I32 arybase = PL_curcop->cop_arybase;
748a9306 2509 I32 elem;
79072805 2510
a0d0e21e 2511 if (SvTYPE(av) == SVt_PVAV) {
533c011a 2512 if (lval && PL_op->op_private & OPpLVAL_INTRO) {
748a9306 2513 I32 max = -1;
924508f0 2514 for (svp = MARK + 1; svp <= SP; svp++) {
748a9306
LW
2515 elem = SvIVx(*svp);
2516 if (elem > max)
2517 max = elem;
2518 }
2519 if (max > AvMAX(av))
2520 av_extend(av, max);
2521 }
a0d0e21e 2522 while (++MARK <= SP) {
748a9306 2523 elem = SvIVx(*MARK);
a0d0e21e 2524
748a9306
LW
2525 if (elem > 0)
2526 elem -= arybase;
a0d0e21e
LW
2527 svp = av_fetch(av, elem, lval);
2528 if (lval) {
3280af22 2529 if (!svp || *svp == &PL_sv_undef)
22c35a8c 2530 DIE(PL_no_aelem, elem);
533c011a 2531 if (PL_op->op_private & OPpLVAL_INTRO)
161b7d16 2532 save_aelem(av, elem, svp);
79072805 2533 }
3280af22 2534 *MARK = svp ? *svp : &PL_sv_undef;
79072805
LW
2535 }
2536 }
748a9306 2537 if (GIMME != G_ARRAY) {
a0d0e21e
LW
2538 MARK = ORIGMARK;
2539 *++MARK = *SP;
2540 SP = MARK;
2541 }
79072805
LW
2542 RETURN;
2543}
2544
2545/* Associative arrays. */
2546
2547PP(pp_each)
2548{
4e35701f 2549 djSP; dTARGET;
79072805 2550 HV *hash = (HV*)POPs;
c07a80fd 2551 HE *entry;
54310121 2552 I32 gimme = GIMME_V;
c750a3ec 2553 I32 realhv = (SvTYPE(hash) == SVt_PVHV);
8ec5e241 2554
c07a80fd 2555 PUTBACK;
c750a3ec
MB
2556 /* might clobber stack_sp */
2557 entry = realhv ? hv_iternext(hash) : avhv_iternext((AV*)hash);
c07a80fd 2558 SPAGAIN;
79072805 2559
79072805
LW
2560 EXTEND(SP, 2);
2561 if (entry) {
54310121 2562 PUSHs(hv_iterkeysv(entry)); /* won't clobber stack_sp */
2563 if (gimme == G_ARRAY) {
c07a80fd 2564 PUTBACK;
c750a3ec
MB
2565 /* might clobber stack_sp */
2566 sv_setsv(TARG, realhv ?
2567 hv_iterval(hash, entry) : avhv_iterval((AV*)hash, entry));
c07a80fd 2568 SPAGAIN;
8990e307 2569 PUSHs(TARG);
79072805 2570 }
79072805 2571 }
54310121 2572 else if (gimme == G_SCALAR)
79072805
LW
2573 RETPUSHUNDEF;
2574
2575 RETURN;
2576}
2577
2578PP(pp_values)
2579{
2580 return do_kv(ARGS);
2581}
2582
2583PP(pp_keys)
2584{
2585 return do_kv(ARGS);
2586}
2587
2588PP(pp_delete)
2589{
4e35701f 2590 djSP;
54310121 2591 I32 gimme = GIMME_V;
2592 I32 discard = (gimme == G_VOID) ? G_DISCARD : 0;
79072805 2593 SV *sv;
5f05dabc 2594 HV *hv;
2595
533c011a 2596 if (PL_op->op_private & OPpSLICE) {
5f05dabc 2597 dMARK; dORIGMARK;
97fcbf96 2598 U32 hvtype;
5f05dabc 2599 hv = (HV*)POPs;
97fcbf96 2600 hvtype = SvTYPE(hv);
5f05dabc 2601 while (++MARK <= SP) {
ae77835f
MB
2602 if (hvtype == SVt_PVHV)
2603 sv = hv_delete_ent(hv, *MARK, discard, 0);
ae77835f
MB
2604 else
2605 DIE("Not a HASH reference");
3280af22 2606 *MARK = sv ? sv : &PL_sv_undef;
5f05dabc 2607 }
54310121 2608 if (discard)
2609 SP = ORIGMARK;
2610 else if (gimme == G_SCALAR) {
5f05dabc 2611 MARK = ORIGMARK;
2612 *++MARK = *SP;
2613 SP = MARK;
2614 }
2615 }
2616 else {
2617 SV *keysv = POPs;
2618 hv = (HV*)POPs;
97fcbf96
MB
2619 if (SvTYPE(hv) == SVt_PVHV)
2620 sv = hv_delete_ent(hv, keysv, discard, 0);
97fcbf96 2621 else
5f05dabc 2622 DIE("Not a HASH reference");
5f05dabc 2623 if (!sv)
3280af22 2624 sv = &PL_sv_undef;
54310121 2625 if (!discard)
2626 PUSHs(sv);
79072805 2627 }
79072805
LW
2628 RETURN;
2629}
2630
a0d0e21e 2631PP(pp_exists)
79072805 2632{
4e35701f 2633 djSP;
a0d0e21e
LW
2634 SV *tmpsv = POPs;
2635 HV *hv = (HV*)POPs;
c750a3ec 2636 if (SvTYPE(hv) == SVt_PVHV) {
ae77835f 2637 if (hv_exists_ent(hv, tmpsv, 0))
c750a3ec
MB
2638 RETPUSHYES;
2639 } else if (SvTYPE(hv) == SVt_PVAV) {
ae77835f 2640 if (avhv_exists_ent((AV*)hv, tmpsv, 0))
c750a3ec
MB
2641 RETPUSHYES;
2642 } else {
a0d0e21e
LW
2643 DIE("Not a HASH reference");
2644 }
a0d0e21e
LW
2645 RETPUSHNO;
2646}
79072805 2647
a0d0e21e
LW
2648PP(pp_hslice)
2649{
4e35701f 2650 djSP; dMARK; dORIGMARK;
a0d0e21e 2651 register HV *hv = (HV*)POPs;
533c011a 2652 register I32 lval = PL_op->op_flags & OPf_MOD;
c750a3ec 2653 I32 realhv = (SvTYPE(hv) == SVt_PVHV);
79072805 2654
0ebe0038
SM
2655 if (!realhv && PL_op->op_private & OPpLVAL_INTRO)
2656 DIE("Can't localize pseudo-hash element");
2657
c750a3ec 2658 if (realhv || SvTYPE(hv) == SVt_PVAV) {
a0d0e21e 2659 while (++MARK <= SP) {
f12c7020 2660 SV *keysv = *MARK;
ae77835f
MB
2661 SV **svp;
2662 if (realhv) {
800e9ae0 2663 HE *he = hv_fetch_ent(hv, keysv, lval, 0);
ae77835f
MB
2664 svp = he ? &HeVAL(he) : 0;
2665 } else {
97fcbf96 2666 svp = avhv_fetch_ent((AV*)hv, keysv, lval, 0);
ae77835f 2667 }
a0d0e21e 2668 if (lval) {
2d8e6c8d
GS
2669 if (!svp || *svp == &PL_sv_undef) {
2670 STRLEN n_a;
2671 DIE(PL_no_helem, SvPV(keysv, n_a));
2672 }
533c011a 2673 if (PL_op->op_private & OPpLVAL_INTRO)
800e9ae0 2674 save_helem(hv, keysv, svp);
93a17b20 2675 }
3280af22 2676 *MARK = svp ? *svp : &PL_sv_undef;
79072805
LW
2677 }
2678 }
a0d0e21e
LW
2679 if (GIMME != G_ARRAY) {
2680 MARK = ORIGMARK;
2681 *++MARK = *SP;
2682 SP = MARK;
79072805 2683 }
a0d0e21e
LW
2684 RETURN;
2685}
2686
2687/* List operators. */
2688
2689PP(pp_list)
2690{
4e35701f 2691 djSP; dMARK;
a0d0e21e
LW
2692 if (GIMME != G_ARRAY) {
2693 if (++MARK <= SP)
2694 *MARK = *SP; /* unwanted list, return last item */
8990e307 2695 else
3280af22 2696 *MARK = &PL_sv_undef;
a0d0e21e 2697 SP = MARK;
79072805 2698 }
a0d0e21e 2699 RETURN;
79072805
LW
2700}
2701
a0d0e21e 2702PP(pp_lslice)
79072805 2703{
4e35701f 2704 djSP;
3280af22
NIS
2705 SV **lastrelem = PL_stack_sp;
2706 SV **lastlelem = PL_stack_base + POPMARK;
2707 SV **firstlelem = PL_stack_base + POPMARK + 1;
a0d0e21e 2708 register SV **firstrelem = lastlelem + 1;
3280af22 2709 I32 arybase = PL_curcop->cop_arybase;
533c011a 2710 I32 lval = PL_op->op_flags & OPf_MOD;
4633a7c4 2711 I32 is_something_there = lval;
79072805 2712
a0d0e21e
LW
2713 register I32 max = lastrelem - lastlelem;
2714 register SV **lelem;
2715 register I32 ix;
2716
2717 if (GIMME != G_ARRAY) {
748a9306
LW
2718 ix = SvIVx(*lastlelem);
2719 if (ix < 0)
2720 ix += max;
2721 else
2722 ix -= arybase;
a0d0e21e 2723 if (ix < 0 || ix >= max)
3280af22 2724 *firstlelem = &PL_sv_undef;
a0d0e21e
LW
2725 else
2726 *firstlelem = firstrelem[ix];
2727 SP = firstlelem;
2728 RETURN;
2729 }
2730
2731 if (max == 0) {
2732 SP = firstlelem - 1;
2733 RETURN;
2734 }
2735
2736 for (lelem = firstlelem; lelem <= lastlelem; lelem++) {
748a9306 2737 ix = SvIVx(*lelem);
a0d0e21e
LW
2738 if (ix < 0) {
2739 ix += max;
2740 if (ix < 0)
3280af22 2741 *lelem = &PL_sv_undef;
a0d0e21e 2742 else if (!(*lelem = firstrelem[ix]))
3280af22 2743 *lelem = &PL_sv_undef;
79072805 2744 }
748a9306
LW
2745 else {
2746 ix -= arybase;
2747 if (ix >= max || !(*lelem = firstrelem[ix]))
3280af22 2748 *lelem = &PL_sv_undef;
748a9306 2749 }
ff0cee69 2750 if (!is_something_there && (SvOK(*lelem) || SvGMAGICAL(*lelem)))
4633a7c4 2751 is_something_there = TRUE;
79072805 2752 }
4633a7c4
LW
2753 if (is_something_there)
2754 SP = lastlelem;
2755 else
2756 SP = firstlelem - 1;
79072805
LW
2757 RETURN;
2758}
2759
a0d0e21e
LW
2760PP(pp_anonlist)
2761{
4e35701f 2762 djSP; dMARK; dORIGMARK;
a0d0e21e 2763 I32 items = SP - MARK;
44a8e56a 2764 SV *av = sv_2mortal((SV*)av_make(items, MARK+1));
2765 SP = ORIGMARK; /* av_make() might realloc stack_sp */
2766 XPUSHs(av);
a0d0e21e
LW
2767 RETURN;
2768}
2769
2770PP(pp_anonhash)
79072805 2771{
4e35701f 2772 djSP; dMARK; dORIGMARK;
a0d0e21e
LW
2773 HV* hv = (HV*)sv_2mortal((SV*)newHV());
2774
2775 while (MARK < SP) {
2776 SV* key = *++MARK;
a0d0e21e
LW
2777 SV *val = NEWSV(46, 0);
2778 if (MARK < SP)
2779 sv_setsv(val, *++MARK);
599cee73
PM
2780 else if (ckWARN(WARN_UNSAFE))
2781 warner(WARN_UNSAFE, "Odd number of elements in hash assignment");
f12c7020 2782 (void)hv_store_ent(hv,key,val,0);
79072805 2783 }
a0d0e21e
LW
2784 SP = ORIGMARK;
2785 XPUSHs((SV*)hv);
79072805
LW
2786 RETURN;
2787}
2788
a0d0e21e 2789PP(pp_splice)
79072805 2790{
4e35701f 2791 djSP; dMARK; dORIGMARK;
a0d0e21e
LW
2792 register AV *ary = (AV*)*++MARK;
2793 register SV **src;
2794 register SV **dst;
2795 register I32 i;
2796 register I32 offset;
2797 register I32 length;
2798 I32 newlen;
2799 I32 after;
2800 I32 diff;
2801 SV **tmparyval = 0;
93965878
NIS
2802 MAGIC *mg;
2803
33c27489
GS
2804 if (mg = SvTIED_mg((SV*)ary, 'P')) {
2805 *MARK-- = SvTIED_obj((SV*)ary, mg);
93965878 2806 PUSHMARK(MARK);
8ec5e241 2807 PUTBACK;
a60c0954 2808 ENTER;
93965878 2809 perl_call_method("SPLICE",GIMME_V);
a60c0954 2810 LEAVE;
93965878
NIS
2811 SPAGAIN;
2812 RETURN;
2813 }
79072805 2814
a0d0e21e 2815 SP++;
79072805 2816
a0d0e21e 2817 if (++MARK < SP) {
84902520 2818 offset = i = SvIVx(*MARK);
a0d0e21e 2819 if (offset < 0)
93965878 2820 offset += AvFILLp(ary) + 1;
a0d0e21e 2821 else
3280af22 2822 offset -= PL_curcop->cop_arybase;
84902520 2823 if (offset < 0)
22c35a8c 2824 DIE(PL_no_aelem, i);
a0d0e21e
LW
2825 if (++MARK < SP) {
2826 length = SvIVx(*MARK++);
48cdf507
GA
2827 if (length < 0) {
2828 length += AvFILLp(ary) - offset + 1;
2829 if (length < 0)
2830 length = 0;
2831 }
79072805
LW
2832 }
2833 else
a0d0e21e 2834 length = AvMAX(ary) + 1; /* close enough to infinity */
79072805 2835 }
a0d0e21e
LW
2836 else {
2837 offset = 0;
2838 length = AvMAX(ary) + 1;
2839 }
93965878
NIS
2840 if (offset > AvFILLp(ary) + 1)
2841 offset = AvFILLp(ary) + 1;
2842 after = AvFILLp(ary) + 1 - (offset + length);
a0d0e21e
LW
2843 if (after < 0) { /* not that much array */
2844 length += after; /* offset+length now in array */
2845 after = 0;
2846 if (!AvALLOC(ary))
2847 av_extend(ary, 0);
2848 }
2849
2850 /* At this point, MARK .. SP-1 is our new LIST */
2851
2852 newlen = SP - MARK;
2853 diff = newlen - length;
13d7cbc1
GS
2854 if (newlen && !AvREAL(ary) && AvREIFY(ary))
2855 av_reify(ary);
a0d0e21e
LW
2856
2857 if (diff < 0) { /* shrinking the area */
2858 if (newlen) {
2859 New(451, tmparyval, newlen, SV*); /* so remember insertion */
2860 Copy(MARK, tmparyval, newlen, SV*);
79072805 2861 }
a0d0e21e
LW
2862
2863 MARK = ORIGMARK + 1;
2864 if (GIMME == G_ARRAY) { /* copy return vals to stack */
2865 MEXTEND(MARK, length);
2866 Copy(AvARRAY(ary)+offset, MARK, length, SV*);
2867 if (AvREAL(ary)) {
bbce6d69 2868 EXTEND_MORTAL(length);
36477c24 2869 for (i = length, dst = MARK; i; i--) {
d689ffdd 2870 sv_2mortal(*dst); /* free them eventualy */
36477c24 2871 dst++;
2872 }
a0d0e21e
LW
2873 }
2874 MARK += length - 1;
79072805 2875 }
a0d0e21e
LW
2876 else {
2877 *MARK = AvARRAY(ary)[offset+length-1];
2878 if (AvREAL(ary)) {
d689ffdd 2879 sv_2mortal(*MARK);
a0d0e21e
LW
2880 for (i = length - 1, dst = &AvARRAY(ary)[offset]; i > 0; i--)
2881 SvREFCNT_dec(*dst++); /* free them now */
79072805 2882 }
a0d0e21e 2883 }
93965878 2884 AvFILLp(ary) += diff;
a0d0e21e
LW
2885
2886 /* pull up or down? */
2887
2888 if (offset < after) { /* easier to pull up */
2889 if (offset) { /* esp. if nothing to pull */
2890 src = &AvARRAY(ary)[offset-1];
2891 dst = src - diff; /* diff is negative */
2892 for (i = offset; i > 0; i--) /* can't trust Copy */
2893 *dst-- = *src--;
79072805 2894 }
a0d0e21e
LW
2895 dst = AvARRAY(ary);
2896 SvPVX(ary) = (char*)(AvARRAY(ary) - diff); /* diff is negative */
2897 AvMAX(ary) += diff;
2898 }
2899 else {
2900 if (after) { /* anything to pull down? */
2901 src = AvARRAY(ary) + offset + length;
2902 dst = src + diff; /* diff is negative */
2903 Move(src, dst, after, SV*);
79072805 2904 }
93965878 2905 dst = &AvARRAY(ary)[AvFILLp(ary)+1];
a0d0e21e
LW
2906 /* avoid later double free */
2907 }
2908 i = -diff;
2909 while (i)
3280af22 2910 dst[--i] = &PL_sv_undef;
a0d0e21e
LW
2911
2912 if (newlen) {
2913 for (src = tmparyval, dst = AvARRAY(ary) + offset;
2914 newlen; newlen--) {
2915 *dst = NEWSV(46, 0);
2916 sv_setsv(*dst++, *src++);
79072805 2917 }
a0d0e21e
LW
2918 Safefree(tmparyval);
2919 }
2920 }
2921 else { /* no, expanding (or same) */
2922 if (length) {
2923 New(452, tmparyval, length, SV*); /* so remember deletion */
2924 Copy(AvARRAY(ary)+offset, tmparyval, length, SV*);
2925 }
2926
2927 if (diff > 0) { /* expanding */
2928
2929 /* push up or down? */
2930
2931 if (offset < after && diff <= AvARRAY(ary) - AvALLOC(ary)) {
2932 if (offset) {
2933 src = AvARRAY(ary);
2934 dst = src - diff;
2935 Move(src, dst, offset, SV*);
79072805 2936 }
a0d0e21e
LW
2937 SvPVX(ary) = (char*)(AvARRAY(ary) - diff);/* diff is positive */
2938 AvMAX(ary) += diff;
93965878 2939 AvFILLp(ary) += diff;
79072805
LW
2940 }
2941 else {
93965878
NIS
2942 if (AvFILLp(ary) + diff >= AvMAX(ary)) /* oh, well */
2943 av_extend(ary, AvFILLp(ary) + diff);
2944 AvFILLp(ary) += diff;
a0d0e21e
LW
2945
2946 if (after) {
93965878 2947 dst = AvARRAY(ary) + AvFILLp(ary);
a0d0e21e
LW
2948 src = dst - diff;
2949 for (i = after; i; i--) {
2950 *dst-- = *src--;
2951 }
79072805
LW
2952 }
2953 }
a0d0e21e
LW
2954 }
2955
2956 for (src = MARK, dst = AvARRAY(ary) + offset; newlen; newlen--) {
2957 *dst = NEWSV(46, 0);
2958 sv_setsv(*dst++, *src++);
2959 }
2960 MARK = ORIGMARK + 1;
2961 if (GIMME == G_ARRAY) { /* copy return vals to stack */
2962 if (length) {
2963 Copy(tmparyval, MARK, length, SV*);
2964 if (AvREAL(ary)) {
bbce6d69 2965 EXTEND_MORTAL(length);
36477c24 2966 for (i = length, dst = MARK; i; i--) {
d689ffdd 2967 sv_2mortal(*dst); /* free them eventualy */
36477c24 2968 dst++;
2969 }
79072805 2970 }
a0d0e21e 2971 Safefree(tmparyval);
79072805 2972 }
a0d0e21e
LW
2973 MARK += length - 1;
2974 }
2975 else if (length--) {
2976 *MARK = tmparyval[length];
2977 if (AvREAL(ary)) {
d689ffdd 2978 sv_2mortal(*MARK);
a0d0e21e
LW
2979 while (length-- > 0)
2980 SvREFCNT_dec(tmparyval[length]);
79072805 2981 }
a0d0e21e 2982 Safefree(tmparyval);
79072805 2983 }
a0d0e21e 2984 else
3280af22 2985 *MARK = &PL_sv_undef;
79072805 2986 }
a0d0e21e 2987 SP = MARK;
79072805
LW
2988 RETURN;
2989}
2990
a0d0e21e 2991PP(pp_push)
79072805 2992{
4e35701f 2993 djSP; dMARK; dORIGMARK; dTARGET;
a0d0e21e 2994 register AV *ary = (AV*)*++MARK;
3280af22 2995 register SV *sv = &PL_sv_undef;
93965878 2996 MAGIC *mg;
79072805 2997
33c27489
GS
2998 if (mg = SvTIED_mg((SV*)ary, 'P')) {
2999 *MARK-- = SvTIED_obj((SV*)ary, mg);
93965878
NIS
3000 PUSHMARK(MARK);
3001 PUTBACK;
a60c0954
NIS
3002 ENTER;
3003 perl_call_method("PUSH",G_SCALAR|G_DISCARD);
3004 LEAVE;
93965878 3005 SPAGAIN;
93965878 3006 }
a60c0954
NIS
3007 else {
3008 /* Why no pre-extend of ary here ? */
3009 for (++MARK; MARK <= SP; MARK++) {
3010 sv = NEWSV(51, 0);
3011 if (*MARK)
3012 sv_setsv(sv, *MARK);
3013 av_push(ary, sv);
3014 }
79072805
LW
3015 }
3016 SP = ORIGMARK;
a0d0e21e 3017 PUSHi( AvFILL(ary) + 1 );
79072805
LW
3018 RETURN;
3019}
3020
a0d0e21e 3021PP(pp_pop)
79072805 3022{
4e35701f 3023 djSP;
a0d0e21e
LW
3024 AV *av = (AV*)POPs;
3025 SV *sv = av_pop(av);
d689ffdd 3026 if (AvREAL(av))
a0d0e21e
LW
3027 (void)sv_2mortal(sv);
3028 PUSHs(sv);
79072805 3029 RETURN;
79072805
LW
3030}
3031
a0d0e21e 3032PP(pp_shift)
79072805 3033{
4e35701f 3034 djSP;
a0d0e21e
LW
3035 AV *av = (AV*)POPs;
3036 SV *sv = av_shift(av);
79072805 3037 EXTEND(SP, 1);
a0d0e21e 3038 if (!sv)
79072805 3039 RETPUSHUNDEF;
d689ffdd 3040 if (AvREAL(av))
a0d0e21e
LW
3041 (void)sv_2mortal(sv);
3042 PUSHs(sv);
79072805 3043 RETURN;
79072805
LW
3044}
3045
a0d0e21e 3046PP(pp_unshift)
79072805 3047{
4e35701f 3048 djSP; dMARK; dORIGMARK; dTARGET;
a0d0e21e
LW
3049 register AV *ary = (AV*)*++MARK;
3050 register SV *sv;
3051 register I32 i = 0;
93965878
NIS
3052 MAGIC *mg;
3053
33c27489
GS
3054 if (mg = SvTIED_mg((SV*)ary, 'P')) {
3055 *MARK-- = SvTIED_obj((SV*)ary, mg);
7fd66d9d 3056 PUSHMARK(MARK);
93965878 3057 PUTBACK;
a60c0954
NIS
3058 ENTER;
3059 perl_call_method("UNSHIFT",G_SCALAR|G_DISCARD);
3060 LEAVE;
93965878 3061 SPAGAIN;
93965878 3062 }
a60c0954
NIS
3063 else {
3064 av_unshift(ary, SP - MARK);
3065 while (MARK < SP) {
3066 sv = NEWSV(27, 0);
3067 sv_setsv(sv, *++MARK);
3068 (void)av_store(ary, i++, sv);
3069 }
79072805 3070 }
a0d0e21e
LW
3071 SP = ORIGMARK;
3072 PUSHi( AvFILL(ary) + 1 );
79072805 3073 RETURN;
79072805
LW
3074}
3075
a0d0e21e 3076PP(pp_reverse)
79072805 3077{
4e35701f 3078 djSP; dMARK;
a0d0e21e
LW
3079 register SV *tmp;
3080 SV **oldsp = SP;
79072805 3081
a0d0e21e
LW
3082 if (GIMME == G_ARRAY) {
3083 MARK++;
3084 while (MARK < SP) {
3085 tmp = *MARK;
3086 *MARK++ = *SP;
3087 *SP-- = tmp;
3088 }
3089 SP = oldsp;
79072805
LW
3090 }
3091 else {
a0d0e21e
LW
3092 register char *up;
3093 register char *down;
3094 register I32 tmp;
3095 dTARGET;
3096 STRLEN len;
79072805 3097
a0d0e21e 3098 if (SP - MARK > 1)
3280af22 3099 do_join(TARG, &PL_sv_no, MARK, SP);
a0d0e21e 3100 else
54b9620d 3101 sv_setsv(TARG, (SP > MARK) ? *SP : DEFSV);
a0d0e21e
LW
3102 up = SvPV_force(TARG, len);
3103 if (len > 1) {
a0ed51b3 3104 if (IN_UTF8) { /* first reverse each character */
dfe13c55
GS
3105 U8* s = (U8*)SvPVX(TARG);
3106 U8* send = (U8*)(s + len);
a0ed51b3
LW
3107 while (s < send) {
3108 if (*s < 0x80) {
3109 s++;
3110 continue;
3111 }
3112 else {
dfe13c55 3113 up = (char*)s;
a0ed51b3 3114 s += UTF8SKIP(s);
dfe13c55 3115 down = (char*)(s - 1);
a0ed51b3
LW
3116 if (s > send || !((*down & 0xc0) == 0x80)) {
3117 warn("Malformed UTF-8 character");
3118 break;
3119 }
3120 while (down > up) {
3121 tmp = *up;
3122 *up++ = *down;
3123 *down-- = tmp;
3124 }
3125 }
3126 }
3127 up = SvPVX(TARG);
3128 }
a0d0e21e
LW
3129 down = SvPVX(TARG) + len - 1;
3130 while (down > up) {
3131 tmp = *up;
3132 *up++ = *down;
3133 *down-- = tmp;
3134 }
3135 (void)SvPOK_only(TARG);
79072805 3136 }
a0d0e21e
LW
3137 SP = MARK + 1;
3138 SETTARG;
79072805 3139 }
a0d0e21e 3140 RETURN;
79072805
LW
3141}
3142
76e3520e 3143STATIC SV *
8ac85365 3144mul128(SV *sv, U8 m)
55497cff 3145{
3146 STRLEN len;
3147 char *s = SvPV(sv, len);
3148 char *t;
3149 U32 i = 0;
3150
3151 if (!strnEQ(s, "0000", 4)) { /* need to grow sv */
09b7f37c 3152 SV *tmpNew = newSVpv("0000000000", 10);
55497cff 3153
09b7f37c 3154 sv_catsv(tmpNew, sv);
55497cff 3155 SvREFCNT_dec(sv); /* free old sv */
09b7f37c 3156 sv = tmpNew;
55497cff 3157 s = SvPV(sv, len);
3158 }
3159 t = s + len - 1;
3160 while (!*t) /* trailing '\0'? */
3161 t--;
3162 while (t > s) {
3163 i = ((*t - '0') << 7) + m;
3164 *(t--) = '0' + (i % 10);
3165 m = i / 10;
3166 }
3167 return (sv);
3168}
3169
a0d0e21e
LW
3170/* Explosives and implosives. */
3171
9d116dd7
JH
3172#if 'I' == 73 && 'J' == 74
3173/* On an ASCII/ISO kind of system */
ba1ac976 3174#define ISUUCHAR(ch) ((ch) >= ' ' && (ch) < 'a')
9d116dd7
JH
3175#else
3176/*
3177 Some other sort of character set - use memchr() so we don't match
3178 the null byte.
3179 */
80252599 3180#define ISUUCHAR(ch) (memchr(PL_uuemap, (ch), sizeof(PL_uuemap)-1) || (ch) == ' ')
9d116dd7
JH
3181#endif
3182
a0d0e21e 3183PP(pp_unpack)
79072805 3184{
4e35701f 3185 djSP;
a0d0e21e 3186 dPOPPOPssrl;
924508f0 3187 SV **oldsp = SP;
54310121 3188 I32 gimme = GIMME_V;
ed6116ce 3189 SV *sv;
a0d0e21e
LW
3190 STRLEN llen;
3191 STRLEN rlen;
3192 register char *pat = SvPV(left, llen);
3193 register char *s = SvPV(right, rlen);
3194 char *strend = s + rlen;
3195 char *strbeg = s;
3196 register char *patend = pat + llen;
3197 I32 datumtype;
3198 register I32 len;
3199 register I32 bits;
79072805 3200
a0d0e21e
LW
3201 /* These must not be in registers: */
3202 I16 ashort;
3203 int aint;
3204 I32 along;
ecfc5424
AD
3205#ifdef HAS_QUAD
3206 Quad_t aquad;
a0d0e21e
LW
3207#endif
3208 U16 aushort;
3209 unsigned int auint;
3210 U32 aulong;
ecfc5424 3211#ifdef HAS_QUAD
e862df63 3212 Uquad_t auquad;
a0d0e21e
LW
3213#endif
3214 char *aptr;
3215 float afloat;
3216 double adouble;
3217 I32 checksum = 0;
3218 register U32 culong;
3219 double cdouble;
fb73857a 3220 int commas = 0;
79072805 3221
54310121 3222 if (gimme != G_ARRAY) { /* arrange to do first one only */
a0d0e21e
LW
3223 /*SUPPRESS 530*/
3224 for (patend = pat; !isALPHA(*patend) || *patend == 'x'; patend++) ;
5a929a98 3225 if (strchr("aAZbBhHP", *patend) || *pat == '%') {
a0d0e21e
LW
3226 patend++;
3227 while (isDIGIT(*patend) || *patend == '*')
3228 patend++;
3229 }
3230 else
3231 patend++;
79072805 3232 }
a0d0e21e
LW
3233 while (pat < patend) {
3234 reparse:
bbdab043
CS
3235 datumtype = *pat++ & 0xFF;
3236 if (isSPACE(datumtype))
3237 continue;
a0d0e21e
LW
3238 if (pat >= patend)
3239 len = 1;
3240 else if (*pat == '*') {
3241 len = strend - strbeg; /* long enough */
3242 pat++;
3243 }
3244 else if (isDIGIT(*pat)) {
3245 len = *pat++ - '0';
3246 while (isDIGIT(*pat))
3247 len = (len * 10) + (*pat++ - '0');
3248 }
3249 else
3250 len = (datumtype != '@');
3251 switch(datumtype) {
3252 default:
bbdab043 3253 croak("Invalid type in unpack: '%c'", (int)datumtype);
fb73857a 3254 case ',': /* grandfather in commas but with a warning */
599cee73
PM
3255 if (commas++ == 0 && ckWARN(WARN_UNSAFE))
3256 warner(WARN_UNSAFE, "Invalid type in unpack: '%c'", (int)datumtype);
fb73857a 3257 break;
a0d0e21e
LW
3258 case '%':
3259 if (len == 1 && pat[-1] != '1')
3260 len = 16;
3261 checksum = len;
3262 culong = 0;
3263 cdouble = 0;
3264 if (pat < patend)
3265 goto reparse;
3266 break;
3267 case '@':
3268 if (len > strend - strbeg)
3269 DIE("@ outside of string");
3270 s = strbeg + len;
3271 break;
3272 case 'X':
3273 if (len > s - strbeg)
3274 DIE("X outside of string");
3275 s -= len;
3276 break;
3277 case 'x':
3278 if (len > strend - s)
3279 DIE("x outside of string");
3280 s += len;
3281 break;
3282 case 'A':
5a929a98 3283 case 'Z':
a0d0e21e
LW
3284 case 'a':
3285 if (len > strend - s)
3286 len = strend - s;
3287 if (checksum)
3288 goto uchar_checksum;
3289 sv = NEWSV(35, len);
3290 sv_setpvn(sv, s, len);
3291 s += len;
5a929a98 3292 if (datumtype == 'A' || datumtype == 'Z') {
a0d0e21e 3293 aptr = s; /* borrow register */
5a929a98
VU
3294 if (datumtype == 'Z') { /* 'Z' strips stuff after first null */
3295 s = SvPVX(sv);
3296 while (*s)
3297 s++;
3298 }
3299 else { /* 'A' strips both nulls and spaces */
3300 s = SvPVX(sv) + len - 1;
3301 while (s >= SvPVX(sv) && (!*s || isSPACE(*s)))
3302 s--;
3303 *++s = '\0';
3304 }
a0d0e21e
LW
3305 SvCUR_set(sv, s - SvPVX(sv));
3306 s = aptr; /* unborrow register */
3307 }
3308 XPUSHs(sv_2mortal(sv));
3309 break;
3310 case 'B':
3311 case 'b':
3312 if (pat[-1] == '*' || len > (strend - s) * 8)
3313 len = (strend - s) * 8;
3314 if (checksum) {
80252599
GS
3315 if (!PL_bitcount) {
3316 Newz(601, PL_bitcount, 256, char);
a0d0e21e 3317 for (bits = 1; bits < 256; bits++) {
80252599
GS
3318 if (bits & 1) PL_bitcount[bits]++;
3319 if (bits & 2) PL_bitcount[bits]++;
3320 if (bits & 4) PL_bitcount[bits]++;
3321 if (bits & 8) PL_bitcount[bits]++;
3322 if (bits & 16) PL_bitcount[bits]++;
3323 if (bits & 32) PL_bitcount[bits]++;
3324 if (bits & 64) PL_bitcount[bits]++;
3325 if (bits & 128) PL_bitcount[bits]++;
a0d0e21e
LW
3326 }
3327 }
3328 while (len >= 8) {
80252599 3329 culong += PL_bitcount[*(unsigned char*)s++];
a0d0e21e
LW
3330 len -= 8;
3331 }
3332 if (len) {
3333 bits = *s;
3334 if (datumtype == 'b') {
3335 while (len-- > 0) {
3336 if (bits & 1) culong++;
3337 bits >>= 1;
3338 }
3339 }
3340 else {
3341 while (len-- > 0) {
3342 if (bits & 128) culong++;
3343 bits <<= 1;
3344 }
3345 }
3346 }
79072805
LW
3347 break;
3348 }
a0d0e21e
LW
3349 sv = NEWSV(35, len + 1);
3350 SvCUR_set(sv, len);
3351 SvPOK_on(sv);
3352 aptr = pat; /* borrow register */
3353 pat = SvPVX(sv);
3354 if (datumtype == 'b') {
3355 aint = len;
3356 for (len = 0; len < aint; len++) {
3357 if (len & 7) /*SUPPRESS 595*/
3358 bits >>= 1;
3359 else
3360 bits = *s++;
3361 *pat++ = '0' + (bits & 1);
3362 }
3363 }
3364 else {
3365 aint = len;
3366 for (len = 0; len < aint; len++) {
3367 if (len & 7)
3368 bits <<= 1;
3369 else
3370 bits = *s++;
3371 *pat++ = '0' + ((bits & 128) != 0);
3372 }
3373 }
3374 *pat = '\0';
3375 pat = aptr; /* unborrow register */
3376 XPUSHs(sv_2mortal(sv));
3377 break;
3378 case 'H':
3379 case 'h':
3380 if (pat[-1] == '*' || len > (strend - s) * 2)
3381 len = (strend - s) * 2;
3382 sv = NEWSV(35, len + 1);
3383 SvCUR_set(sv, len);
3384 SvPOK_on(sv);
3385 aptr = pat; /* borrow register */
3386 pat = SvPVX(sv);
3387 if (datumtype == 'h') {
3388 aint = len;
3389 for (len = 0; len < aint; len++) {
3390 if (len & 1)
3391 bits >>= 4;
3392 else
3393 bits = *s++;
3280af22 3394 *pat++ = PL_hexdigit[bits & 15];
a0d0e21e
LW
3395 }
3396 }
3397 else {
3398 aint = len;
3399 for (len = 0; len < aint; len++) {
3400 if (len & 1)
3401 bits <<= 4;
3402 else
3403 bits = *s++;
3280af22 3404 *pat++ = PL_hexdigit[(bits >> 4) & 15];
a0d0e21e
LW
3405 }
3406 }
3407 *pat = '\0';
3408 pat = aptr; /* unborrow register */
3409 XPUSHs(sv_2mortal(sv));
3410 break;
3411 case 'c':
3412 if (len > strend - s)
3413 len = strend - s;
3414 if (checksum) {
3415 while (len-- > 0) {
3416 aint = *s++;
3417 if (aint >= 128) /* fake up signed chars */
3418 aint -= 256;
3419 culong += aint;
3420 }
3421 }
3422 else {
3423 EXTEND(SP, len);
bbce6d69 3424 EXTEND_MORTAL(len);
a0d0e21e
LW
3425 while (len-- > 0) {
3426 aint = *s++;
3427 if (aint >= 128) /* fake up signed chars */
3428 aint -= 256;
3429 sv = NEWSV(36, 0);
1e422769 3430 sv_setiv(sv, (IV)aint);
a0d0e21e
LW
3431 PUSHs(sv_2mortal(sv));
3432 }
3433 }
3434 break;
3435 case 'C':
3436 if (len > strend - s)
3437 len = strend - s;
3438 if (checksum) {
3439 uchar_checksum:
3440 while (len-- > 0) {
3441 auint = *s++ & 255;
3442 culong += auint;
3443 }
3444 }
3445 else {
3446 EXTEND(SP, len);
bbce6d69 3447 EXTEND_MORTAL(len);
a0d0e21e
LW
3448 while (len-- > 0) {
3449 auint = *s++ & 255;
3450 sv = NEWSV(37, 0);
1e422769 3451 sv_setiv(sv, (IV)auint);
a0d0e21e
LW
3452 PUSHs(sv_2mortal(sv));
3453 }
3454 }
3455 break;
a0ed51b3
LW
3456 case 'U':
3457 if (len > strend - s)
3458 len = strend - s;
3459 if (checksum) {
3460 while (len-- > 0 && s < strend) {
dfe13c55 3461 auint = utf8_to_uv((U8*)s, &along);
a0ed51b3 3462 s += along;
32d8b6e5
GA
3463 if (checksum > 32)
3464 cdouble += (double)auint;
3465 else
3466 culong += auint;
a0ed51b3
LW
3467 }
3468 }
3469 else {
3470 EXTEND(SP, len);
3471 EXTEND_MORTAL(len);
3472 while (len-- > 0 && s < strend) {
dfe13c55 3473 auint = utf8_to_uv((U8*)s, &along);
a0ed51b3
LW
3474 s += along;
3475 sv = NEWSV(37, 0);
bdeef251 3476 sv_setuv(sv, (UV)auint);
a0ed51b3
LW
3477 PUSHs(sv_2mortal(sv));
3478 }
3479 }
3480 break;
a0d0e21e 3481 case 's':
96e4d5b1 3482 along = (strend - s) / SIZE16;
a0d0e21e
LW
3483 if (len > along)
3484 len = along;
3485 if (checksum) {
3486 while (len-- > 0) {
96e4d5b1 3487 COPY16(s, &ashort);
3488 s += SIZE16;
a0d0e21e
LW
3489 culong += ashort;
3490 }
3491 }
3492 else {
3493 EXTEND(SP, len);
bbce6d69 3494 EXTEND_MORTAL(len);
a0d0e21e 3495 while (len-- > 0) {
96e4d5b1 3496 COPY16(s, &ashort);
3497 s += SIZE16;
a0d0e21e 3498 sv = NEWSV(38, 0);
1e422769 3499 sv_setiv(sv, (IV)ashort);
a0d0e21e
LW
3500 PUSHs(sv_2mortal(sv));
3501 }
3502 }
3503 break;
3504 case 'v':
3505 case 'n':
3506 case 'S':
96e4d5b1 3507 along = (strend - s) / SIZE16;
a0d0e21e
LW
3508 if (len > along)
3509 len = along;
3510 if (checksum) {
3511 while (len-- > 0) {
96e4d5b1 3512 COPY16(s, &aushort);
3513 s += SIZE16;
a0d0e21e
LW
3514#ifdef HAS_NTOHS
3515 if (datumtype == 'n')
6ad3d225 3516 aushort = PerlSock_ntohs(aushort);
79072805 3517#endif
a0d0e21e
LW
3518#ifdef HAS_VTOHS
3519 if (datumtype == 'v')
3520 aushort = vtohs(aushort);
79072805 3521#endif
a0d0e21e
LW
3522 culong += aushort;
3523 }
3524 }
3525 else {
3526 EXTEND(SP, len);
bbce6d69 3527 EXTEND_MORTAL(len);
a0d0e21e 3528 while (len-- > 0) {
96e4d5b1 3529 COPY16(s, &aushort);
3530 s += SIZE16;
a0d0e21e
LW
3531 sv = NEWSV(39, 0);
3532#ifdef HAS_NTOHS
3533 if (datumtype == 'n')
6ad3d225 3534 aushort = PerlSock_ntohs(aushort);
79072805 3535#endif
a0d0e21e
LW
3536#ifdef HAS_VTOHS
3537 if (datumtype == 'v')
3538 aushort = vtohs(aushort);
79072805 3539#endif
1e422769 3540 sv_setiv(sv, (IV)aushort);
a0d0e21e
LW
3541 PUSHs(sv_2mortal(sv));
3542 }
3543 }
3544 break;
3545 case 'i':
3546 along = (strend - s) / sizeof(int);
3547 if (len > along)
3548 len = along;
3549 if (checksum) {
3550 while (len-- > 0) {
3551 Copy(s, &aint, 1, int);
3552 s += sizeof(int);
3553 if (checksum > 32)
3554 cdouble += (double)aint;
3555 else
3556 culong += aint;
3557 }
3558 }
3559 else {
3560 EXTEND(SP, len);
bbce6d69 3561 EXTEND_MORTAL(len);
a0d0e21e
LW
3562 while (len-- > 0) {
3563 Copy(s, &aint, 1, int);
3564 s += sizeof(int);
3565 sv = NEWSV(40, 0);
20408e3c
GS
3566#ifdef __osf__
3567 /* Without the dummy below unpack("i", pack("i",-1))
3568 * return 0xFFffFFff instead of -1 for Digital Unix V4.0
3569 * cc with optimization turned on */
3570 (aint) ?
3571 sv_setiv(sv, (IV)aint) :
3572#endif
1e422769 3573 sv_setiv(sv, (IV)aint);
a0d0e21e
LW
3574 PUSHs(sv_2mortal(sv));
3575 }
3576 }
3577 break;
3578 case 'I':
3579 along = (strend - s) / sizeof(unsigned int);
3580 if (len > along)
3581 len = along;
3582 if (checksum) {
3583 while (len-- > 0) {
3584 Copy(s, &auint, 1, unsigned int);
3585 s += sizeof(unsigned int);
3586 if (checksum > 32)
3587 cdouble += (double)auint;
3588 else
3589 culong += auint;
3590 }
3591 }
3592 else {
3593 EXTEND(SP, len);
bbce6d69 3594 EXTEND_MORTAL(len);
a0d0e21e
LW
3595 while (len-- > 0) {
3596 Copy(s, &auint, 1, unsigned int);
3597 s += sizeof(unsigned int);
3598 sv = NEWSV(41, 0);
9d645a59
AB
3599#ifdef __osf__
3600 /* Without the dummy below unpack("I", pack("I",0xFFFFFFFF))
3601 * returns 1.84467440737096e+19 instead of 0xFFFFFFFF for
3602 * DEC C V5.8-009 on Digital UNIX V4.0 (Rev. 1091) (aka V4.0D)
3603 * with optimization turned on.
3604 * (DEC C V5.2-040 on Digital UNIX V4.0 (Rev. 564) (aka V4.0B)
3605 * does not have this problem even with -O4)
3606 */
3607 (auint) ?
3608 sv_setuv(sv, (UV)auint) :
3609#endif
1e422769 3610 sv_setuv(sv, (UV)auint);
a0d0e21e
LW
3611 PUSHs(sv_2mortal(sv));
3612 }
3613 }
3614 break;
3615 case 'l':
96e4d5b1 3616 along = (strend - s) / SIZE32;
a0d0e21e
LW
3617 if (len > along)
3618 len = along;
3619 if (checksum) {
3620 while (len-- > 0) {
96e4d5b1 3621 COPY32(s, &along);
3622 s += SIZE32;
a0d0e21e
LW
3623 if (checksum > 32)
3624 cdouble += (double)along;
3625 else
3626 culong += along;
3627 }
3628 }
3629 else {
3630 EXTEND(SP, len);
bbce6d69 3631 EXTEND_MORTAL(len);
a0d0e21e 3632 while (len-- > 0) {
96e4d5b1 3633 COPY32(s, &along);
3634 s += SIZE32;
a0d0e21e 3635 sv = NEWSV(42, 0);
1e422769 3636 sv_setiv(sv, (IV)along);
a0d0e21e
LW
3637 PUSHs(sv_2mortal(sv));
3638 }
79072805 3639 }
a0d0e21e
LW
3640 break;
3641 case 'V':
3642 case 'N':
3643 case 'L':
96e4d5b1 3644 along = (strend - s) / SIZE32;
a0d0e21e
LW
3645 if (len > along)
3646 len = along;
3647 if (checksum) {
3648 while (len-- > 0) {
96e4d5b1 3649 COPY32(s, &aulong);
3650 s += SIZE32;
a0d0e21e
LW
3651#ifdef HAS_NTOHL
3652 if (datumtype == 'N')
6ad3d225 3653 aulong = PerlSock_ntohl(aulong);
79072805 3654#endif
a0d0e21e
LW
3655#ifdef HAS_VTOHL
3656 if (datumtype == 'V')
3657 aulong = vtohl(aulong);
79072805 3658#endif
a0d0e21e
LW
3659 if (checksum > 32)
3660 cdouble += (double)aulong;
3661 else
3662 culong += aulong;
3663 }
3664 }
3665 else {
3666 EXTEND(SP, len);
bbce6d69 3667 EXTEND_MORTAL(len);
a0d0e21e 3668 while (len-- > 0) {
96e4d5b1 3669 COPY32(s, &aulong);
3670 s += SIZE32;
a0d0e21e
LW
3671#ifdef HAS_NTOHL
3672 if (datumtype == 'N')
6ad3d225 3673 aulong = PerlSock_ntohl(aulong);
79072805 3674#endif
a0d0e21e
LW
3675#ifdef HAS_VTOHL
3676 if (datumtype == 'V')
3677 aulong = vtohl(aulong);
79072805 3678#endif
1e422769 3679 sv = NEWSV(43, 0);
3680 sv_setuv(sv, (UV)aulong);
a0d0e21e
LW
3681 PUSHs(sv_2mortal(sv));
3682 }
3683 }
3684 break;
3685 case 'p':
3686 along = (strend - s) / sizeof(char*);
3687 if (len > along)
3688 len = along;
3689 EXTEND(SP, len);
bbce6d69 3690 EXTEND_MORTAL(len);
a0d0e21e
LW
3691 while (len-- > 0) {
3692 if (sizeof(char*) > strend - s)
3693 break;
3694 else {
3695 Copy(s, &aptr, 1, char*);
3696 s += sizeof(char*);
3697 }
3698 sv = NEWSV(44, 0);
3699 if (aptr)
3700 sv_setpv(sv, aptr);
3701 PUSHs(sv_2mortal(sv));
3702 }
3703 break;
def98dd4 3704 case 'w':
def98dd4 3705 EXTEND(SP, len);
bbce6d69 3706 EXTEND_MORTAL(len);
8ec5e241 3707 {
bbce6d69 3708 UV auv = 0;
3709 U32 bytes = 0;
3710
3711 while ((len > 0) && (s < strend)) {
3712 auv = (auv << 7) | (*s & 0x7f);
3713 if (!(*s++ & 0x80)) {
3714 bytes = 0;
3715 sv = NEWSV(40, 0);
3716 sv_setuv(sv, auv);
3717 PUSHs(sv_2mortal(sv));
3718 len--;
3719 auv = 0;
3720 }
3721 else if (++bytes >= sizeof(UV)) { /* promote to string */
bbce6d69 3722 char *t;
2d8e6c8d 3723 STRLEN n_a;
bbce6d69 3724
fc36a67e 3725 sv = newSVpvf("%.*Vu", (int)TYPE_DIGITS(UV), auv);
bbce6d69 3726 while (s < strend) {
3727 sv = mul128(sv, *s & 0x7f);
3728 if (!(*s++ & 0x80)) {
3729 bytes = 0;
3730 break;
3731 }
3732 }
2d8e6c8d 3733 t = SvPV(sv, n_a);
bbce6d69 3734 while (*t == '0')
3735 t++;
3736 sv_chop(sv, t);
3737 PUSHs(sv_2mortal(sv));
3738 len--;
3739 auv = 0;
3740 }
3741 }
3742 if ((s >= strend) && bytes)
3743 croak("Unterminated compressed integer");
3744 }
def98dd4 3745 break;
a0d0e21e
LW
3746 case 'P':
3747 EXTEND(SP, 1);
3748 if (sizeof(char*) > strend - s)
3749 break;
3750 else {
3751 Copy(s, &aptr, 1, char*);
3752 s += sizeof(char*);
3753 }