Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
locale.c: Add check that strxfrm didn't fail
The code failed to take into account that strxfrm() can fail for reasons
besides buffer length.  It does not return errors, and the only way to
check is to set errno to 0 beforehand, and check that it is still 0
afterwards.
  • Loading branch information
khwilliamson committed Apr 30, 2021
1 parent 020fff6 commit e2f4172
Showing 1 changed file with 14 additions and 5 deletions.
19 changes: 14 additions & 5 deletions locale.c
Expand Up @@ -5439,16 +5439,25 @@ Perl__mem_collxfrm(pTHX_ const char *input_string,
* give up */
for (;;) {

errno = 0;
*xlen = strxfrm(xbuf + COLLXFRM_HDR_LEN, s, xAlloc - COLLXFRM_HDR_LEN);

/* If the transformed string occupies less space than we told strxfrm()
* was available, it means it successfully transformed the whole
* string. */
* was available, it means it transformed the whole string. */
if (*xlen < xAlloc - COLLXFRM_HDR_LEN) {

/* Some systems include a trailing NUL in the returned length.
* Ignore it, using a loop in case multiple trailing NULs are
* returned. */
/* But there still could have been a problem */
if (errno != 0) {
DEBUG_L(PerlIO_printf(Perl_debug_log,
"strxfrm failed for LC_COLLATE=%s; errno=%d, input=%s\n",
PL_collation_name, errno,
_byte_dump_string((U8 *) s, len, 1)));
goto bad;
}

/* Here, the transformation was successful. Some systems include a
* trailing NUL in the returned length. Ignore it, using a loop in
* case multiple trailing NULs are returned. */
while ( (*xlen) > 0
&& *(xbuf + COLLXFRM_HDR_LEN + (*xlen) - 1) == '\0')
{
Expand Down

0 comments on commit e2f4172

Please sign in to comment.