[Patch, libfortran] Improve performance of byte swapped IO
Janne Blomqvist
blomqvist.janne@gmail.com
Sat Jan 5 21:13:00 GMT 2013
On Sat, Jan 5, 2013 at 5:35 PM, Richard Biener
<richard.guenther@gmail.com> wrote:
> On Fri, Jan 4, 2013 at 11:35 PM, Andreas Schwab <schwab@linux-m68k.org> wrote:
>> Janne Blomqvist <blomqvist.janne@gmail.com> writes:
>>
>>> diff --git a/libgfortran/io/file_pos.c b/libgfortran/io/file_pos.c
>>> index c8ecc3a..bf2250a 100644
>>> --- a/libgfortran/io/file_pos.c
>>> +++ b/libgfortran/io/file_pos.c
>>> @@ -140,15 +140,21 @@ unformatted_backspace (st_parameter_filepos *fpp, gfc_unit *u)
>>> }
>>> else
>>> {
>>> + uint32_t u32;
>>> + uint64_t u64;
>>> switch (length)
>>> {
>>> case sizeof(GFC_INTEGER_4):
>>> - reverse_memcpy (&m4, p, sizeof (m4));
>>> + memcpy (&u32, p, sizeof (u32));
>>> + u32 = __builtin_bswap32 (u32);
>>> + m4 = *(GFC_INTEGER_4*)&u32;
>>
>> Isn't that an aliasing violation?
>
> It looks like one. Why not simply do
>
> m4 = (GFC_INTEGER_4) u32;
>
> ? I suppose GFC_INTEGER_4 is always the same size as uint32_t but signed?
Yes, GFC_INTEGER_4 is a typedef for int32_t. As for why I didn't do
the above, C99 6.3.1.3(3) says that if the unsigned value is outside
the range of the signed variable, the result is
implementation-defined. Though I suppose the sensible
"implementation-defined behavior" in this case on a two's complement
target is to just do a bitwise copy.
Anyway, to be really safe one could use memcpy instead; the compiler
optimizes small fixed size memcpy's just fine. Updated patch attached.
--
Janne Blomqvist
-------------- next part --------------
A non-text attachment was scrubbed...
Name: bswap2.diff
Type: application/octet-stream
Size: 7690 bytes
Desc: not available
URL: <http://gcc.gnu.org/pipermail/fortran/attachments/20130105/baeb2ade/attachment.obj>
More information about the Fortran
mailing list