From: pito <pi...@vo...> - 2010-09-11 15:17:44
|
> Please keep in mind that machine stack is not > indefinite (64 bytes only). So if your routine > is pushing something on stack and doing some > calls it can get tight. I've changed that to 256: .set rstackstart = RAMEND ; start address of return stack, grows downward .set stackstart = RAMEND - 256 ; 80 start address of data stack, grows downward > Regarding you other email, regarding "here", "dp" > etc. DP and HERE are stored in EEPROM (in my case > EEPROM So when RAM is needed within fuX word and only there, I have to read HERE and DP and from that point to allocate RAM fro fuX. When leaving fuX, I do not need to write the new pointers to EEPROM, I just leave that as they are (as I do not need RAM anymore.. So the template for fictious word 'fuX' is now (based on my amforth .lst as the Registers are concerned): ; amforth 4.1 ; ..core\words\fuX.asm ; Function fuX( a b c -- m l k ) ; R( ? -- ? ) ; calculates a special function fuX ; it uses ALL registers except Y ; it calls subroutines placed within the word fuX ; does not use Y - points the data stack VE_FUX: .dw $ff03 ;? .db "fuX",0 .dw VE_HEAD .set VE_HEAD = VE_FUX XT_FUX: .dw PFA_FUX PFA_FUX: push R0 push R1 ; R2 you may use, restore to 0 ; R3 you may use, restore to 0 push R4 push R5 push R6 push R7 push R8 push R9 push R10 push R11 push R12 push R13 ; R14 you may use, no need to push/pop, = temp4 ; R15 you may use, no need to push/pop, = temp5 ; R16 you may use, no need to push/pop, = temp0 ; R17 you may use, no need to push/pop, = temp1 ; R18 you may use, no need to push/pop, = temp2 ; R19 you may use, no need to push/pop, = temp3 ; R20 you may use, no need to push/pop, = temp6 ; R21 you may use, no need to push/pop, = temp7 push R22 push R23 ; R24 do not push/pop, = tosl ; R25 do not push/pop, = tosh push R26 push R27 ; R28 do not use, = Y ; R29 do not use, = Y ; R30 you may use, no need to push/pop, = Z ; R31 you may use, no need to push/pop, = Z do_something ld R24, Y+ ld R25, Y+ ; takes c from stack do_something ld R24, Y+ ld R25, Y+ ; takes b from stack do_something ld R24, Y+ ld R25, Y+ ; takes a from stack do_something work_with_RAM_indirect_Using_Z work_with_RAM_indirect_Using_X call sub3 do_something jmp label1 do_something label1: do_something jmp label2 ; ijmp rjmp as well do_something call sub3 do_something jmp label3 label2: do_something call sub1 ; rcall icall as well call sub2 do_something label3: do_something call sub2 do_something st -Y, R25 st -Y, R24 ; puts m on stack do_something st -Y, R25 st -Y, R24 ; puts l on stack do_something st -Y, R24 st -Y, R25 ; puts k on stack pop R27 ; RESTORE REGISTERS IN REVERSE ORDER .... pop R4 ldi R3, 0 ldi R2, 0 pop R1 pop R0 jmp label_end ; jmp to the end of the word "fuX" sub1: do_something call sub3 ret sub2: do_something call sub1 ret sub3: do_something work_with_RAM_indirect_Using_Z work_with_RAM_indirect_Using_X ret label_end: jmp_ DO_NEXT ; this is the end of the word "fuX" |