0

well it works, but i keep getting many errors related to init and freeRecursive that are my recursive functions to generate and delete my trie

most of my errors are related to the condition of checking if one of the pointers in the array alphabet is null, but i cant get around this fault.

#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <cs50.h>

#include "dictionary.h"

int words = 0;
node *dict;
/**
 * Returns true if word is in dictionary else false.
 */
bool check(const char *word)
{
    // TODO
    node *pointer = dict;
    // if (pointer->alphabet[2] != NULL) printf("HELLO\n");
    // printf("%i\n",pointer->value);
    int i = 0;
    while (*(word+i) != '\0') {
        int index = *(word+i) - 'a';
        if (*(word+i) == '\'') index = 26;
        if (index < 0) index+= 32;
        if ( pointer->alphabet[index] == NULL ) return false;
        pointer = pointer->alphabet[index];
        i++;
    }
    if (pointer->value == 1) return true;
    else return false;
}

/**
 * Loads dictionary into memory. Returns true if successful else false.
 */
bool load(const char *dictionary)
{
    // TODO
    FILE *f = fopen(dictionary, "r");
    if (f == NULL) return false;
    dict = malloc(sizeof(node));
    char *word = malloc(sizeof(char)*LENGTH);
    while (fscanf(f, "%s", word)!=EOF) {
        // printf("%s\n",word);
        init(word, dict);
        words++;
    }
    free(word);
    fclose(f);
    return true;
}

void init (char *word, node *dict) {
    // if (dict == NULL) {
    // }
    // char *holdChar = word;
    if (*word == '\0') {
        dict->value = 1;
        // printf("check\n");
    }
    else {
        int index = *word - 'a';
        if (*word == '\'') index = 26;
        // dict->value = 1;
        // printf("%i\n",index);
        //node *hold = dict->alphabet[index];
        if (dict->alphabet[index] == NULL) {
            dict->alphabet[index] = malloc(sizeof(node));
        }
        init ((word+1), dict->alphabet[index]);
    }
}

/**
 * Returns number of words in dictionary if loaded else 0 if not yet loaded.
 */
unsigned int size(void)
{
    // TODO
    return words;
}

/**
 * Unloads dictionary from memory. Returns true if successful else false.
 */
bool unload(void)
{
    node *pointer = dict;
    freeRecursive(pointer);
    // free(dict->alphabet[2]->alphabet[0]->alphabet[19]);
    // free(dict->alphabet[2]->alphabet[0]);
    // free(dict->alphabet[2]);
    // free(dict);
    return true;
    // for (int i = 0; i < 26; i++) {
    //     if (point->alphabet[i] != NULL){
    //         point = point->alphabet[i];
    //         unload();
    //     }
    // }
    // free(point);
    // return true;
}

void freeRecursive (node *side) {
    if(!side) return;
    for (int i = 0; i < 27; i++) {
        // if (side->alphabet[i] != NULL) {
        //     // printf("%i\n",i);
        //     freeRecursive(side->alphabet[i]);
        // }
        freeRecursive(side->alphabet[i]);
    }
    free(side);
}


==34590== Memcheck, a memory error detector
==34590== Copyright (C) 2002-2013, and GNU GPL'd, by Julian Seward et al.
==34590== Using Valgrind-3.10.1 and LibVEX; rerun with -h for copyright info
==34590== Command: ./speller dictionaries/small texts/a.txt
==34590== 
==34590== Conditional jump or move depends on uninitialised value(s)
==34590==    at 0x40127F: init (dictionary.c:70)
==34590==    by 0x4011C2: load (dictionary.c:48)
==34590==    by 0x4008ED: main (speller.c:40)
==34590==  Uninitialised value was created by a heap allocation
==34590==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==34590==    by 0x401175: load (dictionary.c:44)
==34590==    by 0x4008ED: main (speller.c:40)
==34590== 
==34590== Conditional jump or move depends on uninitialised value(s)
==34590==    at 0x40127F: init (dictionary.c:70)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4011C2: load (dictionary.c:48)
==34590==    by 0x4008ED: main (speller.c:40)
==34590==  Uninitialised value was created by a heap allocation
==34590==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==34590==    by 0x401290: init (dictionary.c:71)
==34590==    by 0x4011C2: load (dictionary.c:48)
==34590==    by 0x4008ED: main (speller.c:40)
==34590== 
==34590== Conditional jump or move depends on uninitialised value(s)
==34590==    at 0x40127F: init (dictionary.c:70)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4011C2: load (dictionary.c:48)
==34590==    by 0x4008ED: main (speller.c:40)
==34590==  Uninitialised value was created by a heap allocation
==34590==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==34590==    by 0x401290: init (dictionary.c:71)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4011C2: load (dictionary.c:48)
==34590==    by 0x4008ED: main (speller.c:40)
==34590== 
==34590== Conditional jump or move depends on uninitialised value(s)
==34590==    at 0x40127F: init (dictionary.c:70)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4011C2: load (dictionary.c:48)
==34590==    by 0x4008ED: main (speller.c:40)
==34590==  Uninitialised value was created by a heap allocation
==34590==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==34590==    by 0x401290: init (dictionary.c:71)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4011C2: load (dictionary.c:48)
==34590==    by 0x4008ED: main (speller.c:40)
==34590== 

