Advertisement
Guest User

main.c

a guest
Feb 6th, 2021
229
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 15.06 KB | None | 0 0
  1.  
  2.  
  3.  
  4. /*************************************************************************/
  5. /* */
  6. /* Copyright (c) 1994 Stanford University */
  7. /* */
  8. /* All rights reserved. */
  9. /* */
  10. /* Permission is given to use, copy, and modify this software for any */
  11. /* non-commercial purpose as long as this copyright notice is not */
  12. /* removed. All other uses, including redistribution in whole or in */
  13. /* part, are forbidden without prior written permission. */
  14. /* */
  15. /* This software is provided with absolutely no warranty and no */
  16. /* support. */
  17. /* */
  18. /*************************************************************************/
  19.  
  20.  
  21. /*
  22. * NAME
  23. * prt - parallel ray tracer
  24. *
  25. * SYNOPSIS
  26. * prt [options] envfile
  27. *
  28. * -h Print this usage message.
  29. * -a<n> Enable antialiasing with n subpixels (default = 1).
  30. * -m<n> Request n megabytes of global memory (default = 32).
  31. * -p<n> Run on n processors (default = 1).
  32. *
  33. * DESCRIPTION
  34. *
  35. * RETURNS
  36. * PRT returns an exit code of 0 to the OS for successful operation; it
  37. * returns a non-zero exit code (usually 1) if any type of error occurs.
  38. *
  39. * EXAMPLES
  40. * To ray trace cube.env on 1 processor and default global memory size:
  41. *
  42. * prt cube.env
  43. *
  44. * To ray trace car.env on 4 processors and 72MB of global memory:
  45. *
  46. * prt -p4 -m72 car.env
  47. *
  48. * FILES
  49. *
  50. * SEE ALSO
  51. *
  52. * DIAGNOSTICS
  53. * All error messages take the form:
  54. *
  55. * prt: Text of the error message.
  56. *
  57. * All possible error messages are listed below, including the potential
  58. * cause of the error, and the corrective action, if any.
  59. *
  60. * FATAL ERRORS
  61. * Invalid option '%c'.
  62. * The command line included an option which was not
  63. * recognized. Check your command line syntax, remove
  64. * the offending option, and try again.
  65. *
  66. * Cannot open file "filename".
  67. * The specified file could not be found, or some other
  68. * OS error prevented it from being opened. Check your
  69. * typing and try again.
  70. *
  71. * Cannot allocate local memory.
  72. * malloc() failed for some reason.
  73. *
  74. * Cannot allocate global memory.
  75. * malloc(); failed for some reason.
  76. *
  77. * Valid range for #processors is [1, %ld].
  78. * Do not exceed the ranges shown by the message.
  79. *
  80. */
  81.  
  82. #define MAIN /* indicate to rt.H that we need main_env for this file*/
  83. #define VERSION "1.00"
  84.  
  85.  
  86. #include <stdio.h>
  87. #include <math.h>
  88. #include "rt.h"
  89.  
  90.  
  91. #include <sys/time.h>
  92. #include <stdio.h>
  93. #include <stddef.h>
  94.  
  95. static double _roi_time_begin;
  96. static double _roi_time_end;
  97.  
  98.  
  99. CHAR *ProgName = "RAYTRACE"; /* The program name. */
  100. INT nprocs = 1; /* The number of processors to use. */
  101. INT MaxGlobMem = 32; /* Maximum global memory needed (MB).*/
  102. INT NumSubRays = 1; /* Number of subpixel samples to calc*/
  103. INT dostats = 0;
  104.  
  105.  
  106. /*
  107. * NAME
  108. * Usage - print proper usage message
  109. *
  110. * SYNOPSIS
  111. * VOID Usage()
  112. *
  113. * RETURNS
  114. * Nothing.
  115. */
  116.  
  117. VOID Usage()
  118. {
  119. fprintf(stdout, "%s - parallel ray tracer\n", ProgName);
  120. fprintf(stdout, "Version %s\n\n", VERSION);
  121.  
  122. fprintf(stdout, "Usage:\t%s [options] envfile\n\n", ProgName);
  123.  
  124. fprintf(stdout, "\t-h\tPrint this usage message.\n");
  125. fprintf(stdout, "\t-a<n>\tEnable antialiasing with n subpixels (default = 1).\n\tWhen using with SPLASH suite for evaluation, use default (no antialiasing)\n");
  126. fprintf(stdout, "\t-m<n>\tRequest n megabytes of global memory (default = 32).\n");
  127. fprintf(stdout, "\t-p<n>\tRun on n processors (default = 1).\n");
  128. fprintf(stdout, "\t-s\tMeasure and print per-process timing information.\n");
  129. fprintf(stdout, "\n");
  130. }
  131.  
  132.  
  133.  
  134. /*
  135. * NAME
  136. * PrintStatistics - print out various ray tracer statistics
  137. *
  138. * SYNOPSIS
  139. * VOID PrintStatistics()
  140. *
  141. * RETURNS
  142. * Nothing.
  143. */
  144.  
  145. VOID PrintStatistics()
  146. {
  147. /*
  148. printf("\n****** Ray trace Stats ******\n");
  149.  
  150. printf("\tResolution:\t\t%ld by %ld\n", Display.xres+1, Display.yres+1);
  151. printf("\tNumber Lights:\t\t%ld\n", nlights);
  152. printf("\tAnti level:\t\t%ld\n", Display.maxAAsubdiv);
  153. printf("\tTotal Rays:\t\t%ld\n", Stats.total_rays);
  154. printf("\tPrimary Rays:\t\t%ld\n", Stats.prim_rays);
  155. printf("\tShadow Rays:\t\t%ld\n", Stats.shad_rays);
  156. printf("\tShadow Rays Hit:\t%ld\n", Stats.shad_rays_hit);
  157. printf("\tShadow Rays Not Hit:\t%ld\n", Stats.shad_rays_not_hit);
  158. printf("\tShadow Coherence Rays:\t%ld\n", Stats.shad_coherence_rays);
  159. printf("\tReflective Rays:\t%ld\n", Stats.refl_rays);
  160. printf("\tTransmissiveRays:\t%ld\n", Stats.trans_rays);
  161. printf("\tAnti-Aliasing Rays:\t%ld\n", Stats.aa_rays);
  162. printf("\tBackground Pixels:\t%ld\n", Stats.coverage);
  163. printf("\tMax Tree depth reached:\t%ld\n", Stats.max_tree_depth);
  164. printf("\tMax # prims tested for a ray:\t%ld\n", Stats.max_objs_ray);
  165. printf("\tMax Rays shot for a pixel:\t%ld\n", Stats.max_rays_pixel);
  166. printf("\tMax # prims tested for a pixel:\t%ld\n", Stats.max_objs_pixel);
  167. printf("\n");
  168. */
  169.  
  170. if (TraversalType == TT_HUG)
  171. {
  172. /* prn_ds_stats();
  173. prn_tv_stats(); */
  174. ma_print();
  175. }
  176. }
  177.  
  178.  
  179.  
  180. /*
  181. * NAME
  182. * StartRayTrace - starting point for all ray tracing proceses
  183. *
  184. * SYNOPSIS
  185. * VOID StartRayTrace()
  186. *
  187. * RETURNS
  188. * Nothing.
  189. */
  190.  
  191. VOID StartRayTrace()
  192. {
  193. INT pid; /* Our internal process id number. */
  194. UINT begin;
  195. UINT end;
  196. UINT lapsed;
  197.  
  198.  
  199. {pthread_mutex_lock(&(gm->pidlock));}
  200. pid = gm->pid++;
  201. {pthread_mutex_unlock(&(gm->pidlock));}
  202.  
  203. if ((pid == 0) || (dostats))
  204. {
  205.  
  206. struct timeval FullTime;
  207.  
  208.  
  209.  
  210. gettimeofday(&FullTime, NULL);
  211.  
  212. (begin) = (unsigned long)(FullTime.tv_usec + FullTime.tv_sec * 1000000);
  213.  
  214. };
  215.  
  216. /* POSSIBLE ENHANCEMENT: Here's where one might lock processes down
  217. to processors if need be */
  218.  
  219. InitWorkPool(pid);
  220. InitRayTreeStack(Display.maxlevel, pid);
  221.  
  222. /*
  223. * Wait for all processes to be created, initialize their work
  224. * pools, and arrive at this point; then proceed. This barrier
  225. * is absolutely required. Read comments in PutJob before
  226. * moving this barrier.
  227. */
  228.  
  229. {
  230.  
  231. unsigned long Error, Cycle;
  232.  
  233. int Cancel, Temp;
  234.  
  235.  
  236.  
  237. Error = pthread_mutex_lock(&(gm->start).mutex);
  238.  
  239. if (Error != 0) {
  240.  
  241. printf("Error while trying to get lock in barrier.\n");
  242.  
  243. exit(-1);
  244.  
  245. }
  246.  
  247.  
  248.  
  249. Cycle = (gm->start).cycle;
  250.  
  251. if (++(gm->start).counter != (gm->nprocs)) {
  252.  
  253. pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &Cancel);
  254.  
  255. while (Cycle == (gm->start).cycle) {
  256.  
  257. Error = pthread_cond_wait(&(gm->start).cv, &(gm->start).mutex);
  258.  
  259. if (Error != 0) {
  260.  
  261. break;
  262.  
  263. }
  264.  
  265. }
  266.  
  267. pthread_setcancelstate(Cancel, &Temp);
  268.  
  269. } else {
  270.  
  271. (gm->start).cycle = !(gm->start).cycle;
  272.  
  273. (gm->start).counter = 0;
  274.  
  275. Error = pthread_cond_broadcast(&(gm->start).cv);
  276.  
  277. }
  278.  
  279. pthread_mutex_unlock(&(gm->start).mutex);
  280.  
  281. }
  282.  
  283. /* POSSIBLE ENHANCEMENT: Here's where one would RESET STATISTICS
  284. and TIMING if one wanted to measure only the parallel part */
  285.  
  286. RayTrace(pid);
  287.  
  288.  
  289. if ((pid == 0) || (dostats)) {
  290. {
  291.  
  292. struct timeval FullTime;
  293.  
  294.  
  295.  
  296. gettimeofday(&FullTime, NULL);
  297.  
  298. (end) = (unsigned long)(FullTime.tv_usec + FullTime.tv_sec * 1000000);
  299.  
  300. };
  301. gm->partime[pid] = (end - begin) & 0x7FFFFFFF;
  302. if (pid == 0) gm->par_start_time = begin;
  303. }
  304. }
  305.  
  306.  
  307.  
  308. /*
  309. * NAME
  310. * main - mainline for the program
  311. *
  312. * SYNOPSIS
  313. * INT main(argc, argv)
  314. * INT argc;
  315. * CHAR *argv[];
  316. *
  317. * DESCRIPTION
  318. * Main parses command line arguments, opens/closes the files involved,
  319. * performs initializations, reads in the model database, partitions it
  320. * as needed, and calls StartTraceRay() to do the work.
  321. *
  322. * RETURNS
  323. * 0 if successful.
  324. * 1 for any type of failure.
  325. */
  326.  
  327. int main(argc, argv)
  328. int argc;
  329. CHAR *argv[];
  330. {
  331. INT i;
  332. UINT begin;
  333. UINT end;
  334. UINT lapsed;
  335. U16 tmp;
  336. CHAR *pch;
  337. MATRIX vtrans, Vinv; /* View transformation and inverse. */
  338.  
  339. #ifdef ENABLE_PARSEC_HOOKS
  340. __parsec_bench_begin (__splash2_raytrace);
  341. #endif
  342.  
  343. /*
  344. * First, process command line arguments.
  345. */
  346.  
  347. while (argc-- > 1 && (*++argv)[0] == '-')
  348. for (pch = argv[0] + 1; *pch != '\0'; pch++)
  349. switch (*pch)
  350. {
  351. case '?':
  352. case 'h':
  353. case 'H':
  354. Usage();
  355. exit(1);
  356.  
  357. case 'a':
  358. case 'A':
  359. AntiAlias = TRUE;
  360. if (*++pch)
  361. NumSubRays = atoi(pch);
  362.  
  363. *pch = '\0';
  364. pch--;
  365. break;
  366.  
  367. case 'm':
  368. if (*++pch)
  369. MaxGlobMem = atoi(pch);
  370.  
  371. *pch = '\0';
  372. pch--;
  373. break;
  374.  
  375. case 'p':
  376. if (*++pch)
  377. nprocs = atoi(pch);
  378.  
  379. *pch = '\0';
  380. pch--;
  381. break;
  382.  
  383. case 's':
  384. case 'S':
  385. dostats = TRUE;
  386. break;
  387.  
  388. default:
  389. fprintf(stderr, "%s: Invalid option \'%c\'.\n", ProgName, *pch);
  390. exit(1);
  391. }
  392.  
  393.  
  394. /*
  395. * If no more command line arguments, the environment file name
  396. * is missing. Print a usage message and terminate.
  397. */
  398.  
  399. if (!argc)
  400. {
  401. Usage();
  402. exit(1);
  403. }
  404.  
  405.  
  406. /*
  407. * Make sure nprocs is within valid range.
  408. */
  409.  
  410. if (nprocs < 1 || nprocs > MAX_PROCS)
  411. {
  412. fprintf(stderr, "%s: Valid range for #processors is [1, %ld].\n", ProgName, MAX_PROCS);
  413. exit(1);
  414. }
  415.  
  416.  
  417. /*
  418. * Print command line parameters.
  419. */
  420.  
  421. printf("\n");
  422. printf("Number of processors: \t%ld\n", nprocs);
  423. printf("Global shared memory size:\t%ld MB\n", MaxGlobMem);
  424. printf("Samples per pixel: \t%ld\n", NumSubRays);
  425. printf("\n");
  426.  
  427.  
  428. /*
  429. * Initialize the shared memory environment and request the total
  430. * amount of amount of shared memory we might need. This
  431. * includes memory for the database, grid, and framebuffer.
  432. */
  433.  
  434. MaxGlobMem <<= 20; /* Convert MB to bytes. */
  435. {;}
  436. gm = (GMEM *)malloc(sizeof(GMEM));;
  437.  
  438.  
  439. /*
  440. * Perform shared environment initializations.
  441. */
  442.  
  443. gm->nprocs = nprocs;
  444. gm->pid = 0;
  445. gm->rid = 1;
  446.  
  447. {
  448.  
  449. unsigned long Error;
  450.  
  451.  
  452.  
  453. Error = pthread_mutex_init(&(gm->start).mutex, NULL);
  454.  
  455. if (Error != 0) {
  456.  
  457. printf("Error while initializing barrier.\n");
  458.  
  459. exit(-1);
  460.  
  461. }
  462.  
  463.  
  464.  
  465. Error = pthread_cond_init(&(gm->start).cv, NULL);
  466.  
  467. if (Error != 0) {
  468.  
  469. printf("Error while initializing barrier.\n");
  470.  
  471. pthread_mutex_destroy(&(gm->start).mutex);
  472.  
  473. exit(-1);
  474.  
  475. }
  476.  
  477.  
  478.  
  479. (gm->start).counter = 0;
  480.  
  481. (gm->start).cycle = 0;
  482.  
  483. }
  484. {pthread_mutex_init(&(gm->pidlock), NULL);}
  485. {pthread_mutex_init(&(gm->ridlock), NULL);}
  486. {pthread_mutex_init(&(gm->memlock), NULL);}
  487. {
  488.  
  489. unsigned long i, Error;
  490.  
  491.  
  492.  
  493. for (i = 0; i < nprocs; i++) {
  494.  
  495. Error = pthread_mutex_init(&gm->wplock[i], NULL);
  496.  
  497. if (Error != 0) {
  498.  
  499. printf("Error while initializing array of locks.\n");
  500.  
  501. exit(-1);
  502.  
  503. }
  504.  
  505. }
  506.  
  507. }
  508.  
  509. /* POSSIBLE ENHANCEMENT: Here is where one might distribute the
  510. raystruct data structure across physically distributed memories as
  511. desired. */
  512.  
  513. if (!GlobalHeapInit(MaxGlobMem))
  514. {
  515. fprintf(stderr, "%s: Cannot initialize global heap.\n", ProgName);
  516. exit(1);
  517. }
  518.  
  519.  
  520. /*
  521. * Initialize HUG parameters, read environment and geometry files.
  522. */
  523.  
  524. Huniform_defaults();
  525. ReadEnvFile(*argv);
  526. ReadGeoFile(GeoFileName);
  527. OpenFrameBuffer();
  528.  
  529.  
  530. /*
  531. * Compute view transform and its inverse.
  532. */
  533.  
  534. CreateViewMatrix();
  535. MatrixCopy(vtrans, View.vtrans);
  536. MatrixInverse(Vinv, vtrans);
  537. MatrixCopy(View.vtransInv, Vinv);
  538.  
  539.  
  540. /*
  541. * Print out what we have so far.
  542. */
  543.  
  544. printf("Number of primitive objects: \t%ld\n", prim_obj_cnt);
  545. printf("Number of primitive elements:\t%ld\n", prim_elem_cnt);
  546.  
  547. /*
  548. * Preprocess database into hierarchical uniform grid.
  549. */
  550.  
  551. if (TraversalType == TT_HUG)
  552. BuildHierarchy_Uniform();
  553.  
  554.  
  555.  
  556. /*
  557. * Now create slave processes.
  558. */
  559.  
  560. fflush(NULL);
  561. struct timeval _t_start;
  562. gettimeofday(&_t_start, NULL);
  563. _roi_time_begin = (double)_t_start.tv_sec + (double)_t_start.tv_usec * 1e-6;
  564.  
  565.  
  566. {
  567.  
  568. struct timeval FullTime;
  569.  
  570.  
  571.  
  572. gettimeofday(&FullTime, NULL);
  573.  
  574. (begin) = (unsigned long)(FullTime.tv_usec + FullTime.tv_sec * 1000000);
  575.  
  576. }
  577. //for (i = 0; i < gm->nprocs - 1; i++)
  578. {
  579.  
  580. long i, Error;
  581.  
  582.  
  583.  
  584. for (i = 0; i < (gm->nprocs) - 1; i++) {
  585.  
  586. Error = pthread_create(&PThreadTable[i], NULL, (void * (*)(void *))(StartRayTrace), NULL);
  587.  
  588. if (Error != 0) {
  589.  
  590. printf("Error in pthread_create().\n");
  591.  
  592. exit(-1);
  593.  
  594. }
  595.  
  596. }
  597.  
  598.  
  599.  
  600. StartRayTrace();
  601.  
  602. }
  603.  
  604. //StartRayTrace();
  605.  
  606. {
  607.  
  608. unsigned long i, Error;
  609.  
  610. for (i = 0; i < (gm->nprocs) - 1; i++) {
  611.  
  612. Error = pthread_join(PThreadTable[i], NULL);
  613.  
  614. if (Error != 0) {
  615.  
  616. printf("Error in pthread_join().\n");
  617.  
  618. exit(-1);
  619.  
  620. }
  621.  
  622. }
  623.  
  624. }
  625. {
  626.  
  627. struct timeval FullTime;
  628.  
  629.  
  630.  
  631. gettimeofday(&FullTime, NULL);
  632.  
  633. (end) = (unsigned long)(FullTime.tv_usec + FullTime.tv_sec * 1000000);
  634.  
  635. }
  636.  
  637. struct timeval _t_end;
  638. gettimeofday(&_t_end, NULL);
  639. _roi_time_end = (double)_t_end.tv_sec + (double)_t_end.tv_usec * 1e-6;
  640. printf("ROI time measured: %.3fs\n", _roi_time_end - _roi_time_begin);
  641. fflush(NULL);
  642.  
  643.  
  644.  
  645.  
  646. /*
  647. * We are finished. Clean up, print statistics and run time.
  648. */
  649.  
  650. CloseFrameBuffer(PicFileName);
  651. PrintStatistics();
  652.  
  653. lapsed = (end - begin) & 0x7FFFFFFF;
  654.  
  655.  
  656.  
  657. printf("TIMING STATISTICS MEASURED BY MAIN PROCESS:\n");
  658. printf(" Overall start time %20lu\n", begin);
  659. printf(" Overall end time %20lu\n", end);
  660. printf(" Total time with initialization %20lu\n", lapsed);
  661. printf(" Total time without initialization %20lu\n", end - gm->par_start_time);
  662.  
  663. if (dostats) {
  664. unsigned totalproctime, maxproctime, minproctime;
  665.  
  666. printf("\n\n\nPER-PROCESS STATISTICS:\n");
  667.  
  668. printf("%20s%20s\n","Proc","Time");
  669. printf("%20s%20s\n\n","","Tracing Rays");
  670. for (i = 0; i < gm->nprocs; i++)
  671. printf("%20d%20d\n",i,gm->partime[i]);
  672.  
  673. totalproctime = gm->partime[0];
  674. minproctime = gm->partime[0];
  675. maxproctime = gm->partime[0];
  676.  
  677. for (i = 1; i < gm->nprocs; i++) {
  678. totalproctime += gm->partime[i];
  679. if (gm->partime[i] > maxproctime)
  680. maxproctime = gm->partime[i];
  681. if (gm->partime[i] < minproctime)
  682. minproctime = gm->partime[i];
  683. }
  684. printf("\n\n%20s%20d\n","Max = ",maxproctime);
  685. printf("%20s%20d\n","Min = ",minproctime);
  686. printf("%20s%20d\n","Avg = ",(int) (((double) totalproctime) / ((double) (1.0 * gm->nprocs))));
  687. }
  688.  
  689. {exit(0);}
  690.  
  691. #ifdef ENABLE_PARSEC_HOOKS
  692. __parsec_bench_end();
  693. #endif
  694. }
  695.  
  696.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement