I measured the size of some big modules, with B::Stats and B::C, statically compiled.
This amounts to about to the same size as dynamic usage via perl, with all options and modules used at once. I.e. the worst-case scenario.
Interestingly Module::Build is much harder to compile - you'd need 6GB RAM at least -
and much bigger in the end-result than Moose, which compiles/compresses really fine.
Modules
Module::Build
perl -e'use Module::Build: print q(k)'
ops | 68K |
files | 48 |
src lines | 18K |
compiled c lines | 1.5M |
perl compiler memory | 360M |
gcc compiler memory | 3.4G |
executable size | 37M |
Moose
ops | 91K |
files | 109 |
src lines | 28K |
compiled c lines | 889K |
perl compiler memory | 218M |
gcc compiler memory | 1.6G |
executable size | 23M |
DateTime::TimeZone
ops | 2.3K |
files | 6 |
src lines | 2.2K |
compiled c lines | 130K |
perl compiler memory | 19M |
gcc compiler memory | 415M |
executable size | 32M |
Typical Apps
Biggest cPanel app
The recipe for less than 2MB RAM and gcc < 4.5 is:
cc_harness -E -o$@-cpp.c $@.c
cc_harness -O0 -fno-var-tracking -fno-stack-protector \
-fno-tree-loop-optimize \
-fpreprocessed -fno-exceptions $@-cpp.c
ops | 467K |
files | 539 |
src lines | 95K |
compiled c lines | 1.5M |
perl compiler memory | 352M |
gcc compiler memory (32bit -O0) | 2.0G |
executable size | 61M |
Typical cPanel app
ops | 120K |
files | 156 |
src lines | 28K |
compiled c lines | 1M |
perl compiler memory | 120M |
gcc compiler memory (32bit -O0) | 734M |
executable size | 42M |
dzil --help
ops | 167K |
files | 214 |
src lines | 48K |
compiled c lines | 1.4M |
perl compiler memory | 485M |
gcc compiler memory | 4.5G |
executable size | 46M |
B::C time | 182s |
cc time | 348s |
Minimal Web apps
A simple two-state form like this without Android.
Plack
ops | 78K |
files | 98 |
src lines | 29K |
compiled c lines | 388K |
perl compiler memory | 95M |
gcc compiler memory | 1.0G |
executable size | 11M |
B::C time | 11s |
cc time | 72s |
Dancer
ops | 123K |
files | 143 |
src lines | 40K |
compiled c lines | 517K |
perl compiler memory | 159M |
gcc compiler memory | 1.1G |
executable size | 14M |
B::C time | 20s |
cc time | 97s |
Mojo (daemon)
ops | 151K |
files | 150 |
src lines | 46K |
compiled c lines | 622K |
perl compiler memory | 153M |
gcc compiler memory | 1.4G |
executable size | 17M |
B::C time | 29s |
cc time | 114s |
Catalyst
catalyst.pl Catalyst::Test; script/catalyst_test_create.pl. Same numbers with the server
ops | 199K |
files | 214 |
src lines | 57K |
compiled c lines | 941K |
perl compiler memory | 267M |
gcc compiler memory | 1.7G |
executable size | 26M |
B::C time | 44s |
cc time | 169s |
Minimal OO frameworks
Moose
ops | 91K |
files | 109 |
src lines | 28K |
compiled c lines | 889K |
perl compiler memory | 218M |
gcc compiler memory | 1.6G |
executable size | 23M |
Mouse
ops | 20K |
files | 23 |
src lines | 6.5K |
compiled c lines | 120K |
perl compiler memory | 19M |
gcc compiler memory | 427M |
executable size | 3.3M |
Moo
ops | 6.4K |
files | 16 |
src lines | 3.7K |
compiled c lines | 96K |
perl compiler memory | 17M |
gcc compiler memory | error (326M) |
executable size | error (2.7M) |
Mo
ops | 3.7K |
files | 8 |
src lines | 2.6K |
compiled c lines | 67K |
perl compiler memory | - (too tiny, not measurable) |
gcc compiler memory | 346M |
executable size | 1.8M |
Summary
If you compile an app like Module::Build, i.e dzil (which means in the convoluted java-like style like Module::Build) you need a really big build machine, and developers will not be able to compile it by themselves, because they have not enough RAM. Errors will only appear daily (from the build machine), not immediately.
Moose alone is okay to use, dzil for sure not.
A minimal web app with Plack, Dancer, Mojo and even Catalyst look all okay.
SW metrics to explain the style, why the numbers are so different in the next blog post.
So if you plan to do "modern perl" you'll either take care, like using Mouse or Moo, or do something like prefork or FCGI and do not care.
Measured numbers are for x86_64 perl5.14.2-nt, gcc -Os -msse4.2 -march=corei7
| * | gcc | c | exe |
| subs | * | mem[M] | lines | size |
Dist::Zilla | 4309 | * | 4500 | 1320K | 46M |
Module::Build | 4017 | * | 3400 | 1500K | 37M |
CPAN | 4142 | * | 3300 | 1319K | 33M |
Catalyst | 4508 | * | 1700 | 941K | 26M |
ExtUtils::CBuilder | 1633 | * | 1552 | 595K | 15M |
Moose | 2523 | * | 1600 | 889K | 23M |
Mojo | 2559 | * | 1400 | 622K | 17M |
Dancer | 2368 | * | 1100 | 517K | 14M |
Plack | 1945 | * | 1000 | 388K | 11M |
ExtUtils::MakeMaker | 1233 | * | 957 | 335K | 8.4M |
DateTime | 1277 | * | 840 | 293K | 6.8M |
DateTime::TimeZone | 542 | * | 415 | 130K | 3.1M |
DateTime::Locale | 471 | * | 464 | 138K | 3.4M |
Mouse | 743 | * | 427 | 120K | 3.3M |
Moo | 572 | * | 326 | 96K | 2.7M |
Mo | 388 | * | 346 | 67K | 1.8M |
Makefile tricks
If you want to check in your Makefile how much memory is available and
disable some gcc optimizations accordingly you can something like this:
Makefile snippet
AVAILMEM=$(shell availmem.sh)
bigapp: $@.pl
if [ ${AVAILMEM} -lt 2000000 ]; then \
echo "less than 2GB free RAM, disable some gcc optimizations"; \
/bin/rm -f $@ $@-cpp.c $@.c; \
perl -c $@.pl; \
perl -MO=C,-O3,-o$@.c $@.pl; \
cc_harness -E -o$@-cpp.c $@.c; \
cc_harness -O0 -fno-var-tracking -fno-stack-protector \
-fno-tree-loop-optimize -fpreprocessed \
-fno-exceptions $@-cpp.c -o$@; \
/bin/rm -f $@-cpp.c $@.c; \
else \
perlcc $(PERLCC_OPTS) $@.pl -o $@; \
fi
My availmem.sh on linux:
#!/bin/sh
memtotal=$(perl -ane'print $F[1] if /^MemTotal:/' /proc/meminfo)
memused=$(perl -ane'print $F[1] if /^Active:/' /proc/meminfo)
echo $(($memtotal - $memused))
This is a surprising result, Module::Build is not that large of a codebase, why should the compiled version be so large? Do you have any ideas?
Can you clarify what you are analyzing? Are you saying to to use something like Module::Build you are needing 3.5gig of memory? And that using Moose requires 1.6gig of memory?
Fascinating stuff. Please give awstats a try if you have some time. :)
I win!!
Chris: I'm testing static compilations. That's everything the modules provides, compiled down to static C. In dynamic perl you would not need that many functions, because not all code paths are always run. Something like a worst-case scenario, like a 50MB lisp image without tree-shaker.
Additionally the "gcc compiler memory" gives you some idea how much memory you would need on your build machine to compile such a static dump via perlcc. Typically jr devs have only 2GB RAM free, so bigger apps are impossible to compile.
I didn't tell you the compile times, but it's linear to gcc memory and compiles c lines.
It only gives a rough estimation, but the compiler is a good measure of a static dump what's in your program. Similar to a MAD dump.
I can also estimate what how big e.g. an android apk will be, if you want to provide cross-compiled native perl apps. You'll also have tough memory limits there.
You also see the advantage of perl over java e.g. for android deployment. perl-style perl code is much smaller and much easier compilable than java-style perl code.
I'll still have to do some basic SW metrics to qualify and quantify the different coding styles, to explain those interesting numbers. That will another blog post.
Hmmm. You realize 8GiB (dual-channel) is
Also, for debug builds, try -O0, that'll make gcc use a lot less memory.
(Trying again, it takes HTML tags. Oops. And no edit… this time I'm using preview1)
Hmmm. You realize 8GiB (dual-channel) is <$50, and 12 GiB (tri-channel) is <$70?
Also, for debug builds, try -O0, that'll make gcc use a lot less memory.
Anthony: Sure, I know that RAM is cheap.
I have 16G because my mainboard does not take 32G.
Problem is reality: From our ~200 developers very few have more than 4GB. Most develop even in VM's with about 1-2MB RAM.
My target is also a webhosting VM with typically 512MB - 1G RAM. The webhosting industry will not change fast. They will rather add more VM's than add more RAM to one VM.
-O0 is out of question because the binary must be optimized. That's the whole deal of static compilation: Optimize once at compile-time, not every time at run-time.
BTW: You can easily check which gcc optimizer paths use most time and memory by passing -v to gcc, check the cc1 command-line and run it with all the -quiet.
-fno-tree-loop-optimize saves most memory in my case, and it is also broken before 4.5.
E.g.
/usr/lib/gcc/x86_64-linux-gnu/4.6/cc1 -v -I /usr/local/include -I /usr/local/lib/perl5/5.14.2/x86_64-linux/CORE -imultilib . -imultiarch x86_64-linux-gnu -D _LARGEFILE_SOURCE -D _FILE_OFFSET_BITS=64 -Os -version -fno-strict-aliasing -fstack-protector dancer.c
Compiler executable checksum: aa5cb4c8e9c62c6cc9349213df314c34
set_regex_charset get_regex_charset get_regex_charset_name {GC 282152k -> 100517k} {GC 262534k -> 166128k} perl_init_aaaa perl_init_aaab perl_init_aaac perl_init_aaad perl_init_aaae perl_init_aaaf perl_init_aaag perl_init_aaah perl_init_aaai perl_init_aaaj perl_init_aaak perl_init_aaal perl_init_aaam perl_init_aaan perl_init_aaao perl_init_aaap perl_init_aaaq perl_init_aaar perl_init_aaas perl_init_aaat perl_init_aaau perl_init_aaav perl_init_aaaw perl_init_aaax perl_init_aaay perl_init_aaaz perl_init_aaba {GC 333199k -> 287947k} perl_init_aabb perl_init_aabc perl_init_aabd perl_init my_share_hek fast_perl_destruct xs_init dl_init main
Analyzing compilation unit
Performing interprocedural optimizations
{GC 577178k -> 437755k} Assembling functions:
perl_init_aaag xs_init my_share_hek.constprop.0 perl_init_aabd perl_init_aabb perl_init_aaba perl_init_aaaz perl_init_aaay perl_init_aaax perl_init_aaaw perl_init_aaav perl_init_aaau perl_init_aaat perl_init_aaas perl_init_aaar perl_init_aaaq perl_init_aaap perl_init_aaao {GC 875984k -> 540786k} perl_init_aaan perl_init_aaam perl_init_aaal perl_init_aaak perl_init_aaaj perl_init_aaai perl_init_aaah perl_init_aaae perl_init_aaad perl_init_aaac perl_init_aaab perl_init_aaaa perl_init my_share_hek fast_perl_destruct main
Execution times (seconds)
garbage collection : 1.59 ( 2%) usr 0.00 ( 0%) sys 1.58 ( 1%) wall 0 kB ( 0%) ggc
callgraph construction: 0.23 ( 0%) usr 0.02 ( 0%) sys 0.38 ( 0%) wall 93797 kB ( 4%) ggc
callgraph optimization: 0.10 ( 0%) usr 0.00 ( 0%) sys 0.08 ( 0%) wall 51 kB ( 0%) ggc
varpool construction : 2.46 ( 3%) usr 0.10 ( 1%) sys 2.54 ( 2%) wall 286759 kB (13%) ggc
ipa cp : 0.01 ( 0%) usr 0.00 ( 0%) sys 0.01 ( 0%) wall 2415 kB ( 0%) ggc
ipa reference : 0.02 ( 0%) usr 0.00 ( 0%) sys 0.03 ( 0%) wall 0 kB ( 0%) ggc
ipa profile : 0.00 ( 0%) usr 0.00 ( 0%) sys 0.01 ( 0%) wall 0 kB ( 0%) ggc
ipa pure const : 0.20 ( 0%) usr 0.00 ( 0%) sys 0.21 ( 0%) wall 1 kB ( 0%) ggc
cfg construction : 0.00 ( 0%) usr 0.00 ( 0%) sys 0.02 ( 0%) wall 72 kB ( 0%) ggc
cfg cleanup : 0.17 ( 0%) usr 0.00 ( 0%) sys 0.14 ( 0%) wall 738 kB ( 0%) ggc
trivially dead code : 0.56 ( 1%) usr 0.00 ( 0%) sys 0.46 ( 0%) wall 0 kB ( 0%) ggc
df scan insns : 0.86 ( 1%) usr 0.00 ( 0%) sys 0.88 ( 1%) wall 3 kB ( 0%) ggc
df multiple defs : 0.17 ( 0%) usr 0.00 ( 0%) sys 0.18 ( 0%) wall 0 kB ( 0%) ggc
df reaching defs : 1.11 ( 1%) usr 0.02 ( 0%) sys 1.05 ( 1%) wall 0 kB ( 0%) ggc
df live regs : 1.44 ( 1%) usr 0.00 ( 0%) sys 1.48 ( 1%) wall 0 kB ( 0%) ggc
df live&initialized regs: 0.39 ( 0%) usr 0.00 ( 0%) sys 0.41 ( 0%) wall 0 kB ( 0%) ggc
df use-def / def-use chains: 0.36 ( 0%) usr 0.00 ( 0%) sys 0.32 ( 0%) wall 0 kB ( 0%) ggc
df reg dead/unused notes: 1.52 ( 2%) usr 0.03 ( 0%) sys 1.67 ( 2%) wall 14615 kB ( 1%) ggc
register information : 0.44 ( 0%) usr 0.00 ( 0%) sys 0.38 ( 0%) wall 0 kB ( 0%) ggc
alias analysis : 0.62 ( 1%) usr 0.00 ( 0%) sys 0.48 ( 0%) wall 37143 kB ( 2%) ggc
alias stmt walking : 9.35 (10%) usr 0.45 ( 3%) sys 9.74 ( 9%) wall 13230 kB ( 1%) ggc
register scan : 0.12 ( 0%) usr 0.00 ( 0%) sys 0.16 ( 0%) wall 83 kB ( 0%) ggc
rebuild jump labels : 0.17 ( 0%) usr 0.00 ( 0%) sys 0.14 ( 0%) wall 0 kB ( 0%) ggc
preprocessing : 2.83 ( 3%) usr 2.86 (20%) sys 5.37 ( 5%) wall 30097 kB ( 1%) ggc
lexical analysis : 2.76 ( 3%) usr 4.01 (28%) sys 7.09 ( 6%) wall 0 kB ( 0%) ggc
parser : 5.95 ( 6%) usr 5.11 (36%) sys 11.13 (10%) wall 639234 kB (30%) ggc
inline heuristics : 0.37 ( 0%) usr 0.00 ( 0%) sys 0.35 ( 0%) wall 2577 kB ( 0%) ggc
integration : 0.08 ( 0%) usr 0.03 ( 0%) sys 0.09 ( 0%) wall 15860 kB ( 1%) ggc
tree gimplify : 1.20 ( 1%) usr 0.06 ( 0%) sys 1.26 ( 1%) wall 176924 kB ( 8%) ggc
tree eh : 0.02 ( 0%) usr 0.01 ( 0%) sys 0.02 ( 0%) wall 0 kB ( 0%) ggc
tree CFG construction : 0.09 ( 0%) usr 0.00 ( 0%) sys 0.08 ( 0%) wall 13789 kB ( 1%) ggc
tree CFG cleanup : 0.37 ( 0%) usr 0.00 ( 0%) sys 0.47 ( 0%) wall 809 kB ( 0%) ggc
tree VRP : 1.18 ( 1%) usr 0.08 ( 1%) sys 1.44 ( 1%) wall 41500 kB ( 2%) ggc
tree copy propagation : 0.60 ( 1%) usr 0.04 ( 0%) sys 0.68 ( 1%) wall 156 kB ( 0%) ggc
tree find ref. vars : 0.12 ( 0%) usr 0.00 ( 0%) sys 0.11 ( 0%) wall 10750 kB ( 1%) ggc
tree PTA : 10.76 (11%) usr 0.03 ( 0%) sys 10.87 (10%) wall 36777 kB ( 2%) ggc
tree PHI insertion : 0.02 ( 0%) usr 0.01 ( 0%) sys 0.05 ( 0%) wall 3807 kB ( 0%) ggc
tree SSA rewrite : 0.42 ( 0%) usr 0.01 ( 0%) sys 0.41 ( 0%) wall 68588 kB ( 3%) ggc
tree SSA other : 0.23 ( 0%) usr 0.09 ( 1%) sys 0.23 ( 0%) wall 6 kB ( 0%) ggc
tree SSA incremental : 0.54 ( 1%) usr 0.02 ( 0%) sys 0.54 ( 0%) wall 8532 kB ( 0%) ggc
tree operand scan : 0.54 ( 1%) usr 0.14 ( 1%) sys 0.71 ( 1%) wall 70745 kB ( 3%) ggc
dominator optimization: 1.04 ( 1%) usr 0.01 ( 0%) sys 1.13 ( 1%) wall 62937 kB ( 3%) ggc
tree CCP : 1.04 ( 1%) usr 0.03 ( 0%) sys 1.11 ( 1%) wall 17702 kB ( 1%) ggc
tree PHI const/copy prop: 0.01 ( 0%) usr 0.00 ( 0%) sys 0.00 ( 0%) wall 1 kB ( 0%) ggc
tree split crit edges : 0.03 ( 0%) usr 0.00 ( 0%) sys 0.01 ( 0%) wall 4725 kB ( 0%) ggc
tree FRE : 1.29 ( 1%) usr 0.12 ( 1%) sys 1.44 ( 1%) wall 2588 kB ( 0%) ggc
tree code sinking : 0.12 ( 0%) usr 0.00 ( 0%) sys 0.12 ( 0%) wall 642 kB ( 0%) ggc
tree linearize phis : 0.05 ( 0%) usr 0.00 ( 0%) sys 0.05 ( 0%) wall 0 kB ( 0%) ggc
tree forward propagate: 0.16 ( 0%) usr 0.02 ( 0%) sys 0.13 ( 0%) wall 4405 kB ( 0%) ggc
tree phiprop : 0.02 ( 0%) usr 0.00 ( 0%) sys 0.00 ( 0%) wall 0 kB ( 0%) ggc
tree conservative DCE : 0.43 ( 0%) usr 0.21 ( 1%) sys 0.53 ( 0%) wall 75 kB ( 0%) ggc
tree aggressive DCE : 0.35 ( 0%) usr 0.18 ( 1%) sys 0.52 ( 0%) wall 4434 kB ( 0%) ggc
tree DSE : 0.34 ( 0%) usr 0.02 ( 0%) sys 0.38 ( 0%) wall 4021 kB ( 0%) ggc
tree loop bounds : 0.03 ( 0%) usr 0.00 ( 0%) sys 0.03 ( 0%) wall 304 kB ( 0%) ggc
tree loop invariant motion: 0.05 ( 0%) usr 0.00 ( 0%) sys 0.05 ( 0%) wall 0 kB ( 0%) ggc
tree canonical iv : 0.02 ( 0%) usr 0.01 ( 0%) sys 0.03 ( 0%) wall 1681 kB ( 0%) ggc
scev constant prop : 0.00 ( 0%) usr 0.00 ( 0%) sys 0.07 ( 0%) wall 1934 kB ( 0%) ggc
complete unrolling : 0.19 ( 0%) usr 0.01 ( 0%) sys 0.32 ( 0%) wall 26098 kB ( 1%) ggc
tree iv optimization : 0.32 ( 0%) usr 0.00 ( 0%) sys 0.30 ( 0%) wall 17886 kB ( 1%) ggc
tree loop init : 0.05 ( 0%) usr 0.00 ( 0%) sys 0.05 ( 0%) wall 923 kB ( 0%) ggc
tree copy headers : 0.00 ( 0%) usr 0.00 ( 0%) sys 0.01 ( 0%) wall 1402 kB ( 0%) ggc
tree SSA uncprop : 0.02 ( 0%) usr 0.00 ( 0%) sys 0.02 ( 0%) wall 0 kB ( 0%) ggc
tree rename SSA copies: 0.12 ( 0%) usr 0.00 ( 0%) sys 0.10 ( 0%) wall 0 kB ( 0%) ggc
dominance frontiers : 0.06 ( 0%) usr 0.00 ( 0%) sys 0.07 ( 0%) wall 0 kB ( 0%) ggc
dominance computation : 0.35 ( 0%) usr 0.01 ( 0%) sys 0.17 ( 0%) wall 0 kB ( 0%) ggc
control dependences : 0.01 ( 0%) usr 0.00 ( 0%) sys 0.01 ( 0%) wall 0 kB ( 0%) ggc
out of ssa : 0.25 ( 0%) usr 0.00 ( 0%) sys 0.27 ( 0%) wall 690 kB ( 0%) ggc
expand vars : 0.12 ( 0%) usr 0.01 ( 0%) sys 0.15 ( 0%) wall 20164 kB ( 1%) ggc
expand : 2.03 ( 2%) usr 0.02 ( 0%) sys 2.04 ( 2%) wall 209068 kB (10%) ggc
post expand cleanups : 0.02 ( 0%) usr 0.00 ( 0%) sys 0.04 ( 0%) wall 69 kB ( 0%) ggc
varconst : 0.00 ( 0%) usr 0.01 ( 0%) sys 0.00 ( 0%) wall 377 kB ( 0%) ggc
forward prop : 0.78 ( 1%) usr 0.01 ( 0%) sys 0.74 ( 1%) wall 15055 kB ( 1%) ggc
CSE : 1.19 ( 1%) usr 0.00 ( 0%) sys 1.18 ( 1%) wall 5718 kB ( 0%) ggc
dead code elimination : 0.38 ( 0%) usr 0.00 ( 0%) sys 0.42 ( 0%) wall 0 kB ( 0%) ggc
dead store elim1 : 0.88 ( 1%) usr 0.00 ( 0%) sys 0.83 ( 1%) wall 16057 kB ( 1%) ggc
dead store elim2 : 0.80 ( 1%) usr 0.00 ( 0%) sys 0.82 ( 1%) wall 15857 kB ( 1%) ggc
loop analysis : 0.01 ( 0%) usr 0.00 ( 0%) sys 0.03 ( 0%) wall 1760 kB ( 0%) ggc
loop invariant motion : 0.35 ( 0%) usr 0.00 ( 0%) sys 0.42 ( 0%) wall 0 kB ( 0%) ggc
CPROP : 1.26 ( 1%) usr 0.01 ( 0%) sys 1.24 ( 1%) wall 16689 kB ( 1%) ggc
code hoisting : 7.99 ( 8%) usr 0.06 ( 0%) sys 8.03 ( 7%) wall 0 kB ( 0%) ggc
CSE 2 : 1.02 ( 1%) usr 0.00 ( 0%) sys 1.04 ( 1%) wall 249 kB ( 0%) ggc
branch prediction : 0.11 ( 0%) usr 0.00 ( 0%) sys 0.09 ( 0%) wall 1755 kB ( 0%) ggc
combiner : 0.95 ( 1%) usr 0.00 ( 0%) sys 1.01 ( 1%) wall 8850 kB ( 0%) ggc
if-conversion : 0.26 ( 0%) usr 0.00 ( 0%) sys 0.30 ( 0%) wall 2617 kB ( 0%) ggc
regmove : 0.17 ( 0%) usr 0.00 ( 0%) sys 0.21 ( 0%) wall 0 kB ( 0%) ggc
integrated RA : 4.32 ( 4%) usr 0.02 ( 0%) sys 4.32 ( 4%) wall 24765 kB ( 1%) ggc
reload : 1.84 ( 2%) usr 0.00 ( 0%) sys 1.89 ( 2%) wall 3241 kB ( 0%) ggc
reload CSE regs : 2.25 ( 2%) usr 0.03 ( 0%) sys 2.26 ( 2%) wall 33987 kB ( 2%) ggc
zee : 0.11 ( 0%) usr 0.00 ( 0%) sys 0.13 ( 0%) wall 0 kB ( 0%) ggc
thread pro- & epilogue: 0.30 ( 0%) usr 0.00 ( 0%) sys 0.36 ( 0%) wall 49 kB ( 0%) ggc
combine stack adjustments: 0.01 ( 0%) usr 0.00 ( 0%) sys 0.02 ( 0%) wall 0 kB ( 0%) ggc
peephole 2 : 0.18 ( 0%) usr 0.00 ( 0%) sys 0.22 ( 0%) wall 1618 kB ( 0%) ggc
hard reg cprop : 0.73 ( 1%) usr 0.00 ( 0%) sys 0.73 ( 1%) wall 375 kB ( 0%) ggc
scheduling 2 : 4.21 ( 4%) usr 0.02 ( 0%) sys 4.32 ( 4%) wall 1084 kB ( 0%) ggc
machine dep reorg : 0.01 ( 0%) usr 0.00 ( 0%) sys 0.00 ( 0%) wall 0 kB ( 0%) ggc
reorder blocks : 0.02 ( 0%) usr 0.00 ( 0%) sys 0.00 ( 0%) wall 1 kB ( 0%) ggc
final : 0.92 ( 1%) usr 0.03 ( 0%) sys 0.98 ( 1%) wall 9 kB ( 0%) ggc
variable output : 1.53 ( 2%) usr 0.02 ( 0%) sys 1.56 ( 1%) wall 27544 kB ( 1%) ggc
rest of compilation : 1.11 ( 1%) usr 0.00 ( 0%) sys 1.04 ( 1%) wall 2185 kB ( 0%) ggc
remove unused locals : 2.37 ( 2%) usr 0.06 ( 0%) sys 2.18 ( 2%) wall 0 kB ( 0%) ggc
address taken : 0.22 ( 0%) usr 0.01 ( 0%) sys 0.14 ( 0%) wall 0 kB ( 0%) ggc
unaccounted todo : 0.32 ( 0%) usr 0.00 ( 0%) sys 0.36 ( 0%) wall 0 kB ( 0%) ggc
repair loop structures: 0.13 ( 0%) usr 0.01 ( 0%) sys 0.14 ( 0%) wall 524 kB ( 0%) ggc
TOTAL : 96.79 14.17 111.21 2138012 kB
@anthony: Even though RAM is cheap, finding a nice laptop/netbook which supports 16-32GB or larger (and preferably an SSD drive) is still a challenge.
*Extremely* surprising. I have no idea why M::B would be so huge under this metric. Can you tell whether it's M::B itself, or its dependencies?
The initial idea why M::B uses much more compiled space is related to the number of subs (CV). The numbers of those are in the last table.
The memory and exe size is roughly comparable to this metric and less to the number of C lines, ops or src lines.
So the lemma would be: Too functional perl style is discouraged, as perl functions are too heavy.
The other explanation I have could be related to the number of global symbols (GV). These currently cannot be compiled down to static code, they need to be initialized dynamically, this increasing the code size and runtime.
But I have not measured them yet.