~njansson/dolfin/hpc

« back to all changes in this revision

Viewing changes to src/kernel/mesh/GeometricPredicates.cpp

  • Committer: Johannes Ring
  • Date: 2008-03-05 22:43:06 UTC
  • Revision ID: johannr@simula.no-20080305224306-2npsdyhfdpl2esji
The BIG commit!

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
// Copyright (C) 1999 Jonathan Richard Shewchuk
2
 
// Licensed under the GNU LGPL Version 2.1.
3
 
//
4
 
// Modified by Johan Jansson, 2006.
5
 
 
6
 
#include <stdio.h>
7
 
#include <stdlib.h>
8
 
#include <math.h>
9
 
#include <dolfin/GeometricPredicates.h>
10
 
 
11
 
using namespace dolfin;
12
 
 
13
 
namespace dolfin
14
 
{
15
 
 
16
 
  // FIXME:
17
 
  // "predicates_init.h" should be generated for the target architecture.
18
 
  // Look into "rounding.h", why does it need "config.h"?
19
 
 
20
 
/*****************************************************************************/
21
 
/*                                                                           */
22
 
/*  Routines for Arbitrary Precision Floating-point Arithmetic               */
23
 
/*  and Fast Robust Geometric Predicates                                     */
24
 
/*  (predicates.c)                                                           */
25
 
/*                                                                           */
26
 
/*  May 18, 1996                                                             */
27
 
/*                                                                           */
28
 
/*  Placed in the public domain by                                           */
29
 
/*  Jonathan Richard Shewchuk                                                */
30
 
/*  School of Computer Science                                               */
31
 
/*  Carnegie Mellon University                                               */
32
 
/*  5000 Forbes Avenue                                                       */
33
 
/*  Pittsburgh, Pennsylvania  15213-3891                                     */
34
 
/*  jrs@cs.cmu.edu                                                           */
35
 
/*                                                                           */
36
 
/*  This file contains C implementation of algorithms for exact addition     */
37
 
/*    and multiplication of floating-point numbers, and predicates for       */
38
 
/*    robustly performing the orientation and incircle tests used in         */
39
 
/*    computational geometry.  The algorithms and underlying theory are      */
40
 
/*    described in Jonathan Richard Shewchuk.  "Adaptive Precision Floating- */
41
 
/*    Point Arithmetic and Fast Robust Geometric Predicates."  Technical     */
42
 
/*    Report CMU-CS-96-140, School of Computer Science, Carnegie Mellon      */
43
 
/*    University, Pittsburgh, Pennsylvania, May 1996.  (Submitted to         */
44
 
/*    Discrete & Computational Geometry.)                                    */
45
 
/*                                                                           */
46
 
/*  This file, the paper listed above, and other information are available   */
47
 
/*    from the Web page http://www.cs.cmu.edu/~quake/robust.html .           */
48
 
/*                                                                           */
49
 
/*****************************************************************************/
50
 
 
51
 
/*****************************************************************************/
52
 
/*                                                                           */
53
 
/*  Using this code:                                                         */
54
 
/*                                                                           */
55
 
/*  First, read the short or long version of the paper (from the Web page    */
56
 
/*    above).                                                                */
57
 
/*                                                                           */
58
 
/*  Be sure to call exactinit() once, before calling any of the arithmetic   */
59
 
/*    functions or geometric predicates.  Also be sure to turn on the        */
60
 
/*    optimizer when compiling this file.                                    */
61
 
/*                                                                           */
62
 
/*                                                                           */
63
 
/*  Several geometric predicates are defined.  Their parameters are all      */
64
 
/*    points.  Each point is an array of two or three floating-point         */
65
 
/*    numbers.  The geometric predicates, described in the papers, are       */
66
 
/*                                                                           */
67
 
/*    orient2d(pa, pb, pc)                                                   */
68
 
/*    orient2dfast(pa, pb, pc)                                               */
69
 
/*    orient3d(pa, pb, pc, pd)                                               */
70
 
/*    orient3dfast(pa, pb, pc, pd)                                           */
71
 
/*    incircle(pa, pb, pc, pd)                                               */
72
 
/*    incirclefast(pa, pb, pc, pd)                                           */
73
 
/*    insphere(pa, pb, pc, pd, pe)                                           */
74
 
/*    inspherefast(pa, pb, pc, pd, pe)                                       */
75
 
/*                                                                           */
76
 
/*  Those with suffix "fast" are approximate, non-robust versions.  Those    */
77
 
/*    without the suffix are adaptive precision, robust versions.  There     */
78
 
/*    are also versions with the suffices "exact" and "slow", which are      */
79
 
/*    non-adaptive, exact arithmetic versions, which I use only for timings  */
80
 
/*    in my arithmetic papers.                                               */
81
 
/*                                                                           */
82
 
/*                                                                           */
83
 
/*  An expansion is represented by an array of floating-point numbers,       */
84
 
/*    sorted from smallest to largest magnitude (possibly with interspersed  */
85
 
/*    zeros).  The length of each expansion is stored as a separate integer, */
86
 
/*    and each arithmetic function returns an integer which is the length    */
87
 
/*    of the expansion it created.                                           */
88
 
/*                                                                           */
89
 
/*  Several arithmetic functions are defined.  Their parameters are          */
90
 
/*                                                                           */
91
 
/*    e, f           Input expansions                                        */
92
 
/*    elen, flen     Lengths of input expansions (must be >= 1)              */
93
 
/*    h              Output expansion                                        */
94
 
/*    b              Input scalar                                            */
95
 
/*                                                                           */
96
 
/*  The arithmetic functions are                                             */
97
 
/*                                                                           */
98
 
/*    grow_expansion(elen, e, b, h)                                          */
99
 
/*    grow_expansion_zeroelim(elen, e, b, h)                                 */
100
 
/*    expansion_sum(elen, e, flen, f, h)                                     */
101
 
/*    expansion_sum_zeroelim1(elen, e, flen, f, h)                           */
102
 
/*    expansion_sum_zeroelim2(elen, e, flen, f, h)                           */
103
 
/*    fast_expansion_sum(elen, e, flen, f, h)                                */
104
 
/*    fast_expansion_sum_zeroelim(elen, e, flen, f, h)                       */
105
 
/*    linear_expansion_sum(elen, e, flen, f, h)                              */
106
 
/*    linear_expansion_sum_zeroelim(elen, e, flen, f, h)                     */
107
 
/*    scale_expansion(elen, e, b, h)                                         */
108
 
/*    scale_expansion_zeroelim(elen, e, b, h)                                */
109
 
/*    compress(elen, e, h)                                                   */
110
 
/*                                                                           */
111
 
/*  All of these are described in the long version of the paper; some are    */
112
 
/*    described in the short version.  All return an integer that is the     */
113
 
/*    length of h.  Those with suffix _zeroelim perform zero elimination,    */
114
 
/*    and are recommended over their counterparts.  The procedure            */
115
 
/*    fast_expansion_sum_zeroelim() (or linear_expansion_sum_zeroelim() on   */
116
 
/*    processors that do not use the round-to-even tiebreaking rule) is      */
117
 
/*    recommended over expansion_sum_zeroelim().  Each procedure has a       */
118
 
/*    little note next to it (in the code below) that tells you whether or   */
119
 
/*    not the output expansion may be the same array as one of the input     */
120
 
/*    expansions.                                                            */
121
 
/*                                                                           */
122
 
/*                                                                           */
123
 
/*  If you look around below, you'll also find macros for a bunch of         */
124
 
/*    simple unrolled arithmetic operations, and procedures for printing     */
125
 
/*    expansions (commented out because they don't work with all C           */
126
 
/*    compilers) and for generating random floating-point numbers whose      */
127
 
/*    significand bits are all random.  Most of the macros have undocumented */
128
 
/*    requirements that certain of their parameters should not be the same   */
129
 
/*    variable; for safety, better to make sure all the parameters are       */
130
 
/*    distinct variables.  Feel free to send email to jrs@cs.cmu.edu if you  */
131
 
/*    have questions.                                                        */
132
 
/*                                                                           */
133
 
/*****************************************************************************/
134
 
 
135
 
 
136
 
/* Use header file generated automatically by predicates_init. */
137
 
#define USE_PREDICATES_INIT
138
 
 
139
 
#ifdef USE_PREDICATES_INIT
140
 
#include "predicates_init.h"
141
 
#endif /* USE_PREDICATES_INIT */
142
 
 
143
 
/* FPU control. We MUST have only double precision (not extended precision) */
144
 
#include "rounding.h"
145
 
 
146
 
/* On some machines, the exact arithmetic routines might be defeated by the  */
147
 
/*   use of internal extended precision floating-point registers.  Sometimes */
148
 
/*   this problem can be fixed by defining certain values to be volatile,    */
149
 
/*   thus forcing them to be stored to memory and rounded off.  This isn't   */
150
 
/*   a great solution, though, as it slows the arithmetic down.              */
151
 
/*                                                                           */
152
 
/* To try this out, write "#define INEXACT volatile" below.  Normally,       */
153
 
/*   however, INEXACT should be defined to be nothing.  ("#define INEXACT".) */
154
 
 
155
 
#define INEXACT                          /* Nothing */
156
 
/* #define INEXACT volatile */
157
 
 
158
 
#define REAL double                      /* float or double */
159
 
#define REALPRINT doubleprint
160
 
#define REALRAND doublerand
161
 
#define NARROWRAND narrowdoublerand
162
 
#define UNIFORMRAND uniformdoublerand
163
 
 
164
 
/* Which of the following two methods of finding the absolute values is      */
165
 
/*   fastest is compiler-dependent.  A few compilers can inline and optimize */
166
 
/*   the fabs() call; but most will incur the overhead of a function call,   */
167
 
/*   which is disastrously slow.  A faster way on IEEE machines might be to  */
168
 
/*   mask the appropriate bit, but that's difficult to do in C.              */
169
 
 
170
 
#define Absolute(a)  ((a) >= 0.0 ? (a) : -(a))
171
 
/* #define Absolute(a)  fabs(a) */
172
 
 
173
 
/* Many of the operations are broken up into two pieces, a main part that    */
174
 
/*   performs an approximate operation, and a "tail" that computes the       */
175
 
/*   roundoff error of that operation.                                       */
176
 
/*                                                                           */
177
 
/* The operations Fast_Two_Sum(), Fast_Two_Diff(), Two_Sum(), Two_Diff(),    */
178
 
/*   Split(), and Two_Product() are all implemented as described in the      */
179
 
/*   reference.  Each of these macros requires certain variables to be       */
180
 
/*   defined in the calling routine.  The variables `bvirt', `c', `abig',    */
181
 
/*   `_i', `_j', `_k', `_l', `_m', and `_n' are declared `INEXACT' because   */
182
 
/*   they store the result of an operation that may incur roundoff error.    */
183
 
/*   The input parameter `x' (or the highest numbered `x_' parameter) must   */
184
 
/*   also be declared `INEXACT'.                                             */
185
 
 
186
 
#define Fast_Two_Sum_Tail(a, b, x, y) \
187
 
  bvirt = x - a; \
188
 
  y = b - bvirt
189
 
 
190
 
#define Fast_Two_Sum(a, b, x, y) \
191
 
  x = (REAL) (a + b); \
192
 
  Fast_Two_Sum_Tail(a, b, x, y)
193
 
 
194
 
#define Fast_Two_Diff_Tail(a, b, x, y) \
195
 
  bvirt = a - x; \
196
 
  y = bvirt - b
197
 
 
198
 
#define Fast_Two_Diff(a, b, x, y) \
199
 
  x = (REAL) (a - b); \
200
 
  Fast_Two_Diff_Tail(a, b, x, y)
201
 
 
202
 
#define Two_Sum_Tail(a, b, x, y) \
203
 
  bvirt = (REAL) (x - a); \
204
 
  avirt = x - bvirt; \
205
 
  bround = b - bvirt; \
206
 
  around = a - avirt; \
207
 
  y = around + bround
208
 
 
209
 
#define Two_Sum(a, b, x, y) \
210
 
  x = (REAL) (a + b); \
211
 
  Two_Sum_Tail(a, b, x, y)
212
 
 
213
 
#define Two_Diff_Tail(a, b, x, y) \
214
 
  bvirt = (REAL) (a - x); \
215
 
  avirt = x + bvirt; \
216
 
  bround = bvirt - b; \
217
 
  around = a - avirt; \
218
 
  y = around + bround
219
 
 
220
 
#define Two_Diff(a, b, x, y) \
221
 
  x = (REAL) (a - b); \
222
 
  Two_Diff_Tail(a, b, x, y)
223
 
 
224
 
#define Split(a, ahi, alo) \
225
 
  c = (REAL) (splitter * a); \
226
 
  abig = (REAL) (c - a); \
227
 
  ahi = c - abig; \
228
 
  alo = a - ahi
229
 
 
230
 
#define Two_Product_Tail(a, b, x, y) \
231
 
  Split(a, ahi, alo); \
232
 
  Split(b, bhi, blo); \
233
 
  err1 = x - (ahi * bhi); \
234
 
  err2 = err1 - (alo * bhi); \
235
 
  err3 = err2 - (ahi * blo); \
236
 
  y = (alo * blo) - err3
237
 
 
238
 
#define Two_Product(a, b, x, y) \
239
 
  x = (REAL) (a * b); \
240
 
  Two_Product_Tail(a, b, x, y)
241
 
 
242
 
/* Two_Product_Presplit() is Two_Product() where one of the inputs has       */
243
 
/*   already been split.  Avoids redundant splitting.                        */
244
 
 
245
 
#define Two_Product_Presplit(a, b, bhi, blo, x, y) \
246
 
  x = (REAL) (a * b); \
247
 
  Split(a, ahi, alo); \
248
 
  err1 = x - (ahi * bhi); \
249
 
  err2 = err1 - (alo * bhi); \
250
 
  err3 = err2 - (ahi * blo); \
251
 
  y = (alo * blo) - err3
252
 
 
253
 
/* Two_Product_2Presplit() is Two_Product() where both of the inputs have    */
254
 
/*   already been split.  Avoids redundant splitting.                        */
255
 
 
256
 
#define Two_Product_2Presplit(a, ahi, alo, b, bhi, blo, x, y) \
257
 
  x = (REAL) (a * b); \
258
 
  err1 = x - (ahi * bhi); \
259
 
  err2 = err1 - (alo * bhi); \
260
 
  err3 = err2 - (ahi * blo); \
261
 
  y = (alo * blo) - err3
262
 
 
263
 
/* Square() can be done more quickly than Two_Product().                     */
264
 
 
265
 
#define Square_Tail(a, x, y) \
266
 
  Split(a, ahi, alo); \
267
 
  err1 = x - (ahi * ahi); \
268
 
  err3 = err1 - ((ahi + ahi) * alo); \
269
 
  y = (alo * alo) - err3
270
 
 
271
 
#define Square(a, x, y) \
272
 
  x = (REAL) (a * a); \
273
 
  Square_Tail(a, x, y)
274
 
 
275
 
/* Macros for summing expansions of various fixed lengths.  These are all    */
276
 
/*   unrolled versions of Expansion_Sum().                                   */
277
 
 
278
 
#define Two_One_Sum(a1, a0, b, x2, x1, x0) \
279
 
  Two_Sum(a0, b , _i, x0); \
280
 
  Two_Sum(a1, _i, x2, x1)
281
 
 
282
 
#define Two_One_Diff(a1, a0, b, x2, x1, x0) \
283
 
  Two_Diff(a0, b , _i, x0); \
284
 
  Two_Sum( a1, _i, x2, x1)
285
 
 
286
 
#define Two_Two_Sum(a1, a0, b1, b0, x3, x2, x1, x0) \
287
 
  Two_One_Sum(a1, a0, b0, _j, _0, x0); \
288
 
  Two_One_Sum(_j, _0, b1, x3, x2, x1)
289
 
 
290
 
#define Two_Two_Diff(a1, a0, b1, b0, x3, x2, x1, x0) \
291
 
  Two_One_Diff(a1, a0, b0, _j, _0, x0); \
292
 
  Two_One_Diff(_j, _0, b1, x3, x2, x1)
293
 
 
294
 
#define Four_One_Sum(a3, a2, a1, a0, b, x4, x3, x2, x1, x0) \
295
 
  Two_One_Sum(a1, a0, b , _j, x1, x0); \
296
 
  Two_One_Sum(a3, a2, _j, x4, x3, x2)
297
 
 
298
 
#define Four_Two_Sum(a3, a2, a1, a0, b1, b0, x5, x4, x3, x2, x1, x0) \
299
 
  Four_One_Sum(a3, a2, a1, a0, b0, _k, _2, _1, _0, x0); \
300
 
  Four_One_Sum(_k, _2, _1, _0, b1, x5, x4, x3, x2, x1)
301
 
 
302
 
#define Four_Four_Sum(a3, a2, a1, a0, b4, b3, b1, b0, x7, x6, x5, x4, x3, x2, \
303
 
                      x1, x0) \
304
 
  Four_Two_Sum(a3, a2, a1, a0, b1, b0, _l, _2, _1, _0, x1, x0); \
305
 
  Four_Two_Sum(_l, _2, _1, _0, b4, b3, x7, x6, x5, x4, x3, x2)
306
 
 
307
 
#define Eight_One_Sum(a7, a6, a5, a4, a3, a2, a1, a0, b, x8, x7, x6, x5, x4, \
308
 
                      x3, x2, x1, x0) \
309
 
  Four_One_Sum(a3, a2, a1, a0, b , _j, x3, x2, x1, x0); \
310
 
  Four_One_Sum(a7, a6, a5, a4, _j, x8, x7, x6, x5, x4)
311
 
 
312
 
#define Eight_Two_Sum(a7, a6, a5, a4, a3, a2, a1, a0, b1, b0, x9, x8, x7, \
313
 
                      x6, x5, x4, x3, x2, x1, x0) \
314
 
  Eight_One_Sum(a7, a6, a5, a4, a3, a2, a1, a0, b0, _k, _6, _5, _4, _3, _2, \
315
 
                _1, _0, x0); \
316
 
  Eight_One_Sum(_k, _6, _5, _4, _3, _2, _1, _0, b1, x9, x8, x7, x6, x5, x4, \
317
 
                x3, x2, x1)
318
 
 
319
 
#define Eight_Four_Sum(a7, a6, a5, a4, a3, a2, a1, a0, b4, b3, b1, b0, x11, \
320
 
                       x10, x9, x8, x7, x6, x5, x4, x3, x2, x1, x0) \
321
 
  Eight_Two_Sum(a7, a6, a5, a4, a3, a2, a1, a0, b1, b0, _l, _6, _5, _4, _3, \
322
 
                _2, _1, _0, x1, x0); \
323
 
  Eight_Two_Sum(_l, _6, _5, _4, _3, _2, _1, _0, b4, b3, x11, x10, x9, x8, \
324
 
                x7, x6, x5, x4, x3, x2)
325
 
 
326
 
/* Macros for multiplying expansions of various fixed lengths.               */
327
 
 
328
 
#define Two_One_Product(a1, a0, b, x3, x2, x1, x0) \
329
 
  Split(b, bhi, blo); \
330
 
  Two_Product_Presplit(a0, b, bhi, blo, _i, x0); \
