コード例 #1
0
ファイル: io_nix.c プロジェクト: xloem/rpavlik-wiiuse
/**
 *	@brief Find a wiimote or wiimotes.
 *
 *	@param wm			An array of wiimote_t structures.
 *	@param max_wiimotes	The number of wiimote structures in \a wm.
 *	@param timeout		The number of seconds before the search times out.
 *
 *	@return The number of wiimotes found.
 *
 *	@see wiimote_connect()
 *
 *	This function will only look for wiimote devices.						\n
 *	When a device is found the address in the structures will be set.		\n
 *	You can then call wiimote_connect() to connect to the found				\n
 *	devices.
 */
int wiiuse_find(struct wiimote_t** wm, int max_wiimotes, int timeout) {
	int device_id;
	int device_sock;
	int found_devices;
	int found_wiimotes;

	/* reset all wiimote bluetooth device addresses */
	for (found_wiimotes = 0; found_wiimotes < max_wiimotes; ++found_wiimotes)
		wm[found_wiimotes]->bdaddr = *BDADDR_ANY;
	found_wiimotes = 0;

	/* get the id of the first bluetooth device. */
	device_id = hci_get_route(NULL);
	if (device_id < 0) {
		perror("hci_get_route");
		return 0;
	}

	/* create a socket to the device */
	device_sock = hci_open_dev(device_id);
	if (device_sock < 0) {
		perror("hci_open_dev");
		return 0;
	}

	inquiry_info scan_info_arr[128];
	inquiry_info* scan_info = scan_info_arr;
	memset(&scan_info_arr, 0, sizeof(scan_info_arr));

	/* scan for bluetooth devices for 'timeout' seconds */
	found_devices = hci_inquiry(device_id, timeout, 128, NULL, &scan_info, IREQ_CACHE_FLUSH);
	if (found_devices < 0) {
		perror("hci_inquiry");
		return 0;
	}

	WIIUSE_INFO("Found %i bluetooth device(s).", found_devices);

	int i = 0;

	/* display discovered devices */
	for (; (i < found_devices) && (found_wiimotes < max_wiimotes); ++i) {
		if ((scan_info[i].dev_class[0] == WM_DEV_CLASS_0) &&
			(scan_info[i].dev_class[1] == WM_DEV_CLASS_1) &&
			(scan_info[i].dev_class[2] == WM_DEV_CLASS_2))
		{
			/* found a device */
			ba2str(&scan_info[i].bdaddr, wm[found_wiimotes]->bdaddr_str);

			WIIUSE_INFO("Found wiimote (%s) [id %i].", wm[found_wiimotes]->bdaddr_str, wm[found_wiimotes]->unid);

			wm[found_wiimotes]->bdaddr = scan_info[i].bdaddr;
			WIIMOTE_ENABLE_STATE(wm[found_wiimotes], WIIMOTE_STATE_DEV_FOUND);
			++found_wiimotes;
		}
	}

	close(device_sock);
	return found_wiimotes;
}
コード例 #2
0
ファイル: wiiuse.c プロジェクト: Maaarmotte/wiiuse
/**
 *	@brief Clean up wiimote_t array created by wiiuse_init()
 */
void wiiuse_cleanup(struct wiimote_t** wm, int wiimotes) {
	int i = 0;

	if (!wm) {
		return;
	}

	WIIUSE_INFO("wiiuse clean up...");

	for (; i < wiimotes; ++i) {
		wiiuse_disconnect(wm[i]);
		wiiuse_cleanup_platform_fields(wm[i]);
		free(wm[i]);
	}

	free(wm);

	return;
}
コード例 #3
0
ファイル: wiiuse.c プロジェクト: Maaarmotte/wiiuse
/**
 *	@brief	The wiimote disconnected.
 *
 *	@param wm	Pointer to a wiimote_t structure.
 */
void wiiuse_disconnected(struct wiimote_t* wm) {
	if (!wm)	{
		return;
	}

	WIIUSE_INFO("Wiimote disconnected [id %i].", wm->unid);

	/* disable the connected flag */
	WIIMOTE_DISABLE_STATE(wm, WIIMOTE_STATE_CONNECTED);

	/* reset a bunch of stuff */
	wm->leds = 0;
	wm->state = WIIMOTE_INIT_STATES;
	wm->read_req = NULL;
#ifndef WIIUSE_SYNC_HANDSHAKE
	wm->handshake_state = 0;
#endif
	wm->btns = 0;
	wm->btns_held = 0;
	wm->btns_released = 0;

	wm->event = WIIUSE_DISCONNECT;
}
コード例 #4
0
ファイル: os_win.c プロジェクト: AchimTuran/wiiuse
int wiiuse_os_find(struct wiimote_t** wm, int max_wiimotes, int timeout) {
	GUID device_id;
	HANDLE dev;
	HDEVINFO device_info;
	int i, index;
	DWORD len;
	SP_DEVICE_INTERFACE_DATA device_data;
	PSP_DEVICE_INTERFACE_DETAIL_DATA detail_data = NULL;
	HIDD_ATTRIBUTES	attr;
	int found = 0;

	(void) timeout; /* unused */

	device_data.cbSize = sizeof(device_data);
	index = 0;

	/* get the device id */
	HidD_GetHidGuid(&device_id);

	/* get all hid devices connected */
	device_info = SetupDiGetClassDevs(&device_id, NULL, NULL, (DIGCF_DEVICEINTERFACE | DIGCF_PRESENT));

	for (;; ++index) {

		if (detail_data) {
			free(detail_data);
			detail_data = NULL;
		}

		/* query the next hid device info */
		if (!SetupDiEnumDeviceInterfaces(device_info, NULL, &device_id, index, &device_data)) {
			break;
		}

		/* get the size of the data block required */
		i = SetupDiGetDeviceInterfaceDetail(device_info, &device_data, NULL, 0, &len, NULL);
		detail_data = (SP_DEVICE_INTERFACE_DETAIL_DATA_A*)malloc(len);
		detail_data->cbSize = sizeof(SP_DEVICE_INTERFACE_DETAIL_DATA);

		/* query the data for this device */
		if (!SetupDiGetDeviceInterfaceDetail(device_info, &device_data, detail_data, len, NULL, NULL)) {
			continue;
		}

		/* open the device */
		dev = CreateFile(detail_data->DevicePath,
		                 (GENERIC_READ | GENERIC_WRITE),
		                 (FILE_SHARE_READ | FILE_SHARE_WRITE),
		                 NULL, OPEN_EXISTING, FILE_FLAG_OVERLAPPED, NULL);
		if (dev == INVALID_HANDLE_VALUE) {
			continue;
		}

		/* get device attributes */
		attr.Size = sizeof(attr);
		i = HidD_GetAttributes(dev, &attr);

		if ((attr.VendorID == WM_VENDOR_ID) && (attr.ProductID == WM_PRODUCT_ID)) {
			/* this is a wiimote */
			wm[found]->dev_handle = dev;

			wm[found]->hid_overlap.hEvent = CreateEvent(NULL, 1, 1, "");
			wm[found]->hid_overlap.Offset = 0;
			wm[found]->hid_overlap.OffsetHigh = 0;

			WIIMOTE_ENABLE_STATE(wm[found], WIIMOTE_STATE_DEV_FOUND);
			WIIMOTE_ENABLE_STATE(wm[found], WIIMOTE_STATE_CONNECTED);

			/* try to set the output report to see if the device is actually connected */
			if (!wiiuse_set_report_type(wm[found])) {
				WIIMOTE_DISABLE_STATE(wm[found], WIIMOTE_STATE_CONNECTED);
				continue;
			}

			/* do the handshake */
			wiiuse_handshake(wm[found], NULL, 0);

			WIIUSE_INFO("Connected to wiimote [id %i].", wm[found]->unid);

			++found;
			if (found >= max_wiimotes) {
				break;
			}
		} else {
			/* not a wiimote */
			CloseHandle(dev);
		}
	}

	if (detail_data) {
		free(detail_data);
	}

	SetupDiDestroyDeviceInfoList(device_info);

	return found;
}
コード例 #5
0
ファイル: io_nix.c プロジェクト: xloem/rpavlik-wiiuse
/**
 *	@brief Connect to a wiimote with a known address.
 *
 *	@param wm		Pointer to a wiimote_t structure.
 *	@param address	The address of the device to connect to.
 *					If NULL, use the address in the struct set by wiiuse_find().
 *
 *	@return 1 on success, 0 on failure
 */
static int wiiuse_connect_single(struct wiimote_t* wm, char* address) {
	struct sockaddr_l2 addr;
	memset(&addr, 0, sizeof (addr));

	if (!wm || WIIMOTE_IS_CONNECTED(wm))
		return 0;

	addr.l2_family = AF_BLUETOOTH;

	if (address)
		/* use provided address */
		str2ba(address, &addr.l2_bdaddr);
	else
		/* use address of device discovered */
		addr.l2_bdaddr = wm->bdaddr;

	/*
	 *	OUTPUT CHANNEL
	 */
	wm->out_sock = socket(AF_BLUETOOTH, SOCK_SEQPACKET, BTPROTO_L2CAP);
	if (wm->out_sock == -1)
		return 0;

	addr.l2_psm = htobs(WM_OUTPUT_CHANNEL);

	/* connect to wiimote */
	if (connect(wm->out_sock, (struct sockaddr*)&addr, sizeof(addr)) < 0) {
		perror("connect() output sock");
		return 0;
	}

	/*
	 *	INPUT CHANNEL
	 */
	wm->in_sock = socket(AF_BLUETOOTH, SOCK_SEQPACKET, BTPROTO_L2CAP);
	if (wm->in_sock == -1) {
		close(wm->out_sock);
		wm->out_sock = -1;
		return 0;
	}

	addr.l2_psm = htobs(WM_INPUT_CHANNEL);

	/* connect to wiimote */
	if (connect(wm->in_sock, (struct sockaddr*)&addr, sizeof(addr)) < 0) {
		perror("connect() interrupt sock");
		close(wm->out_sock);
		wm->out_sock = -1;
		return 0;
	}

	WIIUSE_INFO("Connected to wiimote [id %i].", wm->unid);

	/* do the handshake */
	WIIMOTE_ENABLE_STATE(wm, WIIMOTE_STATE_CONNECTED);
	wiiuse_handshake(wm, NULL, 0);

	wiiuse_set_report_type(wm);

	return 1;
}
コード例 #6
0
ファイル: os_nix.c プロジェクト: Maaarmotte/wiiuse
int wiiuse_os_find(struct wiimote_t** wm, int max_wiimotes, int timeout) {
	int device_id;
	int device_sock;
	inquiry_info scan_info_arr[128];
	inquiry_info* scan_info = scan_info_arr;
	int found_devices;
	int found_wiimotes;
	int i = 0;

	/* reset all wiimote bluetooth device addresses */
	for (found_wiimotes = 0; found_wiimotes < max_wiimotes; ++found_wiimotes) {
		/* bacpy(&(wm[found_wiimotes]->bdaddr), BDADDR_ANY); */
		memset(&(wm[found_wiimotes]->bdaddr), 0, sizeof(bdaddr_t));
	}
	found_wiimotes = 0;

	/* get the id of the first bluetooth device. */
	device_id = hci_get_route(NULL);
	if (device_id < 0) {
		if (errno == ENODEV) {
			WIIUSE_ERROR("Could not detect a Bluetooth adapter!");
		} else {
			perror("hci_get_route");
		}
		return 0;
	}

	/* create a socket to the device */
	device_sock = hci_open_dev(device_id);
	if (device_sock < 0) {
		perror("hci_open_dev");
		return 0;
	}

	memset(&scan_info_arr, 0, sizeof(scan_info_arr));

	/* scan for bluetooth devices for 'timeout' seconds */
	found_devices = hci_inquiry(device_id, timeout, 128, NULL, &scan_info, IREQ_CACHE_FLUSH);
	if (found_devices < 0) {
		perror("hci_inquiry");
		close(device_sock);
		return 0;
	}

	WIIUSE_INFO("Found %i bluetooth device(s).", found_devices);

	/* display discovered devices */
	for (i = 0; (i < found_devices) && (found_wiimotes < max_wiimotes); ++i) {
		bool is_wiimote_regular =   (scan_info[i].dev_class[0] == WM_DEV_CLASS_0) &&
									(scan_info[i].dev_class[1] == WM_DEV_CLASS_1) &&
									(scan_info[i].dev_class[2] == WM_DEV_CLASS_2);
		
		bool is_wiimote_plus =      (scan_info[i].dev_class[0] == WM_PLUS_DEV_CLASS_0) &&
									(scan_info[i].dev_class[1] == WM_PLUS_DEV_CLASS_1) &&
									(scan_info[i].dev_class[2] == WM_PLUS_DEV_CLASS_2);
		if (is_wiimote_regular || is_wiimote_plus) {
			/* found a device */
			ba2str(&scan_info[i].bdaddr, wm[found_wiimotes]->bdaddr_str);
			
			const char* str_type;
			if(is_wiimote_regular)
			{
				wm[found_wiimotes]->type = WIIUSE_WIIMOTE_REGULAR;
				str_type = " (regular wiimote)";
			}
			else if(is_wiimote_plus)
			{
				wm[found_wiimotes]->type = WIIUSE_WIIMOTE_MOTION_PLUS_INSIDE;
				str_type = " (motion plus inside)";
			}

			WIIUSE_INFO("Found wiimote (type: %s) (%s) [id %i].", str_type, wm[found_wiimotes]->bdaddr_str, wm[found_wiimotes]->unid);

			wm[found_wiimotes]->bdaddr = scan_info[i].bdaddr;
			WIIMOTE_ENABLE_STATE(wm[found_wiimotes], WIIMOTE_STATE_DEV_FOUND);
			++found_wiimotes;
		}
	}

	close(device_sock);
	return found_wiimotes;
}