You are viewing a plain text version of this content. The canonical link for it is here.
Posted to modperl@perl.apache.org by Gerald Richter <ri...@ecos.de> on 2000/07/27 20:51:36 UTC

RE: Templating System (preview Embperl 2.0)

>
> Jonathan and I spoke briefly at the conference about working together on a
> combined effort of some sort - I could really use Mason's caching
> technology, and he could really use my XML stuff. So maybe something will
> come of that, who knows.

That's exactly what I already started with Embperl 2.0. Embperl 1.3b4
(http://perl.apache.org/embperl/) has already a component handling with the
same power like Mason (also the approach is a little different). Additionaly
it handles some html specific things, that Mason doesn't (like dynamic
tables, formfiled processing, etc.).

Embperl 2.0 add's the possibility to define/modify your own syntax, so you
are able to define custom html/xml tags that call's subroutines (or generate
arbitary perl code, like loops etc.). Also I personaly don't like that
approach, you are able to define very easy things like using the id
attribute of an existing tag, like it was requested earlier in this thread,
to genrate perl code from it. On my talk at the Perl conference I had an
example how at dynamicly rewrite the source url of every image tag, just by
defining a perl subroutine with three lines of code. To keep it fast Embperl
is written in C. It parses the html/xml into a DOM Tree and precompiles the
Perl code into an a Perl sub (That is done by Embperl 1.x already for three
years). Up to this point Embperl 2.0 is already working (also the current
version is called alpha, this is mainly due to the missing features and not
a problem a stability). Next I will add caching of the output or
intermediate steps (the currenty alpha already caches the Source DOM tree
and the compiled Perl code). Unless Mason, Embperl is not only able to cache
plain HTML (or other ascii) files, but also cache DOM trees in any step of
the the processing. To make this memory efficient, I have written a DOM
storage for Embperl which is very memory efficient (e.g. able to store only
differences between serveral modification of a DOM tree) and fast. Like
AxKit Embperl will be able to join any number of processors (stylesheets in
AxKit terminology) to form a processing pipe that modifies the DOM tree.
This will for example make it possible to use EMbperl and SSI in the same
page, while the file must be parsed only once. Since Embperl can replace any
of these steps by custom modules, there will also be the possiblity to use
an XML parser (instead of the Embperl parser, which is optimized for the
current usage) and use things like XSLT to create the HTML (or whatever)
output. For XML processing Embperl 2.0 will offer similar features like
AxKit, but written in C, so it will be faster.

