⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 myutil.c

📁 disksim是一个非常优秀的磁盘仿真工具
💻 C
📖 第 1 页 / 共 2 页
字号:
/* libparam (version 1.0) * Authors: John Bucy, Greg Ganger * Contributors: John Griffin, Jiri Schindler, Steve Schlosser * * Copyright (c) of Carnegie Mellon University, 2001-2008. * * This software is being provided by the copyright holders under the * following license. By obtaining, using and/or copying this * software, you agree that you have read, understood, and will comply * with the following terms and conditions: * * Permission to reproduce, use, and prepare derivative works of this * software is granted provided the copyright and "No Warranty" * statements are included with all reproductions and derivative works * and associated documentation. This software may also be * redistributed without charge provided that the copyright and "No * Warranty" statements are included in all redistributions. * * NO WARRANTY. THIS SOFTWARE IS FURNISHED ON AN "AS IS" BASIS. * CARNEGIE MELLON UNIVERSITY MAKES NO WARRANTIES OF ANY KIND, EITHER * EXPRESSED OR IMPLIED AS TO THE MATTER INCLUDING, BUT NOT LIMITED * TO: WARRANTY OF FITNESS FOR PURPOSE OR MERCHANTABILITY, EXCLUSIVITY * OF RESULTS OR RESULTS OBTAINED FROM USE OF THIS SOFTWARE. CARNEGIE * MELLON UNIVERSITY DOES NOT MAKE ANY WARRANTY OF ANY KIND WITH * RESPECT TO FREEDOM FROM PATENT, TRADEMARK, OR COPYRIGHT * INFRINGEMENT.  COPYRIGHT HOLDERS WILL BEAR NO LIABILITY FOR ANY USE * OF THIS SOFTWARE OR DOCUMENTATION.   */#include <stdlib.h>#include <stdio.h>#include <ctype.h>#include <stdlib.h>#include <string.h>#include <libddbg/libddbg.h>#include <sys/types.h>#include <sys/stat.h>#include <unistd.h>#include <unistd.h>#include <fcntl.h>#include <libgen.h>#include "libparam.h"#include "bitvector.h"static lp_topoloader_t topoloader = 0;void lp_register_topoloader(lp_topoloader_t l) {  topoloader = l;}char *lp_builtin_names[] = {  0,  "Block",  "String",  "Int",  "Double",  "List",   "Topospec"};// FILE *libparamin = 0;struct lp_subtype **lp_typetbl;int lp_typetbl_len;struct lp_tlt **lp_tlts;int lp_tlts_len;//extern char lp_filename[];//extern char lp_cwd[];char **lp_searchpath = 0;int lp_searchpath_len = 0;extern int lp_lineno;static void destroy_block(struct lp_block *b);static void destroy_value(struct lp_value *v);static void destroy_param(struct lp_param *p);static void destroy_list(struct lp_list *l);static void destroy_topospec(struct lp_topospec *t);int dumb_split(char *s, char **t, int *i);int dumb_split2(char *s, char **s1, char **s2);static int lp_max_mod = 0;static int lp_mod_size = 0;struct lp_mod **lp_modules = 0;static char **overrides = 0;static int overrides_len = 0;#define outputfile stdoutstruct lp_value *lp_new_intv(int i) {  struct lp_value *v = calloc(1, sizeof(struct lp_value));  v->v.i = i;  v->t = I;  return v;}struct lp_value *lp_new_doublev(double d) {  struct lp_value *v = calloc(1, sizeof(struct lp_value));  v->v.d = d;  v->t = D;  return v;}struct lp_value *lp_new_stringv(char *s) {  struct lp_value *v = calloc(1, sizeof(struct lp_value));  v->v.s = s;  v->t = S;  return v;}struct lp_value *lp_new_listv(struct lp_list *l){  struct lp_value *v = calloc(1, sizeof(struct lp_value));  v->v.l = l;  v->t = LIST;  return v;}struct lp_value *lp_new_blockv(struct lp_block *b){  struct lp_value *v = calloc(1, sizeof(struct lp_value));  v->v.b = b;  v->t = b->type;  return v;}struct lp_param *lp_new_param(char *name, char *source, struct lp_value *v){  struct lp_param *result = calloc(1, sizeof(struct lp_param));  result->source_file = source;  result->name = name;  result->v = v;    return result;}struct lp_list *lp_new_list(void) {  struct lp_list *l = calloc(1, sizeof(struct lp_list));  l->values = calloc(8, sizeof(struct lp_value *));  l->values_len = 8;  l->values_pop = 0;  l->linelen = 1;  return l;}struct lp_block *lp_new_block(void){  struct lp_block *b = calloc(1, sizeof(struct lp_block));  b->params = calloc(8, sizeof(struct lp_param *));  b->params_len = 8;  return b;}struct lp_list *lp_new_intlist(int *intarr, int len){  int i;  struct lp_list *l = lp_new_list();  for(i = 0; i < len; i++) {    lp_list_add(l, lp_new_intv(intarr[i]));  }  return l;}int lp_register_module(struct lp_mod *m) {  int c;  for(c = 0; c < lp_max_mod; c++) {    if(!strcmp(m->name, lp_modules[c]->name)) {      return -1;    }  }  if(c >= lp_mod_size) {    lp_mod_size *= 2; lp_mod_size++;    lp_modules = realloc(lp_modules, lp_mod_size * sizeof(int *));  }  if(c > 0)     lp_modules[c] = m;  else     lp_modules[0] = m;  lp_max_mod++;  return c;}static void die(char *msg) {  fprintf(stderr, "*** error: FATAL: %s\n", msg);  exit(1);}static void destroy_param(struct lp_param *p){  free(p->name);  destroy_value(p->v);  free(p);}static void destroy_list(struct lp_list *l) {  int c;  for(c = 0; c < l->values_len; c++)    if(l->values[c])      destroy_value(l->values[c]);  free(l->values);  free(l);}static void destroy_value(struct lp_value *v) {  int d;  switch(v->t) {  case S:    free(v->v.s);     break;      case LIST:    destroy_list(v->v.l);    break;      case I:   case D: break;  case TOPOSPEC:    for(d = 0; d < v->v.t.len; d++)      destroy_topospec(&v->v.t.l[d]);    free(v->v.t.l);    break;        default:    destroy_block(v->v.b);  }  free(v);}static void destroy_block(struct lp_block *b) {  int c;  for(c = 0; c < b->params_len; c++) {    if(b->params[c]) {      destroy_param(b->params[c]);    }   }  free(b->name);  free(b->params);  free(b);}static void destroy_topospec(struct lp_topospec *t){  free(t->type);  free(t->name);  destroy_list(t->l);}static struct lp_block *copy_block(struct lp_block *);static struct lp_list *copy_list(struct lp_list *);static struct lp_value *copy_value(struct lp_value *);static struct lp_param *copy_param(struct lp_param *);static struct lp_block *copy_block(struct lp_block *b){  int c;  struct lp_block *result = calloc(1, sizeof(*result));  memcpy(result, b, sizeof(struct lp_block));  result->params = calloc(b->params_len, sizeof(result->params[0]));  if(b->name) {    result->name = strdup(b->name);  }  for(c = 0; c < b->params_len; c++) {    if(b->params[c]) {      result->params[c] = copy_param(b->params[c]);    }  }  return result;}static struct lp_list *copy_list(struct lp_list *l) {  int c;  struct lp_list *result = calloc(1, sizeof(*result));  memcpy(result, l, sizeof(struct lp_list));  result->values = calloc(l->values_len, sizeof(result->values[0]));  memcpy(result->values, l->values, l->values_len * sizeof(int *));  for(c = 0; c < l->values_len; c++) {    if(l->values[c]) {      result->values[c] = copy_value(l->values[c]);    }  }  return result;}static struct lp_value *copy_value(struct lp_value *v) {  struct lp_value *result = calloc(1, sizeof(struct lp_value));  memcpy(result, v, sizeof(struct lp_value));  switch(v->t) {  case S:    result->v.s = strdup(v->v.s);    break;  case LIST:    result->v.l = copy_list(v->v.l);    break;  case BLOCK:    result->v.b = copy_block(v->v.b);    break;  default:    break;  }    return result;}static struct lp_param *copy_param(struct lp_param *p) {  struct lp_param *result = calloc(1, sizeof(struct lp_param));  result->name = strdup(p->name);  result->v = copy_value(p->v);  return result;}static int indent_level = 0;static void indent(FILE *f) {  char *space = calloc(1, 3*indent_level+1);  memset(space, (int)' ', 3*indent_level);  space[3*indent_level] = 0;  fprintf(f, "%s", space);  free(space);}void unparse_source(char *source, FILE *outfile) {  fprintf(outfile, "source %s", source);}void unparse_type(int t, FILE *outfile) {  if(t < 0) {    fprintf(outfile, "%s", lp_builtin_names[abs(t)]);  }  else {    if(t > lp_max_mod) {      fprintf(outfile, "<UNKNOWN TYPE>");    }    else {      fprintf(outfile, "%s", lp_modules[t]->name);    }  }}void unparse_param(struct lp_param *p, FILE *outfile) {  fprintf(outfile, "%s = ", p->name);  if(p->source_file && p->v->source_file) {    if(strcmp(p->source_file, p->v->source_file)) {      unparse_source(p->v->source_file, outfile);      return;    }  }  unparse_value(p->v, outfile);}void unparse_value(struct lp_value *v, FILE *outfile) {  int c;  switch(v->t) {  case I:    fprintf(outfile, "%d", v->v.i);    break;  case D:    if(v->v.d == 0.0) {      fprintf(outfile, "0.0");    }    else {      fprintf(outfile, "%f", v->v.d);    }    break;  case S:    fprintf(outfile, "%s", v->v.s);    break;  case LIST:    unparse_list(v->v.l, outfile);    break;  case TOPOSPEC:    for(c = 0; c < v->v.t.len; c++)      unparse_topospec(&v->v.t.l[c], outfile);    break;  default:  case BLOCK:    unparse_block(v->v.b, outfile);    break;  }}void unparse_list(struct lp_list *l, FILE *outfile) {  int printed = 0;  int c;/*    indent(outfile); */  fprintf(outfile, "[ ");  indent_level++;  for(c = 0; c < l->values_len; c++) {     if(!l->values[c])       continue;    if(c) {      fprintf(outfile, ", ");      if(!(c % l->linelen)) {	fprintf(outfile, "\n");	indent(outfile);      }    }    else {      fprintf(outfile, "\n");      indent(outfile);    }    printed++;    unparse_value(l->values[c], outfile);  }  indent_level--;  if((c > 0) && printed) {    fprintf(outfile, "\n");    indent(outfile);  }  fprintf(outfile, "]");}void unparse_block(struct lp_block *b, FILE *outfile) {  int c;/*    indent(outfile); */  if(b->name) {    /* a block definition */    fprintf(outfile, "%s %s {\n", lp_modules[b->type]->name, b->name);  }  else {    /* a block value */    fprintf(outfile, "%s {\n", lp_modules[b->type]->name);  }  indent_level++;  for(c = 0; c < b->params_len; c++) {    if(!b->params[c]) continue;    if(c) fprintf(outfile, ",\n");    unparse_param(b->params[c], outfile);  }  indent_level--;  fprintf(outfile, "\n");  indent(outfile);  fprintf(outfile, "}");  if(b->name) {    fprintf(outfile, " # end of %s spec", b->name);    fprintf(outfile, "\n\n");  }}void unparse_topospec(struct lp_topospec *t, FILE *outfile) {  fprintf(outfile, "%s %s ", t->type, t->name);  unparse_list(t->l, outfile);  // unparse_list() prints a trailing newline...  //  fprintf(outputfile, "\n"); }// somewhat of a hackvoid unparse_tl_topospec(struct lp_topospec *t, FILE *outfile) {  fprintf(outfile, "topospec ");  unparse_topospec(t, outfile);  fprintf(outfile, "\n\n");}void unparse_inst(struct lp_inst *i, FILE *outfile) {  fprintf(outfile, "instantiate ");  unparse_list(i->l, outfile);  fprintf(outfile, " as %s\n\n", i->name);}void unparse_tlt(struct lp_tlt *tlt, FILE *outfile, char *infile) {  if(tlt->source_file && infile) {    if(strcmp(tlt->source_file, infile)) {      unparse_source(tlt->source_file, outfile);      return;    }  }    switch(tlt->what) {  case TLT_BLOCK: unparse_block(tlt->it.block, outfile); break;  case TLT_TOPO:  unparse_tl_topospec(tlt->it.topo, outfile); break;  case TLT_INST:  unparse_inst(tlt->it.inst, outfile); break;  default:        ddbg_assert(0); break;  };  }void lp_unparse_tlts(struct lp_tlt **tlts, 		     int tlts_len, 		     FILE *outfile, 		     char *infile) {  int c;  for(c = 0; c < tlts_len; c++) {    if(tlts[c] != 0) {      unparse_tlt(tlts[c], outfile, infile);    }  }}/* instantiate all the elements of <l> as <name> */int lp_inst_list(struct lp_inst *i){  int c;    /*      unparse_block(spec, outputfile); */  for(c = 0; c < i->l->values_len; c++) {    if(!i->l->values[c]) continue;        ddbg_assert3(i->l->values[c]->t == S, 	       ("bad type for component %s", i->l->values[c]->v.s));        lp_instantiate(i->l->values[c]->v.s, i->name);  }    return 0;}/* instantiate <targ> as <name> */int *lp_instantiate(char *targ, char *name) {  char *nametmp;  struct lp_block *spec;  int *obj;    /*    unparse_block(b, outputfile); */  spec = lp_lookup_spec(name);  ddbg_assert3(spec != 0, ("no such type %s.\n", name));  // this is a bit of a hack; we swap the name of the component  // being instantiated with the name of the module that's being  // instantiated so that the loader function sees the target  // name  nametmp = spec->name;  spec->name = targ;    //  fprintf(stderr, "*** Instantiating %s as %s\n", targ, name);  obj = lp_override_inst(spec, 			 targ,			 lp_modules[spec->type]->fn,			 overrides, 			 overrides_len);  // swap the name back  spec->name = nametmp;  if(!obj) {    return 0;  }    if(lp_modules[spec->type]->callback) {    lp_modules[spec->type]->callback(lp_modules[spec->type]->ctx, obj);  }  return obj;}/* 0 on success, nonzero on error */int check_types(struct lp_block *b) {  int c = 0;  /* we'll do all of the type checking here so that    * the per-mod loaders only have to sanitize values */  for(c = 0; c < b->params_len; c++) {    if(b->params[c]) {      if(lp_param_name(b->type, b->params[c]->name) == -1) {	fprintf(stderr, "*** warning: parameter %s not valid in context %s\n",		b->params[c]->name, lp_modules[b->type]->name);	      }      else if(lp_modules[b->type]->modvars[lp_param_name(b->type, b->params[c]->name)].type	 != PTYPE(b->params[c])) {	/* implicitly convert ints to doubles */	if((lp_modules[b->type]->modvars[lp_param_name(b->type, b->params[c]->name)].type	    == D)	   && (PTYPE(b->params[c]) == I)) {	  b->params[c]->v->t = D;	  DVAL(b->params[c]) = (double) IVAL(b->params[c]);	}	  	else { 	  fprintf(stderr, "*** error: type error: %s::\"%s\" cannot take type ",		  lp_modules[b->type]->name,		  b->params[c]->name);	  /*  	  unparse_type(PTYPE(b->params[c]), stderr); */	  fprintf(stderr, "\n");	  die("check_types() failed");	}      }            if(PTYPE(b->params[c]) >= BLOCK) {	check_types(BVAL(b->params[c]));      }      else if(PTYPE(b->params[c]) == LIST) {	int d;	struct lp_list *l = LVAL(b->params[c]);	for(d = 0; d < l->values_len; d++) {	  if(l->values[d]) {	    if(l->values[d]->t >= BLOCK) {	      check_types(l->values[d]->v.b);	    }	  }	}      }    }  }  return 0;}void load_block(struct lp_block *b) {  int n;  lp_lookup_type(b->name, &n);  lp_typetbl[n]->spec = b;}void load_topo(struct lp_topospec *t, int len) {/*    unparse_topospec(t, outputfile); */  topoloader(t, len);}void printvars(void) {  int c, d;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -