Re: Testing on NULL an unitialized values

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Zitat von "Tor Lillqvist" <tml@xxxxxx>:

You are right, that in some seldom situations it might make sense
to initialize values to other start values. But they should always be
predictable.

You didn't get the reasoning about letting the compiler, or valgrind,
catch use of uninitialized variables, did you?
[...]


Let's just take an example that makes it more clear.


See attachement ( I hope the list allows attachements ).


I get two results: with
      char* mytext = NULL;

=========================
oliver@siouxsie:~$ a.out
 selected number: 0
Text: ATTENTION! No text selected. Fix Bug, please!
 selected number: 1
Text: two
 selected number: 2
Aborted
oliver@siouxsie:~$
=========================

Instead ov abort() I could select whatever I want.
I, as programmer, have control about it.


With
  char* mytext;

I get

=========================
oliver@siouxsie:~$ a.out
 selected number: 0
Text: ATTENTION! No text selected. Fix Bug, please!
 selected number: 1
Text: two
 selected number: 2
Text: two
 selected number: 3
Segmentation fault
oliver@siouxsie:~$
=========================

In this case I have no control.


Compiling with -Wall:
=========================
oliver@siouxsie:~$ vim checks.c
oliver@siouxsie:~$ gcc -g -Wall checks.c
oliver@siouxsie:~$ a.out
(...)
=========================



Using valgrind:
----------------

In case of   char* mytext = NULL;
=========================
oliver@siouxsie:~$ vim checks.c
oliver@siouxsie:~$ gcc -Wall checks.c
oliver@siouxsie:~$ valgrind a.out
==29758== Memcheck, a memory error detector
==29758== Copyright (C) 2002-2009, and GNU GPL'd, by Julian Seward et al.
==29758== Using Valgrind-3.5.0-Debian and LibVEX; rerun with -h for copyright info
==29758== Command: a.out
==29758==
 selected number: 0
Text: ATTENTION! No text selected. Fix Bug, please!
 selected number: 1
Text: two
 selected number: 2
==29758==
==29758== HEAP SUMMARY:
==29758==     in use at exit: 4 bytes in 1 blocks
==29758==   total heap usage: 1 allocs, 0 frees, 4 bytes allocated
==29758==
==29758== LEAK SUMMARY:
==29758==    definitely lost: 4 bytes in 1 blocks
==29758==    indirectly lost: 0 bytes in 0 blocks
==29758==      possibly lost: 0 bytes in 0 blocks
==29758==    still reachable: 0 bytes in 0 blocks
==29758==         suppressed: 0 bytes in 0 blocks
==29758== Rerun with --leak-check=full to see details of leaked memory
==29758==
==29758== For counts of detected and suppressed errors, rerun with: -v
==29758== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 4 from 4)
Aborted
oliver@siouxsie:~$
=========================


In Case of  char* mytext;


=========================
oliver@siouxsie:~$ vim checks.c
oliver@siouxsie:~$ gcc -Wall checks.c
oliver@siouxsie:~$ valgrind a.out
==29795== Memcheck, a memory error detector
==29795== Copyright (C) 2002-2009, and GNU GPL'd, by Julian Seward et al.
==29795== Using Valgrind-3.5.0-Debian and LibVEX; rerun with -h for copyright info
==29795== Command: a.out
==29795==
 selected number: 0
Text: ATTENTION! No text selected. Fix Bug, please!
 selected number: 1
Text: two
 selected number: 2
