home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 October / usenetsourcesnewsgroupsinfomagicoctober1994disk2.iso / misc / volume40 / lic / part05 < prev    next >
Text File  |  1993-11-09  |  62KB  |  2,065 lines

  1. Newsgroups: comp.sources.misc
  2. From: casey@gauss.llnl.gov (Casey Leedom)
  3. Subject: v40i119:  lic - LLNL Line Integral Convolution, v1.3, Part05/09
  4. Message-ID: <1993Nov9.170952.26760@sparky.sterling.com>
  5. X-Md4-Signature: 04c794282e80fb12c44bc143dd9fe995
  6. Sender: kent@sparky.sterling.com (Kent Landfield)
  7. Organization: Sterling Software
  8. Date: Tue, 9 Nov 1993 17:09:52 GMT
  9. Approved: kent@sparky.sterling.com
  10.  
  11. Submitted-by: casey@gauss.llnl.gov (Casey Leedom)
  12. Posting-number: Volume 40, Issue 119
  13. Archive-name: lic/part05
  14. Environment: UNIX
  15. Supersedes: lic: Volume 38, Issue 104
  16.  
  17. #! /bin/sh
  18. # This is a shell archive.  Remove anything before this line, then feed it
  19. # into a shell via "sh file" or similar.  To overwrite existing files,
  20. # type "sh file -c".
  21. # Contents:  lic.1.3/liblic/LIC_Create.3 lic.1.3/lic/lic.1
  22. #   lic.1.3/lic/lic.c lic.1.3/test/gl-disp.c
  23. # Wrapped by kent@sparky on Tue Nov  9 10:09:39 1993
  24. PATH=/bin:/usr/bin:/usr/ucb:/usr/local/bin:/usr/lbin:$PATH ; export PATH
  25. echo If this archive is complete, you will see the following message:
  26. echo '          "shar: End of archive 5 (of 9)."'
  27. if test -f 'lic.1.3/liblic/LIC_Create.3' -a "${1}" != "-c" ; then 
  28.   echo shar: Will not clobber existing file \"'lic.1.3/liblic/LIC_Create.3'\"
  29. else
  30.   echo shar: Extracting \"'lic.1.3/liblic/LIC_Create.3'\" \(11379 characters\)
  31.   sed "s/^X//" >'lic.1.3/liblic/LIC_Create.3' <<'END_OF_FILE'
  32. X.\" Copyright (c) 1993 The Regents of the University of California.
  33. X.\" All rights reserved.
  34. X.\"
  35. X.\" Redistribution and use in source and binary forms, with or without
  36. X.\" modification, are permitted provided that the following conditions
  37. X.\" are met:
  38. X.\" 1. Redistributions of source code must retain the above copyright
  39. X.\"    notice, this list of conditions and the following disclaimer.
  40. X.\" 2. Redistributions in binary form must reproduce the above copyright
  41. X.\"    notice, this list of conditions and the following disclaimer in the
  42. X.\"    documentation and/or other materials provided with the distribution.
  43. X.\" 3. All advertising materials mentioning features or use of this software
  44. X.\"    must display the following acknowledgement:
  45. X.\"    This product includes software developed by the University of
  46. X.\"    California, Lawrence Livermore National Laboratory and its
  47. X.\"    contributors.
  48. X.\" 4. Neither the name of the University nor the names of its contributors
  49. X.\"    may be used to endorse or promote products derived from this software
  50. X.\"    without specific prior written permission.
  51. X.\"
  52. X.\" THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
  53. X.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  54. X.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  55. X.\" ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
  56. X.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  57. X.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  58. X.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  59. X.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  60. X.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  61. X.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  62. X.\" SUCH DAMAGE.
  63. X.\"
  64. X.de Hd
  65. X.ds Dt \\$4
  66. X..
  67. X.Hd $Header: /usr/local/src/lic/liblic/RCS/LIC_Create.3,v 1.8 1993/10/28 01:08:08 casey Exp $
  68. X.TH LIC_CREATE 3 \*(Dt
  69. X.SH NAME
  70. XLIC_Create \- create Line Integral Convolution object instance
  71. X.SH SYNOPSIS
  72. X.nf
  73. X#include <lic.h>
  74. X
  75. X.ta \w'LIC *\fBLIC_Create\fP('u +\w'unsigned charXXX('u
  76. XLIC *\fBLIC_Create\fP(unsigned char    *\fIInputImage\fP,
  77. X.ta \w'LIC *\fBLIC_Create\fP('u +\w'unsigned charXXX(*'u
  78. X    int        \fIiiXres\fP,
  79. X    int        \fIiiYres\fP,
  80. X    int        \fIiiZres\fP,
  81. X.ta \w'LIC *\fBLIC_Create\fP('u +\w'unsigned charXXX('u
  82. X    float    *\fIInputField\fP,
  83. X.ta \w'LIC *\fBLIC_Create\fP('u +\w'unsigned charXXX(*'u
  84. X    int        \fIifXres\fP,
  85. X    int        \fIifYres\fP,
  86. X    int        \fIifZres\fP,
  87. X.ta \w'LIC *\fBLIC_Create\fP('u +\w'unsigned charXXX('u
  88. X    unsigned char    *\fIOutputImage\fP,
  89. X.ta \w'LIC *\fBLIC_Create\fP('u +\w'unsigned charXXX(*'u
  90. X    LIC_Filter    \fIFilter\fP,
  91. X    int        \fINormalizationType\fP,
  92. X    int        \fINormalized\fP,
  93. X    double    \fILength\fP,
  94. X    double    \fIFrequency\fP,
  95. X    int        \fIVariableLength\fP,
  96. X    int        \fIVariableSpeed\fP,
  97. X    int    \fIDefaultRed\fP,
  98. X    int    \fIDefaultGreen\fP,
  99. X    int    \fIDefaultBlue\fP,
  100. X    int    \fIDefaultAlpha\fP,
  101. X.ta \w'LIC *\fBLIC_Create\fP('u +\w'unsigned charXXX'u
  102. X    void        (*\fIUpdateUser\fP)(double \fIpercent-complete\fP),
  103. X    void        (*\fIReportError\fP)(const char *\fImessage\fP))
  104. X.DT
  105. X.fi
  106. X.SH DESCRIPTION
  107. X.if t .ds pi \(*p
  108. X.if n .ds pi Pi
  109. X.B LIC_Create
  110. Xconstructs an instance of a LIC object.
  111. X.PP
  112. X.I InputImage
  113. Xis the input image to be convolved,
  114. X.I InputField
  115. Xis the input vector field which controls the directional convolution and
  116. X.I OutputImage
  117. Xis the output image where Line Integral Convolution results will be placed.
  118. X.IR iiXres ,
  119. X.I iiYres
  120. Xand
  121. X.I iiZres
  122. Xare the X, Y and Z sizes of
  123. X.IR InputImage .
  124. X.IR ifXres ,
  125. X.I ifYres
  126. Xand
  127. X.I ifZres
  128. Xare the X, Y and Z sizes of
  129. X.I InputField
  130. Xand
  131. X.IR OutputImage .
  132. XIf
  133. X.I InputImage
  134. Xis smaller than
  135. X.I InputField
  136. Xin some dimension, references to
  137. X.I InputImage
  138. Xpixels corresponding to
  139. X.I InputField
  140. Xcells will be wrapped toriodally.
  141. XIf
  142. X.B NULL
  143. Xis passed for
  144. X.IR OutputImage ,
  145. X.B LIC_Create
  146. Xwill automatically allocate space for it.
  147. X.PP
  148. XThe input and output images and input vector field are stored as raw binary
  149. Xrow major arrays.
  150. X.PP
  151. X.I InputImage
  152. Xand
  153. X.I OutputImage
  154. Xare arrays of pixels.  Each pixel is 1 to 4 bytes and must match
  155. Xthe pixel size configured into the LIC library when it was compiled (see
  156. X.B LIC_ConfiguredPixelSize
  157. Xin the
  158. X.B LIC_Query
  159. Xmanual page).
  160. X.PP
  161. X.I InputField
  162. Xis an array of single precision floating point Cartesian vectors. Each vector
  163. Xis of rank equal to the dimension of the data, 2 for two-dimensional
  164. Xfields and 3 for three-dimensional fields.  The vectors are stored as
  165. Xtwo- and three-tuples, respectively, ordered as x-ordinate, y-ordinate
  166. Xand, if applicable, z-ordinate.
  167. X.PP
  168. XNote that vectors with positive y-coordinates point towards lower row
  169. Xcoordinates.  That is, towards the \(lqtop\(rq of a two-dimensional
  170. Ximage.  Positive x-coordinates and z-coordinates point towards larger
  171. Xcolumn and plane coordinates, respectively.  The y-coordinate flip is
  172. Xa consequence of using the left-handed image field coordinate system
  173. Xto access the input vector field which contains right-handed vectors.
  174. X.PP
  175. X.I Filter
  176. Xmust be a pointer to a LIC_Filter type function:
  177. X.PP
  178. X.RS
  179. X.nf
  180. Xdouble \fIFilter\fP(LIC *\fIThis\fP, double \fIa\fP, double \fIb\fP, int \fIspeed\fP)
  181. X.fi
  182. X.RE
  183. X.PP
  184. X.I Filter
  185. Xshould return the integral of the filter kernel between
  186. X.I a
  187. Xand
  188. X.IR b .
  189. X.I speed
  190. Xspecifies the speed with respect to phase shift animation that
  191. X.I Filter
  192. Xshould use for its filter kernel.
  193. X.I speed
  194. Xis used to implement the variable speed option (though many filters ignore
  195. Xthis parameter).
  196. X.PP
  197. XThe following filters are supplied with the LIC library:
  198. X.PP
  199. X.RS
  200. X.nf
  201. Xdouble \fBLIC_Box\fP(LIC *\fIThis\fP, double \fIa\fP, double \fIb\fP, int \fIspeed\fP)
  202. Xdouble \fBLIC_Ripple\fP(LIC *\fIThis\fP, double \fIa\fP, double \fIb\fP, int \fIspeed\fP)
  203. Xdouble \fBLIC_Ramp\fP(LIC *\fIThis\fP, double \fIa\fP, double \fIb\fP, int \fIspeed\fP)
  204. Xdouble \fBLIC_Select\fP(LIC *\fIThis\fP, double \fIa\fP, double \fIb\fP, int \fIspeed\fP)
  205. X.fi
  206. X.RE
  207. X.PP
  208. XThey implement a box filter, a Hanning windowed Hanning ripple filter,
  209. Xa ramp filter and a pixel selection filter, respectively.  See
  210. X.BR LIC_Filters (3)
  211. Xfor more information on LIC filters and the integration process.
  212. X.PP
  213. X.I NormalizationType
  214. Xspecifies the type of normalization to be used:
  215. X.B LIC_FIXED
  216. Xor
  217. X.BR LIC_VARIABLE .
  218. XWith fixed normalization, output image pixels will be attenuated near
  219. Xinput vector field singularities and edges of the input field where
  220. Xvectors are not parallel to the edges.  With variable normalization,
  221. Xoutput image pixels will maintain an even brightness level (relative
  222. Xto the input image pixels they are summed from).
  223. X.PP
  224. X.I Normalized
  225. Xspecifies that the input vector field is normalized: all vectors have
  226. Xmagnitude 1 or 0.  If the vector field is not normalized, a separate
  227. Xnormalized copy will be constructed for use in the convolution
  228. Xmethods.  This may affect the ability to handle large problems because
  229. Xof memory constraints.  If this becomes a problem, you may want to
  230. Xconsider pre-normalizing the vector field.  However, this isn't an
  231. Xoption if you want to do variable length or variable speed convolution
  232. Xsince the vector magnitudes are used to control the length and speed
  233. Xvariations (see variable length and variable speed documentation
  234. Xbelow).
  235. X.PP
  236. X.I Length
  237. Xspecifies the length of the filter kernel.  The filter kernel will actually be
  238. X.RI 2* Length ,
  239. Xextending from
  240. X.RI - Length
  241. Xto
  242. X.RI + Length .
  243. XIt is an error to specify a
  244. X.I length
  245. Xless than
  246. X.BR 0 .
  247. X.PP
  248. X.I Frequency
  249. Xspecifies the frequency of the filter kernel.
  250. X.I Frequency
  251. Xis interpreted as the number of cycles of the filter kernel over the domain
  252. X.RB - \*(pi
  253. Xto
  254. X.BR \*(pi .
  255. X(See
  256. X.B LIC_ChangePhase
  257. Xin the
  258. X.BR LIC_Modify (3)
  259. Xmanual page for a description of how to change the phase of the filter
  260. Xkernel.)
  261. X.I Frequency
  262. Xis scaled to the length of the filter kernel.  Thus, a
  263. X.I Frequency
  264. Xof 2 will cause two repetitions of the filter kernel across the domain
  265. X.RI - Length
  266. Xto
  267. X.RI + Length .
  268. X.I Frequency
  269. Xmust be non-zero and positive.
  270. XCurrently, the only filter supplied with the LIC library that uses this
  271. Xoption is
  272. X.BR LIC_Ripple .
  273. X.PP
  274. X.I VariableLength
  275. Xis a boolean flag which, when TRUE, specifies that variable length filtering
  276. Xshould be performed.  The LIC filter length for each vector \fIv\fP will
  277. Xvary from 0 to
  278. X.I Length
  279. Xbased on the vector's magnitude.  This magnitude scaling is performed
  280. Xby finding the maximum magnitude vector in the input vector field,
  281. X\fImax_v\fP, and then using a filter length equal to
  282. X\fILength\fP  * ||\fIv\fP|| / ||\fImax_v\fP||.
  283. XThe filter will be dilated to match the length of the convolution.
  284. XThis prevents any visual artifacts which might occur because of abrupt
  285. Xfilter truncation if the filter were not dilated.
  286. X.PP
  287. X.I VariableSpeed
  288. Xis a boolean flag which, when TRUE, specifies that variable
  289. X.I speed
  290. Xfiltering should be performed.
  291. XHigh magnitude regions of the vector field will use high
  292. X.I speed
  293. Xversions of the filter.  These higher speeds variations are typically
  294. Xphase multiplied versions of the base phase and are used in periodic
  295. Xmotion animations to give the appearance of higher speed in higher magnitude
  296. Xregions of the vector field.
  297. XHowever, it is up to each filter to implement its own interpretation of
  298. X.IR speed .
  299. X.PP
  300. XFor the ripple filter, the speed variations use a different phase for each
  301. Xvector
  302. X.I v
  303. Xbased on its magnitude.  These phase variations vary from
  304. X.I Phase
  305. Xto 3 *
  306. X.IR Phase .
  307. X.PP
  308. XVariable speed filtering is currently only implemented by the ripple
  309. Xfilter (it doesn't have any effect on the box filter and is of dubious
  310. Xvalue for the ramp filter.)
  311. X.PP
  312. X.IR DefaultRed ,
  313. X.IR DefaultGreen ,
  314. X.I DefaultBlue
  315. Xand
  316. X.I DefaultAlpha
  317. Xdefine the default red, green, blue and alpha pixel values to use to represent
  318. Xzero magnitude vectors.  A value of
  319. X.B -1
  320. Xspecifies that the underlaying input image pixel value should be used.
  321. XFor
  322. X.B MONOCHROME
  323. Ximages,
  324. X.I default-alpha
  325. Xcontrols the default pixel value.
  326. X.PP
  327. X.I UpdateUser
  328. Xshould be
  329. X.B NULL
  330. Xor a pointer to user supplied function.  If
  331. X.RB non- NULL ,
  332. Xit will be called by
  333. X.B LIC_ComputeImage
  334. Xfrom time to time to report computation progress with a
  335. X.I percent-complete
  336. Xvalue between 0.0 and 100.0.
  337. X.PP
  338. X.B ReportError
  339. Xshould be
  340. X.B NULL
  341. Xor a pointer to user supplied function.  If
  342. X.RB non- NULL ,
  343. Xit will be called by the LIC library routines to report various errors.
  344. XTypically these will be to report memory allocation failure or errors
  345. Xin user supplied parameters.  A
  346. X.B NULL
  347. Xterminated character string value,
  348. X.IR message ,
  349. Xwill be passed to
  350. X.BR ReportError .
  351. X.I message
  352. Xwill not contain a trailing newline.
  353. X.SH "RETURN VALUES"
  354. X.B NULL
  355. Xwill be returned if
  356. X.B LIC_Create
  357. Xis unable to allocate memory for the new LIC instance, otherwise a pointer
  358. Xto the new instance is returned.
  359. X.SH ERRORS
  360. XLIC_Create: Unable to allocate memory for LIC instance variable
  361. X.PP
  362. XLIC_Create: Unable to allocate memory for normalized input vector field
  363. X.PP
  364. XLIC_Create: Unable to allocate memory for output image
  365. X.SH "SEE ALSO"
  366. X.BR LIC (3),
  367. X.BR LIC_Destroy (3),
  368. X.BR LIC_Modify (3),
  369. X.BR LIC_Query (3)
  370. X.SH BUGS
  371. XIf a negative
  372. X.I Length
  373. Xis specified, a length of 0 will be used instead.
  374. XIf a negative or zero
  375. X.I Frequency
  376. Xis specified, a frequency of 1e-6 will be used instead.  In both cases error
  377. Xmessages should probably be output.
  378. X.SH STANDARDS
  379. XThis is unsupported, non-standard software.  It is not the subject of any
  380. Xstandards effort.
  381. END_OF_FILE
  382.   if test 11379 -ne `wc -c <'lic.1.3/liblic/LIC_Create.3'`; then
  383.     echo shar: \"'lic.1.3/liblic/LIC_Create.3'\" unpacked with wrong size!
  384.   fi
  385.   # end of 'lic.1.3/liblic/LIC_Create.3'
  386. fi
  387. if test -f 'lic.1.3/lic/lic.1' -a "${1}" != "-c" ; then 
  388.   echo shar: Will not clobber existing file \"'lic.1.3/lic/lic.1'\"
  389. else
  390.   echo shar: Extracting \"'lic.1.3/lic/lic.1'\" \(12167 characters\)
  391.   sed "s/^X//" >'lic.1.3/lic/lic.1' <<'END_OF_FILE'
  392. X.\" Copyright (c) 1993 The Regents of the University of California.
  393. X.\" All rights reserved.
  394. X.\"
  395. X.\" Redistribution and use in source and binary forms, with or without
  396. X.\" modification, are permitted provided that the following conditions
  397. X.\" are met:
  398. X.\" 1. Redistributions of source code must retain the above copyright
  399. X.\"    notice, this list of conditions and the following disclaimer.
  400. X.\" 2. Redistributions in binary form must reproduce the above copyright
  401. X.\"    notice, this list of conditions and the following disclaimer in the
  402. X.\"    documentation and/or other materials provided with the distribution.
  403. X.\" 3. All advertising materials mentioning features or use of this software
  404. X.\"    must display the following acknowledgement:
  405. X.\"    This product includes software developed by the University of
  406. X.\"    California, Lawrence Livermore National Laboratory and its
  407. X.\"    contributors.
  408. X.\" 4. Neither the name of the University nor the names of its contributors
  409. X.\"    may be used to endorse or promote products derived from this software
  410. X.\"    without specific prior written permission.
  411. X.\"
  412. X.\" THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
  413. X.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  414. X.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  415. X.\" ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
  416. X.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  417. X.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  418. X.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  419. X.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  420. X.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  421. X.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  422. X.\" SUCH DAMAGE.
  423. X.\"
  424. X.de Hd
  425. X.ds Dt \\$4
  426. X..
  427. X.Hd $Header: /usr/local/src/lic/lic/RCS/lic.1,v 1.14 1993/11/05 00:30:51 casey Exp $
  428. X.TH LIC 1 \*(Dt
  429. X.SH NAME
  430. Xlic \- Line Integral Convolution processor
  431. X.SH SYNOPSIS
  432. X.nf
  433. X\fBlic\fP [\fIoptions\fP] \fIinput-image\fP \fIinput-vector-field\fP \fIoutput-image\fP
  434. X.fi
  435. X.SH DESCRIPTION
  436. X.if t .ds pi \(*p
  437. X.if n .ds pi Pi
  438. X.B lic
  439. Xis a command line interface to the
  440. X.I "Line Integral Convolution"
  441. Xlibrary.  Line Integral Convolution was designed for vector field
  442. Xvisualization but has applications in a number of other domains
  443. Xincluding image processing, special effects and artistic rendering.
  444. XFor an in depth description of Line Integral Convolution, see
  445. X.BR LIC (3).
  446. X.PP
  447. XThe input and output files are stored as raw binary files without any
  448. Xheaders.  The files are organized as sequential row major (C-style)
  449. Xarrays.
  450. X.PP
  451. XThe
  452. X.I input-image
  453. Xand
  454. X.I output-image
  455. Xfiles are arrays of pixels.  Each pixel is 1 to 4 bytes and must match
  456. Xthe pixel size configured into
  457. X.B lic
  458. Xwhen it was compiled (see
  459. X.B LIC_ConfiguredPixelSize
  460. Xin the
  461. X.B LIC_Query
  462. Xmanual page).
  463. X.PP
  464. XThe
  465. X.I input-vector-field
  466. Xfile is an array of single precision floating point vectors. Each vector
  467. Xis of rank equal to the dimension of the data, 2 for two-dimensional
  468. Xfields and 3 for three-dimensional fields.  The vectors are stored as
  469. Xtwo- and three-tuples, respectively, ordered as x-coordinate, y-coordinate
  470. Xand, if applicable, z-coordinate.
  471. X.PP
  472. XNote that vectors with positive y-coordinates point towards lower row
  473. Xcoordinates.  That is, towards the \(lqtop\(rq of a two-dimensional
  474. Ximage.  Positive x-coordinates and z-coordinates point towards larger
  475. Xcolumn and plane coordinates, respectively.  The y-coordinate flip is
  476. Xa consequence of using the left-handed image field coordinate system
  477. Xto access the input vector field which contains right-handed vectors.
  478. X.PP
  479. XThe
  480. X.I output-image
  481. Xis created by
  482. X.BR lic .
  483. XThe x-y-z size of the file is equal to that of the
  484. X.IR input-vector-field .
  485. XAs a safety feature
  486. X.B lic
  487. Xwill never overwrite an existing file.
  488. X.PP
  489. XOptions available are:
  490. X.PP
  491. X\fB\-x\fP \fIx-extent\fP (required parameter, \fBno default\fP)
  492. X.br
  493. X\fB\-y\fP \fIy-extent\fP (required parameter, \fBno default\fP)
  494. X.br
  495. X\fB\-z\fP \fIz-extent\fP (default: \fB1\fP)
  496. X.RS 5
  497. XSets the
  498. X.IR x ,
  499. X.I y
  500. Xand
  501. X.I z
  502. Xsize of
  503. X.IR input-vector-field .
  504. XThe
  505. X.B \-x
  506. Xand
  507. X.B \-y
  508. Xoptions are not optional.  They must be provided.  The
  509. X.B \-z
  510. Xis optional and defaults to the value of
  511. X.BR 1 .
  512. X.RE
  513. X.PP
  514. X\fB\-i\fP \fIi-extent\fP (default: \fIx-extent\fP)
  515. X.br
  516. X\fB\-j\fP \fIj-extent\fP (default: \fIy-extent\fP)
  517. X.br
  518. X\fB\-k\fP \fIk-extent\fP (default: \fIz-extent\fP)
  519. X.RS 5
  520. XSets the
  521. X.IR x ,
  522. X.I y
  523. Xand
  524. X.I z
  525. Xsize of
  526. X.IR input-image .
  527. XIf not specified, they will default to the same values specified for
  528. X.IR input-vector-field .
  529. XThe sizes for
  530. X.I input-image
  531. Xand
  532. X.I input-vector-field
  533. Xneed not match in any way.  If
  534. X.I input-image
  535. Xis smaller than
  536. X.I input-vector-field
  537. Xin some dimension, references to
  538. X.I input-image
  539. Xpixels corresponding to
  540. X.I input-vector-field
  541. Xcells will be wrapped toriodally.
  542. X.RE
  543. X.TP 5
  544. X\fB\-f\fP \fIfilter\fP (default: \fBbox\fP)
  545. XSpecifies the filter shape to use for the LIC.
  546. XAvailable filters are:
  547. X.PP
  548. X.RS
  549. X.TP 8
  550. X.B box
  551. XSpecifies a constant box shape filter: \fIk\fP(\fIs\fP) =  1.
  552. XAll input image pixels along LIC paths will be given equal weight.
  553. X.TP 8
  554. X.B ripple
  555. XSpecifies a phase shifted Hanning ripple function, windowed by a Hanning
  556. Xfunction: \fIk\fP(\fIs\fP) = (cos(\fId\fP*\fIs\fP + \fIphase\fP) + 1)/2
  557. X* (cos(\fIc\fP*\fIs\fP) + 1)/2.
  558. XWhere
  559. X.I d
  560. Xand
  561. X.I c
  562. Xare the dilation constants for the ripple and window functions,
  563. Xrespectively, and
  564. X.I phase
  565. Xis the phase shift of the ripple function.
  566. X.I d
  567. Xand
  568. X.I c
  569. Xcontrol the number of cycles of the Hanning functions over the filter kernel
  570. Xfrom
  571. X.RI - L
  572. Xto
  573. X.RI + L .
  574. X.I d
  575. Xis controlled by the
  576. X.B \-d
  577. Xoption and
  578. X.I c
  579. Xis always equal to
  580. X.BR 1 .
  581. X.I phase
  582. Xis controlled by the
  583. X.B \-p
  584. Xoption.
  585. X.TP 8
  586. X.B ramp
  587. XSpecifies a ramp shape filter whose value is
  588. X.B 0
  589. Xat
  590. X.RI - L
  591. Xand
  592. X.B 1
  593. Xat
  594. X.RI + L :
  595. X\fIk\fP(\fIs\fP) = (\fIs\fP + \fIL\fP) / 2\fIL\fP.
  596. X.TP 8
  597. X.B select
  598. XSpecifies a filter which is used to select an approximately one pixel
  599. Xwide window near the end of the advected streamline and place it at
  600. Xthe advection starting pixel.  This is achieved using a narrow
  601. XGaussian filter and placing this filter near the end of the advected
  602. Xstreamline.  This can be used to produce a warp of the input image.
  603. X.RE
  604. X.TP 5
  605. X\fB\-n\fP \fInormalization\fP (default: \fBvariable\fP)
  606. XSpecifies the type of normalization to be used:
  607. X.B fixed
  608. Xor
  609. X.BR variable .
  610. XWith
  611. X.B fixed
  612. Xnormalization, output image pixels will be attenuated near input vector
  613. Xfield singularities and edges of the input vector field where vectors are not
  614. Xparallel to the edges.
  615. XWith
  616. X.B variable
  617. Xnormalization, output image pixels will maintain an even brightness level
  618. X(relative to the input image pixels they are summed from).
  619. X.TP 5
  620. X\fB\-N\fP
  621. XSpecifies that the input vector field is normalized: all vectors have
  622. Xmagnitude 1 or 0.  If the vector field is not normalized, a separate
  623. Xnormalized copy will be constructed for use in the convolution
  624. Xmethods.  This may affect the ability to handle large problems because
  625. Xof memory constraints.  If this becomes a problem, you may want to
  626. Xconsider pre-normalizing the vector field.  However, this isn't an
  627. Xoption if you want to do variable length or variable speed convolution
  628. Xsince the vector magnitudes are used to control the length and speed
  629. Xvariations (see variable length and variable speed documentation
  630. Xbelow).
  631. X.TP 5
  632. X\fB\-l\fP \fIfilter-length\fP (default: \fB10.0\fP)
  633. XSpecifies the length,
  634. X.IR L ,
  635. Xof the filter kernel.  The length of the filter kernel will actually be
  636. X.RI 2* L ,
  637. Xextending from
  638. X.RI - L
  639. Xto
  640. X.RI + L .
  641. X.PP
  642. X\fB\-d\fP \fIfilter-frequency\fP (default: \fB3.0\fP)
  643. X.br
  644. X\fB\-p\fP \fIfilter-phase\fP (default: \fB0.0\fP)
  645. X.RS 5
  646. XSpecifies the frequency and phase of the filter kernel.
  647. X.I filter-frequency
  648. Xis interpreted as the number of cycles of the filter kernel over the domain
  649. X.RB - \*(pi
  650. Xto
  651. X.BR \*(pi .
  652. X.I filter-phase
  653. Xis interpreted as the phase offset of the filter kernel in the same domain.
  654. XBoth
  655. X.I filter-frequency
  656. Xand
  657. X.I filter-phase
  658. Xare scaled to the length of the filter kernel.  Thus, a
  659. X.I filter-frequency
  660. Xof 2 will cause two repetitions of the filter kernel across the domain
  661. X.RI - L
  662. Xto
  663. X.RI + L .
  664. XCurrently, only the
  665. X.B ripple
  666. Xfilter uses these options.
  667. X.RE
  668. X.TP 5
  669. X\fB\-L\fP
  670. XSpecifies that variable length filtering should be performed.  The LIC
  671. Xfilter length for each vector \fIv\fP will vary from 0 to
  672. X.I L
  673. Xbased on the vector's magnitude.  This magnitude scaling is performed
  674. Xby finding the maximum magnitude vector in the input vector field,
  675. X\fImax_v\fP, and then using a filter length equal to
  676. X\fIL\fP  * ||\fIv\fP|| / ||\fImax_v\fP||.
  677. XThe filter will be dilated to match the length of the convolution.
  678. XThis prevents any visual artifacts which might occur because of abrupt
  679. Xfilter truncation if the filter were not dilated.
  680. X.TP 5
  681. X\fB\-S\fP
  682. XSpecifies that variable
  683. X.I speed
  684. Xfiltering should be performed.
  685. XHigh magnitude regions of the vector field will use high
  686. X.I speed
  687. Xversions of the filter.  These higher speeds variations are typically
  688. Xfrequency scaled versions of the base filter and are used in periodic
  689. Xmotion animations to give the appearance of higher speed in higher magnitude
  690. Xregions of the vector field.
  691. XHowever, it is up to each filter to implement its own interpretation of
  692. X.IR speed .
  693. X.PP
  694. XFor the
  695. X.B ripple
  696. Xfilter, the speed variations use a different frequency for each vector
  697. X.I v
  698. Xbased on its magnitude.  These frequency variations vary from 6 *
  699. X.I filter-frequency
  700. Xfor zero magnitude vectors to
  701. X.I filter-frequency
  702. Xfor maximum magnitude vectors.  Variable speed filtering is currently only
  703. Ximplemented by the
  704. X.B ripple
  705. Xfilter (it doesn't have any effect on the
  706. X.B box
  707. Xfilter and is of dubious value for the
  708. X.B ramp
  709. Xfilter.)
  710. X.PP
  711. X\fB\-r\fP \fIdefault-red\fP (default: \fB-1\fP)
  712. X.br
  713. X\fB\-g\fP \fIdefault-green\fP (default: \fB-1\fP)
  714. X.br
  715. X\fB\-b\fP \fIdefault-blue\fP (default: \fB-1\fP)
  716. X.br
  717. X\fB\-a\fP \fIdefault-alpha\fP (default: \fB-1\fP)
  718. X.RS 5
  719. XDefine the default red, green, blue and alpha pixel values to use to represent
  720. Xzero magnitude vectors.  A value of
  721. X.B -1
  722. Xspecifies that the underlaying input image pixel value should be used.
  723. XFor
  724. X.B MONOCHROME
  725. Ximages,
  726. X.I default-alpha
  727. Xcontrols the default pixel value.
  728. X.RE
  729. X.TP 5
  730. X\fB\-t\fP \fIthreads\fP (default: \fB1\fP)
  731. XSpecifies the number of parallel threads to use when computing
  732. X.IR output-image .
  733. XIf
  734. X.BR 0 ,
  735. Xthe maximum number of CPUs available for parallel processing on the
  736. Xcurrent system will be used.  Note that parallel processing support is
  737. Xnot available on all systems.  If a value other than
  738. X.B 1
  739. Xis specified on a system which does not support parallel processing, a
  740. Xwarning will be issued and the calculation will proceed single
  741. Xthreaded.
  742. X.TP 5
  743. X\fB\-T\fP
  744. XCauses execution performance statistics to be displayed at the end of
  745. Xthe computation.  The statistics include wall clock time, CPU time,
  746. XCPU utilization, cells processed per second, average convolution line
  747. Xlength, etc.
  748. X.TP 5
  749. X\fB\-v\fP
  750. XCauses verbose performance information to be displayed during the
  751. Xexecution of the calculation.  A progress message will be printed
  752. Xperiodically detailing how much of the computation has been finished
  753. Xand an estimate of the completion time for the entire computation.
  754. XSpecifying
  755. X.B \-v
  756. Xautomatically implies
  757. X.BR \-T .
  758. X.TP 5
  759. X\fB\-V\fP
  760. XCauses configuration information about the LIC library version to be printed.
  761. XCurrently the size of pixels and their types,
  762. X.BR RGB ,
  763. X.BR ABGR ,
  764. X.BR MONOCHROME ,
  765. Xetc. are controlled by library compile-time definitions.
  766. X.SH ERRORS
  767. XObjections to bad command line arguments, missing files, wrong size files,
  768. Xoutput files already existing, etc.  Additionally, complaints about not
  769. Xbeing able to map files into memory
  770. X.RB ( mmap
  771. Xversion) or inability to allocate memory
  772. X.RB ( malloc
  773. Xversion).
  774. X.SH "SEE ALSO"
  775. X.BR LIC (3),
  776. X.BR LIC_Filters (3)
  777. X.SH BUGS
  778. XPixel types and sizes are configured into the LIC software at compile time.
  779. XOnly single precision vector field ordinate values are supported.  These should
  780. Xboth be handled dynamically at run time.
  781. X.SH STANDARDS
  782. XThis is unsupported, non-standard software.  It is not the subject of any
  783. Xstandards effort.
  784. END_OF_FILE
  785.   if test 12167 -ne `wc -c <'lic.1.3/lic/lic.1'`; then
  786.     echo shar: \"'lic.1.3/lic/lic.1'\" unpacked with wrong size!
  787.   fi
  788.   # end of 'lic.1.3/lic/lic.1'
  789. fi
  790. if test -f 'lic.1.3/lic/lic.c' -a "${1}" != "-c" ; then 
  791.   echo shar: Will not clobber existing file \"'lic.1.3/lic/lic.c'\"
  792. else
  793.   echo shar: Extracting \"'lic.1.3/lic/lic.c'\" \(24791 characters\)
  794.   sed "s/^X//" >'lic.1.3/lic/lic.c' <<'END_OF_FILE'
  795. X/*
  796. X * $Header: /usr/local/src/lic/lic/RCS/lic.c,v 1.31 1993/11/05 00:30:51 casey Exp $
  797. X */
  798. X
  799. X/*
  800. X * Copyright (c) 1993 The Regents of the University of California.
  801. X * All rights reserved.
  802. X *
  803. X * Redistribution and use in source and binary forms, with or without
  804. X * modification, are permitted provided that the following conditions
  805. X * are met:
  806. X * 1. Redistributions of source code must retain the above copyright
  807. X *    notice, this list of conditions and the following disclaimer.
  808. X * 2. Redistributions in binary form must reproduce the above copyright
  809. X *    notice, this list of conditions and the following disclaimer in the
  810. X *    documentation and/or other materials provided with the distribution.
  811. X * 3. All advertising materials mentioning features or use of this software
  812. X *    must display the following acknowledgement:
  813. X *    This product includes software developed by the University of
  814. X *    California, Lawrence Livermore National Laboratory and its
  815. X *    contributors.
  816. X * 4. Neither the name of the University nor the names of its contributors
  817. X *    may be used to endorse or promote products derived from this software
  818. X *    without specific prior written permission.
  819. X *
  820. X * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
  821. X * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  822. X * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  823. X * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
  824. X * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  825. X * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  826. X * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  827. X * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  828. X * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  829. X * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  830. X * SUCH DAMAGE.
  831. X */
  832. X
  833. X#ifndef lint
  834. X    static char rcsid[] = "$Header: /usr/local/src/lic/lic/RCS/lic.c,v 1.31 1993/11/05 00:30:51 casey Exp $";
  835. X    static char copyright[] =
  836. X    "Copyright (c) 1993 The Regents of the University of California.\n"
  837. X    "All rights reserved.\n";
  838. X#endif
  839. X
  840. X
  841. X/*
  842. X * UNIX command line interface to the Line Integral Convolution library.
  843. X */
  844. X
  845. X
  846. X#include <stdlib.h>
  847. X#include <unistd.h>
  848. X#include <errno.h>
  849. X#include <string.h>
  850. X#include <stdio.h>
  851. X#include <time.h>
  852. X#include <sys/times.h>
  853. X#include <sys/types.h>
  854. X
  855. X#include <fcntl.h>
  856. X#include <math.h>
  857. X#include <sys/stat.h>
  858. X
  859. X#if defined(HAS_MMAP)
  860. X#   include <sys/mman.h>
  861. X#endif
  862. X
  863. X#include <lic.h>
  864. X
  865. X
  866. X#ifdef NEED_STRERROR
  867. X    /*
  868. X     * strerror is supposed to be defined in <string.h> and supplied in the
  869. X     * standard C library according to the ANSI C X3.159-1989 specification,
  870. X     * but Sun OS 4.1.1 fails to define or supply it ...  Unfortunately the
  871. X     * only way we can control this is with an externally supplied define.
  872. X     */
  873. X    extern int      errno;        /* system error number */
  874. X    extern char     *sys_errlist[];    /* system error messages */
  875. X    extern int      sys_nerr;        /* number of entries in sys_errlist */
  876. X
  877. X    static char *
  878. X    strerror(int err)
  879. X    {
  880. X    if (err < 0 || err >= sys_nerr) {
  881. X        static char msg[100];
  882. X
  883. X        sprintf(msg, "system error number %d", err);
  884. X        return(msg);
  885. X    }
  886. X    return(sys_errlist[err]);
  887. X    }
  888. X#endif
  889. X
  890. X
  891. X/*
  892. X *    Arguments
  893. X *    =========
  894. X */
  895. Xstatic char *usage =
  896. X"usage: %s [options] input-image input-vector-field output-image\n"
  897. X"  -x x-extent         - input-vector-field X extent     (required: no default)\n"
  898. X"  -y y-extent         - input-vector-field Y extent     (required: no default)\n"
  899. X"  -z z-extent         - input-vector-field Z extent     (default: 1)\n"
  900. X"  -i i-extent         - input-image X extent            (default: x-extent)\n"
  901. X"  -j j-extent         - input-image Y extent            (default: y-extent)\n"
  902. X"  -k k-extent         - input-image Z extent            (default: z-extent)\n"
  903. X"  -f filter           - 'box', 'ripple', 'ramp' or      (default: 'box')\n"
  904. X"                        'select'\n"
  905. X"  -n normalization    - 'fixed' or 'variable'           (default: 'variable')\n"
  906. X"  -N                  - input vector field already normalized\n"
  907. X"  -l filter-length    -                                 (default: 10.0)\n"
  908. X"  -d filter-frequency -                                 (default: 3.0)\n"
  909. X"  -p filter-phase     -                                 (default: 0.0)\n"
  910. X"  -L                  - vary filter-length based on vector magnitude\n"
  911. X"  -S                  - vary filter-phase based on vector magnitude\n"
  912. X"  -r default-red      - for zero vectors                (default: -1)\n"
  913. X"  -g default-green    - for zero vectors                (default: -1)\n"
  914. X"  -b default-blue     - for zero vectors                (default: -1)\n"
  915. X"  -a default-alpha    - for zero vectors                (default: -1)\n"
  916. X"  -t threads          - number of parallel threads      (default: 1)\n"
  917. X"  -T                  - overall timing information\n"
  918. X"  -v                  - verbose progress and overall timing information\n"
  919. X"  -V                  - version information\n"
  920. X    ;
  921. X
  922. Xstatic char *myname;            /* argv[0]: name we were invoked by */
  923. Xstatic int    size_x;            /* -x: X extent */
  924. Xstatic int    size_y;            /* -y: Y extent */
  925. Xstatic int    size_z        = 1;    /* -z: Z extent (default 1) */
  926. Xstatic int    size_i;            /* -i: input image X extent */
  927. Xstatic int    size_j;            /* -j: input image Y extent */
  928. Xstatic int    size_k;            /* -k: input image Z extent */
  929. Xstatic LIC_Filter
  930. X              filter        = LIC_Box;    /* -f: filter */
  931. Xstatic int    normalization = LIC_VARIABLE;
  932. X                     /* -n: normalization */
  933. Xstatic int    normalized    = FALSE;    /* -N: input vectors prenormalized */
  934. Xstatic double filter_length = 10.0;    /* -l: filter length */
  935. Xstatic double filter_frequency = 3.0;    /* -d: filter frequency */
  936. Xstatic double filter_phase  = 0.0;    /* -p: filter phase */
  937. Xstatic int    vary_length   = FALSE;    /* -L: vary length by vector mag. */
  938. Xstatic int    vary_speed    = FALSE;    /* -S: vary phase by vector mag. */
  939. Xstatic int    default_red   = -1;    /* -r: default red for zero vector */
  940. Xstatic int    default_green = -1;    /* -g: default green ... */
  941. Xstatic int    default_blue  = -1;    /* -b: default blue ... */
  942. Xstatic int    default_alpha = -1;    /* -a: default alpha ... */
  943. Xstatic int    threads       = 1;    /* -t: number of parallel threads */
  944. Xstatic int    timing        = FALSE;    /* -T: display timing information */
  945. Xstatic int    verbose       = FALSE;    /* -v: display progress information */
  946. Xstatic int    version       = FALSE;    /* -V: display version information */
  947. X
  948. Xstatic char  *in_img;            /* input image filename */
  949. Xstatic char  *in_vec;            /* input vector field filename */
  950. Xstatic char  *out_img;            /* output image filename */
  951. X
  952. X
  953. X/*
  954. X *    Local variables
  955. X *    ===============
  956. X */
  957. Xstatic time_t     t0;            /* time we started/ended the LIC */
  958. Xstatic clock_t    t0_clk, tN_clk;    /*   calculation */
  959. Xstatic struct tms t0_tms, tN_tms;
  960. X
  961. Xstatic void      *in_img_addr,        /* virtual addresses of memory */
  962. X                 *in_vec_addr,        /*   mapped input image, input */
  963. X                 *out_img_addr;        /*   vector field and output image */
  964. Xstatic off_t      in_img_size,        /* sizes of image and vector files */
  965. X                  in_vec_size,
  966. X                  out_img_size;
  967. X#if !defined(HAS_MMAP)
  968. X    static int    out_img_fd;        /* output image file descriptor */
  969. X#endif
  970. X
  971. X
  972. X/*
  973. X *    Local routines
  974. X *    ==============
  975. X */
  976. Xint         main(int argc, char *argv[]);
  977. Xstatic void ParseArguments(int argc, char *argv[]);
  978. Xstatic void LoadFiles(void);
  979. Xstatic void UnloadFiles(void);
  980. Xstatic void LicFiles(void);
  981. Xstatic void PrintLicStatus(double PercentDone);
  982. Xstatic void PrintLicError(const char *message);
  983. X
  984. X
  985. Xint
  986. Xmain(int argc, char *argv[])
  987. X{
  988. X    ParseArguments(argc, argv);
  989. X    LoadFiles();
  990. X    LicFiles();
  991. X    UnloadFiles();
  992. X    exit(EXIT_SUCCESS);
  993. X    /*NOTREACHED*/
  994. X}
  995. X
  996. X
  997. Xstatic void
  998. XParseArguments(int argc, char *argv[])
  999. X{
  1000. X    int          ch;
  1001. X#if defined(HAS_HP_GETOPT)
  1002. X    extern int   getopt(int, char * const [], const char *);
  1003. X#else
  1004. X    extern int   getopt(int, char **, char *);
  1005. X#endif
  1006. X    extern char *optarg;
  1007. X    extern int   optind;
  1008. X
  1009. X    myname = strrchr(argv[0], '/');
  1010. X    if (myname != NULL)
  1011. X    myname++;
  1012. X    else
  1013. X    myname = argv[0];
  1014. X    while ((ch = getopt(argc, argv, "x:y:z:i:j:k:f:n:Nl:d:p:LSr:g:b:a:t:TvV")) != EOF)
  1015. X    switch ((char)ch)
  1016. X    {
  1017. X        default:
  1018. X        case '?':
  1019. X        (void)fprintf(stderr, "%s: unknown option -%c\n",
  1020. X                  myname, ch);
  1021. X        (void)fprintf(stderr, usage, myname);
  1022. X        exit(EXIT_FAILURE);
  1023. X        /*NOTREACHED*/
  1024. X
  1025. X        case 'x':
  1026. X        size_x = atoi(optarg);
  1027. X        if (size_x <= 0)
  1028. X            goto bad_size;
  1029. X        break;
  1030. X
  1031. X        case 'y':
  1032. X        size_y = atoi(optarg);
  1033. X        if (size_y <= 0)
  1034. X            goto bad_size;
  1035. X        break;
  1036. X
  1037. X        case 'z':
  1038. X        size_z = atoi(optarg);
  1039. X        if (size_z <= 0)
  1040. X            goto bad_size;
  1041. X        break;
  1042. X
  1043. X        case 'i':
  1044. X        size_i = atoi(optarg);
  1045. X        if (size_i <= 0)
  1046. X            goto bad_size;
  1047. X        break;
  1048. X
  1049. X        case 'j':
  1050. X        size_j = atoi(optarg);
  1051. X        if (size_j <= 0)
  1052. X            goto bad_size;
  1053. X        break;
  1054. X
  1055. X        case 'k':
  1056. X        size_k = atoi(optarg);
  1057. X        if (size_k <= 0)
  1058. X            goto bad_size;
  1059. X        break;
  1060. X
  1061. X        bad_size:
  1062. X        (void)fprintf(stderr, "%s: bad size specification: -%c %d"
  1063. X                  " -- must be greater than 0\n",
  1064. X                  myname, ch, atoi(optarg));
  1065. X        exit(EXIT_FAILURE);
  1066. X        /*NOTREACHED*/
  1067. X
  1068. X        case 'f':
  1069. X        if (strcasecmp(optarg, "box") == 0)
  1070. X            filter = LIC_Box;
  1071. X        else if (strcasecmp(optarg, "ripple") == 0)
  1072. X            filter = LIC_Ripple;
  1073. X        else if (strcasecmp(optarg, "ramp") == 0)
  1074. X            filter = LIC_Ramp;
  1075. X        else if (strcasecmp(optarg, "select") == 0)
  1076. X            filter = LIC_Select;
  1077. X        else
  1078. X        {
  1079. X            (void)fprintf(stderr, "%: invalid filter type %s"
  1080. X                  " -- use 'box', 'ripple', 'ramp'"
  1081. X                  " or 'select'\n",
  1082. X                  myname, optarg);
  1083. X            exit(EXIT_FAILURE);
  1084. X            /*NOTREACHED*/
  1085. X        }
  1086. X        break;
  1087. X
  1088. X        case 'n':
  1089. X        if (strcasecmp(optarg, "fixed") == 0)
  1090. X            normalization = LIC_FIXED;
  1091. X        else if (strcasecmp(optarg, "variable") == 0)
  1092. X            normalization = LIC_VARIABLE;
  1093. X        else
  1094. X        {
  1095. X            (void)fprintf(stderr, "%: invalid normalization type %s"
  1096. X                  " -- use 'fixed' or 'variable'\n",
  1097. X                  myname, optarg);
  1098. X            exit(EXIT_FAILURE);
  1099. X            /*NOTREACHED*/
  1100. X        }
  1101. X        break;
  1102. X
  1103. X        case 'N':
  1104. X        normalized = TRUE;
  1105. X        break;
  1106. X
  1107. X        case 'l':
  1108. X        filter_length = atof(optarg);
  1109. X        if (filter_length < 0.0)
  1110. X        {
  1111. X            (void)fprintf(stderr, "%s: invalid filter length %f"
  1112. X                  " -- must be greater than or equal to 0.0\n",
  1113. X                  myname, filter_length);
  1114. X            exit(EXIT_FAILURE);
  1115. X            /*NOTREACHED*/
  1116. X        }
  1117. X        break;
  1118. X
  1119. X        case 'd':
  1120. X        filter_frequency = atof(optarg);
  1121. X        if (filter_frequency <= 0.0)
  1122. X        {
  1123. X            (void)fprintf(stderr, "%s: invalid filter frequency %f"
  1124. X                  " -- must be greater than 0.0\n",
  1125. X                  myname, filter_length);
  1126. X            exit(EXIT_FAILURE);
  1127. X            /*NOTREACHED*/
  1128. X        }
  1129. X        break;
  1130. X
  1131. X        case 'p':
  1132. X        filter_phase = atof(optarg);
  1133. X        break;
  1134. X
  1135. X        case 'L':
  1136. X        vary_length = TRUE;
  1137. X        break;
  1138. X
  1139. X        case 'S':
  1140. X        vary_speed = TRUE;
  1141. X        break;
  1142. X
  1143. X        case 'r':
  1144. X        default_red = atoi(optarg);
  1145. X        if (default_red < -1 || default_red > 255)
  1146. X            goto bad_color;
  1147. X        break;
  1148. X
  1149. X        case 'g':
  1150. X        default_green = atoi(optarg);
  1151. X        if (default_green < -1 || default_green > 255)
  1152. X            goto bad_color;
  1153. X        break;
  1154. X
  1155. X        case 'b':
  1156. X        default_blue = atoi(optarg);
  1157. X        if (default_blue < -1 || default_blue > 255)
  1158. X            goto bad_color;
  1159. X        break;
  1160. X
  1161. X        case 'a':
  1162. X        default_alpha = atoi(optarg);
  1163. X        if (default_alpha < -1 || default_alpha > 255)
  1164. X            goto bad_color;
  1165. X        break;
  1166. X
  1167. X        bad_color:
  1168. X        (void)fprintf(stderr, "%s: bad color specification: -%c %d"
  1169. X                  " -- must be between -1 and 255\n",
  1170. X                  myname, ch, atoi(optarg));
  1171. X        exit(EXIT_FAILURE);
  1172. X        /*NOTREACHED*/
  1173. X
  1174. X        case 't':
  1175. X        threads = atoi(optarg);
  1176. X        if (threads < 0)
  1177. X        {
  1178. X            (void)fprintf(stderr, "%s: invalid number of threads %d"
  1179. X                  " -- must be greather than or equal to 0\n",
  1180. X                  myname, threads);
  1181. X            threads = 1;
  1182. X            exit(EXIT_FAILURE);
  1183. X            /*NOTREACHED*/
  1184. X        }
  1185. X        break;
  1186. X
  1187. X        case 'T':
  1188. X        timing = TRUE;
  1189. X        break;
  1190. X
  1191. X        case 'v':
  1192. X        verbose = TRUE;
  1193. X        timing = TRUE;
  1194. X        break;
  1195. X
  1196. X        case 'V':
  1197. X        version = TRUE;
  1198. X        break;
  1199. X    }
  1200. X
  1201. X    if (version)
  1202. X    (void)printf("%s: compiled with LIC library version %s"
  1203. X             " using %d byte %s pixels\n",
  1204. X             myname, LIC_VERSION,
  1205. X             LIC_ConfiguredPixelSize(),
  1206. X             LIC_ConfiguredPixelType());
  1207. X
  1208. X    if (argc != optind + 3)
  1209. X    {
  1210. X    (void)fprintf(stderr, "%s: need three file options\n", myname);
  1211. X    (void)fprintf(stderr, usage, myname);
  1212. X    exit(EXIT_FAILURE);
  1213. X    /*NOTREACHED*/
  1214. X    }
  1215. X    in_img = argv[optind + 0];
  1216. X    in_vec = argv[optind + 1];
  1217. X    out_img = argv[optind + 2];
  1218. X    if (size_x == 0 || size_y == 0)
  1219. X    {
  1220. X    (void)fprintf(stderr, "%s: need both -x and -y options ...\n",
  1221. X              myname);
  1222. X    exit(EXIT_FAILURE);
  1223. X    /*NOTREACHED*/
  1224. X    }
  1225. X    if (size_i == 0)
  1226. X    size_i = size_x;
  1227. X    if (size_j == 0)
  1228. X    size_j = size_y;
  1229. X    if (size_k == 0)
  1230. X    size_k = size_z;
  1231. X}
  1232. X
  1233. X
  1234. X#if defined(HAS_MMAP)
  1235. X
  1236. X/*
  1237. X * Versions of LoadFiles and UnloadFiles for systems that support mmap(2).
  1238. X */
  1239. X
  1240. Xstatic void
  1241. XLoadFiles(void)
  1242. X    /*
  1243. X     * Map input and output files into virtual memory.  Make sure that the
  1244. X     * input files match the user specified sizes and pre-extend the
  1245. X     * output file to its final length.
  1246. X     */
  1247. X{
  1248. X    char        c;
  1249. X    int         fd;
  1250. X    struct stat stbuf;
  1251. X
  1252. X    /*
  1253. X     * Map input vector field into virtual memory.  (We always map the
  1254. X     * input vector field first because it will always be larger than
  1255. X     * either of the other two files.  This should, hopefully, give the
  1256. X     * operating system the best possible chance to find virtual address
  1257. X     * space for the three files.)
  1258. X     */
  1259. X    fd = open(in_vec, O_RDONLY);
  1260. X    if (fd < 0)
  1261. X    {
  1262. X    (void)fprintf(stderr, "%s: unable to open %s: %s\n",
  1263. X              myname, in_vec, strerror(errno));
  1264. X    exit(EXIT_FAILURE);
  1265. X    /*NOTREACHED*/
  1266. X    }
  1267. X    if (fstat(fd, &stbuf) < 0)
  1268. X    {
  1269. X    (void)fprintf(stderr, "%s: unable to stat %s: %s\n",
  1270. X              myname, in_vec, strerror(errno));
  1271. X    exit(EXIT_FAILURE);
  1272. X    /*NOTREACHED*/
  1273. X    }
  1274. X    in_vec_size = stbuf.st_size;
  1275. X    if (size_x * size_y * size_z * sizeof(float) * (size_z == 1 ? 2 : 3)
  1276. X    != in_vec_size)
  1277. X    {
  1278. X    (void)fprintf(stderr, "%s: input vector field size doesn't"
  1279. X              " match %d * x=%d * y=%d * z=%d\n",
  1280. X              myname, sizeof(float) * (size_z == 1 ? 2 : 3),
  1281. X              size_x, size_y, size_z);
  1282. X    exit(EXIT_FAILURE);
  1283. X    /*NOTREACHED*/
  1284. X    }
  1285. X    in_vec_addr = mmap((void *)0, (int)in_vec_size, PROT_READ,
  1286. X               MAP_SHARED, fd, (off_t)0);
  1287. X    if ((int)in_vec_addr == -1)
  1288. X    {
  1289. X    (void)fprintf(stderr, "%s: unable to map %s: %s\n",
  1290. X              myname, in_vec, strerror(errno));
  1291. X    exit(EXIT_FAILURE);
  1292. X    /*NOTREACHED*/
  1293. X    }
  1294. X    (void)close(fd);
  1295. X
  1296. X    /*
  1297. X     * Map input image into virtual memory.
  1298. X     */
  1299. X    fd = open(in_img, O_RDONLY);
  1300. X    if (fd < 0)
  1301. X    {
  1302. X    (void)fprintf(stderr, "%s: unable to open %s: %s\n",
  1303. X              myname, in_img, strerror(errno));
  1304. X    exit(EXIT_FAILURE);
  1305. X    /*NOTREACHED*/
  1306. X    }
  1307. X    if (fstat(fd, &stbuf) < 0)
  1308. X    {
  1309. X    (void)fprintf(stderr, "%s: unable to stat %s: %s\n",
  1310. X              myname, in_img, strerror(errno));
  1311. X    exit(EXIT_FAILURE);
  1312. X    /*NOTREACHED*/
  1313. X    }
  1314. X    in_img_size = stbuf.st_size;
  1315. X    if (size_i * size_j * size_k * LIC_ConfiguredPixelSize() != in_img_size)
  1316. X    {
  1317. X    (void)fprintf(stderr, "%s: input image size doesn't"
  1318. X              " match %d * x=%d * y=%d * z=%d\n",
  1319. X              myname, LIC_ConfiguredPixelSize(),
  1320. X              size_i, size_j, size_k);
  1321. X    exit(EXIT_FAILURE);
  1322. X    /*NOTREACHED*/
  1323. X    }
  1324. X    in_img_addr = mmap((void *)0, (int)in_img_size, PROT_READ,
  1325. X               MAP_SHARED, fd, (off_t)0);
  1326. X    if ((int)in_img_addr == -1)
  1327. X    {
  1328. X    (void)fprintf(stderr, "%s: unable to map %s: %s\n",
  1329. X              myname, in_img, strerror(errno));
  1330. X    exit(EXIT_FAILURE);
  1331. X    /*NOTREACHED*/
  1332. X    }
  1333. X    (void)close(fd);
  1334. X
  1335. X    /*
  1336. X     * Map output image into virtual memory.  O_EXCL prevents lic from
  1337. X     * overwriting a file that already exists.  Have to use O_RDWR rather
  1338. X     * than O_WRONLY because the OS will end up ``paging in pages from the
  1339. X     * file'' (sic).  In reality they'll just be zero fill on demand pages ...
  1340. X     */
  1341. X    fd = open(out_img, O_CREAT|O_EXCL|O_RDWR, 0666);
  1342. X    if (fd < 0)
  1343. X    {
  1344. X    (void)fprintf(stderr, "%s: unable to open %s: %s\n",
  1345. X              myname, out_img, strerror(errno));
  1346. X    exit(EXIT_FAILURE);
  1347. X    /*NOTREACHED*/
  1348. X    }
  1349. X    out_img_size = size_x * size_y * size_z * LIC_ConfiguredPixelSize();
  1350. X    (void)lseek(fd, out_img_size - 1, SEEK_SET);
  1351. X    c = '\0';
  1352. X    if (write(fd, &c, 1) != 1)
  1353. X    {
  1354. X    (void)fprintf(stderr, "%s: unable to preextend %s to %ld bytes: %s\n",
  1355. X              myname, out_img, strerror(errno));
  1356. X    exit(EXIT_FAILURE);
  1357. X    /*NOTREACHED*/
  1358. X    }
  1359. X    out_img_addr = mmap((void *)0, (int)out_img_size, PROT_WRITE,
  1360. X            MAP_SHARED, fd, (off_t)0);
  1361. X    if ((int)out_img_addr == -1)
  1362. X    {
  1363. X    (void)fprintf(stderr, "%s: unable to map %s: %s\n",
  1364. X              myname, out_img, strerror(errno));
  1365. X    exit(EXIT_FAILURE);
  1366. X    /*NOTREACHED*/
  1367. X    }
  1368. X    (void)close(fd);
  1369. X}
  1370. X
  1371. X
  1372. Xstatic void
  1373. XUnloadFiles(void)
  1374. X    /*
  1375. X     * Unmap input and output files from virtual memory.
  1376. X     */
  1377. X{
  1378. X    (void)munmap(in_img_addr, (int)in_img_size);
  1379. X    (void)munmap(in_vec_addr, (int)in_vec_size);
  1380. X    (void)munmap(out_img_addr, (int)out_img_size);
  1381. X}
  1382. X
  1383. X#else /* HAS_MMAP */
  1384. X
  1385. X/*
  1386. X * Versions of LoadFiles and UnloadFiles for systems that *don't* support
  1387. X * mmap(2).
  1388. X */
  1389. X
  1390. Xstatic void
  1391. XLoadFiles(void)
  1392. X    /*
  1393. X     * Load input files into malloc'ed memory and malloc memory for
  1394. X     * output image.  Make sure that the input files match the user
  1395. X     * specified sizes.  Preallocate output image on disk in order to
  1396. X     * make sure we have the space to output the image later in
  1397. X     * UnloadFiles.
  1398. X     */
  1399. X{
  1400. X    int         fd;
  1401. X    struct stat stbuf;
  1402. X
  1403. X    /*
  1404. X     * Load input image into malloc'ed memory.
  1405. X     */
  1406. X    fd = open(in_img, O_RDONLY);
  1407. X    if (fd < 0)
  1408. X    {
  1409. X    (void)fprintf(stderr, "%s: unable to open %s: %s\n",
  1410. X              myname, in_img, strerror(errno));
  1411. X    exit(EXIT_FAILURE);
  1412. X    /*NOTREACHED*/
  1413. X    }
  1414. X    if (fstat(fd, &stbuf) < 0)
  1415. X    {
  1416. X    (void)fprintf(stderr, "%s: unable to stat %s: %s\n",
  1417. X              myname, in_img, strerror(errno));
  1418. X    exit(EXIT_FAILURE);
  1419. X    /*NOTREACHED*/
  1420. X    }
  1421. X    in_img_size = stbuf.st_size;
  1422. X    if (size_i * size_j * size_k * LIC_ConfiguredPixelSize()
  1423. X    != in_img_size)
  1424. X    {
  1425. X    (void)fprintf(stderr, "%s: input image size doesn't"
  1426. X              " match %d * x=%d * y=%d * z=%d\n",
  1427. X              myname, LIC_ConfiguredPixelSize(),
  1428. X              size_i, size_j, size_k);
  1429. X    exit(EXIT_FAILURE);
  1430. X    /*NOTREACHED*/
  1431. X    }
  1432. X    in_img_addr = malloc(in_img_size);
  1433. X    if (in_img_addr == NULL)
  1434. X    {
  1435. X    (void)fprintf(stderr, "%s: unable to allocate %u bytes for"
  1436. X              " input image\n", myname, in_img_size);
  1437. X    exit(EXIT_FAILURE);
  1438. X    /*NOTREACHED*/
  1439. X    }
  1440. X    if (read(fd, in_img_addr, in_img_size) != in_img_size)
  1441. X    {
  1442. X    (void)fprintf(stderr, "%s: unable to read %u bytes from %s\n",
  1443. X              myname, in_img_size, in_img);
  1444. X    exit(EXIT_FAILURE);
  1445. X    /*NOTREACHED*/
  1446. X    }
  1447. X    (void)close(fd);
  1448. X
  1449. X    /*
  1450. X     * Load input vector field into malloc'ed memory.
  1451. X     */
  1452. X    fd = open(in_vec, O_RDONLY);
  1453. X    if (fd < 0)
  1454. X    {
  1455. X    (void)fprintf(stderr, "%s: unable to open %s: %s\n",
  1456. X              myname, in_vec, strerror(errno));
  1457. X    exit(EXIT_FAILURE);
  1458. X    /*NOTREACHED*/
  1459. X    }
  1460. X    if (fstat(fd, &stbuf) < 0)
  1461. X    {
  1462. X    (void)fprintf(stderr, "%s: unable to stat %s: %s\n",
  1463. X              myname, in_vec, strerror(errno));
  1464. X    exit(EXIT_FAILURE);
  1465. X    /*NOTREACHED*/
  1466. X    }
  1467. X    in_vec_size = stbuf.st_size;
  1468. X    if (size_x * size_y * size_z * sizeof(float) * (size_z == 1 ? 2 : 3)
  1469. X    != in_vec_size)
  1470. X    {
  1471. X    (void)fprintf(stderr, "%s: input vector field size doesn't"
  1472. X              " match %d * x=%d * y=%d * z=%d\n",
  1473. X              myname, (size_z == 1 ? 2 : 3),
  1474. X              size_x, size_y, size_z);
  1475. X    exit(EXIT_FAILURE);
  1476. X    /*NOTREACHED*/
  1477. X    }
  1478. X    in_vec_addr = malloc(in_vec_size);
  1479. X    if (in_vec_addr == NULL)
  1480. X    {
  1481. X    (void)fprintf(stderr, "%s: unable to allocate %u bytes for"
  1482. X              " input vector field\n", myname, in_vec_size);
  1483. X    exit(EXIT_FAILURE);
  1484. X    /*NOTREACHED*/
  1485. X    }
  1486. X    if (read(fd, in_vec_addr, in_vec_size) != in_vec_size)
  1487. X    {
  1488. X    (void)fprintf(stderr, "%s: unable to read %u bytes from %s\n",
  1489. X              myname, in_vec_size, in_vec);
  1490. X    exit(EXIT_FAILURE);
  1491. X    /*NOTREACHED*/
  1492. X    }
  1493. X    (void)close(fd);
  1494. X
  1495. X    /*
  1496. X     * Open output file and allocate space for output image (both in
  1497. X     * memory and on disk).  O_EXCL prevents lic from overwriting a file
  1498. X     * that already exists.
  1499. X     */
  1500. X    out_img_fd = open(out_img, O_CREAT|O_EXCL|O_WRONLY, 0666);
  1501. X    if (out_img_fd < 0)
  1502. X    {
  1503. X    (void)fprintf(stderr, "%s: unable to open %s: %s\n",
  1504. X              myname, out_img, strerror(errno));
  1505. X    exit(EXIT_FAILURE);
  1506. X    /*NOTREACHED*/
  1507. X    }
  1508. X    out_img_size = size_x * size_y * size_z * LIC_ConfiguredPixelSize();
  1509. X    out_img_addr = malloc(out_img_size);
  1510. X    if (out_img_addr == NULL)
  1511. X    {
  1512. X    (void)fprintf(stderr, "%s: unable to allocate %u bytes for"
  1513. X              " output image\n", myname, out_img_size);
  1514. X    exit(EXIT_FAILURE);
  1515. X    /*NOTREACHED*/
  1516. X    }
  1517. X    if (write(out_img_fd, out_img_addr, out_img_size) != out_img_size)
  1518. X    {
  1519. X    (void)fprintf(stderr, "%s: unable to extend %s to %u bytes\n",
  1520. X              myname, out_img, out_img_size);
  1521. X    exit(EXIT_FAILURE);
  1522. X    /*NOTREACHED*/
  1523. X    }
  1524. X    (void)lseek(out_img_fd, (off_t)0, SEEK_SET);
  1525. X}
  1526. X
  1527. X
  1528. Xstatic void
  1529. XUnloadFiles(void)
  1530. X    /*
  1531. X     * Free malloc'ed space used by input files, write output image and
  1532. X     * free up it's malloc'ed memory.
  1533. X     */
  1534. X{
  1535. X    if (write(out_img_fd, out_img_addr, out_img_size) != out_img_size)
  1536. X    (void)fprintf(stderr, "%s: unable to write %u bytes to %s!\n",
  1537. X              myname, out_img_size, out_img);
  1538. X    close(out_img_fd);
  1539. X    free(in_img_addr);
  1540. X    free(in_vec_addr);
  1541. X    free(out_img_addr);
  1542. X}
  1543. X
  1544. X#endif /* HAS_MMAP */
  1545. X
  1546. X
  1547. Xstatic void
  1548. XLicFiles()
  1549. X    /*
  1550. X     * Execute LIC algorithm on arguments.
  1551. X     */
  1552. X{
  1553. X    LIC *lic;
  1554. X
  1555. X    lic = LIC_Create((unsigned char *)in_img_addr, size_i, size_j, size_k,
  1556. X             (float *)        in_vec_addr, size_x, size_y, size_z,
  1557. X             (unsigned char *)out_img_addr,
  1558. X             filter, normalization, normalized,
  1559. X             filter_length,
  1560. X             filter_frequency,
  1561. X             vary_length,
  1562. X             vary_speed && (filter == LIC_Ripple),
  1563. X             default_red, default_green, default_blue, default_alpha,
  1564. X             verbose ? PrintLicStatus : (void (*)(double))NULL,
  1565. X             PrintLicError);
  1566. X    if (lic == (LIC *)NULL)
  1567. X    {
  1568. X    (void)fprintf(stderr, "%s: LIC_Create returned NULL!\n", myname);
  1569. X    return;
  1570. X    }
  1571. X    LIC_ChangePhase(lic, filter_phase);
  1572. X    LIC_ChangeNumThreads(lic, threads);
  1573. X
  1574. X    /*
  1575. X     * Build integral tables here so the build isn't computed as part of the
  1576. X     * time to compute the image.
  1577. X     */
  1578. X    LIC_BuildIntegralTables(lic);
  1579. X
  1580. X    t0 = time(NULL);
  1581. X    t0_clk = times(&t0_tms);
  1582. X    LIC_ComputeImage(lic);
  1583. X    tN_clk = times(&tN_tms);
  1584. X
  1585. X    LIC_Destroy(lic);
  1586. X
  1587. X    if (timing)
  1588. X    {
  1589. X    long   clk_tck = sysconf(_SC_CLK_TCK);
  1590. X#if defined(HAS_OLD_TIMES)
  1591. X        double wall   = (double)(time(NULL) - t0);
  1592. X#else
  1593. X    double wall   = (double)(tN_clk - t0_clk) / clk_tck;
  1594. X#endif
  1595. X    double cpu    = (double)(  tN_tms.tms_utime  - t0_tms.tms_utime
  1596. X                 + tN_tms.tms_cutime - t0_tms.tms_cutime)
  1597. X                /clk_tck;
  1598. X    double ncells = (double)(size_x * size_y * size_z);
  1599. X
  1600. X    if (wall == 0.0)
  1601. X        wall = 1.0e-6;
  1602. X    if (cpu == 0.0)
  1603. X        cpu  = 1.0e-6;
  1604. X    (void)printf("\n"
  1605. X             "Performance statistics\n"
  1606. X             "-------------------------------------------\n"
  1607. X             "Wall time (seconds)              = %.2f\n"
  1608. X             "CPU time (seconds)               = %.2f\n"
  1609. X             "CPU utilization                  = %d%%\n"
  1610. X             "Cells processed per Wall second  = %.2f\n"
  1611. X             "Cells processed per CPU second   = %.2f\n"
  1612. X             "Ave loop count                   = %.2f\n"
  1613. X             "Ave length                       = %.2f\n",
  1614. X             wall,
  1615. X             cpu,
  1616. X             (int)(cpu/wall*100),
  1617. X             ncells/wall,
  1618. X             ncells/cpu,
  1619. X             lic->TotalLoopCount/ncells/2,
  1620. X             lic->TotalLength/ncells/2);
  1621. X    }
  1622. X}
  1623. X
  1624. X
  1625. Xstatic void
  1626. XPrintLicStatus(double PercentDone)
  1627. X    /*
  1628. X     * Output the current LIC progress statistics.  (Only called if verbose
  1629. X     * is TRUE.)
  1630. X     */
  1631. X{
  1632. X    if (PercentDone == 0.0)
  1633. X    (void)printf("%s: %6.2f%% done ...\r", myname, PercentDone);
  1634. X    else
  1635. X    {
  1636. X    /*
  1637. X     * Should really use a smoothed exponentially decaying sample series
  1638. X     * of CPU utilization to predict future CPU utilization to get better
  1639. X     * estimates of completion times.  But, I mean, get real.  This is
  1640. X     * really just a convenience! :-)  So, we cheat and just use CPU
  1641. X     * utilization since the start of the computation to predict future
  1642. X     * CPU ultilization.
  1643. X     */
  1644. X    time_t t  = time(NULL);
  1645. X    time_t tN = t0 + (unsigned int)((double)(t-t0) * 100/PercentDone);
  1646. X    char      *cp = ctime(&tN);
  1647. X    char       cbuf[26];
  1648. X
  1649. X    (void)strcpy(cbuf, cp);
  1650. X    cbuf[24] = '\0';
  1651. X    (void)printf("%s: %6.2f%% done, estimated completion: %s\r",
  1652. X             myname, PercentDone, cbuf);
  1653. X    }
  1654. X    fflush(stdout);
  1655. X}
  1656. X
  1657. X
  1658. Xstatic void
  1659. XPrintLicError(const char *message)
  1660. X    /*
  1661. X     * Print an error reported by the LIC subroutine library.
  1662. X     */
  1663. X{
  1664. X    (void)fprintf(stderr, "%s: LIC library error: %s\n", myname);
  1665. X}
  1666. END_OF_FILE
  1667.   if test 24791 -ne `wc -c <'lic.1.3/lic/lic.c'`; then
  1668.     echo shar: \"'lic.1.3/lic/lic.c'\" unpacked with wrong size!
  1669.   fi
  1670.   # end of 'lic.1.3/lic/lic.c'
  1671. fi
  1672. if test -f 'lic.1.3/test/gl-disp.c' -a "${1}" != "-c" ; then 
  1673.   echo shar: Will not clobber existing file \"'lic.1.3/test/gl-disp.c'\"
  1674. else
  1675.   echo shar: Extracting \"'lic.1.3/test/gl-disp.c'\" \(7984 characters\)
  1676.   sed "s/^X//" >'lic.1.3/test/gl-disp.c' <<'END_OF_FILE'
  1677. X/*
  1678. X * Quick program to display raw rasters on SGI using GL.
  1679. X */
  1680. X
  1681. X
  1682. X#include <stdlib.h>
  1683. X#include <unistd.h>
  1684. X#include <errno.h>
  1685. X#include <fcntl.h>
  1686. X#include <string.h>
  1687. X#include <stdio.h>
  1688. X#include <sys/types.h>
  1689. X#include <sys/stat.h>
  1690. X
  1691. X#include <gl/gl.h>
  1692. X#include <gl/device.h>
  1693. X
  1694. X
  1695. X/*
  1696. X * Use LIC library to snag input raster file pixel format but could just
  1697. X * as easily be specified from the command line.  PIXEL_TYPE should be
  1698. X * MONOCHOROME, RGB, BGR, ARGB, ABGR, RGBA or BGRA.  PIXEL_SIZE should be 1,
  1699. X * 3 or 4 corresponding to the above types.
  1700. X */
  1701. X
  1702. X#include <lic.h>
  1703. X
  1704. X#define    PIXEL_TYPE    LIC_ConfiguredPixelType()
  1705. X#define    PIXEL_SIZE    LIC_ConfiguredPixelSize()
  1706. X
  1707. X
  1708. X/*
  1709. X * Command line arguments.
  1710. X */
  1711. Xstatic char *myname;
  1712. Xstatic char *file;
  1713. Xstatic int   xres, yres, zres;
  1714. X
  1715. X
  1716. X/*
  1717. X * Local routines.
  1718. X */
  1719. Xstatic void           ParseArguments(int argc, char *argv[]);
  1720. Xstatic unsigned char *LoadRaster(char *file, int pixels);
  1721. X
  1722. Xstatic unsigned long *ConvertRaster(unsigned char *raster, int pixels);
  1723. Xstatic void           ConvertRasterMONO(unsigned long *buffer,
  1724. X                    unsigned char *raster, int pixels);
  1725. Xstatic void           ConvertRasterRGB (unsigned long *buffer,
  1726. X                    unsigned char *raster, int pixels,
  1727. X                    int ir, int ig, int ib);
  1728. Xstatic void           ConvertRasterARGB(unsigned long *buffer,
  1729. X                    unsigned char *raster, int pixels,
  1730. X                    int ia, int ir, int ig, int ib);
  1731. X
  1732. Xstatic void           DisplayRaster(unsigned long *buffer,
  1733. X                    int xres, int yres, int zres);
  1734. X
  1735. X
  1736. Xint
  1737. Xmain(int argc, char *argv[])
  1738. X{
  1739. X    unsigned char *raster;
  1740. X    unsigned long *buffer;
  1741. X
  1742. X    ParseArguments(argc, argv);
  1743. X    raster = LoadRaster(file, xres*yres*zres);
  1744. X    buffer = ConvertRaster(raster, xres*yres*zres);
  1745. X    free(raster);
  1746. X    DisplayRaster(buffer, xres, yres, zres);
  1747. X    free(buffer);
  1748. X    exit(0);
  1749. X}
  1750. X
  1751. X
  1752. Xstatic void
  1753. XParseArguments(int argc, char *argv[])
  1754. X    /*
  1755. X     * Grab arguments.
  1756. X     */
  1757. X{
  1758. X    myname = argv[0];
  1759. X    if (argc != 4 && argc != 5)
  1760. X    {
  1761. X    (void)fprintf(stderr, "usage: %s file_name x_res y_res [z_res]\n", myname);
  1762. X    exit(EXIT_FAILURE);
  1763. X    }
  1764. X    file = argv[1];
  1765. X    xres = atoi(argv[2]);
  1766. X    yres = atoi(argv[3]);
  1767. X    if (argc == 4)
  1768. X    zres = 1;
  1769. X    else
  1770. X    zres = atoi(argv[4]);
  1771. X}
  1772. X
  1773. X
  1774. Xstatic unsigned char *
  1775. XLoadRaster(char *file, int pixels)
  1776. X    /*
  1777. X     * Allocate space for input raster, load input raster from file and
  1778. X     * return pointer to loaded raster.
  1779. X     */
  1780. X{
  1781. X    unsigned char *raster;
  1782. X    size_t         raster_size;
  1783. X    int            fd, cc;
  1784. X    struct stat    stbuf;
  1785. X
  1786. X    raster_size = pixels * PIXEL_SIZE;
  1787. X    raster = (unsigned char *)malloc(raster_size);
  1788. X    if (raster == NULL)
  1789. X    {
  1790. X    (void)fprintf(stderr, "%s: unable to allocate memory for raster\n",
  1791. X              myname);
  1792. X    exit(EXIT_FAILURE);
  1793. X    /*NOTREACHED*/
  1794. X    }
  1795. X
  1796. X    fd = open(file, O_RDONLY);
  1797. X    if (fd < 0)
  1798. X    {
  1799. X    (void)fprintf(stderr, "%s: unable to open %s: %s\n",
  1800. X              myname, file, strerror(errno));
  1801. X    exit(EXIT_FAILURE);
  1802. X    /*NOTREACHED*/
  1803. X    }
  1804. X    if (fstat(fd, &stbuf) < 0)
  1805. X    {
  1806. X    (void)fprintf(stderr, "%s: unable to stat %s: %s\n",
  1807. X              myname, file, strerror(errno));
  1808. X    exit(EXIT_FAILURE);
  1809. X    /*NOTREACHED*/
  1810. X    }
  1811. X    if (stbuf.st_size != raster_size)
  1812. X    {
  1813. X    (void)fprintf(stderr, "%s: %s size is %d, not %d * %d = %d\n",
  1814. X              myname, file, (int)stbuf.st_size,
  1815. X              pixels, PIXEL_SIZE, raster_size);
  1816. X    exit(EXIT_FAILURE);
  1817. X    /*NOTREACHED*/
  1818. X    }
  1819. X    cc = read(fd, (void *)raster, raster_size);
  1820. X    if (cc != raster_size)
  1821. X    {
  1822. X    if (cc < 0)
  1823. X        (void)fprintf(stderr, "%s: error reading %s: %s\n",
  1824. X              myname, file, strerror(errno));
  1825. X    else
  1826. X        (void)fprintf(stderr, "%s: incomplete read of %s:"
  1827. X              " only got %d of %d requested\n",
  1828. X              myname, (int)cc, (int)raster_size);
  1829. X    exit(EXIT_FAILURE);
  1830. X    /*NOTREACHED*/
  1831. X    }
  1832. X    (void)close(fd);
  1833. X
  1834. X    return(raster);
  1835. X}
  1836. X
  1837. X
  1838. Xstatic unsigned long *
  1839. XConvertRaster(unsigned char *raster, int pixels)
  1840. X    /*
  1841. X     * Convert raw raster image into SGI ABGR image suitable for lrectwrite.
  1842. X     * Return pointer to converted raster in malloc'ed storage.
  1843. X     */
  1844. X{
  1845. X    unsigned long *buffer;
  1846. X
  1847. X    buffer = (unsigned long *)malloc(pixels * sizeof(long));
  1848. X    if (buffer == NULL)
  1849. X    {
  1850. X    (void)fprintf(stderr, "%s: unable to allocate memory for raster\n",
  1851. X              myname);
  1852. X    exit(EXIT_FAILURE);
  1853. X    /*NOTREACHED*/
  1854. X    }
  1855. X
  1856. X    if (strcmp(PIXEL_TYPE, "MONOCHROME") == 0)
  1857. X    ConvertRasterMONO(buffer, raster, pixels);
  1858. X    else if (strcmp(PIXEL_TYPE, "RGB") == 0)
  1859. X    ConvertRasterRGB(buffer, raster, pixels, 0, 1, 2);
  1860. X    else if (strcmp(PIXEL_TYPE, "BGR") == 0)
  1861. X    ConvertRasterRGB(buffer, raster, pixels, 2, 1, 0);
  1862. X    else if (strcmp(PIXEL_TYPE, "ARGB") == 0)
  1863. X    ConvertRasterARGB(buffer, raster, pixels, 0, 1, 2, 3);
  1864. X    else if (strcmp(PIXEL_TYPE, "ABGR") == 0)
  1865. X    ConvertRasterARGB(buffer, raster, pixels, 0, 3, 2, 1);
  1866. X    else if (strcmp(PIXEL_TYPE, "RGBA") == 0)
  1867. X    ConvertRasterARGB(buffer, raster, pixels, 3, 0, 1, 2);
  1868. X    else if (strcmp(PIXEL_TYPE, "BGRA") == 0)
  1869. X    ConvertRasterARGB(buffer, raster, pixels, 3, 2, 1, 0);
  1870. X    else
  1871. X    {
  1872. X    (void)fprintf(stderr, "%s: unknown pixel type %s\n",
  1873. X              myname, PIXEL_TYPE);
  1874. X    exit(EXIT_FAILURE);
  1875. X    /*NOTREACHED*/
  1876. X    }
  1877. X
  1878. X    return(buffer);
  1879. X}
  1880. X
  1881. X
  1882. Xstatic void
  1883. XConvertRasterMONO(unsigned long *buffer, unsigned char *raster, int pixels)
  1884. X{
  1885. X    int            i;
  1886. X    unsigned char *rp, *bp;
  1887. X
  1888. X    for (i = 0, rp = raster, bp = (unsigned char *)buffer;
  1889. X     i < pixels;
  1890. X     i++, rp += 1, bp += sizeof(long))
  1891. X    {
  1892. X    bp[0] = 255;
  1893. X    bp[1] = rp[0];
  1894. X    bp[2] = rp[0];
  1895. X    bp[3] = rp[0];
  1896. X    }
  1897. X}
  1898. X
  1899. X
  1900. Xstatic void
  1901. XConvertRasterRGB(unsigned long *buffer, unsigned char *raster, int pixels,
  1902. X         int ir, int ig, int ib)
  1903. X{
  1904. X    int            i;
  1905. X    unsigned char *rp, *bp;
  1906. X
  1907. X    for (i = 0, rp = raster, bp = (unsigned char *)buffer;
  1908. X     i < pixels;
  1909. X     i++, rp += 3, bp += sizeof(long))
  1910. X    {
  1911. X    bp[0] = 255;
  1912. X    bp[1] = rp[ib];
  1913. X    bp[2] = rp[ig];
  1914. X    bp[3] = rp[ir];
  1915. X    }
  1916. X}
  1917. X
  1918. X
  1919. Xstatic void
  1920. XConvertRasterARGB(unsigned long *buffer, unsigned char *raster, int pixels,
  1921. X          int ia, int ir, int ig, int ib)
  1922. X{
  1923. X    int            i;
  1924. X    unsigned char *rp, *bp;
  1925. X
  1926. X    for (i = 0, rp = raster, bp = (unsigned char *)buffer;
  1927. X     i < pixels;
  1928. X     i++, rp += 4, bp += sizeof(long))
  1929. X    {
  1930. X    bp[0] = rp[ia];
  1931. X    bp[1] = rp[ib];
  1932. X    bp[2] = rp[ig];
  1933. X    bp[3] = rp[ir];
  1934. X    }
  1935. X}
  1936. X
  1937. X
  1938. Xstatic void
  1939. XDisplayRaster(unsigned long *buffer, int xres, int yres, int zres)
  1940. X    /*
  1941. X     * Display SGI raster and wait for "Q" key to be pressed.  When
  1942. X     * "Q" is pressed, close window and return.
  1943. X     */
  1944. X{
  1945. X    long  winid;
  1946. X    long dev;
  1947. X    short val;
  1948. X
  1949. X    prefsize(xres, yres);
  1950. X    winid = winopen("gl-disp raster display tool");
  1951. X    if (winid == -1)
  1952. X    {
  1953. X    (void)fprintf(stderr, "%s: unable to open a graphics window\n",
  1954. X              myname);
  1955. X    exit(EXIT_FAILURE);
  1956. X    /*NOTREACHED*/
  1957. X    }
  1958. X    RGBmode();
  1959. X    gconfig();
  1960. X    cpack(0);
  1961. X    clear();
  1962. X
  1963. X    qreset();
  1964. X    qdevice(QKEY);
  1965. X    qdevice(ESCKEY);
  1966. X
  1967. X    if (zres == 1)
  1968. X    {
  1969. X    lrectwrite(0, 0, xres-1, yres-1, buffer);
  1970. X    for (;;)
  1971. X    {
  1972. X        dev = qread(&val);
  1973. X        if (dev == REDRAW)
  1974. X        lrectwrite(0, 0, xres-1, yres-1, buffer);
  1975. X        else if (dev == QKEY || dev == ESCKEY)
  1976. X        break;
  1977. X    }
  1978. X    }
  1979. X    else
  1980. X    {
  1981. X    int            paused = FALSE;
  1982. X    unsigned int   isize = xres*yres;
  1983. X    unsigned long *bp = buffer;
  1984. X    unsigned long *ep = buffer + zres*isize;
  1985. X
  1986. X    qdevice(SPACEKEY);
  1987. X    qdevice(NKEY);
  1988. X    qdevice(PKEY);
  1989. X
  1990. X    for (;;)
  1991. X    {
  1992. X        lrectwrite(0, 0, xres-1, yres-1, bp);
  1993. X        if (!paused)
  1994. X        {
  1995. X        bp += isize;
  1996. X        if (bp >= ep)
  1997. X            bp = buffer;
  1998. X        }
  1999. X
  2000. X        while (paused || qtest())
  2001. X        {
  2002. X        dev = qread(&val);
  2003. X        if (val == 0)
  2004. X            continue;
  2005. X        if (dev == REDRAW)
  2006. X            lrectwrite(0, 0, xres-1, yres-1, bp);
  2007. X        else if (dev == QKEY || dev == ESCKEY)
  2008. X            goto out;
  2009. X        else if (dev == SPACEKEY)
  2010. X            paused = !paused;
  2011. X        else if (paused)
  2012. X        {
  2013. X            if (dev == NKEY)
  2014. X            {
  2015. X            bp += isize;
  2016. X            if (bp >= ep)
  2017. X                bp = buffer;
  2018. X            break;
  2019. X            }
  2020. X            else if (dev == PKEY)
  2021. X            {
  2022. X            if (bp == buffer)
  2023. X                bp = ep;
  2024. X            bp -= isize;
  2025. X            break;
  2026. X            }
  2027. X        }
  2028. X        }
  2029. X    }
  2030. X    out:
  2031. X
  2032. X    unqdevice(SPACEKEY);
  2033. X    unqdevice(NKEY);
  2034. X    unqdevice(PKEY);
  2035. X    }
  2036. X
  2037. X    unqdevice(QKEY);
  2038. X    unqdevice(ESCKEY);
  2039. X    qreset();
  2040. X    winclose(winid);
  2041. X}
  2042. END_OF_FILE
  2043.   if test 7984 -ne `wc -c <'lic.1.3/test/gl-disp.c'`; then
  2044.     echo shar: \"'lic.1.3/test/gl-disp.c'\" unpacked with wrong size!
  2045.   fi
  2046.   # end of 'lic.1.3/test/gl-disp.c'
  2047. fi
  2048. echo shar: End of archive 5 \(of 9\).
  2049. cp /dev/null ark5isdone
  2050. MISSING=""
  2051. for I in 1 2 3 4 5 6 7 8 9 ; do
  2052.     if test ! -f ark${I}isdone ; then
  2053.     MISSING="${MISSING} ${I}"
  2054.     fi
  2055. done
  2056. if test "${MISSING}" = "" ; then
  2057.     echo You have unpacked all 9 archives.
  2058.     rm -f ark[1-9]isdone ark[1-9][0-9]isdone
  2059. else
  2060.     echo You still must unpack the following archives:
  2061.     echo "        " ${MISSING}
  2062. fi
  2063. exit 0
  2064. exit 0 # Just in case...
  2065.