From: jbn@lulea.trab.se (Johan Bengtsson)
Newsgroups: comp.std.c++
Subject: Re: Zero-length structures and pointer comparisons
Date: 12 Dec 92 18:10:40 GMT
Organization: Telia Research AB, Aurorum 6, 951 75 Lulea, Sweden
X-Newsreader: TIN [version 1.1 + PL8]

Jim Adcock (jimad@microsoft.com) wrote:
: dag@control.lth.se (Dag Bruck) writes:
: |In <comp.std.c++> ralpht@meaddata.com (Ralph W. Trickey) writes:
: |>|> >
: |>|> >  I don't think that requiring total ordering would break any existing
: |>|> >program, but it would break quite a few existing compilers.
: |>
: |>This language change that would slow down existing programs. Possibly
: |>to the point where they no longer meet specifications. I consider this
: |>breaking programs.
: |
: |Could someone do the net a great favour and check it?  There's a lot
: |of speculation but nobody has measured how severe the slow-down would be.

: People who are experienced with PCs don't have to measure this problem
: because they are well aware of the issues and the code sizes involved.
: What you ask for is essentially the same thing as "Huge" model which
: PC compilers support but *which PC programmers don't use* -- because its too
: expensive.

: But, since *you* request the numbers, here's a simple example:

: Compaq Deskpro 386/20
: C7 compiler all optimizations.

: Comparing an pointer inner loop, incrementing one pointer and comparing
: with another pointer within a loop.

: The "total ordering" approach loop executes approx 3X slower than
: the typical PC segment:offset approach.

Jim, I think your result is slightly misleading, since the "huge"
model involves other overhead than pointer comparison (as someone
already pointed out).  Here are more accurate measures:

Dell 486/33
MSC 6.00A compiler all optimizations (/Ozax).

Same test as Jim, test program at end.

The first two numbers are for the normal "large" memory model.
The last two numbers are for the "huge" model.
/AL:	p1 < p2			28 sec.
/AL:	(long)p1 < (long)p2	55 sec.
/AH:	p1 < p2			96 sec.
/AH:	(long)p1 < (long)p2	87 sec.

So, like Jim, I find a more than 3x worst-case speed reduction
when switching from "large" to "huge".

However, the real slowdown is just 2x (55/28).  Note that the figure
I gave in an earlier posting (33 %) was for unoptimized code.

Side note: It seems to pay off to cast to long in the "huge"
model.  In this case the programmers knows more than the compiler
is allowed to (that the pointer won't travel over more than 64 K).

I would think the size overhead Jim mentioned (28 bytes) is excessive too.

Other than the measurements, I agree with Jim.  The total
ordering penalty should only be payed when used.  The ptrcmp()
function proposed in another posting achieves just that.

Test program follows (press 'n' to skip).

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

#define LOOPS 100L * 1000L

int main(void)
{
   char* ap = (char*) malloc(65000U);
   char* bp = (char*) malloc(65000U);
   char* aend = ap + 1000;
   long i;

   if ( ap < bp || bp < ap ) {
      printf( "p1<p2 is probably totally ordered.\n" );
   } else {
      printf( "p1<p2 is not totally ordered.\n" );
      if ( (long)(ap) < (long)(bp) || (long)(bp) < (long)(ap) ) {
         printf( "\tbut (long)p1<(long)p2 is probably totally ordered.\n" );
      }
   }

   system( "echo. | time" );
   for ( i = 0; i < LOOPS; ++i ) {
      char* p = ap;
      while ( p++ < aend )
         { }
   }
   system( "echo. | time" );
   for ( i = 0; i < LOOPS; ++i ) {
      char* p = ap;
      while ( (long)(p++) < (long)(aend) )
         { }
   }
   system( "echo. | time" );

   return 0;
}

-- 
--------------------------------------------------------------------------
| Johan Bengtsson, Telia Research AB, Aurorum 6, S-951 75 Lulea, Sweden  |
| Johan.Bengtsson@lulea.trab.se; Voice:(+46)92075471; Fax:(+46)92075490  |
--------------------------------------------------------------------------
Newsgroups: comp.std.c++