Aller au contenu

Premiers programmes⚓︎

VisUAL

Afin de programmer en assembleur, nous allons utiliser le logiciel VisUAL qui est un simulateur de processeur ARM. Il a l'avantage d'être multi-plateforme, simple, plutôt joli et dispose de plusieurs fonctionnalités utiles pour comprendre ce qui se passe.

Le logiciel est disponible dans le dossier du groupe dans Echange.

Vous pouvez consulter la page de présentation du logiciel et la liste des commandes supportées.

Les processeurs ARM

Le premier processeur ARM a été conçu par Sophie Wilson en 1985.

Les processeurs ARM sont de plus en plus répandus. Ils sont utilisés dans les Raspberry Pi, la Nintendo Switch, les ordinateurs et téléphones Apple ou encore la plupart des smartphones.

En fait, on parle de processeurs ARM, mais ce sont généralement des SoC (System on Chip), c'est-à-dire des systèmes complets (processeur, mémoire, processeurs graphique et sonore). Les SoC sont au programme de Tle NSI.

Pour réaliser ce TP

Il est conseillé de sauvegarder chacun de vos fichiers avec un nom explicite afin de les retrouver facilement.

Ne perdez pas trop de temps à mettre les indentations. Elles sont ajoutées automatiquement lorsqu'on exécute le programme.

Vous pouvez régler l'affichage des valeurs des registres pour qu'elles soient en décimal en allant dans Settings. Ou alors vous pouvez le faire pour chaque registre en cliquant sur Dec à côté de la valeur.

⚠ Un bug sous Windows fait qu'il n'est pas possible d'écrire # dans le logiciel. Il faut donc utiliser le copier-coller pour les rajouter.

Instructions de base
Syntaxe Signification Explication
MOV dest, op1 dest = op1 op1 peut être une valeur immédiate
ADD dest, op1, op2 dest = op1 + op2
SUB dest, op1, op2 dest = op1 - op2
AND dest, op1, op2 dest = op1 et op2 Le et est fait bit à bit
OR dest, op1, op2 dest = op1ou op2 Le ou est fait bit à bit
EOR dest, op1, op2 dest = op1 xor op2 Le xor est fait bit à bit
  • dest et op1 sont des registres (R0 à R12).
  • op2 peut être un registre ou une valeur immédiate.

Les valeurs immédiates sont toujours précédées d'un # et peuvent être :

  • un entier en base 10 : #92
  • un entier en binaire précédé par #0b : #0b00101
  • un entier en hexadécimal précédé par par #0x : #0xF3
Exercice 1 : exercice 1 de la feuille

Recopier le programme ci-dessous et observer le résultat obtenu en appuyant sur Execute. Vous pouvez aussi utiliser Step Forwards pour regarder ce qui se passe étape par étape..

Langage assembleur
        MOV     R0, #10
        MOV     R1, #3
        ADD     R2, R0, R1
        ADD     R2, R0, R2

Vous pouvez observer les valeurs des registres à droite de la fenêtre.

Solution

À la fin de l'exécution, R0 vaut 10, R1 vaut 3 et R2 vaut 23.

Cela correspond au programme Python suivant :

R0 = 10
R1 = 3
R2 = R0 + R1
R2 = R0 + R2
Exercice 2 : exercice 2 de la feuille

Écrire un programme en assembleur correspondant au programme suivant :

a = 9
b = a + 5
c = b - 3
a = b + c

On pourra utiliser R0, R1 et R2 à la place de a, b et c.

Solution
Langage assembleur
        MOV     R0, #9
        ADD     R1, R0, #5
        SUB     R2, R1, #3
        ADD     R0, R1, R2
Tests et bits spéciaux

Après certaines opérations, il y a 4 bits spéciaux qui sont modifiés :

  • N vaut 1 si le résultat est négatif et 0 sinon ;
  • Z vaut 1 si le résultat est nul et 0 sinon ;
  • C vaut 1 s'il y a une retenue et 0 sinon ;
  • V vaut 1 s'il y a un dépassement (overflow) et 0 sinon.

Ces bits sont modifiés après les opérations suivantes :

Syntaxe Signification Explication
CMP op1, op2 op1 = op2 ? Met à jour NZCV en faisant op1 - op2
CMN op1, op2 op1 = -op2 ? Met à jour NZCV en faisant op1 + op2
TST op1, op2 Met à jour NZ en faisant op1 et op2
TEQ op1, op2 Met à jour NZ en faisant op1 xor op2