331
 
  Two_Product_Presplit(a1, b, bhi, blo, _j, _0); \
332
 
  Two_Sum(_i, _0, _k, x1); \
333
 
  Fast_Two_Sum(_j, _k, x3, x2)
334
 
 
335
 
#define Four_One_Product(a3, a2, a1, a0, b, x7, x6, x5, x4, x3, x2, x1, x0) \
336
 
  Split(b, bhi, blo); \
337
 
  Two_Product_Presplit(a0, b, bhi, blo, _i, x0); \
338
 
  Two_Product_Presplit(a1, b, bhi, blo, _j, _0); \
339
 
  Two_Sum(_i, _0, _k, x1); \
340
 
  Fast_Two_Sum(_j, _k, _i, x2); \
341
 
  Two_Product_Presplit(a2, b, bhi, blo, _j, _0); \
342
 
  Two_Sum(_i, _0, _k, x3); \
343
 
  Fast_Two_Sum(_j, _k, _i, x4); \
344
 
  Two_Product_Presplit(a3, b, bhi, blo, _j, _0); \
345
 
  Two_Sum(_i, _0, _k, x5); \
346
 
  Fast_Two_Sum(_j, _k, x7, x6)
347
 
 
348
 
#define Two_Two_Product(a1, a0, b1, b0, x7, x6, x5, x4, x3, x2, x1, x0) \
349
 
  Split(a0, a0hi, a0lo); \
350
 
  Split(b0, bhi, blo); \
351
 
  Two_Product_2Presplit(a0, a0hi, a0lo, b0, bhi, blo, _i, x0); \
352
 
  Split(a1, a1hi, a1lo); \
353
 
  Two_Product_2Presplit(a1, a1hi, a1lo, b0, bhi, blo, _j, _0); \
354
 
  Two_Sum(_i, _0, _k, _1); \
355
 
  Fast_Two_Sum(_j, _k, _l, _2); \
356
 
  Split(b1, bhi, blo); \
357
 
  Two_Product_2Presplit(a0, a0hi, a0lo, b1, bhi, blo, _i, _0); \
358
 
  Two_Sum(_1, _0, _k, x1); \
359
 
  Two_Sum(_2, _k, _j, _1); \
360
 
  Two_Sum(_l, _j, _m, _2); \
361
 
  Two_Product_2Presplit(a1, a1hi, a1lo, b1, bhi, blo, _j, _0); \
362
 
  Two_Sum(_i, _0, _n, _0); \
363
 
  Two_Sum(_1, _0, _i, x2); \
364
 
  Two_Sum(_2, _i, _k, _1); \
365
 
  Two_Sum(_m, _k, _l, _2); \
366
 
  Two_Sum(_j, _n, _k, _0); \
367
 
  Two_Sum(_1, _0, _j, x3); \
368
 
  Two_Sum(_2, _j, _i, _1); \
369
 
  Two_Sum(_l, _i, _m, _2); \
370
 
  Two_Sum(_1, _k, _i, x4); \
371
 
  Two_Sum(_2, _i, _k, x5); \
372
 
  Two_Sum(_m, _k, x7, x6)
373
 
 
374
 
/* An expansion of length two can be squared more quickly than finding the   */
375
 
/*   product of two different expansions of length two, and the result is    */
376
 
/*   guaranteed to have no more than six (rather than eight) components.     */
377
 
 
378
 
#define Two_Square(a1, a0, x5, x4, x3, x2, x1, x0) \
379
 
  Square(a0, _j, x0); \
380
 
  _0 = a0 + a0; \
381
 
  Two_Product(a1, _0, _k, _1); \
382
 
  Two_One_Sum(_k, _1, _j, _l, _2, x1); \
383
 
  Square(a1, _j, _1); \
384
 
  Two_Two_Sum(_j, _1, _l, _2, x5, x4, x3, x2)
385
 
 
386
 
#ifndef USE_PREDICATES_INIT
387
 
 
388
 
static REAL splitter;     /* = 2^ceiling(p / 2) + 1.  Used to split floats in half. */
389
 
/* A set of coefficients used to calculate maximum roundoff errors.          */
390
 
static REAL resulterrbound;
391
 
static REAL ccwerrboundA, ccwerrboundB, ccwerrboundC;
392
 
static REAL o3derrboundA, o3derrboundB, o3derrboundC;
393
 
static REAL iccerrboundA, iccerrboundB, iccerrboundC;
394
 
static REAL isperrboundA, isperrboundB, isperrboundC;
395
 
 
396
 
#endif /* USE_PREDICATES_INIT */
397
 
 
398
 
/*****************************************************************************/
399
 
/*                                                                           */
400
 
/*  doubleprint()   Print the bit representation of a double.                */
401
 
/*                                                                           */
402
 
/*  Useful for debugging exact arithmetic routines.                          */
403
 
/*                                                                           */
404
 
/*****************************************************************************/
405
 
 
406
 
/*
407
 
void doubleprint(number)
408
 
double number;
409
 
{
410
 
  unsigned long long no;
411
 
  unsigned long long sign, expo;
412
 
  int exponent;
413
 
  int i, bottomi;
414
 
 
415
 
  no = *(unsigned long long *) &number;
416
 
  sign = no & 0x8000000000000000ll;
417
 
  expo = (no >> 52) & 0x7ffll;
418
 
  exponent = (int) expo;
419
 
  exponent = exponent - 1023;
420
 
  if (sign) {
421
 
    printf("-");
422
 
  } else {
423
 
    printf(" ");
424
 
  }
425
 
  if (exponent == -1023) {
426
 
    printf(
427
 
      "0.0000000000000000000000000000000000000000000000000000_     (   )");
428
 
  } else {
429
 
    printf("1.");
430
 
    bottomi = -1;
431
 
    for (i = 0; i < 52; i++) {
432
 
      if (no & 0x0008000000000000ll) {
433
 
        printf("1");
434
 
        bottomi = i;
435
 
      } else {
436
 
        printf("0");
437
 
      }
438
 
      no <<= 1;
439
 
    }
440
 
    printf("_%d  (%d)", exponent, exponent - 1 - bottomi);
441
 
  }
442
 
}
443
 
*/
444
 
 
445
 
/*****************************************************************************/
446
 
/*                                                                           */
447
 
/*  floatprint()   Print the bit representation of a float.                  */
448
 
/*                                                                           */
449
 
/*  Useful for debugging exact arithmetic routines.                          */
450
 
/*                                                                           */
451
 
/*****************************************************************************/
452
 
 
453
 
/*
454
 
void floatprint(number)
455
 
float number;
456
 
{
457
 
  unsigned no;
458
 
  unsigned sign, expo;
459
 
  int exponent;
460
 
  int i, bottomi;
461
 
 
462
 
  no = *(unsigned *) &number;
463
 
  sign = no & 0x80000000;
464
 
  expo = (no >> 23) & 0xff;
465
 
  exponent = (int) expo;
466
 
  exponent = exponent - 127;
467
 
  if (sign) {
468
 
    printf("-");
469
 
  } else {
470
 
    printf(" ");
471
 
  }
472
 
  if (exponent == -127) {
473
 
    printf("0.00000000000000000000000_     (   )");
474
 
  } else {
475
 
    printf("1.");
476
 
    bottomi = -1;
477
 
    for (i = 0; i < 23; i++) {
478
 
      if (no & 0x00400000) {
479
 
        printf("1");
480
 
        bottomi = i;
481
 
      } else {
482
 
        printf("0");
483
 
      }
484
 
      no <<= 1;
485
 
    }
486
 
    printf("_%3d  (%3d)", exponent, exponent - 1 - bottomi);
487
 
  }
488
 
}
489
 
*/
490
 
 
491
 
/*****************************************************************************/
492
 
/*                                                                           */
493
 
/*  expansion_print()   Print the bit representation of an expansion.        */
494
 
/*                                                                           */
495
 
/*  Useful for debugging exact arithmetic routines.                          */
496
 
/*                                                                           */
497
 
/*****************************************************************************/
498
 
 
499
 
/*
500
 
void expansion_print(elen, e)
501
 
int elen;
502
 
REAL *e;
503
 
{
504
 
  int i;
505
 
 
506
 
  for (i = elen - 1; i >= 0; i--) {
507
 
    REALPRINT(e[i]);
508
 
    if (i > 0) {
509
 
      printf(" +\n");
510
 
    } else {
511
 
      printf("\n");
512
 
    }
513
 
  }
514
 
}
515
 
*/
516
 
 
517
 
/*****************************************************************************/
518
 
/*                                                                           */
519
 
/*  doublerand()   Generate a double with random 53-bit significand and a    */
520
 
/*                 random exponent in [0, 511].                              */
521
 
/*                                                                           */
522
 
/*****************************************************************************/
523
 
 
524
 
/*
525
 
static double doublerand()
526
 
{
527
 
  double result;
528
 
  double expo;
529
 
  long a, b, c;
530
 
  long i;
531
 
 
532
 
  a = random();
533
 
  b = random();
534
 
  c = random();
535
 
  result = (double) (a - 1073741824) * 8388608.0 + (double) (b >> 8);
536
 
  for (i = 512, expo = 2; i <= 131072; i *= 2, expo = expo * expo) {
537
 
    if (c & i) {
538
 
      result *= expo;
539
 
    }
540
 
  }
541
 
  return result;
542
 
}
543
 
*/
544
 
 
545
 
/*****************************************************************************/
546
 
/*                                                                           */
547
 
/*  narrowdoublerand()   Generate a double with random 53-bit significand    */
548
 
/*                       and a random exponent in [0, 7].                    */
549
 
/*                                                                           */
550
 
/*****************************************************************************/
551
 
 
552
 
/*
553
 
static double narrowdoublerand()
554
 
{
555
 
  double result;
556
 
  double expo;
557
 
  long a, b, c;
558
 
  long i;
559
 
 
560
 
  a = random();
561
 
  b = random();
562
 
  c = random();
563
 
  result = (double) (a - 1073741824) * 8388608.0 + (double) (b >> 8);
564
 
  for (i = 512, expo = 2; i <= 2048; i *= 2, expo = expo * expo) {
565
 
    if (c & i) {
566
 
      result *= expo;
567
 
    }
568
 
  }
569
 
  return result;
570
 
}
571
 
*/
572
 
 
573
 
/*****************************************************************************/
574
 
/*                                                                           */
575
 
/*  uniformdoublerand()   Generate a double with random 53-bit significand.  */
576
 
/*                                                                           */
577
 
/*****************************************************************************/
578
 
 
579
 
/*
580
 
static double uniformdoublerand()
581
 
{
582
 
  double result;
583
 
  long a, b;
584
 
 
585
 
  a = random();
586
 
  b = random();
587
 
  result = (double) (a - 1073741824) * 8388608.0 + (double) (b >> 8);
588
 
  return result;
589
 
}
590
 
*/
591
 
 
592
 
/*****************************************************************************/
593
 
/*                                                                           */
594
 
/*  floatrand()   Generate a float with random 24-bit significand and a      */
595
 
/*                random exponent in [0, 63].                                */
596
 
/*                                                                           */
597
 
/*****************************************************************************/
598
 
 
599
 
/*
600
 
static float floatrand()
601
 
{
602
 
  float result;
603
 
  float expo;
604
 
  long a, c;
605
 
  long i;
606
 
 
607
 
  a = random();
608
 
  c = random();
609
 
  result = (float) ((a - 1073741824) >> 6);
610
 
  for (i = 512, expo = 2; i <= 16384; i *= 2, expo = expo * expo) {
611
 
    if (c & i) {
612
 
      result *= expo;
613
 
    }
614
 
  }
615
 
  return result;
616
 
}
617
 
*/
618
 
 
619
 
/*****************************************************************************/
620
 
/*                                                                           */
621
 
/*  narrowfloatrand()   Generate a float with random 24-bit significand and  */
622
 
/*                      a random exponent in [0, 7].                         */
623
 
/*                                                                           */
624
 
/*****************************************************************************/
625
 
 
626
 
/*
627
 
static float narrowfloatrand()
628
 
{
629
 
  float result;
630
 
  float expo;
631
 
  long a, c;
632
 
  long i;
633
 
 
634
 
  a = random();
635
 
  c = random();
636
 
  result = (float) ((a - 1073741824) >> 6);
637
 
  for (i = 512, expo = 2; i <= 2048; i *= 2, expo = expo * expo) {
638
 
    if (c & i) {
639
 
      result *= expo;
640
 
    }
641
 
  }
642
 
  return result;
643
 
}
644
 
*/
645
 
 
646
 
/*****************************************************************************/
647
 
/*                                                                           */
648
 
/*  uniformfloatrand()   Generate a float with random 24-bit significand.    */
649
 
/*                                                                           */
650
 
/*****************************************************************************/
651
 
 
652
 
/*
653
 
static float uniformfloatrand()
654
 
{
655
 
  float result;
656
 
  long a;
657
 
 
658
 
  a = random();
659
 
  result = (float) ((a - 1073741824) >> 6);
660
 
  return result;
661
 
}
662
 
*/
663
 
 
664
 
/*****************************************************************************/
665
 
/*                                                                           */
666
 
/*  fast_expansion_sum_zeroelim()   Sum two expansions, eliminating zero     */
667
 
/*                                  components from the output expansion.    */
668
 
/*                                                                           */
669
 
/*  Sets h = e + f.  See the long version of my paper for details.           */
670
 
/*                                                                           */
671
 
/*  If round-to-even is used (as with IEEE 754), maintains the strongly      */
672
 
/*  nonoverlapping property.  (That is, if e is strongly nonoverlapping, h   */
673
 
/*  will be also.)  Does NOT maintain the nonoverlapping or nonadjacent      */
674
 
/*  properties.                                                              */
675
 
/*                                                                           */
676
 
/*****************************************************************************/
677
 
 
678
 
static int fast_expansion_sum_zeroelim(int elen, REAL *e, 
679
 
                                       int flen, REAL *f, REAL *h)
680
 
     /* h cannot be e or f. */
681
 
{
682
 
  REAL Q;
683
 
  INEXACT REAL Qnew;
684
 
  INEXACT REAL hh;
685
 
  INEXACT REAL bvirt;
686
 
  REAL avirt, bround, around;
687
 
  int eindex, findex, hindex;
688
 
  REAL enow, fnow;
689
 
 
690
 
  enow = e[0];
691
 
  fnow = f[0];
692
 
  eindex = findex = 0;
693
 
  if ((fnow > enow) == (fnow > -enow)) {
694
 
    Q = enow;
695
 
    enow = e[++eindex];
696
 
  } else {
697
 
    Q = fnow;
698
 
    fnow = f[++findex];
699
 
  }
700
 
  hindex = 0;
701
 
  if ((eindex < elen) && (findex < flen)) {
702
 
    if ((fnow > enow) == (fnow > -enow)) {
703
 
      Fast_Two_Sum(enow, Q, Qnew, hh);
704
 
      enow = e[++eindex];
705
 
    } else {
706
 
      Fast_Two_Sum(fnow, Q, Qnew, hh);
707
 
      fnow = f[++findex];
708
 
    }
709
 
    Q = Qnew;
710
 
    if (hh != 0.0) {
711
 
      h[hindex++] = hh;
712
 
    }
713
 
    while ((eindex < elen) && (findex < flen)) {
714
 
      if ((fnow > enow) == (fnow > -enow)) {
715
 
        Two_Sum(Q, enow, Qnew, hh);
716
 
        enow = e[++eindex];
717
 
      } else {
718
 
        Two_Sum(Q, fnow, Qnew, hh);
719
 
        fnow = f[++findex];
720
 
      }
721
 
      Q = Qnew;
722
 
      if (hh != 0.0) {
723
 
        h[hindex++] = hh;
724
 
      }
725
 
    }
726
 
  }
727
 
  while (eindex < elen) {
728
 
    Two_Sum(Q, enow, Qnew, hh);
729
 
    enow = e[++eindex];
730
 
    Q = Qnew;
731
 
    if (hh != 0.0) {
732
 
      h[hindex++] = hh;
733
 
    }
734
 
  }
735
 
  while (findex < flen) {
736
 
    Two_Sum(Q, fnow, Qnew, hh);
737
 
    fnow = f[++findex];
738
 
    Q = Qnew;
739
 
    if (hh != 0.0) {
740
 
      h[hindex++] = hh;
741
 
    }
742
 
  }
743
 
  if ((Q != 0.0) || (hindex == 0)) {
744
 
    h[hindex++] = Q;
745
 
  }
746
 
  return hindex;
747
 
}
748
 
 
749
 
/*****************************************************************************/
750
 
/*                                                                           */
751
 
/*  scale_expansion_zeroelim()   Multiply an expansion by a scalar,          */
752
 
/*                               eliminating zero components from the        */
753
 
/*                               output expansion.                           */
754
 
/*                                                                           */
755
 
/*  Sets h = be.  See either version of my paper for details.                */
756
 
/*                                                                           */
757
 
/*  Maintains the nonoverlapping property.  If round-to-even is used (as     */
758
 
/*  with IEEE 754), maintains the strongly nonoverlapping and nonadjacent    */
759
 
/*  properties as well.  (That is, if e has one of these properties, so      */
760
 
/*  will h.)                                                                 */
761
 
/*                                                                           */
762
 
/*****************************************************************************/
763
 
 
764
 
static int scale_expansion_zeroelim(int elen, REAL *e, REAL b, REAL *h)
765
 
     /* e and h cannot be the same. */
766
 
{
767
 
  INEXACT REAL Q, sum;
768
 
  REAL hh;
769
 
  INEXACT REAL product1;
770
 
  REAL product0;
771
 
  int eindex, hindex;
772
 
  REAL enow;
773
 
  INEXACT REAL bvirt;
774
 
  REAL avirt, bround, around;
775
 
  INEXACT REAL c;
776
 
  INEXACT REAL abig;
777
 
  REAL ahi, alo, bhi, blo;
778
 
  REAL err1, err2, err3;
779
 
 
780
 
  Split(b, bhi, blo);
781
 
  Two_Product_Presplit(e[0], b, bhi, blo, Q, hh);
782
 
  hindex = 0;
783
 
  if (hh != 0) {
784
 
    h[hindex++] = hh;
785
 
  }
786
 
  for (eindex = 1; eindex < elen; eindex++) {
787
 
    enow = e[eindex];
788
 
    Two_Product_Presplit(enow, b, bhi, blo, product1, product0);
789
 
    Two_Sum(Q, product0, sum, hh);
790
 
    if (hh != 0) {
791
 
      h[hindex++] = hh;
792
 
    }
793
 
    Fast_Two_Sum(product1, sum, Q, hh);
794
 
    if (hh != 0) {
795
 
      h[hindex++] = hh;
796
 
    }
797
 
  }
798
 
  if ((Q != 0.0) || (hindex == 0)) {
799
 
    h[hindex++] = Q;
800
 
  }
801
 
  return hindex;
802
 
}
803
 
 
804
 
/*****************************************************************************/
805
 
/*                                                                           */
806
 
/*  estimate()   Produce a one-word estimate of an expansion's value.        */
807
 
/*                                                                           */
808
 
/*  See either version of my paper for details.                              */
809
 
/*                                                                           */
810
 
/*****************************************************************************/
811
 
 
812
 
static REAL estimate(int elen, REAL *e)
813
 
