aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorErik Staats <estaats@google.com>2018-02-15 19:16:23 -0800
committerErik Staats <estaats@google.com>2018-02-15 19:16:23 -0800
commita5b2dbcb183586b50c588025f16789ea93336dd3 (patch)
treefa1f946f57c32dd73e1be81a13aa7fb6bc052170
parent9142a68b659e77c2f8830927fe3f53720a49c810 (diff)
parenta9d63d6f7cc7394f5c6c9ed888de2d0dcd3ac6b5 (diff)
Merge branch 'android-msm-angler-3.10-security-next' into android-msm-angler-3.10android-8.1.0_r0.41
April 2018.1 Bug: 73498878
-rw-r--r--drivers/net/usb/cdc-phonet.c4
-rw-r--r--drivers/net/usb/cdc_ether.c8
-rw-r--r--drivers/net/usb/qmi_wwan.c7
-rw-r--r--drivers/net/wireless/bcmdhd/wl_cfg80211.c76
-rw-r--r--drivers/net/wireless/bcmdhd/wl_cfg80211.h6
-rw-r--r--drivers/net/wireless/bcmdhd/wl_cfgvendor.c37
-rw-r--r--drivers/net/wireless/bcmdhd/wl_cfgvendor.h3
-rw-r--r--drivers/platform/msm/ipa/ipa_hdr.c26
-rw-r--r--drivers/platform/msm/ipa/rmnet_ipa.c7
-rw-r--r--drivers/soc/qcom/qdsp6v2/apr.c3
-rw-r--r--drivers/usb/class/cdc-acm.c5
-rw-r--r--drivers/usb/class/cdc-wdm.c7
-rw-r--r--net/ipv4/raw.c15
-rw-r--r--net/wireless/nl80211.c10
-rw-r--r--security/keys/encrypted-keys/encrypted.c31
15 files changed, 143 insertions, 102 deletions
diff --git a/drivers/net/usb/cdc-phonet.c b/drivers/net/usb/cdc-phonet.c
index 7d78669000d7..af49e8fcd711 100644
--- a/drivers/net/usb/cdc-phonet.c
+++ b/drivers/net/usb/cdc-phonet.c
@@ -343,9 +343,9 @@ int usbpn_probe(struct usb_interface *intf, const struct usb_device_id *id)
data = intf->altsetting->extra;
len = intf->altsetting->extralen;
- while (len >= 3) {
+ while (len > 0) {
u8 dlen = data[0];
- if (dlen < 3)
+ if ((len < dlen) || (dlen < 3 ))
return -EINVAL;
/* bDescriptorType */
diff --git a/drivers/net/usb/cdc_ether.c b/drivers/net/usb/cdc_ether.c
index b1897c7afdd8..71e11ebf11a3 100644
--- a/drivers/net/usb/cdc_ether.c
+++ b/drivers/net/usb/cdc_ether.c
@@ -128,7 +128,13 @@ int usbnet_generic_cdc_bind(struct usbnet *dev, struct usb_interface *intf)
memset(info, 0, sizeof *info);
info->control = intf;
- while (len > 3) {
+ while (len > 0) {
+
+ if ((len < buf [0]) || (buf [0] < 3)) {
+ dev_dbg(&intf->dev, "invalid descriptor buffer length\n");
+ goto bad_desc;
+ }
+
if (buf [1] != USB_DT_CS_INTERFACE)
goto next_desc;
diff --git a/drivers/net/usb/qmi_wwan.c b/drivers/net/usb/qmi_wwan.c
index 43204f4be2da..15ffe00aabbe 100644
--- a/drivers/net/usb/qmi_wwan.c
+++ b/drivers/net/usb/qmi_wwan.c
@@ -235,9 +235,14 @@ static int qmi_wwan_bind(struct usbnet *dev, struct usb_interface *intf)
info->data = intf;
/* and a number of CDC descriptors */
- while (len > 3) {
+ while (len > 0) {
struct usb_descriptor_header *h = (void *)buf;
+ if ((len < buf[0]) || (buf[0] < 3)) {
+ dev_dbg(&intf->dev, "invalid descriptor buffer length\n");
+ goto err;
+ }
+
/* ignore any misplaced descriptors */
if (h->bDescriptorType != USB_DT_CS_INTERFACE)
goto next_desc;
diff --git a/drivers/net/wireless/bcmdhd/wl_cfg80211.c b/drivers/net/wireless/bcmdhd/wl_cfg80211.c
index e7ababd395be..72243f219f4d 100644
--- a/drivers/net/wireless/bcmdhd/wl_cfg80211.c
+++ b/drivers/net/wireless/bcmdhd/wl_cfg80211.c
@@ -8930,6 +8930,32 @@ static s32 wl_get_assoc_ies(struct bcm_cfg80211 *cfg, struct net_device *ndev)
assoc_info.req_len = htod32(assoc_info.req_len);
assoc_info.resp_len = htod32(assoc_info.resp_len);
assoc_info.flags = htod32(assoc_info.flags);
+
+ if (assoc_info.req_len >
+ (MAX_REQ_LINE + sizeof(struct dot11_assoc_req) +
+ ((assoc_info.flags & WLC_ASSOC_REQ_IS_REASSOC) ?
+ ETHER_ADDR_LEN : 0))) {
+ err = BCME_BADLEN;
+ goto exit;
+ }
+ if ((assoc_info.req_len > 0) &&
+ (assoc_info.req_len < (sizeof(struct dot11_assoc_req) +
+ ((assoc_info.flags & WLC_ASSOC_REQ_IS_REASSOC) ?
+ ETHER_ADDR_LEN : 0)))) {
+ err = BCME_BADLEN;
+ goto exit;
+ }
+ if (assoc_info.resp_len >
+ (MAX_REQ_LINE + sizeof(struct dot11_assoc_resp))) {
+ err = BCME_BADLEN;
+ goto exit;
+ }
+ if ((assoc_info.resp_len > 0) &&
+ (assoc_info.resp_len < sizeof(struct dot11_assoc_resp))) {
+ err = BCME_BADLEN;
+ goto exit;
+ }
+
if (conn_info->req_ie_len) {
conn_info->req_ie_len = 0;
bzero(conn_info->req_ie, sizeof(conn_info->req_ie));
@@ -8938,48 +8964,42 @@ static s32 wl_get_assoc_ies(struct bcm_cfg80211 *cfg, struct net_device *ndev)
conn_info->resp_ie_len = 0;
bzero(conn_info->resp_ie, sizeof(conn_info->resp_ie));
}
+
if (assoc_info.req_len) {
- err = wldev_iovar_getbuf(ndev, "assoc_req_ies", NULL, 0, cfg->extra_buf,
- WL_ASSOC_INFO_MAX, NULL);
+ err = wldev_iovar_getbuf(ndev, "assoc_req_ies", NULL, 0,
+ cfg->extra_buf, WL_ASSOC_INFO_MAX, NULL);
if (unlikely(err)) {
WL_ERR(("could not get assoc req (%d)\n", err));
- return err;
+ goto exit;
}
- conn_info->req_ie_len = assoc_info.req_len - sizeof(struct dot11_assoc_req);
+ conn_info->req_ie_len = assoc_info.req_len -
+ sizeof(struct dot11_assoc_req);
if (assoc_info.flags & WLC_ASSOC_REQ_IS_REASSOC) {
conn_info->req_ie_len -= ETHER_ADDR_LEN;
}
- if (conn_info->req_ie_len <= MAX_REQ_LINE)
- memcpy(conn_info->req_ie, cfg->extra_buf, conn_info->req_ie_len);
- else {
- WL_ERR(("IE size %d above max %d size \n",
- conn_info->req_ie_len, MAX_REQ_LINE));
- return err;
- }
- } else {
- conn_info->req_ie_len = 0;
+ memcpy(conn_info->req_ie, cfg->extra_buf,
+ conn_info->req_ie_len);
}
+
if (assoc_info.resp_len) {
- err = wldev_iovar_getbuf(ndev, "assoc_resp_ies", NULL, 0, cfg->extra_buf,
- WL_ASSOC_INFO_MAX, NULL);
+ err = wldev_iovar_getbuf(ndev, "assoc_resp_ies", NULL, 0,
+ cfg->extra_buf, WL_ASSOC_INFO_MAX, NULL);
if (unlikely(err)) {
WL_ERR(("could not get assoc resp (%d)\n", err));
- return err;
- }
- conn_info->resp_ie_len = assoc_info.resp_len -sizeof(struct dot11_assoc_resp);
- if (conn_info->resp_ie_len <= MAX_REQ_LINE)
- memcpy(conn_info->resp_ie, cfg->extra_buf, conn_info->resp_ie_len);
- else {
- WL_ERR(("IE size %d above max %d size \n",
- conn_info->resp_ie_len, MAX_REQ_LINE));
- return err;
+ goto exit;
}
- } else {
- conn_info->resp_ie_len = 0;
+ conn_info->resp_ie_len =
+ assoc_info.resp_len - sizeof(struct dot11_assoc_resp);
+ memcpy(conn_info->resp_ie, cfg->extra_buf,
+ conn_info->resp_ie_len);
}
- WL_DBG(("req len (%d) resp len (%d)\n", conn_info->req_ie_len,
- conn_info->resp_ie_len));
+exit:
+ if (err) {
+ WL_ERR(("err:%d assoc-req:%u,resp:%u conn-req:%u,resp:%u\n",
+ err, assoc_info.req_len, assoc_info.resp_len,
+ conn_info->req_ie_len, conn_info->resp_ie_len));
+ }
return err;
}
diff --git a/drivers/net/wireless/bcmdhd/wl_cfg80211.h b/drivers/net/wireless/bcmdhd/wl_cfg80211.h
index 56701ca3306b..db89ca39afe4 100644
--- a/drivers/net/wireless/bcmdhd/wl_cfg80211.h
+++ b/drivers/net/wireless/bcmdhd/wl_cfg80211.h
@@ -360,12 +360,12 @@ struct net_info {
};
/* association inform */
-#define MAX_REQ_LINE 1024
+#define MAX_REQ_LINE 1024u
struct wl_connect_info {
u8 req_ie[MAX_REQ_LINE];
- s32 req_ie_len;
+ u32 req_ie_len;
u8 resp_ie[MAX_REQ_LINE];
- s32 resp_ie_len;
+ u32 resp_ie_len;
};
/* firmware /nvram downloading controller */
diff --git a/drivers/net/wireless/bcmdhd/wl_cfgvendor.c b/drivers/net/wireless/bcmdhd/wl_cfgvendor.c
index ece2b39364e2..32a95866fe30 100644
--- a/drivers/net/wireless/bcmdhd/wl_cfgvendor.c
+++ b/drivers/net/wireless/bcmdhd/wl_cfgvendor.c
@@ -1955,35 +1955,6 @@ wl_cfgvendor_rtt_cancel_responder(struct wiphy *wiphy, struct wireless_dev *wdev
return err;
}
#endif /* RTT_SUPPORT */
-static int wl_cfgvendor_priv_string_handler(struct wiphy *wiphy,
- struct wireless_dev *wdev, const void *data, int len)
-{
- struct bcm_cfg80211 *cfg = wiphy_priv(wiphy);
- int err = 0;
- int data_len = 0;
-
- bzero(cfg->ioctl_buf, WLC_IOCTL_MAXLEN);
-
- if (strncmp((char *)data, BRCM_VENDOR_SCMD_CAPA, strlen(BRCM_VENDOR_SCMD_CAPA)) == 0) {
- err = wldev_iovar_getbuf(bcmcfg_to_prmry_ndev(cfg), "cap", NULL, 0,
- cfg->ioctl_buf, WLC_IOCTL_MAXLEN, &cfg->ioctl_buf_sync);
- if (unlikely(err)) {
- WL_ERR(("error (%d)\n", err));
- return err;
- }
- data_len = strlen(cfg->ioctl_buf);
- cfg->ioctl_buf[data_len] = '\0';
- }
-
- err = wl_cfgvendor_send_cmd_reply(wiphy, bcmcfg_to_prmry_ndev(cfg),
- cfg->ioctl_buf, data_len+1);
- if (unlikely(err))
- WL_ERR(("Vendor Command reply failed ret:%d \n", err));
- else
- WL_INFORM(("Vendor Command reply sent successfully!\n"));
-
- return err;
-}
#ifdef LINKSTAT_SUPPORT
#define NUM_RATE 32
@@ -2867,14 +2838,6 @@ exit:
static const struct wiphy_vendor_command wl_vendor_cmds [] = {
- {
- {
- .vendor_id = OUI_BRCM,
- .subcmd = BRCM_VENDOR_SCMD_PRIV_STR
- },
- .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
- .doit = wl_cfgvendor_priv_string_handler
- },
#ifdef GSCAN_SUPPORT
{
{
diff --git a/drivers/net/wireless/bcmdhd/wl_cfgvendor.h b/drivers/net/wireless/bcmdhd/wl_cfgvendor.h
index e15666f720e5..5a0ef5176c6a 100644
--- a/drivers/net/wireless/bcmdhd/wl_cfgvendor.h
+++ b/drivers/net/wireless/bcmdhd/wl_cfgvendor.h
@@ -413,9 +413,6 @@ typedef enum gscan_complete_event {
WIFI_SCAN_BUFFER_THR_BREACHED
} gscan_complete_event_t;
-/* Capture the BRCM_VENDOR_SUBCMD_PRIV_STRINGS* here */
-#define BRCM_VENDOR_SCMD_CAPA "cap"
-
#if (LINUX_VERSION_CODE > KERNEL_VERSION(3, 13, 0)) || defined(WL_VENDOR_EXT_SUPPORT)
extern int wl_cfgvendor_attach(struct wiphy *wiphy, dhd_pub_t *dhd);
extern int wl_cfgvendor_detach(struct wiphy *wiphy);
diff --git a/drivers/platform/msm/ipa/ipa_hdr.c b/drivers/platform/msm/ipa/ipa_hdr.c
index 92974c7878ed..94f0529b00db 100644
--- a/drivers/platform/msm/ipa/ipa_hdr.c
+++ b/drivers/platform/msm/ipa/ipa_hdr.c
@@ -809,8 +809,17 @@ int __ipa_del_hdr(u32 hdr_hdl, bool by_user)
return -EINVAL;
}
- if (by_user)
+ if (by_user) {
+ if (!strcmp(entry->name, IPA_LAN_RX_HDR_NAME)) {
+ IPADBG("Trying to delete hdr %s offset=%u\n",
+ entry->name, entry->offset_entry->offset);
+ if (!entry->offset_entry->offset) {
+ IPAERR("User cannot delete default header\n");
+ return -EPERM;
+ }
+ }
entry->user_deleted = true;
+ }
if (--entry->ref_cnt) {
IPADBG("hdr_hdl %x ref_cnt %d\n", hdr_hdl, entry->ref_cnt);
@@ -1113,8 +1122,19 @@ int ipa_reset_hdr(void)
&ipa_ctx->hdr_tbl.head_hdr_entry_list, link) {
/* do not remove the default header */
- if (!strcmp(entry->name, IPA_LAN_RX_HDR_NAME))
- continue;
+ if (!strcmp(entry->name, IPA_LAN_RX_HDR_NAME)) {
+ IPADBG("Trying to remove hdr %s offset=%u\n",
+ entry->name, entry->offset_entry->offset);
+ if (!entry->offset_entry->offset) {
+ if (entry->is_hdr_proc_ctx) {
+ mutex_unlock(&ipa_ctx->lock);
+ WARN_ON(1);
+ return -EFAULT;
+ }
+ IPADBG("skip default header\n");
+ continue;
+ }
+ }
if (ipa_id_find(entry->id) == NULL) {
WARN_ON(1);
diff --git a/drivers/platform/msm/ipa/rmnet_ipa.c b/drivers/platform/msm/ipa/rmnet_ipa.c
index ba5426fd0e85..6ff19436a2c9 100644
--- a/drivers/platform/msm/ipa/rmnet_ipa.c
+++ b/drivers/platform/msm/ipa/rmnet_ipa.c
@@ -375,12 +375,15 @@ int copy_ul_filter_rule_to_ipa(struct ipa_install_fltr_rule_req_msg_v01
{
int rc = 0, i, j;
+ /* prevent multi-threads accessing num_q6_rule */
+ mutex_lock(&add_mux_channel_lock);
if (rule_req->filter_spec_list_valid == true) {
num_q6_rule = rule_req->filter_spec_list_len;
IPAWANDBG("Received (%d) install_flt_req\n", num_q6_rule);
} else {
num_q6_rule = 0;
IPAWANERR("got no UL rules from modem\n");
+ mutex_unlock(&add_mux_channel_lock);
return -EINVAL;
}
/* copy UL filter rules from Modem*/
@@ -539,6 +542,7 @@ int copy_ul_filter_rule_to_ipa(struct ipa_install_fltr_rule_req_msg_v01
ipv4_frag_eq_present = rule_req->filter_spec_list[i].
filter_rule.ipv4_frag_eq_present;
}
+ mutex_unlock(&add_mux_channel_lock);
return rc;
}
@@ -1329,8 +1333,11 @@ static int ipa_wwan_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
IPAWANERR("failed to config egress endpoint\n");
if (num_q6_rule != 0) {
+ /* protect num_q6_rule */
+ mutex_lock(&add_mux_channel_lock);
/* already got Q6 UL filter rules*/
rc = wwan_add_ul_flt_rule_to_ipa();
+ mutex_unlock(&add_mux_channel_lock);
egress_set = true;
if (rc)
IPAWANERR("install UL rules failed\n");
diff --git a/drivers/soc/qcom/qdsp6v2/apr.c b/drivers/soc/qcom/qdsp6v2/apr.c
index a295373ed88c..5f25054e9f02 100644
--- a/drivers/soc/qcom/qdsp6v2/apr.c
+++ b/drivers/soc/qcom/qdsp6v2/apr.c
@@ -551,7 +551,8 @@ void apr_cb_func(void *buf, int len, void *priv)
temp_port = ((data.dest_port >> 8) * 8) + (data.dest_port & 0xFF);
pr_debug("port = %d t_port = %d\n", data.src_port, temp_port);
- if (c_svc->port_cnt && c_svc->port_fn[temp_port])
+ if (((temp_port >= 0) && (temp_port < APR_MAX_PORTS))
+ && (c_svc->port_cnt && c_svc->port_fn[temp_port]))
c_svc->port_fn[temp_port](&data, c_svc->port_priv[temp_port]);
else if (c_svc->fn)
c_svc->fn(&data, c_svc->priv);
diff --git a/drivers/usb/class/cdc-acm.c b/drivers/usb/class/cdc-acm.c
index 31e965297c52..2cf90208e3bc 100644
--- a/drivers/usb/class/cdc-acm.c
+++ b/drivers/usb/class/cdc-acm.c
@@ -1025,6 +1025,11 @@ static int acm_probe(struct usb_interface *intf,
}
while (buflen > 0) {
+ if ((buflen < buffer[0]) || (buffer[0] < 3)) {
+ dev_err(&intf->dev, "invalid descriptor buffer length\n");
+ break;
+ }
+
if (buffer[1] != USB_DT_CS_INTERFACE) {
dev_err(&intf->dev, "skipping garbage\n");
goto next_desc;
diff --git a/drivers/usb/class/cdc-wdm.c b/drivers/usb/class/cdc-wdm.c
index 6463ca3bcfba..010ff5bafb60 100644
--- a/drivers/usb/class/cdc-wdm.c
+++ b/drivers/usb/class/cdc-wdm.c
@@ -839,7 +839,12 @@ static int wdm_probe(struct usb_interface *intf, const struct usb_device_id *id)
if (!buffer)
goto err;
- while (buflen > 2) {
+ while (buflen > 0) {
+ if ((buflen < buffer[0]) || (buffer[0] < 3)) {
+ dev_err(&intf->dev, "invalid descriptor buffer length\n");
+ goto err;
+ }
+
if (buffer[1] != USB_DT_CS_INTERFACE) {
dev_err(&intf->dev, "skipping garbage\n");
goto next_desc;
diff --git a/net/ipv4/raw.c b/net/ipv4/raw.c
index c9b79f481939..b304648a759a 100644
--- a/net/ipv4/raw.c
+++ b/net/ipv4/raw.c
@@ -473,11 +473,16 @@ static int raw_sendmsg(struct kiocb *iocb, struct sock *sk, struct msghdr *msg,
u8 tos;
int err;
struct ip_options_data opt_copy;
+ int hdrincl;
err = -EMSGSIZE;
if (len > 0xFFFF)
goto out;
+ /* hdrincl should be READ_ONCE(inet->hdrincl)
+ * but READ_ONCE() doesn't work with bit fields
+ */
+ hdrincl = inet->hdrincl;
/*
* Check the flags.
*/
@@ -548,7 +553,7 @@ static int raw_sendmsg(struct kiocb *iocb, struct sock *sk, struct msghdr *msg,
/* Linux does not mangle headers on raw sockets,
* so that IP options + IP_HDRINCL is non-sense.
*/
- if (inet->hdrincl)
+ if (hdrincl)
goto done;
if (ipc.opt->opt.srr) {
if (!daddr)
@@ -570,12 +575,12 @@ static int raw_sendmsg(struct kiocb *iocb, struct sock *sk, struct msghdr *msg,
flowi4_init_output(&fl4, ipc.oif, sk->sk_mark, tos,
RT_SCOPE_UNIVERSE,
- inet->hdrincl ? IPPROTO_RAW : sk->sk_protocol,
+ hdrincl ? IPPROTO_RAW : sk->sk_protocol,
inet_sk_flowi_flags(sk) | FLOWI_FLAG_CAN_SLEEP |
- (inet->hdrincl ? FLOWI_FLAG_KNOWN_NH : 0),
+ (hdrincl ? FLOWI_FLAG_KNOWN_NH : 0),
daddr, saddr, 0, 0, sk->sk_uid);
- if (!inet->hdrincl) {
+ if (!hdrincl) {
err = raw_probe_proto_opt(&fl4, msg);
if (err)
goto done;
@@ -597,7 +602,7 @@ static int raw_sendmsg(struct kiocb *iocb, struct sock *sk, struct msghdr *msg,
goto do_confirm;
back_from_confirm:
- if (inet->hdrincl)
+ if (hdrincl)
err = raw_send_hdrinc(sk, &fl4, msg->msg_iov, len,
&rt, msg->msg_flags);
diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c
index 4cca5fd91f33..0da9035d7c6f 100644
--- a/net/wireless/nl80211.c
+++ b/net/wireless/nl80211.c
@@ -458,6 +458,14 @@ nl80211_match_policy[NL80211_SCHED_SCAN_MATCH_ATTR_MAX + 1] = {
[NL80211_SCHED_SCAN_MATCH_ATTR_RSSI] = { .type = NLA_U32 },
};
+/* policy for packet pattern attributes */
+static const struct nla_policy
+nl80211_packet_pattern_policy[MAX_NL80211_WOWLAN_PKTPAT + 1] = {
+ [NL80211_WOWLAN_PKTPAT_MASK] = { .type = NLA_BINARY, },
+ [NL80211_WOWLAN_PKTPAT_PATTERN] = { .type = NLA_BINARY, },
+ [NL80211_WOWLAN_PKTPAT_OFFSET] = { .type = NLA_U32 },
+};
+
static int nl80211_prepare_wdev_dump(struct sk_buff *skb,
struct netlink_callback *cb,
struct cfg80211_registered_device **rdev,
@@ -8128,7 +8136,7 @@ static int nl80211_set_wowlan(struct sk_buff *skb, struct genl_info *info)
nla_for_each_nested(pat, tb[NL80211_WOWLAN_TRIG_PKT_PATTERN],
rem) {
nla_parse(pat_tb, MAX_NL80211_WOWLAN_PKTPAT,
- nla_data(pat), nla_len(pat), NULL);
+ nla_data(pat), nla_len(pat), nl80211_packet_pattern_policy);
err = -EINVAL;
if (!pat_tb[NL80211_WOWLAN_PKTPAT_MASK] ||
!pat_tb[NL80211_WOWLAN_PKTPAT_PATTERN])
diff --git a/security/keys/encrypted-keys/encrypted.c b/security/keys/encrypted-keys/encrypted.c
index c4c8df4b214d..258bd532cbf3 100644
--- a/security/keys/encrypted-keys/encrypted.c
+++ b/security/keys/encrypted-keys/encrypted.c
@@ -141,23 +141,22 @@ static int valid_ecryptfs_desc(const char *ecryptfs_desc)
*/
static int valid_master_desc(const char *new_desc, const char *orig_desc)
{
- if (!memcmp(new_desc, KEY_TRUSTED_PREFIX, KEY_TRUSTED_PREFIX_LEN)) {
- if (strlen(new_desc) == KEY_TRUSTED_PREFIX_LEN)
- goto out;
- if (orig_desc)
- if (memcmp(new_desc, orig_desc, KEY_TRUSTED_PREFIX_LEN))
- goto out;
- } else if (!memcmp(new_desc, KEY_USER_PREFIX, KEY_USER_PREFIX_LEN)) {
- if (strlen(new_desc) == KEY_USER_PREFIX_LEN)
- goto out;
- if (orig_desc)
- if (memcmp(new_desc, orig_desc, KEY_USER_PREFIX_LEN))
- goto out;
- } else
- goto out;
+ int prefix_len;
+
+ if (!strncmp(new_desc, KEY_TRUSTED_PREFIX, KEY_TRUSTED_PREFIX_LEN))
+ prefix_len = KEY_TRUSTED_PREFIX_LEN;
+ else if (!strncmp(new_desc, KEY_USER_PREFIX, KEY_USER_PREFIX_LEN))
+ prefix_len = KEY_USER_PREFIX_LEN;
+ else
+ return -EINVAL;
+
+ if (!new_desc[prefix_len])
+ return -EINVAL;
+
+ if (orig_desc && strncmp(new_desc, orig_desc, prefix_len))
+ return -EINVAL;
+
return 0;
-out:
- return -EINVAL;
}
/*