Vom C-Programm zum Prozeß

/* addbetr.c 31.12.2000 kw
 * Kleines Beispiel
 */

int betrag( int wert )
{
  if( wert<0 )
    {
      return -wert;
    }
  else
    {
      return wert;
    }
}

int addierebetraege( int summand1, int summand2 )
{
  int summe;

  summe = betrag( summand1 ) + betrag( summand2 );

  return summe;
}

int main( int nargs, char **args )
{
  int i, j, erg;

  i = 12;
  j = 13;

  erg = addierebetraege( i, j );

  return 0;
}

                    .text


                    ;   1:addbetr.c     **** /* addbetr.c 31.12.2000 kw
                    ;   2:addbetr.c     ****  * Kleines Beispiel
                    ;   3:addbetr.c     ****  */
                    ;   4:addbetr.c     **** 
                    ;   5:addbetr.c     **** int betrag( int wert )
                    .globl betrag
                            .type    betrag,@function


                    ;   6:addbetr.c     **** {
                    betrag:
 0000 55                    pushl %ebp
 0001 89E5                  movl %esp,%ebp


                    ;   7:addbetr.c     ****   if( wert<0 )
 0003 837D0800              cmpl $0,8(%ebp)
 0007 7D0B                  jge .L3


                    ;   8:addbetr.c     ****     {
                    ;   9:addbetr.c     ****       return -wert;
 0009 8B5508                movl 8(%ebp),%edx
 000c F7DA                  negl %edx
 000e 89D0                  movl %edx,%eax
 0010 EB0E                  jmp .L2


                    ;  10:addbetr.c     ****     }
 0012 EB0C                  jmp .L4
                    .L3:


                    ;  11:addbetr.c     ****   else
                    ;  12:addbetr.c     ****     {
                    ;  13:addbetr.c     ****       return wert;
 0014 8B5508                movl 8(%ebp),%edx
 0017 89D0                  movl %edx,%eax
 0019 EB05                  jmp .L2
 001b 908D7426              .p2align 4,,7
      00
                    .L4:


                    ;  14:addbetr.c     ****     }
                    ;  15:addbetr.c     **** }
                    .L2:
 0020 89EC                  movl %ebp,%esp
 0022 5D                    popl %ebp
 0023 C3                    ret
 0024 8DB60000              .align 16
      00008DBF 
      00000000 


                    ;  16:addbetr.c     **** 
                    ;  17:addbetr.c     **** int addierebetraege( int summand1, int summand2 )
                    ;  18:addbetr.c     **** {
                    .globl addierebetraege
                            .type    addierebetraege,@function
                    addierebetraege:
 0030 55                    pushl %ebp
 0031 89E5                  movl %esp,%ebp
 0033 83EC14                subl $20,%esp
 0036 53                    pushl %ebx


                    ;  19:addbetr.c     ****   int summe;
                    ;  20:addbetr.c     **** 
                    ;  21:addbetr.c     ****   summe = betrag( summand1 ) + betrag( summand2 );
 0037 83C4F4                addl $-12,%esp
 003a 8B4508                movl 8(%ebp),%eax
 003d 50                    pushl %eax
 003e E8FCFFFF              call betrag
 0043 83C410                addl $16,%esp
 0046 89C3                  movl %eax,%ebx
 0048 83C4F4                addl $-12,%esp
 004b 8B450C                movl 12(%ebp),%eax
 004e 50                    pushl %eax
 004f E8FCFFFF              call betrag
      FF
 0054 83C410                addl $16,%esp
 0057 89C0                  movl %eax,%eax
 0059 8D1418                leal (%eax,%ebx),%edx
 005c 8955FC                movl %edx,-4(%ebp)


                    ;  22:addbetr.c     **** 
                    ;  23:addbetr.c     ****   return summe;
 005f 8B55FC                movl -4(%ebp),%edx
 0062 89D0                  movl %edx,%eax
 0064 EB00                  jmp .L5


                    ;  24:addbetr.c     **** }
                    .L5:
 0066 8B5DE8                movl -24(%ebp),%ebx
 0069 89EC                  movl %ebp,%esp
 006b 5D                    popl %ebp
 006c C3                    ret
 006d 8D7600                .align 16


                    ;  25:addbetr.c     **** 
                    ;  26:addbetr.c     **** int main( int nargs, char **args )
                    ;  27:addbetr.c     **** {
                    .globl main
                            .type    main,@function
                    main:
 0070 55                    pushl %ebp
 0071 89E5                  movl %esp,%ebp
 0073 83EC18                subl $24,%esp


                    ;  28:addbetr.c     ****   int i, j, erg;
                    ;  29:addbetr.c     **** 
                    ;  30:addbetr.c     ****   i = 12;
 0076 C745FC0C              movl $12,-4(%ebp)
      000000


                    ;  31:addbetr.c     ****   j = 13;
 007d C745F80D              movl $13,-8(%ebp)
      000000


                    ;  32:addbetr.c     **** 
                    ;  33:addbetr.c     ****   erg = addierebetraege( i, j );
 0084 83C4F8                addl $-8,%esp
 0087 8B45F8                movl -8(%ebp),%eax
 008a 50                    pushl %eax
 008b 8B45FC                movl -4(%ebp),%eax
 008e 50                    pushl %eax
 008f E8FCFFFF              call addierebetraege
      FF
 0094 83C410                addl $16,%esp
 0097 89C0                  movl %eax,%eax
 0099 8945F4                movl %eax,-12(%ebp)


                    ;  34:addbetr.c     **** 
                    ;  35:addbetr.c     ****   return 0;
 009c 31C0                  xorl %eax,%eax
 009e EB00                  jmp .L6


                    ;  36:addbetr.c     **** }
                            .p2align 4,,7
                    .L6:
 00a0 89EC                  movl %ebp,%esp
 00a2 5D                    popl %ebp
 00a3 C3                    ret

Ein Intel-Prozessor führt beim Befehl call folgendes aus:

  1. Der aktuelle Wert des program counters (von Intel EPI genannt) wird auf dem Stack abgelegt. Der abgelegte Wert ist zu diesem Zeitpunkt die Adresse des Befehls nach dem call, also die Adresse zu der nach Ende des Unterprogramms zurückgesprungen werden muß, um die Befehle nach dem call auszuführen.
  2. Es wird zu der Adresse verzweigt, die als Operand angegeben ist. Im Falle des hier verwendeten kurzen Sprungs mit OP-code 0xEP ist dies ein 1 Byte großer Wert, der die Differenz zwischen der anzuspringenden Adresse und dem Wert des program counters angibt. So sind relative Sprünge von -128 bis +127 Byte, bezogen auf den folgenden Befehl (Wert von EPI alias program counter).



AnyWare@Wachtler.de