Example #1
0
static int
dict_insert(DICT *dict, struct object *obj, void *data)
{
    INFUN();
    
    if (!obj)
        return DICT_NULL_OBJECT;

    if (!data)
        return DICT_NULL_DATA;

    if (!dict)
        return DICT_NULL_DICT;
    

    if (dict->used && (dict->used >= dict->dict->data->num_keypairs)) {
        struct mapping  *nmap, *tmp;

        nmap = allocate_mapping(dict->dict->data->num_keypairs << 1);
        tmp = merge_mappings(dict->dict, nmap, PIKE_ARRAY_OP_AND);
        free_mapping(dict->dict);
        free_mapping(nmap);
        dict->dict = tmp;
    }

    {
        struct svalue   skey, sval, *tmp;
        char            addr[64];
        
        sval.type = T_OBJECT;
        sval.u.object = obj;

        sprintf(addr, "0x%X", (unsigned)data);
        skey.type = T_STRING;
        skey.u.string = make_shared_string(addr);

        tmp = low_mapping_lookup(dict->dict, &skey);
        if (tmp) {
            free_string(skey.u.string);
	    OUTFUN();
            return DICT_EXISTS;
        }

        mapping_insert(dict->dict, &skey, &sval);
        dict->used++;
    }

    OUTFUN();
    return DICT_OK;
}
Example #2
0
static struct object*
dict_lookup(DICT *dict, void *data)
{
    struct svalue   *obj, skey;
    char             addr[64];
    
    INFUN();
    if (!dict || !data)
        return NULL;

    sprintf(addr, "0x%X", (unsigned)data);
    skey.type = T_STRING;
    skey.u.string = make_shared_string(addr);
    
    obj = low_mapping_lookup(dict->dict, &skey);

    free_string(skey.u.string);

    OUTFUN();
    return obj->u.object;
}
Example #3
0
static void f_buf_append( INT32 args )
{
  struct pike_string *str;
  struct svalue skey, sval; /* header, value */
  int slash_n = 0, cnt, num;
  unsigned char *pp,*ep;
  struct svalue *tmp;
  int os=0, i, j=0, l, qmark = -1;
  unsigned char *in, *query;
  
  if( Pike_sp[-1].type != T_STRING )
    Pike_error("Wrong type of argument to append()\n");
  
  str = Pike_sp[-1].u.string;
  
  if( str->len >= BUF->free ) {
    pop_n_elems(args);
    push_int(413); /* Request Entity Too Large */
    return;
  }

  MEMCPY( BUF->pos, str->str, str->len );

  for( ep = (BUF->pos + str->len), pp = MAX(BUF->data, BUF->pos-3); 
       pp < ep && slash_n < 2; pp++ )
    if( *pp == '\n' )       slash_n++;
    else if( *pp != '\r' )  slash_n=0;
  
  BUF->free -= str->len;
  BUF->pos += str->len;
  BUF->pos[0] = 0;
  pop_n_elems( args );
  if( slash_n != 2 )
  {
    /* need more data */
    push_int( 0 );
    return;
  }

  skey.type = sval.type = T_STRING;

  sval.u.string = make_shared_binary_string( (char *)pp, BUF->pos - pp);
  mapping_insert(BUF->other, SVAL(data), &sval); /* data */
  free_string(sval.u.string);
  
  in = BUF->data;
  l = pp - BUF->data;

  /* find method */
  for( i = 0; i < l; i++ ) {
    if( in[i] == ' ' ) 
      break;
    else if(in[i] == '\n') {
      push_int( 400 ); /* Bad Request */
      return;
    }
  }
  sval.u.string = make_shared_binary_string((char *)in, i);
  mapping_insert(BUF->other, SVAL(method), &sval);
  free_string(sval.u.string);
  
  i++; in += i; l -= i;

  /* find file */
  for( i = 0; i < l; i++ ) {
    if(in[i] == ' ') {
      break;
    } else  if(in[i] == '\n') {
      push_int( 400 ); /* Bad Request */
      return;
    }
  }
  sval.u.string = make_shared_binary_string((char *)in, i);
  mapping_insert(BUF->other, SVAL(raw_url), &sval);
  free_string(sval.u.string);

  /* Decode file part and return pointer to query, if any */
  query = char_decode_url(in, i);

  /* Decoded, query-less file up to the first \0 */
  sval.u.string = make_shared_string((char *)in); 
  mapping_insert(BUF->other, SVAL(file), &sval);
  free_string(sval.u.string);
  
  if(query != NULL)  {
    /* Store the query string */
    sval.u.string = make_shared_binary_string((char *)query, i - (query-in)); /* Also up to first null */
    mapping_insert(BUF->other, SVAL(query), &sval);
    free_string(sval.u.string);
  }
  
  i++; in += i; l -= i;

  /* find protocol */
  for( i = 0; i < l; i++ ) {
    if( in[i] == '\n' ) break;
    else if(in[i] == ' ') {
      push_int( 400 ); /* Bad Request */
      return;
    }
  }
  if( in[i-1] != '\r' ) 
    i++;
  sval.u.string = make_shared_binary_string((char *)in, i-1);
  mapping_insert(BUF->other, SVAL(protocol), &sval);
  free_string(sval.u.string);

  in += i; l -= i;
  if( *in == '\n' ) (in++),(l--);

  for(i = 0; i < l; i++)
  {
    if(in[i] >= 'A' && in[i] <= 'Z') in[i] |= 32; /* Lowercasing the header */
    else if( in[i] == ':' )
    {
      /* in[os..i-1] == the header */
      
      skey.u.string = make_shared_binary_string((char*)in+os, i - os);
      os = i+1;
      while(in[os]==' ') os++; /* Remove initial spaces */
      for(j=os;j<l;j++)  if( in[j] == '\n' || in[j]=='\r')  break; 

      if((tmp = low_mapping_lookup(BUF->headers, &skey)) &&
         tmp->type == T_STRING)
      {
        int len = j - os + 1;
        int len2 = len +tmp->u.string->len;
        sval.u.string = begin_shared_string(len2);
        MEMCPY(sval.u.string->str,
               tmp->u.string->str, tmp->u.string->len);
        sval.u.string->str[tmp->u.string->len] = ',';
        MEMCPY(sval.u.string->str + tmp->u.string->len + 1,
               (char*)in + os, len);
        sval.u.string = end_shared_string(sval.u.string);
      } else {
        sval.u.string = make_shared_binary_string((char*)in + os, j - os);
      }
      
      mapping_insert(BUF->headers, &skey, &sval);
      if( in[j+1] == '\n' ) j++;
      os = j+1;
      i = j;
      free_string(sval.u.string);
      free_string(skey.u.string);
    }
  }
  push_int(1);
}
Example #4
0
/* This function parses the query string */
static void f_parse_query_string( INT32 args )     
{
  struct pike_string *query; /* Query string to parse */
  struct svalue *exist, skey, sval; /* svalues used */
  struct mapping *variables; /* Mapping to store vars in */
  unsigned char *ptr;   /* Pointer to current char in loop */
  unsigned char *name;  /* Pointer to beginning of name */
  unsigned char *equal; /* Pointer to the equal sign */
  unsigned char *end;   /* Pointer to the ending null char */
  int namelen, valulen; /* Length of the current name and value */
  get_all_args("Caudium.parse_query_string", args, "%S%m", &query, &variables);
  skey.type = sval.type = T_STRING;
  /* end of query string */
  end = (unsigned char *)(query->str + query->len);
  name = ptr = (unsigned char *)query->str;
  equal = NULL;
  for(; ptr <= end; ptr++) {
    switch(*ptr)
    {
     case '=':
      /* Allow an unencoded '=' in the value. It's invalid but... */
      if(equal == NULL)
	equal=ptr;
      break;
     case '\0':
      if(ptr != end)
	continue;
     case ';': /* It's recommended to support ';'
		  instead of '&' in query strings... */
     case '&':
      if(equal == NULL) { /* value less variable, we can ignore this */
	name = ptr+1;
	break;
      }
      namelen = equal - name;
      valulen = ptr - ++equal;
      skey.u.string = url_decode(name, namelen, 0);
      if (skey.u.string == NULL) { /* OOM. Bail out */
	Pike_error("Caudium.parse_query_string(): Out of memory in url_decode().\n");
      }
      exist = low_mapping_lookup(variables, &skey);
      if(exist == NULL || exist->type != T_STRING) {
	sval.u.string = url_decode(equal, valulen, 0);
	if (sval.u.string == NULL) { /* OOM. Bail out */
	  Pike_error("Caudium.parse_query_string(): "
		     "Out of memory in url_decode().\n");
	}
      } else {
	/* Add strings separed with '\0'... */
	struct pike_string *tmp;
	tmp = url_decode(equal, valulen, 1);
	if (tmp == NULL) {
	  Pike_error("Caudium.parse_query_string(): "
		     "Out of memory in url_decode().\n");
	}
	sval.u.string = add_shared_strings(exist->u.string, tmp);
	free_string(tmp);
      }
      mapping_insert(variables, &skey, &sval);
      free_string(skey.u.string);
      free_string(sval.u.string);

      /* Reset pointers */
      equal = NULL;
      name = ptr+1;
    }
  }
  pop_n_elems(args);
}