Damm algorithm: Difference between revisions
Content added Content deleted
(PHP implementation of Damm algorithm) |
Not a robot (talk | contribs) (Add ARM Assembly) |
||
Line 350: | Line 350: | ||
{{output}} |
{{output}} |
||
<lang applescript>{"5724 is valid", "57240 is valid", "572400 is valid", "87591 is invalid", "100 is invalid", "3922446 is valid"}</lang> |
<lang applescript>{"5724 is valid", "57240 is valid", "572400 is valid", "87591 is invalid", "100 is invalid", "3922446 is valid"}</lang> |
||
=={{header|ARM Assembly}}== |
|||
<lang>.text |
|||
.global _start |
|||
@@@ Check if the zero-terminated ASCII string in [r0], |
|||
@@@ which should contain a decimal number, has a |
|||
@@@ matching check digit. Zero flag set if true, |
|||
@@@ check digit returned in r0. |
|||
damm: mov r1,#0 @ R1 = interim digit |
|||
ldr r2,=3f @ R2 = table base address |
|||
1: ldrb r3,[r0],#1 @ Load byte |
|||
tst r3,r3 @ Zero yet? |
|||
beq 2f @ If so, stop |
|||
sub r3,r3,#'0 @ Subtract ASCII 0 |
|||
lsl r1,r1,#1 @ Table lookup |
|||
add r1,r1,r1,lsl#2 @ R3 = R1*10 + R3 |
|||
add r3,r1,r3 |
|||
ldrb r1,[r2,r3] @ R1 = new interim digit |
|||
b 1b @ Next value |
|||
2: movs r0,r1 @ Set flag according to r0. |
|||
bx lr |
|||
3: .byte 0,3,1,7,5,9,8,6,4,2 @ Since the table is constant, |
|||
.byte 7,0,9,2,1,5,4,8,6,3 @ it can be stored as part of |
|||
.byte 4,2,0,6,8,7,1,3,5,9 @ the subroutine. |
|||
.byte 1,7,5,0,9,8,3,4,2,6 @ This way the OS will even mark |
|||
.byte 6,1,2,3,0,4,5,9,7,8 @ it as read-only, so we can |
|||
.byte 3,6,7,4,2,0,9,5,8,1 @ be sure nothing changes it. |
|||
.byte 5,8,6,9,7,2,0,1,3,4 |
|||
.byte 8,9,4,5,3,6,2,0,1,7 |
|||
.byte 9,4,3,8,6,1,7,2,0,5 |
|||
.byte 2,5,8,1,4,3,6,7,9,0 |
|||
.align 4 @ Instructions must be word-aligned |
|||
@@@ Grab the argument from the command line, and see |
|||
@@@ if it matches. |
|||
_start: pop {r0} @ Is there even an argument? |
|||
cmp r0,#2 |
|||
movne r7,#1 @ If not, exit immediately |
|||
swine #0 |
|||
add sp,sp,#4 @ Discard program name |
|||
pop {r0} @ Grab argument |
|||
bl damm @ Check if it matches |
|||
ldreq r1,=pass @ If yes, say 'pass' |
|||
ldrne r1,=fail @ If not, say 'fail' |
|||
mov r0,#1 @ Print string to stdout |
|||
mov r2,#5 @ Both are 5 characters |
|||
mov r7,#4 @ Write syscall = 4 |
|||
swi #0 |
|||
mov r0,#0 @ Exit |
|||
mov r7,#1 |
|||
swi #0 |
|||
pass: .ascii "Pass\n" |
|||
fail: .ascii "Fail\n"</lang> |
|||
{{out}} |
|||
<pre>$ for x in 5724 5725 112946 112949; do echo -n $x:; ./damm $x; done |
|||
5724:Pass |
|||
5725:Fail |
|||
112946:Pass |
|||
112949:Fail</pre> |
|||
=={{header|AutoHotkey}}== |
=={{header|AutoHotkey}}== |