Empresas
Empregos
  • Sobre nós
  • Soluções
    • Publicação de vagas
      Publique sua vaga e receba candidatos qualificados em 48h.
    • Avaliações de candidatos
      Mais de 500 testes técnicos e psicológicos, mais anti-fraude.
    • Headhunting
      Busca executiva personalizada do início ao fim.
    • Folha de Pagamento + EOR
      Dispersão de folha e EOR em mais de 15 países da LATAM.
  • Preços
  • Empregos

0

179
Visualizações
Alineación malloc y C: ¿es segura esta optimización hecha a mano?

Puse todo el código pero, por supuesto, está en archivos diferentes (archivos .h y .c )

 typedef unsigned char ubyte; typedef unsigned int uint; #include<stdbool.h> typedef struct Cube { ubyte n; ubyte e; ubyte s; ubyte w; } Cube; typedef struct Piece { Cube c; bool is_main; char offset_n; char offset_s; } Piece; typedef struct Block { ubyte total; Piece* pieces; } Block; Block *block_create(uint nb_pieces) { Block *block = malloc(sizeof(Block) + (sizeof(Piece) * nb_pieces)); block->pieces = (Piece *) (&block + sizeof(Block)); return block; }

Me pregunto si esta línea de código: block->pieces = (&block + sizeof(Block)); estará siempre a salvo. Quiero decir: ¿podemos estar seguros de que, inmediatamente después de sizeof(Piece) , tendremos precisamente (sizeof(Piece) * nb_pieces) ? ¿Estamos seguros de que nunca habrá un problema de alineación (es decir, tal vez si está alineado en 64 bits, la memoria para sizeof(Block) será inferior a 8 bytes y block->pieces no debería apuntar exactamente a sizeof(Block) , pero " sizeof(Block) 64 bits alineados").

Espero ser lo suficientemente claro.

over 4 years ago · Santiago Trujillo
1 Respostas
Responde à pergunta

0

Primero, esto no está haciendo lo que esperas, y por múltiples razones:

 block->pieces = (&block + sizeof(Block));

Primero, &block es la dirección de la variable block , no el contenido de block , y tiene el tipo block ** . A lo sumo, puede agregar con seguridad 1 valor de este puntero porque cualquier otra cosa creará un puntero más allá del final de esta variable que no es válido.

Entonces necesitarías cambiar &block a block . Eso aún no hará lo que espera porque la aritmética de punteros incrementa la dirección sin procesar en múltiplos del tamaño del objeto. Por lo tanto, agregar sizeof(Block) a esto no es mover hacia arriba 1 elemento de la matriz, sino mover hacia arriba los elementos de la matriz sizeof(Block) .

Para solucionar esto, necesitaría block + 1 . Ahora debe comenzar a preocuparse por la alineación. Para que su matriz de Pieces se alinee correctamente, debe verificar si _Alignof(Block) y _Alignof(Piece) son iguales. De lo contrario, deberá agregar bytes de relleno:

 int padding = 0; if (_Alignof(Block) % _Alignof(Piece) != 0) { padding = _Alignof(Piece) - (_Alignof(Block) % _Alignof(Piece)); } Block *block = malloc(sizeof(Block) + padding + (sizeof(Piece) * nb_pieces)); block->pieces = (Piece *)((char *)(block + 1) + padding);

Por supuesto, puede evitar todo esto haciendo que el miembro de pieces sea un miembro de matriz flexible :

 typedef struct Block { ubyte total; Piece pieces[]; } Block;

Y la asignación por sí sola será suficiente.

over 4 years ago · Santiago Trujillo Relatório
Responde à pergunta
Encontrar trabalhos remotos

Descubra a nova forma de encontrar um emprego!

melhores empregos
Principais categorias de trabalho
Empresas
Postar vaga Preços Comercial
Jurídico
Termos e Condições Política de privacidade
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomende algumas ofertas para mim
Preciso de ajuda