Import of kernel-6.12.0-211.28.1.el10_2
This commit is contained in:
parent
f190b9663a
commit
c259bc25aa
@ -597,8 +597,10 @@ static void vgic_its_invalidate_cache(struct vgic_its *its)
|
||||
unsigned long idx;
|
||||
|
||||
xa_for_each(&its->translation_cache, idx, irq) {
|
||||
xa_erase(&its->translation_cache, idx);
|
||||
vgic_put_irq(kvm, irq);
|
||||
/* Only the context that erases the entry drops its cache ref. */
|
||||
irq = xa_erase(&its->translation_cache, idx);
|
||||
if (irq)
|
||||
vgic_put_irq(kvm, irq);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -95,7 +95,6 @@ static struct workqueue_struct *iwcm_wq;
|
||||
struct iwcm_work {
|
||||
struct work_struct work;
|
||||
struct iwcm_id_private *cm_id;
|
||||
struct list_head list;
|
||||
struct iw_cm_event event;
|
||||
struct list_head free_list;
|
||||
};
|
||||
@ -178,7 +177,6 @@ static int alloc_work_entries(struct iwcm_id_private *cm_id_priv, int count)
|
||||
return -ENOMEM;
|
||||
}
|
||||
work->cm_id = cm_id_priv;
|
||||
INIT_LIST_HEAD(&work->list);
|
||||
put_work(work);
|
||||
}
|
||||
return 0;
|
||||
@ -213,7 +211,6 @@ static void free_cm_id(struct iwcm_id_private *cm_id_priv)
|
||||
static bool iwcm_deref_id(struct iwcm_id_private *cm_id_priv)
|
||||
{
|
||||
if (refcount_dec_and_test(&cm_id_priv->refcount)) {
|
||||
BUG_ON(!list_empty(&cm_id_priv->work_list));
|
||||
free_cm_id(cm_id_priv);
|
||||
return true;
|
||||
}
|
||||
@ -260,7 +257,6 @@ struct iw_cm_id *iw_create_cm_id(struct ib_device *device,
|
||||
refcount_set(&cm_id_priv->refcount, 1);
|
||||
init_waitqueue_head(&cm_id_priv->connect_wait);
|
||||
init_completion(&cm_id_priv->destroy_comp);
|
||||
INIT_LIST_HEAD(&cm_id_priv->work_list);
|
||||
INIT_LIST_HEAD(&cm_id_priv->work_free_list);
|
||||
|
||||
return &cm_id_priv->id;
|
||||
@ -1007,13 +1003,13 @@ static int process_event(struct iwcm_id_private *cm_id_priv,
|
||||
}
|
||||
|
||||
/*
|
||||
* Process events on the work_list for the cm_id. If the callback
|
||||
* function requests that the cm_id be deleted, a flag is set in the
|
||||
* cm_id flags to indicate that when the last reference is
|
||||
* removed, the cm_id is to be destroyed. This is necessary to
|
||||
* distinguish between an object that will be destroyed by the app
|
||||
* thread asleep on the destroy_comp list vs. an object destroyed
|
||||
* here synchronously when the last reference is removed.
|
||||
* Process events for the cm_id. If the callback function requests
|
||||
* that the cm_id be deleted, a flag is set in the cm_id flags to
|
||||
* indicate that when the last reference is removed, the cm_id is
|
||||
* to be destroyed. This is necessary to distinguish between an
|
||||
* object that will be destroyed by the app thread asleep on the
|
||||
* destroy_comp list vs. an object destroyed here synchronously
|
||||
* when the last reference is removed.
|
||||
*/
|
||||
static void cm_work_handler(struct work_struct *_work)
|
||||
{
|
||||
@ -1024,35 +1020,26 @@ static void cm_work_handler(struct work_struct *_work)
|
||||
int ret = 0;
|
||||
|
||||
spin_lock_irqsave(&cm_id_priv->lock, flags);
|
||||
while (!list_empty(&cm_id_priv->work_list)) {
|
||||
work = list_first_entry(&cm_id_priv->work_list,
|
||||
struct iwcm_work, list);
|
||||
list_del_init(&work->list);
|
||||
levent = work->event;
|
||||
put_work(work);
|
||||
spin_unlock_irqrestore(&cm_id_priv->lock, flags);
|
||||
|
||||
if (!test_bit(IWCM_F_DROP_EVENTS, &cm_id_priv->flags)) {
|
||||
ret = process_event(cm_id_priv, &levent);
|
||||
if (ret) {
|
||||
destroy_cm_id(&cm_id_priv->id);
|
||||
WARN_ON_ONCE(iwcm_deref_id(cm_id_priv));
|
||||
}
|
||||
} else
|
||||
pr_debug("dropping event %d\n", levent.event);
|
||||
if (iwcm_deref_id(cm_id_priv))
|
||||
return;
|
||||
spin_lock_irqsave(&cm_id_priv->lock, flags);
|
||||
}
|
||||
levent = work->event;
|
||||
put_work(work);
|
||||
spin_unlock_irqrestore(&cm_id_priv->lock, flags);
|
||||
|
||||
if (!test_bit(IWCM_F_DROP_EVENTS, &cm_id_priv->flags)) {
|
||||
ret = process_event(cm_id_priv, &levent);
|
||||
if (ret) {
|
||||
destroy_cm_id(&cm_id_priv->id);
|
||||
WARN_ON_ONCE(iwcm_deref_id(cm_id_priv));
|
||||
}
|
||||
} else
|
||||
pr_debug("dropping event %d\n", levent.event);
|
||||
if (iwcm_deref_id(cm_id_priv))
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* This function is called on interrupt context. Schedule events on
|
||||
* the iwcm_wq thread to allow callback functions to downcall into
|
||||
* the CM and/or block. Events are queued to a per-CM_ID
|
||||
* work_list. If this is the first event on the work_list, the work
|
||||
* element is also queued on the iwcm_wq thread.
|
||||
* the CM and/or block.
|
||||
*
|
||||
* Each event holds a reference on the cm_id. Until the last posted
|
||||
* event has been delivered and processed, the cm_id cannot be
|
||||
@ -1094,7 +1081,6 @@ static int cm_event_handler(struct iw_cm_id *cm_id,
|
||||
}
|
||||
|
||||
refcount_inc(&cm_id_priv->refcount);
|
||||
list_add_tail(&work->list, &cm_id_priv->work_list);
|
||||
queue_work(iwcm_wq, &work->work);
|
||||
out:
|
||||
spin_unlock_irqrestore(&cm_id_priv->lock, flags);
|
||||
|
||||
@ -50,7 +50,6 @@ struct iwcm_id_private {
|
||||
struct ib_qp *qp;
|
||||
struct completion destroy_comp;
|
||||
wait_queue_head_t connect_wait;
|
||||
struct list_head work_list;
|
||||
spinlock_t lock;
|
||||
refcount_t refcount;
|
||||
struct list_head work_free_list;
|
||||
|
||||
@ -140,8 +140,9 @@ int mana_ib_install_cq_cb(struct mana_ib_dev *mdev, struct mana_ib_cq *cq)
|
||||
|
||||
if (cq->queue.id >= gc->max_num_cqs)
|
||||
return -EINVAL;
|
||||
/* Create CQ table entry */
|
||||
WARN_ON(gc->cq_table[cq->queue.id]);
|
||||
/* Create CQ table entry, sharing a CQ between WQs is not supported */
|
||||
if (gc->cq_table[cq->queue.id])
|
||||
return -EINVAL;
|
||||
if (cq->queue.kmem)
|
||||
gdma_cq = cq->queue.kmem;
|
||||
else
|
||||
|
||||
@ -21,6 +21,9 @@ static int mana_ib_cfg_vport_steering(struct mana_ib_dev *dev,
|
||||
|
||||
gc = mdev_to_gc(dev);
|
||||
|
||||
if (rx_hash_key_len > sizeof(req->hashkey))
|
||||
return -EINVAL;
|
||||
|
||||
req_buf_size = struct_size(req, indir_tab, MANA_INDIRECT_TABLE_DEF_SIZE);
|
||||
req = kzalloc(req_buf_size, GFP_KERNEL);
|
||||
if (!req)
|
||||
|
||||
@ -390,6 +390,19 @@ static void nvmet_tcp_fatal_error(struct nvmet_tcp_queue *queue)
|
||||
|
||||
static void nvmet_tcp_socket_error(struct nvmet_tcp_queue *queue, int status)
|
||||
{
|
||||
/*
|
||||
* Keep rcv_state at RECV_ERR even for the internal -ESHUTDOWN path.
|
||||
* nvmet_tcp_handle_icreq() can return -ESHUTDOWN after the ICReq has
|
||||
* already been consumed and queue teardown has started.
|
||||
*
|
||||
* If nvmet_tcp_data_ready() or nvmet_tcp_write_space() queues
|
||||
* nvmet_tcp_io_work() again before nvmet_tcp_release_queue_work()
|
||||
* cancels it, the queue must not keep that old receive state.
|
||||
* Otherwise the next nvmet_tcp_io_work() run can reach
|
||||
* nvmet_tcp_done_recv_pdu() and try to handle the same ICReq again.
|
||||
*
|
||||
* That is why queue->rcv_state needs to be updated before we return.
|
||||
*/
|
||||
queue->rcv_state = NVMET_TCP_RECV_ERR;
|
||||
if (status == -EPIPE || status == -ECONNRESET)
|
||||
kernel_sock_shutdown(queue->sock, SHUT_RDWR);
|
||||
@ -906,11 +919,24 @@ static int nvmet_tcp_handle_icreq(struct nvmet_tcp_queue *queue)
|
||||
iov.iov_len = sizeof(*icresp);
|
||||
ret = kernel_sendmsg(queue->sock, &msg, &iov, 1, iov.iov_len);
|
||||
if (ret < 0) {
|
||||
spin_lock_bh(&queue->state_lock);
|
||||
if (queue->state == NVMET_TCP_Q_DISCONNECTING) {
|
||||
spin_unlock_bh(&queue->state_lock);
|
||||
return -ESHUTDOWN;
|
||||
}
|
||||
queue->state = NVMET_TCP_Q_FAILED;
|
||||
spin_unlock_bh(&queue->state_lock);
|
||||
return ret; /* queue removal will cleanup */
|
||||
}
|
||||
|
||||
spin_lock_bh(&queue->state_lock);
|
||||
if (queue->state == NVMET_TCP_Q_DISCONNECTING) {
|
||||
spin_unlock_bh(&queue->state_lock);
|
||||
/* Tell nvmet_tcp_socket_error() teardown is in progress. */
|
||||
return -ESHUTDOWN;
|
||||
}
|
||||
queue->state = NVMET_TCP_Q_LIVE;
|
||||
spin_unlock_bh(&queue->state_lock);
|
||||
nvmet_prepare_receive_pdu(queue);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -2751,7 +2751,6 @@ qla24xx_els_dcmd_iocb(scsi_qla_host_t *vha, int els_opcode,
|
||||
if (!elsio->u.els_logo.els_logo_pyld) {
|
||||
/* ref: INIT */
|
||||
kref_put(&sp->cmd_kref, qla2x00_sp_release);
|
||||
qla2x00_free_fcport(fcport);
|
||||
return QLA_FUNCTION_FAILED;
|
||||
}
|
||||
|
||||
@ -2776,7 +2775,6 @@ qla24xx_els_dcmd_iocb(scsi_qla_host_t *vha, int els_opcode,
|
||||
if (rval != QLA_SUCCESS) {
|
||||
/* ref: INIT */
|
||||
kref_put(&sp->cmd_kref, qla2x00_sp_release);
|
||||
qla2x00_free_fcport(fcport);
|
||||
return QLA_FUNCTION_FAILED;
|
||||
}
|
||||
|
||||
|
||||
@ -42,7 +42,9 @@ struct inet_connection_sock_af_ops {
|
||||
struct request_sock *req,
|
||||
struct dst_entry *dst,
|
||||
struct request_sock *req_unhash,
|
||||
bool *own_req);
|
||||
bool *own_req,
|
||||
void (*opt_child_init)(struct sock *newsk,
|
||||
const struct sock *sk));
|
||||
u16 net_header_len;
|
||||
u16 sockaddr_len;
|
||||
int (*setsockopt)(struct sock *sk, int level, int optname,
|
||||
|
||||
@ -465,7 +465,9 @@ struct sock *tcp_v4_syn_recv_sock(const struct sock *sk, struct sk_buff *skb,
|
||||
struct request_sock *req,
|
||||
struct dst_entry *dst,
|
||||
struct request_sock *req_unhash,
|
||||
bool *own_req);
|
||||
bool *own_req,
|
||||
void (*opt_child_init)(struct sock *newsk,
|
||||
const struct sock *sk));
|
||||
int tcp_v4_do_rcv(struct sock *sk, struct sk_buff *skb);
|
||||
int tcp_v4_connect(struct sock *sk, struct sockaddr *uaddr, int addr_len);
|
||||
int tcp_connect(struct sock *sk);
|
||||
|
||||
@ -1,2 +1,2 @@
|
||||
sbat,1,SBAT Version,sbat,1,https://github.com/rhboot/shim/blob/main/SBAT.md
|
||||
kernel.almalinux,1,AlmaLinux,kernel-core,6.12.0-211.26.1.el10.x86_64,mailto:security@almalinux.org
|
||||
kernel.almalinux,1,AlmaLinux,kernel-core,6.12.0-211.28.1.el10.x86_64,mailto:security@almalinux.org
|
||||
|
||||
@ -202,7 +202,7 @@ struct sock *tcp_get_cookie_sock(struct sock *sk, struct sk_buff *skb,
|
||||
bool own_req;
|
||||
|
||||
child = icsk->icsk_af_ops->syn_recv_sock(sk, skb, req, dst,
|
||||
NULL, &own_req);
|
||||
NULL, &own_req, NULL);
|
||||
if (child) {
|
||||
refcount_set(&req->rsk_refcnt, 1);
|
||||
sock_rps_save_rxhash(child, skb);
|
||||
|
||||
@ -247,7 +247,7 @@ static struct sock *tcp_fastopen_create_child(struct sock *sk,
|
||||
bool own_req;
|
||||
|
||||
child = inet_csk(sk)->icsk_af_ops->syn_recv_sock(sk, skb, req, NULL,
|
||||
NULL, &own_req);
|
||||
NULL, &own_req, NULL);
|
||||
if (!child)
|
||||
return NULL;
|
||||
|
||||
|
||||
@ -1739,7 +1739,9 @@ struct sock *tcp_v4_syn_recv_sock(const struct sock *sk, struct sk_buff *skb,
|
||||
struct request_sock *req,
|
||||
struct dst_entry *dst,
|
||||
struct request_sock *req_unhash,
|
||||
bool *own_req)
|
||||
bool *own_req,
|
||||
void (*opt_child_init)(struct sock *newsk,
|
||||
const struct sock *sk))
|
||||
{
|
||||
struct inet_request_sock *ireq;
|
||||
bool found_dup_sk = false;
|
||||
@ -1795,6 +1797,10 @@ struct sock *tcp_v4_syn_recv_sock(const struct sock *sk, struct sk_buff *skb,
|
||||
}
|
||||
sk_setup_caps(newsk, dst);
|
||||
|
||||
#if IS_ENABLED(CONFIG_IPV6)
|
||||
if (opt_child_init)
|
||||
opt_child_init(newsk, sk);
|
||||
#endif
|
||||
tcp_ca_openreq_child(newsk, dst);
|
||||
|
||||
tcp_sync_mss(newsk, dst_mtu(dst));
|
||||
|
||||
@ -862,7 +862,7 @@ struct sock *tcp_check_req(struct sock *sk, struct sk_buff *skb,
|
||||
* socket is created, wait for troubles.
|
||||
*/
|
||||
child = inet_csk(sk)->icsk_af_ops->syn_recv_sock(sk, skb, req, NULL,
|
||||
req, &own_req);
|
||||
req, &own_req, NULL);
|
||||
if (!child)
|
||||
goto listen_overflow;
|
||||
|
||||
|
||||
@ -681,6 +681,9 @@ int ip6_err_gen_icmpv6_unreach(struct sk_buff *skb, int nhs, int type,
|
||||
if (!skb2)
|
||||
return 1;
|
||||
|
||||
/* Remove debris left by IPv4 stack. */
|
||||
memset(IP6CB(skb2), 0, sizeof(*IP6CB(skb2)));
|
||||
|
||||
skb_dst_drop(skb2);
|
||||
skb_pull(skb2, nhs);
|
||||
skb_reset_network_header(skb2);
|
||||
|
||||
@ -1343,11 +1343,48 @@ static void tcp_v6_restore_cb(struct sk_buff *skb)
|
||||
sizeof(struct inet6_skb_parm));
|
||||
}
|
||||
|
||||
/* Called from tcp_v4_syn_recv_sock() for v6_mapped children. */
|
||||
static void tcp_v6_mapped_child_init(struct sock *newsk, const struct sock *sk)
|
||||
{
|
||||
struct inet_sock *newinet = inet_sk(newsk);
|
||||
struct ipv6_pinfo *newnp;
|
||||
|
||||
newinet->pinet6 = newnp = tcp_inet6_sk(newsk);
|
||||
|
||||
memcpy(newnp, tcp_inet6_sk(sk), sizeof(struct ipv6_pinfo));
|
||||
|
||||
newnp->saddr = newsk->sk_v6_rcv_saddr;
|
||||
|
||||
inet_csk(newsk)->icsk_af_ops = &ipv6_mapped;
|
||||
if (sk_is_mptcp(newsk))
|
||||
mptcpv6_handle_mapped(newsk, true);
|
||||
newsk->sk_backlog_rcv = tcp_v4_do_rcv;
|
||||
#if defined(CONFIG_TCP_MD5SIG) || defined(CONFIG_TCP_AO)
|
||||
tcp_sk(newsk)->af_specific = &tcp_sock_ipv6_mapped_specific;
|
||||
#endif
|
||||
|
||||
newnp->ipv6_mc_list = NULL;
|
||||
newnp->ipv6_ac_list = NULL;
|
||||
newnp->ipv6_fl_list = NULL;
|
||||
newnp->pktoptions = NULL;
|
||||
newnp->opt = NULL;
|
||||
|
||||
/* tcp_v4_syn_recv_sock() has initialized newinet->mc_{index,ttl} */
|
||||
newnp->mcast_oif = newinet->mc_index;
|
||||
newnp->mcast_hops = newinet->mc_ttl;
|
||||
|
||||
newnp->rcv_flowinfo = 0;
|
||||
if (inet6_test_bit(REPFLOW, sk))
|
||||
newnp->flow_label = 0;
|
||||
}
|
||||
|
||||
static struct sock *tcp_v6_syn_recv_sock(const struct sock *sk, struct sk_buff *skb,
|
||||
struct request_sock *req,
|
||||
struct dst_entry *dst,
|
||||
struct request_sock *req_unhash,
|
||||
bool *own_req)
|
||||
bool *own_req,
|
||||
void (*opt_child_init)(struct sock *newsk,
|
||||
const struct sock *sk))
|
||||
{
|
||||
struct inet_request_sock *ireq;
|
||||
struct ipv6_pinfo *newnp;
|
||||
@ -1363,60 +1400,10 @@ static struct sock *tcp_v6_syn_recv_sock(const struct sock *sk, struct sk_buff *
|
||||
#endif
|
||||
struct flowi6 fl6;
|
||||
|
||||
if (skb->protocol == htons(ETH_P_IP)) {
|
||||
/*
|
||||
* v6 mapped
|
||||
*/
|
||||
|
||||
newsk = tcp_v4_syn_recv_sock(sk, skb, req, dst,
|
||||
req_unhash, own_req);
|
||||
|
||||
if (!newsk)
|
||||
return NULL;
|
||||
|
||||
inet_sk(newsk)->pinet6 = tcp_inet6_sk(newsk);
|
||||
|
||||
newnp = tcp_inet6_sk(newsk);
|
||||
newtp = tcp_sk(newsk);
|
||||
|
||||
memcpy(newnp, np, sizeof(struct ipv6_pinfo));
|
||||
|
||||
newnp->saddr = newsk->sk_v6_rcv_saddr;
|
||||
|
||||
inet_csk(newsk)->icsk_af_ops = &ipv6_mapped;
|
||||
if (sk_is_mptcp(newsk))
|
||||
mptcpv6_handle_mapped(newsk, true);
|
||||
newsk->sk_backlog_rcv = tcp_v4_do_rcv;
|
||||
#if defined(CONFIG_TCP_MD5SIG) || defined(CONFIG_TCP_AO)
|
||||
newtp->af_specific = &tcp_sock_ipv6_mapped_specific;
|
||||
#endif
|
||||
|
||||
newnp->ipv6_mc_list = NULL;
|
||||
newnp->ipv6_ac_list = NULL;
|
||||
newnp->ipv6_fl_list = NULL;
|
||||
newnp->pktoptions = NULL;
|
||||
newnp->opt = NULL;
|
||||
newnp->mcast_oif = inet_iif(skb);
|
||||
newnp->mcast_hops = ip_hdr(skb)->ttl;
|
||||
newnp->rcv_flowinfo = 0;
|
||||
if (inet6_test_bit(REPFLOW, sk))
|
||||
newnp->flow_label = 0;
|
||||
|
||||
/*
|
||||
* No need to charge this sock to the relevant IPv6 refcnt debug socks count
|
||||
* here, tcp_create_openreq_child now does this for us, see the comment in
|
||||
* that function for the gory details. -acme
|
||||
*/
|
||||
|
||||
/* It is tricky place. Until this moment IPv4 tcp
|
||||
worked with IPv6 icsk.icsk_af_ops.
|
||||
Sync it now.
|
||||
*/
|
||||
tcp_sync_mss(newsk, inet_csk(newsk)->icsk_pmtu_cookie);
|
||||
|
||||
return newsk;
|
||||
}
|
||||
|
||||
if (skb->protocol == htons(ETH_P_IP))
|
||||
return tcp_v4_syn_recv_sock(sk, skb, req, dst,
|
||||
req_unhash, own_req,
|
||||
tcp_v6_mapped_child_init);
|
||||
ireq = inet_rsk(req);
|
||||
|
||||
if (sk_acceptq_is_full(sk))
|
||||
|
||||
@ -809,7 +809,9 @@ static struct sock *subflow_syn_recv_sock(const struct sock *sk,
|
||||
struct request_sock *req,
|
||||
struct dst_entry *dst,
|
||||
struct request_sock *req_unhash,
|
||||
bool *own_req)
|
||||
bool *own_req,
|
||||
void (*opt_child_init)(struct sock *newsk,
|
||||
const struct sock *sk))
|
||||
{
|
||||
struct mptcp_subflow_context *listener = mptcp_subflow_ctx(sk);
|
||||
struct mptcp_subflow_request_sock *subflow_req;
|
||||
@ -856,7 +858,7 @@ static struct sock *subflow_syn_recv_sock(const struct sock *sk,
|
||||
|
||||
create_child:
|
||||
child = listener->icsk_af_ops->syn_recv_sock(sk, skb, req, dst,
|
||||
req_unhash, own_req);
|
||||
req_unhash, own_req, opt_child_init);
|
||||
|
||||
if (child && *own_req) {
|
||||
struct mptcp_subflow_context *ctx = mptcp_subflow_ctx(child);
|
||||
|
||||
@ -1164,7 +1164,8 @@ static int rxgk_verify_authenticator(struct rxrpc_connection *conn,
|
||||
}
|
||||
|
||||
p = auth;
|
||||
ret = rxgk_do_verify_authenticator(conn, krb5, skb, p, p + auth_len);
|
||||
ret = rxgk_do_verify_authenticator(conn, krb5, skb, p,
|
||||
p + auth_len / sizeof(*p));
|
||||
error:
|
||||
kfree(auth);
|
||||
return ret;
|
||||
|
||||
@ -125,7 +125,9 @@ static struct sock *smc_tcp_syn_recv_sock(const struct sock *sk,
|
||||
struct request_sock *req,
|
||||
struct dst_entry *dst,
|
||||
struct request_sock *req_unhash,
|
||||
bool *own_req)
|
||||
bool *own_req,
|
||||
void (*opt_child_init)(struct sock *newsk,
|
||||
const struct sock *sk))
|
||||
{
|
||||
struct smc_sock *smc;
|
||||
struct sock *child;
|
||||
@ -143,7 +145,7 @@ static struct sock *smc_tcp_syn_recv_sock(const struct sock *sk,
|
||||
|
||||
/* passthrough to original syn recv sock fct */
|
||||
child = smc->ori_af_ops->syn_recv_sock(sk, skb, req, dst, req_unhash,
|
||||
own_req);
|
||||
own_req, opt_child_init);
|
||||
/* child must not inherit smc or its ops */
|
||||
if (child) {
|
||||
rcu_assign_sk_user_data(child, NULL);
|
||||
|
||||
@ -3808,7 +3808,7 @@ static int default_noexec __ro_after_init;
|
||||
|
||||
static int __file_map_prot_check(const struct cred *cred,
|
||||
const struct file *file, unsigned long prot,
|
||||
bool shared, bool bf_user_file)
|
||||
bool shared, bool mounter, bool bf_user_file)
|
||||
{
|
||||
struct inode *inode = NULL;
|
||||
bool prot_exec = prot & PROT_EXEC;
|
||||
@ -3822,7 +3822,7 @@ static int __file_map_prot_check(const struct cred *cred,
|
||||
}
|
||||
|
||||
if (default_noexec && prot_exec &&
|
||||
(!file || IS_PRIVATE(inode) || (!shared && prot_write))) {
|
||||
(!file || IS_PRIVATE(inode) || (!shared && prot_write)) && !mounter) {
|
||||
int rc;
|
||||
u32 sid = cred_sid(cred);
|
||||
|
||||
@ -3852,9 +3852,9 @@ static int __file_map_prot_check(const struct cred *cred,
|
||||
|
||||
static inline int file_map_prot_check(const struct cred *cred,
|
||||
const struct file *file,
|
||||
unsigned long prot, bool shared)
|
||||
unsigned long prot, bool shared, bool mounter)
|
||||
{
|
||||
return __file_map_prot_check(cred, file, prot, shared, false);
|
||||
return __file_map_prot_check(cred, file, prot, shared, mounter, false);
|
||||
}
|
||||
|
||||
static int selinux_mmap_addr(unsigned long addr)
|
||||
@ -3871,7 +3871,7 @@ static int selinux_mmap_addr(unsigned long addr)
|
||||
}
|
||||
|
||||
static int selinux_mmap_file_common(const struct cred *cred, struct file *file,
|
||||
unsigned long prot, bool shared)
|
||||
unsigned long prot, bool shared, bool mounter)
|
||||
{
|
||||
if (file) {
|
||||
int rc;
|
||||
@ -3884,7 +3884,7 @@ static int selinux_mmap_file_common(const struct cred *cred, struct file *file,
|
||||
return rc;
|
||||
}
|
||||
|
||||
return file_map_prot_check(cred, file, prot, shared);
|
||||
return file_map_prot_check(cred, file, prot, shared, mounter);
|
||||
}
|
||||
|
||||
static int selinux_mmap_file(struct file *file,
|
||||
@ -3892,7 +3892,8 @@ static int selinux_mmap_file(struct file *file,
|
||||
unsigned long prot, unsigned long flags)
|
||||
{
|
||||
return selinux_mmap_file_common(current_cred(), file, prot,
|
||||
(flags & MAP_TYPE) == MAP_SHARED);
|
||||
(flags & MAP_TYPE) == MAP_SHARED,
|
||||
false);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -3925,7 +3926,8 @@ static int selinux_mmap_backing_file(struct vm_area_struct *vma,
|
||||
prot |= PROT_EXEC;
|
||||
|
||||
return selinux_mmap_file_common(backing_file->f_cred, backing_file,
|
||||
prot, vma->vm_flags & VM_SHARED);
|
||||
prot, vma->vm_flags & VM_SHARED,
|
||||
true);
|
||||
}
|
||||
|
||||
static int selinux_file_mprotect(struct vm_area_struct *vma,
|
||||
@ -3986,11 +3988,11 @@ static int selinux_file_mprotect(struct vm_area_struct *vma,
|
||||
}
|
||||
}
|
||||
|
||||
rc = __file_map_prot_check(cred, file, prot, shared, backing_file);
|
||||
rc = __file_map_prot_check(cred, file, prot, shared, false, backing_file);
|
||||
if (rc)
|
||||
return rc;
|
||||
if (backing_file) {
|
||||
rc = file_map_prot_check(file->f_cred, file, prot, shared);
|
||||
rc = file_map_prot_check(file->f_cred, file, prot, shared, true);
|
||||
if (rc)
|
||||
return rc;
|
||||
}
|
||||
|
||||
@ -1,2 +1,2 @@
|
||||
sbat,1,SBAT Version,sbat,1,https://github.com/rhboot/shim/blob/main/SBAT.md
|
||||
kernel-uki-virt-addons.almalinux,1,AlmaLinux,kernel-uki-virt-addons,6.12.0-211.26.1.el10.x86_64,mailto:security@almalinux.org
|
||||
kernel-uki-virt-addons.almalinux,1,AlmaLinux,kernel-uki-virt-addons,6.12.0-211.28.1.el10.x86_64,mailto:security@almalinux.org
|
||||
|
||||
2
uki.sbat
2
uki.sbat
@ -1,2 +1,2 @@
|
||||
sbat,1,SBAT Version,sbat,1,https://github.com/rhboot/shim/blob/main/SBAT.md
|
||||
kernel-uki-virt.almalinux,1,AlmaLinux,kernel-uki-virt,6.12.0-211.26.1.el10.x86_64,mailto:security@almalinux.org
|
||||
kernel-uki-virt.almalinux,1,AlmaLinux,kernel-uki-virt,6.12.0-211.28.1.el10.x86_64,mailto:security@almalinux.org
|
||||
|
||||
Loading…
Reference in New Issue
Block a user