Exemple #1
0
//ハンドルの解放
//解放後handleはNULLに
void UPNP_SERVER_CloseHandle(
	UPNP_SERVER_HANDLE* handle			//[IN]UPNP_SERVER_CreateHandleの戻り値
)
{
	UPNP_SSDP_HANDLE_ITEM* item = NULL;
	if( handle == NULL ){
		return;
	}
	item = (UPNP_SSDP_HANDLE_ITEM*)*handle;
	if(item != NULL ){
		if( item->notifySendThread != NULL ){
			UPNP_SERVER_StopNotifySend(item);
		}
		if( item->ssdpSrvThread != NULL ){
			_UPNP_SERVER_StopSSDP(item);
		}
		MP_LOCK_CloseHandle(&item->lockHandle);

		SORT_LIST_CloseHandle(&item->ssdpSockList);
		SORT_LIST_CloseHandle(&item->recvThreadList);
		SORT_LIST_CloseHandle(&item->notifyDeviceList);
		
#ifdef _WIN32
		WSACleanup();
#endif
		free(item);
	}
	*handle = NULL;
}
Exemple #2
0
void UPNP_MSEARCH_HANDLE_ITEM_Close(UPNP_MSEARCH_HANDLE_ITEM* item)
{
	if( item == NULL ){
		return;
	}

	if( item->msearchThread != NULL ){
		item->msearchStopFlag = 1;
		MP_THREAD_WaitEndThread(&(item->msearchThread));
	}
	MP_LOCK_CloseHandle(&item->lockHandle);

	SORT_LIST_CloseHandle(&item->resultList);

	free(item);
}
Exemple #3
0
int UPNP_UTIL_CreateUUID(char* uuid, int uuidSize, unsigned short deviceType, unsigned short uniqueID, unsigned short value)
{
	SORT_LIST_HANDLE nicList = NULL;
	MP_NIC_INFO* nicInfo = NULL;
	unsigned int key = 0x45504744;

	if( uuidSize < 37 ){
		return -1;
	}
	
	nicList = MP_NIC_GetNICInfo();
	if( nicList == NULL ){
		return -1;
	}
	nicInfo = (MP_NIC_INFO*)SORT_LIST_GetItemByIndex(nicList, 0);
#ifdef _WIN32
	sprintf_s(uuid, uuidSize, "%08x-%04x-%04x-%04x-%02x%02x%02x%02x%02x%02x",
		key,
		deviceType,
		uniqueID,
		value,
		nicInfo->macAddressValue[0],
		nicInfo->macAddressValue[1],
		nicInfo->macAddressValue[2],
		nicInfo->macAddressValue[3],
		nicInfo->macAddressValue[4],
		nicInfo->macAddressValue[5]
	);
#else;
	sprintf(uuid, "%08X-%04X-%04X-%04X-%02X%02X%02X%02X%02X%02X",
		key,
		deviceType,
		uniqueID,
		value,
		nicInfo->macAddressValue[0],
		nicInfo->macAddressValue[1],
		nicInfo->macAddressValue[2],
		nicInfo->macAddressValue[3],
		nicInfo->macAddressValue[4],
		nicInfo->macAddressValue[5]
	);
#endif

	SORT_LIST_CloseHandle(&nicList);

	return 1;
}
Exemple #4
0
void UPNP_SSDP_NOTIFY_DEVICE_INFO_Delete(void* item)
{
	UPNP_SSDP_NOTIFY_DEVICE_INFO* info = (UPNP_SSDP_NOTIFY_DEVICE_INFO*)item;
	if( info == NULL ){
		return ;
	}

	if( info->uuid != NULL ){
		free(info->uuid);
	}
	if( info->locationUri != NULL ){
		free(info->locationUri);
	}

	SORT_LIST_CloseHandle(&info->urnList);

	free(item);
}
Exemple #5
0
void HTTP_REQUEST_HEADER_Delete(void* item)
{
	HTTP_REQUEST_HEADER* info = (HTTP_REQUEST_HEADER*)item;
	if( info == NULL ){
		return ;
	}

	if( info->method != NULL ){
		free(info->method);
	}
	if( info->uri != NULL ){
		free(info->uri);
	}
	if( info->version != NULL ){
		free(info->version);
	}
	if( info->headerList != NULL ){
		SORT_LIST_CloseHandle(&info->headerList);
	}
	free(item);
}
Exemple #6
0
int UPNP_SERVER_SendNotifyAlive(UPNP_SSDP_HANDLE_ITEM* handle, UPNP_SSDP_NOTIFY_DEVICE_INFO* devInfo)
{
	int ret = 0;
	int urnCount = 0;
	char* urn = NULL;
	int i=0;
	int j=0;
	char sendMsg[2048] = "";
	SORT_LIST_HANDLE nicList = NULL;
	int nicCount = 0;
	MP_NIC_INFO* nicInfo = NULL;

	SOCKET sock;
	struct sockaddr_in addr;
	struct sockaddr_in send_addr;
	int opt = 1;
	unsigned long ipAdrr = 0;
	int ttl = 3;

	char sendMsgFormat[] = "NOTIFY * HTTP/1.1\r\nHOST: 239.255.255.250:1900\r\nCACHE-CONTROL: max-age = 1800\r\nLOCATION: http://%s:%d%s\r\nNT: %s\r\nNTS: ssdp:alive\r\nSERVER: %s\r\nUSN: %s\r\n\r\n";
	char nt[512] = "";
	char usn[512] = "";
	char ua[128] = "";

	if( handle == NULL || devInfo == NULL){
		ret = -1;
		goto Err_End;
	}

	nicList = MP_NIC_GetNICInfo();
	if( nicList == NULL ){
		ret = -3;
		goto Err_End;
	}

	UPNP_UTIL_GetUserAgent(ua, sizeof(ua));

	nicInfo = MP_NIC_INFO_New();
	nicInfo->ipv4 = (char*)malloc(strlen("127.0.0.1")+1);
	nicInfo->name = (char*)malloc(strlen("Loop Back")+1);
	nicInfo->macAddress = (char*)malloc(strlen("00-00-00-00-00-00")+1);
#ifdef _WIN32
	strcpy_s(nicInfo->ipv4 , strlen("127.0.0.1")+1, "127.0.0.1");
	strcpy_s(nicInfo->name , strlen("Loop Back")+1, "Loop Back");
	strcpy_s(nicInfo->macAddress, strlen("00-00-00-00-00-00")+1, "00-00-00-00-00-00");
#else
	strcpy(nicInfo->ipv4 , "127.0.0.1");
	strcpy(nicInfo->name , "Loop Back");
	strcpy(nicInfo->macAddress , "00-00-00-00-00-00");
#endif
	memset(nicInfo->macAddressValue, 0, 6);
	SORT_LIST_AddItem(nicList, nicInfo->name, nicInfo);

	nicCount = SORT_LIST_GetCount(nicList);
	if( nicCount <= 0 ){
		ret = -4;
		goto Err_End;
	}

	memset((char*)&send_addr, 0, sizeof(struct sockaddr_in)); 
	send_addr.sin_family = AF_INET;
	send_addr.sin_addr.s_addr = inet_addr("239.255.255.250");
	send_addr.sin_port = htons(1900);

	//見つかったNIC全てで送信
	for( i=0; i<nicCount; i++ ){
		nicInfo = (MP_NIC_INFO*)SORT_LIST_GetItemByIndex(nicList, i);

		ipAdrr = inet_addr(nicInfo->ipv4);

		memset((char*)&addr, 0, sizeof(struct sockaddr_in)); 
		addr.sin_family = AF_INET;
		addr.sin_port = 0;
		addr.sin_addr.S_un.S_addr = ipAdrr;

		sock = socket(AF_INET, SOCK_DGRAM, 0);
		if( sock < 0 ){
			continue;
		}

		if( setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (const char *)&opt, sizeof(opt)) < 0 ){
			closesocket(sock);
			continue;
		}

		if(setsockopt(sock, IPPROTO_IP, IP_MULTICAST_IF, (char *)&ipAdrr, sizeof(ipAdrr)) < 0){
			closesocket(sock);
			continue;
		}
		if(setsockopt(sock, IPPROTO_IP, IP_MULTICAST_TTL, (char *)&ttl, sizeof(ttl)) < 0){
			closesocket(sock);
			continue;
		}

		//upnp:rootdevice
		memset(sendMsg, 0, 2048);
#ifdef _WIN32
		sprintf_s(usn, sizeof(usn), "uuid:%s::upnp:rootdevice", devInfo->uuid);
		sprintf_s(sendMsg, sizeof(sendMsg), sendMsgFormat,
			nicInfo->ipv4,
			devInfo->locationPort,
			devInfo->locationUri,
			"upnp:rootdevice",
			ua,
			usn
			);
#else
		sprintf(usn, "uuid:%s::upnp:rootdevice", devInfo->uuid);
		sprintf(sendMsg, sendMsgFormat,
			nicInfo->ipv4,
			devInfo->locationPort,
			devInfo->locationUri,
			"upnp:rootdevice",
			ua,
			usn
			);
#endif
		if( sendto(sock, sendMsg, (int)strlen(sendMsg), 0, (struct sockaddr *)&send_addr, sizeof(send_addr)) < 0 ){
			closesocket(sock);
			continue;
		}

		//uuid:device-UUID
		memset(sendMsg, 0, 2048);
#ifdef _WIN32
		sprintf_s(nt, sizeof(usn), "uuid:%s", devInfo->uuid);
		sprintf_s(usn, sizeof(usn), "uuid:%s", devInfo->uuid);
		sprintf_s(sendMsg, sizeof(sendMsg), sendMsgFormat,
			nicInfo->ipv4,
			devInfo->locationPort,
			devInfo->locationUri,
			nt,
			ua,
			usn
			);
#else
		sprintf(nt, "uuid:%s", devInfo->uuid);
		sprintf(usn, "uuid:%s", devInfo->uuid);
		sprintf(sendMsg, sendMsgFormat,
			nicInfo->ipv4,
			devInfo->locationPort,
			devInfo->locationUri,
			nt,
			ua,
			usn
			);
#endif
		if( sendto(sock, sendMsg, (int)strlen(sendMsg), 0, (struct sockaddr *)&send_addr, sizeof(send_addr)) < 0 ){
			closesocket(sock);
			continue;
		}

		//urn:schemas-upnp-org:device:deviceType:ver
		//urn:schemas-upnp-org:service:serviceType:ver
		urnCount = SORT_LIST_GetCount(devInfo->urnList);
		for( j=0; j<urnCount; j++ ){
			urn = (char*)SORT_LIST_GetItemByIndex(devInfo->urnList, j);
			memset(sendMsg, 0, 2048);
#ifdef _WIN32
			sprintf_s(nt, sizeof(usn), "%s", urn);
			sprintf_s(usn, sizeof(usn), "uuid:%s::%s", devInfo->uuid, urn);
			sprintf_s(sendMsg, sizeof(sendMsg), sendMsgFormat,
				nicInfo->ipv4,
				devInfo->locationPort,
				devInfo->locationUri,
				nt,
				ua,
				usn
				);
#else
			sprintf(nt, "%s", urn);
			sprintf(usn, "uuid:%s::%s", devInfo->uuid, urn);
			sprintf(sendMsg, sendMsgFormat,
				nicInfo->ipv4,
				devInfo->locationPort,
				devInfo->locationUri,
				nt,
				ua,
				usn
				);
#endif
			if( sendto(sock, sendMsg, (int)strlen(sendMsg), 0, (struct sockaddr *)&send_addr, sizeof(send_addr)) < 0 ){
				break;
			}
		}
		closesocket(sock);
	}