{
814
 
  REAL Q;
815
 
  int eindex;
816
 
 
817
 
  Q = e[0];
818
 
  for (eindex = 1; eindex < elen; eindex++) {
819
 
    Q += e[eindex];
820
 
  }
821
 
  return Q;
822
 
}
823
 
 
824
 
/*****************************************************************************/
825
 
/*                                                                           */
826
 
/*  orient2dfast()   Approximate 2D orientation test.  Nonrobust.            */
827
 
/*  orient2dexact()   Exact 2D orientation test.  Robust.                    */
828
 
/*  orient2dslow()   Another exact 2D orientation test.  Robust.             */
829
 
/*  orient2d()   Adaptive exact 2D orientation test.  Robust.                */
830
 
/*                                                                           */
831
 
/*               Return a positive value if the points pa, pb, and pc occur  */
832
 
/*               in counterclockwise order; a negative value if they occur   */
833
 
/*               in clockwise order; and zero if they are collinear.  The    */
834
 
/*               result is also a rough approximation of twice the signed    */
835
 
/*               area of the triangle defined by the three points.           */
836
 
/*                                                                           */
837
 
/*  Only the first and last routine should be used; the middle two are for   */
838
 
/*  timings.                                                                 */
839
 
/*                                                                           */
840
 
/*  The last three use exact arithmetic to ensure a correct answer.  The     */
841
 
/*  result returned is the determinant of a matrix.  In orient2d() only,     */
842
 
/*  this determinant is computed adaptively, in the sense that exact         */
843
 
/*  arithmetic is used only to the degree it is needed to ensure that the    */
844
 
/*  returned value has the correct sign.  Hence, orient2d() is usually quite */
845
 
/*  fast, but will run more slowly when the input points are collinear or    */
846
 
/*  nearly so.                                                               */
847
 
/*                                                                           */
848
 
/*****************************************************************************/
849
 
 
850
 
static REAL orient2dadapt(REAL *pa, REAL *pb, REAL *pc, REAL detsum)
851
 
{
852
 
  INEXACT REAL acx, acy, bcx, bcy;
853
 
  REAL acxtail, acytail, bcxtail, bcytail;
854
 
  INEXACT REAL detleft, detright;
855
 
  REAL detlefttail, detrighttail;
856
 
  REAL det, errbound;
857
 
  REAL B[4], C1[8], C2[12], D[16];
858
 
  INEXACT REAL B3;
859
 
  int C1length, C2length, Dlength;
860
 
  REAL u[4];
861
 
  INEXACT REAL u3;
862
 
  INEXACT REAL s1, t1;
863
 
  REAL s0, t0;
864
 
 
865
 
  INEXACT REAL bvirt;
866
 
  REAL avirt, bround, around;
867
 
  INEXACT REAL c;
868
 
  INEXACT REAL abig;
869
 
  REAL ahi, alo, bhi, blo;
870
 
  REAL err1, err2, err3;
871
 
  INEXACT REAL _i, _j;
872
 
  REAL _0;
873
 
 
874
 
  acx = (REAL) (pa[0] - pc[0]);
875
 
  bcx = (REAL) (pb[0] - pc[0]);
876
 
  acy = (REAL) (pa[1] - pc[1]);
877
 
  bcy = (REAL) (pb[1] - pc[1]);
878
 
 
879
 
  Two_Product(acx, bcy, detleft, detlefttail);
880
 
  Two_Product(acy, bcx, detright, detrighttail);
881
 
 
882
 
  Two_Two_Diff(detleft, detlefttail, detright, detrighttail,
883
 
               B3, B[2], B[1], B[0]);
884
 
  B[3] = B3;
885
 
 
886
 
  det = estimate(4, B);
887
 
  errbound = ccwerrboundB * detsum;
888
 
  if ((det >= errbound) || (-det >= errbound)) {
889
 
    return det;
890
 
  }
891
 
 
892
 
  Two_Diff_Tail(pa[0], pc[0], acx, acxtail);
893
 
  Two_Diff_Tail(pb[0], pc[0], bcx, bcxtail);
894
 
  Two_Diff_Tail(pa[1], pc[1], acy, acytail);
895
 
  Two_Diff_Tail(pb[1], pc[1], bcy, bcytail);
896
 
 
897
 
  if ((acxtail == 0.0) && (acytail == 0.0)
898
 
      && (bcxtail == 0.0) && (bcytail == 0.0)) {
899
 
    return det;
900
 
  }
901
 
 
902
 
  errbound = ccwerrboundC * detsum + resulterrbound * Absolute(det);
903
 
  det += (acx * bcytail + bcy * acxtail)
904
 
       - (acy * bcxtail + bcx * acytail);
905
 
  if ((det >= errbound) || (-det >= errbound)) {
906
 
    return det;
907
 
  }
908
 
 
909
 
  Two_Product(acxtail, bcy, s1, s0);
910
 
  Two_Product(acytail, bcx, t1, t0);
911
 
  Two_Two_Diff(s1, s0, t1, t0, u3, u[2], u[1], u[0]);
912
 
  u[3] = u3;
913
 
  C1length = fast_expansion_sum_zeroelim(4, B, 4, u, C1);
914
 
 
915
 
  Two_Product(acx, bcytail, s1, s0);
916
 
  Two_Product(acy, bcxtail, t1, t0);
917
 
  Two_Two_Diff(s1, s0, t1, t0, u3, u[2], u[1], u[0]);
918
 
  u[3] = u3;
919
 
  C2length = fast_expansion_sum_zeroelim(C1length, C1, 4, u, C2);
920
 
 
921
 
  Two_Product(acxtail, bcytail, s1, s0);
922
 
  Two_Product(acytail, bcxtail, t1, t0);
923
 
  Two_Two_Diff(s1, s0, t1, t0, u3, u[2], u[1], u[0]);
924
 
  u[3] = u3;
925
 
  Dlength = fast_expansion_sum_zeroelim(C2length, C2, 4, u, D);
926
 
 
927
 
  return(D[Dlength - 1]);
928
 
}
929
 
 
930
 
REAL orient2d(REAL *pa, REAL *pb, REAL *pc)
931
 
{
932
 
  REAL detleft, detright, det;
933
 
  REAL detsum, errbound;
934
 
  REAL orient;
935
 
 
936
 
  FPU_ROUND_DOUBLE;
937
 
 
938
 
  detleft = (pa[0] - pc[0]) * (pb[1] - pc[1]);
939
 
  detright = (pa[1] - pc[1]) * (pb[0] - pc[0]);
940
 
  det = detleft - detright;
941
 
 
942
 
  if (detleft > 0.0) {
943
 
    if (detright <= 0.0) {
944
 
      FPU_RESTORE;
945
 
      return det;
946
 
    } else {
947
 
      detsum = detleft + detright;
948
 
    }
949
 
  } else if (detleft < 0.0) {
950
 
    if (detright >= 0.0) {
951
 
      FPU_RESTORE;
952
 
      return det;
953
 
    } else {
954
 
      detsum = -detleft - detright;
955
 
    }
956
 
  } else {
957
 
    FPU_RESTORE;
958
 
    return det;
959
 
  }
960
 
 
961
 
  errbound = ccwerrboundA * detsum;
962
 
  if ((det >= errbound) || (-det >= errbound)) {
963
 
    FPU_RESTORE;
964
 
    return det;
965
 
  }
966
 
 
967
 
  orient = orient2dadapt(pa, pb, pc, detsum);
968
 
  FPU_RESTORE;
969
 
  return orient;
970
 
}
971
 
 
972
 
/*****************************************************************************/
973
 
/*                                                                           */
974
 
/*  orient3dfast()   Approximate 3D orientation test.  Nonrobust.            */
975
 
/*  orient3dexact()   Exact 3D orientation test.  Robust.                    */
976
 
/*  orient3dslow()   Another exact 3D orientation test.  Robust.             */
977
 
/*  orient3d()   Adaptive exact 3D orientation test.  Robust.                */
978
 
/*                                                                           */
979
 
/*               Return a positive value if the point pd lies below the      */
980
 
/*               plane passing through pa, pb, and pc; "below" is defined so */
981
 
/*               that pa, pb, and pc appear in counterclockwise order when   */
982
 
/*               viewed from above the plane.  Returns a negative value if   */
983
 
/*               pd lies above the plane.  Returns zero if the points are    */
984
 
/*               coplanar.  The result is also a rough approximation of six  */
985
 
/*               times the signed volume of the tetrahedron defined by the   */
986
 
/*               four points.                                                */
987
 
/*                                                                           */
988
 
/*  Only the first and last routine should be used; the middle two are for   */
989
 
/*  timings.                                                                 */
990
 
/*                                                                           */
991
 
/*  The last three use exact arithmetic to ensure a correct answer.  The     */
992
 
/*  result returned is the determinant of a matrix.  In orient3d() only,     */
993
 
/*  this determinant is computed adaptively, in the sense that exact         */
994
 
/*  arithmetic is used only to the degree it is needed to ensure that the    */
995
 
/*  returned value has the correct sign.  Hence, orient3d() is usually quite */
996
 
/*  fast, but will run more slowly when the input points are coplanar or     */
997
 
/*  nearly so.                                                               */
998
 
/*                                                                           */
999
 
/*****************************************************************************/
1000
 
 
1001
 
static REAL orient3dadapt(REAL *pa, REAL *pb, REAL *pc, REAL *pd, 
1002
 
                          REAL permanent)
1003
 
{
1004
 
  INEXACT REAL adx, bdx, cdx, ady, bdy, cdy, adz, bdz, cdz;
1005
 
  REAL det, errbound;
1006
 
 
1007
 
  INEXACT REAL bdxcdy1, cdxbdy1, cdxady1, adxcdy1, adxbdy1, bdxady1;
1008
 
  REAL bdxcdy0, cdxbdy0, cdxady0, adxcdy0, adxbdy0, bdxady0;
1009
 
  REAL bc[4], ca[4], ab[4];
1010
 
  INEXACT REAL bc3, ca3, ab3;
1011
 
  REAL adet[8], bdet[8], cdet[8];
1012
 
  int alen, blen, clen;
1013
 
  REAL abdet[16];
1014
 
  int ablen;
1015
 
  REAL *finnow, *finother, *finswap;
1016
 
  REAL fin1[192], fin2[192];
1017
 
  int finlength;
1018
 
 
1019
 
  REAL adxtail, bdxtail, cdxtail;
1020
 
  REAL adytail, bdytail, cdytail;
1021
 
  REAL adztail, bdztail, cdztail;
1022
 
  INEXACT REAL at_blarge, at_clarge;
1023
 
  INEXACT REAL bt_clarge, bt_alarge;
1024
 
  INEXACT REAL ct_alarge, ct_blarge;
1025
 
  REAL at_b[4], at_c[4], bt_c[4], bt_a[4], ct_a[4], ct_b[4];
1026
 
  int at_blen, at_clen, bt_clen, bt_alen, ct_alen, ct_blen;
1027
 
  INEXACT REAL bdxt_cdy1, cdxt_bdy1, cdxt_ady1;
1028
 
  INEXACT REAL adxt_cdy1, adxt_bdy1, bdxt_ady1;
1029
 
  REAL bdxt_cdy0, cdxt_bdy0, cdxt_ady0;
1030
 
  REAL adxt_cdy0, adxt_bdy0, bdxt_ady0;
1031
 
  INEXACT REAL bdyt_cdx1, cdyt_bdx1, cdyt_adx1;
1032
 
  INEXACT REAL adyt_cdx1, adyt_bdx1, bdyt_adx1;
1033
 
  REAL bdyt_cdx0, cdyt_bdx0, cdyt_adx0;
1034
 
  REAL adyt_cdx0, adyt_bdx0, bdyt_adx0;
1035
 
  REAL bct[8], cat[8], abt[8];
1036
 
  int bctlen, catlen, abtlen;
1037
 
  INEXACT REAL bdxt_cdyt1, cdxt_bdyt1, cdxt_adyt1;
1038
 
  INEXACT REAL adxt_cdyt1, adxt_bdyt1, bdxt_adyt1;
1039
 
  REAL bdxt_cdyt0, cdxt_bdyt0, cdxt_adyt0;
1040
 
  REAL adxt_cdyt0, adxt_bdyt0, bdxt_adyt0;
1041
 
  REAL u[4], v[12], w[16];
1042
 
  INEXACT REAL u3;
1043
 
  int vlength, wlength;
1044
 
  REAL negate;
1045
 
 
1046
 
  INEXACT REAL bvirt;
1047
 
  REAL avirt, bround, around;
1048
 
  INEXACT REAL c;
1049
 
  INEXACT REAL abig;
1050
 
  REAL ahi, alo, bhi, blo;
1051
 
  REAL err1, err2, err3;
1052
 
  INEXACT REAL _i, _j, _k;
1053
 
  REAL _0;
1054
 
 
1055
 
  adx = (REAL) (pa[0] - pd[0]);
1056
 
  bdx = (REAL) (pb[0] - pd[0]);
1057
 
  cdx = (REAL) (pc[0] - pd[0]);
1058
 
  ady = (REAL) (pa[1] - pd[1]);
1059
 
  bdy = (REAL) (pb[1] - pd[1]);
1060
 
  cdy = (REAL) (pc[1] - pd[1]);
1061
 
  adz = (REAL) (pa[2] - pd[2]);
1062
 
  bdz = (REAL) (pb[2] - pd[2]);
1063
 
  cdz = (REAL) (pc[2] - pd[2]);
1064
 
 
1065
 
  Two_Product(bdx, cdy, bdxcdy1, bdxcdy0);
1066
 
  Two_Product(cdx, bdy, cdxbdy1, cdxbdy0);
1067
 
  Two_Two_Diff(bdxcdy1, bdxcdy0, cdxbdy1, cdxbdy0, bc3, bc[2], bc[1], bc[0]);
1068
 
  bc[3] = bc3;
1069
 
  alen = scale_expansion_zeroelim(4, bc, adz, adet);
1070
 
 
1071
 
  Two_Product(cdx, ady, cdxady1, cdxady0);
1072
 
  Two_Product(adx, cdy, adxcdy1, adxcdy0);
1073
 
  Two_Two_Diff(cdxady1, cdxady0, adxcdy1, adxcdy0, ca3, ca[2], ca[1], ca[0]);
1074
 
  ca[3] = ca3;
1075
 
  blen = scale_expansion_zeroelim(4, ca, bdz, bdet);
1076
 
 
1077
 
  Two_Product(adx, bdy, adxbdy1, adxbdy0);
1078
 
  Two_Product(bdx, ady, bdxady1, bdxady0);
1079
 
  Two_Two_Diff(adxbdy1, adxbdy0, bdxady1, bdxady0, ab3, ab[2], ab[1], ab[0]);
1080
 
  ab[3] = ab3;
1081
 
  clen = scale_expansion_zeroelim(4, ab, cdz, cdet);
1082
 
 
1083
 
  ablen = fast_expansion_sum_zeroelim(alen, adet, blen, bdet, abdet);
1084
 
  finlength = fast_expansion_sum_zeroelim(ablen, abdet, clen, cdet, fin1);
1085
 
 
1086
 
  det = estimate(finlength, fin1);
1087
 
  errbound = o3derrboundB * permanent;
1088
 
  if ((det >= errbound) || (-det >= errbound)) {
1089
 
    return det;
1090
 
  }
1091
 
 
1092
 
  Two_Diff_Tail(pa[0], pd[0], adx, adxtail);
1093
 
  Two_Diff_Tail(pb[0], pd[0], bdx, bdxtail);
1094
 
  Two_Diff_Tail(pc[0], pd[0], cdx, cdxtail);
1095
 
  Two_Diff_Tail(pa[1], pd[1], ady, adytail);
1096
 
  Two_Diff_Tail(pb[1], pd[1], bdy, bdytail);
1097
 
  Two_Diff_Tail(pc[1], pd[1], cdy, cdytail);
1098
 
  Two_Diff_Tail(pa[2], pd[2], adz, adztail);
1099
 
  Two_Diff_Tail(pb[2], pd[2], bdz, bdztail);
1100
 
  Two_Diff_Tail(pc[2], pd[2], cdz, cdztail);
1101
 
 
1102
 
  if ((adxtail == 0.0) && (bdxtail == 0.0) && (cdxtail == 0.0)
1103
 
      && (adytail == 0.0) && (bdytail == 0.0) && (cdytail == 0.0)
1104
 
      && (adztail == 0.0) && (bdztail == 0.0) && (cdztail == 0.0)) {
1105
 
    return det;
1106
 
  }
1107
 
 
1108
 
  errbound = o3derrboundC * permanent + resulterrbound * Absolute(det);
1109
 
  det += (adz * ((bdx * cdytail + cdy * bdxtail)
1110
 
                 - (bdy * cdxtail + cdx * bdytail))
1111
 
          + adztail * (bdx * cdy - bdy * cdx))
1112
 
       + (bdz * ((cdx * adytail + ady * cdxtail)
1113
 
                 - (cdy * adxtail + adx * cdytail))
1114
 
          + bdztail * (cdx * ady - cdy * adx))
1115
 
       + (cdz * ((adx * bdytail + bdy * adxtail)
1116
 
                 - (ady * bdxtail + bdx * adytail))
1117
 
          + cdztail * (adx * bdy - ady * bdx));
1118
 
  if ((det >= errbound) || (-det >= errbound)) {
1119
 
    return det;
1120
 
  }
1121
 
 
1122
 
  finnow = fin1;
1123
 
  finother = fin2;
1124
 
 
1125
 
  if (adxtail == 0.0) {
1126
 
    if (adytail == 0.0) {
1127
 
      at_b[0] = 0.0;
1128
 
      at_blen = 1;
1129
 
      at_c[0] = 0.0;
1130
 
      at_clen = 1;
1131
 
    } else {
1132
 
      negate = -adytail;
1133
 
      Two_Product(negate, bdx, at_blarge, at_b[0]);
1134
 
      at_b[1] = at_blarge;
1135
 
      at_blen = 2;
1136
 
      Two_Product(adytail, cdx, at_clarge, at_c[0]);
1137
 
      at_c[1] = at_clarge;
1138
 
      at_clen = 2;
1139
 
    }
1140
 
  } else {
1141
 
    if (adytail == 0.0) {
1142
 
      Two_Product(adxtail, bdy, at_blarge, at_b[0]);
1143
 
      at_b[1] = at_blarge;
1144
 
      at_blen = 2;
1145
 
      negate = -adxtail;
1146
 
      Two_Product(negate, cdy, at_clarge, at_c[0]);
1147
 
      at_c[1] = at_clarge;
1148
 
      at_clen = 2;
1149
 
    } else {
1150
 
      Two_Product(adxtail, bdy, adxt_bdy1, adxt_bdy0);
1151
 
      Two_Product(adytail, bdx, adyt_bdx1, adyt_bdx0);
1152
 
      Two_Two_Diff(adxt_bdy1, adxt_bdy0, adyt_bdx1, adyt_bdx0,
1153
 
                   at_blarge, at_b[2], at_b[1], at_b[0]);
1154
 
      at_b[3] = at_blarge;
1155
 
      at_blen = 4;
1156
 
      Two_Product(adytail, cdx, adyt_cdx1, adyt_cdx0);
1157
 
      Two_Product(adxtail, cdy, adxt_cdy1, adxt_cdy0);
1158
 
      Two_Two_Diff(adyt_cdx1, adyt_cdx0, adxt_cdy1, adxt_cdy0,
1159
 
                   at_clarge, at_c[2], at_c[1], at_c[0]);
1160
 
      at_c[3] = at_clarge;
1161
 
      at_clen = 4;
1162
 
    }
1163
 
  }
1164
 
  if (bdxtail == 0.0) {
1165
 
    if (bdytail == 0.0) {
1166
 
      bt_c[0] = 0.0;
1167
 
      bt_clen = 1;
1168
 
      bt_a[0] = 0.0;
1169
 
      bt_alen = 1;
1170
 
    } else {
1171
 
      negate = -bdytail;
1172
 
      Two_Product(negate, cdx, bt_clarge, bt_c[0]);
1173
 
      bt_c[1] = bt_clarge;
1174
 
      bt_clen = 2;
1175
 
      Two_Product(bdytail, adx, bt_alarge, bt_a[0]);
1176
 
      bt_a[1] = bt_alarge;
1177
 
      bt_alen = 2;
1178
 
    }
1179
 
  } else {
1180
 
    if (bdytail == 0.0) {
1181
 
      Two_Product(bdxtail, cdy, bt_clarge, bt_c[0]);
1182
 
      bt_c[1] = bt_clarge;
1183
 
      bt_clen = 2;
1184
 
      negate = -bdxtail;
1185
 
      Two_Product(negate, ady, bt_alarge, bt_a[0]);
1186
 
      bt_a[1] = bt_alarge;
1187
 
      bt_alen = 2;
1188
 
    } else {
1189
 
      Two_Product(bdxtail, cdy, bdxt_cdy1, bdxt_cdy0);
1190
 
      Two_Product(bdytail, cdx, bdyt_cdx1, bdyt_cdx0);
1191
 
      Two_Two_Diff(bdxt_cdy1, bdxt_cdy0, bdyt_cdx1, bdyt_cdx0,
1192
 
                   bt_clarge, bt_c[2], bt_c[1], bt_c[0]);
1193
 
      bt_c[3] = bt_clarge;
1194
 
      bt_clen = 4;
1195
 
      Two_Product(bdytail, adx, bdyt_adx1, bdyt_adx0);
1196
 
      Two_Product(bdxtail, ady, bdxt_ady1, bdxt_ady0);
1197
 
      Two_Two_Diff(bdyt_adx1, bdyt_adx0, bdxt_ady1, bdxt_ady0,
1198
 
                  bt_alarge, bt_a[2], bt_a[1], bt_a[0]);
1199
 
      bt_a[3] = bt_alarge;
1200
 
      bt_alen = 4;
1201
 
    }
1202
 
  }
1203
 
  if (cdxtail == 0.0) {
1204
 
    if (cdytail == 0.0) {
1205
 
      ct_a[0] = 0.0;
1206
 
      ct_alen = 1;
1207
 
      ct_b[0] = 0.0;
1208
 
      ct_blen = 1;
1209
 
    } else {
1210
 
      negate = -cdytail;
1211
 
      Two_Product(negate, adx, ct_alarge, ct_a[0]);
1212
 
      ct_a[1] = ct_alarge;
1213
 
      ct_alen = 2;
1214
 
      Two_Product(cdytail, bdx, ct_blarge, ct_b[0]);
1215
 
      ct_b[1] = ct_blarge;
1216
 
      ct_blen = 2;
1217
 
    }
1218
 
  } else {
1219
 
    if (cdytail == 0.0) {
1220
 
      Two_Product(cdxtail, ady, ct_alarge, ct_a[0]);
1221
 
      ct_a[1] = ct_alarge;
1222
 
      ct_alen = 2;
1223
 
      negate = -cdxtail;
1224
 
      Two_Product(negate, bdy, ct_blarge, ct_b[0]);
1225
 
      ct_b[1] = ct_blarge;
1226
 
      ct_blen = 2;
1227
 
    } else {
1228
 
      Two_Product(cdxtail, ady, cdxt_ady1, cdxt_ady0);
1229
 
      Two_Product(cdytail, adx, cdyt_adx1, cdyt_adx0);
1230
 
      Two_Two_Diff(cdxt_ady1, cdxt_ady0, cdyt_adx1, cdyt_adx0,
1231
 
                   ct_alarge, ct_a[2], ct_a[1], ct_a[0]);
1232
 
      ct_a[3] = ct_alarge;
1233
 
      ct_alen = 4;
1234
 
      Two_Product(cdytail, bdx, cdyt_bdx1, cdyt_bdx0);
1235
 
      Two_Product(cdxtail, bdy, cdxt_bdy1, cdxt_bdy0);
1236
 
      Two_Two_Diff(cdyt_bdx1, cdyt_bdx0, cdxt_bdy1, cdxt_bdy0,
1237
 
                   ct_blarge, ct_b[2], ct_b[1], ct_b[0]);
1238
 
      ct_b[3] = ct_blarge;
1239
 
      ct_blen = 4;
1240
 
    }
1241
 
  }
1242
 
 
1243
 
  bctlen = fast_expansion_sum_zeroelim(bt_clen, bt_c, ct_blen, ct_b, bct);
1244
 
  wlength = scale_expansion_zeroelim(bctlen, bct, adz, w);
1245
 
  finlength = fast_expansion_sum_zeroelim(finlength, finnow, wlength, w,
1246
 
                                          finother);
1247
 
  finswap = finnow; finnow = finother; finother = finswap;
1248
 
 
1249
 
  catlen = fast_expansion_sum_zeroelim(ct_alen, ct_a, at_clen, at_c, cat);
1250
 
  wlength = scale_expansion_zeroelim(catlen, cat, bdz, w);
1251
 
  finlength = fast_expansion_sum_zeroelim(finlength, finnow, wlength, w,
1252
 
                                          finother);
1253
 
  finswap = finnow; finnow = finother; finother = finswap;
1254
 
 
1255
 
  abtlen = fast_expansion_sum_zeroelim(at_blen, at_b, bt_alen, bt_a, abt);
1256
 
  wlength = scale_expansion_zeroelim(abtlen, abt, cdz, w);
1257
 
  finlength = fast_expansion_sum_zeroelim(finlength, finnow, wlength, w,
1258
 
                                          finother);
1259
 
  finswap = finnow; finnow = finother; finother = finswap;
1260
 
 
1261
 
  if (adztail != 0.0) {
1262
 
    vlength = scale_expansion_zeroelim(4, bc, adztail, v);
1263
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, vlength, v,
1264
 
                                            finother);
1265
 
    finswap = finnow; finnow = finother; finother = finswap;
1266
 
  }
