[Haskell-cafe] announce: Glome.hs raytracer
Derek Elkins
derek.a.elkins at gmail.com
Wed Mar 26 18:09:45 EDT 2008
On Wed, 2008-03-26 at 14:45 -0700, Don Stewart wrote:
> jsnow:
> > I have recently posted a haskell port of my ocaml raytracer, Glome:
> >
> > http://syn.cs.pdx.edu/~jsnow/glome/
> >
> > It supports spheres and triangles as base primitives, and is able to
> > parse files in the NFF format used by the standard procedural database
> > (http://tog.acm.org/resources/SPD/). It uses a bounding interval
> > heirarchy acceleration structure, so it can render fairly complicated
> > scenes in a reasonable amount of time. Shadows and reflections are
> > supported, but not specular highlights or refraction.
> >
> > It's still slower than the ocaml version, but at least they're in the
> > same ballpark (and a good part of that difference may be inefficiencies
> > in my BIH traversal). I would welcome any advice on making it go faster
> > or use less memory.
> >
> > I compile the program with "ghc Glome.hs --make -fasm -O2 -threaded
> > -fglasgow-exts -funbox-strict-fields -fbang-patterns -fexcess-precision
> > -optc-ffast-math -optc-O2 -optc-mfpmath=sse -optc-msse2". (I assume the
> > -optc options don't do anything unless you compile via C.)
> >
> > Here are some of my current concerns:
> >
> > -Multi-core parallelism is working, but not as well as I'd expect: I get
> > about a 25% reduction in runtime on two cores rather than 50%. I split
> > the default screen size of 512x512 into 16 blocks, and run "parMap" on
> > those blocks with a function that turns the screen coordinates of that
> > block into a list of (x,y,r,g,b) tuples that get drawn as pixels to the
> > screen through OpenGL by the original thread.
> >
> > -Memory consumption is atrocious: 146 megs to render a scene that's a
> > 33k ascii file. Where does it all go? A heap profile reports the max
> > heap size at a rather more reasonable 500k or so. (My architecture is
> > 64 bit ubuntu on a dual-core amd.)
>
> > -Collecting rendering stats is not easy without global variables. It
> > occurs to me that it would be neat if there were some sort of write-only
> > global variables that can be incremented by pure code but can only be
> > read from within monadic code; that would be sufficient to ensure that
> > the pure code wasn't affected by the values. The sorts of things I'm
> > looking for are the number of calls to "trace" per image, the number of
> > BIH branches traversed and ray/triangle and ray/sphere intersections per
> > pixel. (Disclaimer: I don't really fully understand monads, so I may
> > be oblivious to an obvious solution.)
>
> Use a Writer monad to log statistics? Maybe a State monad.
>
> > -Is there a fast way to cast between Float and Double? I'm using Float
> > currently, and the only reason is because that's what the OpenGL api
> > expects. I'd like to be able to use either representation, but the only
> > way to cast that I've found so far is "float_conv x =
> > fromRational(toRational x)", which is too slow.
>
> I'd try realToFrac, which should be pretty much optimised away.
>
> With doubles, ensure you use -fexcess-precision
Unless something has changed, you also want to be compiling with -fvia-C
if you are going to be doing floating point intensive computations.
More information about the Haskell-Cafe
mailing list