[gforth] / gforth / prim  

gforth: gforth/prim

Diff for /gforth/prim between version 1.132 and 1.155

version 1.132, Thu Aug 7 08:50:00 2003 UTC version 1.155, Fri Aug 27 15:53:50 2004 UTC
Line 136 
Line 136 
 \ throw execute, cfa and NEXT1 out?  \ throw execute, cfa and NEXT1 out?
 \ macroize *ip, ip++, *ip++ (pipelining)?  \ macroize *ip, ip++, *ip++ (pipelining)?
   
   \ Stack caching setup
   
   ifdef(`M4_ENGINE_FAST', `include(cache1.vmg)', `include(cache0.vmg)')
   
 \ these m4 macros would collide with identifiers  \ these m4 macros would collide with identifiers
 undefine(`index')  undefine(`index')
 undefine(`shift')  undefine(`shift')
 undefine(`symbols')  undefine(`symbols')
   
   \F 0 [if]
   
   \ run-time routines for non-primitives.  They are defined as
   \ primitives, because that simplifies things.
   
   (docol) ( -- R:a_retaddr )      gforth-internal paren_docol
   ""run-time routine for colon definitions""
   #ifdef NO_IP
   a_retaddr = next_code;
   INST_TAIL;
   goto **(Label *)PFA(CFA);
   #else /* !defined(NO_IP) */
   a_retaddr = (Cell *)IP;
   SET_IP((Xt *)PFA(CFA));
   #endif /* !defined(NO_IP) */
   
   (docon) ( -- w )        gforth-internal paren_docon
   ""run-time routine for constants""
   w = *(Cell *)PFA(CFA);
   #ifdef NO_IP
   INST_TAIL;
   goto *next_code;
   #endif /* defined(NO_IP) */
   
   (dovar) ( -- a_body )   gforth-internal paren_dovar
   ""run-time routine for variables and CREATEd words""
   a_body = PFA(CFA);
   #ifdef NO_IP
   INST_TAIL;
   goto *next_code;
   #endif /* defined(NO_IP) */
   
   (douser) ( -- a_user )  gforth-internal paren_douser
   ""run-time routine for constants""
   a_user = (Cell *)(up+*(Cell *)PFA(CFA));
   #ifdef NO_IP
   INST_TAIL;
   goto *next_code;
   #endif /* defined(NO_IP) */
   
   (dodefer) ( -- )        gforth-internal paren_dodefer
   ""run-time routine for deferred words""
   #ifndef NO_IP
   ip=IP; /* undo any ip updating that may have been performed by NEXT_P0 */
   #endif /* !defined(NO_IP) */
   SUPER_END; /* !! probably unnecessary and may lead to measurement errors */
   EXEC(*(Xt *)PFA(CFA));
   
   (dofield) ( n1 -- n2 )  gforth-internal paren_field
   ""run-time routine for fields""
   n2 = n1 + *(Cell *)PFA(CFA);
   #ifdef NO_IP
   INST_TAIL;
   goto *next_code;
   #endif /* defined(NO_IP) */
   
   (dodoes) ( -- a_body R:a_retaddr )      gforth-internal paren_dodoes
   ""run-time routine for @code{does>}-defined words""
   #ifdef NO_IP
   a_retaddr = next_code;
   a_body = PFA(CFA);
   INST_TAIL;
   goto **(Label *)DOES_CODE1(CFA);
   #else /* !defined(NO_IP) */
   a_retaddr = (Cell *)IP;
   a_body = PFA(CFA);
   SET_IP(DOES_CODE1(CFA));
   #endif /* !defined(NO_IP) */
   
   (does-handler) ( -- )   gforth-internal paren_does_handler
   ""just a slot to have an encoding for the DOESJUMP,
   which is no longer used anyway (!! eliminate this)""
   
   \F [endif]
   
 \g control  \g control
   
 noop    ( -- )          gforth  noop    ( -- )          gforth
Line 150 
Line 229 
 call    ( #a_callee -- R:a_retaddr )    new  call    ( #a_callee -- R:a_retaddr )    new
 ""Call callee (a variant of docol with inline argument).""  ""Call callee (a variant of docol with inline argument).""
 #ifdef NO_IP  #ifdef NO_IP
   assert(0);
 INST_TAIL;  INST_TAIL;
 JUMP(a_callee);  JUMP(a_callee);
 #else  #else
Line 169 
Line 249 
 #ifndef NO_IP  #ifndef NO_IP
 ip=IP;  ip=IP;
 #endif  #endif
 IF_spTOS(spTOS = sp[0]);  IF_spTOS(spTOS = sp[0]); /* inst_tail would produce a NEXT_P1 */
 SUPER_END;  SUPER_END;
 EXEC(xt);  EXEC(xt);
   
Line 179 
Line 259 
 #ifndef NO_IP  #ifndef NO_IP
 ip=IP;  ip=IP;
 #endif  #endif
 IF_spTOS(spTOS = sp[0]);  IF_spTOS(spTOS = sp[0]); /* inst_tail would produce a NEXT_P1 */
 SUPER_END;  SUPER_END;
 EXEC(*(Xt *)a_addr);  EXEC(*(Xt *)a_addr);
 :  :
Line 244 
Line 324 
 JUMP(a_target);  JUMP(a_target);
 #else  #else
 SET_IP((Xt *)a_target);  SET_IP((Xt *)a_target);
   INST_TAIL;
   NEXT_P2;
 #endif  #endif
   SUPER_CONTINUE;  /* we do our own control flow, so don't append NEXT etc. */
 :  :
  r> @ >r ;   r> @ >r ;
   
Line 353 
Line 436 
 /* dependent upon two's complement arithmetic */  /* dependent upon two's complement arithmetic */
 Cell olddiff = n1-nlimit;  Cell olddiff = n1-nlimit;
 n2=n1+n;  n2=n1+n;
 ,if ((olddiff^(olddiff+n))>=0   /* the limit is not crossed */  ,if (((olddiff^(olddiff+n))    /* the limit is not crossed */
     || (olddiff^n)>=0          /* it is a wrap-around effect */) {       &(olddiff^n))             /* OR it is a wrap-around effect */
       >=0) { /* & is used to avoid having two branches for gforth-native */
 ,:  ,:
  r> swap   r> swap
  r> r> 2dup - >r   r> r> 2dup - >r
Line 383 
Line 467 
     newdiff = -newdiff;      newdiff = -newdiff;
 }  }
 n2=n1+n;  n2=n1+n;
 ,if (diff>=0 || newdiff<0) {  ,if (((~diff)|newdiff)<0) { /* use | to avoid two branches for gforth-native */
 ,)  ,)
   
 \+  \+
Line 594 
Line 678 
 :  :
  rot 2dup swap - >r min swap -text dup   rot 2dup swap - >r min swap -text dup
  IF  rdrop  ELSE  drop r> sgn  THEN ;   IF  rdrop  ELSE  drop r> sgn  THEN ;
   : -text ( c_addr1 u c_addr2 -- n )
    swap bounds
    ?DO  dup c@ I c@ = WHILE  1+  LOOP  drop 0
    ELSE  c@ I c@ - unloop  THEN  sgn ;
 : sgn ( n -- -1/0/1 )  : sgn ( n -- -1/0/1 )
  dup 0= IF EXIT THEN  0< 2* 1+ ;   dup 0= IF EXIT THEN  0< 2* 1+ ;
   
Line 793 
Line 881 
 ud = (UDCell)u1 * (UDCell)u2;  ud = (UDCell)u1 * (UDCell)u2;
 #endif  #endif
 :  :
    >r >r 0 0 r> r> [ 8 cells ] literal 0     0 -rot dup [ 8 cells ] literal -
    DO     DO
        over >r dup >r 0< and d2*+ drop          dup 0< I' and d2*+ drop
        r> 2* r> swap     LOOP ;
    LOOP 2drop ;  
 : d2*+ ( ud n -- ud+n c )  : d2*+ ( ud n -- ud+n c )
    over MINI     over MINI
    and >r >r 2dup d+ swap r> + swap r> ;     and >r >r 2dup d+ swap r> + swap r> ;
Line 904 
Line 991 
   
 rshift  ( u1 n -- u2 )          core    r_shift  rshift  ( u1 n -- u2 )          core    r_shift
 ""Logical shift right by @i{n} bits.""  ""Logical shift right by @i{n} bits.""
   #ifdef BROKEN_SHIFT
     u2 = rshift(u1, n);
   #else
   u2 = u1>>n;    u2 = u1>>n;
   #endif
 :  :
     0 ?DO 2/ MAXI and LOOP ;      0 ?DO 2/ MAXI and LOOP ;
   
 lshift  ( u1 n -- u2 )          core    l_shift  lshift  ( u1 n -- u2 )          core    l_shift
   #ifdef BROKEN_SHIFT
     u2 = lshift(u1, n);
   #else
   u2 = u1<<n;    u2 = u1<<n;
   #endif
 :  :
     0 ?DO 2* LOOP ;      0 ?DO 2* LOOP ;
   
Line 1084 
Line 1179 
 :  :
  r> r> drop >r ;   r> r> drop >r ;
   
 2>r     ( w1 w2 -- R:w1 R:w2 )  core-ext        two_to_r  2>r     ( d -- R:d )    core-ext        two_to_r
 :  :
  swap r> swap >r swap >r >r ;   swap r> swap >r swap >r >r ;
   
 2r>     ( R:w1 R:w2 -- w1 w2 )  core-ext        two_r_from  2r>     ( R:d -- d )    core-ext        two_r_from
 :  :
  r> r> swap r> swap >r swap ;   r> r> swap r> swap >r swap ;
   
 2r@     ( R:w1 R:w2 -- R:w1 R:w2 w1 w2 )        core-ext        two_r_fetch  2r@     ( R:d -- R:d d )        core-ext        two_r_fetch
 :  :
  i' j ;   i' j ;
   
 2rdrop  (  R:w1 R:w2 -- )               gforth  two_r_drop  2rdrop  ( R:d -- )              gforth  two_r_drop
 :  :
  r> r> drop r> drop >r ;   r> r> drop r> drop >r ;
   
Line 1316 
Line 1411 
   
 \g compiler  \g compiler
   
   \+f83headerstring
   
   (f83find)       ( c_addr u f83name1 -- f83name2 )       new     paren_f83find
   for (; f83name1 != NULL; f83name1 = (struct F83Name *)(f83name1->next))
     if ((UCell)F83NAME_COUNT(f83name1)==u &&
         memcasecmp(c_addr, f83name1->name, u)== 0 /* or inline? */)
       break;
   f83name2=f83name1;
   :
       BEGIN  dup WHILE  (find-samelen)  dup  WHILE
           >r 2dup r@ cell+ char+ capscomp  0=
           IF  2drop r>  EXIT  THEN
           r> @
       REPEAT  THEN  nip nip ;
   : (find-samelen) ( u f83name1 -- u f83name2/0 )
       BEGIN  2dup cell+ c@ $1F and <> WHILE  @  dup 0= UNTIL  THEN ;
   : capscomp ( c_addr1 u c_addr2 -- n )
    swap bounds
    ?DO  dup c@ I c@ <>
        IF  dup c@ toupper I c@ toupper =
        ELSE  true  THEN  WHILE  1+  LOOP  drop 0
    ELSE  c@ toupper I c@ toupper - unloop  THEN  sgn ;
   : sgn ( n -- -1/0/1 )
    dup 0= IF EXIT THEN  0< 2* 1+ ;
   
   \-
   
 (listlfind)     ( c_addr u longname1 -- longname2 )     new     paren_listlfind  (listlfind)     ( c_addr u longname1 -- longname2 )     new     paren_listlfind
 longname2=listlfind(c_addr, u, longname1);  longname2=listlfind(c_addr, u, longname1);
 :  :
Line 1326 
Line 1448 
     REPEAT  THEN  nip nip ;      REPEAT  THEN  nip nip ;
 : (findl-samelen) ( u longname1 -- u longname2/0 )  : (findl-samelen) ( u longname1 -- u longname2/0 )
     BEGIN  2dup cell+ @ lcount-mask and <> WHILE  @  dup 0= UNTIL  THEN ;      BEGIN  2dup cell+ @ lcount-mask and <> WHILE  @  dup 0= UNTIL  THEN ;
   : capscomp ( c_addr1 u c_addr2 -- n )
    swap bounds
    ?DO  dup c@ I c@ <>
        IF  dup c@ toupper I c@ toupper =
        ELSE  true  THEN  WHILE  1+  LOOP  drop 0
    ELSE  c@ toupper I c@ toupper - unloop  THEN  sgn ;
   : sgn ( n -- -1/0/1 )
    dup 0= IF EXIT THEN  0< 2* 1+ ;
   
 \+hash  \+hash
   
Line 1349 
Line 1479 
             IF  2drop r> rdrop  EXIT  THEN  THEN              IF  2drop r> rdrop  EXIT  THEN  THEN
         rdrop r>          rdrop r>
  REPEAT nip nip ;   REPEAT nip nip ;
   : -text ( c_addr1 u c_addr2 -- n )
    swap bounds
    ?DO  dup c@ I c@ = WHILE  1+  LOOP  drop 0
    ELSE  c@ I c@ - unloop  THEN  sgn ;
   : sgn ( n -- -1/0/1 )
    dup 0= IF EXIT THEN  0< 2* 1+ ;
   
 (hashkey1)      ( c_addr u ubits -- ukey )              gforth  paren_hashkey1  (hashkey1)      ( c_addr u ubits -- ukey )              gforth  paren_hashkey1
 ""ukey is the hash key for the string c_addr u fitting in ubits bits""  ""ukey is the hash key for the string c_addr u fitting in ubits bits""
Line 1368 
Line 1504 
   
 \+  \+
   
   \+
   
 (parse-white)   ( c_addr1 u1 -- c_addr2 u2 )    gforth  paren_parse_white  (parse-white)   ( c_addr1 u1 -- c_addr2 u2 )    gforth  paren_parse_white
 struct Cellpair r=parse_white(c_addr1, u1);  struct Cellpair r=parse_white(c_addr1, u1);
 c_addr2 = (Char *)(r.n1);  c_addr2 = (Char *)(r.n1);
Line 1463 
Line 1601 
 return (Label *)n;  return (Label *)n;
   
 (system)        ( c_addr u -- wretval wior )    gforth  paren_system  (system)        ( c_addr u -- wretval wior )    gforth  paren_system
 #ifndef MSDOS  wretval = gforth_system(c_addr, u);
 int old_tp=terminal_prepped;  
 deprep_terminal();  
 #endif  
 wretval=system(cstr(c_addr,u,1)); /* ~ expansion on first part of string? */  
 wior = IOR(wretval==-1 || (wretval==127 && errno != 0));  wior = IOR(wretval==-1 || (wretval==127 && errno != 0));
 #ifndef MSDOS  
 if (old_tp)  
   prep_terminal();  
 #endif  
   
 getenv  ( c_addr1 u1 -- c_addr2 u2 )    gforth  getenv  ( c_addr1 u1 -- c_addr2 u2 )    gforth
 ""The string @i{c-addr1 u1} specifies an environment variable. The string @i{c-addr2 u2}  ""The string @i{c-addr1 u1} specifies an environment variable. The string @i{c-addr2 u2}
Line 1561 
Line 1691 
 u = strlen(c_addr);  u = strlen(c_addr);
   
 strsignal       ( n -- c_addr u )       gforth  strsignal       ( n -- c_addr u )       gforth
 c_addr = strsignal(n);  c_addr = (Address)strsignal(n);
 u = strlen(c_addr);  u = strlen(c_addr);
   
 call-c  ( w -- )        gforth  call_c  call-c  ( w -- )        gforth  call_c
Line 2189 
Line 2319 
 #  endif  #  endif
 #endif  #endif
   
   wcall   ( u -- )        gforth
   IF_fpTOS(fp[0]=fpTOS);
   FP=fp;
   sp=(Cell*)(SYSCALL(Cell*(*)(Cell *, void *))u)(sp, &FP);
   fp=FP;
   IF_spTOS(spTOS=sp[0];)
   IF_fpTOS(fpTOS=fp[0]);
   
 \+FFCALL  \+FFCALL
   
 av-start-void   ( c_addr -- )    gforth  av_start_void  av-start-void   ( c_addr -- )    gforth  av_start_void
Line 2219 
Line 2357 
 av_double(alist, r);  av_double(alist, r);
   
 av-longlong        ( d -- )        gforth  av_longlong  av-longlong        ( d -- )        gforth  av_longlong
   #ifdef BUGGY_LONG_LONG
   av_longlong(alist, d.lo);
   #else
 av_longlong(alist, d);  av_longlong(alist, d);
   #endif
   
 av-ptr        ( c_addr -- )        gforth  av_ptr  av-ptr        ( c_addr -- )        gforth  av_ptr
 av_ptr(alist, void*, c_addr);  av_ptr(alist, void*, c_addr);
   
   av-int-r  ( R:w -- )  gforth  av_int_r
   av_int(alist, w);
   
   av-float-r      ( -- )  gforth  av_float_r
   float r = *(Float*)lp;
   lp += sizeof(Float);
   av_float(alist, r);
   
   av-double-r     ( -- )  gforth  av_double_r
   double r = *(Float*)lp;
   lp += sizeof(Float);
   av_double(alist, r);
   
   av-longlong-r   ( R:d -- )      gforth  av_longlong_r
   #ifdef BUGGY_LONG_LONG
   av_longlong(alist, d.lo);
   #else
   av_longlong(alist, d);
   #endif
   
   av-ptr-r        ( R:c_addr -- ) gforth  av_ptr_r
   av_ptr(alist, void*, c_addr);
   
 av-call-void    ( -- )          gforth  av_call_void  av-call-void    ( -- )          gforth  av_call_void
 SAVE_REGS  SAVE_REGS
 av_call(alist);  av_call(alist);
Line 2232 
Line 2397 
 av-call-int    ( -- w )        gforth  av_call_int  av-call-int    ( -- w )        gforth  av_call_int
 SAVE_REGS  SAVE_REGS
 av_call(alist);  av_call(alist);
   REST_REGS
 w = irv;  w = irv;
   
 av-call-float   ( -- r )        gforth  av_call_float  av-call-float   ( -- r )        gforth  av_call_float
Line 2250 
Line 2416 
 SAVE_REGS  SAVE_REGS
 av_call(alist);  av_call(alist);
 REST_REGS  REST_REGS
   #ifdef BUGGY_LONG_LONG
   d.lo = llrv;
   d.hi = 0;
   #else
 d = llrv;  d = llrv;
   #endif
   
 av-call-ptr   ( -- c_addr )        gforth  av_call_ptr  av-call-ptr   ( -- c_addr )        gforth  av_call_ptr
 SAVE_REGS  SAVE_REGS
Line 2258 
Line 2429 
 REST_REGS  REST_REGS
 c_addr = prv;  c_addr = prv;
   
 alloc-callback  ( xt -- c_addr )        gforth  alloc_callback  alloc-callback  ( a_ip -- c_addr )      gforth  alloc_callback
 c_addr = (char *)alloc_callback(engine_callback, ((Xt *)xt)+2);  c_addr = (char *)alloc_callback(engine_callback, (Xt *)a_ip);
   
   va-start-void   ( -- )  gforth  va_start_void
   va_start_void(clist);
   
 va-start-int    ( -- w )        gforth  va_start_int  va-start-int    ( -- )  gforth  va_start_int
 w = va_start_int(clist);  va_start_int(clist);
   
 va-start-longlong       ( -- d )        gforth  va_start_longlong  va-start-longlong       ( -- )  gforth  va_start_longlong
 d = va_start_longlong(clist);  va_start_longlong(clist);
   
 va-start-ptr    ( -- c_addr )   gforth  va_start_ptr  va-start-ptr    ( -- )  gforth  va_start_ptr
 c_addr = (char *)va_start_ptr(clist, (char *));  va_start_ptr(clist, (char *));
   
 va-start-float  ( -- r )        gforth  va_start_float  va-start-float  ( -- )  gforth  va_start_float
 r = va_start_float(clist);  va_start_float(clist);
   
 va-start-double ( -- r )        gforth  va_start_double  va-start-double ( -- )  gforth  va_start_double
 r = va_start_double(clist);  va_start_double(clist);
   
   va-arg-int      ( -- w )        gforth  va_arg_int
   w = va_arg_int(clist);
   
   va-arg-longlong ( -- d )        gforth  va_arg_longlong
   #ifdef BUGGY_LONG_LONG
   d.lo = va_arg_longlong(clist);
   d.hi = 0;
   #else
   d = va_arg_longlong(clist);
   #endif
   
   va-arg-ptr      ( -- c_addr )   gforth  va_arg_ptr
   c_addr = (char *)va_arg_ptr(clist,char*);
   
   va-arg-float    ( -- r )        gforth  va_arg_float
   r = va_arg_float(clist);
   
   va-arg-double   ( -- r )        gforth  va_arg_double
   r = va_arg_double(clist);
   
 va-return-void ( -- )   gforth va_return_void  va-return-void ( -- )   gforth va_return_void
 va_return_void(clist);  va_return_void(clist);
Line 2289 
Line 2483 
 return 0;  return 0;
   
 va-return-longlong ( d -- )     gforth va_return_longlong  va-return-longlong ( d -- )     gforth va_return_longlong
   #ifdef BUGGY_LONG_LONG
   va_return_longlong(clist, d.lo);
   #else
 va_return_longlong(clist, d);  va_return_longlong(clist, d);
   #endif
 return 0;  return 0;
   
 va-return-float ( r -- )        gforth va_return_float  va-return-float ( r -- )        gforth va_return_float
Line 2300 
Line 2498 
 va_return_double(clist, r);  va_return_double(clist, r);
 return 0;  return 0;
   
 \-  \+
   
   \+OLDCALL
   
 define(`uploop',  define(`uploop',
        `pushdef(`$1', `$2')_uploop(`$1', `$2', `$3', `$4', `$5')`'popdef(`$1')')         `pushdef(`$1', `$2')_uploop(`$1', `$2', `$3', `$4', `$5')`'popdef(`$1')')
Line 2341 
Line 2541 
 \+  \+
 \+  \+
   
 wcall   ( u -- )        gforth  \g peephole
 IF_fpTOS(fp[0]=fpTOS);  
 FP=fp;  
 sp=(Cell*)(SYSCALL(Cell*(*)(Cell *, void *))u)(sp, &FP);  
 fp=FP;  
 IF_spTOS(spTOS=sp[0];)  
 IF_fpTOS(fpTOS=fp[0]);  
   
 \+peephole  \+peephole
   
 \g peephole  
   
 compile-prim1 ( a_prim -- ) gforth compile_prim1  compile-prim1 ( a_prim -- ) gforth compile_prim1
 ""compile prim (incl. immargs) at @var{a_prim}""  ""compile prim (incl. immargs) at @var{a_prim}""
 compile_prim1(a_prim);  compile_prim1(a_prim);
Line 2360 
Line 2552 
 finish-code ( -- ) gforth finish_code  finish-code ( -- ) gforth finish_code
 ""Perform delayed steps in code generation (branch resolution, I-cache  ""Perform delayed steps in code generation (branch resolution, I-cache
 flushing).""  flushing).""
   IF_spTOS(sp[0]=spTOS); /* workaround for failing to save spTOS
                             (gcc-2.95.1, gforth-fast --enable-force-reg) */
 finish_code();  finish_code();
   IF_spTOS(spTOS=sp[0]);
   
 forget-dyncode ( c_code -- f ) gforth-internal forget_dyncode  forget-dyncode ( c_code -- f ) gforth-internal forget_dyncode
 f = forget_dyncode(c_code);  f = forget_dyncode(c_code);
Line 2395 
Line 2590 
   
 \g static_super  \g static_super
   
 \C #if !defined(GFORTH_DEBUGGING) && !defined(INDIRECT_THREADED) && !defined(DOUBLY_INDIRECT) && !defined(VM_PROFILING)  ifdef(`M4_ENGINE_FAST',
   `include(peeprules.vmg)')
 include(peeprules.vmg)  
   
 \C #endif  
   
 \g end  \g end


Generate output suitable for use with a patch program
Legend:
Removed from v.1.132  
changed lines
  Added in v.1.155

CVS Admin

Powered by ViewCVS 1.0-dev
(Powered by ViewCVS)

ViewCVS and CVS Help