Code optimization <LEA Instruction>

From: Richard B. Johnson (root@chaos.analogic.com)
Date: Thu Jan 27 2000 - 17:01:48 EST


The Intel reference manual tells about optimizing code.
One of the things it states is that the LEA instruction can
be used to change the value of an index register faster than
using the ADD instruction (Page G-10, Intel '486 Rag).

I note that recent 'C' compilers do this. There are a lot of
LEA instructions that have replaced simple adds for adding
a constant displacement to an index register.

As usual, the Intel reference manual is wrong for all types
of CPUs that I have tested (486-686).

I wish somebody would have tested this information before wrong
information went into the code-generation of the 'C' compilers.

The following program clearly shows that many more 'addl' instructions
may be executed than 'leal' instructions within a given time.

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <signal.h>

int main(void);
void dummy(int unused);

volatile int true;

void dummy(int unused)
{
  true = 0;
}

int main()
{
    long leal = 0;
    long addl = 0;
        printf("Testing...");
        fflush(stdout);
        (void)signal(SIGALRM, dummy);
        (void)alarm(1);
        true++;
        while(true)
        {
            __asm__ __volatile__(
            ".align 8\n"
            "\tleal 2(%eax), %eax\n" /* 10 leals */
            "\tleal 2(%eax), %eax\n"
            "\tleal 2(%eax), %eax\n"
            "\tleal 2(%eax), %eax\n"
            "\tleal 2(%eax), %eax\n"
            "\tleal 2(%eax), %eax\n"
            "\tleal 2(%eax), %eax\n"
            "\tleal 2(%eax), %eax\n"
            "\tleal 2(%eax), %eax\n"
            "\tleal 2(%eax), %eax\n"
                       );
            leal++;
        }
        (void)signal(SIGALRM, dummy);
        (void)alarm(1);
        true++;
        while(true)
        {
            __asm__ __volatile__(
            ".align 8\n"
            "\taddl $2, %eax\n" /* 10 adds */
            "\taddl $2, %eax\n"
            "\taddl $2, %eax\n"
            "\taddl $2, %eax\n"
            "\taddl $2, %eax\n"
            "\taddl $2, %eax\n"
            "\taddl $2, %eax\n"
            "\taddl $2, %eax\n"
            "\taddl $2, %eax\n"
            "\taddl $2, %eax\n"
                    );
            addl++;
        }
        printf("\nNr adds = %ld Nr leals = %ld\n", addl, leal);
        return 0;
}

Testing...
Nr adds = 54644887 Nr leals = 39623932

The main point is, when attempting to optimize code, it would be
a good idea to test the many possible instruction-sequences before
you commit yourself, especially when providing inline 'asm' or
generating compiler output.

Cheers,
Dick Johnson

Penguin : Linux version 2.3.39 on an i686 machine (800.63 BogoMips).

-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.rutgers.edu
Please read the FAQ at http://www.tux.org/lkml/



This archive was generated by hypermail 2b29 : Mon Jan 31 2000 - 21:00:19 EST