So i am so close to finally completing this present and i still have some final errors to go through. Valgrind is saying that it is still leaking memory for some reason and i cant find the reason why.
error below:
running valgrind --show-leak-kinds=all --xml=yes --xml-file=/tmp/tmpnbjzjhsm -- ./speller substring/dict substring/text...
checking for output "MISSPELLED WORDS\n\nca\ncats\ncaterpill\ncaterpillars\n\nWORDS MISSPELLED: 4\nWORDS IN DICTIONARY: 2\nWORDS IN TEXT: 6\n"...
checking that program exited with status 0...
checking for valgrind errors...
112 bytes in 2 blocks are still reachable in loss record 1 of 1: (file: dictionary.c, line: 89)
valgrind has this see below:
^C==5410==
==5410== Process terminating with default action of signal 2 (SIGINT)
==5410== at 0x4C2F3C0: ??? (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==5410== by 0x4C3361D: strcasecmp (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==5410== by 0x40108F: check (dictionary.c:36)
==5410== by 0x400C89: main (speller.c:112)
==5410==
==5410== HEAP SUMMARY:
==5410== in use at exit: 8,013,648 bytes in 143,092 blocks
==5410== total heap usage: 143,096 allocs, 4 frees, 8,023,416 bytes allocated
==5410==
==5410== 552 bytes in 1 blocks are still reachable in loss record 1 of 3
==5410== at 0x4C2FB0F: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==5410== by 0x5258E49: __fopen_internal (iofopen.c:65)
==5410== by 0x5258E49: fopen@@GLIBC_2.2.5 (iofopen.c:89)
==5410== by 0x400A23: main (speller.c:55)
==5410==
==5410== 920,192 bytes in 16,432 blocks are still reachable in loss record 2 of 3
==5410== at 0x4C2FB0F: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==5410== by 0x4011FB: load (dictionary.c:89)
==5410== by 0x400964: main (speller.c:40)
==5410==
==5410== 7,092,904 bytes in 126,659 blocks are definitely lost in loss record 3 of 3
==5410== at 0x4C2FB0F: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==5410== by 0x4011FB: load (dictionary.c:89)
==5410== by 0x400964: main (speller.c:40)
==5410==
==5410== LEAK SUMMARY:
==5410== definitely lost: 7,092,904 bytes in 126,659 blocks
==5410== indirectly lost: 0 bytes in 0 blocks
==5410== possibly lost: 0 bytes in 0 blocks
==5410== still reachable: 920,744 bytes in 16,433 blocks
==5410== suppressed: 0 bytes in 0 blocks
==5410==
==5410== For counts of detected and suppressed errors, rerun with: -v
==5410== ERROR SUMMARY: 1 errors from 1 contexts (suppressed: 0 from 0)
code starts below -----
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include "dictionary.h"
#include "string.h"
#include <ctype.h>
#include <strings.h>
// Represents a node in a hash table
typedef struct node
{
char word[LENGTH + 1];
struct node *next;
}
node;
// Number of buckets in hash table
const unsigned int N = 10000;
int number_words = 0;
// Hash table
node *table[N]; // array of node pointer every element in that arraay is a pointer change it to some higher value and can spread buckets
// Returns true if word is in dictionary else false
bool check(const char *word)
{
int index = hash(word);
node*cursor = table[index];
while (cursor != NULL)
{
if (strcasecmp(cursor ->word, word) == 0)
{
return true;
}
else
{
cursor = cursor -> next;
}
}
return false;
}
// Hashes word to a number
unsigned int hash(const char *word)
{
// TODO
unsigned int hashvalue = 0;
for (int i = 0 ; word[i] != '\0'; i++)
{
hashvalue += tolower(word[i])* (i + 1);
}
return hashvalue % N;
}
// Loads dictionary into memory, returning true if successful else false
bool load(const char *dictionary)
{
FILE *file = fopen(dictionary, "r");
if (file == NULL)
{
printf("there is an error on file open");
return 1;
}
for (int i = 0; i < N; i++)
{
table[i] = NULL;
}
char words[45];
while(fscanf(file, "%s", words) != EOF)
{
node *n = malloc(sizeof(node));
if (n == NULL)
{
printf("with n in 63");
unload();
return 1;
}
strcpy(n ->word, words);
n -> next = NULL;
number_words++;
int h_index = hash(words);
if (table[h_index] == NULL)
{
table[h_index] = n;
n -> next = NULL;
}
if (table[h_index] != NULL)
{
n -> next = table[h_index];
table[h_index] -> next = n;
}
}
fclose(file);
return true;
}
// Returns number of words in dictionary if loaded else 0 if not yet loaded
unsigned int size(void)
{
return number_words;
return 0;
}
// Unloads dictionary from memory, returning true if successful else false//
bool unload(void)
{
for(int i = 0; i < N; i++)
{
node *head = table[i];
node *cursor = head;
while (cursor != NULL)
{
node *tmp = cursor;
cursor = cursor -> next;
free(tmp);
tmp = cursor;
}
return true;
}
return false;