⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 connection.c

📁 Linux的蓝牙操作工具。配合bluez-lib使用
💻 C
📖 第 1 页 / 共 2 页
字号:
	}	reply = dbus_message_new_method_return(msg);	if (!reply)		return DBUS_HANDLER_RESULT_NEED_MEMORY;	dbus_message_append_args(reply, DBUS_TYPE_STRING, &nc->desc,					DBUS_TYPE_INVALID);	return send_message_and_unref(conn, reply);}static DBusHandlerResult get_interface(DBusConnection *conn, DBusMessage *msg,					void *data){	struct network_conn *nc = data;	const char *pdev = nc->dev;	DBusMessage *reply;	if (nc->state != CONNECTED) {		error_failed(conn, msg, "Device not connected");		return DBUS_HANDLER_RESULT_HANDLED;	}	reply = dbus_message_new_method_return(msg);	if (!reply)		return DBUS_HANDLER_RESULT_NEED_MEMORY;	dbus_message_append_args(reply, DBUS_TYPE_STRING, &pdev,					DBUS_TYPE_INVALID);	return send_message_and_unref(conn, reply);}/* Connect and initiate BNEP session */static DBusHandlerResult connection_connect(DBusConnection *conn,						DBusMessage *msg, void *data){	struct network_conn *nc = data;	DBusError derr;	if (nc->state != DISCONNECTED) {		error_failed(conn, msg, "Device already connected");		return DBUS_HANDLER_RESULT_HANDLED;	}	dbus_error_init(&derr);	if (!dbus_message_get_args(msg, &derr,				DBUS_TYPE_INVALID)) {		error_invalid_arguments(conn, msg, derr.message);		dbus_error_free(&derr);		return DBUS_HANDLER_RESULT_HANDLED;	}	nc->sk = socket(AF_BLUETOOTH, SOCK_SEQPACKET, BTPROTO_L2CAP);	nc->state = CONNECTING;	if (nc->sk < 0) {		error("Cannot create L2CAP socket. %s(%d)", strerror(errno),				errno);		goto fail;	}	nc->msg = dbus_message_ref(msg);	if (l2cap_connect(nc) < 0) {		error("Connect failed. %s(%d)", strerror(errno), errno);		goto fail;	}	return DBUS_HANDLER_RESULT_HANDLED;fail:	if (nc->msg) {		dbus_message_unref(nc->msg);		nc->msg = NULL;	}	nc->state = DISCONNECTED;	error_connection_attempt_failed(conn, msg, errno);	return DBUS_HANDLER_RESULT_HANDLED;}static DBusHandlerResult connection_cancel(DBusConnection *conn,						DBusMessage *msg, void *data){	struct network_conn *nc = data;	DBusMessage *reply;	if (nc->state != CONNECTING) {		error_failed(conn, msg, "Device has no pending connect");		return DBUS_HANDLER_RESULT_HANDLED;	}	close(nc->sk);	nc->state = DISCONNECTED;	reply = dbus_message_new_method_return(msg);	return send_message_and_unref(conn, reply);}static DBusHandlerResult connection_disconnect(DBusConnection *conn,					DBusMessage *msg, void *data){	struct network_conn *nc = data;	DBusMessage *reply;	if (nc->state != CONNECTED) {		error_failed(conn, msg, "Device not connected");		return DBUS_HANDLER_RESULT_HANDLED;	}	bnep_if_down(nc->dev);	bnep_kill_connection(&nc->dst);	reply = dbus_message_new_method_return(msg);	if (!reply)		return DBUS_HANDLER_RESULT_NEED_MEMORY;	return send_message_and_unref(conn, reply);}static DBusHandlerResult is_connected(DBusConnection *conn, DBusMessage *msg,					void *data){	struct network_conn *nc = data;	DBusMessage *reply;	gboolean up;	reply = dbus_message_new_method_return(msg);	if (!reply)		return DBUS_HANDLER_RESULT_NEED_MEMORY;	up = (nc->state == CONNECTED);	dbus_message_append_args(reply, DBUS_TYPE_BOOLEAN, &up,					DBUS_TYPE_INVALID);	return send_message_and_unref(conn, reply);}static DBusHandlerResult get_info(DBusConnection *conn,					DBusMessage *msg, void *data){	struct network_conn *nc = data;	DBusMessage *reply;	DBusMessageIter iter;	DBusMessageIter dict;	const char *uuid;	char raddr[18];	const char *paddr = raddr;	reply = dbus_message_new_method_return(msg);	if (!reply)		return DBUS_HANDLER_RESULT_NEED_MEMORY;	dbus_message_iter_init_append(reply, &iter);	dbus_message_iter_open_container(&iter, DBUS_TYPE_ARRAY,			DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING			DBUS_TYPE_STRING_AS_STRING DBUS_TYPE_VARIANT_AS_STRING			DBUS_DICT_ENTRY_END_CHAR_AS_STRING, &dict);	dbus_message_iter_append_dict_entry(&dict, "name",			DBUS_TYPE_STRING, &nc->name);	uuid = bnep_uuid(nc->id);	dbus_message_iter_append_dict_entry(&dict, "uuid",			DBUS_TYPE_STRING, &uuid);	ba2str(&nc->dst, raddr);	dbus_message_iter_append_dict_entry(&dict, "address",			DBUS_TYPE_STRING, &paddr);	dbus_message_iter_close_container(&iter, &dict);	return send_message_and_unref(conn, reply);}static void connection_free(struct network_conn *nc){	if (!nc)		return;	if (nc->path)		g_free(nc->path);	if (nc->state == CONNECTED) {		bnep_if_down(nc->dev);		bnep_kill_connection(&nc->dst);	}	if (nc->name)		g_free(nc->name);	if (nc->desc)		g_free(nc->desc);		g_free(nc);	nc = NULL;}static void connection_unregister(DBusConnection *conn, void *data){	struct network_conn *nc = data;	info("Unregistered connection path:%s", nc->path);	connection_free(nc);}static DBusMethodVTable connection_methods[] = {	{ "GetAdapter",		get_adapter,		"",	"s"	},	{ "GetAddress",		get_address,		"",	"s"	},	{ "GetUUID",		get_uuid,		"",	"s"	},	{ "GetName",		get_name,		"",	"s"	},	{ "GetDescription",	get_description,	"",	"s"	},	{ "GetInterface",	get_interface,		"",	"s"	},	{ "Connect",		connection_connect,	"",	"s"	},	{ "CancelConnect",	connection_cancel,	"",	""	},	{ "Disconnect",		connection_disconnect,	"",	""	},	{ "IsConnected",	is_connected,		"",	"b"	},	{ "GetInfo",		get_info,		"",	"a{sv}" },	{ NULL, NULL, NULL, NULL }};static DBusSignalVTable connection_signals[] = {	{ "Connected",		""	},	{ "Disconnected",	""	},	{ NULL, NULL }};int connection_register(const char *path, bdaddr_t *src, bdaddr_t *dst,			uint16_t id, const char *name, const char *desc){	struct network_conn *nc;	bdaddr_t default_src;	int dev_id;	if (!path)		return -EINVAL;	bacpy(&default_src, BDADDR_ANY);	dev_id = hci_get_route(&default_src);	if (dev_id < 0 || hci_devba(dev_id, &default_src) < 0)		return -1;	nc = g_new0(struct network_conn, 1);	/* register path */	if (!dbus_connection_create_object_path(connection, path, nc,						connection_unregister)) {		connection_free(nc);		return -1;	}	if (!dbus_connection_register_interface(connection, path,						NETWORK_CONNECTION_INTERFACE,						connection_methods,						connection_signals, NULL)) {		error("D-Bus failed to register %s interface",				NETWORK_CONNECTION_INTERFACE);		dbus_connection_destroy_object_path(connection, path);		return -1;	}	nc->path = g_strdup(path);	bacpy(&nc->store, src);	bacpy(&nc->src, &default_src);	bacpy(&nc->dst, dst);	nc->id = id;	nc->name = g_strdup(name);	nc->desc = g_strdup(desc);	memset(nc->dev, 0, 16);	strncpy(nc->dev, prefix, strlen(prefix));	nc->state = DISCONNECTED;	info("Registered connection path:%s", path);	return 0;}int connection_store(const char *path, gboolean default_path){	struct network_conn *nc;	const char *role;	char key[32], *value;	char filename[PATH_MAX + 1];	char src_addr[18], dst_addr[18];	int len, err;	if (!dbus_connection_get_object_user_data(connection,				path, (void *) &nc))		return -ENOENT;	if (!nc->name || !nc->desc)		return -EINVAL;	/* FIXME: name and desc validation - remove ':' */	ba2str(&nc->dst, dst_addr);	role = bnep_name(nc->id);	snprintf(key, 32, "%s#%s", dst_addr, role);	ba2str(&nc->store, src_addr);	create_name(filename, PATH_MAX, STORAGEDIR, src_addr, "network");	create_file(filename, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);	if (default_path)		err = textfile_put(filename, "default", key);	else {		len = strlen(nc->name) + strlen(nc->desc)  + 2;		value = g_malloc0(len);		snprintf(value, len, "%s:%s", nc->name, nc->desc);		err = textfile_put(filename, key, value);		g_free(value);	}	return err;}int connection_find_data(const char *path, const char *pattern){	struct network_conn *nc;	char addr[18], key[32];	const char *role;	if (!dbus_connection_get_object_user_data(connection,		path, (void *) &nc))		return -1;	if (strcasecmp(pattern, nc->dev) == 0)		return 0;	if (strcasecmp(pattern, nc->name) == 0)		return 0;	ba2str(&nc->dst, addr);	if (strcasecmp(pattern, addr) == 0)		return 0;	role = bnep_name(nc->id);	snprintf(key, 32, "%s#%s", addr, role);	if (strcasecmp(pattern, key) == 0)		return 0;	return -1;}gboolean connection_has_pending(const char *path){	struct network_conn *nc;	if (!dbus_connection_get_object_user_data(connection,				path, (void *) &nc))		return FALSE;	return (nc->state == CONNECTING);}int connection_remove_stored(const char *path){	struct network_conn *nc;	const char *role;	char key[32];	char filename[PATH_MAX + 1];	char src_addr[18], dst_addr[18];	int err;	if (!dbus_connection_get_object_user_data(connection,				path, (void *) &nc))		return -ENOENT;	ba2str(&nc->dst, dst_addr);	role = bnep_name(nc->id);	snprintf(key, 32, "%s#%s", dst_addr, role);	ba2str(&nc->store, src_addr);	create_name(filename, PATH_MAX, STORAGEDIR, src_addr, "network");	err = textfile_del(filename, key);	return err;}gboolean connection_is_connected(const char *path){	struct network_conn *nc;	if (!dbus_connection_get_object_user_data(connection,				path, (void *) &nc))		return FALSE;	return (nc->state == CONNECTED);}int connection_init(DBusConnection *conn, const char *iface_prefix){	connection = dbus_connection_ref(conn);	prefix = iface_prefix;	return 0;}void connection_exit(){	dbus_connection_unref(connection);	connection = NULL;	prefix = NULL;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -