1. 程式人生 > >(一百一十二)Android O wpa_supplicant初始化學習(五)—— retrieveIfacePtr 流程探討

(一百一十二)Android O wpa_supplicant初始化學習(五)—— retrieveIfacePtr 流程探討

前言:一直想梳理下WiFi在supplicant的連線流程,但是初始化流程梳理的千瘡八孔,少了前置步驟很難梳理。先看下一個基礎的介面retrieveIfacePtr流程。

 

1.目標介面

sta_iface.cpp

/**
 * Retrieve the underlying |wpa_supplicant| struct
 * pointer for this iface.
 * If the underlying iface is removed, then all RPC method calls on this object
 * will return failure.
 */
wpa_supplicant *StaIface::retrieveIfacePtr()
{
	return wpa_supplicant_get_iface(wpa_global_, ifname_.c_str());
}

註釋表示這個介面是用來獲取潛在的對應於iface 的 wpa_supplicant結構體指標,如果潛在的介面被移除了,那麼所有的RPC方法呼叫就將返回fail.

 

2.獲取流程梳理

2.1 sta_iface.cpp

/**
 * Retrieve the underlying |wpa_supplicant| struct
 * pointer for this iface.
 * If the underlying iface is removed, then all RPC method calls on this object
 * will return failure.
 */
wpa_supplicant *StaIface::retrieveIfacePtr()
{
	return wpa_supplicant_get_iface(wpa_global_, ifname_.c_str());
}

 

2.2 wpa_supplicant.c

/**
 * wpa_supplicant_get_iface - Get a new network interface
 * @global: Pointer to global data from wpa_supplicant_init()
 * @ifname: Interface name
 * Returns: Pointer to the interface or %NULL if not found
 */
struct wpa_supplicant * wpa_supplicant_get_iface(struct wpa_global *global,
						 const char *ifname)
{
	struct wpa_supplicant *wpa_s;

	for (wpa_s = global->ifaces; wpa_s; wpa_s = wpa_s->next) {
		if (os_strcmp(wpa_s->ifname, ifname) == 0)
			return wpa_s;
	}
	return NULL;
}

得到一個網路介面,入參一共兩個,一個是從wpa_supplicant_init獲取的global指標,還有一個是介面名稱,返回的是一個介面指標或者null.

這裡只看到獲取流程,再看下新增流程流程就理順了。

 

3.新增流程梳理

這裡簡單回顧下supplicant的main.c中的流程是

先呼叫

    global = wpa_supplicant_init(&params);

獲取一個global物件

後呼叫

        wpa_s = wpa_supplicant_add_iface(global, &ifaces[i], NULL);

新增介面

 

3.1 wpa_supplicant.c

/**
 * wpa_supplicant_init - Initialize %wpa_supplicant
 * @params: Parameters for %wpa_supplicant
 * Returns: Pointer to global %wpa_supplicant data, or %NULL on failure
 *
 * This function is used to initialize %wpa_supplicant. After successful
 * initialization, the returned data pointer can be used to add and remove
 * network interfaces, and eventually, to deinitialize %wpa_supplicant.
 */
struct wpa_global * wpa_supplicant_init(struct wpa_params *params)

使用wpa_params初始化出一個wpa_global物件。

 

/**
 * wpa_supplicant_add_iface - Add a new network interface
 * @global: Pointer to global data from wpa_supplicant_init()
 * @iface: Interface configuration options
 * @parent: Parent interface or %NULL to assign new interface as parent
 * Returns: Pointer to the created interface or %NULL on failure
 *
 * This function is used to add new network interfaces for %wpa_supplicant.
 * This can be called before wpa_supplicant_run() to add interfaces before the
 * main event loop has been started. In addition, new interfaces can be added
 * dynamically while %wpa_supplicant is already running. This could happen,
 * e.g., when a hotplug network adapter is inserted.
 */
struct wpa_supplicant * wpa_supplicant_add_iface(struct wpa_global *global,
						 struct wpa_interface *iface,
						 struct wpa_supplicant *parent)
{
...
	if (wpa_supplicant_init_iface(wpa_s, &t_iface)) {
		wpa_printf(MSG_DEBUG, "Failed to add interface %s",
			   iface->ifname);
		wpa_supplicant_deinit_iface(wpa_s, 0, 0);
		return NULL;
	}
...
	wpa_s->next = global->ifaces;
	global->ifaces = wpa_s;
...
}

這邊新增介面,其實就是個連結串列,初始化一個wpa_supplicant承載介面各項屬性,然後將之前的連結串列新增到新連結串列後面,再以新連結串列元素為head.

再看下初始化

static int wpa_supplicant_init_iface(struct wpa_supplicant *wpa_s,
				     struct wpa_interface *iface)
{
	struct wpa_driver_capa capa;
	int capa_res;
	u8 dfs_domain;

	wpa_printf(MSG_DEBUG, "Initializing interface '%s' conf '%s' driver "
		   "'%s' ctrl_interface '%s' bridge '%s'", iface->ifname,
		   iface->confname ? iface->confname : "N/A",
		   iface->driver ? iface->driver : "default",
		   iface->ctrl_interface ? iface->ctrl_interface : "N/A",
		   iface->bridge_ifname ? iface->bridge_ifname : "N/A");
   os_strlcpy(wpa_s->ifname, iface->ifname, sizeof(wpa_s->ifname));

這邊用介面的名稱初始化了wpa_s的ifname引數,這樣看起來流程就對的上了。