在某些 UNIX 实现上,无法对通过 memalign() 分配的内存块调用 free()

在某些 UNIX 实现上,无法对通过 memalign() 分配的内存块调用 free()

我只使用 Linux,但我想了解这意味着什么:

Linux编程接口

使用 分配的内存块memalign()posix_memalign() 应使用 释放free()

在某些 UNIX 实现上,不可能调用free()通过 分配的内存块memalign(),因为该memalign() 实现使用malloc()分配内存块,然后返回指向该块中具有适当对齐方式的地址的指针。 glibc 的实现memalign()不受此限制。

man memalign

POSIX 要求posix_memalign()可以使用 释放从 获得的内存free(3)。有些系统无法回收使用 memalign()or分配的内存valloc()(因为只能传递free(3)从 获得的指针malloc(3),而例如, memalign()会调用malloc(3)然后对齐获得的值)。 glibc 实现允许使用 回收从任何这些函数获得的内存free(3)

我对内存对齐不太了解,也不了解“例如,memalign()会调用malloc(3)然后对齐获得的值”。

有人能告诉我这里发生了什么事以及可能出了什么问题free()吗?

答案1

posix_memalign应使用它,因为它是由 POSIX 定义的,正如其名称所示。有关问题,memalign请参阅例如Solaris 10 内存分配函数手册页

free() 的参数是指向先前由 malloc()、calloc() 或 realloc() 分配的块的指针。执行 free() 后,该空间可供应用程序进一步分配,但不会返回给系统。仅当应用程序终止时,内存才会返回到系统。如果 ptr 是空指针,则不会发生任何操作。如果将随机数传递给 free(),则结果是不确定的。

的描述free()甚至没有提到memalign分配。

例如,memalign()会调用malloc(3),然后对齐获得的值

以下实现是给定描述的示例:

void *memalign(size_t alignment, size_t size)
{
    void *mem;
    uintptr_t uip_mem, uip_align;

    // fail if alignment is smaller than sizeof(void*) or not a power of two
    if (alignment < sizeof(void*) || alignment & (alignment - 1)) {
        errno = EINVAL;
        return NULL;
    }

    // allocate alignment extra bytes to prevent heap overflow
    mem = malloc(size + alignment);
    if (mem == NULL)
        return NULL;

    uip_mem = (uintptr_t) mem;
    uip_align = (uintptr_t) alignment;

    // align up returned address
    return (void*) ((uip_mem + uip_align - 1) & -uip_align);
}

这个维基百科页面有关对齐的更多信息。先前的实现可能会也可能不会返回与 所返回的地址相同的地址malloc,具体取决于其对齐方式。由于返回的地址可能与调用返回的地址不完全相同malloc,因此无法安全地传递给,因为它期望(或其他分配函数)free返回未更改的值。malloc

相关内容