mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-13 01:29:28 +02:00
* system unit can be build for subarch avrtiny
git-svn-id: trunk@44032 -
This commit is contained in:
parent
6c71fd461d
commit
17c4834a4a
@ -31,6 +31,7 @@ procedure fpc_cpuinit;{$ifdef SYSTEMINLINE}inline;{$endif}
|
||||
end;
|
||||
|
||||
|
||||
{$ifndef CPUAVR_16_REGS}
|
||||
{$define FPC_SYSTEM_HAS_MOVE}
|
||||
procedure Move(const source;var dest;count:SizeInt);[public, alias: 'FPC_MOVE']; assembler; nostackframe;
|
||||
asm
|
||||
@ -70,7 +71,7 @@ asm
|
||||
pop r29
|
||||
pop r28
|
||||
end;
|
||||
|
||||
{$endif CPUAVR_16_REGS}
|
||||
|
||||
{$define FPC_SYSTEM_HAS_FILLCHAR}
|
||||
Procedure FillChar(var x;count:SizeInt;value:byte);
|
||||
|
@ -42,6 +42,50 @@ finish:
|
||||
mov R24, R22 // Move result from R22 to R24
|
||||
end;
|
||||
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
function fpc_divmod_word(n, z: word): word; assembler; nostackframe;
|
||||
label
|
||||
div1, div2, div3, finish;
|
||||
asm
|
||||
// Symbol Name Register(s)
|
||||
// z (A) dividend R23, R22
|
||||
// n (B) divisor R25, R24
|
||||
// p (P) remainder R21, R20
|
||||
// i counter R18
|
||||
|
||||
clr R20 // clear remainder low
|
||||
clr R21 // clear remainder hi
|
||||
ldi R18, 16 // iterate over 16 bits
|
||||
|
||||
div1:
|
||||
lsl R22 // shift left A_L
|
||||
rol R23
|
||||
rol R20 // shift left P with carry from A shift
|
||||
rol R21
|
||||
sub R20, R24 // Subtract B from P, P <= P - B
|
||||
sbc R21, R25
|
||||
brlo div2
|
||||
ori R22, 1 // Set A[0] = 1
|
||||
rjmp div3
|
||||
div2: // negative branch, A[0] = 0 (default after shift), restore P
|
||||
add R20, R24 // restore old value of P
|
||||
adc R21, R25
|
||||
|
||||
div3:
|
||||
dec R18
|
||||
brne div1
|
||||
|
||||
finish:
|
||||
mov R24, R22 // Move result from R22:R23 to R24:R25
|
||||
mov R25, R23 // Move result from R22:R23 to R24:R25
|
||||
end;
|
||||
|
||||
function fpc_divmod_dword(n, z: dword): dword; assembler; nostackframe;
|
||||
label
|
||||
div1, div2, div3, finish;
|
||||
asm
|
||||
end;
|
||||
{$else CPUAVR_16_REGS}
|
||||
// z in Ra, n in Rb, 0 in Rp
|
||||
function fpc_divmod_word(n, z: word): word; assembler; nostackframe;
|
||||
label
|
||||
@ -134,4 +178,5 @@ finish:
|
||||
pop R15
|
||||
pop R16
|
||||
pop R17
|
||||
end;
|
||||
end;
|
||||
{$endif CPUAVR_16_REGS}
|
||||
|
@ -13,6 +13,7 @@
|
||||
|
||||
**********************************************************************}
|
||||
|
||||
{$ifndef CPUAVR_16_REGS}
|
||||
{$define FPC_SYSTEM_HAS_SHR_QWORD}
|
||||
// Simplistic version with checking if whole bytes can be shifted
|
||||
// Doesn't change bitshift portion even if possible because of byteshift
|
||||
@ -563,3 +564,4 @@ asm
|
||||
adc R25, R1
|
||||
fin:
|
||||
end;
|
||||
{$endif CPUAVR_16_REGS}
|
||||
|
@ -26,7 +26,11 @@
|
||||
function fpc_div_byte(n, z: byte): byte; assembler; nostackframe;
|
||||
{$ifdef FPC_IS_SYSTEM}[public,alias: 'FPC_DIV_BYTE'];{$endif}
|
||||
asm
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
cp R24, R17
|
||||
{$else CPUAVR_16_REGS}
|
||||
cp R24, R1
|
||||
{$endif CPUAVR_16_REGS}
|
||||
brne .LNonZero
|
||||
{$ifdef CPUAVR_HAS_JMP_CALL}
|
||||
call fpc_divbyzero
|
||||
@ -55,7 +59,11 @@ function fpc_div_byte(n, z: byte): byte; external name 'FPC_DIV_BYTE';
|
||||
function fpc_mod_byte(n, z: byte): byte; assembler; nostackframe;
|
||||
{$ifdef FPC_IS_SYSTEM}[public,alias: 'FPC_MOD_BYTE'];{$endif}
|
||||
asm
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
cp R24, R17
|
||||
{$else CPUAVR_16_REGS}
|
||||
cp R24, R1
|
||||
{$endif CPUAVR_16_REGS}
|
||||
brne .LNonZero
|
||||
{$ifdef CPUAVR_HAS_JMP_CALL}
|
||||
call fpc_divbyzero
|
||||
@ -84,8 +92,13 @@ function fpc_mod_byte(n, z: byte): byte; external name 'FPC_MOD_BYTE';
|
||||
function fpc_div_word(n, z: word): word; assembler; nostackframe;
|
||||
{$ifdef FPC_IS_SYSTEM}[public,alias: 'FPC_DIV_WORD'];{$endif}
|
||||
asm
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
cp R24, R17
|
||||
cpc R25, R17
|
||||
{$else CPUAVR_16_REGS}
|
||||
cp R24, R1
|
||||
cpc R25, R1
|
||||
{$endif CPUAVR_16_REGS}
|
||||
brne .LNonZero
|
||||
{$ifdef CPUAVR_HAS_JMP_CALL}
|
||||
call fpc_divbyzero
|
||||
@ -97,7 +110,12 @@ asm
|
||||
rcall fpc_divmod_word
|
||||
{$endif CPUAVR_HAS_JMP_CALL}
|
||||
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
mov R24, R20
|
||||
mov R25, R21
|
||||
{$else CPUAVR_16_REGS}
|
||||
movw R24, R22
|
||||
{$endif CPUAVR_16_REGS}
|
||||
end;
|
||||
|
||||
{It is a compilerproc (systemh.inc), make an alias for internal use.}
|
||||
@ -114,8 +132,13 @@ function fpc_div_word(n, z: word): word; external name 'FPC_DIV_WORD';
|
||||
function fpc_mod_word(n, z: word): word; assembler; nostackframe;
|
||||
{$ifdef FPC_IS_SYSTEM}[public,alias: 'FPC_MOD_WORD'];{$endif}
|
||||
asm
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
cp R24, R17
|
||||
cpc R25, R17
|
||||
{$else CPUAVR_16_REGS}
|
||||
cp R24, R1
|
||||
cpc R25, R1
|
||||
{$endif CPUAVR_16_REGS}
|
||||
brne .LNonZero
|
||||
{$ifdef CPUAVR_HAS_JMP_CALL}
|
||||
call fpc_divbyzero
|
||||
@ -127,7 +150,12 @@ asm
|
||||
rcall fpc_divmod_word
|
||||
{$endif CPUAVR_HAS_JMP_CALL}
|
||||
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
mov R24, R20
|
||||
mov R25, R21
|
||||
{$else CPUAVR_16_REGS}
|
||||
movw R24, R20
|
||||
{$endif CPUAVR_16_REGS}
|
||||
end;
|
||||
|
||||
{It is a compilerproc (systemh.inc), make an alias for internal use.}
|
||||
@ -144,10 +172,17 @@ function fpc_mod_word(n, z: word): word; external name 'FPC_MOD_WORD';
|
||||
function fpc_div_dword(n, z: dword): dword; assembler; nostackframe;
|
||||
{$ifdef FPC_IS_SYSTEM}[public,alias: 'FPC_DIV_DWORD'];{$endif}
|
||||
asm
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
cp R24, R17
|
||||
cpc R25, R17
|
||||
cpc R22, R17
|
||||
cpc R23, R17
|
||||
{$else CPUAVR_16_REGS}
|
||||
cp R24, R1
|
||||
cpc R25, R1
|
||||
cpc R22, R1
|
||||
cpc R23, R1
|
||||
{$endif CPUAVR_16_REGS}
|
||||
brne .LNonZero
|
||||
{$ifdef CPUAVR_HAS_JMP_CALL}
|
||||
call fpc_divbyzero
|
||||
@ -159,8 +194,15 @@ asm
|
||||
rcall fpc_divmod_dword
|
||||
{$endif CPUAVR_HAS_JMP_CALL}
|
||||
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
mov R22, R18 // Move result from R18:R21 to R22:R25
|
||||
mov R23, R19 // Move result from R18:R21 to R22:R25
|
||||
mov R24, R20
|
||||
mov R25, R21
|
||||
{$else CPUAVR_16_REGS}
|
||||
movw R22, R18 // Move result from R18:R21 to R22:R25
|
||||
movw R24, R20
|
||||
{$endif CPUAVR_16_REGS}
|
||||
end;
|
||||
|
||||
{It is a compilerproc (systemh.inc), make an alias for internal use.}
|
||||
@ -177,10 +219,17 @@ function fpc_div_dword(n, z: dword): dword; external name 'FPC_DIV_DWORD';
|
||||
function fpc_mod_dword(n, z: dword): dword; assembler; nostackframe;
|
||||
{$ifdef FPC_IS_SYSTEM}[public,alias: 'FPC_MOD_DWORD'];{$endif}
|
||||
asm
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
cp R24, R17
|
||||
cpc R25, R17
|
||||
cpc R22, R17
|
||||
cpc R23, R17
|
||||
{$else CPUAVR_16_REGS}
|
||||
cp R24, R1
|
||||
cpc R25, R1
|
||||
cpc R22, R1
|
||||
cpc R23, R1
|
||||
{$endif CPUAVR_16_REGS}
|
||||
brne .LNonZero
|
||||
{$ifdef CPUAVR_HAS_JMP_CALL}
|
||||
call fpc_divbyzero
|
||||
|
@ -100,10 +100,18 @@ procedure fpc_longjmp(var S : jmp_buf;value : shortint);assembler;[Public, alias
|
||||
// restore stack pointer
|
||||
ld r18,x+
|
||||
ld r19,x+
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
in r16,63
|
||||
{$else CPUAVR_16_REGS}
|
||||
in r0,63
|
||||
{$endif CPUAVR_16_REGS}
|
||||
cli
|
||||
out 62,r19
|
||||
{$ifdef CPUAVR_16_REGS}
|
||||
out 63,r16
|
||||
{$else CPUAVR_16_REGS}
|
||||
out 63,r0
|
||||
{$endif CPUAVR_16_REGS}
|
||||
out 61,r18
|
||||
|
||||
// restore return address
|
||||
|
Loading…
Reference in New Issue
Block a user