Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > C/C++ программирование > Общие вопросы C/C++
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 18.05.2011, 11:49   #1
moiav
 
Регистрация: 24.07.2009
Сообщений: 3
По умолчанию Как передать структуру через socket

Добрый день. Подскажите пожалуйста, как передать структуру через socket/
Вот код.
Сама структура:
Код:
//Структура сообщения
#pragma pack(push, 1)
typedef struct TMsgBlock
{
        long sendTime;
    unsigned short reciptID;
    unsigned short senderID;
    unsigned short rMsgNum;
        unsigned short sMsgNum;
        unsigned short blockSize;
        char block[256];    
};
#pragma pack(pop)
 
//Структура пакета
#pragma pack(push, 1)
typedef struct TTransferPack
{
        char signature[4];
        unsigned short size;
        unsigned short checkSum;
        TMsgBlock msgBlock;
};
#pragma pack(pop)
Функция для отправки пакета:
Код:
bool Client::SendPack(TMsgBlock* msgBlock)
{
        TTransferPack pack;
        memset(&pack, 0, MAX_SIZE);
//Здесь происходит заполнение полей структуры TTransferPack
        Package::Instance()->PreparePackage(&pack, msgBlock);
        int size = PACK_HEADER_SIZE + pack.size;
        pack.msgBlock.sendTime = GetTickCount();
        if(send(this->sock, (char*)&pack, size, 0) <= 0)
        {
                this->OnLinkError(this->handle, this->serverHandle, WSAGetLastError());
                this->Disconnect();
                return false;
        }
        return true;
}
Вызов функции SendPack:
Код:
bool Client::OpenConnection(void)
{
        ...
        TMsgBlock msgBlock;
        memset(&msgBlock, 0, sizeof(TMsgBlock));
//Здесь происходит заполнение полей структуры TMsgBlock
        this->CreateLinkMessage(&msgBlock);
        this->SendPack(&msgBlock);
        ...
}
В общем, отправляется какая-то белиберда.
Заранее большое спасибо.
moiav вне форума Ответить с цитированием
Старый 18.05.2011, 12:03   #2
veniside
Старожил
 
Регистрация: 03.01.2011
Сообщений: 2,508
По умолчанию

//Здесь происходит заполнение полей структуры TTransferPack

> отправляется какая-то белиберда

чем заполнили, то и отправляется )

может на принимающей стороне что-то не так?
"Когда приходит положенное время, человек перестаёт играть в пинбол. Только и всего."
veniside вне форума Ответить с цитированием
Старый 18.05.2011, 13:09   #3
moiav
 
Регистрация: 24.07.2009
Сообщений: 3
По умолчанию

К сожалению, заполняется все корректно. На принимающей стороне тоже проблем нет.
moiav вне форума Ответить с цитированием
Старый 18.05.2011, 14:16   #4
veniside
Старожил
 
Регистрация: 03.01.2011
Сообщений: 2,508
По умолчанию

не верю. В строке

Код:
send(this->sock, (char*)&pack, size, 0)
ошибки нет (если считать pack и size корректно заполненымы). Всё остально от сокета не зависит.

Значит, или заполняете неправильно, или принимаете не то, что ожидаете.

> memset(&pack, 0, MAX_SIZE);

Кстати, а чему равно MAX_SIZE?
"Когда приходит положенное время, человек перестаёт играть в пинбол. Только и всего."
veniside вне форума Ответить с цитированием
Старый 18.05.2011, 14:30   #5
moiav
 
Регистрация: 24.07.2009
Сообщений: 3
По умолчанию

MAX_SIZE = 4096
При отладке значения всех полей pack нормальные. Можно из этого считать, что заполняется правильно?
size вроде корректно заполнен. Вычисляется по сумме размеров всех полей структуры.
moiav вне форума Ответить с цитированием
Старый 18.05.2011, 14:40   #6
veniside
Старожил
 
Регистрация: 03.01.2011
Сообщений: 2,508
По умолчанию

> MAX_SIZE = 4096

хм, обявление TTransferPack pack; выделяет на стеке sizeof(TTransferPack) байт (несложно подсчитать, что это примерно 300 байт, не больше) . И тут вы забиваете 4096 нулей по этому адресу. Как будет работать программа после этого не знает ни один компилятор.

Что интересно, тут у вас всё хорошо:

Код:
memset(&msgBlock, 0, sizeof(TMsgBlock));
Если у вас размер пакета динамический, то и выделять память нужно динамически. Ни или во всяком случае не запихивать нечто размером в 4КБ в нечто, размером 300 байт.
"Когда приходит положенное время, человек перестаёт играть в пинбол. Только и всего."
veniside вне форума Ответить с цитированием
Старый 18.05.2011, 16:27   #7
-LeV-
Пользователь
 
Регистрация: 05.06.2010
Сообщений: 29
По умолчанию

Если передача идет по TCP то он разбивает пакеты как хочет, так что

Код:
int remain = sizeof(RecvData);
    while(remain)
    {
      remain -= recv(s, (char*)(&RecvData+sizeof(RecvData)-remain), remain, 0);
    }
-LeV- вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Как передать структуру в поток при _beginthread Ksardas13 Общие вопросы C/C++ 2 10.03.2012 05:00
Как передать заголовки в php через CURL sergeiqwe PHP 1 07.11.2010 21:08
Работа программы через сеть - ошибка Socket Error #11004 ??? $T@LKER Помощь студентам 2 30.07.2010 14:20
Как правильно передать через ссылку двумерный динамический массив? amerhant Общие вопросы C/C++ 2 21.04.2010 23:50
Как передать POST data через запрос в веб-приложение Anticrim Java для Web (EE, Servlet, JSP, Tomcat, Spring MVC) 3 03.10.2007 18:19