1267
 
  if (bdztail != 0.0) {
1268
 
    vlength = scale_expansion_zeroelim(4, ca, bdztail, v);
1269
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, vlength, v,
1270
 
                                            finother);
1271
 
    finswap = finnow; finnow = finother; finother = finswap;
1272
 
  }
1273
 
  if (cdztail != 0.0) {
1274
 
    vlength = scale_expansion_zeroelim(4, ab, cdztail, v);
1275
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, vlength, v,
1276
 
                                            finother);
1277
 
    finswap = finnow; finnow = finother; finother = finswap;
1278
 
  }
1279
 
 
1280
 
  if (adxtail != 0.0) {
1281
 
    if (bdytail != 0.0) {
1282
 
      Two_Product(adxtail, bdytail, adxt_bdyt1, adxt_bdyt0);
1283
 
      Two_One_Product(adxt_bdyt1, adxt_bdyt0, cdz, u3, u[2], u[1], u[0]);
1284
 
      u[3] = u3;
1285
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1286
 
                                              finother);
1287
 
      finswap = finnow; finnow = finother; finother = finswap;
1288
 
      if (cdztail != 0.0) {
1289
 
        Two_One_Product(adxt_bdyt1, adxt_bdyt0, cdztail, u3, u[2], u[1], u[0]);
1290
 
        u[3] = u3;
1291
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1292
 
                                                finother);
1293
 
        finswap = finnow; finnow = finother; finother = finswap;
1294
 
      }
1295
 
    }
1296
 
    if (cdytail != 0.0) {
1297
 
      negate = -adxtail;
1298
 
      Two_Product(negate, cdytail, adxt_cdyt1, adxt_cdyt0);
1299
 
      Two_One_Product(adxt_cdyt1, adxt_cdyt0, bdz, u3, u[2], u[1], u[0]);
1300
 
      u[3] = u3;
1301
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1302
 
                                              finother);
1303
 
      finswap = finnow; finnow = finother; finother = finswap;
1304
 
      if (bdztail != 0.0) {
1305
 
        Two_One_Product(adxt_cdyt1, adxt_cdyt0, bdztail, u3, u[2], u[1], u[0]);
1306
 
        u[3] = u3;
1307
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1308
 
                                                finother);
1309
 
        finswap = finnow; finnow = finother; finother = finswap;
1310
 
      }
1311
 
    }
1312
 
  }
1313
 
  if (bdxtail != 0.0) {
1314
 
    if (cdytail != 0.0) {
1315
 
      Two_Product(bdxtail, cdytail, bdxt_cdyt1, bdxt_cdyt0);
1316
 
      Two_One_Product(bdxt_cdyt1, bdxt_cdyt0, adz, u3, u[2], u[1], u[0]);
1317
 
      u[3] = u3;
1318
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1319
 
                                              finother);
1320
 
      finswap = finnow; finnow = finother; finother = finswap;
1321
 
      if (adztail != 0.0) {
1322
 
        Two_One_Product(bdxt_cdyt1, bdxt_cdyt0, adztail, u3, u[2], u[1], u[0]);
1323
 
        u[3] = u3;
1324
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1325
 
                                                finother);
1326
 
        finswap = finnow; finnow = finother; finother = finswap;
1327
 
      }
1328
 
    }
1329
 
    if (adytail != 0.0) {
1330
 
      negate = -bdxtail;
1331
 
      Two_Product(negate, adytail, bdxt_adyt1, bdxt_adyt0);
1332
 
      Two_One_Product(bdxt_adyt1, bdxt_adyt0, cdz, u3, u[2], u[1], u[0]);
1333
 
      u[3] = u3;
1334
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1335
 
                                              finother);
1336
 
      finswap = finnow; finnow = finother; finother = finswap;
1337
 
      if (cdztail != 0.0) {
1338
 
        Two_One_Product(bdxt_adyt1, bdxt_adyt0, cdztail, u3, u[2], u[1], u[0]);
1339
 
        u[3] = u3;
1340
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1341
 
                                                finother);
1342
 
        finswap = finnow; finnow = finother; finother = finswap;
1343
 
      }
1344
 
    }
1345
 
  }
1346
 
  if (cdxtail != 0.0) {
1347
 
    if (adytail != 0.0) {
1348
 
      Two_Product(cdxtail, adytail, cdxt_adyt1, cdxt_adyt0);
1349
 
      Two_One_Product(cdxt_adyt1, cdxt_adyt0, bdz, u3, u[2], u[1], u[0]);
1350
 
      u[3] = u3;
1351
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1352
 
                                              finother);
1353
 
      finswap = finnow; finnow = finother; finother = finswap;
1354
 
      if (bdztail != 0.0) {
1355
 
        Two_One_Product(cdxt_adyt1, cdxt_adyt0, bdztail, u3, u[2], u[1], u[0]);
1356
 
        u[3] = u3;
1357
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1358
 
                                                finother);
1359
 
        finswap = finnow; finnow = finother; finother = finswap;
1360
 
      }
1361
 
    }
1362
 
    if (bdytail != 0.0) {
1363
 
      negate = -cdxtail;
1364
 
      Two_Product(negate, bdytail, cdxt_bdyt1, cdxt_bdyt0);
1365
 
      Two_One_Product(cdxt_bdyt1, cdxt_bdyt0, adz, u3, u[2], u[1], u[0]);
1366
 
      u[3] = u3;
1367
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1368
 
                                              finother);
1369
 
      finswap = finnow; finnow = finother; finother = finswap;
1370
 
      if (adztail != 0.0) {
1371
 
        Two_One_Product(cdxt_bdyt1, cdxt_bdyt0, adztail, u3, u[2], u[1], u[0]);
1372
 
        u[3] = u3;
1373
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, 4, u,
1374
 
                                                finother);
1375
 
        finswap = finnow; finnow = finother; finother = finswap;
1376
 
      }
1377
 
    }
1378
 
  }
1379
 
 
1380
 
  if (adztail != 0.0) {
1381
 
    wlength = scale_expansion_zeroelim(bctlen, bct, adztail, w);
1382
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, wlength, w,
1383
 
                                            finother);
1384
 
    finswap = finnow; finnow = finother; finother = finswap;
1385
 
  }
1386
 
  if (bdztail != 0.0) {
1387
 
    wlength = scale_expansion_zeroelim(catlen, cat, bdztail, w);
1388
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, wlength, w,
1389
 
                                            finother);
1390
 
    finswap = finnow; finnow = finother; finother = finswap;
1391
 
  }
1392
 
  if (cdztail != 0.0) {
1393
 
    wlength = scale_expansion_zeroelim(abtlen, abt, cdztail, w);
1394
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, wlength, w,
1395
 
                                            finother);
1396
 
    finswap = finnow; finnow = finother; finother = finswap;
1397
 
  }
1398
 
 
1399
 
  return finnow[finlength - 1];
1400
 
}
1401
 
 
1402
 
REAL orient3d(REAL *pa, REAL *pb, REAL *pc, REAL *pd)
1403
 
{
1404
 
  REAL adx, bdx, cdx, ady, bdy, cdy, adz, bdz, cdz;
1405
 
  REAL bdxcdy, cdxbdy, cdxady, adxcdy, adxbdy, bdxady;
1406
 
  REAL det;
1407
 
  REAL permanent, errbound;
1408
 
  REAL orient;
1409
 
 
1410
 
  FPU_ROUND_DOUBLE;
1411
 
 
1412
 
  adx = pa[0] - pd[0];
1413
 
  bdx = pb[0] - pd[0];
1414
 
  cdx = pc[0] - pd[0];
1415
 
  ady = pa[1] - pd[1];
1416
 
  bdy = pb[1] - pd[1];
1417
 
  cdy = pc[1] - pd[1];
1418
 
  adz = pa[2] - pd[2];
1419
 
  bdz = pb[2] - pd[2];
1420
 
  cdz = pc[2] - pd[2];
1421
 
 
1422
 
  bdxcdy = bdx * cdy;
1423
 
  cdxbdy = cdx * bdy;
1424
 
 
1425
 
  cdxady = cdx * ady;
1426
 
  adxcdy = adx * cdy;
1427
 
 
1428
 
  adxbdy = adx * bdy;
1429
 
  bdxady = bdx * ady;
1430
 
 
1431
 
  det = adz * (bdxcdy - cdxbdy) 
1432
 
      + bdz * (cdxady - adxcdy)
1433
 
      + cdz * (adxbdy - bdxady);
1434
 
 
1435
 
  permanent = (Absolute(bdxcdy) + Absolute(cdxbdy)) * Absolute(adz)
1436
 
            + (Absolute(cdxady) + Absolute(adxcdy)) * Absolute(bdz)
1437
 
            + (Absolute(adxbdy) + Absolute(bdxady)) * Absolute(cdz);
1438
 
  errbound = o3derrboundA * permanent;
1439
 
  if ((det > errbound) || (-det > errbound)) {
1440
 
    FPU_RESTORE;
1441
 
    return det;
1442
 
  }
1443
 
 
1444
 
  orient = orient3dadapt(pa, pb, pc, pd, permanent);
1445
 
  FPU_RESTORE;
1446
 
  return orient;
1447
 
}
1448
 
 
1449
 
/*****************************************************************************/
1450
 
/*                                                                           */
1451
 
/*  incirclefast()   Approximate 2D incircle test.  Nonrobust.               */
1452
 
/*  incircleexact()   Exact 2D incircle test.  Robust.                       */
1453
 
/*  incircleslow()   Another exact 2D incircle test.  Robust.                */
1454
 
/*  incircle()   Adaptive exact 2D incircle test.  Robust.                   */
1455
 
/*                                                                           */
1456
 
/*               Return a positive value if the point pd lies inside the     */
1457
 
/*               circle passing through pa, pb, and pc; a negative value if  */
1458
 
/*               it lies outside; and zero if the four points are cocircular.*/
1459
 
/*               The points pa, pb, and pc must be in counterclockwise       */
1460
 
/*               order, or the sign of the result will be reversed.          */
1461
 
/*                                                                           */
1462
 
/*  Only the first and last routine should be used; the middle two are for   */
1463
 
/*  timings.                                                                 */
1464
 
/*                                                                           */
1465
 
/*  The last three use exact arithmetic to ensure a correct answer.  The     */
1466
 
/*  result returned is the determinant of a matrix.  In incircle() only,     */
1467
 
/*  this determinant is computed adaptively, in the sense that exact         */
1468
 
/*  arithmetic is used only to the degree it is needed to ensure that the    */
1469
 
/*  returned value has the correct sign.  Hence, incircle() is usually quite */
1470
 
/*  fast, but will run more slowly when the input points are cocircular or   */
1471
 
/*  nearly so.                                                               */
1472
 
/*                                                                           */
1473
 
/*****************************************************************************/
1474
 
 
1475
 
static REAL incircleadapt(REAL *pa, REAL *pb, REAL *pc, REAL *pd, 
1476
 
                          REAL permanent)
1477
 
