如何将C结构正确写入磁盘上的文件,因此可以在其上使用mmap?

问题描述 投票:0回答:1

我在内存中使用以下C结构:

typedef struct MyStructHdr
{

    char        text[4];
    int         version_num;

    uint64 init_value;

    uint64 entries[];

} MyStructHdr;

typedef MyStructHdr *MyStruct;

Field entries[]是指向某个灵活数组的指针。类型uint64是定制的便携式应用程序特定类型,在32位OS上增加了uint64_t支持。

我必须正确地将此结构写入文件,以便以后可以在同一平台/ OS上使用mmap()

map = (MyStruct) mmap(NULL, MyStructActualSize,
                      PROT_READ | PROT_WRITE, MAP_SHARED,
                      mystruct_fd, 0);

我现在要做什么?我只是简单地使用MyStruct逐一写入entries[]字段(并通过缓冲区逐个写入write()字段)。最后写入CRC32校验和。

在我使用的所有64位系统上,一切都正常。似乎前4个字符+ 32位int对齐到单个64位块中,并且uint64只是扩展为uint64_t,因此在写入后,所有内容均正确mmap编写。

但是,我担心在32位系统或某些特定的OS /体系结构上,将应用不同的对齐规则,并且没有uint64_t,并且uint64扩展为类似内容:

{
    int val1;
    unsigned long int val2;
}

写入后我将得到不正确的mmap

将这种结构写入文件并在之后使用mmap的可移植方式是什么?

P.S。实际上,这全都与PostgreSQL扩展有关,uint64这里是pg_atomic_uint64,但我认为这个问题更笼统。

c memory data-structures mmap memory-alignment
1个回答
0
投票

您不应该一个个地写成员,因为这不会考虑成员之间的填充。一次写下整个内容:

write(fd, MyStruct, sizeof(MyStructHdr) + entry_count * sizeof(uint64));

其中entry_count是灵活数组成员中的元素数。

© www.soinside.com 2019 - 2024. All rights reserved.