From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 48) id 011B4385DDD8; Tue, 11 Jun 2024 15:22:50 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org 011B4385DDD8 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gcc.gnu.org; s=default; t=1718119371; bh=XypLzLxgdChmTeil3EdG3d1yRsN2VnEao5JpOtU2L9s=; h=From:To:Subject:Date:In-Reply-To:References:From; b=nvh3uedjfaNQRruifCI5UPrM0xbr0S3JJ4ELD0QGzI1wQ8mn6izk1PoG9QpaMG/yy xaTbDoeYRXwkxz5bayj/WZw2rC4bLI3U1rOCs7eZEqeqDozBgxQj5Nia8uEX41f6wV hhAAeJ1U2BUrAt58K+LswwzGYHqMtIbKrPnpqb24= From: "redi at gcc dot gnu.org" To: gcc-bugs@gcc.gnu.org Subject: [Bug libstdc++/37475] codecvt::do_in/do_out functions return "ok" when the output sequence has zero length Date: Tue, 11 Jun 2024 15:22:50 +0000 X-Bugzilla-Reason: CC X-Bugzilla-Type: changed X-Bugzilla-Watch-Reason: None X-Bugzilla-Product: gcc X-Bugzilla-Component: libstdc++ X-Bugzilla-Version: unknown X-Bugzilla-Keywords: X-Bugzilla-Severity: normal X-Bugzilla-Who: redi at gcc dot gnu.org X-Bugzilla-Status: NEW X-Bugzilla-Resolution: X-Bugzilla-Priority: P3 X-Bugzilla-Assigned-To: unassigned at gcc dot gnu.org X-Bugzilla-Target-Milestone: --- X-Bugzilla-Flags: X-Bugzilla-Changed-Fields: Message-ID: In-Reply-To: References: Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable X-Bugzilla-URL: http://gcc.gnu.org/bugzilla/ Auto-Submitted: auto-generated MIME-Version: 1.0 List-Id: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=3D37475 --- Comment #11 from Jonathan Wakely --- This changes the loop to always run if the input is non-empty, and so return partial if the destination is empty. --- a/libstdc++-v3/config/locale/gnu/codecvt_members.cc +++ b/libstdc++-v3/config/locale/gnu/codecvt_members.cc @@ -131,10 +131,16 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION // mbsnrtowcs is *very* fast but stops if encounters NUL characters: // in case we store a L'\0' and then continue, in a loop. // NB: mbsnrtowcs is a GNU extension - for (__from_next =3D __from, __to_next =3D __to; - __from_next < __from_end && __to_next < __to_end - && __ret =3D=3D ok;) + __from_next =3D __from; + __to_next =3D __to; + while (__from_next < __from_end) { + if (__to_next >=3D __to_end) + { + __ret =3D partial; + break; + } + const extern_type* __from_chunk_end; __from_chunk_end =3D static_cast(memchr(__from_= next, '\0', __from_end @@ -162,12 +168,14 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION __from_next =3D __from; __state =3D __tmp_state; __ret =3D error; + break; } else if (__from_next && __from_next < __from_chunk_end) { // It is unclear what to return in this case (see DR 382). __to_next +=3D __conv; __ret =3D partial; + break; } else { @@ -175,7 +183,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION __to_next +=3D __conv; } - if (__from_next < __from_end && __ret =3D=3D ok) + if (__from_next < __from_end) { if (__to_next < __to_end) { @@ -185,7 +193,10 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION *__to_next++ =3D L'\0'; } else - __ret =3D partial; + { + __ret =3D partial; + break; + } } }=