【问题标题】:Read struct from binary file using read使用 read 从二进制文件中读取结构
【发布时间】:2014-02-02 20:39:08
【问题描述】:

我正在用 C 语言对复杂的客户端/服务器(多聊天室)程序进行简单操作。

我有一个名为 node

的链表结构
struct node
{
    char *user;
    char *passwd;
    int id;
    int connected;
    struct node *next;
};

还有一个叫做room

的结构
struct room
{
    char *name;
    int capacity;
    int room_id;
    int admin_id;
    struct room *next;
    struct node *users;
};

我将其声明为全局变量:

struct room *rooms = NULL;

我已经用互斥锁和信号量保护了它。

所以我只想在服务器结束时编写这个结构,然后在服务器再次启动时加载它。这样做的逻辑存在于两个文件中,server.c*server_utils.c*,如下所示:

server.c

int main (void)
{
    [...]
    struct stat st;
    [...]
    stat ("rooms.bin", &st);
    if (st.st_size > 0)
    {
        // Load rooms
        load_rooms ();
    }
    else
    {
        [...]
    }
    [...]
    exit (EXIT_SUCCESS);
}

*server_utils.c*

[...]

void load_rooms (void)
{
    int fd;
    if ((fd = open ("rooms.bin", O_RDONLY)) < 0)
    {
        perror ("open");
        exit (EXIT_FAILURE);
    }
    else
    {
        read (fd, &rooms, sizeof (rooms));
    }
}

void save_rooms (void)
{
    int fd;
    if ((fd = open ("rooms.bin", O_WRONLY | O_CREAT | O_TRUNC, 0644)) < 0)
    {
        perror ("open");
        exit (EXIT_FAILURE);
    }
    else
    {
        write (fd, &rooms, sizeof (rooms));
    }
}

[...]

我发现的问题是,当我从二进制文件中读取结构时

read (fd, &rooms, sizeof (rooms));

然后我尝试用

打印结构
void rooms_linkedlist_print (struct room *head)
{
    struct room *curr = head;
    char str[1024];
    while (curr != NULL)
    {
        write (1, curr->name, strlen (curr->name));
        write (1, "\n", strlen ("\n"));
        bzero (str, 1024);
        sprintf (str, "%d\n", curr->capacity);
        write (1, str, strlen (str));
        bzero (str, 1024);
        sprintf (str, "%d\n", curr->room_id);
        write (1, str, strlen (str));
        bzero (str, 1024);
        sprintf (str, "%d\n", curr->admin_id);
        write (1, str, strlen (str));
        curr = curr->next;
    }
}

我得到一个分段错误(核心转储)。关于我做错了什么有什么想法吗?

【问题讨论】:

    标签: c file struct


    【解决方案1】:

    你的房间结构里面有指针。

    当您重新加载数据时,这些指针将不再一定指向分配的内存,从而导致分段错误。

    您可以通过将使用指针更改为使用房间数组中的索引来解决此问题。

    【讨论】:

    • 我无法更改该指针,因为我不知道长度,所以我正在考虑将每个原始数据存储到一个文件中,然后在我做的时候用这个数据值再次创建结构文件不存在时的第一次。
    猜你喜欢
    • 2011-05-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-12-25
    • 1970-01-01
    • 2020-05-06
    相关资源
    最近更新 更多