Re: Dramatic slowdown -ping Rob

new topic     » goto parent     » topic index » view thread      » older message » newer message

As promised, I looked into the performance issue raised
by Pete Lomax a while back. I don't think there is any
bug in Euphoria itself (ref counts etc.). 
I rather think WATCOM's storage 
allocator for DOS has some very quirky behavior. In exw.exe
I don't use the WATCOM allocator, I use Microsoft's.
I earlier reported no problem with ex.exe for 2.5,
but I think I must have been using exw.exe for 2.5.
exw runs the code below very fast regardless of the 
size of the sequences. People noticed a big slowdown
with ex.exe when moving from 27 to 28. I believe that's because 
I allocate 50% more space when the size becomes 28. 
For speed in handling small sequences, I map to a set of 
standard memory block sizes:
16, 24, 32, 48, 64, 96, 128 bytes, 192 bytes, 256 etc.
I think 27 would need 128, while 28 would need 192.

However, strangely enough, when the size is increased from 28 to 
100, it runs really fast, even though more processing is being
done by Euphoria.

I also noticed that when it runs slow, it actually runs fast
to start with, and then at a certain point it starts taking longer
and longer to allocate a block.

I downloaded the WATCOM source, but I couldn't really understand
how the allocator works. From the comments it did seem like it
was fairly complex, with a lot of special cases, and multiple heaps,
and there was special code added to deal with worst case situations.

Below is Pete's code with a lot of mods to get better information.

-- Time profile based on 167 samples.
-- Left margin shows the percentage of total execution time
-- consumed by the statement(s) on that line.

       |
       |constant START = time()
       |constant INNER=28 --27 good, 28 bad, 50 bad, 100 good, why?
       |sequence table
       |table=repeat(repeat(0,INNER),1024)
       |integer used
       |used=1
       |sequence t1, t2
       |atom t
       |t = time()
       |
       |for i=1 to 45000 do
       |    used+=1
  0.60 |    if remainder(i,3000) = 0 then
  0.60 |        printf(1, "%d: %.2f\n", {i, time()-t})
       |        t = time()
       |    end if
  0.60 |    if used>length(table) then
       |        t1 = repeat(0, INNER)
       |        t2 = repeat(t1, 1024)
  2.40 |        table &= t2
       |    end if
 95.81 |    table[used][1]=99  -- here's where almost all 
       |                       -- the 28-long sequence blocks are allocated
       |end for
       |
       |printf(1, "Elapsed time: %f\n", time() - START)


Regards,
   Rob Craig
   Rapid Deployment Software
   http://www.RapidEuphoria.com

new topic     » goto parent     » topic index » view thread      » older message » newer message

Search



Quick Links

User menu

Not signed in.

Misc Menu