Let me say one word to mixing design and code. Template::Toolkit (and other
modules, which don't directly include perl code), reclains, that they better
separate code and design, but form my point of view they simply create a new
"language". If you want to separate code and design, that could also be done
with modules like Embperl, Mason, ASP which directly inlcude Perl code.
Simply create a Perl module which contains your code and do only calls to
this module and not include the real code in your page. That's only a matter
of discipline. The main adavatage I see for this modules is, that they don't
restrict you to do so. For small projects, it's often very handy to inlcude
the few lines of Perl code you need directly in the page.

Gerald





-------------------------------------------------------------
Gerald Richter    ecos electronic communication services gmbh
Internetconnect * Webserver/-design/-datenbanken * Consulting

Post:       Tulpenstrasse 5         D-55276 Dienheim b. Mainz
E-Mail:     richter@ecos.de         Voice:    +49 6133 925151
WWW:        http://www.ecos.de      Fax:      +49 6133 925152
-------------------------------------------------------------


Re: Templating System (preview Embperl 2.0)

Posted by ___cliff rayman___ <cl...@genwax.com>.
is this a gauntlet being thrown down?
i hear the sound of parsing engines grinding away:
gentleman - start your benchmarks.


--
___cliff rayman___cliff@genwax.com___http://www.genwax.com/

"Paul J. Lucas" wrote:

> On Thu, 27 Jul 2000, Gerald Richter wrote:
>
> > To keep it fast Embperl is written in C.
>
>         Unless you use mmap(2), you can't compete with the speed of
>         HTML Tree.  The only downside of mmap(2) is that HTML Tree must
>         be first in an Apache::Filter filter chain.
>
>         - Paul





Re: Templating System (preview Embperl 2.0)

Posted by Gisle Aas <gi...@ActiveState.com>.
"Paul J. Lucas" <pj...@barefooters.org> writes:

> On Fri, 28 Jul 2000, Gerald Richter wrote:
> 
> > As far as I understand you you use mmap to read in the source file, is this
> > correct?
> 
> 	Yes.
> 
> > If this is true, then it will not make much difference, because reading in
> > the source is only a very small piece of all the time that it takes to
> > generate the output from a dynamic page.
> 
> 	I suggest you do some benchmarks.  I have, albeit many months
> 	ago.  If I recall correctly, I took Yahoo's home page and ran
> 	it through my HTML Tree and that of Gisle Aas: HTML was about
> 	7-8 times faster.

That does not show that mmap is superior.

I have not been able to build your module on my system, so I have not
been able to set up any benchmarks myself.  My guess is that you
compared your module parsing speed with that of the HTML::TreeBuilder
module?  Could you please be specific with what versions of the
modules you compared?  Perhaps also post the benchmark code you used.
Also tell me what HTML::Parser you had installed.  Did you use
HTML-Parser-3?

If your module is that much faster than the basic HTML::Parser then I
must be doing something very wrong.

> > My point was, that the C implementation of parsering and DOM tree
> > storage/caching, is much faster (uses much less memory) then doing the same
> > in Perl.
> 
> 	...and faster still with mmap(2).

I don't believe mmap buys you any significant.  And it has the
drawback that you can't parse from pipes or sockets.

I made this little test program.  I am not able to measure mmap to be
faster than fread on my system.  I am testing with Yahoo's home page.
Do you get different numbers?

Regards,
Gisle

----------------------------------------------------------->8------------
#include <unistd.h>
#include <sys/mman.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <stdio.h>

void
with_mmap(char *file)
{
    struct stat sbuf;
    int fd;
    void* area;
    char* c;
    int size;
    unsigned int checksum;

    fd = open(file, O_RDONLY);
    fstat(fd, &sbuf);
    size = sbuf.st_size;
    area = mmap(0, size, PROT_READ, MAP_SHARED, fd, 0);

    /* read the mapped area */
    checksum = 0;
    c = area;
    while (size--) {
	checksum += *c++;
    }
    munmap(area, sbuf.st_size);

    printf("%s: sum=%x\n", file, checksum);
}

void
with_fread(char *file)
{
    FILE* f = fopen(file, "r");
    char buf[32*1024];
    unsigned int checksum;
    size_t n;

    checksum = 0;
    while ( (n = fread(buf, 1, sizeof(buf), f))) {
	char *c = buf;
	int n_orig = n;
	while (n--)
	    checksum += *c++;
	if (n_orig < sizeof(buf))
	    break;
    }
    fclose(f);

    printf("%s: sum=%x\n", file, checksum);
}



int
main(int argc, char** argv)
{
    int i;
    void (*f)(char*);

    if (argc <= 1) {
	fprintf(stderr, "Missing type\n");
	return -1;
    }

    if (strcmp(argv[1], "mmap") == 0)
	f = with_mmap;
    else if (strcmp(argv[1], "fread") == 0)
	f = with_fread;
    else {
	fprintf(stderr, "Bad type '%s'\n", argv[1]);
	return -1;
    }

    for (i = 2; i < argc; i++) {
	f(argv[i]);
    }
    return 0;
}

RE: Templating System (preview Embperl 2.0)

Posted by Gerald Richter <ri...@ecos.de>.
>
> 	I suggest you do some benchmarks.  I have, albeit many months
> 	ago.  If I recall correctly, I took Yahoo's home page and ran
> 	it through my HTML Tree and that of Gisle Aas: HTML was about
> 	7-8 times faster.
>

I don't use Gisle Aas HTML Parser. Embperl has it's own. This parser maybe a
little slower then yours, because it's configuarble what it can parse. That
gives you very much flexibility with using custom html/xml tags. On the
otherside parsing is only done for the first request and then I keep the
parsed result. So if you do 1000 request to a page, the parser time only
counts on the first request. You may even do that parsing stuff at server
startup time (at least for often requested pages)


> > My point was, that the C implementation of parsering and DOM tree
> > storage/caching, is much faster (uses much less memory) then
> doing the same
> > in Perl.
>
> 	...and faster still with mmap(2).
>
I have already keeped that information in my mind (and in my bookmark list
:-). There is always something that could be done faster and Embperl 2.0 is
just starting and I know that there is more potential to optimze it.

Anyway, thanks for the hint with mmap. Maybe if I had knew about your parser
before, I had used it instead of creating my own one.

Gerald


RE: Templating System (preview Embperl 2.0)

Posted by "Paul J. Lucas" <pj...@barefooters.org>.
On Fri, 28 Jul 2000, Gerald Richter wrote:

> As far as I understand you you use mmap to read in the source file, is this
> correct?

	Yes.

> If this is true, then it will not make much difference, because reading in
> the source is only a very small piece of all the time that it takes to
> generate the output from a dynamic page.

	I suggest you do some benchmarks.  I have, albeit many months
	ago.  If I recall correctly, I took Yahoo's home page and ran
	it through my HTML Tree and that of Gisle Aas: HTML was about
	7-8 times faster.

> My point was, that the C implementation of parsering and DOM tree
> storage/caching, is much faster (uses much less memory) then doing the same
> in Perl.

	...and faster still with mmap(2).

	- Paul


RE: Templating System (preview Embperl 2.0)

Posted by Gerald Richter <ri...@ecos.de>.
>
> > To keep it fast Embperl is written in C.
>
> 	Unless you use mmap(2), you can't compete with the speed of
> 	HTML Tree.  The only downside of mmap(2) is that HTML Tree must
> 	be first in an Apache::Filter filter chain.
>

As far as I understand you you use mmap to read in the source file, is this
correct?

If this is true, then it will not make much difference, because reading in
the source is only a very small piece of all the time that it takes to
generate the output from a dynamic page. But I never said Embperl is the
fastest modules of all and I didn't have taken a closer look to HTML Tree.
So maybe HTML Tree is faster, but from the decription in the thread it does
not have all the functionalty that Embperl 2 have/will have (of course HTML
Tree will develop also).

My point was, that the C implementation of parsering and DOM tree
storage/caching, is much faster (uses much less memory) then doing the same
in Perl.

Gerald

-------------------------------------------------------------
Gerald Richter    ecos electronic communication services gmbh
Internetconnect * Webserver/-design/-datenbanken * Consulting

Post:       Tulpenstrasse 5         D-55276 Dienheim b. Mainz
E-Mail:     richter@ecos.de         Voice:    +49 6133 925151
WWW:        http://www.ecos.de      Fax:      +49 6133 925152
-------------------------------------------------------------


Re: [OT]: mmap (Was: Templating System (preview Embperl 2.0))

Posted by Malcolm Beattie <mb...@sable.ox.ac.uk>.
Paul J. Lucas writes:
> On Fri, 28 Jul 2000, Malcolm Beattie wrote:
> 
> > Assuming the kernel only keeps track of the last fault position in the file,
> > it won't recognise that it's being read linearly (twice :-) and may well not
> > do the async read ahead and drop behind in page cache that it would do
> > otherwise. Once again, you'll lose performance with mmap.
> 
> 	And reading in the file twice into two separate I/O buffers
> 	is better?

I've forgotten exactly what the original situation was so I'm not
sure whether it's better or not. With mmap you also have the
potential disadvantage that you're taking a page fault into the
kernel for every single page (say 4k or 8k) whereas with read(),
a single system call will fill up a much larger buffer with data.
It's also possible that the kernel can play tricks to get you the
data from a read better (on some architectures it could avoid
copying through the cache or it may be able to get the data
transferred from the source directly into your buffer without
passing through the CPU or suchlike).

Basically, mmap may well be an advantage from the ease or
elegance-of-coding point of view and in some cases it may win out
over read() for performance/scalability or whatever but it's not a
foregone conclusion and there are kernel/architecture-specific
difference which may swing the balance one way or the other. Now
we're getting offtopic though.

I really just wanted to make the points that saying "mmap is
always better than read" is not true and that there are things
going on behind the scenes.

--Malcolm

-- 
Malcolm Beattie <mb...@sable.ox.ac.uk>  I am looking for a Linux (and
Unix Systems Programmer                  maybe Apache/mod_perl) job/contract
Oxford University Computing Services   http://users.ox.ac.uk/~mbeattie/cv.html

Re: [OT]: mmap (Was: Templating System (preview Embperl 2.0))

Posted by "Paul J. Lucas" <pj...@barefooters.org>.
On Fri, 28 Jul 2000, Malcolm Beattie wrote:

> Assuming the kernel only keeps track of the last fault position in the file,
> it won't recognise that it's being read linearly (twice :-) and may well not
> do the async read ahead and drop behind in page cache that it would do
> otherwise. Once again, you'll lose performance with mmap.

	And reading in the file twice into two separate I/O buffers
	is better?

	- Paul


Re: [OT]: mmap (Was: Templating System (preview Embperl 2.0))

Posted by Malcolm Beattie <mb...@sable.ox.ac.uk>.
Paul J. Lucas writes:
> > This is the quote from "Philip and Alex..." that I was talking about
> > earlier. I don't know if its relevant or not:
> > 
> > They replied "NaviServer uses memory-mapped file I/O on single-processor
> > machines but automatically configures itself to use operating system read on
> > multi-CPU machines so as to reduce shared memory contention."
> 
> 	mmap(2) is *supposed* to share memory when read-only which is
> 	what's beign done for HTML file reads, so I don't understand
> 	what "contention" there could possibly be.

That's where some of the subtlety comes in. The first that springs
to mind is that with multiple CPUs of an architecture with a
virtually indexed cache, if the mmap maps the file at different
virtual addresses (as it very well may without slow global
communication between the reading processes) then the data will end
up being duplicated in processor cache. That slows things down.

Another point is that it can be harder for the kernel to notice
when a file is being read linearly when all it sees is page faults
through an address space. That means it may not do read-ahead on
that file as well. Most decent Unices will probably try to keep
track these days (certainly Linux does page-ahead and in fact
page-around to try to predict when to read-ahead or drop-behind
or whatever). On the other hand, if you have two concurrent
processes doing the reading then you'll get page faults at, for
example, byte 8k, 16k, 8k(second process starting), 24k, 16k and
so on. Assuming the kernel only keeps track of the last fault
position in the file, it won't recognise that it's being read
linearly (twice :-) and may well not do the async read ahead and
drop behind in page cache that it would do otherwise. Once again,
you'll lose performance with mmap.

--Malcolm

-- 
Malcolm Beattie <mb...@sable.ox.ac.uk>
Unix Systems Programmer
Oxford University Computing Services

Re: [OT]: mmap (Was: Templating System (preview Embperl 2.0))

Posted by Matt Sergeant <ma...@sergeant.org>.
On Fri, 28 Jul 2000, Paul J. Lucas wrote:

> > This is the quote from "Philip and Alex..." that I was talking about
> > earlier. I don't know if its relevant or not:
> > 
> > They replied "NaviServer uses memory-mapped file I/O on single-processor
> > machines but automatically configures itself to use operating system read on
> > multi-CPU machines so as to reduce shared memory contention."
> 
> 	mmap(2) is *supposed* to share memory when read-only which is
> 	what's beign done for HTML file reads, so I don't understand
> 	what "contention" there could possibly be.
> 
> 	Additionally, any OS that doesn't get mmap right is severly
> 	broken and shouldn't be used.

Well Philip does recommend HPUX ;-)