==29795== Conditional jump or move depends on uninitialised value(s)
==29795==    at 0x4005C5: print_text_checks_null (in /home/oliver/a.out)
==29795==    by 0x400692: print_all_messages (in /home/oliver/a.out)
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
==29795== Conditional jump or move depends on uninitialised value(s)
==29795==    at 0x4E6FA50: vfprintf (vfprintf.c:1601)
==29795==    by 0x4E79BE9: printf (printf.c:35)
==29795==    by 0x4005DF: print_text_checks_null (in /home/oliver/a.out)
==29795==    by 0x400692: print_all_messages (in /home/oliver/a.out)
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
==29795== Use of uninitialised value of size 8
==29795==    at 0x4E72A87: vfprintf (vfprintf.c:1601)
==29795==    by 0x4E79BE9: printf (printf.c:35)
==29795==    by 0x4005DF: print_text_checks_null (in /home/oliver/a.out)
==29795==    by 0x400692: print_all_messages (in /home/oliver/a.out)
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
==29795== Conditional jump or move depends on uninitialised value(s)
==29795==    at 0x4E9B6ED: _IO_file_xsputn@@GLIBC_2.2.5 (fileops.c:1314)
==29795==    by 0x4E72711: vfprintf (vfprintf.c:1601)
==29795==    by 0x4E79BE9: printf (printf.c:35)
==29795==    by 0x4005DF: print_text_checks_null (in /home/oliver/a.out)
==29795==    by 0x400692: print_all_messages (in /home/oliver/a.out)
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
==29795== Use of uninitialised value of size 8
==29795==    at 0x4E9B6F3: _IO_file_xsputn@@GLIBC_2.2.5 (fileops.c:1316)
==29795==    by 0x4E72711: vfprintf (vfprintf.c:1601)
==29795==    by 0x4E79BE9: printf (printf.c:35)
==29795==    by 0x4005DF: print_text_checks_null (in /home/oliver/a.out)
==29795==    by 0x400692: print_all_messages (in /home/oliver/a.out)
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
==29795== Conditional jump or move depends on uninitialised value(s)
==29795==    at 0x4E9B703: _IO_file_xsputn@@GLIBC_2.2.5 (fileops.c:1314)
==29795==    by 0x4E72711: vfprintf (vfprintf.c:1601)
==29795==    by 0x4E79BE9: printf (printf.c:35)
==29795==    by 0x4005DF: print_text_checks_null (in /home/oliver/a.out)
==29795==    by 0x400692: print_all_messages (in /home/oliver/a.out)
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
==29795== Use of uninitialised value of size 8
==29795==    at 0x4E9B70D: _IO_file_xsputn@@GLIBC_2.2.5 (fileops.c:1316)
==29795==    by 0x4E72711: vfprintf (vfprintf.c:1601)
==29795==    by 0x4E79BE9: printf (printf.c:35)
==29795==    by 0x4005DF: print_text_checks_null (in /home/oliver/a.out)
==29795==    by 0x400692: print_all_messages (in /home/oliver/a.out)
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
==29795== Use of uninitialised value of size 8
==29795==    at 0x4E9B6B0: _IO_file_xsputn@@GLIBC_2.2.5 (fileops.c:1348)
==29795==    by 0x4E72711: vfprintf (vfprintf.c:1601)
==29795==    by 0x4E79BE9: printf (printf.c:35)
==29795==    by 0x4005DF: print_text_checks_null (in /home/oliver/a.out)
==29795==    by 0x400692: print_all_messages (in /home/oliver/a.out)
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
==29795== Conditional jump or move depends on uninitialised value(s)
==29795==    at 0x4E9B6C0: _IO_file_xsputn@@GLIBC_2.2.5 (fileops.c:1347)
==29795==    by 0x4E72711: vfprintf (vfprintf.c:1601)
==29795==    by 0x4E79BE9: printf (printf.c:35)
==29795==    by 0x4005DF: print_text_checks_null (in /home/oliver/a.out)
==29795==    by 0x400692: print_all_messages (in /home/oliver/a.out)
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
Text: two
 selected number: 3
==29795== Jump to the invalid address stated on the next line
==29795==    at 0x0: ???
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==  Address 0x0 is not stack'd, malloc'd or (recently) free'd
==29795==
==29795==
==29795== Process terminating with default action of signal 11 (SIGSEGV)
==29795==  Bad permissions for mapped region at address 0x0
==29795==    at 0x0: ???
==29795==    by 0x4006CD: main (in /home/oliver/a.out)
==29795==
==29795== HEAP SUMMARY:
==29795==     in use at exit: 4 bytes in 1 blocks
==29795==   total heap usage: 1 allocs, 0 frees, 4 bytes allocated
==29795==
==29795== LEAK SUMMARY:
==29795==    definitely lost: 4 bytes in 1 blocks
==29795==    indirectly lost: 0 bytes in 0 blocks
==29795==      possibly lost: 0 bytes in 0 blocks
==29795==    still reachable: 0 bytes in 0 blocks
==29795==         suppressed: 0 bytes in 0 blocks
==29795== Rerun with --leak-check=full to see details of leaked memory
==29795==
==29795== For counts of detected and suppressed errors, rerun with: -v
==29795== Use --track-origins=yes to see where uninitialised values come from
==29795== ERROR SUMMARY: 14 errors from 10 contexts (suppressed: 4 from 4)
Segmentation fault
oliver@siouxsie:~$
=========================


Now you can meditate about the many messages of valgrind on undefined values and how they relate to the uninitialized values in the Gimp-code.

Didn't knew that result, because I use valgrind since two days, on recommendation of the gimp-irc-people.

But it looks like it affirms what I'm talking about.

-Wall has no effect here, and valgrind says the same as me. :)



