Discussion:
unknown
1970-01-01 00:00:00 UTC
Permalink
I can provide much more information about this if needed, and I appreciate
your time.

-Agathe

--089e0158b0d81d53370502787ead
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir="ltr"><div><div><div>flam3 and Apophysis, which have been around for over a decade,
are two well known software applications for rendering fractals, or to
be more specific, Fractal Flames, which are a member of Iterated
Function System class of fractals.  flam3 and Apophysis are both GPL,
with flam3 written in C.<br><br></div>Chaotica, a proprietary renderer
by Glare Technologies, started to appear around 2010, with commercial
licences being available for purchase starting with version 0.3.<br><br>An
important aspect of the Fractal Flame algorithm is the variation
functions, which you can think of them as a kind of plugins if you&#39;re
not familiar with the algorithm.  flam3 implements several dozen
variation functions, many of which have been developed over the years. 
Let&#39;s take a look at a few of them:<br><br>1)<br>void var2_spherical (flam3_iter_helper *f, double weight) {<br>   double r2 = weight / ( f-&gt;precalc_sumsq + EPS);<br>   f-&gt;p0 += r2 * f-&gt;tx;<br>   f-&gt;p1 += r2 * f-&gt;ty;<br>}<br><br></div><div>Basically,
the spherical variation function takes a 2D point and a weight as
input. The weight is divided by the squared norm and then multiplied by
the input point.  An interesting thing to note is the EPS, which is a
very small value added to avoid division by zero.  Instead of adding
EPS, a much better solution would have been to check to see if the input
point is at zero.  A numerical error is being introduced by adding EPS,
and that error gets larger as the input point approaches (0,0).  What
are the chances that Glare Technologies made the same mistake?  Here is
the objdump of an older version of Chaotica :<br><br><br>0000000000465b80 &lt;spherical::apply(vec4&lt;double&gt; const&amp;, vec4&lt;double&gt;&amp;, RenderThread*) const&gt;:<br>  465b80:    f2 0f 10 1e              movsd  (%rsi),%xmm3<br>  465b84:    f2 0f 10 56 08           movsd  0x8(%rsi),%xmm2<br>  465b89:    66 0f 28 c3              movapd %xmm3,%xmm0<br>  465b8d:    66 0f 28 ca              movapd %xmm2,%xmm1<br>  465b91:    f2 0f 59 c3              mulsd  %xmm3,%xmm0<br>  465b95:    f2 0f 59 ca              mulsd  %xmm2,%xmm1<br>  465b99:    f2 0f 58 c1              addsd  %xmm1,%xmm0<br>  465b9d:    f2 0f 10 4f 08           movsd  0x8(%rdi),%xmm1<br> 
465ba2:    f2 0f 58 05 26 e1 0c     addsd  0xce126(%rip),%xmm0        #
533cd0 &lt;typeinfo name for ArgumentParserExcep+0x20&gt;<br>  465ba9:    00 <br>  465baa:    f2 0f 5e c8              divsd  %xmm0,%xmm1<br>  465bae:    f2 0f 59 d9              mulsd  %xmm1,%xmm3<br>  465bb2:    f2 0f 59 ca              mulsd  %xmm2,%xmm1<br>  465bb6:    f2 0f 11 1a              movsd  %xmm3,(%rdx)<br>  465bba:    f2 0f 11 4a 08           movsd  %xmm1,0x8(%rdx)<br>  465bbf:    c3                       retq   <br><br><br></div><div>It is the same as far as we can tell, and there is no instruction for an _if_ statement.  It gets more interesting.<br><br><br>void var35_gaussian (flam3_iter_helper *f, double weight) {<br>   double ang, r, sina, cosa;<br>   ang = flam3_random_isaac_01(f-&gt;rc) * 2 * M_PI;<br>   sincos(ang,&amp;sina,&amp;cosa);<br>   r = weight * ( flam3_random_isaac_01(f-&gt;rc) + flam3_random_isaac_01(f-&gt;rc)<br>                   + flam3_random_isaac_01(f-&gt;rc) + flam3_random_isaac_01(f-&gt;rc) - 2.0 );<br>   f-&gt;p0 += r * cosa;<br>   f-&gt;p1 += r * sina;<br>}<br><br><br></div><div>The
gaussian variation function is supposed to sample a 2D point from a
normal distribution.  The actual equation we believe was meant to be
used in flam3 looks like this:<br><br></div><div> /// x and y are in [0,1)<br></div><div>a = sigma * sqrt(-2 * log(x))<br></div><div>b = 2 * PI * y<br></div><div>nx = a * sin(b)<br></div><div>ny = a * cos(b)<br><br></div><div>The
problem with the implementation in flam3 is that it doesn&#39;t even come
close to generating sample points from a normal distribtuion, mainly
because the calls to sqrt() and log() were omitted, presumably for
performance reason.  What are the chances that Chaotica implements the
same inaccurate yet distinct variation function?  Well, there are two
ways to prove.  The first is visually; the result of a numerical
integration of the gaussian variation function from flam3 using such
tenchniques as Monte Carlo produces the same exact results as what you
get in Chaotica.  The second method is to study the assembly code, which
I will link to instead of pasting the code:<br><br><a href="http://pastebin.com/bAj2J0uz" target="_blank">http://pastebin.com/bAj2J0uz</a><br><br></div><div> There is no call to sqrt() or log().  As far as the equation goes, it is the same.<br><br></div><div>The
list goes on and on, as there are tens of variation functions which
have been developed over the years, and pretty much all of them appeared
almost overnight in Chaotica.<br><br></div><div>I write this on behalf
of a small group of FOSS developers and artists.  We would like to know
if these findings prove that Chaotica is in violation of the GPL, and if
anything can be done about it.  If this does not constitute a GPL
violation, we would like for someone to please explain why it is not. 
Chaotica actually has had support for loading and rendering flam3 files,
which is something difficult to do without studying flam3 source code. 
Loading...