Example #1
0
void foo() { 
  if(s->type == T_INT && count->type == T_INT)
    s->u.integer+=count->u.integer;
  else {          
    push_svalue(s); push_svalue(count); f_add(2);                         
    mapping_string_insert(mappingen, key, Pike_sp-1); pop_stack();
  }
  if(s->type == T_INT && count->type == T_INT &&                
     !INT_TYPE_ADD_OVERFLOW(count->u.integer, s->u.integer))
  { /*fast      
      add*/} else { /*f_add*/ }   
}
Example #2
0
static void pextsElementDecl(void *ctx, const xmlChar *name, int type, xmlElementContentPtr content)
{
  struct mapping  *cmap;
  
  DBG_FUNC_ENTER();
  if (CB_ABSENT(elementDeclSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  safe_push_text(name);
  push_int(type);
  cmap = tree2mapping(content);
  if (cmap)
    push_mapping(cmap);
  else
    push_int(0);
  push_svalue(&THIS->user_data);
  
  CB_CALL(elementDeclSAX, 5);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #3
0
PMOD_EXPORT struct object *bignum_from_svalue(struct svalue *s)
{
  push_svalue(s);
  convert_stack_top_to_bignum();
  dmalloc_touch_svalue(sp-1);
  return (--sp)->u.object;
}
Example #4
0
static void pextsFatalError(void *ctx, const char *msg, ...)
{
  char    *vmsg;
  va_list  ap;
  
  DBG_FUNC_ENTER();
  if (CB_ABSENT(fatalErrorSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  /* I'm being lazy here :> */
  vmsg = NULL;
  va_start(ap, msg);
  if (vasprintf(&vmsg, msg, ap) < -1)
    push_int(0);
  else {
    push_text(vmsg);
    free(vmsg);
  }
  push_svalue(&THIS->user_data);
  CB_CALL(fatalErrorSAX, 3);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #5
0
void f_query_temp () {
    int idx;
    object_t *ob;
    unsigned short type;
    svalue_t *value;
    char *src, *dst;
    mapping_t *map;
    char *tmpstr;

    if( st_num_arg==2 ) {
        ob=sp->u.ob;
        pop_stack();
    } else
        ob = current_object;

    idx = find_global_variable(ob->prog, "tmp_dbase", &type, 0);
    if (idx == -1)
    {
        free_string_svalue(sp--);
        push_undefined();
        return;
    }
    value = &ob->variables[idx];

    if( value->type != T_MAPPING )
    {
    	free_string_svalue(sp--);
    	error("(query_temp) %s 物件的资料库变数型态错误。\n", ob->obname);
    }

    map = value->u.map;
    src = (char *)sp->u.string;
    dst = tmpstr = (char *)DMALLOC(SVALUE_STRLEN(sp) + 1, TAG_STRING, "query_temp");

    while (*src)
    {
	while (*src != '/' && *src)
	    *dst++ = *src++;
	if (*src == '/')
	{
	    while (*++src == '/');
	    if( dst == tmpstr ) continue;
	}
	*dst = '\0';
	value = find_string_in_mapping(map, tmpstr);

	if( value == &const0u ) break;
	if( value->type != T_MAPPING )
	{
	    if(*src) value = &const0u;
	    break;
	}
	map = value->u.map;
	dst = tmpstr;
    }

    FREE(tmpstr);
    free_string_svalue(sp--);
    push_svalue(value);
}
Example #6
0
/* EFUN: filter (array part)
   
   Runs all elements of an array through fun
   and returns an array holding those elements that fun
   returned 1 for.
   */
struct vector *
filter_arr(struct vector *p, struct closure *fun)
{
    struct vector *r;
    char *flags;
    int cnt,res;
    
    if (p->size<1)
	return allocate_array(0);

    res = 0;
    flags = tmpalloc((size_t)p->size + 1); 
    for (cnt = 0; cnt < p->size; cnt++) {
	push_svalue(&p->item[cnt]);
	(void)call_var(1, fun);
	if (sp->type == T_NUMBER && sp->u.number) {
	    flags[cnt] = 1; 
	    res++; 
	} else
	    flags[cnt] = 0;
	pop_stack();
    }
    r = allocate_array(res);
    for (cnt = res = 0; res < r->size && cnt < p->size; cnt++) {
	if (flags[cnt]) 
	    assign_svalue_no_free(&r->item[res++], &p->item[cnt]);
    }
/*    tmpfree(flags); */
    return r;
}
Example #7
0
void
f_reference_allowed()
  {
    svalue_t *sv = sp - st_num_arg + 1;
    svalue_t *v;
    object_t *referee = NULL;
    object_t *referrer_obj = command_giver; /* Default to this_player(). */
    const char *referrer_name = NULL;
    int result = 0;
    int num_arg = st_num_arg;

    /* Maybe I could learn how to use this :p 
    CHECK_TYPES(sp-1, T_NUMBER, 1, F_MEMBER_ARRAY); */

    if (sv->type == T_OBJECT && sv->u.ob) {
        referee = sv->u.ob;
    }

    if (st_num_arg > 1) {
        if (sv[1].type == T_STRING && sv[1].u.string) {
            /* We've been passed in a string, now we need to call 
             * find_player() */ 
#ifdef F_FIND_PLAYER
            /* If we have a find_player() efun, then we need to sue 
             * the following method.  This hasn't been tested!
             */ 
             referrer = find_living_object(sv[1].u.string, 1);
#else
            if (simul_efun_ob) {
                push_svalue(&sv[1]);
                v = apply("find_player", simul_efun_ob, 1, ORIGIN_EFUN);

                if (v && v->type == T_OBJECT) {
                    referrer_obj = v->u.ob;
                    referrer_name = sv[1].u.string;
                }
                else {
                    referrer_obj = NULL;
                    referrer_name = sv[1].u.string;
                }
            }
#endif
        }
        if (sv[1].type == T_OBJECT && sv[1].u.ob) { 
            referrer_obj = sv[1].u.ob;
            referrer_name = NULL;
        }
    }

    if (referee && (referrer_obj || referrer_name)) {
        result = reference_allowed(referee, referrer_obj, referrer_name);

        pop_n_elems(num_arg);
        push_number(result);
    } else { 
        pop_n_elems(num_arg);
        push_undefined();
    }
}
Example #8
0
PMOD_EXPORT void convert_svalue_to_bignum(struct svalue *s)
{
  push_svalue(s);
  convert_stack_top_to_bignum();
  free_svalue(s);
  *s=sp[-1];
  sp--;
  dmalloc_touch_svalue(sp);
}
Example #9
0
static void image_ttf_face_names(INT32 args)
{
   int n,i;
   int has[8]={0,0,0,0,0,0,0,0}; /* iso8859=20, unicode=30, any=1 */
   char *hasname[8]={"copyright","family","style","full",
		     "expose","version","postscript","trademark"};
   struct array *a,*b;

   image_ttf_face__names(args);

   if (sp[-1].type!=T_ARRAY)
      Pike_error("Image.TTF.Face->names(): internal error, weird _names()\n");

   a=sp[-1].u.array;

   n=0;
   for (i=0; i<a->size; i++)
   {
      int ihas=1;
      int what;
      b=a->item[i].u.array;

      what=b->item[3].u.integer;
      if (what>=8 || what<0) continue; /* weird */
      switch (b->item[0].u.integer*100+b->item[1].u.integer)
      {
	 case 301: /* M$:  unicode */
	 case 300: /* M$:  unicode (?) */
	    ihas=30;
	    break;
	 case 202: /* ISO: iso-8859-1 */
	    ihas=20;
	    break;
      }
      if (ihas<has[what]) continue; /* worse */

      push_text(hasname[what]);

      if (ihas==30) /* unicode, M$ but weird enough correct byteorder */
      {
	 ptrdiff_t n = b->item[4].u.string->len/2;
	 struct pike_string *ps=begin_wide_shared_string(n,1);
	 p_wchar1 *d=STR1(ps);
	 p_wchar0 *s=STR0(b->item[4].u.string);
	 while (n--) *(d++)=((p_wchar1)s[0]<<8)|(p_wchar1)s[1],s+=2;
	 push_string(end_shared_string(ps));
      }
      else
	 push_svalue(b->item+4);

      n++;
   }
   f_aggregate_mapping(n*2);
   stack_swap();
   pop_stack();
}
Example #10
0
struct vector *
make_unique(struct vector *arr, struct closure *fun, struct svalue *skipnum)
{
    struct vector *res, *ret;
    struct unique *head, *nxt, *nxt2;
    
    int cnt, ant, cnt2;
    
    if (arr->size < 1)
	return allocate_array(0);

    head = 0; 
    ant = 0; 
    INCREF(arr->ref);
    for(cnt = 0; cnt < arr->size; cnt++) 
    {
	if (arr->item[cnt].type == T_OBJECT)
	{
            push_svalue(&arr->item[cnt]);
            (void)call_var(1, fun);

	    if ((!sp) || (sp->type != skipnum->type) || !equal_svalue(sp, skipnum)) 
	    {
		if (sp) 
		{
		    ant = put_in(&head, sp, &(arr->item[cnt]));
		}
	    }

            pop_stack();
	}
    }
    DECREF(arr->ref);
    ret = allocate_array(ant);
    
    for (cnt = ant - 1; cnt >= 0; cnt--) /* Reverse to compensate put_in */
    {
	ret->item[cnt].type = T_POINTER;
	ret->item[cnt].u.vec = res = allocate_array(head->count);
	nxt2 = head;
	head = head->next;
	cnt2 = 0;
	while (nxt2) 
	{
	    assign_svalue_no_free (&res->item[cnt2++], nxt2->val);
	    free_svalue(&nxt2->mark);
	    nxt = nxt2->same;
/*	    tmpfree((char *) nxt2); */
	    nxt2 = nxt;
	}
	if (!head) 
	    break; /* It shouldn't but, to avoid skydive just in case */
    }
    return ret;
}
Example #11
0
static void
efun_write(struct svalue *fp)
{
    push_number(0);

    if (!command_giver)
    {
	if (fp[0].type == T_STRING)
	    (void)printf("%s", fp[0].u.string);
	return;
    }
    push_svalue(fp);
    (void)apply("catch_tell", command_giver, 1, 0);
}
Example #12
0
void implode_array P4(funptr_t *, fp, array_t *, arr, 
		      svalue_t *, dest, int, first_on_stack) {
    int i = 0, n;
    svalue_t *v;

    if (first_on_stack) {
	if (!(n = arr->size)) {
	    *dest = *sp--;
	    return;
	}
    } else {
	if (!(n = arr->size)) {
	    *dest = const0;
	    return;
	} else if (n == 1) {
	    assign_svalue_no_free(dest, &arr->item[0]);
	    return;
	}
    }

    if (!first_on_stack)
	push_svalue(&arr->item[i++]);
	
    while (1) {
	push_svalue(&arr->item[i++]);
	v = call_function_pointer(fp, 2);
	if (!v) {
	    *dest = const0;
	    return;
	}
	if (i < n)
	    push_svalue(v);
	else
	    break;
    }
    assign_svalue_no_free(dest, v);
}
Example #13
0
static void pextsEndDocument(void *ctx)
{
  DBG_FUNC_ENTER();
  if (CB_ABSENT(endDocumentSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  push_svalue(&THIS->user_data);
  CB_CALL(endDocumentSAX, 2);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #14
0
/* Runs all elements of an array through fun
   and replaces each value in arr by the value returned by fun
   */
struct vector *
map_array (struct vector *arr, struct closure *fun)
{
    struct vector *r;
    int cnt;

    r = allocate_array(arr->size);
    push_vector(r, 0);
    for (cnt = 0; cnt < arr->size; cnt++) {
	push_svalue(&arr->item[cnt]);
	(void)call_var(1, fun);
	r->item[cnt] = *sp;	/* Just copy it.  Reference count is correct */
	sp--;			/* since we loose a reference here. */
    }
    sp--;
    return r;
}
Example #15
0
static void pextsComment(void *ctx, const xmlChar *value)
{
  DBG_FUNC_ENTER();
  if (CB_ABSENT(commentSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  safe_push_text(value);
  push_svalue(&THIS->user_data);
  CB_CALL(commentSAX, 3);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #16
0
/* New version used when not in -o mode. The epilog() in master.c is
 * supposed to return an array of files (castles in 2.4.5) to load. The array
 * returned by apply() will be freed at next call of apply(), which means that
 * the ref count has to be incremented to protect against deallocation.
 *
 * The master object is asked to do the actual loading.
 */
void preload_objects (int eflag)
{
    VOLATILE array_t *prefiles;
    svalue_t *ret;
    VOLATILE int ix;
    error_context_t econ;

    save_context(&econ);
    if (SETJMP(econ.context)) {
        restore_context(&econ);
        pop_context(&econ);
        return;
    }
    push_number(eflag);
    ret = apply_master_ob(APPLY_EPILOG, 1);
    pop_context(&econ);
    if ((ret == 0) || (ret == (svalue_t *)-1) || (ret->type != T_ARRAY))
        return;
    else
        prefiles = ret->u.arr;
    if ((prefiles == 0) || (prefiles->size < 1))
        return;

    debug_message("\nLoading preloaded files ...\n");
    prefiles->ref++;
    ix = 0;
    /* in case of an error, effectively do a 'continue' */
    save_context(&econ);
    if (SETJMP(econ.context)) {
        restore_context(&econ);
        ix++;
    }
    for ( ; ix < prefiles->size; ix++) {
        if (prefiles->item[ix].type != T_STRING)
            continue;

        set_eval(max_cost);

        push_svalue(((array_t *)prefiles)->item + ix);
        (void) apply_master_ob(APPLY_PRELOAD, 1);
    }
    free_array((array_t *)prefiles);
    pop_context(&econ);
}       /* preload_objects() */
Example #17
0
static int got_port_event (struct fd_callback_box *box, int DEBUGUSED(event))
{
  struct port *p = (struct port *) box;
#ifdef PIKE_DEBUG
#ifndef __NT__
  if(!query_nonblocking(p->box.fd))
    Pike_fatal("Port is in blocking mode in port accept callback!!!\n");
#endif
  if (event != PIKE_FD_READ)
    Pike_fatal ("Got unexpected event %d.\n", event);
#endif

  p->my_errno = errno;		/* Propagate backend setting. */
  p->immediate_cnt++;
  push_svalue (&p->id);
  apply_svalue(& p->accept_callback, 1);
  pop_stack();
  return 0;
}
Example #18
0
static void pextsProcessingInstruction(void *ctx, const xmlChar *target, const xmlChar *data)
{
  DBG_FUNC_ENTER();
  if (CB_ABSENT(processingInstructionSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  safe_push_text(target);
  safe_push_text(data);
  push_svalue(&THIS->user_data);
  CB_CALL(processingInstructionSAX, 4);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #19
0
static int pextsHasExternalSubset(void *ctx)
{
  struct svalue   sv;
  
  DBG_FUNC_ENTER();
  if (CB_ABSENT(hasExternalSubsetSAX)) {
    DBG_FUNC_LEAVE();
    return 0;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  push_svalue(&THIS->user_data);
  CB_CALL(hasExternalSubsetSAX, 2);
  stack_pop_to(&sv);
  
  DBG_FUNC_LEAVE();
  return sv.u.integer;
}
Example #20
0
static int pextsIsStandalone(void *ctx)
{
  struct svalue   sv;
  
  DBG_FUNC_ENTER();
  if (CB_ABSENT(isStandaloneSAX)) {
    DBG_FUNC_LEAVE();
    return 1;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  push_svalue(&THIS->user_data);
  CB_CALL(isStandaloneSAX, 2);
  stack_pop_to(&sv);
  
  DBG_FUNC_LEAVE();
  return sv.u.integer;
}
Example #21
0
static void pextsExternalSubset(void *ctx, const xmlChar *name, const xmlChar *externalId, const xmlChar *systemId)
{
  DBG_FUNC_ENTER();
  if (CB_ABSENT(externalSubsetSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  safe_push_text(name);
  safe_push_text(externalId);
  safe_push_text(systemId);
  push_svalue(&THIS->user_data);
  CB_CALL(externalSubsetSAX, 5);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #22
0
static void pextsAttributeDecl(void *ctx, const xmlChar *elem, const xmlChar *fullname, int type, int def,
                               const xmlChar *defaultValue, xmlEnumerationPtr tree)
{
  int  nenum;
  
  DBG_FUNC_ENTER();
  if (CB_ABSENT(attributeDeclSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  safe_push_text(elem);
  safe_push_text(fullname);
  push_int(type);
  push_int(def);
  safe_push_text(defaultValue);
  push_svalue(&THIS->user_data);
  
  if (tree) {
    xmlEnumerationPtr   tmp = tree;
    struct array      *arr;
    
    nenum = 0;
    while (tree) {
      safe_push_text(tmp->name);
      tmp = tmp->next;
      nenum++;
    }
    arr = aggregate_array(nenum);
    push_array(arr);
  } else
    push_int(0);

  CB_CALL(attributeDeclSAX, 8);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #23
0
static void pextsNotationDecl(void *ctx, const xmlChar *name, const xmlChar *publicId, const xmlChar *systemId)
{
  DBG_FUNC_ENTER();
  if (CB_ABSENT(notationDeclSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  safe_push_text(name);
  safe_push_text(publicId);
  safe_push_text(systemId);
  push_svalue(&THIS->user_data);
  
  CB_CALL(notationDeclSAX, 5);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #24
0
static void pextsCdataBlock(void *ctx, const xmlChar *value, int len)
{
  DBG_FUNC_ENTER();
  if (CB_ABSENT(cdataBlockSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  if (value)
    push_string(make_shared_binary_string((const char*)value, (size_t) len));
  else
    push_int(0);
  push_svalue(&THIS->user_data);
  CB_CALL(cdataBlockSAX, 3);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #25
0
static void pextsIgnorableWhitespace(void *ctx, const xmlChar *ch, int len)
{
  DBG_FUNC_ENTER();
  if (CB_ABSENT(ignorableWhitespaceSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  if (ch && len)
    push_string(make_shared_binary_string((const char*)ch, (size_t) len));
  else
    push_int(0);
  push_svalue(&THIS->user_data);
  CB_CALL(ignorableWhitespaceSAX, 3);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #26
0
/* Called when the sending is finished. Either due to broken connection
 * or no more data to send.
 */
static void finished(void)
{
  DERR(fprintf(stderr, "Done writing (%d sent)\n", (INT32)THIS->written));

  THIS->finished   = 1;
  while(THIS->inputs != NULL) {
    free_input(THIS->inputs);
  }

  if(THIS->outp != NULL) {
    free_output(THIS->outp);
    THIS->outp = NULL;
  }

  if(THIS->cb.type != T_INT)
  {
    DERR(fprintf(stderr, "Calling done callback\n"));
    push_svalue(&(THIS->args));
    apply_svalue(&(THIS->cb),1);
    pop_stack();
  }
}
Example #27
0
static void pextsEntityDecl(void *ctx, const xmlChar *name, int type, const xmlChar *publicId,
                            const xmlChar *systemId, xmlChar *content)
{
  DBG_FUNC_ENTER();
  if (CB_ABSENT(entityDeclSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  safe_push_text(name);
  push_int(type);
  safe_push_text(publicId);
  safe_push_text(systemId);
  safe_push_text(content);
  push_svalue(&THIS->user_data);

  CB_CALL(entityDeclSAX, 7);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #28
0
static void pextsStartElement(void *ctx, const xmlChar *name, const xmlChar **atts)
{
  int              npairs;
  const xmlChar  **tmp;
  
  DBG_FUNC_ENTER();
  if (CB_ABSENT(startElementSAX)) {
    DBG_FUNC_LEAVE();
    return;
  }

  THIS->ctxt = (xmlParserCtxtPtr)ctx;
  
  push_object(this_object());
  safe_push_text(name);
  if (atts) {
    npairs = 0;
    tmp = atts;
    while (tmp && *tmp) {
      safe_push_text(*tmp);
      tmp++;
      safe_push_text(*tmp);
      tmp++;
      npairs += 2;
    }
    f_aggregate_mapping(npairs);
  } else {
    push_int(0);
  }
  push_svalue(&THIS->user_data);
  
  CB_CALL(startElementSAX, 4);
  pop_stack();
  
  DBG_FUNC_LEAVE();
}
Example #29
0
void image_xbm_encode( INT32 args )
{
  struct image *img = NULL;
  struct pike_string *name = NULL, *buf;
  if (!args)
    Pike_error("Image.XBM.encode: too few arguments\n");
   
  if (Pike_sp[-args].type!=PIKE_T_OBJECT ||
      !(img=(struct image*)
        get_storage(Pike_sp[-args].u.object,image_program)))
    Pike_error("Image.XBM.encode: illegal argument 1\n");
   
  if (!img->img)
    Pike_error("Image.XBM.encode: no image\n");

  if (args>1)
  {
    if (Pike_sp[1-args].type!=PIKE_T_MAPPING)
      Pike_error("Image.XBM.encode: illegal argument 2\n");
      
    push_svalue(Pike_sp+1-args);
    ref_push_string(param_name); 
    f_index(2);
    if(Pike_sp[-1].type == PIKE_T_STRING)
    {
      if(Pike_sp[-1].u.string->size_shift)
        Pike_error("The name of the image must be a normal non-wide string (sorry, not my fault)\n");
      name = Pike_sp[-1].u.string;
    }
    pop_stack();
  }

  buf = save_xbm( img, name );
  pop_n_elems(args);
  push_string( buf );
}
Example #30
0
void f_addn_temp () {
    int i, j;
    object_t *ob;
    unsigned short type;
    mapping_t *map;
    svalue_t *value;
    char *src, *dst;
    char *tmpstr;

    if( st_num_arg == 3 )
    {
        ob = sp->u.ob;
        pop_stack();
    }
    else
        ob = current_object;

    i = find_global_variable(ob->prog, "tmp_dbase", &type, 0);
    if (i == -1)
    {
        pop_2_elems();
        error("(addn_temp) %s 物件未宣告全域映射资料库变数。\n", ob->obname);
    }

    value = &ob->variables[i];

    if( value->type != T_MAPPING )
    {
    	pop_2_elems();
    	error("(addn_temp) %s 物件的资料库变数型态错误。\n", ob->obname);
    }

    map = value->u.map;
    src = (char *)(sp-1)->u.string;
    dst = tmpstr = (char *)DMALLOC(SVALUE_STRLEN(sp-1) + 1, TAG_STRING, "addn_temp");
    j=0;

    while (*src)
    {
    	i=0;
    	if( ++j > 20 )
	{
    		pop_2_elems();
    		error("(addn_temp) %s too deep mapping(20)。\n", ob->obname);
    	}

	while (*src != '/' && *src)
	{
	    *(dst+i) = *src++;
	    i++;
	}

	if (*src == '/')
	{
	    while (*++src == '/');
	    if(!i) continue;
	}
	*(dst+i) = '\0';

	value = find_string_in_mapping(map, tmpstr);

	if(!*src)
	{
    		if( value == &const0u || value->type != T_NUMBER )
    		{
    			value = insert_in_mapping(map, dst);
			*value = *sp--;
    		}
    		else
    			value->u.number += (sp--)->u.number;
    		break;
    	}

	if(value == &const0u || value->type != T_MAPPING)
	{
    		value = insert_in_mapping(map, dst);
		value->type = T_MAPPING;
		value->u.map = allocate_mapping(0);
	}

	map = value->u.map;
	dst = tmpstr;
    }

    FREE(tmpstr);
    free_string_svalue(sp--);
    push_svalue(value);
}