Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Receiving multicast packets WINCE500 bug

184 views
Skip to first unread message

eric

unread,
Dec 15, 2009, 4:25:54 AM12/15/09
to
Hello,

i can not receive multicast packets on windows ce 5.0 (and even not on
WINCE600).
Sending multicast packets works fine. And if i run the code from my
wince receiver on a
WINXP machine i can receive these packets. So it is a problem in
windows ce.

I read posts from other developers with same problem. But there is no
solution. You can read here:
# http://forum.soft32.com/pda/Multicast-group-address-bug-WinCE-ftopict65376.html
# http://groups.google.com/group/microsoft.public.windowsce.app.development/browse_thread/thread/b56a4973efa56dbe/b6e9b76e066a8673
# http://www.eggheadcafe.com/software/aspnet/29584779/multicast-group-address-b.aspx

You can find the original demo source code from Microsoft (CE 3.0)
here (which is not working):
http://msdn.microsoft.com/en-us/library/aa454073.aspx


So if anybody has an idea what goes on here and how to receive packets
from a multicast group please tell me.

Thanks,

eric.

eric

unread,
Dec 15, 2009, 5:53:45 AM12/15/09
to

R. de Gravelaine

unread,
Dec 15, 2009, 6:52:41 AM12/15/09
to

Hello,

Windows CE is not necessarily wrong, but the network driver can be, if
it is not able to process multicast address lists correctly.
Unfortunately, you will not have the answer unless you debug this
driver, or the BSP provider does it for you.

Remi


eric a �crit :

eric

unread,
Dec 15, 2009, 7:37:23 AM12/15/09
to
Thanks for your your reply.

I use the NDISUIO driver to query the ethernet controller (DM9000).
I do to set the multicast MAC to the driver:

BYTE byMAC[] = {0x04,0x00,0x00,0x5E,0x00,0x01};
TCHAR *pT = L"DM9CE1";
BYTE *p = (BYTE*) malloc(sizeof(NDISUIO_SET_OID)+2);
NDISUIO_SET_OID *pO = (NDISUIO_SET_OID*) p;
pO->Oid = OID_802_3_MULTICAST_LIST;
pO->ptcDeviceName = pT;
memcpy(p+8,&byMAC,6);
DWORD dwRetIo = DeviceIoControl( hNUIO,IOCTL_NDISUIO_SET_OID_VALUE,
p, sizeof
(NDISUIO_SET_OID)+2,
NULL,
0,&dwRet, NULL);

I can query with IOCTL_NDISUIO_QUERY_OID_VALUE and get the MAC i set.

And i write NDIS_PACKET_TYPE_GROUP | NDIS_PACKET_TYPE_MULTICAST |
NDIS_PACKET_TYPE_PROMISCUOUS
with the OID_GEN_CURRENT_PACKET_FILTER and IOCTL_NDISUIO_SET_OID_VALUE
to the DM9000 ethernet controller.

What do you think.
Are you able to receive multicast packets on WINCE ?

Thanks,

eric.

Paul G. Tobey [eMVP]

unread,
Dec 15, 2009, 9:42:24 AM12/15/09
to
There are restrictions on what actually works, but yes, I can receive
multicast packets on Windows CE. As noted, probably, in the past posts that
you've seen, you can't have A, B, C, or D in the IP A.B.C.D be 0 or, if it
remember right, 1. These are known issues and just have never become
high-priority enough for MS to fix, I guess. You can start a support
incident, and when they find it's a bug, ask for a QFE. I've done that
before with no luck, but more requests equal more priority.

Paul T.

"eric" <daniel...@yahoo.de> wrote in message
news:91d2f8b7-2c57-4f80...@d21g2000yqn.googlegroups.com...

eric

unread,
Dec 15, 2009, 10:09:24 AM12/15/09
to
Hi,

Paul T i saw you where very active regarding this issue (you are most
of the time very busy ;-)).
I tried several IPs. Without any luck.

You wrote (posted on Wednesday, March 28, 2007 12:44 PM):

