Index: /branches/arm/lisp-kernel/arm-spentry.s
===================================================================
--- /branches/arm/lisp-kernel/arm-spentry.s	(revision 13785)
+++ /branches/arm/lisp-kernel/arm-spentry.s	(revision 13786)
@@ -249,5 +249,4 @@
         __(test_two_fixnums(arg_y,arg_z,imm0))
         __(bne 1f)
-        __(uuo_suspend_now(al))
         __(cmp arg_y,#(nbits_in_word-fixnumshift)<<fixnumshift)
         __(bhs 1f)
@@ -1911,39 +1910,10 @@
 
 
-/* Destructuring-bind, macro-bind.  */
-   
-/* OK to use arg_x, arg_y for whatever (tagged) purpose;  */
-/* likewise immX regs.  */
-/* arg_z preserved, nothing else in particular defined on exit.  */
-/* nargs contains req count (0-255) in PPC bits mask_req_start/mask_req_width,  */
-/* opt count (0-255) in PPC bits mask_opt_start/mask_opt_width,  */
-/* key count (0-255) in PPC bits mask_key_start/mask_key_width,  */
-/* opt-supplied-p flag in PPC bit mask_initopt,  */
-/* keyp flag in PPC bit mask_keyp,  */
-/* &allow-other-keys flag in PPC bit mask_aok,  */
-/* &rest flag in PPC bit mask_restp.  */
-/* When mask_keyp bit is set, keyvect contains vector of keyword symbols,  */
-/* length key count.  */
-
-_spentry(macro_bind)
-        __(mov whole_reg,arg_reg)
-        __(extract_lisptag(imm0,arg_reg))
-        __(cmp imm0,#tag_list)
-        __(bne 1f)
-        __(_cdr(arg_reg,arg_reg))
-        __(b C(destbind1))
-1:
-        __(mov arg_y,#XCALLNOMATCH)
-        __(mov arg_z,whole_reg)
-        __(set_nargs(2))
-        __(b _SPksignalerr)
-
-_spentry(destructuring_bind)
-        __(mov whole_reg,arg_reg)
-        __(b C(destbind1))
-
-_spentry(destructuring_bind_inner)
-        __(mov whole_reg,arg_z)
-        __(b C(destbind1))
+
+_spentry(unused0)
+
+_spentry(unused1)
+
+_spentry(unused2)
 
 dnl /* vpush the values in the value set atop the vsp, incrementing nargs.  */
@@ -2971,6 +2941,180 @@
         
         
-                        
-                        
+_spentry(eabi_ff_call)                                
+
+_spentry(debind)
+        new_local_labels()
+        __(mov temp0,vsp)
+        __(mov temp1,arg_z)
+        __(ands imm0,nargs,#0xff)
+        __(mov arg_y,#nil_value)
+        __(b local_label(req_test))
+local_label(req_loop):  
+        __(cmp arg_reg,#nil_value)
+        __(extract_lisptag(imm1,arg_reg))
+        __(beq local_label(toofew))
+        __(cmp imm1,#tag_list)
+        __(bne local_label(badlist))
+        __(subs imm0,imm0,#1)
+        __(_car(arg_x,arg_reg))
+        __(_cdr(arg_reg,arg_reg))
+        __(vpush1(arg_x))
+local_label(req_test):
+        __(bne local_label(req_loop))
+        __(mov imm0,#0xff)
+        __(ands imm0,imm0,nargs,lsr #8)
+        __(beq local_label(rest_keys))
+        __(tst nargs,#mask_initopt)
+        __(bne local_label(opt_supp))
+	/* 'simple' &optionals:	 no supplied-p, default to nil.   */
+local_label(simple_opt_loop):
+        __(cmp arg_reg,#nil_value)
+        __(extract_lisptag(imm1,arg_reg))
+        __(beq local_label(default_simple_opt))
+        __(cmp imm1,#tag_list)
+        __(bne local_label(badlist))
+        __(subs imm0,imm0,#1)
+        __(_car(arg_x,arg_reg))
+        __(_cdr(arg_reg,arg_reg))
+        __(vpush1(arg_x))
+        __(bne local_label(simple_opt_loop))
+        __(b local_label(rest_keys))
+local_label(default_simple_opt):        
+        __(subs imm0,imm0,#1)
+        __(vpush1(arg_y))
+        __(bne local_label(default_simple_opt))
+        __(b local_label(rest_keys))
+local_label(opt_supp):   
+        __(cmp arg_reg,#nil_value)
+        __(extract_lisptag(imm1,arg_reg))
+        __(beq local_label(default_hard_opt))
+        __(cmp imm1,#tag_list)
+        __(bne local_label(badlist))
+        __(subs imm0,imm0,#1)
+        __(_car(arg_x,arg_reg))
+        __(_cdr(arg_reg,arg_reg))
+        __(vpush1(arg_x))
+        __(add arg_x,arg_y,#t_offset)
+        __(vpush1(arg_x))
+        __(bne local_label(opt_supp))
+        __(b local_label(rest_keys))
+local_label(default_hard_opt):  
+        __(subs imm0,imm0,#1)
+        __(vpush1(arg_y))
+        __(vpush1(arg_y))
+        __(bne local_label(default_hard_opt))
+local_label(rest_keys): 
+        __(tst nargs,#mask_restp)
+        __(bne local_label(have_rest))
+        __(tst nargs,#mask_keyp)
+        __(bne local_label(have_keys))
+        __(cmp arg_reg,#nil_value)
+        __(bne local_label(toomany))
+        __(bx lr)
+local_label(have_rest): 
+        __(vpush1(arg_reg))
+        __(tst nargs,#mask_keyp)
+        __(bne local_label(have_keys))
+        __(bx lr)
+local_label(have_keys): 
+        __(mov imm0,#256)
+        __(mov arg_y,arg_reg)
+local_label(count_keys_loop):   
+        __(cmp arg_y,#nil_value)
+        __(beq local_label(counted_keys))
+        __(subs imm0,imm0,#1)
+        __(bmi local_label(toomany))
+        __(extract_lisptag(imm1,arg_y))
+        __(cmp imm1,#tag_list)
+        __(bne local_label(badlist))
+        __(_cdr(arg_y,arg_y))
+        __(extract_lisptag(imm1,arg_y))
+        __(cmp imm1,#tag_list)
+        __(bne local_label(badlist))
+        __(_cdr(arg_y,arg_y))
+        __(b local_label(count_keys_loop))
+local_label(counted_keys):      
+	/* We've got a proper, even-length list of key/value pairs in  */
+	/* arg_reg. For each keyword var in the lambda-list, push a pair  */
+	/* of NILs on the vstack.  (We've also cdred down arg_y until it */
+        /* contains NIL.) */
+        __(mov imm0,#0xff)
+        __(ands imm0,imm0,nargs,lsr #16)
+        __(mov imm1,vsp)
+        __(b local_label(push_pair_test))
+local_label(push_pair_loop):
+        __(subs imm0,imm0,#1)
+        __(vpush1(arg_y))
+        __(vpush1(arg_y))
+local_label(push_pair_test):    
+        __(bne local_label(push_pair_loop))
+        __(b local_label(provided_key_loop))
+        
+local_label(next_provided_key): 
+        __(_car(arg_x,arg_reg))
+        __(ref_nrs_symbol(imm0,kallowotherkeys,imm0))
+        __(cmp arg_x,imm0)
+        __(bne local_label(not_aok))
+        __(tst nargs,#mask_aok_seen)
+        __(beq local_label(not_aok))
+        __(_cdr(arg_x,arg_reg))
+        __(_car(arg_x,arg_x))
+        __(orr nargs,nargs,#mask_aok_seen)
+        __(cmp arg_x,#nil_value)
+        __(orrne nargs,nargs,#mask_aok)
+        __(_car(arg_x,arg_reg))
+local_label(not_aok):   
+        __(getvheader(imm0,keyvect_reg))
+        __(header_length(imm0,imm0))
+        __(add imm0,imm0,#misc_data_offset)
+        __(b local_label(match_key_test))
+local_label(match_key_loop):    
+        __(ldr arg_y,[keyvect_reg,imm0])
+        __(cmp arg_x,arg_y)
+        __(bne local_label(match_key_test))
+        __(sub imm0,imm0,#misc_data_offset)
+        __(sub imm0,imm1,imm0,lsl #1)
+        __(ldr arg_y,[imm0,#-node_size])
+        __(cmp arg_y,#nil_value)
+        __(beq local_label(provided_key_done))
+        __(_cdr(arg_x,arg_reg))
+        __(_car(arg_x,arg_x))
+        __(str arg_x,[imm0,#0])
+        __(mov arg_x,#nil_value)
+        __(add arg_x,arg_x,#t_offset)
+        __(str arg_x,[imm0,#-node_size])
+        __(b local_label(provided_key_done))
+local_label(match_key_test):    
+        __(sub imm0,imm0,#node_size)
+        __(cmp imm0,#misc_data_offset)
+        __(bge local_label(match_key_loop))
+        __(orr nargs,nargs,#mask_unknown_keyword_seen)
+local_label(provided_key_done): 
+        __(_cdr(arg_reg,arg_reg))
+        __(_cdr(arg_reg,arg_reg))
+local_label(provided_key_loop):
+        __(cmp arg_reg,#nil_value)
+        __(bne local_label(next_provided_key))
+        __(tst nargs,#mask_unknown_keyword_seen)
+        __(bxeq lr)
+        __(tst nargs,#mask_aok)
+        __(bxne lr)
+local_label(badkeys):
+        __(mov arg_y,#XBADKEYS)
+        __(b local_label(destructure_error))
+local_label(toomany):   
+        __(mov arg_y,#XCALLTOOMANY)
+        __(b local_label(destructure_error))
+local_label(toofew):    
+        __(mov arg_y,#XCALLTOOFEW)
+        __(b local_label(destructure_error))
+local_label(badlist):   
+        __(mov arg_y,#XCALLNOMATCH)
+local_label(destructure_error): 
+        __(mov vsp,temp0)
+        __(mov arg_z,temp1)        
+        __(set_nargs(2))
+        __(b _SPksignalerr)
+        
 
 /*  EOF, basically  */
@@ -3780,218 +3924,5 @@
 	__(b _SPksignalerr)                
 
-C(destbind1): 
-dnl  /* Extract required arg count.  */
-dnl  /* A bug in gas: can't handle shift count of "32" (= 0  */
-dnl  ifelse(eval(mask_req_width+mask_req_start),eval(32),`
-dnl  __(clrlwi. imm0,nargs,mask_req_start)
-dnl  ',`
-dnl  __(extrwi. imm0,nargs,mask_req_width,mask_req_start)
-dnl  ')
-dnl  __(extrwi imm1,nargs,mask_opt_width,mask_opt_start)
-dnl  __(rlwinm imm2,nargs,0,mask_initopt,mask_initopt)
-dnl  __(rlwinm imm4,nargs,0,mask_keyp,mask_keyp)
-dnl  __(cmpri(cr4,imm4,0))
-dnl  __(rlwinm imm4,nargs,0,mask_restp,mask_restp)
-dnl  __(cmpri(cr5,imm4,0))
-dnl  __(cmpri(cr1,imm1,0))
-dnl  __(cmpri(cr2,imm2,0))
-dnl  /* Save entry vsp in case of error.  */
-dnl  __(mov imm4,vsp)
-dnl  __(beq 2f)
-dnl 1:
-dnl  __(cmpri(cr7,arg_reg,nil_value))
-dnl   __(extract_lisptag(imm3,arg_reg))
-dnl   __(cmpri(cr3,imm3,tag_list))
-dnl  __(subi imm0,imm0,1)
-dnl  __(cmpri(imm0,0))
-dnl  __(beq cr7,toofew)
-dnl  __(bne cr3,badlist)
-dnl  __(ldr arg_x,[arg_reg,#cons.car])
-dnl  __(ldr arg_reg,[arg_reg,#cons.cdr])
-dnl  __(vpush1(arg_x))
-dnl  __(bne 1b)
-dnl 2:
-dnl  __(beq cr1,rest_keys)
-dnl  __(bne cr2,opt_supp)
-dnl  /* 'simple' &optionals:  no supplied-p, default to nil.  */
-dnl simple_opt_loop:
-dnl  __(cmpri(arg_reg,nil_value))
-dnl   __(extract_lisptag(imm3,arg_reg))
-dnl   __(cmpri(cr3,imm3,tag_list))
-dnl  __(subi imm1,imm1,1)
-dnl  __(cmpri(cr1,imm1,0))
-dnl  __(mov imm5,#nil_value)
-dnl  __(beq default_simple_opt)
-dnl  __(bne cr3,badlist)
-dnl  __(ldr arg_x,[arg_reg,#cons.car])
-dnl  __(ldr arg_reg,[arg_reg,#cons.cdr])
-dnl  __(vpush1(arg_x))
-dnl  __(bne cr1,simple_opt_loop)
-dnl  __(b rest_keys)
-dnl default_simple_opt_loop:
-dnl  __(subi imm1,imm1,1)
-dnl  __(cmpri(cr1,imm1,0))
-dnl default_simple_opt:
-dnl  __(vpush1(imm5))
-dnl  __(bne cr1,default_simple_opt_loop)
-dnl  __(b rest_keys)
-dnl  /* Provide supplied-p vars for the &optionals.  */
-dnl opt_supp:
-dnl  __(mov arg_y,#t_value)
-dnl opt_supp_loop:
-dnl  __(cmpri(arg_reg,nil_value))
-dnl   __(extract_lisptag(imm3,arg_reg))
-dnl   __(cmpri(cr3,imm3,tag_list))
-dnl  __(subi imm1,imm1,1)
-dnl  __(cmpri(cr1,imm1,0))
-dnl  __(beq default_hard_opt)
-dnl  __(bne cr3,badlist)
-dnl  __(ldr arg_x,[arg_reg,#cons.car])
-dnl  __(ldr arg_reg,[arg_reg,#cons.cdr])
-dnl  __(vpush1(arg_x))
-dnl  __(vpush1(arg_y))
-dnl  __(bne cr1,opt_supp_loop)
-dnl  __(b rest_keys)
-dnl default_hard_opt_loop:
-dnl  __(subi imm1,imm1,1)
-dnl  __(cmpri(cr1,imm1,0))
-dnl default_hard_opt:
-dnl  __(vpush1(imm5))
-dnl  __(vpush1(imm5))
-dnl  __(bne cr1,default_hard_opt_loop)
-dnl rest_keys:
-dnl  __(cmpri(arg_reg,nil_value))
-dnl  __(bne cr5,have_rest)
-dnl  __(bne cr4,have_keys)
-dnl  __(bne toomany)
-dnl  __(bx lr)
-dnl have_rest:
-dnl  __(vpush1(arg_reg))
-dnl  __(beqlr cr4)
-dnl have_keys:
-dnl  /* Ensure that arg_reg contains a proper,even-length list.  */
-dnl  /* Insist that its length is <= 512 (as a cheap circularity check.)  */
-dnl  __(mov imm0,#256)
-dnl  __(mov arg_x,arg_reg)
-dnl count_keys_loop:
-dnl   __(extract_lisptag(imm3,arg_x))
-dnl   __(cmpri(cr3,imm3,tag_list))
-dnl  __(cmpri(arg_x,nil_value))
-dnl  __(subi imm0,imm0,1)
-dnl  __(cmpri(cr4,imm0,0))
-dnl  __(beq counted_keys)
-dnl  __(bne cr3,badlist)
-dnl  __(ldr arg_x,[arg_x,#cons.cdr])
-dnl   __(extract_lisptag(imm3,arg_x))
-dnl   __(cmpri(cr3,imm3,tag_list))
-dnl  __(blt cr4,toomany)
-dnl  __(cmpri(arg_x,nil_value))
-dnl  __(beq db_badkeys)
-dnl  __(bne cr3,badlist)
-dnl  __(ldr arg_x,[arg_x,#cons.cdr])
-dnl  __(b count_keys_loop)
-dnl counted_keys:
-dnl  /* We've got a proper, even-length list of key/value pairs in */
-dnl  /* arg_reg. For each keyword var in the lambda-list, push a pair */
-dnl  /* of NILs on the vstack.  */
-dnl  __(extrwi. imm0,nargs,mask_key_width,mask_key_start )
-dnl  __(mov imm2,imm0)  /* save number of keys  */
-dnl  __(mov imm5,#nil_value)
-dnl  __(b push_pair_test)
-dnl push_pair_loop:
-dnl  __(cmpri(imm0,1))
-dnl  __(subi imm0,imm0,1)
-dnl  __(vpush1(imm5))
-dnl  __(vpush1(imm5))
-dnl push_pair_test:
-dnl  __(bne push_pair_loop)
-dnl  __(slwi imm2,imm2,dnode_shift)  /* pairs -> bytes  */
-dnl  __(add imm2,vsp,imm2)  /* imm2 points below pairs  */
-dnl  __(mov imm0,#0)   /* count unknown keywords so far  */
-dnl  __(extrwi imm1,nargs,1,mask_aok) /* unknown keywords allowed  */
-dnl  __(extrwi nargs,nargs,mask_key_width,mask_key_start)
-dnl  /* Now, for each keyword/value pair in the list  */
-dnl  /*  a) if the keyword is found in the keyword vector, set the  */
-dnl  /*     corresponding entry on the vstack to the value and the  */
-dnl  /*     associated supplied-p var to T.  */
-dnl  /*  b) Regardless of whether or not the keyword is found,  */
-dnl         /*     if :ALLOW-OTHER-KEYS is provided with a non-nil value, */
-dnl  /*     set the low bit of imm1 to indicate that unknown keywords  */
-dnl  /*     are acceptable. (This bit is pre-set above to the value */
-dnl         /*     the encoded value of &allow_other_keys.) */
-dnl  /*  c) If the keyword is not found (and isn't :ALLOW-OTHER-KEYS), increment  */
-dnl  /*     the count of unknown keywords in the high bits of imm1*/
-dnl  /* At the end of the list, signal an error if any unknown keywords were seen  */
-dnl  /* but not allowed.  Otherwise, return.  */
-dnl 
-dnl match_keys_loop:
-dnl  __(cmpri(arg_reg,nil_value))
-dnl  __(mov imm0,#0)
-dnl  __(mov imm3,#misc_data_offset)
-dnl  __(beq matched_keys)
-dnl  __(ldr arg_x,[arg_reg,#cons.car])
-dnl  __(mov arg_y,#nrs.kallowotherkeys)
-dnl  __(cmpr(cr3,arg_x,arg_y)) /* :ALLOW-OTHER-KEYS ?  */
-dnl  __(ldr arg_reg,[arg_reg,#cons.cdr])
-dnl  __(ldr arg_y,[arg_reg,#cons.car])
-dnl  __(cmpr(cr4,imm0,nargs))
-dnl  __(ldr arg_reg,[arg_reg,#cons.cdr])
-dnl  __(b match_test)
-dnl match_loop:
-dnl  __(ldrx(temp0,keyvect_reg,imm3))
-dnl  __(cmpr(arg_x,temp0))
-dnl  __(addi imm0,imm0,1)
-dnl  __(cmpr(cr4,imm0,nargs))
-dnl  __(addi imm3,imm3,node_size)
-dnl  __(bne match_test)
-dnl  /* Got a hit.  Unless this keyword's been seen already, set it.  */
-dnl  __(slwi imm0,imm0,dnode_shift)
-dnl  __(subf imm0,imm0,imm2)
-dnl  __(ldr temp0,[imm0,#0])
-dnl  __(cmpri(temp0,nil_value))
-dnl  __(mov temp0,#t_value)
-dnl  __(bne match_keys_loop) /* already saw this  */
-dnl  __(str(arg_y,node_size*1(imm0)))
-dnl  __(str(temp0,node_size*0(imm0)))
-dnl         __(bne cr3,match_keys_loop)
-dnl  __(b match_keys_check_aok)
-dnl match_test:
-dnl  __(bne cr4,match_loop)
-dnl         __(beq cr3,match_keys_check_aok)
-dnl         __(addi imm1,imm1,node_size)
-dnl         __(b match_keys_loop)
-dnl match_keys_check_aok:
-dnl         __(andi. imm0,imm1,2)  /* check "seen-aok" bit in imm1 */
-dnl         __(cmpri cr1,arg_y,nil_value) /* check value */
-dnl         __(ori imm1,imm1,2)
-dnl         __(bne match_keys_loop) /* duplicate aok */
-dnl         __(beq cr1,match_keys_loop)
-dnl         __(ori imm1,imm1,1)
-dnl  __(b match_keys_loop)
-dnl matched_keys:
-dnl         __(clrrwi. imm0,imm1,2)
-dnl         __(beqlr)
-dnl         __(andi. imm1,imm1,1)
-dnl         __(bnelr)
-dnl  /* Some unrecognized keywords.  Complain generically about  */
-dnl  /* invalid keywords.  */
-dnl db_badkeys:
-dnl  __(mov arg_y,#XBADKEYS)
-dnl  __(b destructure_error)
-dnl toomany:
-dnl  __(mov arg_y,#XCALLTOOMANY)
-dnl  __(b destructure_error)
-dnl toofew:
-dnl  __(mov arg_y,#XCALLTOOFEW)
-dnl  __(b destructure_error)
-dnl badlist:
-dnl  __(mov arg_y,#XCALLNOMATCH)
-dnl  /* b destructure_error  */
-dnl destructure_error:
-dnl  __(mov vsp,imm4)  /* undo everything done to the stack  */
-dnl  __(mov arg_z,whole_reg)
-dnl  __(set_nargs(2))
-dnl  __(b _SPksignalerr)
-
+        
 /* imm2: (tstack-consed) target catch frame, imm0: count of intervening  */
 /* frames. If target isn't a multiple-value receiver, discard extra values */