Err_End:
	if( nicList != NULL){
		SORT_LIST_CloseHandle(&nicList);
	}
	return ret;
}
Exemple #7
0
void UPNP_SERVER_SSDPMSearchMsg(UPNP_SSDP_RECV_PARAM* param, HTTP_REQUEST_HEADER* httpReqHeader, char* src)
{
	UPNP_SSDP_RECV_PARAM* info = NULL;
	UPNP_SSDP_HANDLE_ITEM* handle = NULL;
	UPNP_MSEARCH_REQUEST_INFO* requestParam = NULL;
	SORT_LIST_HANDLE resDeviceList = NULL;
	HTTP_HEADER_FIELD_INFO* headerItem = NULL;
	UPNP_MSEARCH_RES_DEV_INFO* devInfo = NULL;
	int length = 0;
	int i=0;
	char nowTime[30] = "";
	char resMsg[1024] = "";
	char buff[256] = "";
	SOCKET sendSock;
	char ua[128] = "";

	info = (UPNP_SSDP_RECV_PARAM*)param;
	if( info == NULL ){
		return ;
	}
	handle = (UPNP_SSDP_HANDLE_ITEM*)info->ssdpHandle;
	if( handle == NULL ){
		return ;
	}
	if( handle->msearchCallBack == NULL ){
		return ;
	}
	requestParam = UPNP_MSEARCH_REQUEST_INFO_New();
	resDeviceList = SORT_LIST_CreateHandle(1, SORT_LIST_COMPDEF_stricmp, NULL, UPNP_MSEARCH_RES_DEV_INFO_Delete);

	//リクエスト全体
	length = (int)strlen(param->recvData);
	requestParam->res = (char*)malloc(length+1);
#ifdef _WIN32
	strcpy_s(requestParam->res, length+1, param->recvData);
#else
	strcpy(requestParam->res, param->recvData);
#endif
	//ヘッダをコピー
	headerItem = (HTTP_HEADER_FIELD_INFO*)SORT_LIST_FindItem(httpReqHeader->headerList, (void*)"HOST" );
	if( headerItem != NULL ){
		length = (int)strlen(headerItem->value);
		requestParam->host = (char*)malloc(length+1);
#ifdef _WIN32
		strcpy_s(requestParam->host, length+1, headerItem->value);
#else
		strcpy(requestParam->host, headerItem->value);
#endif
	}
	headerItem = (HTTP_HEADER_FIELD_INFO*)SORT_LIST_FindItem(httpReqHeader->headerList, (void*)"MAN" );
	if( headerItem != NULL ){
		length = (int)strlen(headerItem->value);
		requestParam->man = (char*)malloc(length+1);
#ifdef _WIN32
		strcpy_s(requestParam->man, length+1, headerItem->value);
#else
		strcpy(requestParam->man, headerItem->value);
#endif
	}
	headerItem = (HTTP_HEADER_FIELD_INFO*)SORT_LIST_FindItem(httpReqHeader->headerList, (void*)"MX" );
	if( headerItem != NULL ){
		length = (int)strlen(headerItem->value);
		requestParam->mx = (char*)malloc(length+1);
#ifdef _WIN32
		strcpy_s(requestParam->mx, length+1, headerItem->value);
#else
		strcpy(requestParam->mx, headerItem->value);
#endif
	}
	headerItem = (HTTP_HEADER_FIELD_INFO*)SORT_LIST_FindItem(httpReqHeader->headerList, (void*)"ST" );
	if( headerItem != NULL ){
		length = (int)strlen(headerItem->value);
		requestParam->st = (char*)malloc(length+1);
#ifdef _WIN32
		strcpy_s(requestParam->st, length+1, headerItem->value);
#else
		strcpy(requestParam->st, headerItem->value);
#endif
	}
	headerItem = (HTTP_HEADER_FIELD_INFO*)SORT_LIST_FindItem(httpReqHeader->headerList, (void*)"USER-AGENT" );
	if( headerItem != NULL ){
		length = (int)strlen(headerItem->value);
		requestParam->userAgent = (char*)malloc(length+1);
#ifdef _WIN32
		strcpy_s(requestParam->userAgent, length+1, headerItem->value);
#else
		strcpy(requestParam->userAgent, headerItem->value);
#endif
	}
	//通知
	handle->msearchCallBack(requestParam, handle->msearchCallBackParam, resDeviceList);

	//MP_Sleep(500);

	MP_TIME_GetNowTime_RFC1123(nowTime, sizeof(nowTime));
	//デバイスごとに送信
	for(i=0; i<SORT_LIST_GetCount(resDeviceList); i++ ){
		devInfo = (UPNP_MSEARCH_RES_DEV_INFO*)SORT_LIST_GetItemByIndex(resDeviceList, i);

		if( param->nicInfo->ipv4 == NULL || devInfo->uri == NULL ){
			continue;
		}
#ifdef _WIN32
		strcpy_s(resMsg, sizeof(resMsg), "HTTP/1.1 200 OK\r\n");

		sprintf_s(buff, sizeof(buff), "CACHE-CONTROL: max-age=%d\r\n", devInfo->max_age);
		strcat_s(resMsg, sizeof(resMsg), buff);

//		sprintf_s(buff, sizeof(buff), "DATE: %s\r\n", nowTime);
//		strcat_s(resMsg, sizeof(resMsg), buff);

		sprintf_s(buff, sizeof(buff), "LOCATION: http://%s:%d%s\r\n", param->nicInfo->ipv4, devInfo->port, devInfo->uri);
		strcat_s(resMsg, sizeof(resMsg), buff);

		sprintf_s(buff, sizeof(buff), "ST: %s\r\n", requestParam->st);
		strcat_s(resMsg, sizeof(resMsg), buff);

		if(devInfo->usn != NULL ){
			sprintf_s(buff, sizeof(buff), "USN: %s\r\n", devInfo->usn);
			strcat_s(resMsg, sizeof(resMsg), buff);
		}

		UPNP_UTIL_GetUserAgent(ua, sizeof(ua));
		sprintf_s(buff, sizeof(buff), "SERVER: %s\r\n", ua);
		strcat_s(resMsg, sizeof(resMsg), buff);

		strcat_s(resMsg, sizeof(resMsg), "EXT:\r\n");

		strcat_s(resMsg, sizeof(resMsg), "\r\n");
#else
		strcpy(resMsg, "HTTP/1.1 200 OK\r\n");

		sprintf(buff, "CACHE-CONTROL: max-age=%d\r\n", devInfo->max_age);
		strcat(resMsg, buff);

//		sprintf(buff, "DATE: %s\r\n", nowTime);
//		strcat(resMsg, buff);

		sprintf(buff, "LOCATION: http://%s:%d%s\r\n", param->nicInfo->ipv4, devInfo->port, devInfo->uri);
		strcat(resMsg, buff);

		sprintf(buff, "ST: %s\r\n", requestParam->st);
		strcat(resMsg, buff);

		if(devInfo->usn != NULL ){
			sprintf(buff, "USN: %s\r\n", devInfo->usn);
			strcat(resMsg, buff);
		}

		UPNP_UTIL_GetUserAgent(ua, sizeof(ua));
		sprintf_s(buff, sizeof(buff), "SERVER: %s\r\n", ua);
		strcat_s(resMsg, sizeof(resMsg), buff);
		strcat(resMsg, "EXT:\r\n");

		strcat(resMsg,  "\r\n");
#endif
		//レスポンス送信
		MP_Sleep(10);
		sendSock = socket(AF_INET, SOCK_DGRAM, 0);
		//OutputDebugStringA(resMsg);
		sendto(sendSock, resMsg, (int)strlen(resMsg), 0, (struct sockaddr *)&param->client, sizeof(param->client));
		shutdown(sendSock, SD_BOTH);
		closesocket(sendSock);
	}

	SORT_LIST_CloseHandle(&resDeviceList);
	UPNP_MSEARCH_REQUEST_INFO_Delete(requestParam);
}
Exemple #8
0
int _UPNP_SERVER_StartSSDP(UPNP_SSDP_HANDLE_ITEM* handle)
{
	int ret = 0;
	struct sockaddr_in addr;
	struct ip_mreq_source mreq;
	int opt = 1;
	SORT_LIST_HANDLE nicList = NULL;
	int listCount = 0;
	MP_NIC_INFO* nicInfo = NULL;
	int success = 0;
	int i=0;
	UPNP_SSDP_SOCKET_ITEM* sockItem = NULL;


	if( handle == NULL ){
		return -1;
	}
	if( handle->ssdpSrvThread != NULL ){
		return -2;
	}

	nicList = MP_NIC_GetNICInfo();
	if( nicList == NULL ){
		ret = -3;
		goto Err_End;
	}

	nicInfo = MP_NIC_INFO_New();
	nicInfo->ipv4 = (char*)malloc(strlen("127.0.0.1")+1);
	nicInfo->name = (char*)malloc(strlen("Loop Back")+1);
	nicInfo->macAddress = (char*)malloc(strlen("00-00-00-00-00-00")+1);
#ifdef _WIN32
	strcpy_s(nicInfo->ipv4 , strlen("127.0.0.1")+1, "127.0.0.1");
	strcpy_s(nicInfo->name , strlen("Loop Back")+1, "Loop Back");
	strcpy_s(nicInfo->macAddress, strlen("00-00-00-00-00-00")+1, "00-00-00-00-00-00");
#else
	strcpy(nicInfo->ipv4 , "127.0.0.1");
	strcpy(nicInfo->name , "Loop Back");
	strcpy(nicInfo->macAddress , "00-00-00-00-00-00");
#endif
	memset(nicInfo->macAddressValue, 0, 6);
	SORT_LIST_AddItem(nicList, nicInfo->name, nicInfo);

	listCount = SORT_LIST_GetCount(nicList);
	if( listCount <= 0 ){
		ret = -4;
		goto Err_End;
	}
	//見つかったNIC全てで受信できるようにする
	for( i=0; i<listCount; i++ ){
		nicInfo = (MP_NIC_INFO*)SORT_LIST_GetItemByIndex(nicList, i);

		sockItem = UPNP_SSDP_SOCKET_ITEM_New();
		sockItem->nicInfo = MP_NIC_INFO_Clone(nicInfo);

		//SSDP待ち受けポート(UDP 1900)の作成
		sockItem->ssdpSock = socket(AF_INET, SOCK_DGRAM, 0);
		if( sockItem->ssdpSock < 0 ){
			ret = -5;
			UPNP_SSDP_SOCKET_ITEM_Delete(sockItem);
			goto Err_End;
		}

		memset((char*)&addr, 0, sizeof(struct sockaddr_in)); 
		addr.sin_family = AF_INET;
		addr.sin_addr.s_addr = htonl(INADDR_ANY);
		addr.sin_port = htons(1900);

		if( setsockopt(sockItem->ssdpSock, SOL_SOCKET, SO_REUSEADDR, (const char *)&opt, sizeof(opt)) < 0 ){
			ret = -6;
			UPNP_SSDP_SOCKET_ITEM_Delete(sockItem);
			goto Err_End;
		}
		if( bind(sockItem->ssdpSock, (struct sockaddr *)&addr, sizeof(addr)) < 0 ){
			ret = -7;
			UPNP_SSDP_SOCKET_ITEM_Delete(sockItem);
			goto Err_End;
		}

		memset(&mreq, 0, sizeof(mreq));
		mreq.imr_interface.S_un.S_addr = INADDR_ANY;
		mreq.imr_sourceaddr.S_un.S_addr = inet_addr(nicInfo->ipv4);
		mreq.imr_multiaddr.S_un.S_addr = inet_addr("239.255.255.250");

		if(setsockopt(sockItem->ssdpSock, IPPROTO_IP, IP_ADD_MEMBERSHIP, (char *)&mreq, sizeof(mreq)) < 0){
			UPNP_SSDP_SOCKET_ITEM_Delete(sockItem);
		}else{
			SORT_LIST_AddItem(handle->ssdpSockList, sockItem->nicInfo->name, sockItem);
		}
	}
	if( SORT_LIST_GetCount(handle->ssdpSockList) <= 0 ){
		ret =  -8;
		goto Err_End;
	}

	handle->ssdpSrvStopFlag = 0;
	handle->ssdpSrvThread = MP_THREAD_BegineThread(UPNP_SERVER_SSDPThread, handle);

	if( nicList != NULL){
		SORT_LIST_CloseHandle(&nicList);
	}
	return 0;

Err_End:
	if( nicList != NULL){
		SORT_LIST_CloseHandle(&nicList);
	}
	SORT_LIST_Clear(handle->ssdpSockList);

	return ret;
}