-- 
<Matt/>

Fastnet Software Ltd. High Performance Web Specialists
Providing mod_perl, XML, Sybase and Oracle solutions
Email for training and consultancy availability.
http://sergeant.org | AxKit: http://axkit.org


Re: [OT]: mmap (Was: Templating System (preview Embperl 2.0))

Posted by "Paul J. Lucas" <pj...@barefooters.org>.
> This is the quote from "Philip and Alex..." that I was talking about
> earlier. I don't know if its relevant or not:
> 
> They replied "NaviServer uses memory-mapped file I/O on single-processor
> machines but automatically configures itself to use operating system read on
> multi-CPU machines so as to reduce shared memory contention."

	mmap(2) is *supposed* to share memory when read-only which is
	what's beign done for HTML file reads, so I don't understand
	what "contention" there could possibly be.

	Additionally, any OS that doesn't get mmap right is severly
	broken and shouldn't be used.

	- Paul


Re: [OT]: mmap (Was: Templating System (preview Embperl 2.0))

Posted by Matt Sergeant <ma...@sergeant.org>.
On Fri, 28 Jul 2000, Paul J. Lucas wrote:

> On Fri, 28 Jul 2000, Kenneth Lee wrote:
> 
> > it would be good for the user to choose between mmap or normal i/o at 
> > compile time. i'll try HTML::Tree anyway in the meantime.
> 
> 	It's not that simple.  Using mmap(2) greatly affects how one
> 	writes code: it's not a drop-in replacement for standard I/O.
> 	An mmap'd file *becomes* memory in the time it takes the OS to
> 	handle a page-fault.  You then further get speed by accessing
> 	the file *as* memory via ordinary pointers rather than function
> 	calls and I/O buffers.  Inside the HTML Tree code is a generic
> 	C++ STL-style container class wrapped around mmap...quite nice
> 	if I do say so myself.
> 
> 	By definition, file I/O off disk can't be faster than mmap(2).

