Mercurial > repos > rhope
view saveload.c @ 121:1af91ceaaf49
Fixed memory leak when an output is only attached to a single null input
author | Mike Pavone <pavone@retrodev.com> |
---|---|
date | Thu, 28 Oct 2010 21:04:12 -0400 |
parents | 76568becd6d6 |
children |
line wrap: on
line source
#include "interp.h" #include "structs.h" #include <stdio.h> #include <string.h> #include <stdlib.h> /* void save_program(char * filename) { worker * aworkerlist; wire * awirelist; FILE * savefile; int def_num, version = 1; savefile = fopen(filename, "wb"); if(!savefile) return; //deflist[current_def].num_workers = num_workers; //deflist[current_def].num_wires = num_wires; fwrite(&version, 4, 1, savefile); fwrite(&num_defs, 4, 1, savefile); fwrite(deflist, sizeof(worker_def), num_defs, savefile); for(def_num = 0; def_num < num_defs; ++def_num) { if(deflist[def_num].workerlist) { fwrite(&def_num, 4, 1, savefile); //fwrite(&(deflist[def_num].num_workers), 4, 1, savefile); fwrite(deflist[def_num].workerlist, sizeof(worker), deflist[def_num].num_workers, savefile); //fwrite(&(deflist[def_num].num_wires), 4, 1, savefile); fwrite(deflist[def_num].wirelist, sizeof(wire), deflist[def_num].num_wires, savefile); } } def_num = -1; fwrite(&def_num, 4, 1, savefile); fclose(savefile); }*/ program * new_program(int def_storage, int comp_storage) { defchunk * defs = malloc(sizeof(defchunk) + (def_storage - 1) * sizeof(worker_def)); program * prog = malloc(sizeof(program)); defs->num_defs = 0; defs->deflist[0].name = NULL; defs->defs_storage = def_storage; defs->next = NULL; prog->current = prog->defs = defs; //prog->deflist = malloc(sizeof(worker_def) * def_storage); //prog->num_defs = 0; //prog->defs_storage = def_storage; prog->companylist = malloc(sizeof(company) * comp_storage); prog->num_companies = 0; prog->companies_storage = comp_storage; prog->refcount = 1; VIS_InitializeCriticalSection(prog->lock); return prog; } int count_defs(defchunk * chunk) { int total = 0; while(chunk) { total += chunk->num_defs; chunk = chunk->next; } return total; } void save_program(program * prog, char * filename) { int version = 2; int total_bytes = 0; int zero = 0; int i; int num_defs; unsigned char size; custom_worker * aworker; //worker_def * deflist = prog->deflist; defchunk * defs = prog->defs; defchunk * current = defs; worker_def * deflist; FILE * savefile; savefile = fopen(filename, "wb"); fwrite(&version, 4, 1, savefile); num_defs = count_defs(defs); fwrite(&(num_defs), 4, 1, savefile); while(current) { deflist = current->deflist; for(i = 0; i < current->num_defs; ++i) { size = strlen(deflist[i].name); fwrite(&size, 1, 1, savefile); fwrite(deflist[i].name, 1, size, savefile); total_bytes += (int)size + 1; } current = current->next; } if(total_bytes % 4 != 0)// pad to a 4 byte boundary fwrite(&zero, 1, 4-(total_bytes % 4), savefile); current = defs; while(current) { deflist = current->deflist; for(i = 0; i < current->num_defs; ++i) { if(deflist[i].type & USER_FLAG) { fwrite(&i, sizeof(int), 1, savefile); fwrite(&(deflist[i].num_inputs), sizeof(short), 1, savefile); fwrite(&(deflist[i].num_outputs), sizeof(short), 1, savefile); fwrite(&(deflist[i].type), sizeof(short), 1, savefile); fwrite(deflist[i].input_types, sizeof(short), deflist[i].num_inputs, savefile); fwrite(deflist[i].output_types, sizeof(short), deflist[i].num_outputs, savefile); total_bytes += sizeof(int) + (sizeof(short) * (3+deflist[i].num_inputs+deflist[i].num_outputs)); if(total_bytes % 4 != 0)// pad to a 4 byte boundary fwrite(&zero, 1, 4-(total_bytes % 4), savefile); if((deflist[i].type & TYPE_MASK) == WORKER_TYPE) { aworker = deflist[i].implement_func; fwrite(&(aworker->num_workers), sizeof(int), 1, savefile); fwrite(aworker->workerlist, sizeof(worker), aworker->num_workers, savefile); fwrite(&(aworker->num_wires), sizeof(int), 1, savefile); fwrite(aworker->wirelist, sizeof(wire), aworker->num_wires, savefile); } } } current = current->next; } i = -1; fwrite(&i, sizeof(int), 1, savefile); fclose(savefile); } program * load_program(char * filename) { custom_worker * aworker; int version; int i,j; int * def_lookup; char name[256]; int total_bytes; int file_defs; unsigned char name_size; FILE * loadfile; char * code; int size; program * prog; loadfile = fopen(filename, "rb"); if(!loadfile) { puts("Error: Could not open file"); fflush(stdout); return NULL; } if(!strcmp(strrchr(filename,'.')+1, "vis")) { //TODO: Fixme /*fread(&version, 4, 1, loadfile); if(version != 2) { puts("Error: Can't read files of this version."); return NULL; } fread(&file_defs, 4, 1, loadfile); def_lookup = malloc(sizeof(int) * file_defs); total_bytes = 0; prog = new_program(file_defs, START_COMP_STORAGE); initworkers(prog); for(i = 0; i < file_defs; ++i) { fread(&name_size, 1, 1, loadfile); fread(name, 1, name_size, loadfile); name[name_size] = '\0'; total_bytes += (int)name_size + 1; for(j = 0; j < prog->num_defs; ++j) { if(!strcmp(name, prog->deflist[j].name)) { def_lookup[i] = j; break; } } if(j >= prog->num_defs) //couldn't find it in the list { def_lookup[i] = prog->num_defs; prog->deflist[prog->num_defs].name = malloc(name_size+1); strcpy(prog->deflist[prog->num_defs].name, name); ++prog->num_defs; } } if(total_bytes % 4 != 0)// pad to a 4 byte boundary fread(&i, 1, 4-(total_bytes % 4), loadfile); do { fread(&i, sizeof(int), 1, loadfile); if(i >= 0) { i = def_lookup[i]; fread(&(prog->deflist[i].num_inputs), sizeof(short), 1, loadfile); fread(&(prog->deflist[i].num_outputs), sizeof(short), 1, loadfile); fread(&(prog->deflist[i].type), sizeof(short), 1, loadfile); prog->deflist[i].input_types = malloc(sizeof(short) * (prog->deflist[i].num_inputs + prog->deflist[i].num_outputs)); prog->deflist[i].output_types = prog->deflist[i].input_types + prog->deflist[i].num_inputs; fread(prog->deflist[i].input_types, sizeof(short), prog->deflist[i].num_inputs, loadfile); fread(prog->deflist[i].output_types, sizeof(short), prog->deflist[i].num_outputs, loadfile); total_bytes += sizeof(int) + (sizeof(short) * (3+prog->deflist[i].num_inputs+prog->deflist[i].num_outputs)); if(total_bytes % 4 != 0)// pad to a 4 byte boundary fread(&j, 1, 4-(total_bytes % 4), loadfile); if((prog->deflist[i].type & TYPE_MASK) == WORKER_TYPE) { aworker = malloc(sizeof(custom_worker)); prog->deflist[i].implement_func = aworker; fread(&(aworker->num_workers), sizeof(int), 1, loadfile); aworker->workerlist = malloc(sizeof(worker) * (aworker->num_workers + 512)); fread(aworker->workerlist, sizeof(worker), aworker->num_workers, loadfile); fread(&(aworker->num_wires), sizeof(int), 1, loadfile); aworker->wirelist = malloc(sizeof(wire) * (aworker->num_wires + 1024)); fread(aworker->wirelist, sizeof(wire), aworker->num_wires, loadfile); aworker->workers_to_wires_down = malloc(sizeof(int) * (aworker->num_wires + 1024)); aworker->workers_to_wires_up = malloc(sizeof(int) * (aworker->num_wires + 1024)); for(j = 0; j < aworker->num_workers; ++j) if(aworker->workerlist[j].type == 2) aworker->workerlist[j].value_index = def_lookup[aworker->workerlist[j].value_index]; } } }while(i >= 0);*/ } else { //Read text program fflush(stdout); fseek(loadfile, 0, SEEK_END); size = ftell(loadfile); fseek(loadfile, 0, SEEK_SET); fflush(stdout); code = malloc(size+1); fread(code, 1, size, loadfile); fclose(loadfile); // num_defs = 0; fflush(stdout); prog = new_program(START_DEF_STORAGE, START_COMP_STORAGE); initpredefworkers(prog); fflush(stdout); parse(code, size, prog); free(code); // num_workers = deflist[0].num_workers; // num_wires = deflist[0].num_wires; } return prog; } /* void load_program(char * filename) { worker * aworkerlist; wire * awirelist; FILE * loadfile; char * code; int size; int def_num, version; loadfile = fopen(filename, "rb"); if(!loadfile) { puts("Error: Could not open file"); return; } if(!strcmp(strrchr(filename,'.')+1, "vis")) { //Read binary program fread(&version, 4, 1, loadfile); if(version != 1) { puts("Error: Can't read files of this version."); return; } //program * new_program = malloc(sizeof(program)); // strcpy(program->filename, filename); fread(&num_defs, 4, 1, loadfile); //program->defs_storage = program->num_defs + 512; //new_program->deflist = malloc(sizeof(worker_def) * (program->defs_storaage)); fread(deflist, sizeof(worker_def), num_defs, loadfile); fread(&def_num, 4, 1, loadfile); while(def_num >= 0 && !feof(loadfile)) { deflist[def_num].workerlist = malloc((deflist[def_num].num_workers+512)*sizeof(worker)); fread(deflist[def_num].workerlist, sizeof(worker), deflist[def_num].num_workers, loadfile); deflist[def_num].wirelist = malloc((deflist[def_num].num_wires+1024)*sizeof(wire)); fread(deflist[def_num].wirelist, sizeof(wire), deflist[def_num].num_wires, loadfile); deflist[def_num].workers_to_wires_up = malloc((deflist[def_num].num_wires+1024)*sizeof(int)); deflist[def_num].workers_to_wires_down = malloc((deflist[def_num].num_wires+1024)*sizeof(int)); fread(&def_num, 4, 1, loadfile); } fclose(loadfile); num_workers = deflist[0].num_workers; num_wires = deflist[0].num_wires; initpredefworkers(); } else { //Read text program fseek(loadfile, 0, SEEK_END); size = ftell(loadfile); fseek(loadfile, 0, SEEK_SET); code = malloc(size+1); fread(code, 1, size, loadfile); num_defs = 0; initpredefworkers(); parse(code, size); num_workers = deflist[0].num_workers; num_wires = deflist[0].num_wires; } }*/