添加哈希节点时出现C分段错误

时间:2011-02-04 23:57:24

标签: c hash

我有一个类型的结构:

struct hashnode_s {
    struct hashnode_s *next;
    char *key;
    ValueType tag;
    union
    {
        int IntegerValue;
        char *StringValue;
    } u;
    int IsInCycle;
};

当我添加一个String类型的项目时,我可以,它的代码是

int hashtbl_InsertString(HASHTBL *hashtbl, const char *key, const char *value)
{
    struct hashnode_s *node;
    hash_size hash;

    hash = SearchForHashIndex(hashtbl, key,value);

    if(hash == -1)
    {
        hash=hashtbl->hashfunc(key);
    }
    /* adding the first node  if not applicable (this is based on value string)*/

    if(hashtbl->nodes[hash]== NULL)
    {
        node = malloc(sizeof(struct hashnode_s));
        node->key = key;
        node->tag = StringConst;
        node->u.StringValue = value;
        node->next = NULL;
        hashtbl->nodes[hash] = node;
    }
    else
    {
        node = hashtbl->nodes[hash];

        if(node->next ==NULL)
        {
            struct hashnode_s *nextNode;
            nextNode = malloc(sizeof(struct hashnode_s));

            if(strcmp(node->u.StringValue,key)==0)
            {
                /* set next */
                nextNode->key = key;
                nextNode->tag = StringConst;
                nextNode->u.StringValue = value;
                nextNode->next = NULL;
                node->next = nextNode;
                hashtbl->nodes[hash] = node;
            }
            else if(strcmp(node->key, value)==0)
            {
                /* switch node positions if the key */
                nextNode->key = key;
                nextNode->tag = StringConst;
                nextNode->u.StringValue = value;
                node->next = NULL;
                nextNode->next = node;
                node = nextNode;
                hashtbl->nodes[hash] = nextNode;
            }
        }
        else
        {
            while(node)
            {
                struct hashnode_s *nextNode;
                nextNode = malloc(sizeof(struct hashnode_s));

                /* TESTING PURPOSES ONLY
                printf("#define %s %s\n",node->key,node->u.StringValue);
                printf("%s==%s\n",node->u.StringValue,key);
                printf("%s==%s\n\n\n",node->key, value);
                */

                if(strcmp(node->u.StringValue,key)==0)
                {
                    nextNode->key = key;
                    nextNode->tag = StringConst;
                    nextNode->u.StringValue = value;
                    nextNode->next = NULL;
                    node->next = nextNode;
                    return 0;
                }
                else if(strcmp(node->key, value)==0)
                {
                    nextNode->key = key;
                    nextNode->tag = StringConst;
                    nextNode->u.StringValue = value;
                    node->next = NULL;
                    nextNode->next = node;
                    node = nextNode;
                    return 0;
                }
                node = node->next;
            }
        }
    }
}

但是当我添加一个整数类型的项目时。它出于某种原因抛出了分段错误?

这是代码。

int hashtbl_InsertValue(HASHTBL *hashtbl, const char *key, int integerValue)
{
    struct hashnode_s *node;
    hash_size hash;

    hash = SearchByKey(hashtbl, key);
    if(hash == -1)
    {
        hash=hashtbl->hashfunc(key);
    }

    if(hashtbl->nodes[hash] ==NULL)
    {
        node = malloc(sizeof(struct hashnode_s));
        node->key = key;
        node->tag = IntegerConst;
        node->u.IntegerValue = integerValue;
        node->next = NULL;
        hashtbl->nodes[hash] = node;
        return 0;
    }
    else
    {
        node = hashtbl->nodes[hash];
        //Check(hashtbl);
        while(node)
        {
            if(strcmp(node->u.StringValue,key)==0)
            {
                struct hashnode_s *nextNode;
                nextNode = malloc(sizeof(struct hashnode_s));

                nextNode->key = key;
                nextNode->tag = IntegerConst;

                nextNode->u.IntegerValue = 5;
                nextNode->next = NULL;

                if(node->next == NULL)
                {
                    // THIS IS WHERE IT CRASHES AT!
                    node->next = nextNode;
                }

                return 0;
            }
            node=node->next;
        }
    }
}

我正试图摆脱分段错误,但我不能有任何想法?

1 个答案:

答案 0 :(得分:0)

在查看代码时,我会注意到一些紧急问题:

  1. 你总是使用StringValue执行strcmp,即使它与IntegerValue在一个联合中,这意味着strcmp将读取一个无效的内存地址并导致整数值的段错误。
  2. 您的哈希表是否已初始化,如果没有,那么您声称的代码行很可能是segfaulting,因为这是第一次在没有写访问权限的页面上进行写入。
  3. 在将分配的节点指定为下一个节点之前检查下一个节点是否为NULL,如果失败则不释放内存,此内存泄漏可能是个问题。对数字1的明显解决方案是使用下一个指针为NULL作为指示符,表示您已到达列表的末尾,而不是检查可能并不总是存在的字符串。
  4. 散列是有符号整数,确保散列函数返回的唯一负数是-1,因为任何其他负数很容易成为另一个越界访问错误。
  5. 如果我是你,那么在尝试追踪这个错误之前我会修复这些其他问题,当你只找一个错误时更容易找到错误。