aboutsummaryrefslogtreecommitdiff
path: root/iconv/loop.c
diff options
context:
space:
mode:
authorUlrich Drepper <drepper@redhat.com>2000-04-27 05:42:19 +0000
committerUlrich Drepper <drepper@redhat.com>2000-04-27 05:42:19 +0000
commit316518d610789256841f929e3c5757d1e385fcd5 (patch)
treecf53931201515683b375870c359e5ec81ffe6088 /iconv/loop.c
parentcd201e387c261f9684a76a51e63f194bf49faa3f (diff)
downloadglibc-316518d610789256841f929e3c5757d1e385fcd5.tar
glibc-316518d610789256841f929e3c5757d1e385fcd5.tar.gz
glibc-316518d610789256841f929e3c5757d1e385fcd5.tar.bz2
glibc-316518d610789256841f929e3c5757d1e385fcd5.zip
Update.
2000-04-26 Ulrich Drepper <drepper@redhat.com> * iconv/gconv_simple.c (utf8_internal_loop): Correctly reconstruct stored character in state in UNPACK_BYTES macro. * iconv/loop.c (SINGLE(LOOPFCT)): Make it actually work. Correct test for available characters, handle result of BODY code correctly. * localedata/Makefile (test-srcs): Add tst-mbswcs1. (distribute): Add tst-mbswcs.sh. Add rule to run tst-mbswcs.sh. * localedata/tst-mbswcs.sh: New file. * localedata/tst-mbswcs1.c: New file. 2000-04-26 Jakub Jelinek <jakub@redhat.com> * nis/nis_callback.c (__nis_create_callback): Do failed memory allocation fixups centrally, fix __builtin_expect call, return NULL on failure, not NIS_NOMEMORY. 2000-04-27 Bruno Haible <haible@clisp.cons.org>
Diffstat (limited to 'iconv/loop.c')
-rw-r--r--iconv/loop.c39
1 files changed, 32 insertions, 7 deletions
diff --git a/iconv/loop.c b/iconv/loop.c
index c8f893406a..9c5dbfca77 100644
--- a/iconv/loop.c
+++ b/iconv/loop.c
@@ -307,10 +307,10 @@ SINGLE(LOOPFCT) (const unsigned char **inptrp, const unsigned char *inend,
#endif
/* Are there enough bytes in the input buffer? */
- if (__builtin_expect (inptr + (MAX_NEEDED_INPUT - inlen) > inend, 0))
+ if (__builtin_expect (inptr + (MIN_NEEDED_INPUT - inlen) > inend, 0))
{
-#ifdef STORE_REST
*inptrp = inend;
+#ifdef STORE_REST
inptr = bytebuf;
inptrp = &inptr;
inend = &bytebuf[inlen];
@@ -335,28 +335,53 @@ SINGLE(LOOPFCT) (const unsigned char **inptrp, const unsigned char *inend,
/* Now add characters from the normal input buffer. */
do
bytebuf[inlen++] = *inptr++;
- while (inlen < MAX_NEEDED_INPUT);
+ while (inlen < MAX_NEEDED_INPUT && inptr < inend);
inptr = bytebuf;
- inend = &inptr[MAX_NEEDED_INPUT];
+ inend = &bytebuf[inlen];
+#undef NEED_LENGTH_TEST
+#define NEED_LENGTH_TEST 1
do
{
BODY
}
while (0);
- if (result == __GCONV_OK)
+ /* Now we either have produced an output character and consumed all the
+ bytes from the state and at least one more, or the character is still
+ incomplete, or we have some other error (like illegal input character,
+ no space in output buffer). */
+ if (inptr != bytebuf)
{
- /* We successfully converted the character (maybe even more).
- Update the pointers passed in. */
+ /* We found a new character. */
assert (inptr - bytebuf > (state->__count & 7));
*inptrp += inptr - bytebuf - (state->__count & 7);
*outptrp = outptr;
+ result = __GCONV_OK;
+
/* Clear the state buffer. */
state->__count &= ~7;
}
+ else if (result == __GCONV_INCOMPLETE_INPUT)
+ {
+ /* This can only happen if we have less than MAX_NEEDED_INPUT bytes
+ available. */
+ assert (inend != &bytebuf[MAX_NEEDED_INPUT]);
+
+ *inptrp += inend - bytebuf - (state->__count & 7);
+#ifdef STORE_REST
+ inptrp = &inptr;
+
+ STORE_REST
+#else
+ /* We don't have enough input for another complete input
+ character. */
+ while (inptr < inend)
+ state->__value.__wchb[inlen++] = *inptr++;
+#endif
+ }
return result;
}