This is the quote from "Philip and Alex..." that I was talking about
earlier. I don't know if its relevant or not:

>>
My favorite AOLserver story starts in the seventh-floor lounge of the MIT
Artificial Intelligence Laboratory. I was asking Robert Thau, primary
author of the Apache server program, why the Netscape 1.1 server was so
slow. He said "Oh that's because those guys don't understand Unix.
They're actually using the read system call to read files." Everyone in
the room laughed except me. What? What's wrong with that? I asked. He
replied, "Everyone knows you can't use read; you have to use memory-mapped
I/O." 
  I knew that the NaviSoft guys were about to release a new version so I
thought I'd give the naifs in Santa Barbara the benefit of some hard-core
MIT engineering knowledge. I told them the story and asked them what
NaviServer, as it was then called, did. They replied "NaviServer uses
memory-mapped file I/O on single-processor machines but automatically
configures itself to use operating system read on multi-CPU machines so
as to reduce shared memory contention."
<<

-- 
<Matt/>

Fastnet Software Ltd. High Performance Web Specialists
Providing mod_perl, XML, Sybase and Oracle solutions
Email for training and consultancy availability.
http://sergeant.org | AxKit: http://axkit.org


[OT]: mmap (Was: Templating System (preview Embperl 2.0))

Posted by "Paul J. Lucas" <pj...@barefooters.org>.
On Fri, 28 Jul 2000, Kenneth Lee wrote:

