[PATCH v3 19/27] PASN: Add support for MIC computation for M3 frame for SME-in-Userspace
Benjamin Berg
benjamin at sipsolutions.net
Thu Jan 22 05:14:59 PST 2026
Hi,
because this is not the first time I have seen this type of bug.
It would be good if everyone would enable ASAN for testing. It used to
be problematic with UML, but that issues has been solved. These days,
there should be no reason to not run hwsim tests with sanitizers
enabled.
See inline
On Thu, 2026-01-15 at 22:02 +0530, Ainy Kumari wrote:
> For SME-in-Userspace scenarios, MIC is computed on frame3 body,
> hash of frame1 body, but frame1 and frame3 contain auth_data starting
> from transaction number to comply with mac80211 requirement, hence
> prepend auth algorithm to frame body for preparing MIC.
>
> Signed-off-by: Ainy Kumari <ainy.kumari at oss.qualcomm.com>
> ---
> src/pasn/pasn_initiator.c | 53 ++++++++++++++++++++++++++++++++++-----
> 1 file changed, 47 insertions(+), 6 deletions(-)
>
> diff --git a/src/pasn/pasn_initiator.c b/src/pasn/pasn_initiator.c
> index 30f42fb65..b7ed5ee9d 100644
> --- a/src/pasn/pasn_initiator.c
> +++ b/src/pasn/pasn_initiator.c
> @@ -582,6 +582,18 @@ static u8 wpas_pasn_get_wrapped_data_format(struct pasn_data *pasn)
> }
>
>
> +static u8 * pasn_prepend_auth_alg(u16 auth_alg, const u8 *buf, size_t len)
> +{
> + u8 *new_buf = os_malloc(len + 2);
> + if (!new_buf)
> + return NULL;
> +
> + os_memcpy(new_buf, &auth_alg, 2);
> + os_memcpy(new_buf + 2, buf, len);
> + return new_buf;
> +}
> +
> +
> struct wpabuf *wpas_pasn_build_auth_1(struct pasn_data *pasn,
> const struct wpabuf *comeback,
> bool verify, bool is_sme_drv)
> @@ -589,6 +601,9 @@ struct wpabuf *wpas_pasn_build_auth_1(struct pasn_data *pasn,
> struct wpabuf *buf, *pubkey = NULL, *wrapped_data_buf = NULL;
> const u8 *pmkid;
> u8 wrapped_data;
> + const u8 *data;
> + size_t data_len;
> + u8 *copy = NULL;
>
> wpa_printf(MSG_DEBUG, "PASN: Building frame 1");
>
> @@ -676,9 +691,23 @@ struct wpabuf *wpas_pasn_build_auth_1(struct pasn_data *pasn,
> }
> #endif /* CONFIG_ENC_ASSOC */
>
> + if (!is_sme_drv) {
> + copy = pasn_prepend_auth_alg(pasn->auth_alg,
> + wpabuf_head_u8(buf),
> + wpabuf_len(buf));
> + if (!copy)
> + goto fail;
> + data = copy;
> + data_len = wpabuf_len(buf) + 2;
> + os_free(copy);
Free'ing the "copy" means that "data" is also invalid. You need to move
the free to the end of the function.
> + } else {
> + data = wpabuf_head_u8(buf) + IEEE80211_HDRLEN;
> + data_len = wpabuf_len(buf) - IEEE80211_HDRLEN;
> + }
> +
> wpabuf_free(pasn->auth1);
> - pasn->auth1 = wpabuf_alloc_copy(wpabuf_head_u8(buf) + IEEE80211_HDRLEN,
> - wpabuf_len(buf) - IEEE80211_HDRLEN);
> + pasn->auth1 = wpabuf_alloc_copy(data, data_len);
> +
> if (!pasn->auth1) {
> wpa_printf(MSG_DEBUG, "PASN: Failed to store a copy of Auth1");
> goto fail;
> @@ -696,6 +725,7 @@ fail:
> wpabuf_free(wrapped_data_buf);
> wpabuf_free(pubkey);
> wpabuf_free(buf);
> + os_free(copy);
> return NULL;
> }
>
> @@ -708,7 +738,7 @@ struct wpabuf *wpas_pasn_build_auth_3(struct pasn_data *pasn,
> u8 mic_len;
> size_t data_len;
> const u8 *data;
> - u8 *ptr;
> + u8 *ptr, *copy = NULL;
> u8 wrapped_data;
> int ret;
> u8 hash[SHA512_MAC_LEN];
> @@ -770,11 +800,21 @@ struct wpabuf *wpas_pasn_build_auth_3(struct pasn_data *pasn,
> wpabuf_put_u8(buf, WLAN_EID_MIC);
> wpabuf_put_u8(buf, mic_len);
> ptr = wpabuf_put(buf, mic_len);
> -
> os_memset(ptr, 0, mic_len);
>
> - data = wpabuf_head_u8(buf) + IEEE80211_HDRLEN;
> - data_len = wpabuf_len(buf) - IEEE80211_HDRLEN;
> + if (!is_sme_drv) {
> + copy = pasn_prepend_auth_alg(pasn->auth_alg,
> + wpabuf_head_u8(buf), wpabuf_len(buf));
> + if (!copy)
> + goto fail;
> + data = copy;
> + data_len = wpabuf_len(buf) + 2;
> + os_free(copy);
Same here.
Benjamin
> + } else {
> + data = wpabuf_head_u8(buf) + IEEE80211_HDRLEN;
> + data_len = wpabuf_len(buf) - IEEE80211_HDRLEN;
> + }
> +
>
> if (!pasn->auth1 ||
> pasn_auth_frame_hash(pasn->hash_alg, wpabuf_head(pasn->auth1),
> @@ -808,6 +848,7 @@ fail:
> pasn->status = WLAN_STATUS_UNSPECIFIED_FAILURE;
> wpabuf_free(wrapped_data_buf);
> wpabuf_free(buf);
> + os_free(copy);
> return NULL;
> }
>
More information about the Hostap
mailing list