LINUX.ORG.RU

вопрос для GCC гуру


0

0

#define CHARN 1024

есть структура

struct foo
{
int x;
int y;
char buff[CHARN];
}

Она передается по сети. ......

Массив может быть полностью заполнен, может наполовину, а может как угодно. Тоеть количество передаваемых данных в массиве меняется.

ВОПРОС: Как сделать так чтобы передавать только только количество фактически записанных данных в структуру + x + y, а не sizeof(struct foo)? Имеется ввиду не sizeof(struct foo), а sizeof(struct foo) - _количество_неиспользованных_байт!

Можно ли в фунции send указать требуемый размер (sizeof(struct foo) - _количество_неиспользованных_байт), вместо sizeof(struct foo)?

Вернее, будут ли проблемы :-)

Спасибо!

anonymous

Ты покажи сначала, где у тебя "количество_неиспользованных_байт".

Идея:

struct foo 
{
    size_t bytes_in_buff;
    int x; 
    int y; 
    char buff[CHARN]; 
};

foo f;

send(.., &f.x, f.bytes_in_buff + sizeof(f.x) + sizeof(f.y),...);

anonymous
()

Использовать strlen? Это при условии что данные кончаются симвлом '\0'.

Evgeny_I
()

Скорее вопрос был про атрибут __packed;

Вроде бы структуру надо объявить с этим отрибутом. В других компиляторах этот атрибут не работает => в общем случае лучше использовать char*.

ival ★★
()
Ответ на: комментарий от ival

какой нахер packed и прочая фигня.

В buff пишется от 0 до CHARN байт. Сколько, каждый раз, неизвестно!
И всегда известно, сколько байт записано в эту структуру. Из CHARN отнимаем количество записанных, получаем количество неиспользованных.

Зачем передавать всю структуру по сети, если можно sizeof(struct foo) - _количество_неиспользованных_!!!

Вот я и спрашиваю! Есть ли более элегантный способ нежили предложил Я!!!

anonymous
()

>Вернее, будут ли проблемы :-)

Если все аккуратно сделаешь, то не будет проблем.

>char buff[CHARN];

Я обычно встречаю в таких случаях char buff[0];

Murr ★★
()
Ответ на: комментарий от Murr

2Murr:

тут именно CHARN нужен. Структура будет в стэке. Она еще и для приема будет использоваться.

а buff[0] я для других целей использую :)

anonymous
()
Ответ на: комментарий от anonymous

>какой нахер packed и прочая фигня.

Я думал имелось ввиду что-то вроде


#include <stdio.h>

struct st {
char c;
int i;
};

int main(void) {
printf("%d", sizeof(st)-sizeof(char)-sizeof(int));
}

ival ★★
()

Вопрос не по теме, но всё же. Будут ли где-либо проблемы со след. кодом (выравнивание?).

struct buffer { size_t len; #define BUF_PREFIX sizeof(size_t) char buf[0]; };

void *p = malloc(BUF_PREFIX + required_nbytes);

anonymous
()
Ответ на: комментарий от anonymous

Выравнивание void вроде тождественно выравниванию char, поэтому если указатель будет использовать для адресации char, то всё должно быть хорошо.

Murr ★★
()
Ответ на: комментарий от anonymous

>Вопрос не по теме, но всё же. >Будут ли где-либо проблемы со след.кодом (выравнивание?).

>struct buffer { > size_t len; > #define BUF_PREFIX sizeof(size_t) > char buf[0]; >}; >void *p = malloc(BUF_PREFIX + required_nbytes);

А откуда следует, что ((buffer*)p)->buf[0] это то, что ожидается, а не со сдвигом на несколько байт(padding?)

может быть все-таки что то вроде

char* alloc_buf(size_t sz) { void* t = malloc(sz + sizeof(size_t)); if (t == NULL) return (char*) t; *((size_t*)t -1) = sz; return (char*)((size_t*)t - 1); }

size_t size(char* buf) { return *((size_t*)buf - 1); }

void free_buf(char* buff) { free( (size_t*)buff - sizeof(size_t)); }

ival ★★
()
Ответ на: комментарий от anonymous

>Вопрос не по теме, но всё же. 
>Будут ли где-либо проблемы со след.кодом (выравнивание?).

>struct buffer { 
>     size_t len; 
>     #define BUF_PREFIX sizeof(size_t) 
>     char buf[0]; 
>}; 
>void *p = malloc(BUF_PREFIX + required_nbytes);

А откуда следует, что ((buffer*)p)->buf[0] это то, 
что ожидается, а не со сдвигом на несколько байт(padding?)


может быть все-таки что то вроде 

char* alloc_buf(size_t sz) {
	void* t = malloc(sz + sizeof(size_t)); 
	if (t == NULL) return (char*) t;
	*((size_t*)t -1) = sz;
	return (char*)((size_t*)t - 1);
}

size_t size(char* buf) {
	return *((size_t*)buf - 1);
}

void free_buf(char* buff) {
	free( (size_t*)buff - sizeof(size_t));
}

ival ★★
()
Ответ на: комментарий от ival

<PRE> > А откуда следует, что ((buffer*)p)->buf[0] это то, > что ожидается, а не со сдвигом на несколько байт(padding?)

Ну это понятно. Я имел в виду следующее.

struct buffer { size_t len; char buf[0]; };

struct buffer *b = malloc(sizeof(size_t) + sizeof("test")); if (p == NULL) return NULL; b->len = sizeof("test") - 1; strcpy(b->buf, "test"); ... free(b); </PRE>

Всегда ли (&b->buf - &b) == sizeof(size_t)?

anonymous
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.