{
1478
 
  INEXACT REAL adx, bdx, cdx, ady, bdy, cdy;
1479
 
  REAL det, errbound;
1480
 
 
1481
 
  INEXACT REAL bdxcdy1, cdxbdy1, cdxady1, adxcdy1, adxbdy1, bdxady1;
1482
 
  REAL bdxcdy0, cdxbdy0, cdxady0, adxcdy0, adxbdy0, bdxady0;
1483
 
  REAL bc[4], ca[4], ab[4];
1484
 
  INEXACT REAL bc3, ca3, ab3;
1485
 
  REAL axbc[8], axxbc[16], aybc[8], ayybc[16], adet[32];
1486
 
  int axbclen, axxbclen, aybclen, ayybclen, alen;
1487
 
  REAL bxca[8], bxxca[16], byca[8], byyca[16], bdet[32];
1488
 
  int bxcalen, bxxcalen, bycalen, byycalen, blen;
1489
 
  REAL cxab[8], cxxab[16], cyab[8], cyyab[16], cdet[32];
1490
 
  int cxablen, cxxablen, cyablen, cyyablen, clen;
1491
 
  REAL abdet[64];
1492
 
  int ablen;
1493
 
  REAL fin1[1152], fin2[1152];
1494
 
  REAL *finnow, *finother, *finswap;
1495
 
  int finlength;
1496
 
 
1497
 
  REAL adxtail, bdxtail, cdxtail, adytail, bdytail, cdytail;
1498
 
  INEXACT REAL adxadx1, adyady1, bdxbdx1, bdybdy1, cdxcdx1, cdycdy1;
1499
 
  REAL adxadx0, adyady0, bdxbdx0, bdybdy0, cdxcdx0, cdycdy0;
1500
 
  REAL aa[4], bb[4], cc[4];
1501
 
  INEXACT REAL aa3, bb3, cc3;
1502
 
  INEXACT REAL ti1, tj1;
1503
 
  REAL ti0, tj0;
1504
 
  REAL u[4], v[4];
1505
 
  INEXACT REAL u3, v3;
1506
 
  REAL temp8[8], temp16a[16], temp16b[16], temp16c[16];
1507
 
  REAL temp32a[32], temp32b[32], temp48[48], temp64[64];
1508
 
  int temp8len, temp16alen, temp16blen, temp16clen;
1509
 
  int temp32alen, temp32blen, temp48len, temp64len;
1510
 
  REAL axtbb[8], axtcc[8], aytbb[8], aytcc[8];
1511
 
  int axtbblen, axtcclen, aytbblen, aytcclen;
1512
 
  REAL bxtaa[8], bxtcc[8], bytaa[8], bytcc[8];
1513
 
  int bxtaalen, bxtcclen, bytaalen, bytcclen;
1514
 
  REAL cxtaa[8], cxtbb[8], cytaa[8], cytbb[8];
1515
 
  int cxtaalen, cxtbblen, cytaalen, cytbblen;
1516
 
  REAL axtbc[8], aytbc[8], bxtca[8], bytca[8], cxtab[8], cytab[8];
1517
 
  int axtbclen = 0, aytbclen = 0;
1518
 
  int bxtcalen = 0, bytcalen = 0;
1519
 
  int cxtablen = 0, cytablen = 0;
1520
 
  REAL axtbct[16], aytbct[16], bxtcat[16], bytcat[16], cxtabt[16], cytabt[16];
1521
 
  int axtbctlen, aytbctlen, bxtcatlen, bytcatlen, cxtabtlen, cytabtlen;
1522
 
  REAL axtbctt[8], aytbctt[8], bxtcatt[8];
1523
 
  REAL bytcatt[8], cxtabtt[8], cytabtt[8];
1524
 
  int axtbcttlen, aytbcttlen, bxtcattlen, bytcattlen, cxtabttlen, cytabttlen;
1525
 
  REAL abt[8], bct[8], cat[8];
1526
 
  int abtlen, bctlen, catlen;
1527
 
  REAL abtt[4], bctt[4], catt[4];
1528
 
  int abttlen, bcttlen, cattlen;
1529
 
  INEXACT REAL abtt3, bctt3, catt3;
1530
 
  REAL negate;
1531
 
 
1532
 
  INEXACT REAL bvirt;
1533
 
  REAL avirt, bround, around;
1534
 
  INEXACT REAL c;
1535
 
  INEXACT REAL abig;
1536
 
  REAL ahi, alo, bhi, blo;
1537
 
  REAL err1, err2, err3;
1538
 
  INEXACT REAL _i, _j;
1539
 
  REAL _0;
1540
 
 
1541
 
  adx = (REAL) (pa[0] - pd[0]);
1542
 
  bdx = (REAL) (pb[0] - pd[0]);
1543
 
  cdx = (REAL) (pc[0] - pd[0]);
1544
 
  ady = (REAL) (pa[1] - pd[1]);
1545
 
  bdy = (REAL) (pb[1] - pd[1]);
1546
 
  cdy = (REAL) (pc[1] - pd[1]);
1547
 
 
1548
 
  Two_Product(bdx, cdy, bdxcdy1, bdxcdy0);
1549
 
  Two_Product(cdx, bdy, cdxbdy1, cdxbdy0);
1550
 
  Two_Two_Diff(bdxcdy1, bdxcdy0, cdxbdy1, cdxbdy0, bc3, bc[2], bc[1], bc[0]);
1551
 
  bc[3] = bc3;
1552
 
  axbclen = scale_expansion_zeroelim(4, bc, adx, axbc);
1553
 
  axxbclen = scale_expansion_zeroelim(axbclen, axbc, adx, axxbc);
1554
 
  aybclen = scale_expansion_zeroelim(4, bc, ady, aybc);
1555
 
  ayybclen = scale_expansion_zeroelim(aybclen, aybc, ady, ayybc);
1556
 
  alen = fast_expansion_sum_zeroelim(axxbclen, axxbc, ayybclen, ayybc, adet);
1557
 
 
1558
 
  Two_Product(cdx, ady, cdxady1, cdxady0);
1559
 
  Two_Product(adx, cdy, adxcdy1, adxcdy0);
1560
 
  Two_Two_Diff(cdxady1, cdxady0, adxcdy1, adxcdy0, ca3, ca[2], ca[1], ca[0]);
1561
 
  ca[3] = ca3;
1562
 
  bxcalen = scale_expansion_zeroelim(4, ca, bdx, bxca);
1563
 
  bxxcalen = scale_expansion_zeroelim(bxcalen, bxca, bdx, bxxca);
1564
 
  bycalen = scale_expansion_zeroelim(4, ca, bdy, byca);
1565
 
  byycalen = scale_expansion_zeroelim(bycalen, byca, bdy, byyca);
1566
 
  blen = fast_expansion_sum_zeroelim(bxxcalen, bxxca, byycalen, byyca, bdet);
1567
 
 
1568
 
  Two_Product(adx, bdy, adxbdy1, adxbdy0);
1569
 
  Two_Product(bdx, ady, bdxady1, bdxady0);
1570
 
  Two_Two_Diff(adxbdy1, adxbdy0, bdxady1, bdxady0, ab3, ab[2], ab[1], ab[0]);
1571
 
  ab[3] = ab3;
1572
 
  cxablen = scale_expansion_zeroelim(4, ab, cdx, cxab);
1573
 
  cxxablen = scale_expansion_zeroelim(cxablen, cxab, cdx, cxxab);
1574
 
  cyablen = scale_expansion_zeroelim(4, ab, cdy, cyab);
1575
 
  cyyablen = scale_expansion_zeroelim(cyablen, cyab, cdy, cyyab);
1576
 
  clen = fast_expansion_sum_zeroelim(cxxablen, cxxab, cyyablen, cyyab, cdet);
1577
 
 
1578
 
  ablen = fast_expansion_sum_zeroelim(alen, adet, blen, bdet, abdet);
1579
 
  finlength = fast_expansion_sum_zeroelim(ablen, abdet, clen, cdet, fin1);
1580
 
 
1581
 
  det = estimate(finlength, fin1);
1582
 
  errbound = iccerrboundB * permanent;
1583
 
  if ((det >= errbound) || (-det >= errbound)) {
1584
 
    return det;
1585
 
  }
1586
 
 
1587
 
  Two_Diff_Tail(pa[0], pd[0], adx, adxtail);
1588
 
  Two_Diff_Tail(pa[1], pd[1], ady, adytail);
1589
 
  Two_Diff_Tail(pb[0], pd[0], bdx, bdxtail);
1590
 
  Two_Diff_Tail(pb[1], pd[1], bdy, bdytail);
1591
 
  Two_Diff_Tail(pc[0], pd[0], cdx, cdxtail);
1592
 
  Two_Diff_Tail(pc[1], pd[1], cdy, cdytail);
1593
 
  if ((adxtail == 0.0) && (bdxtail == 0.0) && (cdxtail == 0.0)
1594
 
      && (adytail == 0.0) && (bdytail == 0.0) && (cdytail == 0.0)) {
1595
 
    return det;
1596
 
  }
1597
 
 
1598
 
  errbound = iccerrboundC * permanent + resulterrbound * Absolute(det);
1599
 
  det += ((adx * adx + ady * ady) * ((bdx * cdytail + cdy * bdxtail)
1600
 
                                     - (bdy * cdxtail + cdx * bdytail))
1601
 
          + 2.0 * (adx * adxtail + ady * adytail) * (bdx * cdy - bdy * cdx))
1602
 
       + ((bdx * bdx + bdy * bdy) * ((cdx * adytail + ady * cdxtail)
1603
 
                                     - (cdy * adxtail + adx * cdytail))
1604
 
          + 2.0 * (bdx * bdxtail + bdy * bdytail) * (cdx * ady - cdy * adx))
1605
 
       + ((cdx * cdx + cdy * cdy) * ((adx * bdytail + bdy * adxtail)
1606
 
                                     - (ady * bdxtail + bdx * adytail))
1607
 
          + 2.0 * (cdx * cdxtail + cdy * cdytail) * (adx * bdy - ady * bdx));
1608
 
  if ((det >= errbound) || (-det >= errbound)) {
1609
 
    return det;
1610
 
  }
1611
 
 
1612
 
  finnow = fin1;
1613
 
  finother = fin2;
1614
 
 
1615
 
  if ((bdxtail != 0.0) || (bdytail != 0.0)
1616
 
      || (cdxtail != 0.0) || (cdytail != 0.0)) {
1617
 
    Square(adx, adxadx1, adxadx0);
1618
 
    Square(ady, adyady1, adyady0);
1619
 
    Two_Two_Sum(adxadx1, adxadx0, adyady1, adyady0, aa3, aa[2], aa[1], aa[0]);
1620
 
    aa[3] = aa3;
1621
 
  }
1622
 
  if ((cdxtail != 0.0) || (cdytail != 0.0)
1623
 
      || (adxtail != 0.0) || (adytail != 0.0)) {
1624
 
    Square(bdx, bdxbdx1, bdxbdx0);
1625
 
    Square(bdy, bdybdy1, bdybdy0);
1626
 
    Two_Two_Sum(bdxbdx1, bdxbdx0, bdybdy1, bdybdy0, bb3, bb[2], bb[1], bb[0]);
1627
 
    bb[3] = bb3;
1628
 
  }
1629
 
  if ((adxtail != 0.0) || (adytail != 0.0)
1630
 
      || (bdxtail != 0.0) || (bdytail != 0.0)) {
1631
 
    Square(cdx, cdxcdx1, cdxcdx0);
1632
 
    Square(cdy, cdycdy1, cdycdy0);
1633
 
    Two_Two_Sum(cdxcdx1, cdxcdx0, cdycdy1, cdycdy0, cc3, cc[2], cc[1], cc[0]);
1634
 
    cc[3] = cc3;
1635
 
  }
1636
 
 
1637
 
  if (adxtail != 0.0) {
1638
 
    axtbclen = scale_expansion_zeroelim(4, bc, adxtail, axtbc);
1639
 
    temp16alen = scale_expansion_zeroelim(axtbclen, axtbc, 2.0 * adx,
1640
 
                                          temp16a);
1641
 
 
1642
 
    axtcclen = scale_expansion_zeroelim(4, cc, adxtail, axtcc);
1643
 
    temp16blen = scale_expansion_zeroelim(axtcclen, axtcc, bdy, temp16b);
1644
 
 
1645
 
    axtbblen = scale_expansion_zeroelim(4, bb, adxtail, axtbb);
1646
 
    temp16clen = scale_expansion_zeroelim(axtbblen, axtbb, -cdy, temp16c);
1647
 
 
1648
 
    temp32alen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1649
 
                                            temp16blen, temp16b, temp32a);
1650
 
    temp48len = fast_expansion_sum_zeroelim(temp16clen, temp16c,
1651
 
                                            temp32alen, temp32a, temp48);
1652
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1653
 
                                            temp48, finother);
1654
 
    finswap = finnow; finnow = finother; finother = finswap;
1655
 
  }
1656
 
  if (adytail != 0.0) {
1657
 
    aytbclen = scale_expansion_zeroelim(4, bc, adytail, aytbc);
1658
 
    temp16alen = scale_expansion_zeroelim(aytbclen, aytbc, 2.0 * ady,
1659
 
                                          temp16a);
1660
 
 
1661
 
    aytbblen = scale_expansion_zeroelim(4, bb, adytail, aytbb);
1662
 
    temp16blen = scale_expansion_zeroelim(aytbblen, aytbb, cdx, temp16b);
1663
 
 
1664
 
    aytcclen = scale_expansion_zeroelim(4, cc, adytail, aytcc);
1665
 
    temp16clen = scale_expansion_zeroelim(aytcclen, aytcc, -bdx, temp16c);
1666
 
 
1667
 
    temp32alen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1668
 
                                            temp16blen, temp16b, temp32a);
1669
 
    temp48len = fast_expansion_sum_zeroelim(temp16clen, temp16c,
1670
 
                                            temp32alen, temp32a, temp48);
1671
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1672
 
                                            temp48, finother);
1673
 
    finswap = finnow; finnow = finother; finother = finswap;
1674
 
  }
1675
 
  if (bdxtail != 0.0) {
1676
 
    bxtcalen = scale_expansion_zeroelim(4, ca, bdxtail, bxtca);
1677
 
    temp16alen = scale_expansion_zeroelim(bxtcalen, bxtca, 2.0 * bdx,
1678
 
                                          temp16a);
1679
 
 
1680
 
    bxtaalen = scale_expansion_zeroelim(4, aa, bdxtail, bxtaa);
1681
 
    temp16blen = scale_expansion_zeroelim(bxtaalen, bxtaa, cdy, temp16b);
1682
 
 
1683
 
    bxtcclen = scale_expansion_zeroelim(4, cc, bdxtail, bxtcc);
1684
 
    temp16clen = scale_expansion_zeroelim(bxtcclen, bxtcc, -ady, temp16c);
1685
 
 
1686
 
    temp32alen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1687
 
                                            temp16blen, temp16b, temp32a);
1688
 
    temp48len = fast_expansion_sum_zeroelim(temp16clen, temp16c,
1689
 
                                            temp32alen, temp32a, temp48);
1690
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1691
 
                                            temp48, finother);
1692
 
    finswap = finnow; finnow = finother; finother = finswap;
1693
 
  }
1694
 
  if (bdytail != 0.0) {
1695
 
    bytcalen = scale_expansion_zeroelim(4, ca, bdytail, bytca);
1696
 
    temp16alen = scale_expansion_zeroelim(bytcalen, bytca, 2.0 * bdy,
1697
 
                                          temp16a);
1698
 
 
1699
 
    bytcclen = scale_expansion_zeroelim(4, cc, bdytail, bytcc);
1700
 
    temp16blen = scale_expansion_zeroelim(bytcclen, bytcc, adx, temp16b);
1701
 
 
1702
 
    bytaalen = scale_expansion_zeroelim(4, aa, bdytail, bytaa);
1703
 
    temp16clen = scale_expansion_zeroelim(bytaalen, bytaa, -cdx, temp16c);
1704
 
 
1705
 
    temp32alen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1706
 
                                            temp16blen, temp16b, temp32a);
1707
 
    temp48len = fast_expansion_sum_zeroelim(temp16clen, temp16c,
1708
 
                                            temp32alen, temp32a, temp48);
1709
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1710
 
                                            temp48, finother);
1711
 
    finswap = finnow; finnow = finother; finother = finswap;
1712
 
  }
1713
 
  if (cdxtail != 0.0) {
1714
 
    cxtablen = scale_expansion_zeroelim(4, ab, cdxtail, cxtab);
1715
 
    temp16alen = scale_expansion_zeroelim(cxtablen, cxtab, 2.0 * cdx,
1716
 
                                          temp16a);
1717
 
 
1718
 
    cxtbblen = scale_expansion_zeroelim(4, bb, cdxtail, cxtbb);
1719
 
    temp16blen = scale_expansion_zeroelim(cxtbblen, cxtbb, ady, temp16b);
1720
 
 
1721
 
    cxtaalen = scale_expansion_zeroelim(4, aa, cdxtail, cxtaa);
1722
 
    temp16clen = scale_expansion_zeroelim(cxtaalen, cxtaa, -bdy, temp16c);
1723
 
 
1724
 
    temp32alen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1725
 
                                            temp16blen, temp16b, temp32a);
1726
 
    temp48len = fast_expansion_sum_zeroelim(temp16clen, temp16c,
1727
 
                                            temp32alen, temp32a, temp48);
1728
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1729
 
                                            temp48, finother);
1730
 
    finswap = finnow; finnow = finother; finother = finswap;
1731
 
  }
1732
 
  if (cdytail != 0.0) {
1733
 
    cytablen = scale_expansion_zeroelim(4, ab, cdytail, cytab);
1734
 
    temp16alen = scale_expansion_zeroelim(cytablen, cytab, 2.0 * cdy,
1735
 
                                          temp16a);
1736
 
 
1737
 
    cytaalen = scale_expansion_zeroelim(4, aa, cdytail, cytaa);
1738
 
    temp16blen = scale_expansion_zeroelim(cytaalen, cytaa, bdx, temp16b);
1739
 
 
1740
 
    cytbblen = scale_expansion_zeroelim(4, bb, cdytail, cytbb);
1741
 
    temp16clen = scale_expansion_zeroelim(cytbblen, cytbb, -adx, temp16c);
1742
 
 
1743
 
    temp32alen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1744
 
                                            temp16blen, temp16b, temp32a);
1745
 
    temp48len = fast_expansion_sum_zeroelim(temp16clen, temp16c,
1746
 
                                            temp32alen, temp32a, temp48);
1747
 
    finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1748
 
                                            temp48, finother);
1749
 
    finswap = finnow; finnow = finother; finother = finswap;
1750
 
  }
1751
 
 
1752
 
  if ((adxtail != 0.0) || (adytail != 0.0)) {
1753
 
    if ((bdxtail != 0.0) || (bdytail != 0.0)
1754
 
        || (cdxtail != 0.0) || (cdytail != 0.0)) {
1755
 
      Two_Product(bdxtail, cdy, ti1, ti0);
1756
 
      Two_Product(bdx, cdytail, tj1, tj0);
1757
 
      Two_Two_Sum(ti1, ti0, tj1, tj0, u3, u[2], u[1], u[0]);
1758
 
      u[3] = u3;
1759
 
      negate = -bdy;
1760
 
      Two_Product(cdxtail, negate, ti1, ti0);
1761
 
      negate = -bdytail;
1762
 
      Two_Product(cdx, negate, tj1, tj0);
1763
 
      Two_Two_Sum(ti1, ti0, tj1, tj0, v3, v[2], v[1], v[0]);
1764
 
      v[3] = v3;
1765
 
      bctlen = fast_expansion_sum_zeroelim(4, u, 4, v, bct);
1766
 
 
1767
 
      Two_Product(bdxtail, cdytail, ti1, ti0);
1768
 
      Two_Product(cdxtail, bdytail, tj1, tj0);
1769
 
      Two_Two_Diff(ti1, ti0, tj1, tj0, bctt3, bctt[2], bctt[1], bctt[0]);
1770
 
      bctt[3] = bctt3;
1771
 
      bcttlen = 4;
1772
 
    } else {
1773
 
      bct[0] = 0.0;
1774
 
      bctlen = 1;
1775
 
      bctt[0] = 0.0;
1776
 
      bcttlen = 1;
1777
 
    }
1778
 
 
1779
 
    if (adxtail != 0.0) {
1780
 
      temp16alen = scale_expansion_zeroelim(axtbclen, axtbc, adxtail, temp16a);
1781
 
      axtbctlen = scale_expansion_zeroelim(bctlen, bct, adxtail, axtbct);
1782
 
      temp32alen = scale_expansion_zeroelim(axtbctlen, axtbct, 2.0 * adx,
1783
 
                                            temp32a);
1784
 
      temp48len = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1785
 
                                              temp32alen, temp32a, temp48);
1786
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1787
 
                                              temp48, finother);
1788
 
      finswap = finnow; finnow = finother; finother = finswap;
