Branch: Tag:

1995-08-09

1995-08-09 10:21:55 by Fredrik Hübinette (Hubbe) <hubbe@hubbe.net>

ulpc dist

Rev: bin/create_testsuite:1.1.1.1
Rev: bin/hilfe.lpc:1.1.1.1
Rev: bin/rsif:1.1.1.1
Rev: bin/uhttpd.lpc:1.1.1.1
Rev: doc/README:1.1.1.1
Rev: doc/builtin/aggregate:1.1.1.1
Rev: doc/builtin/aggregate_list:1.1.1.1
Rev: doc/builtin/aggregate_mapping:1.1.1.1
Rev: doc/builtin/all_efuns:1.1.1.1
Rev: doc/builtin/allocate:1.1.1.1
Rev: doc/builtin/arrayp:1.1.1.1
Rev: doc/builtin/backtrace:1.1.1.1
Rev: doc/builtin/call_function:1.1.1.1
Rev: doc/builtin/call_out:1.1.1.1
Rev: doc/builtin/call_out_info:1.1.1.1
Rev: doc/builtin/catch:1.1.1.1
Rev: doc/builtin/clone:1.1.1.1
Rev: doc/builtin/combine_path:1.1.1.1
Rev: doc/builtin/compile_file:1.1.1.1
Rev: doc/builtin/compile_string:1.1.1.1
Rev: doc/builtin/copy_value:1.1.1.1
Rev: doc/builtin/crypt:1.1.1.1
Rev: doc/builtin/ctime:1.1.1.1
Rev: doc/builtin/destruct:1.1.1.1
Rev: doc/builtin/equal:1.1.1.1
Rev: doc/builtin/exit:1.1.1.1
Rev: doc/builtin/explode:1.1.1.1
Rev: doc/builtin/find_call_out:1.1.1.1
Rev: doc/builtin/floatp:1.1.1.1
Rev: doc/builtin/function_name:1.1.1.1
Rev: doc/builtin/function_object:1.1.1.1
Rev: doc/builtin/functionp:1.1.1.1
Rev: doc/builtin/hash:1.1.1.1
Rev: doc/builtin/implode:1.1.1.1
Rev: doc/builtin/indices:1.1.1.1
Rev: doc/builtin/intp:1.1.1.1
Rev: doc/builtin/listp:1.1.1.1
Rev: doc/builtin/lower_case:1.1.1.1
Rev: doc/builtin/m_delete:1.1.1.1
Rev: doc/builtin/mappingp:1.1.1.1
Rev: doc/builtin/mkmapping:1.1.1.1
Rev: doc/builtin/next_object:1.1.1.1
Rev: doc/builtin/object_program:1.1.1.1
Rev: doc/builtin/objectp:1.1.1.1
Rev: doc/builtin/programp:1.1.1.1
Rev: doc/builtin/query_host_name:1.1.1.1
Rev: doc/builtin/query_num_arg:1.1.1.1
Rev: doc/builtin/random:1.1.1.1
Rev: doc/builtin/regexpp:1.1.1.1
Rev: doc/builtin/remove_call_out:1.1.1.1
Rev: doc/builtin/replace:1.1.1.1
Rev: doc/builtin/reverse:1.1.1.1
Rev: doc/builtin/rusage:1.1.1.1
Rev: doc/builtin/search:1.1.1.1
Rev: doc/builtin/sizeof:1.1.1.1
Rev: doc/builtin/sscanf:1.1.1.1
Rev: doc/builtin/stringp:1.1.1.1
Rev: doc/builtin/sum:1.1.1.1
Rev: doc/builtin/this_object:1.1.1.1
Rev: doc/builtin/throw:1.1.1.1
Rev: doc/builtin/time:1.1.1.1
Rev: doc/builtin/trace:1.1.1.1
Rev: doc/builtin/upper_case:1.1.1.1
Rev: doc/builtin/values:1.1.1.1
Rev: doc/builtin/zero_type:1.1.1.1
Rev: doc/files/cd:1.1.1.1
Rev: doc/files/exec:1.1.1.1
Rev: doc/files/file:1.1.1.1
Rev: doc/files/file_stat:1.1.1.1
Rev: doc/files/fork:1.1.1.1
Rev: doc/files/get_dir:1.1.1.1
Rev: doc/files/getcwd:1.1.1.1
Rev: doc/files/mkdir:1.1.1.1
Rev: doc/files/mv:1.1.1.1
Rev: doc/files/perror:1.1.1.1
Rev: doc/files/port:1.1.1.1
Rev: doc/files/rm:1.1.1.1
Rev: doc/lpc/command_line_options:1.1.1.1
Rev: doc/lpc/control_structures:1.1.1.1
Rev: doc/lpc/hilfe.hilfe:1.1.1.1
Rev: doc/lpc/how_to_make_modules:1.1.1.1
Rev: doc/manual/i-overview.html:1.1.1.1
Rev: doc/manual/index.html:1.1.1.1
Rev: doc/manual/t-hello.html:1.1.1.1
Rev: doc/manual/ulpc-inside3.gif:1.1.1.1
Rev: doc/math/acos:1.1.1.1
Rev: doc/math/asin:1.1.1.1
Rev: doc/math/atan:1.1.1.1
Rev: doc/math/ceil:1.1.1.1
Rev: doc/math/cos:1.1.1.1
Rev: doc/math/exp:1.1.1.1
Rev: doc/math/floor:1.1.1.1
Rev: doc/math/log:1.1.1.1
Rev: doc/math/pow:1.1.1.1
Rev: doc/math/sin:1.1.1.1
Rev: doc/math/sqrt:1.1.1.1
Rev: doc/math/tan:1.1.1.1
Rev: doc/operators/addition:1.1.1.1
Rev: doc/regexp/regexp:1.1.1.1
Rev: doc/simulated/PI:1.1.1.1
Rev: doc/simulated/capitalize:1.1.1.1
Rev: doc/simulated/code_value:1.1.1.1
Rev: doc/simulated/describe_backtrace:1.1.1.1
Rev: doc/simulated/file_size:1.1.1.1
Rev: doc/simulated/filter_array:1.1.1.1
Rev: doc/simulated/get_function:1.1.1.1
Rev: doc/simulated/getenv:1.1.1.1
Rev: doc/simulated/l_sizeof:1.1.1.1
Rev: doc/simulated/m_indices:1.1.1.1
Rev: doc/simulated/m_sizeof:1.1.1.1
Rev: doc/simulated/m_values:1.1.1.1
Rev: doc/simulated/map_array:1.1.1.1
Rev: doc/simulated/master:1.1.1.1
Rev: doc/simulated/member_array:1.1.1.1
Rev: doc/simulated/popen:1.1.1.1
Rev: doc/simulated/previous_object:1.1.1.1
Rev: doc/simulated/read_bytes:1.1.1.1
Rev: doc/simulated/regexp:1.1.1.1
Rev: doc/simulated/search_array:1.1.1.1
Rev: doc/simulated/sort_array:1.1.1.1
Rev: doc/simulated/spawn:1.1.1.1
Rev: doc/simulated/strlen:1.1.1.1
Rev: doc/simulated/strstr:1.1.1.1
Rev: doc/simulated/sum_arrays:1.1.1.1
Rev: doc/simulated/this_function:1.1.1.1
Rev: doc/simulated/write:1.1.1.1
Rev: doc/simulated/write_file:1.1.1.1
Rev: doc/sprintf/sprintf:1.1.1.1
Rev: doc/types/array:1.1.1.1
Rev: doc/types/float:1.1.1.1
Rev: doc/types/function:1.1.1.1
Rev: doc/types/int:1.1.1.1
Rev: doc/types/list:1.1.1.1
Rev: doc/types/mapping:1.1.1.1
Rev: doc/types/object:1.1.1.1
Rev: doc/types/program:1.1.1.1
Rev: doc/types/string:1.1.1.1
Rev: lib/conftest.h:1.1.1.1
Rev: lib/master.lpc:1.1.1.1
Rev: lib/simulate.lpc:1.1.1.1
Rev: lib/testsuite.lpc:1.1.1.1
Rev: src/BUGS:1.1.1.1
Rev: src/COPYING:1.1.1.1
Rev: src/COPYRIGHT:1.1.1.1
Rev: src/DISCLAIMER:1.1.1.1
Rev: src/Makefile.in:1.1.1.1
Rev: src/README:1.1.1.1
Rev: src/add_efun.c:1.1.1.1
Rev: src/add_efun.h:1.1.1.1
Rev: src/alloca.c:1.1.1.1
Rev: src/array.c:1.1.1.1
Rev: src/array.h:1.1.1.1
Rev: src/backend.c:1.1.1.1
Rev: src/backend.h:1.1.1.1
Rev: src/builtin_efuns.c:1.1.1.1
Rev: src/builtin_efuns.h:1.1.1.1
Rev: src/call_out.c:1.1.1.1
Rev: src/call_out.h:1.1.1.1
Rev: src/callback.c:1.1.1.1
Rev: src/callback.h:1.1.1.1
Rev: src/config.h:1.1.1.1
Rev: src/configure.in:1.1.1.1
Rev: src/debug.c:1.1.1.1
Rev: src/debug.h:1.1.1.1
Rev: src/docode.c:1.1.1.1
Rev: src/docode.h:1.1.1.1
Rev: src/dynamic_buffer.c:1.1.1.1
Rev: src/dynamic_buffer.h:1.1.1.1
Rev: src/efun.h:1.1.1.1
Rev: src/error.c:1.1.1.1
Rev: src/error.h:1.1.1.1
Rev: src/fd_control.c:1.1.1.1
Rev: src/fd_control.h:1.1.1.1
Rev: src/fsort.c:1.1.1.1
Rev: src/fsort.h:1.1.1.1
Rev: src/global.h:1.1.1.1
Rev: src/hashtable.c:1.1.1.1
Rev: src/hashtable.h:1.1.1.1
Rev: src/install-sh:1.1.1.1
Rev: src/interpret.c:1.1.1.1
Rev: src/interpret.h:1.1.1.1
Rev: src/language.y:1.1.1.1
Rev: src/las.c:1.1.1.1
Rev: src/las.h:1.1.1.1
Rev: src/lex.c:1.1.1.1
Rev: src/lex.h:1.1.1.1
Rev: src/list.c:1.1.1.1
Rev: src/list.h:1.1.1.1
Rev: src/lpc_types.c:1.1.1.1
Rev: src/lpc_types.h:1.1.1.1
Rev: src/machine.h.in:1.1.1.1
Rev: src/macros.h:1.1.1.1
Rev: src/main.c:1.1.1.1
Rev: src/main.h:1.1.1.1
Rev: src/mapping.c:1.1.1.1
Rev: src/mapping.h:1.1.1.1
Rev: src/memory.c:1.1.1.1
Rev: src/memory.h:1.1.1.1
Rev: src/module.c:1.1.1.1
Rev: src/module.h:1.1.1.1
Rev: src/modules/efuns.c:1.1.1.1
Rev: src/modules/files/Makefile.in:1.1.1.1
Rev: src/modules/files/configure.in:1.1.1.1
Rev: src/modules/files/datagram.c:1.1.1.1
Rev: src/modules/files/efuns.c:1.1.1.1
Rev: src/modules/files/file.c:1.1.1.1
Rev: src/modules/files/file.h:1.1.1.1
Rev: src/modules/files/file_machine.h.in:1.1.1.1
Rev: src/modules/files/socket.c:1.1.1.1
Rev: src/modules/math/Makefile.in:1.1.1.1
Rev: src/modules/math/configure.in:1.1.1.1
Rev: src/modules/math/math.c:1.1.1.1
Rev: src/modules/regexp/Makefile.in:1.1.1.1
Rev: src/modules/regexp/configure.in:1.1.1.1
Rev: src/modules/regexp/glue.c:1.1.1.1
Rev: src/modules/regexp/regexp.c:1.1.1.1
Rev: src/modules/regexp/regexp.h:1.1.1.1
Rev: src/modules/sprintf/Makefile.in:1.1.1.1
Rev: src/modules/sprintf/configure.in:1.1.1.1
Rev: src/modules/sprintf/sprintf.c:1.1.1.1
Rev: src/object.c:1.1.1.1
Rev: src/object.h:1.1.1.1
Rev: src/opcodes.c:1.1.1.1
Rev: src/opcodes.h:1.1.1.1
Rev: src/operators.c:1.1.1.1
Rev: src/operators.h:1.1.1.1
Rev: src/otable.h:1.1.1.1
Rev: src/port.c:1.1.1.1
Rev: src/port.h:1.1.1.1
Rev: src/program.c:1.1.1.1
Rev: src/program.h:1.1.1.1
Rev: src/rusage.c:1.1.1.1
Rev: src/rusage.h:1.1.1.1
Rev: src/stralloc.c:1.1.1.1
Rev: src/stralloc.h:1.1.1.1
Rev: src/stuff.c:1.1.1.1
Rev: src/stuff.h:1.1.1.1
Rev: src/svalue.c:1.1.1.1
Rev: src/svalue.h:1.1.1.1
Rev: src/todo:1.1.1.1
Rev: src/types.h:1.1.1.1
Rev: src/ualarm.c:1.1.1.1