>>I have a simple WinSock C program that will work fine if the group number
>>passes the tests of a.0.0.c where c doesn't have bit zero or one set, but
>>will fail reliably if any of those requirements is not met. [...]

So if I use a IP 234.0.0.8 it should work. Or do you mean that B,C,D
should be kind of
234.12.12.12 ? So B,C,D are not 0 or not 1 (and also the lowest two
bit are not 1).

Could you say what IP works for you?


Thanks,

eric.

R. de Gravelaine

unread,
Dec 15, 2009, 10:33:12 AM12/15/09
to
At the first glance, I see nothing wrong with your code.

I am sure I can receive multicast packets on Wince 6.0 R2 (QFE up to
April 2009), at least SSDP M-SEARCH messages, multicasted to
239.255.255.250:1900.
My network driver is the E100BEX, for Intel E100 chips.

As you can break into NDISUIO, you should be able to check whether
incoming multicast packets are propagated by the driver to upper layers
or not. I don't remember exactly how to to that by I know it is feasible.

Good luck.
Remi


eric a �crit :

eric

unread,
Dec 15, 2009, 12:26:00 PM12/15/09
to
Thanks for respond.

Now i set the filter to _ALL_MULTICAST and i can see debugmessages
from the ethernet controller (dm9000) when
i start sending multicast packets. So the controller gets the packets.
I have to investigate why the packets are not getting directed
to the upper layers through wince.

But if anyone has ideas please tell me.

Thanks,
eric.

Paul G. Tobey [ eMVP ]

unread,
Dec 16, 2009, 6:50:01 PM12/16/09
to
I'm *way* off-site for the new couple of days, but I did post one working
multicast group that I was able to use successfully a while back. Maybe you
can search on "multicast" in the groups using Google Groups and see if you
can spot the thread...

Paul T.

"eric" wrote:

> .
>

eric

unread,
Dec 17, 2009, 5:55:20 AM12/17/09
to
Paul T,

i tried with:

#define RECV_IP_ADDR "224.0.0.103"
#define DEST_PORT 45000

but also no luck.
It is strange to me that there are such major problems regarding
multicast in wince.

eric.

Paul G. Tobey [ eMVP ]

unread,
Dec 18, 2009, 11:09:01 AM12/18/09
to
Well, your group number does not meet the specifications on the bug that we
talked about before. A.B.C.D, remember. B and C must be zero and D must not
have bits 0 or 1 set. 103 is 0x67, so both bits 0 and 1 are set.

I've previously used 224.0.0.4, I see from the archives, successfully, and I
think that .103 should work, too. If setting the right group number doesn't
work, maybe back off on the low-level stuff you're doing and try to just use
WinSock to configure everything.

socket( DGRAM )
bind( htons( yourport ) )
setsockopt( IPPROTO_IP, IP_ADD_MEMBERSHIP, buffer containing 224.0.0.4 )
recvfrom() or recv()
sendto() or send()

That's all that should be required in a normal program.

Paul T.

"eric" wrote:

> .
>

eric

unread,
Dec 18, 2009, 11:47:17 AM12/18/09
to
I use the sample code here: http://msdn.microsoft.com/en-us/library/aa454073.aspx

I am afraid it does not work.
Paul T could you send me your test code please. I am going crazy on
that issue.

It is very important to me to get that running.

Thank you very much so far,

eric.

R. de Gravelaine

unread,
Dec 18, 2009, 11:59:02 AM12/18/09
to
Hi Paul,

How can you explain that UPnP's multicast address 239.255.255.250 used
for SSDP works, at least in CE 6.0 R2?
Where did you get the A.0.0.X rule from? From the source code of an
older version or from MS?

There is a strange comment and code in the SSDP code
(Private\Servers\Upnp\Ssdp\Core\socket.cpp) when it comes to open the
multicast socket:

// Bind to adapter index to work around week host model of TCPIP stack
WSAIoctl(socketSSDP, SIO_INDEX_BIND, &dwMulticastInterfaceIndex,
sizeof(dwMulticastInterfaceIndex), NULL, 0, &dw, NULL, NULL);

Do you think this can be of some use for the OP?