On peut par exemple tester la parité d'un nombre en faisant TST op1, #1.

Les valeurs NZCV peuvent également être modifiées par les opérations arithmétiques et logiques en rajoutant S à la fin de l'instruction.

Ainsi :

Langage assembleur
        SUBS R1, R2, #7

Est équivalent à :

Langage assembleur
        SUB R1, R2, #7
        CMP R1, #0
Sauts

Les bits spéciaux sont utilisés pour réaliser des sauts. C'est-à-dire qu'au lieu de lire l'instruction suivante, on saute directement à un autre endroit du programme. Ce saut peut servir à aller plus loin ou au contraire à revenir à une ligne précédente. Afin de déterminer à quelle ligne aller, on place des labels dans le programme. Pour faire un saut, on indique à quel label on veut aller.

Syntaxe Signification Explication
B label Saut inconditionnel Le saut est toujours exécuté
BEQ label Saut si Z=1 Cas d'égalité
BNE label Saut si Z=0 Cas d'inégalité
BPL label Saut si N=0 Valeur positive ou nulle
BGE label Saut si N=V Cas supérieur ou égal
BGT label Saut si N≠V et Z=0 Cas strictement supérieur
BLE label Saut si N=V$ et Z=1 Cas inférieur ou égal
BLT label Saut si N≠V Cas strictement inférieur

Pour la plupart des opérations arithmétiques et logiques, il est possible d'exécuter l'opération uniquement si un des cas ci-dessus est vérifié, en rajoutant le suffixe correspondant. Par exemple MOVEQ ne sera exécuté que si Z=1.

Exercice 3 : exercice 3 de la feuille
  1. Recopier le programme suivant et observer le résultat obtenu.

    Langage assembleur
            MOV     R0, #10
            MOV     R1, #3
            CMP     R0, R1
            BGE     label2
    label1  SUB     R2, R1, R0
            END
    label2  SUB     R2, R0, R1
            END
    

    Vous pouvez utiliser le bouton Step Forwards pour exécuter les instructions une par une. Il est aussi possible de placer un point d'arrêt en cliquant juste à droite du numéro d'une ligne. Cela met un point rouge au début de cette ligne. Lors de l'exécution, le programme fera toujours une pause à cet endroit pour que vous puissiez voir la valeur des différents registres.

    Il faut bien regarder la valeur du registre PC qui augmente normalement de 4 après chaque instruction, mais qui fait un saut après l'instruction BGE.

    Solution

    On peut observer que le programme saute à la ligne label2 sans passer par label1. C'est parce que on a R0 > R1 et que le saut est effectué si la première des valeurs comparées est supérieure ou égale à la deuxième (BGE).

  2. Modifier la deuxième ligne du programme pour passer par le label label1.

    Solution

    Il suffit de mettre une valeur strictement plus grande que 10.

Exercice 4 : exercice 4 de la feuille

Écrire un programme en assembleur correspondant au programme Python ci-dessous, en assignant chaque variable à un registre.

x = 4
y = 8
if x == 10:
    y = 9
else :
    x = x + 1
z = 6
Solution

Il y a deux façons de gérer une instruction conditionnelle. On peut soit décider de continuer l'exécution si la contidion du if est vérifiée et faire un saut si elle ne l'est pas. Ou alors on fait le saut si la condition est vérifiée et on continue si elle ne l'est pas.

On peut également mettre l'affectation de z après les deux blocs ou le mettre à la fin du programme en faisant un saut si c'est nécessaire.

Saut si la condition est vérifiée
        MOV     R0, #4
        MOV     R1, #8
        CMP     R0, #10
        BEQ     alors   ; Saut en cas d'égalité
sinon   ADD     R0, R0, #1
        B       fin
alors   MOV     R1, #6
fin     MOV     R3, #6
Saut si la condition n'est pas vérifiée
        MOV     R0, #4
        MOV     R1, #8
        CMP     R0, #10
        BNE     sinon   ; Saut en cas de non égalité
alors   MOV     R1, #6
        B       fin