1789
 
      if (bdytail != 0.0) {
1790
 
        temp8len = scale_expansion_zeroelim(4, cc, adxtail, temp8);
1791
 
        temp16alen = scale_expansion_zeroelim(temp8len, temp8, bdytail,
1792
 
                                              temp16a);
1793
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp16alen,
1794
 
                                                temp16a, finother);
1795
 
        finswap = finnow; finnow = finother; finother = finswap;
1796
 
      }
1797
 
      if (cdytail != 0.0) {
1798
 
        temp8len = scale_expansion_zeroelim(4, bb, -adxtail, temp8);
1799
 
        temp16alen = scale_expansion_zeroelim(temp8len, temp8, cdytail,
1800
 
                                              temp16a);
1801
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp16alen,
1802
 
                                                temp16a, finother);
1803
 
        finswap = finnow; finnow = finother; finother = finswap;
1804
 
      }
1805
 
 
1806
 
      temp32alen = scale_expansion_zeroelim(axtbctlen, axtbct, adxtail,
1807
 
                                            temp32a);
1808
 
      axtbcttlen = scale_expansion_zeroelim(bcttlen, bctt, adxtail, axtbctt);
1809
 
      temp16alen = scale_expansion_zeroelim(axtbcttlen, axtbctt, 2.0 * adx,
1810
 
                                            temp16a);
1811
 
      temp16blen = scale_expansion_zeroelim(axtbcttlen, axtbctt, adxtail,
1812
 
                                            temp16b);
1813
 
      temp32blen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1814
 
                                              temp16blen, temp16b, temp32b);
1815
 
      temp64len = fast_expansion_sum_zeroelim(temp32alen, temp32a,
1816
 
                                              temp32blen, temp32b, temp64);
1817
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp64len,
1818
 
                                              temp64, finother);
1819
 
      finswap = finnow; finnow = finother; finother = finswap;
1820
 
    }
1821
 
    if (adytail != 0.0) {
1822
 
      temp16alen = scale_expansion_zeroelim(aytbclen, aytbc, adytail, temp16a);
1823
 
      aytbctlen = scale_expansion_zeroelim(bctlen, bct, adytail, aytbct);
1824
 
      temp32alen = scale_expansion_zeroelim(aytbctlen, aytbct, 2.0 * ady,
1825
 
                                            temp32a);
1826
 
      temp48len = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1827
 
                                              temp32alen, temp32a, temp48);
1828
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1829
 
                                              temp48, finother);
1830
 
      finswap = finnow; finnow = finother; finother = finswap;
1831
 
 
1832
 
 
1833
 
      temp32alen = scale_expansion_zeroelim(aytbctlen, aytbct, adytail,
1834
 
                                            temp32a);
1835
 
      aytbcttlen = scale_expansion_zeroelim(bcttlen, bctt, adytail, aytbctt);
1836
 
      temp16alen = scale_expansion_zeroelim(aytbcttlen, aytbctt, 2.0 * ady,
1837
 
                                            temp16a);
1838
 
      temp16blen = scale_expansion_zeroelim(aytbcttlen, aytbctt, adytail,
1839
 
                                            temp16b);
1840
 
      temp32blen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1841
 
                                              temp16blen, temp16b, temp32b);
1842
 
      temp64len = fast_expansion_sum_zeroelim(temp32alen, temp32a,
1843
 
                                              temp32blen, temp32b, temp64);
1844
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp64len,
1845
 
                                              temp64, finother);
1846
 
      finswap = finnow; finnow = finother; finother = finswap;
1847
 
    }
1848
 
  }
1849
 
  if ((bdxtail != 0.0) || (bdytail != 0.0)) {
1850
 
    if ((cdxtail != 0.0) || (cdytail != 0.0)
1851
 
        || (adxtail != 0.0) || (adytail != 0.0)) {
1852
 
      Two_Product(cdxtail, ady, ti1, ti0);
1853
 
      Two_Product(cdx, adytail, tj1, tj0);
1854
 
      Two_Two_Sum(ti1, ti0, tj1, tj0, u3, u[2], u[1], u[0]);
1855
 
      u[3] = u3;
1856
 
      negate = -cdy;
1857
 
      Two_Product(adxtail, negate, ti1, ti0);
1858
 
      negate = -cdytail;
1859
 
      Two_Product(adx, negate, tj1, tj0);
1860
 
      Two_Two_Sum(ti1, ti0, tj1, tj0, v3, v[2], v[1], v[0]);
1861
 
      v[3] = v3;
1862
 
      catlen = fast_expansion_sum_zeroelim(4, u, 4, v, cat);
1863
 
 
1864
 
      Two_Product(cdxtail, adytail, ti1, ti0);
1865
 
      Two_Product(adxtail, cdytail, tj1, tj0);
1866
 
      Two_Two_Diff(ti1, ti0, tj1, tj0, catt3, catt[2], catt[1], catt[0]);
1867
 
      catt[3] = catt3;
1868
 
      cattlen = 4;
1869
 
    } else {
1870
 
      cat[0] = 0.0;
1871
 
      catlen = 1;
1872
 
      catt[0] = 0.0;
1873
 
      cattlen = 1;
1874
 
    }
1875
 
 
1876
 
    if (bdxtail != 0.0) {
1877
 
      temp16alen = scale_expansion_zeroelim(bxtcalen, bxtca, bdxtail, temp16a);
1878
 
      bxtcatlen = scale_expansion_zeroelim(catlen, cat, bdxtail, bxtcat);
1879
 
      temp32alen = scale_expansion_zeroelim(bxtcatlen, bxtcat, 2.0 * bdx,
1880
 
                                            temp32a);
1881
 
      temp48len = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1882
 
                                              temp32alen, temp32a, temp48);
1883
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1884
 
                                              temp48, finother);
1885
 
      finswap = finnow; finnow = finother; finother = finswap;
1886
 
      if (cdytail != 0.0) {
1887
 
        temp8len = scale_expansion_zeroelim(4, aa, bdxtail, temp8);
1888
 
        temp16alen = scale_expansion_zeroelim(temp8len, temp8, cdytail,
1889
 
                                              temp16a);
1890
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp16alen,
1891
 
                                                temp16a, finother);
1892
 
        finswap = finnow; finnow = finother; finother = finswap;
1893
 
      }
1894
 
      if (adytail != 0.0) {
1895
 
        temp8len = scale_expansion_zeroelim(4, cc, -bdxtail, temp8);
1896
 
        temp16alen = scale_expansion_zeroelim(temp8len, temp8, adytail,
1897
 
                                              temp16a);
1898
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp16alen,
1899
 
                                                temp16a, finother);
1900
 
        finswap = finnow; finnow = finother; finother = finswap;
1901
 
      }
1902
 
 
1903
 
      temp32alen = scale_expansion_zeroelim(bxtcatlen, bxtcat, bdxtail,
1904
 
                                            temp32a);
1905
 
      bxtcattlen = scale_expansion_zeroelim(cattlen, catt, bdxtail, bxtcatt);
1906
 
      temp16alen = scale_expansion_zeroelim(bxtcattlen, bxtcatt, 2.0 * bdx,
1907
 
                                            temp16a);
1908
 
      temp16blen = scale_expansion_zeroelim(bxtcattlen, bxtcatt, bdxtail,
1909
 
                                            temp16b);
1910
 
      temp32blen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1911
 
                                              temp16blen, temp16b, temp32b);
1912
 
      temp64len = fast_expansion_sum_zeroelim(temp32alen, temp32a,
1913
 
                                              temp32blen, temp32b, temp64);
1914
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp64len,
1915
 
                                              temp64, finother);
1916
 
      finswap = finnow; finnow = finother; finother = finswap;
1917
 
    }
1918
 
    if (bdytail != 0.0) {
1919
 
      temp16alen = scale_expansion_zeroelim(bytcalen, bytca, bdytail, temp16a);
1920
 
      bytcatlen = scale_expansion_zeroelim(catlen, cat, bdytail, bytcat);
1921
 
      temp32alen = scale_expansion_zeroelim(bytcatlen, bytcat, 2.0 * bdy,
1922
 
                                            temp32a);
1923
 
      temp48len = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1924
 
                                              temp32alen, temp32a, temp48);
1925
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1926
 
                                              temp48, finother);
1927
 
      finswap = finnow; finnow = finother; finother = finswap;
1928
 
 
1929
 
 
1930
 
      temp32alen = scale_expansion_zeroelim(bytcatlen, bytcat, bdytail,
1931
 
                                            temp32a);
1932
 
      bytcattlen = scale_expansion_zeroelim(cattlen, catt, bdytail, bytcatt);
1933
 
      temp16alen = scale_expansion_zeroelim(bytcattlen, bytcatt, 2.0 * bdy,
1934
 
                                            temp16a);
1935
 
      temp16blen = scale_expansion_zeroelim(bytcattlen, bytcatt, bdytail,
1936
 
                                            temp16b);
1937
 
      temp32blen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1938
 
                                              temp16blen, temp16b, temp32b);
1939
 
      temp64len = fast_expansion_sum_zeroelim(temp32alen, temp32a,
1940
 
                                              temp32blen, temp32b, temp64);
1941
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp64len,
1942
 
                                              temp64, finother);
1943
 
      finswap = finnow; finnow = finother; finother = finswap;
1944
 
    }
1945
 
  }
1946
 
  if ((cdxtail != 0.0) || (cdytail != 0.0)) {
1947
 
    if ((adxtail != 0.0) || (adytail != 0.0)
1948
 
        || (bdxtail != 0.0) || (bdytail != 0.0)) {
1949
 
      Two_Product(adxtail, bdy, ti1, ti0);
1950
 
      Two_Product(adx, bdytail, tj1, tj0);
1951
 
      Two_Two_Sum(ti1, ti0, tj1, tj0, u3, u[2], u[1], u[0]);
1952
 
      u[3] = u3;
1953
 
      negate = -ady;
1954
 
      Two_Product(bdxtail, negate, ti1, ti0);
1955
 
      negate = -adytail;
1956
 
      Two_Product(bdx, negate, tj1, tj0);
1957
 
      Two_Two_Sum(ti1, ti0, tj1, tj0, v3, v[2], v[1], v[0]);
1958
 
      v[3] = v3;
1959
 
      abtlen = fast_expansion_sum_zeroelim(4, u, 4, v, abt);
1960
 
 
1961
 
      Two_Product(adxtail, bdytail, ti1, ti0);
1962
 
      Two_Product(bdxtail, adytail, tj1, tj0);
1963
 
      Two_Two_Diff(ti1, ti0, tj1, tj0, abtt3, abtt[2], abtt[1], abtt[0]);
1964
 
      abtt[3] = abtt3;
1965
 
      abttlen = 4;
1966
 
    } else {
1967
 
      abt[0] = 0.0;
1968
 
      abtlen = 1;
1969
 
      abtt[0] = 0.0;
1970
 
      abttlen = 1;
1971
 
    }
1972
 
 
1973
 
    if (cdxtail != 0.0) {
1974
 
      temp16alen = scale_expansion_zeroelim(cxtablen, cxtab, cdxtail, temp16a);
1975
 
      cxtabtlen = scale_expansion_zeroelim(abtlen, abt, cdxtail, cxtabt);
1976
 
      temp32alen = scale_expansion_zeroelim(cxtabtlen, cxtabt, 2.0 * cdx,
1977
 
                                            temp32a);
1978
 
      temp48len = fast_expansion_sum_zeroelim(temp16alen, temp16a,
1979
 
                                              temp32alen, temp32a, temp48);
1980
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
1981
 
                                              temp48, finother);
1982
 
      finswap = finnow; finnow = finother; finother = finswap;
1983
 
      if (adytail != 0.0) {
1984
 
        temp8len = scale_expansion_zeroelim(4, bb, cdxtail, temp8);
1985
 
        temp16alen = scale_expansion_zeroelim(temp8len, temp8, adytail,
1986
 
                                              temp16a);
1987
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp16alen,
1988
 
                                                temp16a, finother);
1989
 
        finswap = finnow; finnow = finother; finother = finswap;
1990
 
      }
1991
 
      if (bdytail != 0.0) {
1992
 
        temp8len = scale_expansion_zeroelim(4, aa, -cdxtail, temp8);
1993
 
        temp16alen = scale_expansion_zeroelim(temp8len, temp8, bdytail,
1994
 
                                              temp16a);
1995
 
        finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp16alen,
1996
 
                                                temp16a, finother);
1997
 
        finswap = finnow; finnow = finother; finother = finswap;
1998
 
      }
1999
 
 
2000
 
      temp32alen = scale_expansion_zeroelim(cxtabtlen, cxtabt, cdxtail,
2001
 
                                            temp32a);
2002
 
      cxtabttlen = scale_expansion_zeroelim(abttlen, abtt, cdxtail, cxtabtt);
2003
 
      temp16alen = scale_expansion_zeroelim(cxtabttlen, cxtabtt, 2.0 * cdx,
2004
 
                                            temp16a);
2005
 
      temp16blen = scale_expansion_zeroelim(cxtabttlen, cxtabtt, cdxtail,
2006
 
                                            temp16b);
2007
 
      temp32blen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
2008
 
                                              temp16blen, temp16b, temp32b);
2009
 
      temp64len = fast_expansion_sum_zeroelim(temp32alen, temp32a,
2010
 
                                              temp32blen, temp32b, temp64);
2011
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp64len,
2012
 
                                              temp64, finother);
2013
 
      finswap = finnow; finnow = finother; finother = finswap;
2014
 
    }
2015
 
    if (cdytail != 0.0) {
2016
 
      temp16alen = scale_expansion_zeroelim(cytablen, cytab, cdytail, temp16a);
2017
 
      cytabtlen = scale_expansion_zeroelim(abtlen, abt, cdytail, cytabt);
2018
 
      temp32alen = scale_expansion_zeroelim(cytabtlen, cytabt, 2.0 * cdy,
2019
 
                                            temp32a);
2020
 
      temp48len = fast_expansion_sum_zeroelim(temp16alen, temp16a,
2021
 
                                              temp32alen, temp32a, temp48);
2022
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp48len,
2023
 
                                              temp48, finother);
2024
 
      finswap = finnow; finnow = finother; finother = finswap;
2025
 
 
2026
 
 
2027
 
      temp32alen = scale_expansion_zeroelim(cytabtlen, cytabt, cdytail,
2028
 
                                            temp32a);
2029
 
      cytabttlen = scale_expansion_zeroelim(abttlen, abtt, cdytail, cytabtt);
2030
 
      temp16alen = scale_expansion_zeroelim(cytabttlen, cytabtt, 2.0 * cdy,
2031
 
                                            temp16a);
2032
 
      temp16blen = scale_expansion_zeroelim(cytabttlen, cytabtt, cdytail,
2033
 
                                            temp16b);
2034
 
      temp32blen = fast_expansion_sum_zeroelim(temp16alen, temp16a,
2035
 
                                              temp16blen, temp16b, temp32b);
2036
 
      temp64len = fast_expansion_sum_zeroelim(temp32alen, temp32a,
2037
 
                                              temp32blen, temp32b, temp64);
2038
 
      finlength = fast_expansion_sum_zeroelim(finlength, finnow, temp64len,
2039
 
                                              temp64, finother);
2040
 
      finswap = finnow; finnow = finother; finother = finswap;
2041
 
    }
2042
 
  }
2043
 
 
2044
 
  return finnow[finlength - 1];
2045
 
}
2046
 
 
2047
 
REAL incircle(REAL *pa, REAL *pb, REAL *pc, REAL *pd)
2048
 
{
2049
 
  REAL adx, bdx, cdx, ady, bdy, cdy;
2050
 
  REAL bdxcdy, cdxbdy, cdxady, adxcdy, adxbdy, bdxady;
2051
 
  REAL alift, blift, clift;
2052
 
  REAL det;
2053
 
  REAL permanent, errbound;
2054
 
  REAL inc;
2055
 
 
2056
 
  FPU_ROUND_DOUBLE;
2057
 
  
2058
 
  adx = pa[0] - pd[0];
2059
 
  bdx = pb[0] - pd[0];
2060
 
  cdx = pc[0] - pd[0];
2061
 
  ady = pa[1] - pd[1];
2062
 
  bdy = pb[1] - pd[1];
2063
 
  cdy = pc[1] - pd[1];
2064
 
 
2065
 
  bdxcdy = bdx * cdy;
2066
 
  cdxbdy = cdx * bdy;
2067
 
  alift = adx * adx + ady * ady;
2068
 
 
2069
 
  cdxady = cdx * ady;
2070
 
  adxcdy = adx * cdy;
2071
 
  blift = bdx * bdx + bdy * bdy;
2072
 
 
2073
 
  adxbdy = adx * bdy;
2074
 
  bdxady = bdx * ady;
2075
 
  clift = cdx * cdx + cdy * cdy;
2076
 
 
2077
 
  det = alift * (bdxcdy - cdxbdy)
2078
 
      + blift * (cdxady - adxcdy)
2079
 
      + clift * (adxbdy - bdxady);
2080
 
 
2081
 
  permanent = (Absolute(bdxcdy) + Absolute(cdxbdy)) * alift
2082
 
            + (Absolute(cdxady) + Absolute(adxcdy)) * blift
2083
 
            + (Absolute(adxbdy) + Absolute(bdxady)) * clift;
2084
 
  errbound = iccerrboundA * permanent;
2085
 
  if ((det > errbound) || (-det > errbound)) {
2086
 
    FPU_RESTORE;
2087
 
    return det;
2088
 
  }
2089
 
 
2090
 
  inc = incircleadapt(pa, pb, pc, pd, permanent);
2091
 
  FPU_RESTORE;
2092
 
  return inc;
2093
 
}
2094
 
 
2095
 
/*****************************************************************************/
2096
 
/*                                                                           */
2097
 
/*  inspherefast()   Approximate 3D insphere test.  Nonrobust.               */
2098
 
/*  insphereexact()   Exact 3D insphere test.  Robust.                       */
2099
 
/*  insphereslow()   Another exact 3D insphere test.  Robust.                */
2100
 
/*  insphere()   Adaptive exact 3D insphere test.  Robust.                   */
2101
 
/*                                                                           */
2102
 
/*               Return a positive value if the point pe lies inside the     */
2103
 
/*               sphere passing through pa, pb, pc, and pd; a negative value */
2104
 
/*               if it lies outside; and zero if the five points are         */
2105
 
/*               cospherical.  The points pa, pb, pc, and pd must be ordered */
2106
 
/*               so that they have a positive orientation (as defined by     */
2107
 
/*               orient3d()), or the sign of the result will be reversed.    */
2108
 
/*                                                                           */
2109
 
/*  Only the first and last routine should be used; the middle two are for   */
2110
 
/*  timings.                                                                 */
2111
 
/*                                                                           */
2112
 
/*  The last three use exact arithmetic to ensure a correct answer.  The     */
2113
 
/*  result returned is the determinant of a matrix.  In insphere() only,     */
2114
 
/*  this determinant is computed adaptively, in the sense that exact         */
2115
 
/*  arithmetic is used only to the degree it is needed to ensure that the    */
2116
 
/*  returned value has the correct sign.  Hence, insphere() is usually quite */
2117
 
/*  fast, but will run more slowly when the input points are cospherical or  */
2118
 
/*  nearly so.                                                               */
2119
 
/*                                                                           */
2120
 
