summaryrefslogtreecommitdiff
path: root/op.c
diff options
context:
space:
mode:
authorNick Ing-Simmons <nik@tiuk.ti.com>1999-05-14 21:04:22 +0000
committerNick Ing-Simmons <nik@tiuk.ti.com>1999-05-14 21:04:22 +0000
commitb7dc083c47d05133e90d62e8b587c747dab89267 (patch)
tree03912da6767f3d0fdff4dff2764a0e1f98cd3005 /op.c
parentcf11f4bfc3057837b3293e13b8edc0381b78e551 (diff)
downloadperl-b7dc083c47d05133e90d62e8b587c747dab89267.tar.gz
Experimental "slab" allocator for ops.
To try it -DPL_OP_SLAB_ALLOC for op.c This is for proof of concept only, it leaks memory (ops are not free'd) so don't use in embedded apps. If this minimalist version does not show performance gain then whole idea is worthless. Nick see's approx 12% speed up vs perlmalloc running perl -Ilib -MCPAN -e '' Solaris2.6, gcc-2.8.1 but numbers are not repeatable. p4raw-id: //depot/perl@3424
Diffstat (limited to 'op.c')
-rw-r--r--op.c79
1 files changed, 59 insertions, 20 deletions
diff --git a/op.c b/op.c
index 919d9d8170..94c0b392d1 100644
--- a/op.c
+++ b/op.c
@@ -22,8 +22,31 @@
#define CHECKCALL this->*PL_check
#else
#define CHECKCALL *PL_check
+#endif
+
+/* #define PL_OP_SLAB_ALLOC */
+
+#ifdef PL_OP_SLAB_ALLOC
+#define SLAB_SIZE 8192
+static char *PL_OpPtr = NULL;
+static int PL_OpSpace = 0;
+#define NewOp(m,var,c,type) do { if ((PL_OpSpace -= c*sizeof(type)) >= 0) \
+ var = (type *)(PL_OpPtr -= c*sizeof(type)); \
+ else \
+ var = (type *) Slab_Alloc(m,c*sizeof(type)); \
+ } while (0)
+
+static void *
+Slab_Alloc(int m, size_t sz)
+{
+ Newz(m,PL_OpPtr,SLAB_SIZE,char);
+ PL_OpSpace = SLAB_SIZE - sz;
+ return PL_OpPtr += PL_OpSpace;
+}
+
+#else
+#define NewOp(m, var, c, type) Newz(m, var, c, type)
#endif
-
/*
* In the following definition, the ", Nullop" is just to make the compiler
* think the expression is of the right type: croak actually does a Siglongjmp.
@@ -706,7 +729,13 @@ op_free(OP *o)
if (o->op_targ > 0)
pad_free(o->op_targ);
+#ifdef PL_OP_SLAB_ALLOC
+ if ((char *) o == PL_OpPtr)
+ {
+ }
+#else
Safefree(o);
+#endif
}
STATIC void
@@ -1999,8 +2028,11 @@ append_list(I32 type, LISTOP *first, LISTOP *last)
first->op_children += last->op_children;
if (first->op_children)
first->op_flags |= OPf_KIDS;
-
- Safefree(last);
+
+#ifdef PL_OP_SLAB_ALLOC
+#else
+ Safefree(last);
+#endif
return (OP*)first;
}
@@ -2055,7 +2087,7 @@ newLISTOP(I32 type, I32 flags, OP *first, OP *last)
{
LISTOP *listop;
- Newz(1101, listop, 1, LISTOP);
+ NewOp(1101, listop, 1, LISTOP);
listop->op_type = type;
listop->op_ppaddr = PL_ppaddr[type];
@@ -2089,7 +2121,7 @@ OP *
newOP(I32 type, I32 flags)
{
OP *o;
- Newz(1101, o, 1, OP);
+ NewOp(1101, o, 1, OP);
o->op_type = type;
o->op_ppaddr = PL_ppaddr[type];
o->op_flags = flags;
@@ -2113,7 +2145,7 @@ newUNOP(I32 type, I32 flags, OP *first)
if (PL_opargs[type] & OA_MARK)
first = force_list(first);
- Newz(1101, unop, 1, UNOP);
+ NewOp(1101, unop, 1, UNOP);
unop->op_type = type;
unop->op_ppaddr = PL_ppaddr[type];
unop->op_first = first;
@@ -2130,7 +2162,7 @@ OP *
newBINOP(I32 type, I32 flags, OP *first, OP *last)
{
BINOP *binop;
- Newz(1101, binop, 1, BINOP);
+ NewOp(1101, binop, 1, BINOP);
if (!first)
first = newOP(OP_NULL, 0);
@@ -2427,7 +2459,7 @@ newPMOP(I32 type, I32 flags)
dTHR;
PMOP *pmop;
- Newz(1101, pmop, 1, PMOP);
+ NewOp(1101, pmop, 1, PMOP);
pmop->op_type = type;
pmop->op_ppaddr = PL_ppaddr[type];
pmop->op_flags = flags;
@@ -2482,7 +2514,7 @@ pmruntime(OP *o, OP *expr, OP *repl)
? OP_REGCRESET
: OP_REGCMAYBE),0,expr);
- Newz(1101, rcop, 1, LOGOP);
+ NewOp(1101, rcop, 1, LOGOP);
rcop->op_type = OP_REGCOMP;
rcop->op_ppaddr = PL_ppaddr[OP_REGCOMP];
rcop->op_first = scalar(expr);
@@ -2577,7 +2609,7 @@ pmruntime(OP *o, OP *expr, OP *repl)
pm->op_pmflags |= PMf_MAYBE_CONST;
pm->op_pmpermflags |= PMf_MAYBE_CONST;
}
- Newz(1101, rcop, 1, LOGOP);
+ NewOp(1101, rcop, 1, LOGOP);
rcop->op_type = OP_SUBSTCONT;
rcop->op_ppaddr = PL_ppaddr[OP_SUBSTCONT];
rcop->op_first = scalar(repl);
@@ -2602,7 +2634,7 @@ OP *
newSVOP(I32 type, I32 flags, SV *sv)
{
SVOP *svop;
- Newz(1101, svop, 1, SVOP);
+ NewOp(1101, svop, 1, SVOP);
svop->op_type = type;
svop->op_ppaddr = PL_ppaddr[type];
svop->op_sv = sv;
@@ -2620,7 +2652,7 @@ newGVOP(I32 type, I32 flags, GV *gv)
{
dTHR;
GVOP *gvop;
- Newz(1101, gvop, 1, GVOP);
+ NewOp(1101, gvop, 1, GVOP);
gvop->op_type = type;
gvop->op_ppaddr = PL_ppaddr[type];
gvop->op_gv = (GV*)SvREFCNT_inc(gv);
@@ -2637,7 +2669,7 @@ OP *
newPVOP(I32 type, I32 flags, char *pv)
{
PVOP *pvop;
- Newz(1101, pvop, 1, PVOP);
+ NewOp(1101, pvop, 1, PVOP);
pvop->op_type = type;
pvop->op_ppaddr = PL_ppaddr[type];
pvop->op_pv = pv;
@@ -2975,7 +3007,7 @@ newSTATEOP(I32 flags, char *label, OP *o)
U32 seq = intro_my();
register COP *cop;
- Newz(1101, cop, 1, COP);
+ NewOp(1101, cop, 1, COP);
if (PERLDB_LINE && PL_curcop->cop_line && PL_curstash != PL_debstash) {
cop->op_type = OP_DBSTATE;
cop->op_ppaddr = PL_ppaddr[ OP_DBSTATE ];
@@ -3142,7 +3174,7 @@ new_logop(I32 type, I32 flags, OP** firstp, OP** otherp)
if (type == OP_ANDASSIGN || type == OP_ORASSIGN)
other->op_private |= OPpASSIGN_BACKWARDS; /* other is an OP_SASSIGN */
- Newz(1101, logop, 1, LOGOP);
+ NewOp(1101, logop, 1, LOGOP);
logop->op_type = type;
logop->op_ppaddr = PL_ppaddr[type];
@@ -3191,7 +3223,7 @@ newCONDOP(I32 flags, OP *first, OP *trueop, OP *falseop)
list(trueop);
scalar(falseop);
}
- Newz(1101, condop, 1, CONDOP);
+ NewOp(1101, condop, 1, CONDOP);
condop->op_type = OP_COND_EXPR;
condop->op_ppaddr = PL_ppaddr[OP_COND_EXPR];
@@ -3224,7 +3256,7 @@ newRANGE(I32 flags, OP *left, OP *right)
OP *flop;
OP *o;
- Newz(1101, condop, 1, CONDOP);
+ NewOp(1101, condop, 1, CONDOP);
condop->op_type = OP_RANGE;
condop->op_ppaddr = PL_ppaddr[OP_RANGE];
@@ -3385,7 +3417,7 @@ newWHILEOP(I32 flags, I32 debuggable, LOOP *loop, I32 whileline, OP *expr, OP *b
o = listop;
if (!loop) {
- Newz(1101,loop,1,LOOP);
+ NewOp(1101,loop,1,LOOP);
loop->op_type = OP_ENTERLOOP;
loop->op_ppaddr = PL_ppaddr[OP_ENTERLOOP];
loop->op_private = 0;
@@ -3411,6 +3443,7 @@ OP *
newFOROP(I32 flags,char *label,line_t forline,OP *sv,OP *expr,OP *block,OP *cont)
{
LOOP *loop;
+ LOOP *tmp;
OP *wop;
int padoff = 0;
I32 iterflags = 0;
@@ -3482,7 +3515,13 @@ newFOROP(I32 flags,char *label,line_t forline,OP *sv,OP *expr,OP *block,OP *cont
loop = (LOOP*)list(convert(OP_ENTERITER, iterflags,
append_elem(OP_LIST, expr, scalar(sv))));
assert(!loop->op_next);
+#ifdef PL_OP_SLAB_ALLOC
+ NewOp(1234,tmp,1,LOOP);
+ Copy(loop,tmp,1,LOOP);
+ loop = tmp;
+#else
Renew(loop, 1, LOOP);
+#endif
loop->op_targ = padoff;
wop = newWHILEOP(flags, 1, loop, forline, newOP(OP_ITER, 0), block, cont);
PL_copline = forline;
@@ -4466,7 +4505,7 @@ ck_eval(OP *o)
cUNOPo->op_first = 0;
op_free(o);
- Newz(1101, enter, 1, LOGOP);
+ NewOp(1101, enter, 1, LOGOP);
enter->op_type = OP_ENTERTRY;
enter->op_ppaddr = PL_ppaddr[OP_ENTERTRY];
enter->op_private = 0;
@@ -4877,7 +4916,7 @@ ck_grep(OP *o)
OPCODE type = o->op_type == OP_GREPSTART ? OP_GREPWHILE : OP_MAPWHILE;
o->op_ppaddr = PL_ppaddr[OP_GREPSTART];
- Newz(1101, gwop, 1, LOGOP);
+ NewOp(1101, gwop, 1, LOGOP);
if (o->op_flags & OPf_STACKED) {
OP* k;