00001
00013 #include "proc.h"
00014 #include "mmu.h"
00015 #include "io_device.h"
00016 #include <string.h>
00017 #include <math.h>
00018
00019
00026 #define LOOP_ITERATIONS 8
00027
00032 #define SIZE_OF_ITEM 10
00033
00039 uint16_t *reference_string;
00040
00045 int reference_count;
00046
00047
00054 #define DSS(p) (((proc_table[p]))->page_count*mmu.page_size)
00055
00062 #define MEM_ACCESS_PROBABILITY(n) (proc_table[n]->percentile)
00063
00069 #define WAIT_FOR_IO_TO_COMPLETE(n) do { \
00070 pthread_mutex_lock(&proc_table[n]->io_lock);\
00071 pthread_cond_wait(&proc_table[n]->io_cond, &proc_table[n]->io_lock);\
00072 pthread_mutex_unlock(&proc_table[n]->io_lock); \
00073 } while (0)
00074
00079 int temporal_locality = 30;
00080
00087 static int only_read_allowed;
00088
00095 proc_t **proc_table;
00096
00102 int max_proc;
00103
00104
00113 static int
00114 simulate_loop(int procnum)
00115 {
00116 int rw, i;
00117 uint32_t addr;
00118
00119 addr = bounded_rand(0, DSS(procnum)-LOOP_ITERATIONS*SIZE_OF_ITEM);
00120 for (i=0; i<LOOP_ITERATIONS; i++) {
00121 rw = only_read_allowed ? 0 : (bounded_rand(0, 100) > 50 ? 1 : 0);
00122 if (memory_access(procnum, addr + (i*SIZE_OF_ITEM), rw) == (uint32_t) - 1)
00123 return 0;
00124 }
00125 return 1;
00126 }
00127
00128
00138 static int
00139 random_access(int procnum)
00140 {
00141 uint32_t addr;
00142 int rw;
00143
00144 if (proc_table[procnum]->last_address == (uint32_t) -1)
00145
00146
00147
00148
00149
00150 addr = bounded_rand(0, DSS(procnum));
00151 else {
00152 if (bounded_rand(0, 100) <= temporal_locality) {
00153 addr = proc_table[procnum]->last_address+1024;
00154 if (addr > DSS(procnum))
00155 addr = proc_table[procnum]->last_address;
00156 } else
00157 addr = bounded_rand(0, DSS(procnum));
00158 }
00159 proc_table[procnum]->last_address = addr;
00160
00161 rw = only_read_allowed ? 0 : (bounded_rand(0, 100) > 50 ? 1 : 0);
00162 return (memory_access(procnum, addr, rw) != (uint32_t) - 1);
00163 }
00164
00165
00177 static void *
00178 thread_proc(int procnum)
00179 {
00180 int condition = 1, reference_item = 0;
00181
00182 fprintf(LOG_FILE(procnum), "INIZIO PROCESSO\n======================\n"
00183 "PID = %d\nPAGINE VIRTUALI = %d\nPROBABILITA' = %.0f%%\n"
00184 "======================\n", procnum, proc_table[procnum]->page_count,
00185 proc_table[procnum]->percentile);
00186
00187 while (condition) {
00188
00189
00190
00191
00192
00193
00194 if (reference_string) {
00195 uint32_t addr;
00196
00197 if (reference_item >= reference_count)
00198 reference_item = 0;
00199 addr = reference_string[reference_item++];
00200 addr *= mmu.page_size;
00201 if (memory_access(procnum, addr, 0) == (uint32_t) -1)
00202 condition = 0;
00203 } else {
00204 if (bounded_rand(0, 100) <= MEM_ACCESS_PROBABILITY(procnum)) {
00205
00206
00207
00208
00209
00210
00211 if (bounded_rand(0, 100) <= 30)
00212 condition = simulate_loop(procnum);
00213 else
00214 condition = random_access(procnum);
00215 } else {
00216
00217
00218
00219
00220 if (io_device_read(procnum))
00221 WAIT_FOR_IO_TO_COMPLETE(procnum);
00222 else
00223 condition = 0;
00224 }
00225 }
00226 }
00227
00228 pthread_exit(NULL);
00229 }
00230
00231
00253 void
00254 proc_init(int num, int percentile, int only_read, int max_memory, char *pl, int lp)
00255 {
00256 char proc_filename[FILENAME_MAX];
00257 int *probs = NULL;
00258 int i, j;
00259
00260 temporal_locality = lp;
00261 only_read_allowed = only_read;
00262 max_proc = num;
00263
00264
00265
00266
00267
00268
00269 if (pl) {
00270 char *ap, *ppl;
00271
00272 probs = XMALLOC(int, max_proc);
00273 for (i=0; i<max_proc; i++)
00274 probs[i] = percentile;
00275 for (i=0, ppl = pl; (ap = strsep(&ppl, ":")) != NULL; ) {
00276 if (*ap != '\0') {
00277 probs[i++] = atof(ap)*100;
00278 }
00279 }
00280 }
00281
00282
00283
00284
00285
00286
00287
00288
00289 proc_table = XMALLOC(proc_t *, max_proc);
00290 for (i = 0; i < max_proc; i++) {
00291 snprintf(proc_filename, FILENAME_MAX, "PROC_%02d.log", i);
00292 proc_table[i] = XMALLOC(proc_t, 1);
00293 proc_table[i]->pid = i;
00294 if (reference_string)
00295 proc_table[i]->page_count = reference_count;
00296 else
00297 proc_table[i]->page_count = max_memory?exp2(mmu.page_bits):bounded_rand(1, exp2(mmu.page_bits));
00298 proc_table[i]->percentile = probs?((i<max_proc)?probs[i]:percentile):percentile;
00299 proc_table[i]->log_file = fopen(proc_filename, "w");
00300 proc_table[i]->stats.mem_accesses = proc_table[i]->stats.page_faults = 0;
00301 proc_table[i]->stats.io_requests = proc_table[i]->stats.time_elapsed = 0;
00302 proc_table[i]->last_address = (uint32_t) -1;
00303 pthread_cond_init(&proc_table[i]->io_cond, NULL);
00304 pthread_mutex_init(&proc_table[i]->io_lock, NULL);
00305
00306
00307
00308
00309
00310
00311
00312 proc_table[i]->page_table = XMALLOC(page_t, proc_table[i]->page_count);
00313 for (j = 0; j < proc_table[i]->page_count; j++) {
00314 proc_table[i]->page_table[j].id = j;
00315 proc_table[i]->page_table[j].frame_id = (uint16_t) -1;
00316 proc_table[i]->page_table[j].present = 0;
00317 proc_table[i]->page_table[j].reference = 0;
00318 proc_table[i]->page_table[j].dirty = 0;
00319 }
00320 }
00321
00322
00323
00324 for (i = 0; i < max_proc; i++)
00325 pthread_create(&proc_table[i]->tid, NULL, (thread_fn_t) & thread_proc, (void *) i);
00326 printf("--> Thread PROC avviati [NUM=%d, PROB=%d%%, OPER=%s, LOCALITY=%d%%]\n",
00327 max_proc, pl?0:percentile, only_read_allowed?"R":"RW", temporal_locality);
00328 }
00329
00330
00338 void process_info(int procnum)
00339 {
00340 proc_t *proc = proc_table[procnum];
00341 int i;
00342
00343 for (i = 0; i < proc->page_count; i++) {
00344 fprintf(proc->log_file, " PAGE %2d : ", i);
00345 if (IS_PAGE_PRESENT(proc->page_table[i])) {
00346 unsigned int frame_id = FRAME_ID(proc->page_table[i]);
00347 fprintf(proc->log_file, "FRAME %2d ", frame_id);
00348 if (IS_PAGE_REFERENCED(proc->page_table[i]))
00349 fprintf(proc->log_file, "[REF");
00350 else
00351 fprintf(proc->log_file, "[NOT REF");
00352 if (IS_PAGE_DIRTY(proc->page_table[i]))
00353 fprintf(proc->log_file, ", DIRTY]\n");
00354 else
00355 fprintf(proc->log_file, "]\n");
00356 } else
00357 fprintf(proc->log_file, "\n");
00358 }
00359 fprintf(proc->log_file, "============================================\n");
00360 }
00361