Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 24 Nov 1998 11:39:17 -0500 (EST)
From:      Simon Shapiro <shimon@simon-shapiro.org>
To:        Doug Rabson <dfr@nlsystems.com>
Cc:        freebsd-alpha@FreeBSD.ORG, Mike Smith <mike@smith.net.au>
Subject:   Re: UnAligned Access, but why?
Message-ID:  <XFMail.981124113917.shimon@simon-shapiro.org>
In-Reply-To: <Pine.BSF.4.01.9811241131400.21711-100000@herring.nlsystems.com>

next in thread | previous in thread | raw e-mail | index | archive | help

Doug Rabson, On 24-Nov-98 you wrote:
>  On Mon, 23 Nov 1998, Mike Smith wrote:
>  
> > > > > 
> > > > > The bus_space_read_[14] are causing unaligned access panics. 
> > > > > These
> > > > > panics
> > > > > can be eliminated by casting explicitly:
> > > >  
> > > >  Don't do this.  Align the objects you're trying to transfer
> > > >  instead.
> > > 
> > > Thanx, but how?  I took the CAM driver as is and just triesd to
> > > actually
> > > align the data.  It makes no difference at all.  I am still getting
> > > the
> > > panics.  If you look again at my example (the one following the
> > > casts), you
> > > will see that it does not help.
> > 
> > I saw no evidence that you were performing aligned transfers; your
> > example was, if I remember correctly, casting some arbitrary pointer to
> > a pointer to a 32-bit object.  This will fail if the arbitrary 
> > pointer's value is not 32-bit aligned.
> > 
> > > Also (forgive my ignorance here), different PCI busss appear to have
> > > different sizes for the same thing.  Or, at least this is how all
> > > this
> > > bus_rea/write stuff tries to imply.
> > 
> > No.  Different PCI bus implementations used different host methods to
> > achieve identical PCI bus transactions.
> > 
> > > The end result is a mass confusion on my part.  i am trying to fit
> > > the
> > > driver into the existing framework, not change the framework (unless
> > > obviously broken).  I do not have enough information to suggest
> > > anything is
> > > broken, except the panics.
> > 
> > The problem is most likely that you are attempting to access a local 
> > memory data structure member of a given size that is not aligned to 
> > that size, or you are attempting to access a data structure inside a 
> > PCI device where the region in question is memory-mapped and the data 
> > structure is not aligned in the mapping according to its size.
> > 
> > > I may need some detailed help here....
> > 
> > You may need to provide a more detailed example.  To begin with, it'd
> > help if you can clarify whether you're sure you understand what
> > constitutes an "unaligned access", as that's pretty key to working out 
> > where you're falling over here.
>  
>  You must not pass unaligned offsets to in[wl], out[wl], read[wl] and
>  write[wl].  For 'w' sized accesses, the offset must be even aligned, for
>  'l' sized accesses, the offset must be a multiple of 4.  I think NetBSD
>  has code to panic if an illegal offset is used to access device memory. 
>  I
>  may do the same (probably for kernels compiled with DIAGNOSTIC defined).

OK.  This all makes lots of sense, but look at the example I provided in
the original post.  It is a modification of code I did not write, but some
of you may have:

/* static __inline void */
void
bus_space_write_4(bus_space_tag_t tag, bus_space_handle_t bsh,
                       bus_size_t offset, u_int32_t value)
{
#if defined(_ALPHA_BUS_PIO_H_)
#if defined(_ALPHA_BUS_MEMIO_H_)
        if (tag == ALPHA_BUS_SPACE_IO)
#endif
        {
                u_int32_t port, data;

                port = (u_int32_t)bsh + (u_int32_t)offset;
                data = (u_int32_t)value;

printf("%s.%d I/O handle = %x, offset = %x, value = %x\n", __FILE__,
__LINE__, b
sh, offset, value);
printf("%s.%d I/O port = %x, data = %x\n", __FILE__, __LINE__, port, data);

>>>>-------->>>> Everything is honky-dory until this point <<<<--------<<<<
                outl(port, data);
>>>>-------->>>>  This printf never happens.  We panic before it happens 

printf("%s.%d I/O DONE = %x, data = %x\n", __FILE__, __LINE__, port, data);
        }
#endif
#if defined(_ALPHA_BUS_MEMIO_H_)
#if defined(_ALPHA_BUS_PIO_H_)
        else
#endif
                writel(bsh + offset, value);
#endif
}

You can trace back this call to the sys/dev/dpt/dpt_scsi.c file the
dpt_send_eata_command function, line 1088, where the line:

        dpt_outl(dpt, HA_WDMAADDR, cmd_busaddr);

can be traced back to bus_space_write_4 above.  Please trust me in saying
that I tried everything you suggest before posting my mssage.  The casts at
the top of my example were necessary to avoid a similar panic.  All  the
data types involoved are taken from the CAM code and are either pointers or
64bit integers.

Simon




To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-alpha" in the body of the message



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?XFMail.981124113917.shimon>