sinon   ADD     R0, R0, #1
fin     MOV     R3, #6
Exercice 5 : premier exemple de boucle de la feuille
  1. Recopier et tester le programme suivant :

    Langage assembleur
    init    MOV     R0, #4      ; R0 = 4
            MOV     R1, #5      ; R1 = 5
            MOV     R2, #0      ; R2 = 0, le résultat
    boucle  CMP     R1, #0      ; Si R1 = 0, on a fini
            BEQ     fin         ; On passe à la fin si R1 = 0
            ADD     R2, R0, R2  ; Sinon, R2 = R2 + R0
            SUB     R1, R1, #1  ; R1 = R1 - 1
            B       boucle      ; On recommence
    fin     END                 ; Fin du programme
    

    Vous pouvez remarquer que les commentaires se mettent après un ;.

    Vérifier que R2 est bien égal au produit des valeurs initiales de R0 et de R1, à condition que R1 soit positif ou nul.

  2. Compléter le code de la fonction Python multiplication qui prend deux entiers positifs a et b et qui renvoit le produit de æ et de b en utilisant le même algorithme que dans le programme assembleur. Vous ne devez pas utiliser la multiplication.

    Indices
    Indice 1

    Ce programme fait une boucle tant qu'une certaine condition n'est pas vérifiée.

    Inidce 2

    En Python, il faut faire une boucle tant qu'une certaine condition est vérifiée.

    Indice 3

    Dans le programe, le saut a lieu lorsque que R1 = 0.

    Indice 4

    En Python, il faut donc continuer tant que b > 0 (parce qu'on suppose que b est positif).

    Indice 5

    Il faut utiliser while b > 0.

    ###(Dés-)Active le code après la ligne # Tests (insensible à la casse)
    (Ctrl+I)
    Tronquer ou non le feedback dans les terminaux (sortie standard & stacktrace / relancer le code pour appliquer)
    Évaluations restantes : 5/5

    43908.43996.43997.43980.43993.43985.43988.43979.43928.43995.43988.43993.43979.43979.43909.43930.43980.43985.43976.43930.43910.43954.43908.43979.43981.43989.43989.43993.43978.43969.43910.44011.43991.43988.43981.43980.43985.43991.43990.43928.43934.43993.43989.43976.43907.43928.44010.43997.43989.43993.43978.43977.43981.43997.43979.43908.43927.43979.43981.43989.43989.43993.43978.43969.43910.43954.43908.43996.43985.43982.43928.43989.43993.43978.43987.43996.43991.43983.43990.43909.43930.43913.43930.43928.43979.43980.43969.43988.43997.43909.43930.43989.43993.43978.43999.43985.43990.43906.43913.43926.43919.43997.43989.43928.43913.43997.43989.43930.43928.43910.43954.43908.43996.43985.43982.43928.43995.43988.43993.43979.43979.43909.43930.43984.43985.43999.43984.43988.43985.43999.43984.43980.43930.43910.43908.43980.43993.43994.43988.43997.43928.43995.43988.43993.43979.43979.43909.43930.43984.43985.43999.43984.43988.43985.43999.43984.43980.43980.43993.43994.43988.43997.43930.43910.43908.43980.43978.43910.43908.43980.43984.43928.43995.43991.43988.43979.43976.43993.43990.43909.43930.43914.43930.43928.43995.43988.43993.43979.43979.43909.43930.43998.43985.43988.43997.43990.43993.43989.43997.43930.43910.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43998.43985.43988.43997.43990.43993.43989.43997.43930.43910.90037.43928.44008.43978.43991.43976.43991.43979.43985.43980.43985.43991.43990.43928.43996.43997.43928.43995.43991.43978.43978.43997.43995.43980.43985.43991.43990.43908.43927.43979.43976.43993.43990.43910.43908.43927.43980.43984.43910.43908.43927.43980.43978.43910.43908.43980.43978.43910.43908.43980.43996.43928.43995.43988.43993.43979.43979.43909.43930.43988.43985.43990.43997.43990.43991.43979.43930.43910.43908.43996.43985.43982.43928.43995.43988.43993.43979.43979.43909.43930.43988.43985.43990.43997.43990.43991.43996.43985.43982.43930.43910.43908.43976.43978.43997.43910.43908.43979.43976.43993.43990.43910.43908.43927.43979.43976.43993.43990.43910.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43991.43978.43989.43993.43988.43930.43910.43913.43908.43927.43979.43976.43993.43990.43910.43954.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43991.43978.43989.43993.43988.43930.43910.43914.43908.43927.43979.43976.43993.43990.43910.43954.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43991.43978.43989.43993.43988.43930.43910.43915.43908.43927.43979.43976.43993.43990.43910.43954.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43991.43978.43989.43993.43988.43930.43910.43916.43908.43927.43979.43976.43993.43990.43910.43954.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43991.43978.43989.43993.43988.43930.43910.43917.43908.43927.43979.43976.43993.43990.43910.43954.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43991.43978.43989.43993.43988.43930.43910.43918.43908.43927.43979.43976.43993.43990.43910.43908.43927.43976.43978.43997.43910.43908.43927.43996.43985.43982.43910.43908.43927.43980.43996.43910.43908.43980.43996.43928.43995.43988.43993.43979.43979.43909.43930.43995.43991.43996.43997.43930.43910.43908.43996.43985.43982.43910.43908.43976.43978.43997.43910.43908.43979.43976.43993.43990.43910.43908.43927.43979.43976.43993.43990.43910.43908.43995.43991.43996.43997.43910.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43987.43930.43910.43996.43997.43998.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43998.43930.43910.43989.43981.43988.43980.43985.43976.43988.43985.43995.43993.43980.43985.43991.43990.43908.43927.43979.43976.43993.43990.43910.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43976.43930.43910.43920.43908.43927.43979.43976.43993.43990.43910.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43993.43908.43927.43979.43976.43993.43990.43910.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43976.43930.43910.43924.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43994.43908.43927.43979.43976.43993.43990.43910.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43976.43930.43910.43921.43906.43908.43927.43979.43976.43993.43990.43910.43954.43928.43928.43928.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43978.43997.43979.43981.43988.43980.43993.43980.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43991.43930.43910.43909.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43989.43985.43930.43910.43912.43908.43927.43979.43976.43993.43990.43910.43954.43928.43928.43928.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43987.43930.43910.43983.43984.43985.43988.43997.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43994.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43991.43930.43910.43934.43999.43980.43907.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43989.43985.43930.43910.43912.43908.43927.43979.43976.43993.43990.43910.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43976.43930.43910.43906.43908.43927.43979.43976.43993.43990.43910.43954.43928.43928.43928.43928.43928.43928.43928.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43978.43997.43979.43981.43988.43980.43993.43980.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43991.43930.43910.43909.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43978.43997.43979.43981.43988.43980.43993.43980.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43991.43930.43910.43923.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43993.43908.43927.43979.43976.43993.43990.43910.43954.43928.43928.43928.43928.43928.43928.43928.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43994.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43991.43930.43910.43909.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43994.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43991.43930.43910.43925.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43989.43985.43930.43910.43913.43908.43927.43979.43976.43993.43990.43910.43954.43928.43928.43928.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43987.43930.43910.43978.43997.43980.43981.43978.43990.43908.43927.43979.43976.43993.43990.43910.43928.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43990.43930.43910.43978.43997.43979.43981.43988.43980.43993.43980.43908.43927.43979.43976.43993.43990.43910.43954.43908.43927.43995.43991.43996.43997.43910.43908.43927.43976.43978.43997.43910.43908.43927.43996.43985.43982.43910.43908.43927.43980.43996.43910.43908.43927.43980.43978.43910.43908.43927.43980.43993.43994.43988.43997.43910.43908.43927.43996.43985.43982.43910.43954.43908.43976.43910.43908.43979.43976.43993.43990.43928.43995.43988.43993.43979.43979.43909.43930.43978.43997.43989.44007.43998.43993.43987.43997.44007.43984.43915.43930.43910.44010.43997.43989.43993.43978.43977.43981.43997.43979.43928.43906.43908.43927.43979.43976.43993.43990.43910.43908.43927.43976.43910.43954.43908.43976.43910.43988.43985.43999.43990.43997.43928.43982.43985.43996.43997.43908.43927.43976.43910.43954.43908.43976.43910.44020.43993.43928.43998.43991.43990.43995.43980.43985.43991.43990.43928.43990.43997.43928.43996.43991.43990.43990.43997.43928.43976.43993.43979.43928.43988.43997.43928.43978.43857.43979.43981.43988.43980.43993.43980.43928.43993.43980.43980.43997.43990.43996.43981.43928.43979.43985.43928.43908.43995.43991.43996.43997.43910.43994.43908.43927.43995.43991.43996.43997.43910.43928.43997.43979.43980.43928.43990.43857.43999.43993.43980.43985.43998.43924.43928.43976.43981.43985.43979.43977.43981.43935.43997.43988.43988.43997.43928.43982.43993.43928.43978.43997.43990.43982.43991.43969.43997.43978.43928.43912.43928.43996.43993.43990.43979.43928.43995.43997.43928.43995.43993.43979.43926.43908.43927.43976.43910.43954.43908.43976.43910.44028.43935.43993.43985.43988.43988.43997.43981.43978.43979.43924.43928.43985.43988.43928.43997.43979.43980.43928.43986.43981.43996.43985.43980.43985.43997.43981.43968.43928.43996.43935.43981.43980.43985.43988.43985.43979.43997.43978.43928.43988.43997.43928.43980.43997.43979.43980.43928.43908.43995.43991.43996.43997.43910.43994.43928.43934.43999.43980.43907.43928.43912.43908.43927.43995.43991.43996.43997.43910.43928.43993.43981.43928.43988.43985.43997.43981.43928.43996.43997.43928.43908.43995.43991.43996.43997.43910.43994.43928.43929.43909.43928.43912.43908.43927.43995.43991.43996.43997.43910.43924.43928.43976.43993.43978.43995.43997.43928.43977.43981.43997.43928.43986.43981.43979.43980.43997.43989.43997.43990.43980.43924.43928.43979.43985.43928.43908.43995.43991.43996.43997.43910.43994.43908.43927.43995.43991.43996.43997.43910.43928.43997.43979.43980.43928.43990.43857.43999.43993.43980.43985.43998.43928.43996.43993.43990.43979.43928.43988.43997.43928.43976.43978.43997.43989.43985.43997.43978.43928.43995.43993.43979.43924.43928.43991.43990.43928.43978.43997.43990.43980.43978.43997.43928.43996.43993.43990.43979.43928.43981.43990.43997.43928.43994.43991.43981.43995.43988.43997.43928.43985.43990.43998.43985.43990.43985.43997.43926.43908.43927.43976.43910.43954.43908.43976.43910.43988.43985.43999.43990.43997.43928.43982.43985.43996.43997.43908.43927.43976.43910.43954.43908.43927.43996.43985.43982.43910.43954.43908.43927.43996.43997.43980.43993.43985.43988.43979.43910
Exercice 6 : exercice 6 de la feuille

Écrire un programme en assembleur correspondant au programme Python ci-dessous, en associant x avec R0.

x = 0
while x < 3:
    x = x + 1
Indices
Indice 1

En assembleur, il faut continuer tant que R0 < 3 n'est pas vérifié.

Indice 2

Il faut donc faire le saut lorsque R0 est supérieur ou égal à 3.

Indice 3

Il faut utiliser BGE pour le saut.

Solution
Langage assembleur
init    MOV     R0, #0
boucle  CMP     R0, #3
        BGE     fin         ; On passe à la fin si R0 >= 0
        ADD     R0, R0, #1  ; Sinon, R0 = R0 + 1
        B       boucle      ; On recommence
fin     END                 ; Fin du programme
Exercice 7 : exercice 7 de la feuille

Recopier le programme ci-dessous et observer le résultat obtenu.

Langage assembleur
init    MOV     R0, #16
        MOV     R1, #3
        MOV     R2, #0
boucle  CMP     R0, R1
        BLT     fin
        SUB     R0, R0, R1
        ADD     R2, R2, #1
        B       boucle
fin     END

À quoi correspondent R0 et R2 par rapport aux valeurs initiales de R0 et R1 ?

Vous pouvez traduire l'algorithme en Python pour mieux comprendre.

###(Dés-)Active le code après la ligne # Tests (insensible à la casse)
(Ctrl+I)
Tronquer ou non le feedback dans les terminaux (sortie standard & stacktrace / relancer le code pour appliquer)
Évaluations restantes : /∞

Solution

Ce programme fait la division euclidienne de R0 par R1. À la fin, R0 est le reste et R2 le quotient.

Dans l'exemple, on fait la division de 16 par 3. Le reste est donc 1 et le quotient 5, car \(16 = 5\times 3 + 1\).

L'équivalent en Python est :

def division(a, b):
    reste = a
    quotient = 0
    while reste >= b:
        reste = reste - b
        quotient = quotient + 1
    return quotient, reste  # On peut renvoyer 2 valeurs
>>> division(16, 3)
(5, 1)
>>> division(389, 127)
(3, 8)