If I modify the string key example to check for duplicates before adding new entries, it dies

69 views
Skip to first unread message

Sir Barksalot

unread,
Dec 9, 2019, 2:13:08 PM12/9/19
to uthash
The example works fine, until I add code to check for duplicates. The output is then "Segmentation fault (core dumped)"
I'm figuring it must be a rookie mistake. Can anybody spot where I've gone wrong? I've commented my changes below

#include <string.h>  /* strcpy */
#include <stdlib.h>  /* malloc */
#include <stdio.h>   /* printf */
#include <uthash.h>

struct my_struct {
    char name[10];             /* key (string is WITHIN the structure) */
    int id;
    UT_hash_handle hh;         /* makes this structure hashable */
};


int main(int argc, char *argv[]) {
    // modified this line to add duplicates
    const char *names[] = { "joe", "bob", "betty", "johnny", "betty", "johnny", "bob", "joe", NULL };
    struct my_struct *s, *tmp, *users = NULL;

    for (int i = 0; names[i]; ++i) {
        s = (struct my_struct *)malloc(sizeof *s);
        strcpy(s->name, names[i]);
        s->id = i;
        // added the lines below to check for duplicates
        HASH_FIND_STR( users, names[i], s);
          if (s) {
            printf("Danger, duplicate detected: %s\n", names[i]);
          } else {
            HASH_ADD_STR( users, name, s );
          }

    }

    HASH_FIND_STR( users, "bob", s);
    if (s) printf("%s's id is %d\n", s->name, s->id);

    for(s=users; s != NULL; s=s->hh.next) {
        printf("user id %d: name %s\n", s->id, s->name);
    }

    /* free the hash table contents */
    HASH_ITER(hh, users, s, tmp) {
      HASH_DEL(users, s);
      free(s);
    }
    return 0;
}

cro...@gmail.com

unread,
Feb 3, 2020, 4:43:42 PM2/3/20
to uthash
HASH_FIND_STR was clobbering s. Try:

   for (int i = 0; names[i]; ++i) {
      s = (struct my_struct *) malloc(sizeof *s);
      strcpy(s->name, names[i]);
      s->id = i;

      HASH_FIND_STR(users, s->name, tmp);
      if (tmp)
         printf("Danger, duplicate detected: %s\n", s->name);
      else
         HASH_ADD_STR(users, name, s);

Sir Barksalot

unread,
Feb 3, 2020, 5:04:38 PM2/3/20
to uthash
Brilliant. Thanks for the insight.

SB

cro...@gmail.com

unread,
Feb 3, 2020, 7:10:52 PM2/3/20
to uthash
Also you’d want to check for the key’s presence before, rather than after, allocating a new node.
Reply all
Reply to author
Forward
0 new messages