mac80211: extend ieee80211_ie_split to support EXTENSION
Current ieee80211_ie_split() implementation doesn't account for elements that are sub-elements of the EXTENSION IE. To extend support to these IEs as well, treat the WLAN_EID_EXTENSION ids in the %ids array as indicating that the next id in the array is a sub-element of the EXTENSION IE. Signed-off-by: Liad Kaufman <liad.kaufman@intel.com> Signed-off-by: Luca Coelho <luciano.coelho@intel.com> Signed-off-by: Johannes Berg <johannes.berg@intel.com>
This commit is contained in:
		
							parent
							
								
									79af1f8661
								
							
						
					
					
						commit
						2512b1b18d
					
				| @ -5934,7 +5934,8 @@ int cfg80211_get_p2p_attr(const u8 *ies, unsigned int len, | |||||||
|  * @ies: the IE buffer |  * @ies: the IE buffer | ||||||
|  * @ielen: the length of the IE buffer |  * @ielen: the length of the IE buffer | ||||||
|  * @ids: an array with element IDs that are allowed before |  * @ids: an array with element IDs that are allowed before | ||||||
|  *	the split |  *	the split. A WLAN_EID_EXTENSION value means that the next | ||||||
|  |  *	EID in the list is a sub-element of the EXTENSION IE. | ||||||
|  * @n_ids: the size of the element ID array |  * @n_ids: the size of the element ID array | ||||||
|  * @after_ric: array IE types that come after the RIC element |  * @after_ric: array IE types that come after the RIC element | ||||||
|  * @n_after_ric: size of the @after_ric array |  * @n_after_ric: size of the @after_ric array | ||||||
| @ -5965,7 +5966,8 @@ size_t ieee80211_ie_split_ric(const u8 *ies, size_t ielen, | |||||||
|  * @ies: the IE buffer |  * @ies: the IE buffer | ||||||
|  * @ielen: the length of the IE buffer |  * @ielen: the length of the IE buffer | ||||||
|  * @ids: an array with element IDs that are allowed before |  * @ids: an array with element IDs that are allowed before | ||||||
|  *	the split |  *	the split. A WLAN_EID_EXTENSION value means that the next | ||||||
|  |  *	EID in the list is a sub-element of the EXTENSION IE. | ||||||
|  * @n_ids: the size of the element ID array |  * @n_ids: the size of the element ID array | ||||||
|  * @offset: offset where to start splitting in the buffer |  * @offset: offset where to start splitting in the buffer | ||||||
|  * |  * | ||||||
|  | |||||||
| @ -1367,13 +1367,29 @@ int cfg80211_get_p2p_attr(const u8 *ies, unsigned int len, | |||||||
| } | } | ||||||
| EXPORT_SYMBOL(cfg80211_get_p2p_attr); | EXPORT_SYMBOL(cfg80211_get_p2p_attr); | ||||||
| 
 | 
 | ||||||
| static bool ieee80211_id_in_list(const u8 *ids, int n_ids, u8 id) | static bool ieee80211_id_in_list(const u8 *ids, int n_ids, u8 id, bool id_ext) | ||||||
| { | { | ||||||
| 	int i; | 	int i; | ||||||
| 
 | 
 | ||||||
| 	for (i = 0; i < n_ids; i++) | 	/* Make sure array values are legal */ | ||||||
| 		if (ids[i] == id) | 	if (WARN_ON(ids[n_ids - 1] == WLAN_EID_EXTENSION)) | ||||||
|  | 		return false; | ||||||
|  | 
 | ||||||
|  | 	i = 0; | ||||||
|  | 	while (i < n_ids) { | ||||||
|  | 		if (ids[i] == WLAN_EID_EXTENSION) { | ||||||
|  | 			if (id_ext && (ids[i + 1] == id)) | ||||||
| 				return true; | 				return true; | ||||||
|  | 
 | ||||||
|  | 			i += 2; | ||||||
|  | 			continue; | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
|  | 		if (ids[i] == id && !id_ext) | ||||||
|  | 			return true; | ||||||
|  | 
 | ||||||
|  | 		i++; | ||||||
|  | 	} | ||||||
| 	return false; | 	return false; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| @ -1403,14 +1419,36 @@ size_t ieee80211_ie_split_ric(const u8 *ies, size_t ielen, | |||||||
| { | { | ||||||
| 	size_t pos = offset; | 	size_t pos = offset; | ||||||
| 
 | 
 | ||||||
| 	while (pos < ielen && ieee80211_id_in_list(ids, n_ids, ies[pos])) { | 	while (pos < ielen) { | ||||||
|  | 		u8 ext = 0; | ||||||
|  | 
 | ||||||
|  | 		if (ies[pos] == WLAN_EID_EXTENSION) | ||||||
|  | 			ext = 2; | ||||||
|  | 		if ((pos + ext) >= ielen) | ||||||
|  | 			break; | ||||||
|  | 
 | ||||||
|  | 		if (!ieee80211_id_in_list(ids, n_ids, ies[pos + ext], | ||||||
|  | 					  ies[pos] == WLAN_EID_EXTENSION)) | ||||||
|  | 			break; | ||||||
|  | 
 | ||||||
| 		if (ies[pos] == WLAN_EID_RIC_DATA && n_after_ric) { | 		if (ies[pos] == WLAN_EID_RIC_DATA && n_after_ric) { | ||||||
| 			pos = skip_ie(ies, ielen, pos); | 			pos = skip_ie(ies, ielen, pos); | ||||||
| 
 | 
 | ||||||
| 			while (pos < ielen && | 			while (pos < ielen) { | ||||||
| 			       !ieee80211_id_in_list(after_ric, n_after_ric, | 				if (ies[pos] == WLAN_EID_EXTENSION) | ||||||
| 						     ies[pos])) | 					ext = 2; | ||||||
|  | 				else | ||||||
|  | 					ext = 0; | ||||||
|  | 
 | ||||||
|  | 				if ((pos + ext) >= ielen) | ||||||
|  | 					break; | ||||||
|  | 
 | ||||||
|  | 				if (!ieee80211_id_in_list(after_ric, | ||||||
|  | 							  n_after_ric, | ||||||
|  | 							  ies[pos + ext], | ||||||
|  | 							  ext == 2)) | ||||||
| 					pos = skip_ie(ies, ielen, pos); | 					pos = skip_ie(ies, ielen, pos); | ||||||
|  | 			} | ||||||
| 		} else { | 		} else { | ||||||
| 			pos = skip_ie(ies, ielen, pos); | 			pos = skip_ie(ies, ielen, pos); | ||||||
| 		} | 		} | ||||||
|  | |||||||
		Loading…
	
		Reference in New Issue
	
	Block a user