(root)/
glibc-2.38/
stdlib/
mblen.c
       1  /* Copyright (C) 1991-2023 Free Software Foundation, Inc.
       2     This file is part of the GNU C Library.
       3  
       4     The GNU C Library is free software; you can redistribute it and/or
       5     modify it under the terms of the GNU Lesser General Public
       6     License as published by the Free Software Foundation; either
       7     version 2.1 of the License, or (at your option) any later version.
       8  
       9     The GNU C Library is distributed in the hope that it will be useful,
      10     but WITHOUT ANY WARRANTY; without even the implied warranty of
      11     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      12     Lesser General Public License for more details.
      13  
      14     You should have received a copy of the GNU Lesser General Public
      15     License along with the GNU C Library; if not, see
      16     <https://www.gnu.org/licenses/>.  */
      17  
      18  #include <stdlib.h>
      19  #include <string.h>
      20  #include <wchar.h>
      21  #include <gconv.h>
      22  #include <wcsmbs/wcsmbsload.h>
      23  
      24  
      25  /* Internal state.  */
      26  static mbstate_t state;
      27  
      28  /* Return the length of the multibyte character (if there is one)
      29     at S which is no longer than N characters.
      30     The ISO C standard says that the `mblen' function must not change
      31     the state of the `mbtowc' function.  */
      32  int
      33  mblen (const char *s, size_t n)
      34  {
      35    int result;
      36  
      37    /* If S is NULL the function has to return null or not null
      38       depending on the encoding having a state depending encoding or
      39       not.  */
      40    if (s == NULL)
      41      {
      42        const struct gconv_fcts *fcts;
      43  
      44        /* Get the conversion functions.  */
      45        fcts = get_gconv_fcts (_NL_CURRENT_DATA (LC_CTYPE));
      46  
      47        /* Reset the state.  */
      48        memset (&state, '\0', sizeof state);
      49  
      50        result = fcts->towc->__stateful;
      51      }
      52    else if (*s == '\0')
      53      /* According to the ISO C 89 standard this is the expected behaviour.  */
      54      result = 0;
      55    else
      56      {
      57        memset (&state, '\0', sizeof state);
      58  
      59        result = __mbrtowc (NULL, s, n, &state);
      60  
      61        /* The `mbrtowc' functions tell us more than we need.  Fold the -1
      62  	 and -2 result into -1.  */
      63        if (result < 0)
      64  	result = -1;
      65      }
      66  
      67    return result;
      68  }