14

The problem is mainly caused by the if statement on line 69 if (temp->word != NULL) { // some code } valgrind is angry because you never really initialized the member word of your struct pointed to by temp, yet you're trying to check whether it has NULL as a value. While the latter might be true, technically there's no guarantee that word will be ...


14

The problem is in the conditions right? specifically in the node, pointed to by node* cur Now it's a problem because the node, node* cur is pointing to is "uninitialized" When we malloc something in the memory, it just allocate some portion of memory and give the address of the starting block of the memory allocated, to the pointer, and that's it. Now if ...


10

I had a ton of errors like that, too... But ALL these errors disappeared, when I changed only 4 single characters in my code! Here's how: I simply used calloc() in place of malloc()! calloc() needs an additional argument for the number of blocks sizeof(x), so use calloc(1, sizeof(node)) instead of malloc(sizeof(node)). It's as simple as that! So, what ...


7

Valgrind basically runs your application in a "sandbox." While running in this sandbox, it is able to insert its own instructions to do advanced debugging and profiling. From the manual: Your program is then run on a synthetic CPU provided by the Valgrind core. As new code is executed for the first time, the core hands ...


7

Hmmm..... 568 bytes in 1 block.... sounds like a file pointer. Did we forget to close an open file somewhere???? ;-) Side note: valgrind usually tells you how you can get more information, with something like For counts of detected and suppressed errors, rerun with: -v If this answers your question, please click on the check mark to accept. ...


5

568 bytes happens to be the size of a structure allocated in fopen and freed in fclose. It seems you don't call fclose on reaching EOF. I don't get that if/else at the end of load, since you can leave the for loop only if c indeed is EOF BTW, fclose(inptr) makes no sense if inptr is NULL. It might cause a segmentation fault in that case.


4

You're totally correct. You have to initialize variables before asking for their values. Since a trie is an array of arrays, the root array can be initialized when declared like that node *root[26] = {NULL}; This way of initializing an array basically tells the compiler to initialize the first element in root (i.e., root[0]) to NULL and all the other ...


3

When implementing a recursive function, the base case should be written first because it's the first thing that should be executed to determine whether there should be one more recursive call or not! What you're doing, basically, is that you're executing the loop no matter whether the base case is reached and that's a bad practice and might sometimes cause ...


3

Totally awesome that you are asking the question even though it passed check50! Kudos. Notice this line Usage: speller [dictionary] text in the valgrind report. Speller didn't really run. You called valgrind but did not supply arguments to speller. Therefore, it didn't do anything, therefore no leaks. If you call valgrind with arguments to speller, you will ...


3