MISSPELLED WORDS

==34590== Conditional jump or move depends on uninitialised value(s)
==34590==    at 0x4010CF: check (dictionary.c:28)
==34590==    by 0x400C77: main (speller.c:112)
==34590==  Uninitialised value was created by a heap allocation
==34590==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==34590==    by 0x401175: load (dictionary.c:44)
==34590==    by 0x4008ED: main (speller.c:40)
==34590== 
kjgsdj
kgdsjglksd
fdsfs
gsdgsdfds
gsdsfd
gsdsdggdsgs
==34590== Conditional jump or move depends on uninitialised value(s)
==34590==    at 0x401324: freeRecursive (dictionary.c:109)
==34590==    by 0x401353: freeRecursive (dictionary.c:115)
==34590==    by 0x4012FC: unload (dictionary.c:92)
==34590==    by 0x400DFC: main (speller.c:152)
==34590==  Uninitialised value was created by a heap allocation
==34590==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==34590==    by 0x401175: load (dictionary.c:44)
==34590==    by 0x4008ED: main (speller.c:40)
==34590== 
==34590== Conditional jump or move depends on uninitialised value(s)
==34590==    at 0x401324: freeRecursive (dictionary.c:109)
==34590==    by 0x401353: freeRecursive (dictionary.c:115)
==34590==    by 0x401353: freeRecursive (dictionary.c:115)
==34590==    by 0x401353: freeRecursive (dictionary.c:115)
==34590==    by 0x4012FC: unload (dictionary.c:92)
==34590==    by 0x400DFC: main (speller.c:152)
==34590==  Uninitialised value was created by a heap allocation
==34590==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==34590==    by 0x401290: init (dictionary.c:71)
==34590==    by 0x4012BA: init (dictionary.c:73)
==34590==    by 0x4011C2: load (dictionary.c:48)
==34590==    by 0x4008ED: main (speller.c:40)
==34590== 
==34590== Conditional jump or move depends on uninitialised value(s)
==34590==    at 0x401324: freeRecursive (dictionary.c:109)
==34590==    by 0x401353: freeRecursive (dictionary.c:115)
==34590==    by 0x401353: freeRecursive (dictionary.c:115)
==34590==    by 0x4012FC: unload (dictionary.c:92)
==34590==    by 0x400DFC: main (speller.c:152)
==34590==  Uninitialised value was created by a heap allocation
==34590==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==34590==    by 0x401290: init (dictionary.c:71)
==34590==    by 0x4011C2: load (dictionary.c:48)
==34590==    by 0x4008ED: main (speller.c:40)
==34590== 

WORDS MISSPELLED:     6
WORDS IN DICTIONARY:  2
WORDS IN TEXT:        8
TIME IN load:         0.04
TIME IN check:        0.00
TIME IN size:         0.00
TIME IN unload:       0.00
TIME IN TOTAL:        0.04

==34590== 
==34590== HEAP SUMMARY:
==34590==     in use at exit: 0 bytes in 0 blocks
==34590==   total heap usage: 15 allocs, 15 frees, 3,869 bytes allocated
==34590== 
==34590== All heap blocks were freed -- no leaks are possible
==34590== 
==34590== For counts of detected and suppressed errors, rerun with: -v
==34590== ERROR SUMMARY: 330 errors from 8 contexts (suppressed: 0 from 0)

1 Answer 1

1

Those valgrind errors are telling you that you malloced some memory (which means that you were given some memory to use) but that you then tested that memory for some condition without having initialized it first. The memory that malloc gives you is/may be full of garbage, so you should never check if it contains a certain value unless you have initialized it. You can do this either by running a loop to set all the node members to null each time, or use calloc which will do that for you.

1
  • yea i thought that was my problem, didnt know about calloc, thanks
    – Oscar
    Commented Sep 21, 2017 at 8:35

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .