Pergunta

Eu estou trabalhando em uma implementação de pool de memória e eu estou um pouco confuso sobre ponteiros de alinhamento ...

Suponha que eu tenho um pool de memória que distribui blocos de memória de tamanho fixo, no ponto de pool de memória criação I malloc ((tamanho) * (num dos blocos)). Se o que está sendo alocado são objetos eo tamanho vem do alinhamento operador sizeof não deve ser uma preocupação, mas se o tamanho é desigual (ele / ela quer 100 blocos de bytes por qualquer motivo), então quando eu dividir o pedaço dado por malloc eu ia acabar com ponteiros desalinhadas. A minha pergunta é que eu deveria sempre alinhar os blocos para algum limite e, se sim, qual? ??

Foi útil?

Solução

X86 irá funcionar sem alinhamento, mas o desempenho é melhor quando os dados são alinhados. O alinhamento para tipo é geralmente sizeof ( tipo ), até um máximo de 16 (bytes).

Eu escrevi este programa de teste bobo só para ter certeza (asuming malloc sabe o que seu fazer), e ele retorna 16 na minha caixa de amd64. Ele retorna 8 quando compilado no modo de 32 bits:

#include <stdlib.h>
#include <stdio.h>

int main() {
    int i;
    unsigned long used_bits = 0, alignment;

    for (i = 0; i < 1000; ++i) {
        used_bits |= (unsigned long)malloc(1);   /* common sizes */
        used_bits |= (unsigned long)malloc(2);   
        used_bits |= (unsigned long)malloc(4);
        used_bits |= (unsigned long)malloc(8);
        used_bits |= (unsigned long)malloc(16);
        used_bits |= (unsigned long)malloc(437); /* random number */
    }

    alignment = 1;
    while (!(used_bits & alignment)) {
        alignment <<= 1;
    }

    printf("Alignment is: %lu\n", alignment);
    return 0;
}

Outras dicas

O alinhamento adequado é, pelo menos útil (performance-wise) na maioria das implementações x86 (e algum tipo de alinhamento é realmente obrigatória em outras arquiteturas). Você pode perguntar (como calloc faz) para um par de argumentos, tamanho dos itens em bytes e número de itens, em vez de apenas um (tamanho em bytes, como malloc faz); então você pode intrinsecamente align (arredondando-se tamanhos de bloco) para a próxima maior potência de 2 acima do tamanho do item (mas interruptor para múltiplos de 16 bytes acima de 16, não manter dobrando para sempre, assim como @derobert recomenda e explica! -). Dessa forma, se um chamador só quer N bytes w / o qualquer alinhamento nem preenchimento, eles podem sempre pedir itens N de 1 byte cada (tal como fariam com calloc e pela mesma razão; -).

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top