0
votes

Valgrind is giving me Conditional jump or move depends on uninitialised value(s) and Uninitialised value was created by a heap allocation errors on my current code:

    void createMonsters(Game *game) {
       (void) game;

       Creature *nr;

       int x = 0;
       int r = 0;
       int y = 0;
       int check = 0;
       int c = game->opts.numMonsters;
       int nrm=0;


       nr=malloc( sizeof (Creature) * c);


        for(int i=0;i<c;i++){

            game->numMonsters=nrm;
            r = rand()%2;
            x = rand() % game->opts.mapWidth;
            y = rand() % game->opts.mapHeight;
            check=1;

            while(check!=2){
                check = isBlocked(game,x,y);
                if(check==1){
                    x = rand() % game->opts.mapWidth;
                    y = rand() % game->opts.mapHeight;
            }
                else{

                    nr[i].pos.y=y;
                    nr[i].pos.x=x;
                    nr[i].attack=attackPunch;
                    nrm += 1;
                    check=2;
            }
        }

            if(r==0){
                nr[i].name[0] = 'C';
                nr[i].maxhp = 15;
                nr[i].hp = nr[i].maxhp;
                nr[i].sign = 'C';
        }
            else{
                nr[i].name[0] = 'D';
                nr[i].maxhp = 50;
                nr[i].hp = nr[i].maxhp;
                nr[i].sign = 'D';


        }    

            game->monsters=nr;

        }
       game->numMonsters=nrm;
    }


int isBlocked(Game *game, int x, int y)
    {
            (void) game;
            (void) x;
            (void) y;
            if(x>game->opts.mapWidth || y>game->opts.mapHeight){
                return 1;
            }        }

            if(game->numMonsters!=0){                   
            for (unsigned int i = 0; i < game->numMonsters; i++){
                Creature *monst = &game->monsters[i];
                if (monst->pos.x == x && monst->pos.y == y){
                    return 1;
                }}
            }



            if(game->map.tile[y][x]==TILE_OPEN || game->map.tile[y][x]==TILE_ROOM){
                return 0;
            }
            else{
                return 1;
            }

     }

Valgrind points to nr=malloc( sizeof (Creature) * c); So what I'm doing wrong?

    typedef struct creature_st {
        char name[20];  // name of the monster
        char sign;  // character that represents monster on the game display
        Point pos;  // location of the monster
        float hp;  // current hitpoints
        unsigned int maxhp;  // maximum hitpoints
        void (*move)(struct game_st *, struct creature_st *);  // current movement algorithm for monster
        void (*attack)(struct game_st *, struct creature_st *);  // current attack algorithm for monster
    } Creature;

Full valgrind error:

==386== Conditional jump or move depends on uninitialised value(s) ==386==    at 0x4C2C1B8: strlen (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so) ==386==    by 0x403F54: test_createMonsters (test_source.c:179) ==386==    by 0x409377: srunner_run (in /tmc/test/test) ==386==    by 0x4057C9: tmc_run_tests (tmc-check.c:134) ==386==    by 0x405464: main (test_source.c:529) ==386==  Uninitialised value was created by a heap allocation ==386==    at 0x4C28C20: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so) ==386==    by 0x4026C2: createMonsters (monster.c:288) ==386==    by 0x403ADF: test_createMonsters (test_source.c:119) ==386==    by 0x409377: srunner_run (in /tmc/test/test) ==386==    by 0x4057C9: tmc_run_tests (tmc-check.c:134) ==386==    by 0x405464: main (test_source.c:529) ==386== 

    typedef struct game_st {
        Map map;
        unsigned int numMonsters;  // number of elements in 'monsters' array
        Creature *monsters;  // dynamic array of all monsters
        Point position;  // current position of the player
        float hp;  // hit points, should never be higher than 'maxhp'
        unsigned int maxhp;  // maximum hit points
        Options opts;
    } Game;
1
is Creature a complete type here? If this is a typedef on a struct is it's definition included?4pie0
Added def of Creature structKimi Heinonen
What I am asking is whether that file has access to that definition of struct?4pie0
Oh, yes it has access to def.Kimi Heinonen
In a context like this, you should really show the full error message from valgrind. Things like the stack trace where the problem is detected and any previous comments it passed are probably relevant. At the least, without seeing the valgrind trace, I'm not going to attempt to guess what you're doing wrong. What's the value in game->opts.numMonsters? It's a little surprising if valgrind waits until you allocate memory to report problems, but that's used to determine c. Also consider the techniques that create an MCVE (minimal reproducible example). Applying those principles to your code may help.Jonathan Leffler

1 Answers

1
votes

Uninitialized value has been created somewhere in your code and that function accesses that value. Use --track-origins=yes option to valgrind to track where that value comes from.