int main(int argc, char *argv[]) { int semid, shmid; unsigned short sem_vals[SEM_COUNT]; struct common *shared; // initialize semaphore space union semin semctlarg; // seed random srand((unsigned)time(&t)); if ((semid = semget(IPC_PRIVATE, SEM_COUNT, 0777)) < 0) { perror("semget_main"); exit(EXIT_FAILURE); } // initialize semaphore values sem_vals[S] = S_VAL; sem_vals[SH] = SH_VAL; sem_vals[SC] = SC_VAL; semctlarg.array = sem_vals; // initialize actual semaphores if ((semctl(semid, SEM_COUNT, SETALL, semctlarg)) < 0) { perror("semctl_main_1"); exit(EXIT_FAILURE); } // find memory id for shared if ((shmid = shmget(IPC_PRIVATE, 1*K, 0777)) < 0) { perror("shmget_main"); exit(EXIT_FAILURE); } // get shared memory pointer if ((shared = (struct common *)shmat(shmid, 0, 0)) < 0) { perror("shmat_main"); exit(EXIT_FAILURE); } // initialize shared memory shared->waiting_c = 0; shared->waiting_h = 0; // count number of carb and hydro atoms randomly spawned int carb_count = 0; int hydro_count = 0; // do random execution int i; int ret_val = 0; for (i = 0; i < ATOM_COUNT; i++) { // spawn carbon atom when rand odd int val = rand(); if (val % 2 != 0) { if ((ret_val = fork()) == 0){ carbon(semid, shmid); } else if (ret_val < 0) { perror("fork"); exit(EXIT_FAILURE); } else { carb_count++; } } else { // otherwise, spawn hydrogen atom when rand even if ((ret_val = fork()) == 0) hydrogen(semid, shmid); else if (ret_val < 0){ perror("fork"); exit(EXIT_FAILURE); } else { hydro_count++; } } } // determine number of carbon atoms already satisfied int num_carb_satisfied = hydro_count / 4; // determine hydrogen left over from previous spawn loop int hydro_left_over = hydro_count % 4; // determine number of carbon left to satisfy int num_carb_left = carb_count - num_carb_satisfied; // determine number of hydrogen needed to satisfy all carbons int num_hydro_left = (num_carb_left * 4) - hydro_left_over; // compensate for mis-matched spawning with extra hydrogen for (i = 0; i < num_hydro_left; i++) { printf("Spawning extra hydrogen...\n"); fflush(stdout); // spawn hydrogen atom if ((ret_val = fork()) == 0){ hydrogen(semid, shmid); } else if (ret_val < 0) { perror("fork"); exit(EXIT_FAILURE); } } int total_atom_count = ATOM_COUNT + num_hydro_left; // wait for all atoms to be destroyed, even though science states that's impossible for (i = 0; i < total_atom_count; i++) { fflush(stdout); printf("Waiting for process %d to exit...\n", i); fflush(stdout); if (wait(0) < 0) { perror("wait"); exit(EXIT_FAILURE); } } fflush(stdout); printf("Sequential CH4 making complete. Shared memory and semaphores are being removed.\n"); fflush(stdout); // remove shared memory if (shmctl(shmid, IPC_RMID, 0) < 0) { perror("shmctl_main"); exit(EXIT_FAILURE); } // remove semaphores if (semctl(semid, SEM_COUNT, IPC_RMID, 0) < 0) { perror("semctl_main_2"); exit(EXIT_FAILURE); } fflush(stdout); printf("Exiting sequential CH4 program...\n"); fflush(stdout); return EXIT_SUCCESS; }
int main(int argc, char** argv){ //Setup tolerances for experiments double rtol, atol; rtol = 1e-11; atol = 1e-15; // Create an array of 400 evenly-spaced T values over the // interval[800,1200] K. Output this to disk as the file // Temp.txt Matrix T_values = Linspace(800, 1200, 400, 1); T_values.Write("Temp.txt"); // Create an array of 600 evenly-spaced t values over the // interval[1 sec,48 hours] K. Output this to disk as the file // temp.txt Matrix t_values = Linspace(1, 172800, 600, 1); t_values.Write("time.txt"); // Create a 400 x 600 array that contains C(0.002,t,T). // Output this to disk as the file C2mm.txt //carbon(0.002, t_values(300), T_values(45), rtol, atol); Matrix C2MM(400, 600); for(int i = 0 ; i < T_values.Size(); i++){ for(int j = 0; j < t_values.Size(); j++){ C2MM(i, j) = carbon( 0.002, t_values(j), T_values(i), rtol, atol); } } C2MM.Write("C2mm.txt"); // Create a 400 x 600 array that contains C(0.004,t,T). // Output this to disk as the file C4mm.txt Matrix C4MM(400, 600); for(int i = 0 ; i < T_values.Size(); i++){ for(int j = 0; j < t_values.Size(); j++){ C4MM(i, j) = carbon( 0.004, t_values(j), T_values(i), rtol, atol); } } C4MM.Write("C4mm.txt"); // Create an array of length 600 containing C(0.002,t,800) // Output to disk as the file C2mm_800K.txt . Repeat this // to output the carbon concentrations for 2mm depth at // 900K (C2mm_900K.txt), 1000K (C2mm_1000K.txt), // 1100K (C2mm_24hour.txt), 1200K (C2mm_1200K.txt) Matrix C2mm_800K(600); Matrix C2mm_900K(600); Matrix C2mm_1000K(600); Matrix C2mm_1100K(600); Matrix C2mm_1200K(600); for(int i =0 ; i < 600 ; i++){ C2mm_800K(i) = carbon(0.002, t_values(i), 800, rtol, atol); C2mm_900K(i) = carbon(0.002, t_values(i), 900, rtol, atol); C2mm_1000K(i) = carbon(0.002, t_values(i), 1000, rtol, atol); C2mm_1100K(i) = carbon(0.002, t_values(i), 1100, rtol, atol); C2mm_1200K(i) = carbon(0.002, t_values(i), 1200, rtol, atol); } C2mm_800K.Write("C2mm_800K.txt"); C2mm_900K.Write("C2mm_900K.txt"); C2mm_1000K.Write("C2mm_1000K.txt"); C2mm_1100K.Write("C2mm_24hour.txt"); C2mm_1200K.Write("C2mm_1200K.txt"); // Create an array of length 600 containing C(0.004,t,800) // Output to disk as the file C4mm_800K.txt . Repeat this // to output the carbon concentrations for 2mm depth at // 900K (C4mm_900K.txt), 1000K (C4mm_1000K.txt), // 1100K (C4mm_1100K.txt), 1200K (C4mm_1200K.txt) Matrix C4mm_800K(600); Matrix C4mm_900K(600); Matrix C4mm_1000K(600); Matrix C4mm_1100K(600); Matrix C4mm_1200K(600); for(int i =0 ; i < 600 ; i++){ C4mm_800K(i) = carbon(0.004, t_values(i), 800, rtol, atol); C4mm_900K(i) = carbon(0.004, t_values(i), 900, rtol, atol); C4mm_1000K(i) = carbon(0.004, t_values(i), 1000, rtol, atol); C4mm_1100K(i) = carbon(0.004, t_values(i), 1100, rtol, atol); C4mm_1200K(i) = carbon(0.004, t_values(i), 1200, rtol, atol); } C4mm_800K.Write("C4mm_800K.txt"); C4mm_900K.Write("C4mm_900K.txt"); C4mm_1000K.Write("C4mm_1000K.txt"); C4mm_1100K.Write("C4mm_1100K.txt"); C4mm_1200K.Write("C4mm_1200K.txt"); return 0; }