Annotation of 41BSD/cmd/liszt/cadr.l, revision 1.1.1.1

1.1       root        1: 
                      2: 
                      3: ;              l i s z t   v 4
                      4: 
                      5: 
                      6: 
                      7: 
                      8: ; Copyright (c) 1980 ,  The Regents of the University of California.
                      9: ; All rights reserved.  
                     10: ; author: j. foderaro
                     11: 
                     12: ; Section EXPR  -- general expression compiler
                     13: 
                     14: (include "caspecs.l")
                     15: 
                     16: (eval-when (compile eval)
                     17:   (cond ((not (getd 'If))
                     18:         (fasl 'camacs))))
                     19: 
                     20: (setq sectioncadrid "@(#)cadr.l        5.4     10/22/80")  ; id for SCCS
                     21: 
                     22: ;--- d-exp :: compile a lisp expression                                = d-exp =
                     23: ;      v-form : a lisp expression to compile
                     24: ; returns an IADR which tells where the value was located.
                     25: ;
                     26: (defun d-exp (v-form)
                     27:   (prog (first resloc tmp ftyp)
                     28: 
                     29:     begin
                     30:        (If (atom v-form)
                     31:            then (setq tmp (d-loc v-form))              ;locate vrble
                     32:                 (If (null g-loc)
                     33:                     then (If g-cc then (d-tst tmp))
                     34:                     else (d-move tmp g-loc))
                     35:                 (d-handlecc)
                     36:                 (return tmp)
                     37: 
                     38:         elseif (atom (setq first (car v-form)))
                     39:            then (If (and fl-xref (not (get first g-refseen)))
                     40:                     then (Push g-reflst first)
                     41:                          (putprop first t g-refseen))
                     42:                 (setq ftyp (d-functyp first))
                     43:                 (If (eq 'macro ftyp)
                     44:                     then (setq v-form (apply first v-form))
                     45:                          (go begin)
                     46:                  elseif (setq tmp (get first 'fl-exprcc))
                     47:                     then (return (funcall tmp))
                     48:                  elseif (setq tmp (get first 'fl-exprm))
                     49:                     then (setq v-form (funcall tmp))
                     50:                          (go begin)
                     51:                  elseif (setq tmp (get first 'fl-expr))
                     52:                     then (funcall tmp)
                     53:                  elseif (setq tmp (or (and (eq 'car first)
                     54:                                            '( a ))
                     55:                                       (and (eq 'cdr first)
                     56:                                            '( d ))
                     57:                                       (d-cxxr first)))
                     58:                     then (return (cc-cxxr (cadr v-form) tmp))
                     59:                   elseif (eq 'nlambda ftyp)
                     60:                     then (d-callbig first `(',(cdr v-form)))
                     61:                   elseif (or (eq 'lambda ftyp) (eq 'lexpr ftyp))
                     62:                     then (setq tmp (length v-form))
                     63:                     
                     64:                          (d-callbig first (cdr v-form)))
                     65:         elseif (eq 'lambda (car first))
                     66:            then (c-lambexp)
                     67: 
                     68:         elseif (or (eq 'quote (car first)) (eq 'function (car first)))
                     69:            then (comp-warn "bizzare function name " (or first))
                     70:                 (setq v-form (cons (cadr first) (cdr v-form)))
                     71:                 (go begin)
                     72:                
                     73:         else (comp-err "bad expression" (or v-form)))
                     74: 
                     75: (If (null g-loc)
                     76:     then (If g-cc then (d-tst 'reg))
                     77:  elseif (eq g-loc 'reg)
                     78:     then (If g-cc then (d-tst 'reg))
                     79:  else (d-move 'reg g-loc))
                     80: (If g-cc then (d-handlecc))))
                     81: 
                     82: ;--- d-functyp :: return the type of function
                     83: ;      - name : function name
                     84: ;
                     85: (defun d-functyp (name)
                     86:   (let (ftyp )
                     87:        (If (atom name) then 
                     88:           (If (setq ftyp (getd name))
                     89:               then (If (bcdp ftyp)
                     90:                        then (getdisc ftyp)
                     91:                     elseif (dtpr ftyp)
                     92:                        then (car ftyp))
                     93:             elseif (get name g-functype) thenret
                     94:             else 'lambda))))           ; default is lambda
                     95: 
                     96: 
                     97: ;--- d-exps :: compile a list of expressions
                     98: ;      - exps : list of expressions
                     99: ; the last expression is evaluated according to g-loc and g-cc, the others
                    100: ; are evaluated with g-loc and g-cc nil.
                    101: ;
                    102: (defun d-exps (exps)
                    103:   (d-exp (do ((ll exps (cdr ll))
                    104:              (g-loc nil)
                    105:              (g-cc  nil)
                    106:              (g-ret nil))
                    107:             ((null (cdr ll)) (car ll))
                    108:             (d-exp (car ll)))))
                    109: 
                    110: 
                    111: ;--- d-pushargs :: compile and push a list of expressions
                    112: ;      - exps : list of expressions
                    113: ; compiles and stacks a list of expressions
                    114: ;
                    115: (defun d-pushargs (args)
                    116:   (If args then (do ((ll args (cdr ll))
                    117:                     (g-loc 'stack)
                    118:                     (g-cc nil)
                    119:                     (g-ret nil))
                    120:                    ((null ll))
                    121:                    (d-exp (car ll))
                    122:                    (Push g-locs nil)
                    123:                    (incr g-loccnt))))
                    124: 
                    125: ;--- d-cxxr :: split apart a cxxr function name
                    126: ;      - name : a possible cxxr function name
                    127: ; returns the a's and d's between c and r in reverse order, or else
                    128: ;  returns nil if this is not a cxxr name
                    129: ;
                    130: (defun d-cxxr (name)
                    131:   (let ((expl (explodec name)))
                    132:        (If (eq 'c (car expl))                  ; must begin with c
                    133:           then (do ((ll (cdr expl) (cdr ll))
                    134:                     (tmp)
                    135:                     (res))
                    136:                    (nil)
                    137:                    (setq tmp (car ll))
                    138:                    (If (null (cdr ll)) 
                    139:                        then (If (eq 'r tmp)    ; must end in r
                    140:                                 then (return res)
                    141:                                 else (return nil))
                    142:                     elseif (or (eq 'a tmp)     ; and contain only a's and d's
                    143:                                (eq 'd tmp))
                    144:                        then (setq res (cons tmp res))
                    145:                     else (return nil))))))
                    146: 
                    147: ;--- d-call :: call another function
                    148: ;      - name : name of funtion to call
                    149: ;      - nargs : number of args stacked (including the function name)
                    150: ;
                    151: (defun d-call (name nargs)
                    152:   (prog (tmp)
                    153:        (forcecomment `(calling ,name))
                    154:        (If (null (setq tmp (cdr (assoc nargs
                    155:                                        '( (1 . (* -8 #.bind-reg))
                    156:                                           (2 . (* -12 #.bind-reg))
                    157:                                           (3 . (* -16 #.bind-reg))
                    158:                                           (4 . (* -20 #.bind-reg))
                    159:                                           (5 . (* -24 #.bind-reg)))))))
                    160:            then   ; lbot will not be set up automatically
                    161:                   (e-write3 'movab             ; must set up lbot
                    162:                             `(,(* -4 nargs) #.Np-reg)
                    163:                             '#.Lbot-reg)
                    164:                   (setq tmp '(* -28 #.bind-reg)))
                    165:        (e-write2 'jsb tmp)))
                    166: 
                    167: ;--- d-callbig :: call a local or global function      
                    168: ;
                    169: ;
                    170: (defun d-callbig (name args)
                    171:   (let ((tmp (get name g-localf))
                    172:        c)
                    173:        (forcecomment `(calling ,name))
                    174:        (If (d-dotailrecursion name args) thenret
                    175:         elseif tmp then ;-- local function call
                    176:                    (d-pushargs args)
                    177:                    (e-write2 'jsb (car tmp))
                    178:                    (setq g-locs (nthcdr (setq c (length args)) g-locs))
                    179:                    (setq g-loccnt (- g-loccnt c))
                    180:        else (If fl-tran        ;-- transfer table linkage
                    181:               then (d-pushargs args)
                    182:                    (setq c (length args))
                    183:                    (d-calltran name c)
                    184:               else ;--- standard function call
                    185:                    (d-pushargs `(',name ,@args))
                    186:                    (d-call name (setq c (1+ (length args)))))
                    187:             (setq g-locs (nthcdr c g-locs))
                    188:             (setq g-loccnt (- g-loccnt c)))
                    189:        (d-clearreg)))
                    190:        
                    191: 
                    192: ;--- d-calltran :: call a function through the transfer table            = d-calltran =
                    193: ;  name - name of function to call
                    194: ;  c - number of arguments to the function
                    195: ;
                    196: (defun d-calltran (name c)
                    197:   (e-write3 'movab `(,(* -4 c) #.Np-reg) '#.Lbot-reg)
                    198:   (e-write3 'calls '$0 (concat "*trantb+" (d-tranloc name)))
                    199:   (e-write3 'movl '#.Lbot-reg '#.Np-reg))
                    200: 
                    201: ;--- d-tranloc :: locate a function in the transfer table        = d-tranloc =
                    202: ;
                    203: ; return the offset we should use for this function call
                    204: ;
                    205: (defun d-tranloc (fname)
                    206:   (cond ((get fname g-tranloc))
                    207:        (t (Push g-tran fname)
                    208:           (let ((newval (* 8 g-trancnt)))
                    209:                (putprop fname newval g-tranloc)
                    210:                (incr g-trancnt)
                    211:                newval))))
                    212: 
                    213: ;--- d-dotailrecursion :: do tail recursion if possible
                    214: ; name - function name we are to call
                    215: ; args - arguments to give to function
                    216: ;
                    217: ; return t iff we were able to do tail recursion
                    218: ; We can do tail recursion if:
                    219: ;  g-ret is set indicating that the result of this call will be returned
                    220: ;       as the value of the function we are compiling
                    221: ;  the function we are calling, name, is the same as the function we are
                    222: ;       compiling, g-fname
                    223: ;  there are no variables shallow bound, since we would have to unbind
                    224: ;       them, which may cause problems in the function.
                    225: ;
                    226: (defun d-dotailrecursion (name args)
                    227:   (If (and g-ret 
                    228:           (eq name g-fname)
                    229:            (do ((loccnt 0)
                    230:                (ll g-locs (cdr ll)))
                    231:               ((null ll) (return t))
                    232:               (If (dtpr (car ll))
                    233:                   then (If (or (eq 'catcherrset (caar ll))
                    234:                                (greaterp (cdar ll) 0))
                    235:                            then (return nil))
                    236:                   else (incr loccnt))))
                    237:       then 
                    238:            ; evalate the arguments and pop them back to the location of
                    239:            ; the original args.
                    240:            (makecomment '(tail merging))
                    241:            (comp-note "Tail merging being done: " v-form)
                    242:            (let ((g-locs g-locs)
                    243:                  (g-loccnt g-loccnt))
                    244:                 (d-pushargs args))     ; push then forget about
                    245:            (let (base-reg nargs)
                    246:                 (If (eq g-ftype 'lexpr)
                    247:                     then ; the beginning of the local variables 
                    248:                          ;has been stacked
                    249:                          (e-write3 'addl2 '$4 'sp)     ; pop off arg count
                    250:                          (e-write4 'addl3 '$4 "(sp)" Lbot-reg) 
                    251:                          (setq base-reg Lbot-reg)      ; will push from   bot
                    252:                     else (setq base-reg oLbot-reg)) ; will push from olbot
                    253:                 (setq nargs (length args))
                    254:                 (do ((i nargs (1- i))
                    255:                      (top (* nargs -4) (+ top 4))
                    256:                      (bot 0 (+ bot 4)))
                    257:                     ((zerop i))
                    258:                     (e-write3 'movl `(,top ,Np-reg) `(,bot ,base-reg)))
                    259:                 (e-write3 'movab `(,(* 4 nargs) ,base-reg) Np-reg)
                    260:                 (e-goto g-topsym))
                    261:            t)) ; return t to indicate that tailrecursion was successful
                    262: 
                    263: 
                    264: 
                    265: 
                    266: ; Section xxx -- specific function compilers
                    267: ;
                    268: 
                    269: ;--- cc-and :: compile an and expression
                    270: ; We evaluate forms from left to right as long as they evaluate to
                    271: ; a non nil value.  We only have to worry about storing the value of
                    272: ; the last expression in g-loc.
                    273: ;
                    274: (defun cc-and nil
                    275:   (let ((finlab (d-genlab))
                    276:        (finlab2)
                    277:        (exps (If (cdr v-form) thenret else '(t))))     ; (and) ==> t
                    278:        (If (null (cdr g-cc))
                    279:           then (d-exp (do ((g-cc (cons nil finlab))
                    280:                            (g-loc)
                    281:                            (g-ret)
                    282:                            (ll exps (cdr ll)))
                    283:                           ((null (cdr ll)) (car ll))
                    284:                           (d-exp (car ll))))
                    285:                (If g-loc then (setq finlab2 (d-genlab))
                    286:                               (e-goto finlab2)
                    287:                               (e-label finlab)
                    288:                               (d-move 'Nil g-loc)
                    289:                               (e-label finlab2)
                    290:                          else (e-label finlab))
                    291:           else ;--- cdr g-cc is non nil, thus there is
                    292:                ; a quick escape possible if one of the
                    293:                ; expressions evals to nil
                    294: 
                    295:                (If (null g-loc) then (setq finlab (cdr g-cc)))
                    296:                (d-exp (do ((g-cc (cons nil finlab))
                    297:                            (g-loc)
                    298:                            (g-ret)
                    299:                            (ll exps (cdr ll)))
                    300:                           ((null (cdr ll)) (car ll))
                    301:                           (d-exp (car ll))))
                    302:                ; if g-loc is non nil, then we have evaled the and
                    303:                ; expression to yield nil, which we must store in
                    304:                ; g-loc and then jump to where the cdr of g-cc takes us
                    305:                (If g-loc then (setq finlab2 (d-genlab))
                    306:                               (e-goto finlab2)
                    307:                               (e-label finlab)
                    308:                               (d-move 'Nil g-loc)
                    309:                               (e-goto (cdr g-cc))
                    310:                               (e-label finlab2))))
                    311:   (d-clearreg))         ; we cannot predict the state of the registers
                    312:            
                    313:                          
                    314: 
                    315: 
                    316: ;--- cc-arg  :: get the nth arg from the current lexpr         = cc-arg =
                    317: ;
                    318: ; the syntax for Franz lisp is (arg i)
                    319: ; for interlisp the syntax is (arg x i) where x is not evaluated and is
                    320: ; the name of the variable bound to the number of args.  We can only handle
                    321: ; the case of x being the variable for the current lexpr we are compiling
                    322: ;
                    323: (defun cc-arg nil 
                    324:   (let ((nillab (d-genlab)) (finlab (d-genlab)))
                    325:        (If (not (eq 'lexpr g-ftype)) 
                    326:           then (comp-err " arg only allowed in lexprs"))
                    327:        (If (and (eq (length (cdr v-form)) 2)  fl-inter)
                    328:           then (If (not (eq (car g-args) (cadr v-form)))
                    329:                    then (comp-err " arg expression is for non local lexpr "
                    330:                                   v-form)
                    331:                    else (setq v-form (cdr v-form))))
                    332:        (If (or g-loc g-cc)
                    333:           then (let ((g-loc 'reg) 
                    334:                      (g-cc (cons nil nillab))
                    335:                      (g-ret))
                    336:                     (d-exp `(cdr ,(cadr v-form))))     ; calc the numeric arg
                    337:                (If g-loc then (d-move '"*-4(fp)[r0]" g-loc)
                    338:                   else (e-tst '"*-4(fp)[r0]"))
                    339:                (d-handlecc)
                    340:                (e-goto finlab)
                    341:                (e-label nillab)
                    342:                ; here we are doing (arg nil) which returns the number of args
                    343:                ; which is always true if anyone is testing 
                    344:                (If g-loc then (d-move '"-8(fp)" g-loc)
                    345:                               (d-handlecc)
                    346:                   elseif (car g-cc) then (e-goto (car g-cc))) ;always true
                    347:                (e-label finlab))))
                    348: 
                    349: 
                    350: ;--- cc-atom :: test for atomness                              = cc-atom  =
                    351: ;
                    352: (defun cc-atom nil
                    353:   (d-typecmplx (cadr v-form) 
                    354:               '#.(concat '$ (plus 1_0 1_1 1_2 1_4 1_5 1_6 1_7 1_9 1_10))))
                    355: 
                    356: 
                    357: ;--- cc-bcdp :: check for bcdpness                             = cc-bcdp  =
                    358: ;
                    359: (defun cc-bcdp nil
                    360:   (d-typesimp (cadr v-form) '$5))
                    361: 
                    362: 
                    363: ;--- cc-bigp :: check for bignumness                           = cc-bigp =
                    364: ;
                    365: (defun cc-bigp nil
                    366:   (d-typesimp (cadr v-form) '$9))
                    367: 
                    368: ;--- c-*catch :: compile a *catch expression                   = c-*catch =
                    369: ;
                    370: ; the form of *catch is (*catch 'tag 'val)
                    371: ; we evaluate 'tag and set up a catch frame, and then eval 'val
                    372: ;
                    373: (defun c-*catch nil
                    374:   (let ((g-loc 'reg)
                    375:        (g-cc nil)
                    376:        (g-ret nil)
                    377:        (finlab (d-genlab)))
                    378:        (d-exp (cadr v-form))           ; calculate tag into r0
                    379:        (d-catcherrset finlab 'reg 'T (caddr v-form))
                    380:        (e-label finlab)))
                    381: 
                    382: 
                    383: 
                    384: ;--- d-catcherrset :: common code to catch and errset 
                    385: ;
                    386: (defun d-catcherrset (finlab tagloc  flagloc expr)
                    387:        (e-write2 'pushab finlab)
                    388:        (e-write2 'pushr '$0x2540)      ; save registers
                    389:        (e-write2 'jsb '_svkludg)               ; save rest of state
                    390:        (e-write2 'pushl Bnp-val)
                    391:        (e-write2 'pushl (e-cvt tagloc))        ; push tag
                    392:        (e-write2 'pushl (e-cvt flagloc))       ; non-nil flag
                    393:        (e-write2 'pushl '_errp)                ; old error pointer
                    394:        (e-write3 'movl 'sp '_errp)     ; set up new error pointer
                    395:        (Push g-locs '(catcherrset . 0))
                    396:        (d-exp expr)                    ; now do the expression
                    397:        (unpush g-locs)
                    398:        (e-write3 'movl '"(sp)" '_errp) ; unlink this error frame
                    399:        (e-write3 'addl2 '$80 'sp)
                    400:        (d-clearreg))                   ; cant predict contents after retune    
                    401: 
                    402: 
                    403: ;--- c-cond :: compile a "cond" expression                     = c-cond =
                    404: ;
                    405: ; not that this version of cond is a 'c' rather than a 'cc' . 
                    406: ; this was done to make coding this routine easier and because
                    407: ; it is believed that it wont harm things much if at all
                    408: ;
                    409: (defun c-cond nil
                    410:   (makecomment '(beginning cond))
                    411:   (do ((clau (cdr v-form) (cdr clau))
                    412:        (finlab (d-genlab))
                    413:        (nxtlab)
                    414:        (save-reguse)
                    415:        (seent))
                    416:       ((or (null clau) seent)
                    417:        ; end of cond
                    418:        ; if haven't seen a t must store a nil in r0
                    419:        (If (null seent)  then (d-move 'Nil 'reg))
                    420:        (e-label finlab))
                    421: 
                    422:       ; case 1 - expr
                    423:       (If (atom (car clau))
                    424:          then (comp-err "bad cond clause " (car clau))
                    425:       ; case 2 - (expr)
                    426:        elseif (null (cdar clau))
                    427:          then (let ((g-loc (If (or g-cc g-loc) then 'reg))
                    428:                     (g-cc (cons finlab nil))
                    429:                     (g-ret))
                    430:                    (d-exp (caar clau)))
                    431:       ; case 3 - (t expr1 expr2 ...)
                    432:        elseif (or (eq t (caar clau))
                    433:                  (equal ''t (caar clau)))
                    434:          then (let ((g-loc (If (or g-cc g-loc) then 'reg))
                    435:                     g-cc)
                    436:                    (d-exps (cdar clau)))
                    437:               (setq seent t)
                    438:       ; case 4 - (expr1 expr2 ...)
                    439:        else (let ((g-loc nil)
                    440:                  (g-cc (cons nil (setq nxtlab (d-genlab))))
                    441:                  (g-ret nil))
                    442:                 (d-exp (caar clau)))
                    443:            (setq save-reguse (copy g-reguse))
                    444:            (let ((g-loc (If (or g-cc g-loc) then 'reg))
                    445:                  g-cc)
                    446:                 (d-exps (cdar clau)))
                    447:            (If (or (cdr clau) (null seent)) then (e-goto finlab))
                    448:            (e-label nxtlab)
                    449:            (setq g-reguse save-reguse)))
                    450:   
                    451:   (d-clearreg))
                    452:              
                    453: 
                    454: 
                    455: ;--- c-cons :: do a cons instruction quickly                   = c-cons =
                    456: ;
                    457: (defun c-cons nil
                    458:   (d-pushargs (cdr v-form))            ; there better be 2 args
                    459:   (e-write2 'jsb '_qcons)
                    460:   (setq g-locs (cddr g-locs))
                    461:   (setq g-loccnt (- g-loccnt 2))
                    462:   (d-clearreg))
                    463: 
                    464: 
                    465: ;--- c-cxr :: compile a cxr instruction                                = c-cxr =
                    466: ; 
                    467: ; this code would also be useful for accessing any vector of lispvals.
                    468: ;
                    469: (defun c-cxr nil
                    470:   (prog (arg1 arg2 arg1loc arg2loc)
                    471:        (setq arg1loc (d-simple (setq arg1 (list 'cdr (cadr v-form))))
                    472:              arg2loc (d-simple (setq arg2 (caddr v-form))))
                    473: 
                    474:        (If (not (and (dtpr arg1loc) (eq 'immed (car arg1loc))))
                    475:            then
                    476:               (If arg2loc 
                    477:                   then (If (null arg1loc) 
                    478:                            then (let ((g-loc 'r1)
                    479:                                       (g-cc))
                    480:                                      (d-exp arg1))
                    481:                            else (d-move arg1loc 'r1))
                    482:                        (d-move arg2loc 'r0)
                    483:                   else (d-pushargs (ncons arg1))
                    484:                        (let ((g-loc 'r0)
                    485:                              (g-cc))
                    486:                             (d-exp arg2))
                    487:                        (d-move 'unstack 'r1)
                    488:                        (decr g-loccnt)
                    489:                        (Pop g-locs))
                    490:               (d-inreg 'r1 nil)                ; register clobbered
                    491:               (If g-loc then (e-move `(0 r0 r1) (e-cvt g-loc))
                    492:                              (d-handlecc)
                    493:                elseif g-cc then (e-tst `(0 r0 r1))
                    494:                                 (d-handlecc))
                    495:            else (let ((g-loc 'r0)
                    496:                       (g-cc))
                    497:                      (d-exp arg2))
                    498:                 (setq arg1loc (list (* 4 (cadr arg1loc)) 'r0))
                    499:                 (If g-loc then (e-move arg1loc (e-cvt g-loc))
                    500:                                (d-handlecc)
                    501:                  elseif g-cc then (e-tst arg1loc)
                    502:                                   (d-handlecc)))))
                    503:                        
                    504:                            
                    505: ;--- cc-cxxr :: compile a "c*r" instr where *                  = c-cxxr =
                    506: ;              is any sequence of a's and d's
                    507: ;      - arg : argument of the cxxr function
                    508: ;      - pat : a list of a's and d's in the reverse order of that
                    509: ;                      which appeared between the c and r
                    510: ;
                    511: (defun cc-cxxr (arg pat)
                    512:   (prog (resloc loc qloc sofar togo keeptrack)
                    513:        ; check for the special case of nil, since car's and cdr's
                    514:        ; are nil anyway
                    515:        (If (null arg) then (If g-loc then (d-move 'Nil g-loc)
                    516:                                           (d-handlecc)
                    517:                             elseif (cdr g-cc) then (e-goto (cdr g-cc)))
                    518:                            (return))
                    519:                                      
                    520:        (If (and (symbolp arg) (setq qloc (d-bestreg arg pat)))
                    521:            then (setq resloc (car qloc)
                    522:                       loc   resloc
                    523:                       sofar  (cadr qloc)
                    524:                       togo   (caddr qloc))
                    525:         else (setq resloc (If (d-simple arg) thenret
                    526:                                else (let ((g-loc 'reg)
                    527:                                           (g-cc nil)
                    528:                                           (g-ret nil))
                    529:                                          (d-exp arg))
                    530:                                'r0))
                    531:               (setq sofar nil
                    532:                     togo  pat))
                    533: 
                    534:        (If (and arg (symbolp arg)) then (setq keeptrack t))
                    535: 
                    536:        ; if resloc is a global variable, we must move it into a register
                    537:        ; right away to be able to do car's and cdr's
                    538:        (If (and (dtpr resloc) (or (eq (car resloc) 'bind)
                    539:                                  (eq (car resloc) 'vstack)))
                    540:           then (d-move resloc 'reg)
                    541:                (setq resloc 'r0))
                    542: 
                    543:        ; now do car's and cdr's .  Values are placed in r0. We stop when
                    544:        ; we can get the result in one machine instruction.  At that point
                    545:        ; we see whether we want the value or just want to set the cc's.
                    546:        ; If the intermediate value is in a register, 
                    547:        ; we can do : car cdr cddr cdar
                    548:        ; If the intermediate value is on the local vrbl stack or lbind
                    549:        ; we can do : cdr
                    550:        (do ((curp togo newp)
                    551:            (newp))
                    552:           ((null curp) (If g-loc then (d-movespec loc g-loc)
                    553:                            elseif g-cc then (e-tst loc))
                    554:                        (d-handlecc))
                    555:           (If (symbolp resloc)
                    556:               then (If (eq 'd (car curp))
                    557:                        then (If (or (null (cdr curp))
                    558:                                     (eq 'a (cadr curp)))
                    559:                                 then (setq newp (cdr curp)   ; cdr
                    560:                                            loc `(0 ,resloc)
                    561:                                            sofar (append sofar (list 'd)))
                    562:                                 else (setq newp (cddr curp)  ; cddr
                    563:                                            loc `(* 0 ,resloc)
                    564:                                            sofar (append sofar (list 'd 'd))))
                    565:                        else (If (or (null (cdr curp))
                    566:                                     (eq 'a (cadr curp)))
                    567:                                 then (setq newp (cdr curp)   ; car
                    568:                                            loc `(4 ,resloc)
                    569:                                            sofar (append sofar (list 'a)))
                    570:                                 else (setq newp (cddr curp)  ; cdar
                    571:                                            loc `(* 4 ,resloc)
                    572:                                            sofar (append sofar (list 'a 'd)))))
                    573:               elseif (and (eq 'd (car curp))
                    574:                           (not (eq '* (car (setq loc (e-cvt resloc))))))
                    575:                 then (setq newp (cdr curp)     ; (cdr <local>)
                    576:                            loc (cons '* loc)
                    577:                            sofar (append sofar (list 'd)))
                    578:               else  (setq loc (e-cvt resloc)
                    579:                           newp curp))
                    580:           (If newp                     ; if this is not the last move
                    581:               then (setq resloc (d-allocreg (If keeptrack then nil else 'r0)))
                    582:                    (d-movespec loc resloc)
                    583:                    (If keeptrack then (d-inreg resloc (cons arg sofar)))))))
                    584: 
                    585: ;--- c-declare :: handle the "declare" form
                    586: ; if a declare is seen inside a function definition, we just 
                    587: ; ignore it.  We probably should see what it is declareing, as it
                    588: ; might be declaring a special.
                    589: ;
                    590: (defun c-declare nil)
                    591: 
                    592: ;--- c-do :: compile a "do" expression                         = c-do =
                    593: ;
                    594: ; a do has this form:
                    595: ;  (do vrbls tst . body)
                    596: ; we note the special case of tst being nil, in which case the loop
                    597: ; is evaluated only once, and thus acts like a let with labels allowed.
                    598: ; The do statement is a cross between a prog and a lambda. It is like
                    599: ; a prog in that labels are allowed. It is like a lambda in that
                    600: ; we stack the values of all init forms then bind to the variables, just
                    601: ; like a lambda expression (that is the initial values of even specials
                    602: ; are stored on the stack, and then copied into the value cell of the
                    603: ; atom during the binding phase. From then on the stack location is
                    604: ; not used).
                    605: ;
                    606: (defun c-do nil
                    607:   (prog (b-vrbls b-tst b-body chklab bodylab x-repeat x-vrbs x-fst
                    608:        g-loc g-cc oldreguse)
                    609:        (forcecomment '(beginning do))
                    610:        (setq g-loc 'reg  chklab (d-genlab)   bodylab (d-genlab))
                    611: 
                    612:        (If (and (cadr v-form) (atom (cadr v-form)))
                    613:            then (setq v-form (d-olddo-to-newdo (cdr v-form))))
                    614: 
                    615:        (Push g-locs (cons 'do 0 ))             ; begin our frame
                    616: 
                    617:        (setq b-vrbls (cadr v-form)
                    618:              b-tst   (caddr v-form)
                    619:              b-body  (cdddr v-form))
                    620: 
                    621:        ; push value of init forms on stack
                    622:        (d-pushargs (mapcar '(lambda (x)
                    623:                                     (If (atom x) then nil ; no init form => nil
                    624:                                         else (cadr x)))
                    625:                            b-vrbls))
                    626: 
                    627:        ; now bind to  the variables in the vrbls form
                    628:        (d-bindlamb (mapcar '(lambda (x)
                    629:                                     (If (atom x) then x
                    630:                                         else (car x)))
                    631:                            b-vrbls))
                    632: 
                    633:        ; search through body for all labels and assign them gensymed labels
                    634:        (Push g-labs (cons (d-genlab)
                    635:                           (do ((ll b-body (cdr ll))
                    636:                                (res))
                    637:                               ((null ll) res)
                    638:                               (If (and (car ll) (symbolp (car ll)))
                    639:                                   then (Push res  (cons (car ll) (d-genlab)))))))
                    640: 
                    641:        ; if the test is non nil, we do the test
                    642:        ; another strange thing, a test form of (pred) will not return
                    643:        ; the value of pred if it is not nil! it will return nil (in this
                    644:        ; way, it is not like a cond clause)
                    645:        (d-clearreg)
                    646:        (If b-tst then (e-label chklab)
                    647:                       (let ((g-cc (cons nil bodylab)) g-loc g-ret)
                    648:                            (d-exp (car b-tst)))        ; eval test
                    649:                                                        ; if false, do body
                    650:                       (If (cdr b-tst) 
                    651:                           then (setq oldreguse (copy g-reguse))
                    652:                                (d-exps (cdr b-tst))
                    653:                                (setq g-reguse oldreguse)
                    654:                           else  (d-move 'Nil 'reg))
                    655:                       (e-goto (caar g-labs))           ; leave do
                    656:                       (e-label bodylab))               ; begin body
                    657: 
                    658:        ; process body
                    659:        (do ((ll b-body (cdr ll))
                    660:             (g-cc) (g-loc)(g-ret))
                    661:            ((null ll))
                    662:            (If (or (null (car ll)) (not (symbolp (car ll))))
                    663:                then (d-exp (car ll))
                    664:                else (e-label (cdr (assoc (car ll) (cdar g-labs))))
                    665:                     (d-clearreg)))
                    666: 
                    667:        (If b-tst then ; determine all repeat forms which must be 
                    668:                       ; evaluated, and all the variables affected.
                    669:                       ; store the results in x-repeat and  x-vrbs
                    670:                       ; if there is just one repeat form, we calculate
                    671:                       ; its value directly into where it is stored,
                    672:                       ; if there is more than one, we stack them
                    673:                       ; and then store them back at once.
                    674:                       (do ((ll b-vrbls (cdr ll)))
                    675:                           ((null ll))
                    676:                           (If (and (dtpr (car ll)) (cddar ll))
                    677:                               then (Push x-repeat (caddar ll))
                    678:                                    (Push x-vrbs   (caar ll))))
                    679:                       (If x-vrbs 
                    680:                            then (If (null (cdr x-vrbs))  ; if just one repeat..
                    681:                                     then (let ((g-loc (d-locv (car x-vrbs)))
                    682:                                                (g-cc nil))
                    683:                                               (d-exp (car x-repeat)))
                    684:                                     else (setq x-fst (car x-repeat))
                    685:                                          (d-pushargs (nreverse (cdr x-repeat)))
                    686:                                          (let ((g-loc (d-locv (car x-vrbs)))
                    687:                                                (g-cc)
                    688:                                                (g-ret))
                    689:                                               (d-exp x-fst))
                    690:                                          (do ((ll (cdr x-vrbs) (cdr ll)))
                    691:                                              ((null ll))
                    692:                                              (d-move 'unstack (d-locv (car ll)))
                    693:                                              (setq g-locs (cdr g-locs))
                    694:                                              (decr g-loccnt))))
                    695:                      (e-goto chklab))
                    696: 
                    697:        (e-label (caar g-labs))                 ; end of do label
                    698:        (d-clearreg)
                    699:        (d-unbind)
                    700:        (setq g-labs (cdr g-labs))))
                    701: 
                    702: 
                    703: ;--- d-olddo-to-newdo  :: map old do to new do
                    704: ;
                    705: ; form of old do is  (do var tst . body)
                    706: ; where var is a symbol, not nil
                    707: ;
                    708: (defun d-olddo-to-newdo (v-l)
                    709:   `(do ((,(car v-l) ,(cadr v-l) ,(caddr v-l)))
                    710:        (,(cadddr v-l))
                    711:        ,@(cddddr v-l)))
                    712: 
                    713: 
                    714: 
                    715: ;--- cc-dtpr :: check for dtprness                             = cc-dtpr =
                    716: ;
                    717: (defun cc-dtpr nil
                    718:   (d-typesimp (cadr v-form) '$3))
                    719: 
                    720: 
                    721: ;--- cc-eq :: compile an "eq" expression                       = cc-eq =
                    722: ;
                    723: (defun cc-eq nil
                    724:   (let ((arg1 (cadr v-form))
                    725:        (arg2 (caddr v-form))
                    726:        arg1loc
                    727:        arg2loc)
                    728:        (If (setq arg2loc (d-simple arg2))
                    729:           then (If (setq arg1loc (d-simple arg1))
                    730:                    then ; eq <simple> <simple>
                    731:                         (d-cmp arg1loc arg2loc)
                    732:                    else ; eq <nonsimple> <simple>
                    733:                         (let ((g-loc 'reg)     ; put <nonsimple> in r0
                    734:                               g-cc
                    735:                               g-ret)
                    736:                              (d-exp arg1))
                    737:                         (d-cmp 'reg arg2loc))
                    738:           else ; since second is nonsimple, must stack first
                    739:                ; arg out of harms way
                    740:                (let ((g-loc 'stack)
                    741:                      g-cc
                    742:                      g-ret)
                    743:                     (d-exp arg1)
                    744:                     (Push g-locs nil)
                    745:                     (incr g-loccnt)
                    746:                     (setq g-loc 'reg)          ; second arg to r0
                    747:                     (d-exp arg2))
                    748:                (d-cmp 'unstack 'reg)
                    749:                (setq g-locs (cdr g-locs))
                    750:                (decr g-loccnt)))
                    751: 
                    752:   (d-invert))
                    753: 
                    754: (defun cc-equal nil
                    755:   (let ((lab1 (d-genlab))
                    756:        (lab11 (d-genlab))
                    757:        lab2)
                    758:        (d-pushargs (cdr v-form))
                    759:        (e-write3 'cmpl "-8(r6)" "-4(r6)")
                    760:        (e-gotonil lab1)
                    761:        (d-calltran 'equal '2)           ; not eq, try equal.
                    762:        (d-clearreg)
                    763:        (e-write2 'tstl 'r0)
                    764:        (e-gotot lab11)         
                    765:        (If g-loc then (d-move 'Nil g-loc))
                    766:        (If (cdr g-cc) then (e-goto (cdr g-cc))
                    767:           else (e-goto (setq lab2 (d-genlab))))
                    768:        (e-writel lab1)
                    769:        (e-dropnp 2)
                    770:        (e-writel lab11)
                    771:        (If g-loc then (d-move 'T g-loc))
                    772:        (If (car g-cc) then (e-goto (car g-cc)))
                    773:        (If lab2 then (e-writel lab2))
                    774:        (setq g-locs (cddr g-locs))
                    775:        (setq g-loccnt (- g-loccnt 2))))
                    776: 
                    777: 
                    778: 
                    779: 
                    780: ;--- c-errset :: compile an errset expression                  = c-errset =
                    781: ;
                    782: ; the errset has this form: (errset 'value ['tag])
                    783: ; where tag defaults to t.
                    784: ;
                    785: (defun c-errset nil
                    786:   (let ((g-loc 'reg)
                    787:        (g-cc nil)
                    788:        (g-ret nil)
                    789:        (finlab (d-genlab)))
                    790:        (d-exp (If (cddr v-form) then (caddr v-form) else t))
                    791:        (d-catcherrset finlab (d-loclit '(ER%all) nil) 'reg (cadr v-form))
                    792:        (d-move 'reg 'stack)
                    793:        (d-calltran 'ncons 1)
                    794:        (e-label finlab)
                    795:        (d-clearreg)))
                    796: 
                    797: 
                    798: ;--- cc-fixp :: check for a fixnum or bignum                   = cc-fixp =
                    799: ;
                    800: (defun cc-fixp nil
                    801:   (d-typecmplx (cadr v-form) 
                    802:               '#.(concat '$ (plus 1_2 1_9))))
                    803: 
                    804: 
                    805: ;--- cc-floatp :: check for a flonum                           = cc-floatp =
                    806: ;
                    807: (defun cc-floatp nil
                    808:   (d-typesimp (cadr v-form) '$4))
                    809: 
                    810: 
                    811: ;--- c-get :: do a get from the prop list
                    812: ;
                    813: (defun c-get nil
                    814:   (If (not (eq 2 (length (cdr v-form))))
                    815:       then (comp-err "Wrong number of args to get " v-form))
                    816:   (d-pushargs (cdr v-form))            ; there better be 2 args
                    817:   (e-write2 'jsb '_qget)
                    818:   (d-clearreg)
                    819:   (setq g-locs (cddr g-locs))
                    820:   (setq g-loccnt (- g-loccnt 2)))
                    821: 
                    822: ;--- c-go :: compile a "go" expression                         = c-go =
                    823: ;
                    824: ; we only compile the (go symbol)type expression, we do not
                    825: ; allow symbol to be anything by a non null symbol.
                    826: ;
                    827: (defun c-go nil
                    828:   ; find number of frames we have to go down to get to the label
                    829:   (do ((labs g-labs (cdr labs))
                    830:        (locs g-locs)
                    831:        (locals 0)
                    832:        (specials 0)
                    833:        (catcherrset 0)
                    834:        (label))
                    835:       ((null labs) (comp-err "go label not found for expression: " (or v-form)))
                    836:       ; if there are any enclosing *catches or errsets, they will be
                    837:       ; first in g-locs
                    838:       (do nil 
                    839:          ((not (and (dtpr (car locs)) (eq (caar locs) 'catcherrset))))
                    840:          (incr catcherrset)
                    841:          (unpush locs))
                    842: 
                    843:       (If (car labs) 
                    844:          then (If (setq label (do ((lbs (cdar labs) (cdr lbs)))
                    845:                                   ((null lbs))
                    846:                                   (If (eq (caar lbs) (cadr v-form))
                    847:                                       then (return (cdar lbs)))))
                    848:                   then (If (not (eq labs g-labs))
                    849:                            then (comp-warn "non local go used : " (or v-form)))
                    850:                        (If (greaterp catcherrset 0)
                    851:                            then (comp-warn "Go through a catch or errset " v-form)
                    852:                                 (do ((i 0 (1+ i)))
                    853:                                     ((equal catcherrset i))
                    854:                                     (e-write3 'movl "(sp)" '_errp)
                    855:                                     (e-write3 'addl2 '$80 'sp)))
                    856:                        (e-pop locals)
                    857:                        (If (greaterp specials 0)
                    858:                            then (e-unshallowbind specials))
                    859:                        (e-goto label)
                    860:                        (return)))
                    861:       ; tally all locals and specials used in this frame
                    862:       (do ()
                    863:          ((dtpr (car locs)) (setq specials (+ specials (cdar locs))
                    864:                                   locs (cdr locs)))
                    865:          (setq locs (cdr locs))
                    866:          (incr locals))))
                    867:                        
                    868: 
                    869: ;--- cc-ingnore :: just ignore this code
                    870: ;
                    871: (defun cc-ignore nil
                    872:   nil)
                    873: 
                    874: ;--- c-lambexp :: compile a lambda expression                  = c-lambexp =
                    875: ;
                    876: (defun c-lambexp nil
                    877:   (let ((g-loc (If (or g-loc g-cc) then 'reg))
                    878:        (g-cc nil))
                    879:        (Push g-locs (cons 'lambda  0)) ; add null lambda header
                    880:        (d-pushargs (cdr v-form))               ; then push vals
                    881:        (d-lambbody (car v-form))
                    882:        (d-clearreg)))
                    883: 
                    884: ;--- d-lambbody :: do a lambda body
                    885: ;      - body : body of lambda expression, eg (lambda () dld)
                    886: ;
                    887: (defun d-lambbody (body)
                    888:   (d-bindlamb (cadr body))             ; bind locals
                    889:   (setq g-labs (cons nil g-labs))      ; no labels allowed
                    890:   (d-clearreg)
                    891:   (d-exp (do ((ll (cddr body) (cdr ll))
                    892:              (g-loc)
                    893:              (g-cc)
                    894:              (g-ret))
                    895:             ((null (cdr ll)) (car ll))
                    896:             (d-exp (car ll))))
                    897: 
                    898:   (setq g-labs (cdr g-labs))
                    899:   (d-unbind))                          ; unbind this frame
                    900: 
                    901: 
                    902: ;--- d-bindlamb :: bind  variables in lambda list
                    903: ;      - vrbs : list of lambda variables, may include nil meaning ignore
                    904: ;
                    905: (defun d-bindlamb (vrbs)
                    906:   (let ((res (d-bindlrec (reverse vrbs) g-locs 0 g-loccnt)))
                    907:        (If res then (e-setupbind)
                    908:                    (mapc '(lambda (vrb) (e-shallowbind (car vrb) (cdr vrb)))
                    909:                          res)
                    910:                    (e-unsetupbind))))
                    911:   
                    912: ;--- d-bindlrec :: recusive routine to bind lambda variables
                    913: ;      - vrb : list of variables yet to bind
                    914: ;      - locs : current location in g-loc
                    915: ;      - specs : number of specials seen so far
                    916: ;      - lev  : how far up from the bottom of stack we are.
                    917: ; returns: list of elements, one for each special, of this form:
                    918: ;              (<specialvrbname> stack <n>)
                    919: ;      where specialvrbname is the name of the special variable, and n is
                    920: ;      the distance from the top of the stack where its initial value is 
                    921: ;      located
                    922: ; also: puts the names of the local variables in the g-locs list, as well
                    923: ;      as placing the number of special variables in the lambda header.
                    924: ;
                    925: (defun d-bindlrec (vrb locs specs lev)
                    926:   (If vrb 
                    927:       then (let ((spcflg (d-specialp (car vrb)))
                    928:                 retv)
                    929:                (If spcflg then (setq specs (1+ specs)))
                    930:                
                    931:                (If (cdr vrb)           ; if more vrbls to go ...
                    932:                    then (setq retv (d-bindlrec (cdr vrb) 
                    933:                                                (cdr locs)
                    934:                                                specs
                    935:                                                (1- lev)))
                    936:                    else (rplacd (cadr locs) specs))    ; else fix up lambda hdr
                    937:                
                    938:                (If (not spcflg) then (rplaca locs (car vrb))
                    939:                    else (Push retv `(,(car vrb) stack ,lev)))
                    940:                
                    941:                retv)))
                    942: ;--- c-list :: compile a list expression                       = c-list =
                    943: ;
                    944: ; this is compiled as a bunch of conses with a nil pushed on the
                    945: ; top for good measure
                    946: ;
                    947: (defun c-list nil
                    948:   (prog (nargs)
                    949:        (setq nargs (length (cdr v-form)))
                    950:        (makecomment '(list expression))
                    951:        (If (zerop nargs) then (d-move 'Nil 'reg)       ; (list) ==> nil
                    952:                               (return))
                    953:        (d-pushargs (cdr v-form))
                    954:        (e-write2 'clrl '(+ #.Np-reg))  ; stack one nil
                    955: 
                    956:        ; now do the consing
                    957:        (do ((i (max 1 nargs) (1- i)))
                    958:           ((zerop i))
                    959:           (e-write2 'jsb '_qcons)
                    960:           (d-clearreg)
                    961:           (If (> i 1) then (d-move 'reg 'stack)))
                    962: 
                    963:        (setq g-locs (nthcdr nargs g-locs)
                    964:             g-loccnt (- g-loccnt nargs))))
                    965: 
                    966: 
                    967: 
                    968: ;--- d-mapconvert - access : function to access parts of lists
                    969: ;                - join         : function to join results
                    970: ;                - resu         : function to apply to result
                    971: ;              - form   : mapping form
                    972: ;      This function converts maps to an equivalent do form.
                    973: ;
                    974: (defun d-mapconvert (access join resu form )
                    975:          (prog (vrbls finvar acc accform compform tmp)
                    976: 
                    977:                (setq finvar (gensym 'X)   ; holds result
                    978: 
                    979:                      vrbls (reverse
                    980:                             (maplist '(lambda (arg)
                    981:                                        ((lambda (temp)
                    982:                                            (cond ((or resu (cdr arg))
                    983:                                                   `(,temp ,(car arg)
                    984:                                                           (cdr ,temp)))
                    985:                                                  (t `(,temp 
                    986:                                                       (setq ,finvar ,(car arg))
                    987:                                                       (cdr ,temp)))))
                    988:                                         (gensym 'X)))
                    989:                                    (reverse (cdr form))))
                    990: 
                    991:                      acc (mapcar '(lambda (tem)
                    992:                                           (cond (access `(,access ,(car tem)))
                    993:                                                 (t (car tem))))
                    994:                                  vrbls)
                    995: 
                    996:                      accform (cond ((or (atom (setq tmp (car form)))
                    997:                                         (null (setq tmp (d-macroexpand tmp)))
                    998:                                         (not (member (car tmp) '(quote function))))
                    999:                                     `(funcall ,tmp ,@acc))
                   1000:                                    (t `(,(cadr tmp) ,@acc))))
                   1001:                (return
                   1002:                 `((lambda (,finvar)
                   1003:                    (do ( ,@vrbls)
                   1004:                        ((null ,(caar vrbls)))
                   1005:                        ,(cond ((eq join 'nconc)
                   1006:                                `(setq ,finvar (nconc ,finvar ,accform)))
                   1007:                               (join `(setq ,finvar (,join ,accform ,finvar)))
                   1008:                               (t accform)))
                   1009:                    ,(cond ((eq resu 'identity) finvar)
                   1010:                           (resu `(,resu ,finvar))
                   1011:                           (t finvar)))
                   1012:                   nil ))))
                   1013: ; apply to successive elements, return second arg
                   1014: (defun cm-mapc nil
                   1015:          (d-mapconvert 'car nil nil (cdr v-form)))
                   1016: 
                   1017: ; apply to successive elements, return list of results
                   1018: (defun cm-mapcar nil
                   1019:          (d-mapconvert 'car 'cons 'nreverse (cdr v-form)))
                   1020: 
                   1021: ; apply to successive elements, returned nconc of results
                   1022: (defun cm-mapcan nil
                   1023:          (d-mapconvert 'car 'nconc 'identity (cdr v-form)))
                   1024: 
                   1025: 
                   1026: ; apply to successive sublists, return second arg
                   1027: (defun cm-map nil
                   1028:          (d-mapconvert nil nil nil (cdr v-form)))
                   1029: 
                   1030: 
                   1031: ; apply to successive sublists, return list of results
                   1032: (defun cm-maplist nil
                   1033:          (d-mapconvert nil 'cons 'reverse (cdr v-form)))
                   1034: 
                   1035: ; apply to successive sublists, return nconc of results
                   1036: (defun cm-mapcon nil
                   1037:          (d-mapconvert nil 'nconc 'identity (cdr v-form)))
                   1038: 
                   1039: 
                   1040: ;--- cc-memq :: compile a memq expression                      = cc-memq =
                   1041: ;
                   1042: (defun cc-memq nil
                   1043:   (let ((loc1 (d-simple (cadr v-form)))
                   1044:        (loc2 (d-simple (caddr v-form)))
                   1045:        looploc finlab)
                   1046:        (If loc2 then (d-clearreg 'r1)
                   1047:                     (If loc1 then (d-move loc1 'r1)
                   1048:                              else (let ((g-loc 'r1)
                   1049:                                         g-cc
                   1050:                                         g-ret)
                   1051:                                        (d-exp (cadr v-form))))
                   1052:                     (d-move loc2 'reg)
                   1053:                else (let ((g-loc 'stack)
                   1054:                           g-cc
                   1055:                           g-ret)
                   1056:                          (d-exp (cadr v-form)))
                   1057:                     (Push g-locs nil)
                   1058:                     (incr g-loccnt)
                   1059:                     (let ((g-loc 'reg)
                   1060:                           g-cc
                   1061:                           g-ret)
                   1062:                          (d-exp (caddr v-form)))
                   1063:                     (d-move 'unstack 'r1)
                   1064:                     (d-clearreg 'r1)
                   1065:                     (unpush g-locs)
                   1066:                     (decr g-loccnt))
                   1067:        ; now set up the jump addresses
                   1068:        (If (null g-loc)
                   1069:           then (setq loc1 (If (car g-cc) thenret
                   1070:                               else (d-genlab))
                   1071:                      loc2 (If (cdr g-cc) thenret
                   1072:                               else (d-genlab)))
                   1073:           else (setq loc1 (d-genlab)
                   1074:                      loc2 (d-genlab)))
                   1075: 
                   1076:        (setq looploc (d-genlab))
                   1077: 
                   1078:        (e-write2 'tstl 'r0)
                   1079:        (e-write2 'jeql loc2)
                   1080:        (e-label looploc)
                   1081:        (e-write3 'cmpl 'r1 "4(r0)")
                   1082:        (e-write2 'jeql loc1)
                   1083:        (e-write3 'movl "(r0)" 'r0)
                   1084:        (e-write2 'jneq looploc)
                   1085:        (If g-loc then (e-label loc2)           ; nil result
                   1086:                      (d-move 'reg g-loc)
                   1087:                      (If (cdr g-cc) then (e-goto (cdr g-cc))
                   1088:                                     else (e-goto (setq finlab (d-genlab))))
                   1089:                 else (If (cdr g-cc) then (e-goto (cdr g-cc))
                   1090:                                     else (e-label loc2)))
                   1091:        (If g-loc then (e-label loc1)           ; non nil result
                   1092:                      (d-move 'reg g-loc)
                   1093:                      (If (car g-cc) then (e-goto (car g-cc)))
                   1094:                 else (If (null (car g-cc)) then (e-label loc1)))
                   1095:        (If finlab then (e-label finlab))))
                   1096: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.