Remi

Paul G. Tobey [eMVP] a �crit :

Paul G. Tobey [eMVP]

unread,
Dec 19, 2009, 10:05:13 AM12/19/09
to
No. I ran a few experiments and found something generally like the 'rule' I
ended up with there, then found a bug report from someone else and verified
that it seemed to match the code. I haven't grabbed the source code of CE6
for comparison. My guess on UPnP would be that the protocol stack from
hardware up to application code is different than for the IP Multicast case.
I seem to remember the bug being in WinSock...

I don't have any CE6 devices to play with. Someone could definitely dig
into that call and what it does. It seems like it could, at least, point to
a way to fix, if the bug is still present.

Paul T.

"R. de Gravelaine" <g_r_a_v_e_...@aton-sys.fr> wrote in message
news:OI0AmNAg...@TK2MSFTNGP04.phx.gbl...

Paul G. Tobey [eMVP]

unread,
Dec 19, 2009, 10:18:36 AM12/19/09
to
Here's the basic multicast code. It's certainly nothing special:
-----
// IPMulticast.cpp : Defines the entry point for the application.
//

#include "stdafx.h"
#include "IPMulticast.h"
#include <commctrl.h>

#define DOWINSOCK2

#ifdef DOWINSOCK2
#include <winsock2.h>
#include <ws2tcpip.h>
#else
#include <winsock.h>
#endif
#include <tchar.h>

#define MAX_LOADSTRING 100
#define DEST_PORT 6633
#define RECEIVE_TERMINATE_EVENT _T( "TerminateMCReceiveThread" )

// Global Variables:
HINSTANCE hInst; // The current instance
HWND hwndCB; // The command bar handle
HWND hWndMain;
HWND loghWnd;

// Global variable associated with multicast.

struct ip_mreq mreq; // Used in adding or dropping
// multicasting addresses.
bool joined = false; // true if we are in a group; false, otherwise

SOCKADDR_IN local_sin; // The local socket address.
SOCKADDR_IN recv_sin; // Holds the source address upon
// recvfrom function returns.

SOCKET Sock = INVALID_SOCKET; // Datagram socket.

// Thread bits.
HANDLE receiveTerminateE = NULL;
HANDLE receiveThreadH = NULL;

// Forward declarations of functions included in this code module:
ATOM MyRegisterClass (HINSTANCE, LPTSTR);
BOOL InitInstance (HINSTANCE, int);
LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK About (HWND, UINT, WPARAM, LPARAM);

void LeaveMulticast()
{
TCHAR szError[ 512 ];
if ( joined )
{
// Terminate the receive thread.
OutputDebugString( _T( "Signaling event\r\n" ) );
SetEvent( receiveTerminateE );
OutputDebugString( _T( "Waiting for thread exit\r\n" ) );
WaitForSingleObject( receiveThreadH, INFINITE );
OutputDebugString( _T( "Thread exit confirmed\r\n" ) );
CloseHandle( receiveThreadH );
CloseHandle( receiveTerminateE );
receiveTerminateE = NULL;
receiveThreadH = NULL;

// Leave the group.
if (setsockopt (Sock,
IPPROTO_IP,
IP_DROP_MEMBERSHIP,
(char FAR *)&mreq,
sizeof (mreq)) == SOCKET_ERROR)
{
wsprintf (szError, TEXT("setsockopt (leave) failed! Error: %d"),
WSAGetLastError ());
MessageBox (NULL, szError, TEXT("Error"), MB_OK);
}

joined = false;
}
}

int WINAPI WinMain( HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow)
{
MSG msg;
HACCEL hAccelTable;
TCHAR szError[ 512 ];

// Perform application initialization:
if (!InitInstance (hInstance, nCmdShow))
{
return FALSE;
}

WSADATA WSAData;

// Initialize Winsock.
if (WSAStartup (WINSOCK_VERSION, &WSAData) != 0)
{
wsprintf (szError, TEXT("WSAStartup failed! Error: %d"),
WSAGetLastError ());
MessageBox (NULL, szError, TEXT("Error"), MB_OK);
return FALSE;
}

// Set up the socket. We aren't associated with a multicast
// group, after this, but the socket will be ready to be
// associated.
if ((Sock = socket (AF_INET, SOCK_DGRAM, 0)) == INVALID_SOCKET)
{
wsprintf (szError, TEXT("Allocating socket failed! Error: %d"),
WSAGetLastError ());
MessageBox (NULL, szError, TEXT("Error"), MB_OK);
return FALSE;
}

// Fill out the local socket's address information.
local_sin.sin_family = AF_INET;
local_sin.sin_port = htons (DEST_PORT);
local_sin.sin_addr.s_addr = htonl (INADDR_ANY);

// Associate the local address with Sock.
if (bind (Sock,
(struct sockaddr FAR *) &local_sin,
sizeof (local_sin)) == SOCKET_ERROR)
{
wsprintf (szError, TEXT("Binding socket failed! Error: %d"),
WSAGetLastError ());
MessageBox (NULL, szError, TEXT("Error"), MB_OK);
closesocket (Sock);
return FALSE;
}

// ... The socket is now ready to be associated.

// Get the accelerators.
hAccelTable = LoadAccelerators(hInstance, (LPCTSTR)IDC_IPMULTICAST);

// Main message loop:
while (GetMessage(&msg, NULL, 0, 0))
{
if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}

// Leave the multicast group.
LeaveMulticast();

// Disable receiving on Sock before closing it.
shutdown (Sock, 0x00);

// Close Sock.
closesocket (Sock);

WSACleanup ();

return msg.wParam;
}

//
// FUNCTION: MyRegisterClass()
//
// PURPOSE: Registers the window class.
//
// COMMENTS:
//
// It is important to call this function so that the application
// will get 'well formed' small icons associated with it.
//
ATOM MyRegisterClass(HINSTANCE hInstance, LPTSTR szWindowClass)
{
WNDCLASS wc;

wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = (WNDPROC) WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInstance;
wc.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_IPMULTICAST));
wc.hCursor = 0;
wc.hbrBackground = (HBRUSH) GetStockObject(WHITE_BRUSH);
wc.lpszMenuName = 0;
wc.lpszClassName = szWindowClass;

return RegisterClass(&wc);
}

//
// FUNCTION: InitInstance(HANDLE, int)
//
// PURPOSE: Saves instance handle and creates main window
//
// COMMENTS:
//
// In this function, we save the instance handle in a global variable and
// create and display the main program window.
//
BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{
TCHAR szTitle[MAX_LOADSTRING]; // The title bar text
TCHAR szWindowClass[MAX_LOADSTRING]; // The window class name

hInst = hInstance; // Store instance handle in our global variable
// Initialize global strings
LoadString(hInstance, IDC_IPMULTICAST, szWindowClass, MAX_LOADSTRING);
MyRegisterClass(hInstance, szWindowClass);

LoadString(hInstance, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);
hWndMain = CreateWindow(szWindowClass, szTitle, WS_VISIBLE,
CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, NULL, NULL,
hInstance, NULL);

if (!hWndMain)
{
return FALSE;
}

ShowWindow(hWndMain, nCmdShow);
UpdateWindow(hWndMain);
if (hwndCB)
CommandBar_Show(hwndCB, TRUE);

return TRUE;
}

TCHAR joinIP[ 64 ]; // New IP address to join.
TCHAR sendMsg[ 512 ]; // Actual message to send.

// Function to wait for receipt of multicast message.
BOOL WaitForMulticast( TCHAR *m, int mlen, timeval timeout )
{
int iRecvLen;
TCHAR szError[ 512 ];

fd_set readfs;
FD_ZERO( &readfs );
FD_SET( Sock, &readfs );

if ( select( 1, &readfs, NULL, NULL, &timeout ) == 1 )
{
char *szMessageA = new char[ mlen ];
iRecvLen = sizeof (recv_sin);

// See how much data this shows. ????
unsigned long siz;
if ( ioctlsocket( Sock, FIONREAD, &siz ) == SOCKET_ERROR )
{
OutputDebugString( _T( "Socket error in ioctlsocket\r\n" ) );
}
else
{
if ( !siz )
{
OutputDebugString( _T( "Sure enough, a zero-length packet!\r\n" ) );
}
}

// Receive data from the multicasting group server. Make sure
// to null-terminate!
if (recvfrom( Sock,
szMessageA,
mlen-1,
0,
(struct sockaddr FAR *) &recv_sin,
&iRecvLen) == SOCKET_ERROR)
{
wsprintf (szError, TEXT("recvfrom failed! Error: %d"),
WSAGetLastError ());
MessageBox (NULL, szError, TEXT("Error"), MB_OK);

delete [] szMessageA;
return FALSE;
}
else
{
// Null-terminate.
szMessageA[ iRecvLen ] = 0;

// Convert the ASCII string to a Unicode string.
MultiByteToWideChar( CP_ACP, 0, szMessageA, iRecvLen,
m, mlen );
m[ iRecvLen ] = 0; // null terminate the string.

delete [] szMessageA;
return TRUE;
}
}
return FALSE;
}

// Mesage handler for the Join dialog box.
LRESULT CALLBACK Join( HWND hDlg, UINT message, WPARAM wParam,
LPARAM lParam)
{
RECT rt, rt1;
int DlgWidth, DlgHeight; // dialog width and height in pixel units
int NewPosX, NewPosY;

switch (message)
{
case WM_INITDIALOG:
// trying to center the dialog
if (GetWindowRect(hDlg, &rt1))
{
GetClientRect(GetParent(hDlg), &rt);
DlgWidth = rt1.right - rt1.left;
DlgHeight = rt1.bottom - rt1.top ;
NewPosX = (rt.right - rt.left - DlgWidth)/2;
NewPosY = (rt.bottom - rt.top - DlgHeight)/2;

// if the dialog box is larger than the physical
// screen
if (NewPosX < 0) NewPosX = 0;
if (NewPosY < 0) NewPosY = 0;
SetWindowPos(hDlg, 0, NewPosX, NewPosY,
0, 0, SWP_NOZORDER | SWP_NOSIZE);
}

// Set the initial value of the edit field.
SetDlgItemText( hDlg, IDC_MULTICAST_ADDR, joinIP );
SetFocus( GetDlgItem( hDlg, IDC_MULTICAST_ADDR ) );
return TRUE;

case WM_COMMAND:
if ( LOWORD(wParam) == IDOK )
{
// Verify the IP address.
GetDlgItemText( hDlg, IDC_MULTICAST_ADDR,
joinIP, sizeof( joinIP ) / sizeof( joinIP[0] ) );

unsigned a, b, c, d;

if ( _stscanf( joinIP, _T( "%u.%u.%u.%u" ), &a, &b, &c, &d ) != 4 )
{
MessageBeep( -1 );
SetFocus( GetDlgItem( hDlg, IDC_MULTICAST_ADDR ) );
// ????
}
else if ( ( a > 255 ) || ( a < 0 ) ||
( b > 255 ) || ( b < 0 ) ||
( c > 255 ) || ( c < 0 ) ||
( d > 255 ) || ( d < 0 ) )
{
MessageBeep( -1 );
SetFocus( GetDlgItem( hDlg, IDC_MULTICAST_ADDR ) );
// ????
}
else
{
EndDialog(hDlg, LOWORD(wParam));
return TRUE;
}
}
else if ( LOWORD(wParam) == IDCANCEL )
{
EndDialog(hDlg, LOWORD(wParam));
return TRUE;
}
break;
}
return FALSE;
}

