Skip to content

AFNI/NIfTI Server

Sections
Personal tools
You are here: Home » AFNI » Documentation

Doxygen Source Code Documentation


Main Page   Alphabetical List   Data Structures   File List   Data Fields   Globals   Search  

user.c

Go to the documentation of this file.
00001 /*<html><pre>  -<a                             href="qh-user.htm"
00002   >-------------------------------</a><a name="TOP">-</a>
00003 
00004    user.c 
00005    user redefinable functions
00006 
00007    see README.txt  see COPYING.txt for copyright information.
00008 
00009    see qhull.h for data structures, macros, and user-callable functions.
00010 
00011    see user_eg.c, unix.c, and qhull_interface.cpp for examples.
00012 
00013    see user.h for user-definable constants
00014 
00015       use qh_NOmem in mem.h to turn off memory management
00016       use qh_NOmerge in user.h to turn off facet merging
00017       set qh_KEEPstatistics in user.h to 0 to turn off statistics
00018 
00019    This is unsupported software.  You're welcome to make changes,
00020    but you're on your own if something goes wrong.  Use 'Tc' to
00021    check frequently.  Usually qhull will report an error if 
00022    a data structure becomes inconsistent.  If so, it also reports
00023    the last point added to the hull, e.g., 102.  You can then trace
00024    the execution of qhull with "T4P102".  
00025 
00026    Please report any errors that you fix to qhull@geom.umn.edu
00027 
00028    call_qhull is a template for calling qhull from within your application
00029 
00030    if you recompile and load this module, then user.o will not be loaded
00031    from qhull.a
00032 
00033    you can add additional quick allocation sizes in qh_user_memsizes
00034 
00035    if the other functions here are redefined to not use qh_print...,
00036    then io.o will not be loaded from qhull.a.  See user_eg.c for an
00037    example.  We recommend keeping io.o for the extra debugging 
00038    information it supplies.
00039 */
00040 
00041 #include "qhull_a.h" 
00042 
00043 /*-<a                             href="qh-user.htm#TOC"
00044   >-------------------------------</a><a name="call_qhull">-</a>
00045 
00046   qh_call_qhull( void )
00047     template for calling qhull from inside your program
00048     remove #if 0, #endif to compile
00049     define: char qh_version[]= "...";
00050 
00051   returns: 
00052     exit code (see qh_ERR... in qhull.h)
00053     all memory freed
00054 
00055   notes:
00056     This can be called any number of times.  
00057 
00058   see:
00059     qh_call_qhull_once()
00060     
00061 */
00062 #if 0
00063 char qh_version[] = "user_eg 98/7/25";  /* used for error messages */
00064 
00065 {
00066   int dim;                  /* dimension of points */
00067   int numpoints;            /* number of points */
00068   coordT *points;           /* array of coordinates for each point */
00069   boolT ismalloc;           /* True if qhull should free points in qh_freeqhull() or reallocation */
00070   char flags[]= "qhull Tv"; /* option flags for qhull, see qh_opt.htm */
00071   FILE *outfile= stdout;    /* output from qh_produce_output()
00072                                use NULL to skip qh_produce_output() */
00073   FILE *errfile= stderr;    /* error messages from qhull code */
00074   int exitcode;             /* 0 if no error from qhull */
00075   facetT *facet;            /* set by FORALLfacets */
00076   int curlong, totlong;     /* memory remaining after qh_memfreeshort */
00077 
00078   /* initialize dim, numpoints, points[], ismalloc here */
00079   exitcode= qh_new_qhull (dim, numpoints, points, ismalloc,
00080                       flags, outfile, errfile); 
00081   if (!exitcode) {                  /* if no error */
00082     /* 'qh facet_list' contains the convex hull */
00083     FORALLfacets {
00084        /* ... your code ... */
00085     }
00086   }
00087   qh_freeqhull(!qh_ALL);
00088   qh_memfreeshort (&curlong, &totlong);
00089   if (curlong || totlong) 
00090     fprintf (errfile, "qhull internal warning (main): did not free %d bytes of long memory (%d pieces)\n", totlong, curlong);
00091 }
00092 #endif
00093 
00094 /*-<a                             href="qh-user.htm#TOC"
00095   >-------------------------------</a><a name="new_qhull">-</a>
00096 
00097   qh_new_qhull( dim, numpoints, points, ismalloc, qhull_cmd, outfile, errfile )
00098     build new qhull data structure and return exitcode (0 if no errors)
00099 
00100   notes:
00101     do not modify points until finished with results.
00102       The qhull data structure contains pointers into the points array.
00103     do not call qhull functions before qh_new_qhull().
00104       The qhull data structure is not initialized until qh_new_qhull().
00105 
00106     outfile may be null
00107     qhull_cmd must start with "qhull "
00108     projects points to a new point array for Delaunay triangulations ('d' and 'v')
00109     transforms points into a new point array for halfspace intersection ('H')
00110        
00111 
00112   To allow multiple, concurrent calls to qhull() 
00113     - set qh_QHpointer in user.h
00114     - use qh_save_qhull and qh_restore_qhull to swap the global data structure between calls.
00115     - use qh_freeqhull(qh_ALL) to free intermediate convex hulls
00116 
00117   see:
00118     user_eg.c for an example
00119 */
00120 int qh_new_qhull (int dim, int numpoints, coordT *points, boolT ismalloc, 
00121                 char *qhull_cmd, FILE *outfile, FILE *errfile) {
00122   int exitcode, hulldim;
00123   boolT new_ismalloc;
00124   static boolT firstcall = True;
00125   coordT *new_points;
00126 
00127   if (firstcall) {
00128     qh_meminit (errfile);
00129     firstcall= False;
00130   }
00131   if (strncmp (qhull_cmd,"qhull ", 6)) {
00132     fprintf (errfile, "qh_new_qhull: start qhull_cmd argument with \"qhull \"\n");
00133     exit(1);
00134   }
00135   qh_initqhull_start (NULL, outfile, errfile);
00136   trace1(( qh ferr, "qh_new_qhull: build new Qhull for %d %d-d points with %s\n", numpoints, dim, qhull_cmd));
00137   exitcode = setjmp (qh errexit);
00138   if (!exitcode)
00139   {
00140     qh NOerrexit = False;
00141     qh_initflags (qhull_cmd);
00142     if (qh DELAUNAY)
00143       qh PROJECTdelaunay= True;
00144     if (qh HALFspace) {
00145       /* points is an array of halfspaces, 
00146          the last coordinate of each halfspace is its offset */
00147       hulldim= dim-1;
00148       qh_setfeasible (hulldim); 
00149       new_points= qh_sethalfspace_all (dim, numpoints, points, qh feasible_point);
00150       new_ismalloc= True;
00151       if (ismalloc)
00152         free (points);
00153     }else {
00154       hulldim= dim;
00155       new_points= points;
00156       new_ismalloc= ismalloc;
00157     }
00158     qh_init_B (new_points, numpoints, hulldim, new_ismalloc);
00159     qh_qhull();
00160     qh_check_output();
00161     if (outfile)
00162       qh_produce_output(); 
00163     if (qh VERIFYoutput && !qh STOPpoint && !qh STOPcone)
00164       qh_check_points();
00165   }
00166   qh NOerrexit = True;
00167   return exitcode;
00168 } /* new_qhull */
00169 
00170 /*-<a                             href="qh-user.htm#TOC"
00171   >-------------------------------</a><a name="errexit">-</a>
00172   
00173   qh_errexit( exitcode, facet, ridge )
00174     report and exit from an error
00175     report facet and ridge if non-NULL
00176     reports useful information such as last point processed
00177     set qh.FORCEoutput to print neighborhood of facet
00178 
00179   see: 
00180     qh_errexit2() in qhull.c for printing 2 facets
00181 
00182   design:
00183     check for error within error processing
00184     compute qh.hulltime
00185     print facet and ridge (if any)
00186     report commandString, options, qh.furthest_id
00187     print summary and statistics (including precision statistics)
00188     if qh_ERRsingular
00189       print help text for singular data set
00190     exit program via long jump (if defined) or exit()      
00191 */
00192 void qh_errexit(int exitcode, facetT *facet, ridgeT *ridge) {
00193 
00194   if (qh ERREXITcalled) {
00195     fprintf (qh ferr, "\nqhull error while processing previous error.  Exit program\n");
00196     exit(1);
00197   }
00198   qh ERREXITcalled= True;
00199   if (!qh QHULLfinished)
00200     qh hulltime= qh_CPUclock - qh hulltime;
00201   qh_errprint("ERRONEOUS", facet, NULL, ridge, NULL);
00202   fprintf (qh ferr, "\nWhile executing: %s | %s\n", qh rbox_command, qh qhull_command);
00203   fprintf(qh ferr, "Options selected for Qhull %s:\n%s\n", qh_version, qh qhull_options);
00204   if (qh furthest_id >= 0) {
00205     fprintf(qh ferr, "Last point added to hull was p%d.", qh furthest_id);
00206     if (zzval_(Ztotmerge))
00207       fprintf(qh ferr, "  Last merge was #%d.", zzval_(Ztotmerge));
00208     if (qh QHULLfinished)
00209       fprintf(qh ferr, "\nQhull has finished constructing the hull.");
00210     else if (qh POSTmerging)
00211       fprintf(qh ferr, "\nQhull has started post-merging.");
00212     fprintf (qh ferr, "\n");
00213   }
00214   if (qh FORCEoutput && (qh QHULLfinished || (!facet && !ridge)))
00215     qh_produce_output();
00216   else {
00217     if (exitcode != qh_ERRsingular && zzval_(Zsetplane) > qh hull_dim+1) {
00218       fprintf (qh ferr, "\nAt error exit:\n");
00219       qh_printsummary (qh ferr);
00220       if (qh PRINTstatistics) {
00221         qh_collectstatistics();
00222         qh_printstatistics(qh ferr, "at error exit");
00223         qh_memstatistics (qh ferr);
00224       }
00225     }
00226     if (qh PRINTprecision)
00227       qh_printstats (qh ferr, qhstat precision, NULL);
00228   }
00229   if (!exitcode)
00230     exitcode= qh_ERRqhull;
00231   else if (exitcode == qh_ERRsingular)
00232     qh_printhelp_singular(qh ferr);
00233   else if (exitcode == qh_ERRprec && !qh PREmerge)
00234     qh_printhelp_degenerate (qh ferr);
00235   if (qh NOerrexit) {
00236     fprintf (qh ferr, "qhull error while ending program.  Exit program\n");
00237     exit(1);
00238   }
00239   qh NOerrexit= True;
00240   longjmp(qh errexit, exitcode);
00241 } /* errexit */
00242 
00243 
00244 /*-<a                             href="qh-user.htm#TOC"
00245   >-------------------------------</a><a name="errprint">-</a>
00246   
00247   qh_errprint( fp, string, atfacet, otherfacet, atridge, atvertex )
00248     prints out the information of facets and ridges to fp
00249     also prints neighbors and geomview output
00250     
00251   notes:
00252     except for string, any parameter may be NULL
00253 */
00254 void qh_errprint(char *string, facetT *atfacet, facetT *otherfacet, ridgeT *atridge, vertexT *atvertex) {
00255   int i;
00256 
00257   if (atfacet) {
00258     fprintf(qh ferr, "%s FACET:\n", string);
00259     qh_printfacet(qh ferr, atfacet);
00260   }
00261   if (otherfacet) {
00262     fprintf(qh ferr, "%s OTHER FACET:\n", string);
00263     qh_printfacet(qh ferr, otherfacet);
00264   }
00265   if (atridge) {
00266     fprintf(qh ferr, "%s RIDGE:\n", string);
00267     qh_printridge(qh ferr, atridge);
00268     if (atridge->top && atridge->top != atfacet && atridge->top != otherfacet)
00269       qh_printfacet(qh ferr, atridge->top);
00270     if (atridge->bottom
00271         && atridge->bottom != atfacet && atridge->bottom != otherfacet)
00272       qh_printfacet(qh ferr, atridge->bottom);
00273     if (!atfacet)
00274       atfacet= atridge->top;
00275     if (!otherfacet)
00276       otherfacet= otherfacet_(atridge, atfacet);
00277   }
00278   if (atvertex) {
00279     fprintf(qh ferr, "%s VERTEX:\n", string);
00280     qh_printvertex (qh ferr, atvertex);
00281   }
00282   if (qh fout && qh FORCEoutput && atfacet && !qh QHULLfinished && !qh IStracing) {
00283     fprintf(qh ferr, "ERRONEOUS and NEIGHBORING FACETS to output\n");
00284     for (i= 0; i < qh_PRINTEND; i++)  /* use fout for geomview output */
00285       qh_printneighborhood (qh fout, qh PRINTout[i], atfacet, otherfacet,
00286                             !qh_ALL);
00287   }
00288 } /* errprint */
00289 
00290 
00291 /*-<a                             href="qh-user.htm#TOC"
00292   >-------------------------------</a><a name="printfacetlist">-</a>
00293   
00294   qh_printfacetlist( fp, facetlist, facets, printall )
00295     print all fields for a facet list and/or set of facets to fp
00296     if !printall, 
00297       only prints good facets
00298 
00299   notes:
00300     also prints all vertices
00301 */
00302 void qh_printfacetlist(facetT *facetlist, setT *facets, boolT printall) {
00303   facetT *facet, **facetp;
00304 
00305   qh_printbegin (qh ferr, qh_PRINTfacets, facetlist, facets, printall);
00306   FORALLfacet_(facetlist)
00307     qh_printafacet(qh ferr, qh_PRINTfacets, facet, printall);
00308   FOREACHfacet_(facets)
00309     qh_printafacet(qh ferr, qh_PRINTfacets, facet, printall);
00310   qh_printend (qh ferr, qh_PRINTfacets, facetlist, facets, printall);
00311 } /* printfacetlist */
00312 
00313 
00314 /*-<a                             href="qh-globa.htm#TOC"
00315   >-------------------------------</a><a name="user_memsizes">-</a>
00316   
00317   qh_user_memsizes()
00318     allocate up to 10 additional, quick allocation sizes
00319 
00320   notes:
00321     increase maximum number of allocations in qh_initqhull_mem()
00322 */
00323 void qh_user_memsizes (void) {
00324 
00325   /* qh_memsize (size); */
00326 } /* user_memsizes */
00327 
 

Powered by Plone

This site conforms to the following standards: