Newsgroup: it.comp.lang.c
Titolo: Dividere dati e ricostruirli

Devo fare una cosa credevo molto semplice, dato un dato (puntatore a
void) grosso a piacere, dividerlo in modo da farlo stare in N paccheti
da K bytes, e ricostruirlo in seguito
Ho provato l'approccio che segue ma ottengo risultati molto strani, una
sequenza di 0 e 6, che non capisco dove vada a pescare peraltro..
Tra l'altro noto che
--8<---------------cut here---------------start------------->8---
    int chunks = (ceil) (size / chunk_size);
--8<---------------cut here---------------end--------------->8---
ad esempio con 100 e 3 mi restituisce 33, invece di 34, come mai?
La divisione non era float in C?
Vi sembrano sensati i parametri alle funzioni?
--8<---------------cut here---------------start------------->8---
// -*- compile-command: "gcc -Wall -Wextra -lm -o test test_packets.c && ./test" -*-
// check out XDR for data binary manipulation also
#include <stdlib.h>
#include <string.h>
#include <math.h>
#include <stdio.h>
#define SIZE 100
void **split_binary(const void *, int, int);
void *rebuild(void **, int, int);
int main() {
    // create some data and split and recombine it
    int i;
    int data[SIZE];
    for (i = 0; i < SIZE; i++) {
        data[i] = i;
    }
    void **chunks = split_binary(data, sizeof(int) * SIZE, 3);
    // now check if they're equivalent
    int *reconstructed = (int *) rebuild(chunks, 34, SIZE);
    // use assert to check for equivalence
    for (i = 0; i < SIZE; i++) {
        printf("%d\n", (int) reconstructed[i]);
    }
    return(0);
}
// splitting the data in binary chunks of len len, returning
// a pointer to the array of chunks
void **split_binary(const void *data, int size, int chunk_size) {
    // allocate enough pointers here, make sure "int" is doing the ceil!
    int chunks = (ceil) (size / chunk_size);
    printf("ceil(%d / %d) = %d", size, chunk_size, chunks);
    void **result = malloc(sizeof(void *) * chunks);
    int i;
    for (i = 0; i < size; i++) {
        result[i] = malloc(sizeof(void *) * chunk_size);
        memcpy(result[i], data + (sizeof(void *) * chunk_size), chunk_size);
    }
    printf("splitting object of length %d in %d pieces\n", size, chunks);
    return result;
}
// reconstruct the object from the chunks and the original size
void *rebuild(void **chunks, int len, int size) {
    int i;
    int offset = 0;
    void *data = malloc(size);
    for (i = 0; i < len; i++) {
        offset += sizeof(chunks[i]);
        memcpy(data + offset, chunks[i], sizeof(chunks[i]) / 8);
        printf("setting %ld bits at offset %d\n", sizeof(chunks[i]), offset);
    }
    return data;
}
--8<---------------cut here---------------end--------------->8---
Grazie mille

 Grazie mille
Letteralmente di nulla, ancora non mi funza - però sono troppo cotto per 
andare avanti e vedere cosa c'è
'notte

 writes:

Sono "fiero" di annunciare che funziona!
--8<---------------cut here---------------start------------->8---
// -*- compile-command: "gcc -Wall -Wextra -lm -o test test_packets.c && ./test" -*-
#include <stdlib.h>
#include <string.h>
#include <math.h>
#include <stdio.h>
#include <assert.h>
#define LEN 1000
#define N_CHUNKS 12
void **split_binary(const void *, int, int);
void *rebuild(void **, int, int);
int main() {
    // create some data and split and recombine it
    int i;
    int data[LEN];
    for (i = 0; i < LEN; i++) {
        data[i] = i;
    }
    int nbytes = LEN * sizeof(int);
    void **chunks = split_binary(data, nbytes, N_CHUNKS);
    // now check if they're equivalent
    int *reconstructed = (int *) rebuild(chunks, nbytes, N_CHUNKS);
    // use assert to check for equivalence
    for (i = 0; i < LEN; i++) {
        /* printf("data[i] = %d, reconstructed[i] = %d\n", data[i], reconstructed[i]); */
        assert(data[i] == (int) reconstructed[i]);
    }
    return(0);
}
// splitting the data in binary chunks of len len, returning
// a pointer to the array of chunks
void **split_binary(const void *data, int size, int num_chunks) {
    // allocate enough pointers here, make sure "int" is doing the ceil!
    int chunk_size = (ceil) ((float) size / num_chunks);
    int i;
    void **result = malloc(sizeof(void *) * num_chunks);
    printf("allocating %d times %d bytes\n", num_chunks, chunk_size);
    for (i = 0; i < num_chunks; i++) {
        result[i] = calloc(1, chunk_size);
        memcpy(result[i], data + (i * chunk_size), chunk_size);
    }
    return result;
}
void *rebuild(void **chunks, int size, int num_chunks) {
    void *data = malloc(size);
    int chunk_size = (ceil) ((float) size / num_chunks);
    int i;
    for (i = 0; i < num_chunks; i++) {
        memcpy(data + (i * chunk_size), chunks[i], chunk_size) ;
        /* printf("setting %d bytes at offset %d\n", chunk_size, (i * chunk_size)); */
    }
    return data;
}
--8<---------------cut here---------------end--------------->8---
Avevo fatto parecchio casino con le dimensioni.
Lo stile fa ancora un po' pietà, come mi converrebbe strutturarlo?
In realtà ora dovrò usare questa "pacchettizzazione" per rompere
pacchetti IPV6 e mandarli su un canale con MTU molto basso...
Anche questo ripetuto due volte
--8<---------------cut here---------------start------------->8---
    int chunk_size = (ceil) ((float) size / num_chunks);
--8<---------------cut here---------------end--------------->8---
mi pare un po' una schifezza...