DWORD WINAPI ReceiveThread( LPVOID lpParameter )
{
OutputDebugString( _T( "Entering receive thread\r\n" ) );

// Wait for the socket to be ready on the receive end.
HANDLE ev = CreateEvent( NULL, FALSE, FALSE,
RECEIVE_TERMINATE_EVENT );
while( WaitForSingleObject( ev, 5 ) == WAIT_TIMEOUT )
{
// Call select and return data, if any.
timeval timeout;
timeout.tv_sec = 0;
timeout.tv_usec = 5000;

TCHAR msg[ 512 ];

if ( WaitForMulticast( msg, sizeof( msg ) / sizeof( msg[0] ),
timeout ) )
{
OutputDebugString( _T( "Receive thread got message\r\n" ) );

// Do something useful with the message.
SendMessage( hWndMain, WM_USER+10, 0, (LPARAM)&msg[ 0 ] );
}
}

OutputDebugString( _T( "Leaving receive thread\r\n" ) );

return 0;
}

void JoinMulticast( HWND hWnd )
{
TCHAR szError[ 512 ];

// Display dialog for specifying group ID.
if ( DialogBox( hInst, (LPCTSTR)IDD_JOINDLG, hWnd,
(DLGPROC)Join ) == IDOK )
{
// If we are already in a group, leave it before moving to the
// new one.
if ( joined )
{
LeaveMulticast();
}

// Join a specified multicast group.
char joinIPs[ 64 ];
WideCharToMultiByte( CP_ACP, 0, joinIP, -1,
joinIPs, sizeof( joinIPs ), NULL, NULL );
mreq.imr_multiaddr.s_addr = inet_addr( joinIPs );
mreq.imr_interface.s_addr = INADDR_ANY;

if (setsockopt (Sock,
IPPROTO_IP,
IP_ADD_MEMBERSHIP,
(char FAR *)&mreq,
sizeof (mreq)) == SOCKET_ERROR)
{
wsprintf (szError, TEXT("setsockopt (join) failed! Error: %d"),
WSAGetLastError ());
MessageBox (NULL, szError, TEXT("Error"), MB_OK);
}
else
{
joined = true;

// Set the Time-to-Live of the multicast.
int iOptVal = 2;
if (setsockopt (Sock,
IPPROTO_IP,
IP_MULTICAST_TTL,
(char FAR *)&iOptVal,
sizeof (int)) == SOCKET_ERROR)
{
wsprintf (szError, TEXT("setsockopt (ttl) failed! Error: %d"),
WSAGetLastError ());
MessageBox (NULL, szError, TEXT("Error"), MB_OK);
}

// Create termination event for thread, if not already
// done.
if ( receiveTerminateE == NULL )
{
receiveTerminateE = CreateEvent( NULL, FALSE, FALSE,
RECEIVE_TERMINATE_EVENT );
}

// Start a new receive thread.
receiveThreadH = CreateThread( NULL, 0, ReceiveThread,
receiveTerminateE, 0, NULL );
}
}
}

// Mesage handler for the Send dialog box.
LRESULT CALLBACK Send( HWND hDlg, UINT message, WPARAM wParam,
LPARAM lParam)
{
RECT rt, rt1;
int DlgWidth, DlgHeight; // dialog width and height in pixel units
int NewPosX, NewPosY;

switch (message)
{
case WM_INITDIALOG:
// trying to center the dialog
if (GetWindowRect(hDlg, &rt1))
{
GetClientRect(GetParent(hDlg), &rt);
DlgWidth = rt1.right - rt1.left;
DlgHeight = rt1.bottom - rt1.top ;
NewPosX = (rt.right - rt.left - DlgWidth)/2;
NewPosY = (rt.bottom - rt.top - DlgHeight)/2;

// if the dialog box is larger than the physical
// screen
if (NewPosX < 0) NewPosX = 0;
if (NewPosY < 0) NewPosY = 0;
SetWindowPos(hDlg, 0, NewPosX, NewPosY,
0, 0, SWP_NOZORDER | SWP_NOSIZE);
}
return TRUE;

case WM_COMMAND:
if ( LOWORD(wParam) == IDOK )
{
// Get the message.
GetDlgItemText( hDlg, IDC_SEND_MSG,
sendMsg, sizeof( sendMsg ) / sizeof( sendMsg[0] ) );

EndDialog(hDlg, LOWORD(wParam));
return TRUE;
}
else if ( LOWORD(wParam) == IDCANCEL )
{
EndDialog(hDlg, LOWORD(wParam));
return TRUE;
}
break;
}
return FALSE;
}

