[Search for users] [Overall Top Noters] [List of all Conferences] [Download this site]

Conference turris::decc

Title:DECC
Notice:General DEC C discussions
Moderator:TLE::D_SMITHNTE
Created:Fri Nov 13 1992
Last Modified:Fri Jun 06 1997
Last Successful Update:Fri Jun 06 1997
Number of topics:2212
Total number of notes:11045

2106.0. "will -assume noaligned_objects fix run-time Unaligned access msgs?" by CAM::JOHNSON (imagine... sharing all the world) Tue Feb 25 1997 14:16

Hi,

Can anyone take a moment to explain any dangers with using 
	-assume noaligned_objects

outside of perhaps slower code...

we just moved from the default compiler to using -migrate, and are now
getting unaligned access messages at run-time:

Unaligned access pid=7773 <bcf_main> va=6cf74 pc=12007dd14 ra=12007d594 type=ldq

this code was originally written under vaxc, and does pointer casting, which
i'm sure is part of the cause of the above messages...

unfortunately, there is no time to try and track these all down for this 
release,and i don't think i'll get agreement on not using -migrate
(which i do believe is the way to go)... i just wanted to check on
people's thoughts of the -assume noaligned_objects switch, verify
that this will solve the problem, and see if there were any other thoughts...

thankx,
sarah
T.RTitleUserPersonal
Name
DateLines
2106.1DECCXL::MARIOTue Feb 25 1997 16:3623
Is this really what you want?  I assume you are on a UNIX release prior
to V4.0 and you want to use -migrate (DECC) because of it's better
performance features over the default cc.  But if you have to slow the
code down by specifying "-assume noaligned_objects", will you be left 
with the performance gain you were looking for?

There are two general cases where the -migrate compiler will expose
unaligned code that the default ACC compiler does not.

One is for unaligned structures.  DECC performs optimizations taking
advantage of the natural alignment of structures guaranteed by the
C language.  The ACC compiler did not do this.

The other is when you are accessing unaligned shorts through short
pointers.  The code from -migrate will cause unaligned faults while
the code from ACC will not.  The ACC code will also quietly give you
the wrong answer if the short spans a quadword boundary.

The -assume noaligned_objects will eliminate the unaligned access
faults but the resulting performance may be worse than what you had
with the default ACC compiler.

Joe
2106.2Fix the source codeCXXC::REPETERich Peterson 381-1802 ZKO2-3/N30Wed Feb 26 1997 13:4254
Since the fault shown in .0 is on an ldq at a 4-byte-aligned address,
most likely this is a struct-pointer dereference, the first of the
differences noted by Joe in .1.

Since you say that this code was originally written under VAX C (where
alignment was not really an issue), and does lots of pointer casting,
it's reasonably likely that you'd get a number of alignments faults.
You may also be getting the same faults on OpenVMS Alpha and just not
noticing because by default they get fixed up silently on that platform.

Instead of using -assume noaligned_objects, which is a huge hammer that
will produce awful generated code to avoid any alignment faults, you
should consider fixing the source code.  The alignment fault locations
identify the faulting instructions, from which you can determine the
source code.  With luck, there may be only a handful of distinct struct
types involved in pointer casts in the faulting locations, and by
analyzing those types you'll be able to do one or more of the following:

   1. Change the larger-aligned type to be smaller-aligned.  
      This can be done with #pragma pack.

   2. Change the smaller-aligned type to be larger-aligned.  This
      can be done by making the interior of the smaller-alligned struct
      a union against a double or a long (__int64 on VMS).  Depending on
      how this is done, you may have to change some or all expressions that
      refer to members of the original struct.  The variant_struct feature
      of -vaxc mode, the unnamed member feature of -ms mode, or a set of
      macro definitions (if the member names are globally unique) can
      be used to avoid changing each referencing expression.

   3. If there are only a handful of specific references that are a problem,
      the problem dereferences can be changed to cast to a pointer to
      an __unaligned struct.  E.g.  if "((struct foo *)ptr)->member" is
      getting an alignment fault, change it to
      "((__unaligned struct foo *)ptr)->member)".  Note the placement of
      __unaligned.  Similar-looking things that will *not* work are:

         ((struct foo * __unaligned)ptr)->member;

         typedef struct foo * fooptr;
         ((__unaligned fooptr)ptr)->member;

      If the pointer type is within a typedef, you cannot use __unaligned
      effectively in a cast using that typedef name.  You either need to
      make a new typedef, or change the cast to use the type underlying
      the original typedef, e.g.:

         typedef __unaligned struct foo * ufooptr;
         ((ufooptr)ptr)->member;
      
      Correct use of __unaligned will produce the same code as -assume
      noaligned_objects, but only on those accesses that are actually
      marked instead of forcing all pointer accesses throughout the code
      to be made that way.