So, have fun with uninitialized values,
or enter the realm of clean programming ;-)


Ciao,
   Oliver






P.S.: In case the attachement will be suppressed,
I paste the code here again.You may ignore the rest
of the mail here, if you can get the file from the attachement.


***********************************************
#include <stdio.h>
#include <stdlib.h>
#include <string.h>



/* just prints us the text         */
/* if text is undefined, we abort. */
/* ------------------------------- */
void print_text_checks_null ( char* print_me )
{
  //fprintf( stderr, "ptr: %p\n", print_me );

  if( print_me != NULL )
  {
    printf("Text: %s\n", print_me);
  }
  else
  {
    abort(); /* abort() or handle otherwise */
  }

  return;
}



/* some functions that generate us a text, */
/* giving us fresh allocated strings.      */

char* put_string_1()
{
  return strdup("one");
}

char* put_string_2()
{
  return strdup("two");
}

char* put_string_3()
{
  return strdup("three");
}



/* just a vector of string generating functions */
/* -------------------------------------------- */
typedef char* (*STRINGFUNC)();
STRINGFUNC func_vec[] = { put_string_1, put_string_2, put_string_3 };



void print_all_messages ( unsigned int selection )
{
  int num_of_functions = sizeof(func_vec)/sizeof(STRINGFUNC);

  //char* mytext = NULL;
  char* mytext;

  /* check maximum index */
  if( selection > num_of_functions )
  {
    abort(); /* abort() or handle otherwise */
  }


  switch( selection )
  {
    case 1:
               mytext = (*func_vec[ selection ])();
               break;

    case 2:    /* we need a different text here! */
               /* decide later, which to choose
               mytext = "I want a different text here!";
               mytext = "I may want another text here...";
               */
               break;

    case 3:
               mytext = (*func_vec[ selection ])();
               break;

    default:
               mytext = "ATTENTION! No text selected. Fix Bug, please!";
               break;
  }

  print_text_checks_null( mytext );


  return;
}




int main()
{

  int idx = 0;


  for( idx = 0; idx < 10; idx++ )
  {
    printf(" selected number: %d\n", idx );
    print_all_messages( idx );
  }



  return 0;
}
***********************************************
#include <stdio.h>
#include <stdlib.h>
#include <string.h>



/* just prints us the text         */
/* if text is undefined, we abort. */
/* ------------------------------- */
void print_text_checks_null ( char* print_me )
{
  //fprintf( stderr, "ptr: %p\n", print_me );

  if( print_me != NULL )
  {
    printf("Text: %s\n", print_me);
  }
  else
  {
    abort(); /* abort() or handle otherwise */
  }

  return;
}



/* some functions that generate us a text, */
/* giving us fresh allocated strings.      */

char* put_string_1()
{
  return strdup("one");
}

char* put_string_2()
{
  return strdup("two");
}

char* put_string_3()
{
  return strdup("three");
}



/* just a vector of string generating functions */
/* -------------------------------------------- */
typedef char* (*STRINGFUNC)();
STRINGFUNC func_vec[] = { put_string_1, put_string_2, put_string_3 };



void print_all_messages ( unsigned int selection )
{
  int num_of_functions = sizeof(func_vec)/sizeof(STRINGFUNC);

  //char* mytext = NULL;
  char* mytext;

  /* check maximum index */
  if( selection > num_of_functions )
  {
    abort(); /* abort() or handle otherwise */
  }



  switch( selection )
  {
    case 1:
               mytext = (*func_vec[ selection ])();
               break;

    case 2:    /* we need a different text here! */
               /* decide later, which to choose
               mytext = "I want a different text here!";
               mytext = "I may want another text here...";
               */
               break;

    case 3:
               mytext = (*func_vec[ selection ])();
               break;

    default:
               mytext = "ATTENTION! No text selected. Fix Bug, please!";
               break;
  }

  print_text_checks_null( mytext );


  return;
}




int main()
{

  int idx = 0;


  for( idx = 0; idx < 10; idx++ )
  {
    printf(" selected number: %d\n", idx );
    print_all_messages( idx );
  }



  return 0;
}

_______________________________________________
Gimp-developer mailing list
Gimp-developer@xxxxxxxxxxxxxxxxxxxxxx
https://lists.XCF.Berkeley.EDU/mailman/listinfo/gimp-developer

[Index of Archives]     [Video For Linux]     [Photo]     [Yosemite News]     [gtk]     [GIMP for Windows]     [KDE]     [GEGL]     [Gimp's Home]     [Gimp on GUI]     [Gimp on Windows]     [Steve's Art]

  Powered by Linux