[PATCH] fix iconv UCS-2BE/UCS-2LE unaligned access handling

GOTO Masanori gotom@debian.or.jp
Sun Jun 27 23:45:00 GMT 2004


The following __gconv_transform_*_* (UCS-2BE/UCS-2LE) cause unaligned
memory access exception when unaligned memory address is passed to
iconv(inbuf, outbuf) on _STRING_ARCH_unaligned=1 architectures:

	* __gconv_transform_internal_ucs2
	* __gconv_transform_internal_ucs2reverse
	* __gconv_transform_ucs2_internal
	* __gconv_transform_ucs2reverse_internal

The problem is the user given buffer in iconv(inbuf, outbuf) may be
unaligned, FROM_LOOP_unaligned (ex: internal_ucs2_loop_unaligned) is
called, but that routine does not handle such buffers as unaligned.

The attached patch fixes this problem.  This patch is intended to
change minimally for iconv source to be affected.  Please consider to
look at it.

Regards,
-- gotom


2004-06-28  GOTO Masanori  <gotom@debian.or.jp>

	* iconv/gconv_simple.c: Use get16/put16 for user given buffer
	in ucs2/ucs2reverse when unaligned memory access is attempted.


Index: iconv/gconv_simple.c
===================================================================
RCS file: /cvs/glibc/libc/iconv/gconv_simple.c,v
retrieving revision 1.64
diff -u -r1.64 gconv_simple.c
--- iconv/gconv_simple.c	15 Mar 2004 22:37:31 -0000	1.64
+++ iconv/gconv_simple.c	27 Jun 2004 15:34:05 -0000
@@ -1158,7 +1158,7 @@
 #define LOOPFCT			FROM_LOOP
 #define BODY \
   {									      \
-    uint16_t u1 = *((const uint16_t *) inptr);				      \
+    uint16_t u1 = get16 (inptr);					      \
 									      \
     if (__builtin_expect (u1 >= 0xd800 && u1 < 0xe000, 0))		      \
       {									      \
@@ -1216,7 +1216,7 @@
       }									      \
     else								      \
       {									      \
-	*((uint16_t *) outptr) = val;					      \
+	put16 (outptr, val);						      \
         outptr += sizeof (uint16_t);					      \
 	inptr += 4;							      \
       }									      \
@@ -1242,7 +1242,7 @@
 #define LOOPFCT			FROM_LOOP
 #define BODY \
   {									      \
-    uint16_t u1 = bswap_16 (*((const uint16_t *) inptr));		      \
+    uint16_t u1 = bswap_16 (get16 (inptr));				      \
 									      \
     if (__builtin_expect (u1 >= 0xd800 && u1 < 0xe000, 0))		      \
       {									      \
@@ -1308,7 +1308,7 @@
       }									      \
     else								      \
       {									      \
-	*((uint16_t *) outptr) = bswap_16 (val);			      \
+	put16 (outptr, bswap_16 (val));					      \
 	outptr += sizeof (uint16_t);					      \
 	inptr += 4;							      \
       }									      \



More information about the Libc-alpha mailing list