/*****************************************************************************/
2121
 
 
2122
 
static REAL insphereexact(REAL *pa, REAL *pb, REAL *pc, REAL *pd, REAL *pe)
2123
 
{
2124
 
  INEXACT REAL axby1, bxcy1, cxdy1, dxey1, exay1;
2125
 
  INEXACT REAL bxay1, cxby1, dxcy1, exdy1, axey1;
2126
 
  INEXACT REAL axcy1, bxdy1, cxey1, dxay1, exby1;
2127
 
  INEXACT REAL cxay1, dxby1, excy1, axdy1, bxey1;
2128
 
  REAL axby0, bxcy0, cxdy0, dxey0, exay0;
2129
 
  REAL bxay0, cxby0, dxcy0, exdy0, axey0;
2130
 
  REAL axcy0, bxdy0, cxey0, dxay0, exby0;
2131
 
  REAL cxay0, dxby0, excy0, axdy0, bxey0;
2132
 
  REAL ab[4], bc[4], cd[4], de[4], ea[4];
2133
 
  REAL ac[4], bd[4], ce[4], da[4], eb[4];
2134
 
  REAL temp8a[8], temp8b[8], temp16[16];
2135
 
  int temp8alen, temp8blen, temp16len;
2136
 
  REAL abc[24], bcd[24], cde[24], dea[24], eab[24];
2137
 
  REAL abd[24], bce[24], cda[24], deb[24], eac[24];
2138
 
  int abclen, bcdlen, cdelen, dealen, eablen;
2139
 
  int abdlen, bcelen, cdalen, deblen, eaclen;
2140
 
  REAL temp48a[48], temp48b[48];
2141
 
  int temp48alen, temp48blen;
2142
 
  REAL abcd[96], bcde[96], cdea[96], deab[96], eabc[96];
2143
 
  int abcdlen, bcdelen, cdealen, deablen, eabclen;
2144
 
  REAL temp192[192];
2145
 
  REAL det384x[384], det384y[384], det384z[384];
2146
 
  int xlen, ylen, zlen;
2147
 
  REAL detxy[768];
2148
 
  int xylen;
2149
 
  REAL adet[1152], bdet[1152], cdet[1152], ddet[1152], edet[1152];
2150
 
  int alen, blen, clen, dlen, elen;
2151
 
  REAL abdet[2304], cddet[2304], cdedet[3456];
2152
 
  int ablen, cdlen;
2153
 
  REAL deter[5760];
2154
 
  int deterlen;
2155
 
  int i;
2156
 
 
2157
 
  INEXACT REAL bvirt;
2158
 
  REAL avirt, bround, around;
2159
 
  INEXACT REAL c;
2160
 
  INEXACT REAL abig;
2161
 
  REAL ahi, alo, bhi, blo;
2162
 
  REAL err1, err2, err3;
2163
 
  INEXACT REAL _i, _j;
2164
 
  REAL _0;
2165
 
 
2166
 
  Two_Product(pa[0], pb[1], axby1, axby0);
2167
 
  Two_Product(pb[0], pa[1], bxay1, bxay0);
2168
 
  Two_Two_Diff(axby1, axby0, bxay1, bxay0, ab[3], ab[2], ab[1], ab[0]);
2169
 
 
2170
 
  Two_Product(pb[0], pc[1], bxcy1, bxcy0);
2171
 
  Two_Product(pc[0], pb[1], cxby1, cxby0);
2172
 
  Two_Two_Diff(bxcy1, bxcy0, cxby1, cxby0, bc[3], bc[2], bc[1], bc[0]);
2173
 
 
2174
 
  Two_Product(pc[0], pd[1], cxdy1, cxdy0);
2175
 
  Two_Product(pd[0], pc[1], dxcy1, dxcy0);
2176
 
  Two_Two_Diff(cxdy1, cxdy0, dxcy1, dxcy0, cd[3], cd[2], cd[1], cd[0]);
2177
 
 
2178
 
  Two_Product(pd[0], pe[1], dxey1, dxey0);
2179
 
  Two_Product(pe[0], pd[1], exdy1, exdy0);
2180
 
  Two_Two_Diff(dxey1, dxey0, exdy1, exdy0, de[3], de[2], de[1], de[0]);
2181
 
 
2182
 
  Two_Product(pe[0], pa[1], exay1, exay0);
2183
 
  Two_Product(pa[0], pe[1], axey1, axey0);
2184
 
  Two_Two_Diff(exay1, exay0, axey1, axey0, ea[3], ea[2], ea[1], ea[0]);
2185
 
 
2186
 
  Two_Product(pa[0], pc[1], axcy1, axcy0);
2187
 
  Two_Product(pc[0], pa[1], cxay1, cxay0);
2188
 
  Two_Two_Diff(axcy1, axcy0, cxay1, cxay0, ac[3], ac[2], ac[1], ac[0]);
2189
 
 
2190
 
  Two_Product(pb[0], pd[1], bxdy1, bxdy0);
2191
 
  Two_Product(pd[0], pb[1], dxby1, dxby0);
2192
 
  Two_Two_Diff(bxdy1, bxdy0, dxby1, dxby0, bd[3], bd[2], bd[1], bd[0]);
2193
 
 
2194
 
  Two_Product(pc[0], pe[1], cxey1, cxey0);
2195
 
  Two_Product(pe[0], pc[1], excy1, excy0);
2196
 
  Two_Two_Diff(cxey1, cxey0, excy1, excy0, ce[3], ce[2], ce[1], ce[0]);
2197
 
 
2198
 
  Two_Product(pd[0], pa[1], dxay1, dxay0);
2199
 
  Two_Product(pa[0], pd[1], axdy1, axdy0);
2200
 
  Two_Two_Diff(dxay1, dxay0, axdy1, axdy0, da[3], da[2], da[1], da[0]);
2201
 
 
2202
 
  Two_Product(pe[0], pb[1], exby1, exby0);
2203
 
  Two_Product(pb[0], pe[1], bxey1, bxey0);
2204
 
  Two_Two_Diff(exby1, exby0, bxey1, bxey0, eb[3], eb[2], eb[1], eb[0]);
2205
 
 
2206
 
  temp8alen = scale_expansion_zeroelim(4, bc, pa[2], temp8a);
2207
 
  temp8blen = scale_expansion_zeroelim(4, ac, -pb[2], temp8b);
2208
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2209
 
                                          temp16);
2210
 
  temp8alen = scale_expansion_zeroelim(4, ab, pc[2], temp8a);
2211
 
  abclen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2212
 
                                       abc);
2213
 
 
2214
 
  temp8alen = scale_expansion_zeroelim(4, cd, pb[2], temp8a);
2215
 
  temp8blen = scale_expansion_zeroelim(4, bd, -pc[2], temp8b);
2216
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2217
 
                                          temp16);
2218
 
  temp8alen = scale_expansion_zeroelim(4, bc, pd[2], temp8a);
2219
 
  bcdlen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2220
 
                                       bcd);
2221
 
 
2222
 
  temp8alen = scale_expansion_zeroelim(4, de, pc[2], temp8a);
2223
 
  temp8blen = scale_expansion_zeroelim(4, ce, -pd[2], temp8b);
2224
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2225
 
                                          temp16);
2226
 
  temp8alen = scale_expansion_zeroelim(4, cd, pe[2], temp8a);
2227
 
  cdelen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2228
 
                                       cde);
2229
 
 
2230
 
  temp8alen = scale_expansion_zeroelim(4, ea, pd[2], temp8a);
2231
 
  temp8blen = scale_expansion_zeroelim(4, da, -pe[2], temp8b);
2232
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2233
 
                                          temp16);
2234
 
  temp8alen = scale_expansion_zeroelim(4, de, pa[2], temp8a);
2235
 
  dealen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2236
 
                                       dea);
2237
 
 
2238
 
  temp8alen = scale_expansion_zeroelim(4, ab, pe[2], temp8a);
2239
 
  temp8blen = scale_expansion_zeroelim(4, eb, -pa[2], temp8b);
2240
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2241
 
                                          temp16);
2242
 
  temp8alen = scale_expansion_zeroelim(4, ea, pb[2], temp8a);
2243
 
  eablen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2244
 
                                       eab);
2245
 
 
2246
 
  temp8alen = scale_expansion_zeroelim(4, bd, pa[2], temp8a);
2247
 
  temp8blen = scale_expansion_zeroelim(4, da, pb[2], temp8b);
2248
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2249
 
                                          temp16);
2250
 
  temp8alen = scale_expansion_zeroelim(4, ab, pd[2], temp8a);
2251
 
  abdlen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2252
 
                                       abd);
2253
 
 
2254
 
  temp8alen = scale_expansion_zeroelim(4, ce, pb[2], temp8a);
2255
 
  temp8blen = scale_expansion_zeroelim(4, eb, pc[2], temp8b);
2256
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2257
 
                                          temp16);
2258
 
  temp8alen = scale_expansion_zeroelim(4, bc, pe[2], temp8a);
2259
 
  bcelen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2260
 
                                       bce);
2261
 
 
2262
 
  temp8alen = scale_expansion_zeroelim(4, da, pc[2], temp8a);
2263
 
  temp8blen = scale_expansion_zeroelim(4, ac, pd[2], temp8b);
2264
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2265
 
                                          temp16);
2266
 
  temp8alen = scale_expansion_zeroelim(4, cd, pa[2], temp8a);
2267
 
  cdalen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2268
 
                                       cda);
2269
 
 
2270
 
  temp8alen = scale_expansion_zeroelim(4, eb, pd[2], temp8a);
2271
 
  temp8blen = scale_expansion_zeroelim(4, bd, pe[2], temp8b);
2272
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2273
 
                                          temp16);
2274
 
  temp8alen = scale_expansion_zeroelim(4, de, pb[2], temp8a);
2275
 
  deblen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2276
 
                                       deb);
2277
 
 
2278
 
  temp8alen = scale_expansion_zeroelim(4, ac, pe[2], temp8a);
2279
 
  temp8blen = scale_expansion_zeroelim(4, ce, pa[2], temp8b);
2280
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp8blen, temp8b,
2281
 
                                          temp16);
2282
 
  temp8alen = scale_expansion_zeroelim(4, ea, pc[2], temp8a);
2283
 
  eaclen = fast_expansion_sum_zeroelim(temp8alen, temp8a, temp16len, temp16,
2284
 
                                       eac);
2285
 
 
2286
 
  temp48alen = fast_expansion_sum_zeroelim(cdelen, cde, bcelen, bce, temp48a);
2287
 
  temp48blen = fast_expansion_sum_zeroelim(deblen, deb, bcdlen, bcd, temp48b);
2288
 
  for (i = 0; i < temp48blen; i++) {
2289
 
    temp48b[i] = -temp48b[i];
2290
 
  }
2291
 
  bcdelen = fast_expansion_sum_zeroelim(temp48alen, temp48a,
2292
 
                                        temp48blen, temp48b, bcde);
2293
 
  xlen = scale_expansion_zeroelim(bcdelen, bcde, pa[0], temp192);
2294
 
  xlen = scale_expansion_zeroelim(xlen, temp192, pa[0], det384x);
2295
 
  ylen = scale_expansion_zeroelim(bcdelen, bcde, pa[1], temp192);
2296
 
  ylen = scale_expansion_zeroelim(ylen, temp192, pa[1], det384y);
2297
 
  zlen = scale_expansion_zeroelim(bcdelen, bcde, pa[2], temp192);
2298
 
  zlen = scale_expansion_zeroelim(zlen, temp192, pa[2], det384z);
2299
 
  xylen = fast_expansion_sum_zeroelim(xlen, det384x, ylen, det384y, detxy);
2300
 
  alen = fast_expansion_sum_zeroelim(xylen, detxy, zlen, det384z, adet);
2301
 
 
2302
 
  temp48alen = fast_expansion_sum_zeroelim(dealen, dea, cdalen, cda, temp48a);
2303
 
  temp48blen = fast_expansion_sum_zeroelim(eaclen, eac, cdelen, cde, temp48b);
2304
 
  for (i = 0; i < temp48blen; i++) {
2305
 
    temp48b[i] = -temp48b[i];
2306
 
  }
2307
 
  cdealen = fast_expansion_sum_zeroelim(temp48alen, temp48a,
2308
 
                                        temp48blen, temp48b, cdea);
2309
 
  xlen = scale_expansion_zeroelim(cdealen, cdea, pb[0], temp192);
2310
 
  xlen = scale_expansion_zeroelim(xlen, temp192, pb[0], det384x);
2311
 
  ylen = scale_expansion_zeroelim(cdealen, cdea, pb[1], temp192);
2312
 
  ylen = scale_expansion_zeroelim(ylen, temp192, pb[1], det384y);
2313
 
  zlen = scale_expansion_zeroelim(cdealen, cdea, pb[2], temp192);
2314
 
  zlen = scale_expansion_zeroelim(zlen, temp192, pb[2], det384z);
2315
 
  xylen = fast_expansion_sum_zeroelim(xlen, det384x, ylen, det384y, detxy);
2316
 
  blen = fast_expansion_sum_zeroelim(xylen, detxy, zlen, det384z, bdet);
2317
 
 
2318
 
  temp48alen = fast_expansion_sum_zeroelim(eablen, eab, deblen, deb, temp48a);
2319
 
  temp48blen = fast_expansion_sum_zeroelim(abdlen, abd, dealen, dea, temp48b);
2320
 
  for (i = 0; i < temp48blen; i++) {
2321
 
    temp48b[i] = -temp48b[i];
2322
 
  }
2323
 
  deablen = fast_expansion_sum_zeroelim(temp48alen, temp48a,
2324
 
                                        temp48blen, temp48b, deab);
2325
 
  xlen = scale_expansion_zeroelim(deablen, deab, pc[0], temp192);
2326
 
  xlen = scale_expansion_zeroelim(xlen, temp192, pc[0], det384x);
2327
 
  ylen = scale_expansion_zeroelim(deablen, deab, pc[1], temp192);
2328
 
  ylen = scale_expansion_zeroelim(ylen, temp192, pc[1], det384y);
2329
 
  zlen = scale_expansion_zeroelim(deablen, deab, pc[2], temp192);
2330
 
  zlen = scale_expansion_zeroelim(zlen, temp192, pc[2], det384z);
2331
 
  xylen = fast_expansion_sum_zeroelim(xlen, det384x, ylen, det384y, detxy);
2332
 
  clen = fast_expansion_sum_zeroelim(xylen, detxy, zlen, det384z, cdet);
2333
 
 
2334
 
  temp48alen = fast_expansion_sum_zeroelim(abclen, abc, eaclen, eac, temp48a);
2335
 
  temp48blen = fast_expansion_sum_zeroelim(bcelen, bce, eablen, eab, temp48b);
2336
 
  for (i = 0; i < temp48blen; i++) {
2337
 
    temp48b[i] = -temp48b[i];
2338
 
  }
2339
 
  eabclen = fast_expansion_sum_zeroelim(temp48alen, temp48a,
2340
 
                                        temp48blen, temp48b, eabc);
2341
 
  xlen = scale_expansion_zeroelim(eabclen, eabc, pd[0], temp192);
2342
 
  xlen = scale_expansion_zeroelim(xlen, temp192, pd[0], det384x);
2343
 
  ylen = scale_expansion_zeroelim(eabclen, eabc, pd[1], temp192);
2344
 
  ylen = scale_expansion_zeroelim(ylen, temp192, pd[1], det384y);
2345
 
  zlen = scale_expansion_zeroelim(eabclen, eabc, pd[2], temp192);
2346
 
  zlen = scale_expansion_zeroelim(zlen, temp192, pd[2], det384z);
2347
 
  xylen = fast_expansion_sum_zeroelim(xlen, det384x, ylen, det384y, detxy);
2348
 
  dlen = fast_expansion_sum_zeroelim(xylen, detxy, zlen, det384z, ddet);
2349
 
 
2350
 
  temp48alen = fast_expansion_sum_zeroelim(bcdlen, bcd, abdlen, abd, temp48a);
2351
 
  temp48blen = fast_expansion_sum_zeroelim(cdalen, cda, abclen, abc, temp48b);
2352
 
  for (i = 0; i < temp48blen; i++) {
2353
 
    temp48b[i] = -temp48b[i];
2354
 
  }
2355
 
  abcdlen = fast_expansion_sum_zeroelim(temp48alen, temp48a,
2356
 
                                        temp48blen, temp48b, abcd);
2357
 
  xlen = scale_expansion_zeroelim(abcdlen, abcd, pe[0], temp192);
2358
 
  xlen = scale_expansion_zeroelim(xlen, temp192, pe[0], det384x);
2359
 
  ylen = scale_expansion_zeroelim(abcdlen, abcd, pe[1], temp192);
2360
 
  ylen = scale_expansion_zeroelim(ylen, temp192, pe[1], det384y);
2361
 
  zlen = scale_expansion_zeroelim(abcdlen, abcd, pe[2], temp192);
2362
 
  zlen = scale_expansion_zeroelim(zlen, temp192, pe[2], det384z);
2363
 
  xylen = fast_expansion_sum_zeroelim(xlen, det384x, ylen, det384y, detxy);
2364
 
  elen = fast_expansion_sum_zeroelim(xylen, detxy, zlen, det384z, edet);
2365
 
 
2366
 
  ablen = fast_expansion_sum_zeroelim(alen, adet, blen, bdet, abdet);
2367
 
  cdlen = fast_expansion_sum_zeroelim(clen, cdet, dlen, ddet, cddet);
2368
 
  cdelen = fast_expansion_sum_zeroelim(cdlen, cddet, elen, edet, cdedet);
2369
 
  deterlen = fast_expansion_sum_zeroelim(ablen, abdet, cdelen, cdedet, deter);
2370
 
 
2371
 
  return deter[deterlen - 1];
2372
 
}
2373
 
 
2374
 
static REAL insphereadapt(REAL *pa, REAL *pb, REAL *pc, REAL *pd, REAL *pe, 
2375
 
                          REAL permanent)
2376
 
