Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > C/C++: Сети > Передача потока данных по сети


Автор: Incinerated 1.4.2008, 08:53
Есть видео-поток:
Код

PAVISTREAM ppstream;
AVIStreamOpenFromFile(&ppstream, "D:\\downloads\\1408.avi", streamtypeVIDEO, 0, 0, NULL);

можно ли его сразу передавать его кусками через сокеты? если можно то как?
Если нельзя, то можно ли сами кадры передавать, т.е. дополним этот код следующим:
Код

AVISTREAMINFO info;
PGETFRAME frame;

ZeroMemory (&info, sizeof(info));
AVIStreamInfo(ppstream, &info, sizeof(info));

memset(&bi, 0, sizeof(BITMAPINFO));
bi.bmiHeader.biSize = sizeof(bi.bmiHeader);
bi.bmiHeader.biWidth = info.rcFrame.right - info.rcFrame.left; //желаемая ширина
bi.bmiHeader.biHeight = info.rcFrame.bottom - info.rcFrame.top; //желаемая высота
bi.bmiHeader.biBitCount = 24;
bi.bmiHeader.biPlanes = 1;
bi.bmiHeader.biCompression = BI_RGB;
bi.bmiHeader.biSizeImage = bi.bmiHeader.biWidth * bi.bmiHeader.biHeight * 4;

frame = ::AVIStreamGetFrameOpen(ppstream,&bi.bmiHeader);


Можно ли теперь передавать по сети кадры на другой комп?

Автор: korian 1.4.2008, 12:11
а в чем проблема? берем байты по адресу frame и передаем.
только лучше, наверно, будет файл кусками передавать, а на той стороне уже декодировать (файл то все-таки сжат - меньше передавать).

Автор: Incinerated 1.4.2008, 12:32
Цитата(korian @ 1.4.2008,  12:11)
а в чем проблема? берем байты по адресу frame и передаем.
только лучше, наверно, будет файл кусками передавать, а на той стороне уже декодировать (файл то все-таки сжат - меньше передавать).

есть 2 вопроса:
1. Как можно по байтово передавать frame.
2. Будет ли проигрыватся на клиентской стороне кусок файла? Ну я буду передавать кусками, он будет принимать, и будет ли он отображать корректно картинку? и вообще сможет ли он открыть файл. Но с файлом мне кажется будет пинг большой, т.к. скорее всего его нужно будет сохранять и переоткрывать функцией AVIStreamOpenFromFile(), а работа с жестким диском  всегда медленнее чем с оперативкой, а у меня клиентов может быть хоть 20...
Есть ли какие нибудь выходы из этой ситуации? 

Автор: opjox 1.4.2008, 13:30
Цитата(Incinerated @  1.4.2008,  12:32 Найти цитируемый пост)
1. Как можно по байтово передавать frame.

Вам для этого будет достаточно обычных сокетов. По ним полно подробной информации в инете, поиски почти не займут время, а изучить их просто за 1-2 дня (для решения нужной вам задачи). 

Автор: Incinerated 1.4.2008, 13:38
Цитата(opjox @ 1.4.2008,  13:30)
Цитата(Incinerated @  1.4.2008,  12:32 Найти цитируемый пост)
1. Как можно по байтово передавать frame.

Вам для этого будет достаточно обычных сокетов. По ним полно подробной информации в инете, поиски почти не займут время, а изучить их просто за 1-2 дня (для решения нужной вам задачи).

работу с сокетами я знаю. Я не знаю как мне frame привести к нужному виду...Есть предположение - использовать memcpy...

Автор: opjox 1.4.2008, 13:55
С AVI прежде не работал, сейчас немого погуглив наткнулся на http://pmg.org.ru/nehe/nehe35.htm , а в нем на такой код (мои коментарии в /**/):

Код