for (int i = 0; i < 26; i++) You have 27 elements (a-z and '), so <=26 or <27 would be appropriate.


3

checking for valgrind errors... Invalid read of size 1: (file: dictionary.c, line: 76) So what's line 76 on dictionary.c? Also, based on the time your spell-checker took for that one text, I can be fairly confident that after fixing any valgrind errors, you won't qualify for the Big Board with your current implementation. The Big Board runs all ...


3

Complicated code in terms of memory management. This set of problems deals with the traditionally more difficult concepts of C programming, so we need a good theoretical basis for dealing with them. We must distinguish between a pointer that stores a memory address only, and the declaration of a new node in the linked list "node * tmp = malloc (sizeof (node)...


2

OK, so it turns out there was already an answer to this on Reddit. The problem was that I was declaring my pointer again, instead of just reassigning. In other words, I was doing: FILE* img = fopen(...);, fclose(img), FILE* img = fopen(...);. When I should be doing: FILE* img = fopen(...);, fclose(img), img = fopen(...);. Check out the reddit post for ...


2

Your code looks mostly good. Although you can return true from your recursive freeTrie() function and then in your unload() function just call freeTrie() on your root node. That's it. You don't need to worry about anything else because, for example, i expect your curr pointer is not malloc'd on the heap. It's just a node pointer in a function on the stack, ...


2

Well, it seems to me that if you want to free that particular malloc, you need to have two free() statements, one immediately before each return so that no matter how you exit, it gets freed. For the return true, it would have to look something like this: if (strcmp (s, head->word) == 0) { free(s); return true; } If you ...


2

The cause you have pasted means that you are checking the value of a variable you didn't previously specify (most likely unloader -> children[i] != NULL). When creating a new node, you should initialize all children node pointers to NULL to make sure they don't contain any uninitialized, "garbage" memory.


2

Your code isn't freeing recursively. It should keep on going down the tree while children[i]!=NULL, only freeing the node when that condition isn't met anymore. It then returns up the tree, freeing each node in turn. In your case, you are going down to the final children[i] then freeing spider, you're not going back up the tree.


2

As noted in the comments, root is not declared globally. It is declared as a local var in both load and check. By declaring it locally in load, the local var root is destroyed when load ends. That means that the trie is lost when load is finished. The memory that was calloc'd still exists, but there is no pointer to it. This needs to be fixed before any ...


2

Can't tell you exactly what's happening without seeing your entire code, but one thing I can tell you right away is that you're forgetting to allocate space for the null terminator when you only malloc the strlen, like this hash_word = malloc(sizeof(word_length));. You should malloc strlen + 1. And note that sizeof(word_length) will give you back the size ...


2

Why are you mallocing space in check? Also, your free(checker) only runs if the word is not found. How about when the word is found? You return true and the function ends, so that free line is never reached.


2

It seems to me that because your hash function is not case-insensitive all of the words with capital letters get hashed to a different location (h) before you get to use strcasecmp.


2

Without seeing more code, it's hard to know. A leak of 568 bytes in 1 block usually indicates a file that wasn't closed. Is it possible that there's a return command executed before the dictionary file was closed? If this answers your question, please click on the check mark to accept. Let's keep up on forum maintenance. ;-)


2

As always, it's most helpful to post actual results in the question. I ran the code and found the following result in valgrind: ==1350== ==1350== HEAP SUMMARY: ==1350== in use at exit: 568 bytes in 1 blocks ==1350== total heap usage: 13 allocs, 12 frees, 1,752 bytes allocated ==1350== This means that there was 1 block of 568 bytes still in use in ...


2

Simply put, the unload function doesn't free anything. Worse, it loses the entire tree/trie. Here's why. First, pointer is created and initialized and set to NULL. Then the for loop starts. As the loop runs, each element in the hashtable array is set to NULL by this line: hashtable[i] = pointer;, losing track of the tree. Finally, the while loop never ...


2

I see two issues with unload. First, when it finishes, it returns false instead of true. Now on to the main issue. Look at this code at the end of load. if (feof(file)) { free(newnode); } This will free the last node created. Unfortunately, it contains the last word processed. When free() is called, it releases the memory but it does NOT reset the ...


2

The issue lies in how you are initializing your nodes. for (int i=0; i<27; i++) { trav->next[x]=NULL; } What is x on that line? Pay special attention to your counting variable in the loop. To answer your question about calloc, calloc will give you initialized (to zero) memory, which means you don't have to do the initialization loop. I would ...


2

The main problem lies in your check function. The for loop setup increments l on each pass. Unfortunately, the code is also incrementing l inside the loop, so every other letter in a word is skipped, pretty much guaranteeing that every word is misspelled. There are some other issues to be fixed. First, the use of atoi() is wrong. It shouldn't be used at ...


2

Valgrind is reporting leaked memory when I run it, and it comes from this line in check: //allocating space for cursor node *cursor = malloc(sizeof(node)); cursor is a pointer. It doesn't need any space allocated for it. This memory is never freed, which valgrind is reporting. Best to just declare it without mallocing.


2

You don't free the realloced memory. Your code buffer_temp_word = NULL; free(buffer_temp_word); means free is called for NULL. You should not change the value of buffer_temp_word there, you could increment a copy instead, or use an index variable. And 8 bytes is correct, in both cases you lose the memory when you are at a char_count ...


2

Why are you freeing new_node inside the load function? All of your nodes will be freed in unload so by freeing the last new node in load, unload hits memory that is no longer yours.


Only top voted, non community-wiki answers of a minimum length are eligible