BOOL SendMulticast( HWND hWnd )
{
TCHAR szError[ 512 ];

if ( !joined )
{
MessageBeep( -1 );
return FALSE;
}

// Get the message to send from the user.
if ( DialogBox( hInst, (LPCTSTR)IDD_SENDDLG, hWnd,
(DLGPROC)Send ) == IDOK )
{
char szMessage[ 512 ];
WideCharToMultiByte( CP_ACP, 0, sendMsg, -1,
szMessage, sizeof( szMessage ), NULL, NULL );

// Actually send a multicast message to the current multicast
// group.
SOCKADDR_IN dest_sin;

dest_sin.sin_family = AF_INET;
dest_sin.sin_port = htons( DEST_PORT );
dest_sin.sin_addr.s_addr = mreq.imr_multiaddr.s_addr;

if (sendto (Sock,
szMessage,
// strlen (szMessage) + 1,
strlen( szMessage ),
0,
(struct sockaddr FAR *) &dest_sin,
sizeof (dest_sin)) == SOCKET_ERROR)
{
wsprintf (szError, TEXT("sendto failed! Error: %d"),
WSAGetLastError ());
MessageBox (NULL, szError, TEXT("Error"), MB_OK);
return FALSE;
}
else
{
return TRUE;
}
}
return FALSE;
}