> it would be good for the user to choose between mmap or normal i/o at 
> compile time. i'll try HTML::Tree anyway in the meantime.

	It's not that simple.  Using mmap(2) greatly affects how one
	writes code: it's not a drop-in replacement for standard I/O.
	An mmap'd file *becomes* memory in the time it takes the OS to
	handle a page-fault.  You then further get speed by accessing
	the file *as* memory via ordinary pointers rather than function
	calls and I/O buffers.  Inside the HTML Tree code is a generic
	C++ STL-style container class wrapped around mmap...quite nice
	if I do say so myself.

	By definition, file I/O off disk can't be faster than mmap(2).

	- Paul


Re: Templating System (preview Embperl 2.0)

Posted by Kenneth Lee <ke...@alfacomtech.com>.
it would be good for the user to choose between mmap or normal i/o at 
compile time. i'll try HTML::Tree anyway in the meantime.


Matt Sergeant wrote:
> 
> On Thu, 27 Jul 2000, Paul J. Lucas wrote:
> 
> > On Thu, 27 Jul 2000, Gerald Richter wrote:
> >
> > > To keep it fast Embperl is written in C.
> >
> >       Unless you use mmap(2), you can't compete with the speed of
> >       HTML Tree.  The only downside of mmap(2) is that HTML Tree must
> >       be first in an Apache::Filter filter chain.
> 
> I've heard that mmap is only faster on single processor systems. On a dual
> or above system you don't want to use memory mapped IO. (This was,
> admittedly, from Phillip and Alex's guide to web publishing).
> 
> Besides, I agree with Gerald, that reading in the template is a tiny
> portion of the overall problem. You may benchmark reading in _and_ parsing
> the template all you like, but ultimately people's web serving bottlenecks
> are generally database access and network latency.

RE: Templating System (preview Embperl 2.0)

Posted by Matt Sergeant <ma...@sergeant.org>.
On Thu, 27 Jul 2000, Paul J. Lucas wrote:

> On Thu, 27 Jul 2000, Gerald Richter wrote:
> 
> > To keep it fast Embperl is written in C.
> 
> 	Unless you use mmap(2), you can't compete with the speed of
> 	HTML Tree.  The only downside of mmap(2) is that HTML Tree must
> 	be first in an Apache::Filter filter chain.

I've heard that mmap is only faster on single processor systems. On a dual
or above system you don't want to use memory mapped IO. (This was,
admittedly, from Phillip and Alex's guide to web publishing).

Besides, I agree with Gerald, that reading in the template is a tiny
portion of the overall problem. You may benchmark reading in _and_ parsing
the template all you like, but ultimately people's web serving bottlenecks
are generally database access and network latency.

-- 
<Matt/>

Fastnet Software Ltd. High Performance Web Specialists
Providing mod_perl, XML, Sybase and Oracle solutions
Email for training and consultancy availability.
http://sergeant.org | AxKit: http://axkit.org


RE: Templating System (preview Embperl 2.0)

Posted by "Paul J. Lucas" <pj...@barefooters.org>.
On Thu, 27 Jul 2000, Gerald Richter wrote:

> To keep it fast Embperl is written in C.

	Unless you use mmap(2), you can't compete with the speed of
	HTML Tree.  The only downside of mmap(2) is that HTML Tree must
	be first in an Apache::Filter filter chain.

	- Paul