pgf=AVIStreamGetFrameOpen(pavi, NULL); /* pgf тоже, что и у вас frame */
...
...
void GrabAVIFrame(int frame) // Захват кадра
{
  LPBITMAPINFOHEADER lpbi;  // Содержит BitmapInfoHeader
  // Получение данных из потока
  lpbi = (LPBITMAPINFOHEADER)AVIStreamGetFrame(pgf, frame); /* вот он опять всплывает*/
  // Указатель на данные возвращенные AVIStreamGetFrame
  // (Пропуск заголовка для получения указателя на данные)
  pdata=(char *)lpbi+lpbi->biSize+lpbi->biClrUsed * sizeof(RGBQUAD); /* а вот и те данные, которые вроде и надо отсылать*/
  // Преобразование информации в нужный нам формат
  DrawDibDraw (hdd, hdc, 0, 0, 256, 256, lpbi, pdata, 0, 0, width, height, 0);
...
...


P.S. в ту статью не вчитывался, возможно выводы мои поспешны, но направление вроде верное

Автор: korian 1.4.2008, 23:52
Цитата(Incinerated @  1.4.2008,  11:32 Найти цитируемый пост)
1. Как можно по байтово передавать frame.

извеняюсь, не доглядел...
надо еще AVIStreamGetFrame вызвать, а потом можно передавать (т.е. передаем по фреймам)

Цитата(Incinerated @  1.4.2008,  11:32 Найти цитируемый пост)
Но с файлом мне кажется будет пинг большой, т.к. скорее всего его нужно будет сохранять и переоткрывать функцией AVIStreamOpenFromFile(), а работа с жестким диском  всегда медленнее чем с оперативкой, а у меня клиентов может быть хоть 20

диск жалко, а сетевуху нет?  smile 

или воспользоваться AVIStreamRead.
я, правда, хз как оно все работает, сам этим не занимался, читаю MSDN... 
если AVIStreamRead читает данные в сжатом формате - то вообще замечательно.
на сервере открываем файл, читаем его с помощью AVIStreamRead. передаем данные клиенту.
на клиенте создаем стрим (CreateEditableStream) и пишим туда, что пришло с сокета (AVIStreamWrite). а потом открываем фреймы.

Автор: Incinerated 7.4.2008, 13:04
Цитата(korian @ 1.4.2008,  23:52)
или воспользоваться AVIStreamRead.
я, правда, хз как оно все работает, сам этим не занимался, читаю MSDN... 
если AVIStreamRead читает данные в сжатом формате - то вообще замечательно.
на сервере открываем файл, читаем его с помощью AVIStreamRead. передаем данные клиенту.
на клиенте создаем стрим (CreateEditableStream) и пишим туда, что пришло с сокета (AVIStreamWrite). а потом открываем фреймы.

AVIStreamRead вроде бы что-то делает, т.е. преобразует в нужный мне формат, чтобы передать... А вот как назад это вопроизвести, пускай даже не по сети, просто на одиночном компьюетер, вот это проблема...Может я чего - то не понимаю или что нибудь не так делаю.
Код

AVIStreamRead(pvideo, AVIStreamStart(pvideo), FramesPerSec,
                  0,0,&L1,&L2);
BYTE *pdata;
pdata = (BYTE*)malloc(L1);
AVIStreamRead(pvideo,0,L2,pdata,L1,NULL,NULL);
sendbuf = (char*)pdata;

вот теоретически в pdata должна быть видео информация о авишке, т.е. тоже самое что и AviStreamInfo... Насколько я знаю структуру видео файлов, но при попытке преобразовать это в AVISTREAMINFO ничего не происходит, записывается NULL.
Вообщем я вообще расстерялся, как это можно сделать:(...

Автор: korian 7.4.2008, 18:20
Цитата(Incinerated @  7.4.2008,  12:04 Найти цитируемый пост)
т.е. тоже самое что и AviStreamInfo

судя по параметрам это не так.
я так понимаю, на сервере надо вызвать AviStreamInfo, получать от туда данные, передавать эту структуру клиенту
после этого вызывать AVIStreamRead и передавать данные клиенту - это поидее кадры.
на клиенте 
CreateEditableStream - создаем новый стрим
EditStreamSetInfo - записываем инфу о стриме
AVIStreamWrite - записываем кадры.
дальше уже показываем этот стрим...

Автор: Incinerated 8.4.2008, 14:34
Цитата(korian @ 7.4.2008,  18:20)
судя по параметрам это не так.
я так понимаю, на сервере надо вызвать AviStreamInfo, получать от туда данные, передавать эту структуру клиенту
после этого вызывать AVIStreamRead и передавать данные клиенту - это поидее кадры.
на клиенте 
CreateEditableStream - создаем новый стрим
EditStreamSetInfo - записываем инфу о стриме
AVIStreamWrite - записываем кадры.
дальше уже показываем этот стрим...

а на сервере мне что делать?! получается мне всю структуру AVISTREAMINFO разбивать на подполя и передавать каждое поле как число? потому что ка киначе сделать я не знаю... И дальше получается мне нужно вызывать функцию AviStreamRead и результат передавать, так?

Автор: korian 8.4.2008, 14:54
Цитата(Incinerated @  8.4.2008,  13:34 Найти цитируемый пост)
разбивать на подполя и передавать каждое поле как число

проще сделать так:
AVISTREAMINFO asi;
...
send(..., &asi, sizeof(asi));

можно было б уже попробывать  smile  не замарачиваясь с сокетам, а просто хотя бы создать копию AVI файла, используя только функции AVI.
а вообще чтобы понять как правильно передавать AVI, надо знать как правильно его отображать и как правильно его редактировать например, если вы из 2-х AVI файлов сможете склеить один новый, который будет показывать:
1-я секунда: первая секунда файла1
2-я секунда: первая секунда файла2
3-я секунда: вторая секунда файла1
...
то имху проблем с передачей у вас не будет, так что есть смысл покопать в эту сторону.

Автор: Incinerated 11.4.2008, 21:13
вообщем не очень все получается. Вот код.
Код

BYTE *pdata;
PAVISTREAM pvideo;
AVISTREAMINFO video_info;
BITMAPINFO bi;

  AVIFileInit();
  AVIStreamOpenFromFile(&pvideo, "D:\\downloads\\Øðåê 1.avi", streamtypeVIDEO, 0, 0, NULL);

ZeroMemory (&video_info, sizeof(video_info));
AVIStreamInfo(pvideo, &video_info, sizeof(video_info));


memset(&bi, 0, sizeof(BITMAPINFO));
bi.bmiHeader.biSize = sizeof(bi.bmiHeader);
bi.bmiHeader.biWidth = video_info.rcFrame.right - video_info.rcFrame.left; //æåëàåìàÿ øèðèíà
bi.bmiHeader.biHeight = video_info.rcFrame.bottom - video_info.rcFrame.top; //æåëàåìàÿ âûñîòà
bi.bmiHeader.biBitCount = 24;
bi.bmiHeader.biPlanes = 1;
bi.bmiHeader.biCompression = BI_RGB;
bi.bmiHeader.biSizeImage = bi.bmiHeader.biWidth * bi.bmiHeader.biHeight * 3;

pdata = (BYTE*)malloc(bi.bmiHeader.biSizeImage);
//считываю в pdata 40 кадр
int i = AVIStreamRead(pvideo,40,1,pdata,sizeof(pdata)+bi.bmiHeader.biSizeImage,NULL,NULL);

//пытаюсь создать поток, как вы говорили, он создается, но
//AVIStreamWrite возвращает ошибку, т.е. не может записать
PAVISTREAM pv1;

i = CreateEditableStream(&pv1,NULL);
i = EditStreamSetInfo(pv1,&video_info,sizeof(video_info));

i = AVIStreamWrite(pv1,0,1,pdata,bi.bmiHeader.biSizeImage,AVIIF_KEYFRAME,NULL,NULL);

HDC hdc = GetDC(Form1->Handle);
//код чтобы получить доступ к кадрам из потока, но т.к. не работает, ниже его не использую
PGETFRAME frame;
frame = ::AVIStreamGetFrameOpen(pv1,&bi.bmiHeader);
BITMAPINFO *getframe;
getframe = (LPBITMAPINFO)::AVIStreamGetFrame(frame,0);
//пытаюсь воспроизвести сам буфер считанный pdata, но на форме отображается вместо
//40 кадра черный прямоугольник, в чем проблема понять не могу
StretchDIBits(hdc,         
        0,                     
        0,                     
        bi.bmiHeader.biWidth,         
        bi.bmiHeader.biHeight,         
        0,                     
        0,                     
        bi.bmiHeader.biWidth,                     
        bi.bmiHeader.biHeight,         
                                pdata,                 
        (LPBITMAPINFO)getframe,
        DIB_PAL_COLORS,
    SRCCOPY);

вроде почти как бы получилось, а вроде и ничего, т.к. черный квадрат из буфера никак не пойдет, да и в стрим не записывается почему то, даже если получится pdata воспроизвести, то как записать в стрим не понятно. Может есть какие нибудь идеи?

Автор: korian 12.4.2008, 23:57
вот шо у меня получилось:
Код

    HRESULT result;

    PAVISTREAM pvideo;
    result = AVIStreamOpenFromFile(&pvideo, _T("g:\\svolochi(rus).avi"), streamtypeVIDEO, 0, 0, NULL);

    AVISTREAMINFO video_info = {};
    result = AVIStreamInfo(pvideo, &video_info, sizeof(video_info));

    BYTE pFormat[1024];
    LONG formatSize = sizeof(pFormat);
    result = AVIStreamReadFormat(pvideo, 0, pFormat, &formatSize);

    BYTE *buffer;
    LONG bufSize = 10240000;
    buffer = new BYTE [bufSize];
    LONG bytes, samples, samploffset;
    samploffset = 0;
    while (1)
    {
        PAVIFILE newFile;
        result = AVIFileOpen(&newFile, _T("tmp.avi"), OF_WRITE | OF_CREATE, NULL);
        PAVISTREAM pv1;
        video_info.dwLength = 0;
        result = AVIFileCreateStream(newFile, &pv1, &video_info);
        assert(result == S_OK);
        AVIFileRelease(newFile);
        assert(result == S_OK);
        result = AVIStreamSetFormat(pv1, 0, pFormat, formatSize);
        assert(result == S_OK);

        const int minSamplesRead = 1000;

        LONG pos = AVIStreamFindSample(pvideo, samploffset + minSamplesRead, FIND_KEY | FIND_NEXT);
        if (pos == -1)
            break;
        for (int i = samploffset; i < pos; ++i)
        {
            result = AVIStreamRead(pvideo,i,1,buffer, bufSize,&bytes,&samples);
            assert(result == S_OK);
            result = AVIStreamWrite(pv1, i-samploffset, 1, buffer, bytes, AVIIF_KEYFRAME, &samples, &bytes);
            assert(result == S_OK);
        }

        BITMAPINFO bi = {};
        bi.bmiHeader.biSize = sizeof(bi.bmiHeader);
        bi.bmiHeader.biWidth = video_info.rcFrame.right - video_info.rcFrame.left;
        bi.bmiHeader.biHeight = video_info.rcFrame.bottom - video_info.rcFrame.top;
        bi.bmiHeader.biBitCount = 24;
        bi.bmiHeader.biPlanes = 1;
        bi.bmiHeader.biCompression = BI_RGB;
        bi.bmiHeader.biSizeImage = bi.bmiHeader.biWidth * bi.bmiHeader.biHeight * 4;

        int a = AVIERR_UNSUPPORTED;
        a = AVIERR_FILEREAD;
        a = AVIERR_FILEOPEN;

        PGETFRAME frame;
        frame = ::AVIStreamGetFrameOpen(pv1, &bi.bmiHeader);
        for (int i = 0; i < pos - samploffset; ++i)
        {
            BITMAPINFO *getframe;
            getframe = (LPBITMAPINFO)::AVIStreamGetFrame(frame,i);

            SetDIBitsToDevice(dc.m_hDC,
                0,                     
                0,                     
                bi.bmiHeader.biWidth,         
                bi.bmiHeader.biHeight,         
                0,                     
                0,                     
                0,
                bi.bmiHeader.biHeight,
                getframe + sizeof(bi),
                getframe,
                DIB_RGB_COLORS);
        }
        result = AVIStreamGetFrameClose(frame);
        assert(result == S_OK);
        int num = AVIStreamRelease(pv1);

        samploffset = pos;
    }

    AVIStreamRelease(pvideo);

    delete [] buffer;


но вообще, это как-то тупа наверно.
каждый раз открывать/закрывать файл... имху должен быть способ лучше.

Автор: Incinerated 13.4.2008, 14:46
вообщем вот что в итоге получилось, но во-первых показывает черный прямоугольник, и во-вторых каждый раз на разном этапе на строчке
result = AVIStreamWrite(pv1, z-stru1.samploffset, 1, stru.buffer, stru.bytes, AVIIF_KEYFRAME, NULL, NULL);
вылетает красная ошибка. Почему я понять не могу.
Вот сервер:
Код

  LONG bufSize = 10240000;
  HRESULT result;
  PAVISTREAM pvideo;
  AVISTREAMINFO video_info = {};
  BITMAPINFO bi;
  struct data{
    BYTE *buffer;
    LONG bytes;
  };
  data stru;
  struct format{
    LONG formatSize;
    BYTE pFormat[1024];
  };
  format tmp;
  struct position{
    LONG pos, samploffset;
  };
  position stru1;

  WSADATA wsaData;
  sockaddr_in RecvAddr;
  int Port = 27015;
  char RecvBuf[1024];
  int  BufLen = 1024;
  sockaddr_in SenderAddr;
  int SenderAddrSize = sizeof(SenderAddr);

  //-----------------------------------------------

  if (WSAStartup(MAKEWORD(2,2), &wsaData) != 0){
    MessageBox(NULL,"Íåâîçìîæíî èíèöèàëèçèðîâàòü ðàáîòó ñ DLL","Îøèáêà",MB_OK);
  }

  //-----------------------------------------------
  SOCKET RecvSocket;
  RecvSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
  if (RecvSocket == INVALID_SOCKET) {
    MessageBox(NULL,"Íåâîçìîæíî ñîçäàòü ñîêåò " + WSAGetLastError(),"Îøèáêà",MB_OK);
    WSACleanup();
  }

  RecvAddr.sin_family = AF_INET;
  RecvAddr.sin_port = htons(Port);
  RecvAddr.sin_addr.s_addr = htonl(INADDR_ANY);

  if (bind(RecvSocket, (SOCKADDR *) &RecvAddr, sizeof(RecvAddr)) ==  SOCKET_ERROR){
    MessageBox(NULL,"Íåâîçìîæíî ñâÿçàòü ëîêàëüíûé àäðåñ ñ ñîêåòîì " + WSAGetLastError(),"Îøèáêà",MB_OK);
        closesocket(RecvSocket);
        WSACleanup();
    }
  //-----------------------------------------------
    AVIFileInit();
    result = AVIStreamOpenFromFile(&pvideo, "d:\\downloads\\1408.avi", streamtypeVIDEO, 0, 0, NULL);

    result = AVIStreamInfo(pvideo, &video_info, sizeof(video_info));

    tmp.formatSize = sizeof(tmp.pFormat);
    result = AVIStreamReadFormat(pvideo, 0, tmp.pFormat, &tmp.formatSize);


    stru.buffer = new BYTE [bufSize];
    stru1.samploffset = 0;
    
  while (true){
    int j =  recvfrom(RecvSocket,
                      RecvBuf,
                      BufLen,
                      0,
                      (SOCKADDR *)&SenderAddr,
                      &SenderAddrSize);
    sendto(RecvSocket,
          (char*)&video_info, sizeof(video_info),
          0,
          (SOCKADDR *) &SenderAddr,
          sizeof(SenderAddr));
    sendto(RecvSocket,
          (char*)&tmp, sizeof(tmp),
          0,
          (SOCKADDR *) &SenderAddr,
          sizeof(SenderAddr));
    while (1){
        const int minSamplesRead = 1000;

        stru1.pos = AVIStreamFindSample(pvideo, stru1.samploffset + minSamplesRead, FIND_KEY | FIND_NEXT);

        sendto(RecvSocket,
              (char*)&stru1, sizeof(stru1),
              0,
              (SOCKADDR *) &SenderAddr,
              sizeof(SenderAddr));
        for (int i = stru1.samploffset; i < stru1.pos; ++i)
        {
            result = AVIStreamRead(pvideo,i,1,stru.buffer, bufSize,&stru.bytes,NULL);
            assert(result == S_OK);
            j = sendto(RecvSocket,
                    (char*)&stru, sizeof(stru),
                    0,
                    (SOCKADDR *) &SenderAddr,
                    sizeof(SenderAddr));
        }

        stru1.samploffset = stru1.pos;
    }

    AVIStreamRelease(pvideo);

    delete &stru;
}
  //-----------------------------------------------

  closesocket(RecvSocket);

  //-----------------------------------------------

  WSACleanup();

вот клиент
Код

 LONG bufSize = 10240000;
  struct data{
    BYTE *buffer;
    LONG bytes;
  };
  data stru;
  struct format{
    LONG formatSize;
    BYTE pFormat[1024];
  };
  format tmp;
  struct position{
    LONG pos, samploffset;
  };
  position stru1;

  WSADATA wsaData;
  SOCKET SendSocket;
  sockaddr_in RecvAddr;
  int Port = 27015;
  char SendBuf[1024] = "";
  int BufLen = 1024;

  //---------------------------------------------

  WSAStartup(MAKEWORD(2,2), &wsaData);

  //---------------------------------------------

  SendSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);

  //---------------------------------------------
  RecvAddr.sin_family = AF_INET;
  RecvAddr.sin_port = htons(Port);
  RecvAddr.sin_addr.s_addr = inet_addr("127.0.0.1");

  //---------------------------------------------
  sendto(SendSocket,
      SendBuf, 
      BufLen,
      0, 
      (SOCKADDR *) &RecvAddr, 
      sizeof(RecvAddr));
      int s = sizeof(RecvAddr);

  AVISTREAMINFO video_info = {};
  
  int j = recvfrom(SendSocket,
    (char*)&video_info,
    sizeof(video_info),
    0,
    (SOCKADDR *) &RecvAddr,
    &s);

  j = recvfrom(SendSocket,
    (char*)&tmp,
    sizeof(tmp),
    0,
    (SOCKADDR *) &RecvAddr,
    &s);

  HRESULT result;
  AVIFileInit();

  stru.buffer = new BYTE [bufSize];
  while (true){
    PAVIFILE newFile;
    PAVISTREAM pv1;
    result = AVIFileOpen(&newFile, "tmp.avi", OF_WRITE | OF_CREATE, NULL);
    video_info.dwLength = 0;
    result = AVIFileCreateStream(newFile, &pv1, &video_info);
    assert(result == S_OK);
    AVIFileRelease(newFile);
    assert(result == S_OK);
    result = AVIStreamSetFormat(pv1, 0, tmp.pFormat, tmp.formatSize);
    assert(result == S_OK);

    j = recvfrom(SendSocket,
      (char*)&stru1,
      sizeof(stru1),
      0,
      (SOCKADDR *) &RecvAddr,
      &s);
      
    for (int z = stru1.samploffset; z<stru1.pos;++z){
      j = recvfrom(SendSocket,
                  (char*)&stru,
                  sizeof(stru),
                  0,
                  (SOCKADDR *) &RecvAddr,
                  &s);
      result = AVIStreamWrite(pv1, z-stru1.samploffset, 1, stru.buffer, stru.bytes, AVIIF_KEYFRAME, NULL, NULL);
      assert(result == S_OK);
    }
    BITMAPINFO bi = {};
    bi.bmiHeader.biSize = sizeof(bi.bmiHeader);
    bi.bmiHeader.biWidth = video_info.rcFrame.right - video_info.rcFrame.left;
    bi.bmiHeader.biHeight = video_info.rcFrame.bottom - video_info.rcFrame.top;
    bi.bmiHeader.biBitCount = 24;
    bi.bmiHeader.biPlanes = 1;
    bi.bmiHeader.biCompression = BI_RGB;
    bi.bmiHeader.biSizeImage = bi.bmiHeader.biWidth * bi.bmiHeader.biHeight * 4;

    PGETFRAME frame;
    frame = ::AVIStreamGetFrameOpen(pv1, &bi.bmiHeader);
    HDC dc = GetDC(Form1->Handle);
    for (int zz = 0; zz < stru1.pos - stru1.samploffset; ++zz){
        BITMAPINFO *getframe;
        getframe = (LPBITMAPINFO)::AVIStreamGetFrame(frame,zz);

        SetDIBitsToDevice(dc,
            0,
            0,
            bi.bmiHeader.biWidth,
            bi.bmiHeader.biHeight,
            0,
            0,
            0,
            bi.bmiHeader.biHeight,
            getframe + sizeof(bi),
            getframe,
            DIB_RGB_COLORS);
    }
    result = AVIStreamGetFrameClose(frame);
    assert(result == S_OK);
    AVIStreamRelease(pv1);
  }
  closesocket(SendSocket);

  //---------------------------------------------

  WSACleanup();


т.е. вроде бы тоже самое, только разбил на сервер и клиент и ни фига не фурычит:(.

Автор: korian 13.4.2008, 17:34
Цитата(Incinerated @  13.4.2008,  13:46 Найти цитируемый пост)
  struct data{
    BYTE *buffer;
    LONG bytes;
  };


Цитата(Incinerated @  13.4.2008,  13:46 Найти цитируемый пост)
      j = recvfrom(SendSocket,
                  (char*)&stru,
                  sizeof(stru),
                  0,
                  (SOCKADDR *) &RecvAddr,
                  &s);


и как вы хотите, чтобы это работало? надо ж данные передавать, а не адреса.

Автор: Incinerated 13.4.2008, 21:11
Цитата(korian @ 13.4.2008,  17:34)
и как вы хотите, чтобы это работало? надо ж данные передавать, а не адреса.

хм, я не проверял работу  в сети, но вообще информация передается таким образом. video_info нормально передалось, все совпадает, я проверял.
Был изначально такой вариант:
сервер
Код

 result = AVIStreamRead(pvideo,i,1,buffer, bufSize,&bytes,NULL);
            assert(result == S_OK);
            j = sendto(RecvSocket,
                    buffer, bytes,
                    0,
                    (SOCKADDR *) &SenderAddr,
                    sizeof(SenderAddr));

но т.к. я не знал как клиенту узнать размер, т.е. bytes, я передал в вот это:
Код

 result = AVIStreamRead(pvideo,i,1,buffer, bufSize,&bytes,NULL);
            assert(result == S_OK);
            j = sendto(RecvSocket,
                    (char*)&bytes,sizeof(bytes),
                    0,
                    (SOCKADDR *) &SenderAddr,
                    sizeof(SenderAddr));
            j = sendto(RecvSocket,
                    buffer, bytes,
                    0,
                    (SOCKADDR *) &SenderAddr,
                    sizeof(SenderAddr));

и клиент:
Код

  j = recvfrom(SendSocket,
                   (char*)&bytes,
                  sizeof(bytes),
                  0,
                  (SOCKADDR *) &RecvAddr,
                  &s);
  j = recvfrom(SendSocket,
                  buffer,
                  bytes,
                  0,
                  (SOCKADDR *) &RecvAddr,
                  &s);
      result = AVIStreamWrite(pv1, z-stru1.samploffset, 1, buffer, bytes, AVIIF_KEYFRAME, NULL, NULL);

в таком варианте все еще намного хуже, он получает примерно кадров 8 и все, клиент не может принять информацию buffer. Просто функция возвращает -1, а сервер все посылает отлично. И черный прямоугольник тоже был.
И еще вопрос, если не (char*)&bytes, то как еще еще передам(так как я передавал, все принималось отлично, но это возможно потому что я как бы сам себе присылал, хотя если подумать, чужая программа не должна иметь доступ к адресам другой).

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)