//
// FUNCTION: WndProc(HWND, unsigned, WORD, LONG)
//
// PURPOSE: Processes messages for the main window.
//
// WM_COMMAND - process the application menu
// WM_PAINT - Paint the main window
// WM_DESTROY - post a quit message and return
//
//
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM
lParam)
{
int wmId, wmEvent;

switch (message)
{
case WM_COMMAND:
wmId = LOWORD(wParam);
wmEvent = HIWORD(wParam);
// Parse the menu selections:
switch (wmId)
{
case IDM_HELP_ABOUT:
DialogBox(hInst, (LPCTSTR)IDD_ABOUTBOX, hWnd, (DLGPROC)About);
break;
case IDM_FILE_EXIT:
DestroyWindow(hWnd);
break;
case IDM_MULTICAST_JOIN:
JoinMulticast(hWnd);
break;
case IDM_MULTICAST_SEND:
SendMulticast(hWnd);
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
break;
case WM_CREATE:
hwndCB = CommandBar_Create(hInst, hWnd, 1);
CommandBar_InsertMenubar(hwndCB, hInst, IDM_MENU, 0);
CommandBar_AddAdornments(hwndCB, 0, 0);

// Get client area.
RECT r;
GetClientRect( hWnd, &r );

// Create a multiline edit to fill our content area.
loghWnd = CreateWindow( _T( "EDIT" ), _T( "" ),
ES_MULTILINE | ES_AUTOVSCROLL | ES_READONLY |
WS_CHILD | WS_BORDER | WS_VISIBLE,
0, CommandBar_Height( hwndCB ), r.right, r.bottom,
hWnd, NULL, hInst, NULL );
if ( loghWnd == NULL )
{
OutputDebugString( _T( "Error creating log window\r\n" ) );
}
SetFocus( loghWnd );// Give some indication that the edit box
// is there.
break;
case WM_DESTROY:
CommandBar_Destroy(hwndCB);
PostQuitMessage(0);
break;

case WM_USER+10:
// Special message sent when data received from socket.
// Append the data to the log window.
TCHAR s[ 512 ];
GetWindowText( loghWnd, s, sizeof( s ) / sizeof( s[0] ) );
_tcscat( s, (TCHAR*)lParam );
SetWindowText( loghWnd, s );
break;

default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
return 0;
}

// Mesage handler for the About box.
LRESULT CALLBACK About(HWND hDlg, UINT message, WPARAM wParam, LPARAM
lParam)
{
RECT rt, rt1;
int DlgWidth, DlgHeight; // dialog width and height in pixel units
int NewPosX, NewPosY;

switch (message)
{
case WM_INITDIALOG:
// trying to center the About dialog
if (GetWindowRect(hDlg, &rt1)) {
GetClientRect(GetParent(hDlg), &rt);
DlgWidth = rt1.right - rt1.left;
DlgHeight = rt1.bottom - rt1.top ;
NewPosX = (rt.right - rt.left - DlgWidth)/2;
NewPosY = (rt.bottom - rt.top - DlgHeight)/2;

// if the About box is larger than the physical screen
if (NewPosX < 0) NewPosX = 0;
if (NewPosY < 0) NewPosY = 0;
SetWindowPos(hDlg, 0, NewPosX, NewPosY,
0, 0, SWP_NOZORDER | SWP_NOSIZE);
}
return TRUE;

case WM_COMMAND:
if ((LOWORD(wParam) == IDOK) || (LOWORD(wParam) == IDCANCEL))
{
EndDialog(hDlg, LOWORD(wParam));
return TRUE;
}
break;
}
return FALSE;
}
-----
Paul T.

"eric" <daniel...@yahoo.de> wrote in message

news:50a12147-7e2c-4767...@n35g2000yqm.googlegroups.com...

R. de Gravelaine

unread,
Dec 19, 2009, 10:46:00 AM12/19/09
to
Hi,

> My guess on UPnP would be that the protocol stack from
> hardware up to application code is different than for the IP Multicast case.
> I seem to remember the bug being in WinSock...

Not sure of that... After a quick look at the code, SSDP appears to use
vanilla sockets.
I don't whether the source code for UPnP/SSDP is available in CE 5 but,
if I were the OP, I would try to reproduce the way MS does create its
multicast socket.

Remi

Paul G. Tobey [eMVP]

unread,
Dec 19, 2009, 4:03:05 PM12/19/09
to
I'll try to get to looking at the CE6 code and comparing to CE5 soon...but I
agree. Known-good code is safer than just working from the documentation.

Paul T.

"R. de Gravelaine" <g_r_a_v_e_...@aton-sys.fr> wrote in message

news:%23azQdJM...@TK2MSFTNGP04.phx.gbl...

eric

unread,
Jan 11, 2010, 11:11:22 AM1/11/10
to
The problem comes from Active Sync.

When not connecting to Active Sync receiving multicast packets is
working without any problems.
When Active Sync connects it runs into NDIS:

***NDIS*** (c, 452) ==>ndisMRequest***NDIS*** (c, 500) ndisMRequest:
Queueing request 0xd15c5250***NDIS*** (c, 875)
==>ndisMDoRequests***NDIS*** (c, 902) ndisMDoRequests: Processing
Request 0xd15c5250, Oid 0x1010103***NDIS*** (c, 1255)
==>ndisMSetInformaiton***NDIS*** (10, 958)
==>ndisMSetMulticastList***NDIS*** (10, 1013) ndisMSetMulticastList:
too many addresses***NDIS*** (10, 1122) <==ndisMSetMulticastList:
0xc0010009***NDIS*** (c, 1287) <==ndisMSetInformaiton: 0xc0010009

because of the "too many addresses" result registering multicast
membership with setsocketoptions does not work (but setsocketoptions
returns no error).
I am going to find a solution for that problem within the ndis.dll.

Anyone with an idea??

eric.

eric

unread,
Jan 11, 2010, 11:37:27 AM1/11/10
to

eric

unread,
Jan 11, 2010, 12:11:41 PM1/11/10
to
EthCreateFilter

MSDN (http://msdn.microsoft.com/en-us/library/ms955466.aspx):
This function is called by a network adapter driver.
It creates and initializes an Ethernet filter library database
associated with one network interface card (network adapter).

MaximumMulticastAddresses
Specifies the maximum number of multicast addresses supported by
the filter.

==> as result ndisMSetMulticastList runs into:
if (Request->DATA.SET_INFORMATION.InformationBufferLength/
ETH_LENGTH_OF_ADDRESS > Miniport->EthDB->MaxMulticastAddresses) //
MaxMulticastAddresses is 0
{
//
// too many multicast addresses
//
...
}

so no more multicast addresses could be installed.

eric.

0 new messages