Other Parts Discussed in Thread: CC3100
To work around the bugs and lack of mDNS query support. I have devised a workaround and would welcome opinions and suggestions regarding this solution.
This is not a just a concept, I have coded this have it working. I can now discover the IP address of my CC3000 device through a query method.
What I have done is use one of the CC3000 sockets as a Broadcast UDP Listener on a certain port. If it receives a broadcast packet to this certain port, it then sends a response back to the IP address that the broadcast packet came from.
Then the client application can either use the source address of the UDP packet or the data contained in the UDP packet (which contains the IP address).
This solution will only work when attempting to find a CC3000 device that is on the same subnet.
Here is the code I use on the CC3000 device side
// Broadcast variables
Int nbytesmDNS;
Int statusmDNS;
Int selectResmDNS;
Long lSocketmDNS;
fd_set readSetmDNS;
timeval timeoutmDNS;
sockaddr_in sLocalAddrmDNS;
sockaddr_in client_addrmDNS;
sockaddr smDNSAddr;
socklen_t addrlenmDNS = sizeof(client_addrmDNS);
------
/* Create broadcast socket 0.0.0.0 */
lSocketmDNS = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
if (lSocketmDNS == -1) {
System_printf("socket failed\n");
Task_exit();
}
int DISCOVER_PORT = 8111; //This can be any port
smDNSAddr.sa_family = AF_INET;
smDNSAddr.sa_data[0] = (DISCOVER_PORT & 0xFF00)>> 8;
smDNSAddr.sa_data[1] = (DISCOVER_PORT & 0x00FF);
smDNSAddr.sa_data[2] = 0;
smDNSAddr.sa_data[3] = 0;
smDNSAddr.sa_data[4] = 0;
smDNSAddr.sa_data[5] = 0;
statusmDNS = bind(lSocketmDNS, &smDNSAddr, sizeof(sockaddr));
if (statusmDNS < 0) {
System_printf("bind failed\n");
closesocket(lSocketmDNS);
Task_exit();
}
memset(&timeoutmDNS, 0, sizeof(timeval));
timeoutmDNS.tv_sec = 0;
timeoutmDNS.tv_usec = 100000;
------------
while (flag){
FD_ZERO(&readSetmDNS);
FD_SET(lSocketmDNS, &readSetmDNS);
// Calling select() before recvfrom() is currently recommended when using the CC3000
// It is also a workaround for a potential race in the CC3000 internals.
selectResmDNS = select(lSocketmDNS + 1, &readSetmDNS, NULL, NULL, &timeoutmDNS);
if ((selectResmDNS > 0) && (selectResmDNS != -1)) {
if(FD_ISSET(lSocketmDNS, &readSetmDNS)) {
nbytesmDNS = recvfrom(lSocketmDNS, buffer, UDPPACKETSIZE, 0,
(sockaddr*)&client_addrmDNS, &addrlenmDNS);
if (nbytesmDNS > 0) {
/* Echo the data back */
int count;
// Send a bunch of UDP response packets, as the sendto() is buggy, and does not send everytime.
for (count=0; count < 10; count++)
{
sendto(lSocketmDNS, (char *)ipRecvd, sizeof((char *)ipRecvd), 0, (sockaddr*)&client_addrmDNS,
sizeof(client_addrmDNS));
}
}
else {
flag = FALSE;
}
}
}
This sample code will be simple to insert in the TI-RTOS UDPEcho example.
So there you have it, I welcome any feedback or opinion regarding this workaround.
Glenn.