(root)/
glibc-2.38/
assert/
assert.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 <assert.h>
      19  #include <atomic.h>
      20  #include <ldsodefs.h>
      21  #include <libintl.h>
      22  #include <stdio.h>
      23  #include <stdlib.h>
      24  #include <sysdep.h>
      25  #include <unistd.h>
      26  #include <sys/mman.h>
      27  
      28  
      29  extern const char *__progname;
      30  
      31  #include <wchar.h>
      32  #include <libio/iolibio.h>
      33  #define fflush(s) _IO_fflush (s)
      34  
      35  /* This function, when passed a string containing an asserted
      36     expression, a filename, and a line number, prints a message
      37     on the standard error stream of the form:
      38  	a.c:10: foobar: Assertion `a == b' failed.
      39     It then aborts program execution via a call to `abort'.  */
      40  
      41  #ifdef FATAL_PREPARE_INCLUDE
      42  # include FATAL_PREPARE_INCLUDE
      43  #endif
      44  
      45  
      46  void
      47  __assert_fail_base (const char *fmt, const char *assertion, const char *file,
      48  		    unsigned int line, const char *function)
      49  {
      50    char *str;
      51  
      52  #ifdef FATAL_PREPARE
      53    FATAL_PREPARE;
      54  #endif
      55  
      56    int total;
      57    if (__asprintf (&str, fmt,
      58  		  __progname, __progname[0] ? ": " : "",
      59  		  file, line,
      60  		  function ? function : "", function ? ": " : "",
      61  		  assertion, &total) >= 0)
      62      {
      63        /* Print the message.  */
      64        (void) __fxprintf (NULL, "%s", str);
      65        (void) fflush (stderr);
      66  
      67        total = (total + 1 + GLRO(dl_pagesize) - 1) & ~(GLRO(dl_pagesize) - 1);
      68        struct abort_msg_s *buf = __mmap (NULL, total, PROT_READ | PROT_WRITE,
      69  					MAP_ANON | MAP_PRIVATE, -1, 0);
      70        if (__glibc_likely (buf != MAP_FAILED))
      71  	{
      72  	  buf->size = total;
      73  	  strcpy (buf->msg, str);
      74  
      75  	  /* We have to free the old buffer since the application might
      76  	     catch the SIGABRT signal.  */
      77  	  struct abort_msg_s *old = atomic_exchange_acquire (&__abort_msg, buf);
      78  
      79  	  if (old != NULL)
      80  	    __munmap (old, old->size);
      81  	}
      82  
      83        free (str);
      84      }
      85    else
      86      {
      87        /* At least print a minimal message.  */
      88        static const char errstr[] = "Unexpected error.\n";
      89        __libc_write (STDERR_FILENO, errstr, sizeof (errstr) - 1);
      90      }
      91  
      92    abort ();
      93  }
      94  
      95  
      96  #undef __assert_fail
      97  void
      98  __assert_fail (const char *assertion, const char *file, unsigned int line,
      99  	       const char *function)
     100  {
     101    __assert_fail_base (_("%s%s%s:%u: %s%sAssertion `%s' failed.\n%n"),
     102  		      assertion, file, line, function);
     103  }