1: + #include <stdio.h> + #include "global.h" + #include "array.h" + #include "call_out.h" + #include "dynamic_buffer.h" + #include "object.h" + #include "interpret.h" + #include "error.h" + #include "builtin_efuns.h"    -  + call_out **pending_calls=0; /* pointer to first busy pointer */ + int num_pending_calls; /* no of busy pointers in buffer */ + static call_out **call_buffer=0; /* pointer to buffer */ + static int call_buffer_size; /* no of pointers in buffer */ +  + extern time_t current_time; +  + static void verify_call_outs() + { + #ifdef DEBUG +  struct array *v; +  int e; +  if(call_buffer) return; +  +  if(num_pending_calls<0 || num_pending_calls>call_buffer_size) +  fatal("Error in call out tables.\n"); +  +  if(pending_calls+num_pending_calls!=call_buffer+call_buffer_size) +  fatal("Error in call out tables.\n"); +  +  for(e=0;e<num_pending_calls;e++) +  { +  if(e) +  { +  if(pending_calls[e-1]>pending_calls[e]) +  fatal("Error in call out order.\n"); +  } +  +  if(!(v=pending_calls[e]->args)) +  fatal("No arguments to call\n"); +  +  if(v->refs!=1) +  fatal("Array should exactly have one reference.\n"); +  +  if(v->malloced_size<v->size) +  fatal("Impossible array.\n"); +  } + #endif + } +  +  + /* start a new call out, return 1 for success */ + static int new_call_out(int num_arg,struct svalue *argp) + { +  int e,c; +  call_out *new,**p,**pos; +  +  if(!call_buffer) +  { +  call_buffer_size=20; +  call_buffer=(call_out **)xalloc(sizeof(call_out *)*call_buffer_size); +  if(!call_buffer) return 0; +  pending_calls=call_buffer+call_buffer_size; +  num_pending_calls=0; +  } +  +  if(num_pending_calls==call_buffer_size) +  { +  /* here we need to allocate space for more pointers */ +  call_out **new_buffer; +  +  new_buffer=(call_out **)xalloc(sizeof(call_out *)*call_buffer_size*2); +  if(!new_buffer) +  return 0; +  +  MEMCPY((char *)(new_buffer+call_buffer_size), +  (char *)call_buffer, +  sizeof(call_out *)*call_buffer_size); +  free((char *)call_buffer); +  call_buffer=new_buffer; +  pending_calls=call_buffer+call_buffer_size; +  call_buffer_size*=2; +  } +  +  /* time to allocate a new call_out struct */ +  f_aggregate(num_arg-1); +  +  new=(call_out *)xalloc(sizeof(call_out)); +  +  if(!new) return 0; +  +  new->time=current_time+argp[0].u.integer; +  if(new->time <= current_time) new->time=current_time+1; +  +  if(fp && fp->current_object) +  { +  new->caller=fp->current_object; +  new->caller->refs++; +  }else{ +  new->caller=0; +  } +  +  new->args=sp[-1].u.array; +  sp -= 2; +  +  /* time to link it into the buffer using binsearch */ +  pos=pending_calls; +  if(new->time>current_time+1) /* do we need to search where ?*/ +  { +  e=num_pending_calls; +  while(e>0) +  { +  c=e/2; +  if(new->time>pos[c]->time) +  { +  pos+=c+1; +  e-=c+1; +  }else{ +  e=c; +  } +  } +  } +  pos--; +  pending_calls--; +  for(p=pending_calls;p<pos;p++) p[0]=p[1]; +  *pos=new; +  num_pending_calls++; +  +  return 1; + } +  + void f_call_out(INT32 args) + { +  struct svalue tmp; +  if(args<2) +  error("Too few arguments to call_out.\n"); +  +  /* Swap, for compatibility */ +  tmp=sp[-args]; +  sp[-args]=sp[1-args]; +  sp[1-args]=tmp; +  +  new_call_out(args,sp-args); + } +  + void do_call_outs() + { +  call_out *c; +  int args; +  verify_call_outs(); +  while(num_pending_calls && +  pending_calls[0]->time<=current_time && +  current_time==get_current_time()) +  { +  /* unlink call out */ +  c=pending_calls[0]; +  pending_calls++; +  num_pending_calls--; +  +  if(c->caller) free_object(c->caller); +  +  args=c->args->size; +  push_array_items(c->args); +  free((char *)c); +  check_destructed(sp-args); +  if(sp[-args].type!=T_INT) +  { +  f_call_function(args); +  pop_stack(); +  }else{ +  pop_n_elems(args); +  } +  verify_call_outs(); +  } + } +  + static int find_call_out(struct svalue *fun) + { +  int e; +  for(e=0;e<num_pending_calls;e++) +  { +  if(is_eq(fun, ITEM(pending_calls[e]->args))) +  return e; +  } +  return -1; + } +  + void f_find_call_out(INT32 args) + { +  int e; +  verify_call_outs(); +  e=find_call_out(sp - args); +  pop_n_elems(args); +  if(e==-1) +  { +  sp->type=T_INT; +  sp->subtype=NUMBER_UNDEFINED; +  sp->u.integer=-1; +  sp++; +  }else{ +  push_int(pending_calls[e]->time-current_time); +  } +  verify_call_outs(); + } +  + void f_remove_call_out(INT32 args) + { +  int e; +  verify_call_outs(); +  e=find_call_out(sp-args); +  if(e!=-1) +  { +  pop_n_elems(args); +  push_int(pending_calls[e]->time-current_time); +  free_array(pending_calls[e]->args); +  if(pending_calls[e]->caller) +  free_object(pending_calls[e]->caller); +  free((char*)(pending_calls[e])); +  for(;e>0;e--) +  pending_calls[e]=pending_calls[e-1]; +  pending_calls++; +  num_pending_calls--; +  }else{ +  pop_n_elems(args); +  sp->type=T_INT; +  sp->subtype=NUMBER_UNDEFINED; +  sp->u.integer=-1; +  sp++; +  } +  verify_call_outs(); + } +  + /* return an array containing info about all call outs: +  * ({ ({ delay, caller, function, args, ... }), ... }) +  */ + struct array *get_all_call_outs() + { +  int e; +  struct array *ret; +  +  verify_call_outs(); +  ret=allocate_array_no_init(num_pending_calls,0,T_ARRAY); +  for(e=0;e<num_pending_calls;e++) +  { +  struct array *v; +  v=allocate_array_no_init(pending_calls[e]->args->size+2, 0, T_MIXED); +  ITEM(v)[0].type=T_INT; +  ITEM(v)[0].subtype=NUMBER_NUMBER; +  ITEM(v)[0].u.integer=pending_calls[e]->time-current_time; +  +  if(pending_calls[e]->caller) +  { +  ITEM(v)[1].type=T_OBJECT; +  (ITEM(v)[1].u.object=pending_calls[e]->caller) ->refs++; +  }else{ +  ITEM(v)[1].type=T_INT; +  ITEM(v)[1].subtype=NUMBER_NUMBER; +  ITEM(v)[1].u.integer=0; +  } +  +  assign_svalues_no_free(ITEM(v)+2,ITEM(pending_calls[e]->args),pending_calls[e]->args->size); +  +  SHORT_ITEM(ret)[e].array=v; +  } +  return ret; + } +  + void f_call_out_info(INT32 args) + { +  pop_n_elems(args); +  push_array(get_all_call_outs()); + } +  + void free_all_call_outs() + { +  int e; +  verify_call_outs(); +  for(e=0;e<num_pending_calls;e++) +  { +  free_array(pending_calls[e]->args); +  if(pending_calls[e]->caller) free_object(pending_calls[e]->caller); +  free((char*)(pending_calls[e])); +  } +  if(call_buffer) free((char*)call_buffer); +  num_pending_calls=0; +  call_buffer=NULL; +  pending_calls=NULL; + } +  + time_t get_next_call_out() + { +  if(num_pending_calls) +  { +  return pending_calls[0]->time; +  }else{ +  return 0; +  } + } +  + #ifdef DEBUG + void verify_all_call_outs() + { +  int e; +  verify_call_outs(); +  for(e=0;e<num_pending_calls;e++) +  { +  checked((void *)pending_calls[e]->caller,1); +  checked((void *)pending_calls[e]->args,1); +  } + } + #endif   Newline at end of file added.