pike.git / src / builtin_functions.c

version» Context lines:

pike.git/src/builtin_functions.c:1:   /*   || This file is part of Pike. For copyright information see COPYRIGHT.   || Pike is distributed under GPL, LGPL and MPL. See the file COPYING   || for more information. - || $Id: builtin_functions.c,v 1.650 2008/01/26 22:34:17 mast Exp $ + || $Id: builtin_functions.c,v 1.651 2008/01/29 20:10:06 grubba Exp $   */      #include "global.h"   #include "interpret.h"   #include "svalue.h"   #include "pike_macros.h"   #include "object.h"   #include "program.h"   #include "array.h"   #include "pike_error.h"
pike.git/src/builtin_functions.c:3327:       /* Perform the actual conversion. */    new_type = object_type_to_program_type(nn->type);    if (new_type) {    free_type(n->type);    n->type = new_type;    }    return NULL;   }    - /*! @decl string reverse(string s) -  *! @decl array reverse(array a) -  *! @decl int reverse(int i) + /*! @decl string reverse(string s, int|void start, int|void end) +  *! @decl array reverse(array a, int|void start, int|void end) +  *! @decl int reverse(int i, int|void start, int|void end)    *!    *! Reverses a string, array or int.    *! -  +  *! @param s +  *! String to reverse. +  *! @param a +  *! Array to reverse. +  *! @param i +  *! Integer to reverse. +  *! @param start +  *! Optional start index of the range to reverse. +  *! Default: @expr{0@} (zero). +  *! @param end +  *! Optional end index of the range to reverse. +  *! Default for strings: @expr{sizeof(s)-1@}. +  *! Default for arrays: @expr{sizeof(a)-1@}. +  *! Default for integers: @expr{Pike.get_runtime_info()->int_size - 1@}. +  *!    *! This function reverses a string, char by char, an array, value    *! by value or an int, bit by bit and returns the result. It's not    *! destructive on the input value.    *!    *! Reversing strings can be particularly useful for parsing difficult    *! syntaxes which require scanning backwards.    *!    *! @seealso    *! @[sscanf()]    */   PMOD_EXPORT void f_reverse(INT32 args)   { -  if(args < 1) -  SIMPLE_TOO_FEW_ARGS_ERROR("reverse", 1); +  struct svalue *sv; +  int start = 0, end = -1;    -  switch(Pike_sp[-args].type) +  get_all_args("reverse", args, "%*.%d%d", &sv, &start, &end); +  +  switch(sv->type)    {    case T_STRING:    {    INT32 e;    struct pike_string *s; -  s=begin_wide_shared_string(Pike_sp[-args].u.string->len, -  Pike_sp[-args].u.string->size_shift); -  switch(Pike_sp[-args].u.string->size_shift) +  if (start < 0) { +  start = 0; +  } else if (start >= sv->u.string->len) { +  /* Noop. */ +  pop_n_elems(args-1); +  break; +  } +  if ((end < 0) || (end >= sv->u.string->len)) { +  end = sv->u.string->len; +  } else if (end <= start) { +  /* Noop. */ +  pop_n_elems(args-1); +  break; +  } else { +  end++; +  } +  s=begin_wide_shared_string(sv->u.string->len, sv->u.string->size_shift); +  switch(sv->u.string->size_shift)    {    case 0: -  for(e=0;e<Pike_sp[-args].u.string->len;e++) -  STR0(s)[e]=STR0(Pike_sp[-args].u.string)[Pike_sp[-args].u.string->len-1-e]; +  for(e=0;e<start;e++) +  STR0(s)[e]=STR0(sv->u.string)[e]; +  for(;e<end;e++) +  STR0(s)[e]=STR0(sv->u.string)[end-1-e-start]; +  for(;e<sv->u.string->len;e++) +  STR0(s)[e]=STR0(sv->u.string)[e];    break;       case 1: -  for(e=0;e<Pike_sp[-args].u.string->len;e++) -  STR1(s)[e]=STR1(Pike_sp[-args].u.string)[Pike_sp[-args].u.string->len-1-e]; +  for(e=0;e<start;e++) +  STR1(s)[e]=STR1(sv->u.string)[e]; +  for(;e<end;e++) +  STR1(s)[e]=STR1(sv->u.string)[end-1-e-start]; +  for(;e<sv->u.string->len;e++) +  STR1(s)[e]=STR1(sv->u.string)[e];    break;       case 2: -  for(e=0;e<Pike_sp[-args].u.string->len;e++) -  STR2(s)[e]=STR2(Pike_sp[-args].u.string)[Pike_sp[-args].u.string->len-1-e]; +  for(e=0;e<start;e++) +  STR2(s)[e]=STR2(sv->u.string)[e]; +  for(;e<end;e++) +  STR2(s)[e]=STR2(sv->u.string)[end-1-e-start]; +  for(;e<sv->u.string->len;e++) +  STR2(s)[e]=STR2(sv->u.string)[e];    break;    }    s=low_end_shared_string(s);    pop_n_elems(args);    push_string(s);    break;    }       case T_INT:    { -  +  /* FIXME: Ought to use INT_TYPE! */    INT32 e;    e=Pike_sp[-args].u.integer;    e=((e & 0x55555555UL)<<1) + ((e & 0xaaaaaaaaUL)>>1);    e=((e & 0x33333333UL)<<2) + ((e & 0xccccccccUL)>>2);    e=((e & 0x0f0f0f0fUL)<<4) + ((e & 0xf0f0f0f0UL)>>4);    e=((e & 0x00ff00ffUL)<<8) + ((e & 0xff00ff00UL)>>8);    e=((e & 0x0000ffffUL)<<16)+ ((e & 0xffff0000UL)>>16);    Pike_sp[-args].u.integer=e;    pop_n_elems(args-1);    break;    }       /* FIXME: Bignum support. */       case T_ARRAY:    { -  struct array *a; -  a=reverse_array(Pike_sp[-args].u.array); +  struct array *a = sv->u.array; +  a = reverse_array(a, start, (end < 0)?a->size:end);    pop_n_elems(args);    push_array(a);    break;    }       default:    SIMPLE_BAD_ARG_ERROR("reverse", 1, "string|int|array");    }   }   
pike.git/src/builtin_functions.c:9152:    tFunc(tInt,tString), OPT_EXTERNAL_DEPEND);       ADD_EFUN2("replace", f_replace,    tOr5(tFunc(tStr tStr tStr,tStr),    tFunc(tStr tArr(tStr) tOr(tArr(tStr), tStr), tStr),    tFunc(tStr tMap(tStr,tStr),tStr),    tFunc(tSetvar(0,tArray) tMix tMix,tVar(0)),    tFunc(tSetvar(1,tMapping) tMix tMix,tVar(1))),    OPT_TRY_OPTIMIZE, optimize_replace, 0);    - /* function(int:int)|function(string:string)|function(0=array:0) */ +     ADD_EFUN("reverse",f_reverse, -  tOr3(tFunc(tInt,tInt), -  tFunc(tStr,tStr), -  tFunc(tSetvar(0, tArray),tVar(0))),0); +  tOr3(tFunc(tInt tOr(tVoid, tInt) tOr(tVoid, tInt), tInt), +  tFunc(tStr tOr(tVoid, tInt) tOr(tVoid, tInt), tStr), +  tFunc(tSetvar(0, tArray) tOr(tVoid, tInt) tOr(tVoid, tInt), +  tVar(0))),0);      /* function(mixed,array:array) */    ADD_EFUN("rows",f_rows,    tOr6(tFunc(tMap(tSetvar(0,tMix),tSetvar(1,tMix)) tArr(tVar(0)),    tArr(tVar(1))),    tFunc(tSet(tSetvar(0,tMix)) tArr(tVar(0)), tArr(tInt01)),    tFunc(tString tArr(tInt), tArr(tInt)),    tFunc(tArr(tSetvar(0,tMix)) tArr(tInt), tArr(tVar(1))),    tFunc(tArray tArr(tNot(tInt)), tArray),    tFunc(tOr4(tObj,tFunction,tPrg(tObj),tInt) tArray, tArray)), 0);