{
2377
 
  INEXACT REAL aex, bex, cex, dex, aey, bey, cey, dey, aez, bez, cez, dez;
2378
 
  REAL det, errbound;
2379
 
 
2380
 
  INEXACT REAL aexbey1, bexaey1, bexcey1, cexbey1;
2381
 
  INEXACT REAL cexdey1, dexcey1, dexaey1, aexdey1;
2382
 
  INEXACT REAL aexcey1, cexaey1, bexdey1, dexbey1;
2383
 
  REAL aexbey0, bexaey0, bexcey0, cexbey0;
2384
 
  REAL cexdey0, dexcey0, dexaey0, aexdey0;
2385
 
  REAL aexcey0, cexaey0, bexdey0, dexbey0;
2386
 
  REAL ab[4], bc[4], cd[4], da[4], ac[4], bd[4];
2387
 
  INEXACT REAL ab3, bc3, cd3, da3, ac3, bd3;
2388
 
  REAL abeps, bceps, cdeps, daeps, aceps, bdeps;
2389
 
  REAL temp8a[8], temp8b[8], temp8c[8], temp16[16], temp24[24], temp48[48];
2390
 
  int temp8alen, temp8blen, temp8clen, temp16len, temp24len, temp48len;
2391
 
  REAL xdet[96], ydet[96], zdet[96], xydet[192];
2392
 
  int xlen, ylen, zlen, xylen;
2393
 
  REAL adet[288], bdet[288], cdet[288], ddet[288];
2394
 
  int alen, blen, clen, dlen;
2395
 
  REAL abdet[576], cddet[576];
2396
 
  int ablen, cdlen;
2397
 
  REAL fin1[1152];
2398
 
  int finlength;
2399
 
 
2400
 
  REAL aextail, bextail, cextail, dextail;
2401
 
  REAL aeytail, beytail, ceytail, deytail;
2402
 
  REAL aeztail, beztail, ceztail, deztail;
2403
 
 
2404
 
  INEXACT REAL bvirt;
2405
 
  REAL avirt, bround, around;
2406
 
  INEXACT REAL c;
2407
 
  INEXACT REAL abig;
2408
 
  REAL ahi, alo, bhi, blo;
2409
 
  REAL err1, err2, err3;
2410
 
  INEXACT REAL _i, _j;
2411
 
  REAL _0;
2412
 
 
2413
 
  aex = (REAL) (pa[0] - pe[0]);
2414
 
  bex = (REAL) (pb[0] - pe[0]);
2415
 
  cex = (REAL) (pc[0] - pe[0]);
2416
 
  dex = (REAL) (pd[0] - pe[0]);
2417
 
  aey = (REAL) (pa[1] - pe[1]);
2418
 
  bey = (REAL) (pb[1] - pe[1]);
2419
 
  cey = (REAL) (pc[1] - pe[1]);
2420
 
  dey = (REAL) (pd[1] - pe[1]);
2421
 
  aez = (REAL) (pa[2] - pe[2]);
2422
 
  bez = (REAL) (pb[2] - pe[2]);
2423
 
  cez = (REAL) (pc[2] - pe[2]);
2424
 
  dez = (REAL) (pd[2] - pe[2]);
2425
 
 
2426
 
  Two_Product(aex, bey, aexbey1, aexbey0);
2427
 
  Two_Product(bex, aey, bexaey1, bexaey0);
2428
 
  Two_Two_Diff(aexbey1, aexbey0, bexaey1, bexaey0, ab3, ab[2], ab[1], ab[0]);
2429
 
  ab[3] = ab3;
2430
 
 
2431
 
  Two_Product(bex, cey, bexcey1, bexcey0);
2432
 
  Two_Product(cex, bey, cexbey1, cexbey0);
2433
 
  Two_Two_Diff(bexcey1, bexcey0, cexbey1, cexbey0, bc3, bc[2], bc[1], bc[0]);
2434
 
  bc[3] = bc3;
2435
 
 
2436
 
  Two_Product(cex, dey, cexdey1, cexdey0);
2437
 
  Two_Product(dex, cey, dexcey1, dexcey0);
2438
 
  Two_Two_Diff(cexdey1, cexdey0, dexcey1, dexcey0, cd3, cd[2], cd[1], cd[0]);
2439
 
  cd[3] = cd3;
2440
 
 
2441
 
  Two_Product(dex, aey, dexaey1, dexaey0);
2442
 
  Two_Product(aex, dey, aexdey1, aexdey0);
2443
 
  Two_Two_Diff(dexaey1, dexaey0, aexdey1, aexdey0, da3, da[2], da[1], da[0]);
2444
 
  da[3] = da3;
2445
 
 
2446
 
  Two_Product(aex, cey, aexcey1, aexcey0);
2447
 
  Two_Product(cex, aey, cexaey1, cexaey0);
2448
 
  Two_Two_Diff(aexcey1, aexcey0, cexaey1, cexaey0, ac3, ac[2], ac[1], ac[0]);
2449
 
  ac[3] = ac3;
2450
 
 
2451
 
  Two_Product(bex, dey, bexdey1, bexdey0);
2452
 
  Two_Product(dex, bey, dexbey1, dexbey0);
2453
 
  Two_Two_Diff(bexdey1, bexdey0, dexbey1, dexbey0, bd3, bd[2], bd[1], bd[0]);
2454
 
  bd[3] = bd3;
2455
 
 
2456
 
  temp8alen = scale_expansion_zeroelim(4, cd, bez, temp8a);
2457
 
  temp8blen = scale_expansion_zeroelim(4, bd, -cez, temp8b);
2458
 
  temp8clen = scale_expansion_zeroelim(4, bc, dez, temp8c);
2459
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a,
2460
 
                                          temp8blen, temp8b, temp16);
2461
 
  temp24len = fast_expansion_sum_zeroelim(temp8clen, temp8c,
2462
 
                                          temp16len, temp16, temp24);
2463
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, aex, temp48);
2464
 
  xlen = scale_expansion_zeroelim(temp48len, temp48, -aex, xdet);
2465
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, aey, temp48);
2466
 
  ylen = scale_expansion_zeroelim(temp48len, temp48, -aey, ydet);
2467
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, aez, temp48);
2468
 
  zlen = scale_expansion_zeroelim(temp48len, temp48, -aez, zdet);
2469
 
  xylen = fast_expansion_sum_zeroelim(xlen, xdet, ylen, ydet, xydet);
2470
 
  alen = fast_expansion_sum_zeroelim(xylen, xydet, zlen, zdet, adet);
2471
 
 
2472
 
  temp8alen = scale_expansion_zeroelim(4, da, cez, temp8a);
2473
 
  temp8blen = scale_expansion_zeroelim(4, ac, dez, temp8b);
2474
 
  temp8clen = scale_expansion_zeroelim(4, cd, aez, temp8c);
2475
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a,
2476
 
                                          temp8blen, temp8b, temp16);
2477
 
  temp24len = fast_expansion_sum_zeroelim(temp8clen, temp8c,
2478
 
                                          temp16len, temp16, temp24);
2479
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, bex, temp48);
2480
 
  xlen = scale_expansion_zeroelim(temp48len, temp48, bex, xdet);
2481
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, bey, temp48);
2482
 
  ylen = scale_expansion_zeroelim(temp48len, temp48, bey, ydet);
2483
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, bez, temp48);
2484
 
  zlen = scale_expansion_zeroelim(temp48len, temp48, bez, zdet);
2485
 
  xylen = fast_expansion_sum_zeroelim(xlen, xdet, ylen, ydet, xydet);
2486
 
  blen = fast_expansion_sum_zeroelim(xylen, xydet, zlen, zdet, bdet);
2487
 
 
2488
 
  temp8alen = scale_expansion_zeroelim(4, ab, dez, temp8a);
2489
 
  temp8blen = scale_expansion_zeroelim(4, bd, aez, temp8b);
2490
 
  temp8clen = scale_expansion_zeroelim(4, da, bez, temp8c);
2491
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a,
2492
 
                                          temp8blen, temp8b, temp16);
2493
 
  temp24len = fast_expansion_sum_zeroelim(temp8clen, temp8c,
2494
 
                                          temp16len, temp16, temp24);
2495
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, cex, temp48);
2496
 
  xlen = scale_expansion_zeroelim(temp48len, temp48, -cex, xdet);
2497
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, cey, temp48);
2498
 
  ylen = scale_expansion_zeroelim(temp48len, temp48, -cey, ydet);
2499
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, cez, temp48);
2500
 
  zlen = scale_expansion_zeroelim(temp48len, temp48, -cez, zdet);
2501
 
  xylen = fast_expansion_sum_zeroelim(xlen, xdet, ylen, ydet, xydet);
2502
 
  clen = fast_expansion_sum_zeroelim(xylen, xydet, zlen, zdet, cdet);
2503
 
 
2504
 
  temp8alen = scale_expansion_zeroelim(4, bc, aez, temp8a);
2505
 
  temp8blen = scale_expansion_zeroelim(4, ac, -bez, temp8b);
2506
 
  temp8clen = scale_expansion_zeroelim(4, ab, cez, temp8c);
2507
 
  temp16len = fast_expansion_sum_zeroelim(temp8alen, temp8a,
2508
 
                                          temp8blen, temp8b, temp16);
2509
 
  temp24len = fast_expansion_sum_zeroelim(temp8clen, temp8c,
2510
 
                                          temp16len, temp16, temp24);
2511
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, dex, temp48);
2512
 
  xlen = scale_expansion_zeroelim(temp48len, temp48, dex, xdet);
2513
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, dey, temp48);
2514
 
  ylen = scale_expansion_zeroelim(temp48len, temp48, dey, ydet);
2515
 
  temp48len = scale_expansion_zeroelim(temp24len, temp24, dez, temp48);
2516
 
  zlen = scale_expansion_zeroelim(temp48len, temp48, dez, zdet);
2517
 
  xylen = fast_expansion_sum_zeroelim(xlen, xdet, ylen, ydet, xydet);
2518
 
  dlen = fast_expansion_sum_zeroelim(xylen, xydet, zlen, zdet, ddet);
2519
 
 
2520
 
  ablen = fast_expansion_sum_zeroelim(alen, adet, blen, bdet, abdet);
2521
 
  cdlen = fast_expansion_sum_zeroelim(clen, cdet, dlen, ddet, cddet);
2522
 
  finlength = fast_expansion_sum_zeroelim(ablen, abdet, cdlen, cddet, fin1);
2523
 
 
2524
 
  det = estimate(finlength, fin1);
2525
 
  errbound = isperrboundB * permanent;
2526
 
  if ((det >= errbound) || (-det >= errbound)) {
2527
 
    return det;
2528
 
  }
2529
 
 
2530
 
  Two_Diff_Tail(pa[0], pe[0], aex, aextail);
2531
 
  Two_Diff_Tail(pa[1], pe[1], aey, aeytail);
2532
 
  Two_Diff_Tail(pa[2], pe[2], aez, aeztail);
2533
 
  Two_Diff_Tail(pb[0], pe[0], bex, bextail);
2534
 
  Two_Diff_Tail(pb[1], pe[1], bey, beytail);
2535
 
  Two_Diff_Tail(pb[2], pe[2], bez, beztail);
2536
 
  Two_Diff_Tail(pc[0], pe[0], cex, cextail);
2537
 
  Two_Diff_Tail(pc[1], pe[1], cey, ceytail);
2538
 
  Two_Diff_Tail(pc[2], pe[2], cez, ceztail);
2539
 
  Two_Diff_Tail(pd[0], pe[0], dex, dextail);
2540
 
  Two_Diff_Tail(pd[1], pe[1], dey, deytail);
2541
 
  Two_Diff_Tail(pd[2], pe[2], dez, deztail);
2542
 
  if ((aextail == 0.0) && (aeytail == 0.0) && (aeztail == 0.0)
2543
 
      && (bextail == 0.0) && (beytail == 0.0) && (beztail == 0.0)
2544
 
      && (cextail == 0.0) && (ceytail == 0.0) && (ceztail == 0.0)
2545
 
      && (dextail == 0.0) && (deytail == 0.0) && (deztail == 0.0)) {
2546
 
    return det;
2547
 
  }
2548
 
 
2549
 
  errbound = isperrboundC * permanent + resulterrbound * Absolute(det);
2550
 
  abeps = (aex * beytail + bey * aextail)
2551
 
        - (aey * bextail + bex * aeytail);
2552
 
  bceps = (bex * ceytail + cey * bextail)
2553
 
        - (bey * cextail + cex * beytail);
2554
 
  cdeps = (cex * deytail + dey * cextail)
2555
 
        - (cey * dextail + dex * ceytail);
2556
 
  daeps = (dex * aeytail + aey * dextail)
2557
 
        - (dey * aextail + aex * deytail);
2558
 
  aceps = (aex * ceytail + cey * aextail)
2559
 
        - (aey * cextail + cex * aeytail);
2560
 
  bdeps = (bex * deytail + dey * bextail)
2561
 
        - (bey * dextail + dex * beytail);
2562
 
  det += (((bex * bex + bey * bey + bez * bez)
2563
 
           * ((cez * daeps + dez * aceps + aez * cdeps)
2564
 
              + (ceztail * da3 + deztail * ac3 + aeztail * cd3))
2565
 
           + (dex * dex + dey * dey + dez * dez)
2566
 
           * ((aez * bceps - bez * aceps + cez * abeps)
2567
 
              + (aeztail * bc3 - beztail * ac3 + ceztail * ab3)))
2568
 
          - ((aex * aex + aey * aey + aez * aez)
2569
 
           * ((bez * cdeps - cez * bdeps + dez * bceps)
2570
 
              + (beztail * cd3 - ceztail * bd3 + deztail * bc3))
2571
 
           + (cex * cex + cey * cey + cez * cez)
2572
 
           * ((dez * abeps + aez * bdeps + bez * daeps)
2573
 
              + (deztail * ab3 + aeztail * bd3 + beztail * da3))))
2574
 
       + 2.0 * (((bex * bextail + bey * beytail + bez * beztail)
2575
 
                 * (cez * da3 + dez * ac3 + aez * cd3)
2576
 
                 + (dex * dextail + dey * deytail + dez * deztail)
2577
 
                 * (aez * bc3 - bez * ac3 + cez * ab3))
2578
 
                - ((aex * aextail + aey * aeytail + aez * aeztail)
2579
 
                 * (bez * cd3 - cez * bd3 + dez * bc3)
2580
 
                 + (cex * cextail + cey * ceytail + cez * ceztail)
2581
 
                 * (dez * ab3 + aez * bd3 + bez * da3)));
2582
 
  if ((det >= errbound) || (-det >= errbound)) {
2583
 
    return det;
2584
 
  }
2585
 
 
2586
 
  return insphereexact(pa, pb, pc, pd, pe);
2587
 
}
2588
 
 
2589
 
REAL insphere(REAL *pa, REAL *pb, REAL *pc, REAL *pd, REAL *pe)
2590
 
{
2591
 
  REAL aex, bex, cex, dex;
2592
 
  REAL aey, bey, cey, dey;
2593
 
  REAL aez, bez, cez, dez;
2594
 
  REAL aexbey, bexaey, bexcey, cexbey, cexdey, dexcey, dexaey, aexdey;
2595
 
  REAL aexcey, cexaey, bexdey, dexbey;
2596
 
  REAL alift, blift, clift, dlift;
2597
 
  REAL ab, bc, cd, da, ac, bd;
2598
 
  REAL abc, bcd, cda, dab;
2599
 
  REAL aezplus, bezplus, cezplus, dezplus;
2600
 
  REAL aexbeyplus, bexaeyplus, bexceyplus, cexbeyplus;
2601
 
  REAL cexdeyplus, dexceyplus, dexaeyplus, aexdeyplus;
2602
 
  REAL aexceyplus, cexaeyplus, bexdeyplus, dexbeyplus;
2603
 
  REAL det;
2604
 
  REAL permanent, errbound;
2605
 
  REAL ins;
2606
 
 
2607
 
  FPU_ROUND_DOUBLE;
2608
 
 
2609
 
  aex = pa[0] - pe[0];
2610
 
  bex = pb[0] - pe[0];
2611
 
  cex = pc[0] - pe[0];
2612
 
  dex = pd[0] - pe[0];
2613
 
  aey = pa[1] - pe[1];
2614
 
  bey = pb[1] - pe[1];
2615
 
  cey = pc[1] - pe[1];
2616
 
  dey = pd[1] - pe[1];
2617
 
  aez = pa[2] - pe[2];
2618
 
  bez = pb[2] - pe[2];
2619
 
  cez = pc[2] - pe[2];
2620
 
  dez = pd[2] - pe[2];
2621
 
 
2622
 
  aexbey = aex * bey;
2623
 
  bexaey = bex * aey;
2624
 
  ab = aexbey - bexaey;
2625
 
  bexcey = bex * cey;
2626
 
  cexbey = cex * bey;
2627
 
  bc = bexcey - cexbey;
2628
 
  cexdey = cex * dey;
2629
 
  dexcey = dex * cey;
2630
 
  cd = cexdey - dexcey;
2631
 
  dexaey = dex * aey;
2632
 
  aexdey = aex * dey;
2633
 
  da = dexaey - aexdey;
2634
 
 
2635
 
  aexcey = aex * cey;
2636
 
  cexaey = cex * aey;
2637
 
  ac = aexcey - cexaey;
2638
 
  bexdey = bex * dey;
2639
 
  dexbey = dex * bey;
2640
 
  bd = bexdey - dexbey;
2641
 
 
2642
 
  abc = aez * bc - bez * ac + cez * ab;
2643
 
  bcd = bez * cd - cez * bd + dez * bc;
2644
 
  cda = cez * da + dez * ac + aez * cd;
2645
 
  dab = dez * ab + aez * bd + bez * da;
2646
 
 
2647
 
  alift = aex * aex + aey * aey + aez * aez;
2648
 
  blift = bex * bex + bey * bey + bez * bez;
2649
 
  clift = cex * cex + cey * cey + cez * cez;
2650
 
  dlift = dex * dex + dey * dey + dez * dez;
2651
 
 
2652
 
  det = (dlift * abc - clift * dab) + (blift * cda - alift * bcd);
2653
 
 
2654
 
  aezplus = Absolute(aez);
2655
 
  bezplus = Absolute(bez);
2656
 
  cezplus = Absolute(cez);
2657
 
  dezplus = Absolute(dez);
2658
 
  aexbeyplus = Absolute(aexbey);
2659
 
  bexaeyplus = Absolute(bexaey);
2660
 
  bexceyplus = Absolute(bexcey);
2661
 
  cexbeyplus = Absolute(cexbey);
2662
 
  cexdeyplus = Absolute(cexdey);
2663
 
  dexceyplus = Absolute(dexcey);
2664
 
  dexaeyplus = Absolute(dexaey);
2665
 
  aexdeyplus = Absolute(aexdey);
2666
 
  aexceyplus = Absolute(aexcey);
2667
 
  cexaeyplus = Absolute(cexaey);
2668
 
  bexdeyplus = Absolute(bexdey);
2669
 
  dexbeyplus = Absolute(dexbey);
2670
 
  permanent = ((cexdeyplus + dexceyplus) * bezplus
2671
 
               + (dexbeyplus + bexdeyplus) * cezplus
2672
 
               + (bexceyplus + cexbeyplus) * dezplus)
2673
 
            * alift
2674
 
            + ((dexaeyplus + aexdeyplus) * cezplus
2675
 
               + (aexceyplus + cexaeyplus) * dezplus
2676
 
               + (cexdeyplus + dexceyplus) * aezplus)
2677
 
            * blift
2678
 
            + ((aexbeyplus + bexaeyplus) * dezplus
2679
 
               + (bexdeyplus + dexbeyplus) * aezplus
2680
 
               + (dexaeyplus + aexdeyplus) * bezplus)
2681
 
            * clift
2682
 
            + ((bexceyplus + cexbeyplus) * aezplus
2683
 
               + (cexaeyplus + aexceyplus) * bezplus
2684
 
               + (aexbeyplus + bexaeyplus) * cezplus)
2685
 
            * dlift;
2686
 
  errbound = isperrboundA * permanent;
2687
 
  if ((det > errbound) || (-det > errbound)) {
2688
 
    FPU_RESTORE;
2689
 
    return det;
2690
 
  }
2691
 
 
2692
 
  ins = insphereadapt(pa, pb, pc, pd, pe, permanent);
2693
 
  FPU_RESTORE;
2694
 
  return ins;
2695
 
}
2696
 
 
2697
 
}