[stream] Fix reading s32 when long is s64
FT_READ_LONG
, FT_GET_LONG
, and related macros did not return
negative values when long
is more than 32 bits. FT_Stream_ReadULong
would read four bytes into the LSB of an FT_ULong
and return that.
Since this can never set the MSb of the FT_ULong
when FT_ULong
is
more than 32 bits the cast to FT_Long
never resulted in a negative
value.
Fix this by modifying FT_Stream_Read*
to return a type of the same
size as the bytes it is reading and changing the FT_READ_*
and
FT_GET_*
macros to cast to the same type returned by FT_Stream_Read*
but with the correctly signed type (instead of casting to what is
assumed to be the type of var
which will happen automatically anyway).
There exist a few cases like with the OFF3
variants where there isn't
generally a type with the correct size. FT_PEEK_OFF3
works around this
loading the bytes into the three most significant bits and then doing a
signed shift down. FT_NEXT_OFF3
also already worked correctly by
casting this signed value to another signed type. FT_Stream_GetUOffset
works correctly but one must be careful not to attempt to cast the
returned value to a signed type. Fortunately there is only
FT_GET_UOFF3
and no FT_GET_OFF3
.
All of these cases are handled correctly when reading values through
FT_Stream_ReadFields
since it generically computes the signed value
through an FT_Int32
. This change is essentially doing the same for
these macros.
-
include/freetype/internal/ftstream.h (FT_NEXT_, FT_GET_, FT_READ*): Update macros and return types to use fixed size types for fixed size values.
-
src/base/ftstream.c (FT_StreamGet*, FT_StreamRead*): Dito.
Issue: #1161 (closed)