^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) #include <linux/in.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) #include <linux/inet.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) #include <linux/list.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) #include <linux/net.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) #include <linux/proc_fs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) #include <linux/rculist.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #include <linux/seq_file.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <linux/socket.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <net/inet_sock.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <net/kcm.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <net/net_namespace.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <net/netns/generic.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) #include <net/tcp.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #ifdef CONFIG_PROC_FS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) static struct kcm_mux *kcm_get_first(struct seq_file *seq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) struct net *net = seq_file_net(seq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) struct kcm_net *knet = net_generic(net, kcm_net_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) return list_first_or_null_rcu(&knet->mux_list,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) struct kcm_mux, kcm_mux_list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) static struct kcm_mux *kcm_get_next(struct kcm_mux *mux)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) struct kcm_net *knet = mux->knet;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) return list_next_or_null_rcu(&knet->mux_list, &mux->kcm_mux_list,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) struct kcm_mux, kcm_mux_list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) static struct kcm_mux *kcm_get_idx(struct seq_file *seq, loff_t pos)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) struct net *net = seq_file_net(seq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) struct kcm_net *knet = net_generic(net, kcm_net_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) struct kcm_mux *m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) list_for_each_entry_rcu(m, &knet->mux_list, kcm_mux_list) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) if (!pos)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) return m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) --pos;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) static void *kcm_seq_next(struct seq_file *seq, void *v, loff_t *pos)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) void *p;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) if (v == SEQ_START_TOKEN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) p = kcm_get_first(seq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) p = kcm_get_next(v);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) ++*pos;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) return p;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) static void *kcm_seq_start(struct seq_file *seq, loff_t *pos)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) __acquires(rcu)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) rcu_read_lock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) if (!*pos)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) return SEQ_START_TOKEN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) return kcm_get_idx(seq, *pos - 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) static void kcm_seq_stop(struct seq_file *seq, void *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) __releases(rcu)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) rcu_read_unlock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) struct kcm_proc_mux_state {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) struct seq_net_private p;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) int idx;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) static void kcm_format_mux_header(struct seq_file *seq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) struct net *net = seq_file_net(seq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) struct kcm_net *knet = net_generic(net, kcm_net_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) seq_printf(seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) "*** KCM statistics (%d MUX) ****\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) knet->count);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) seq_printf(seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) "%-14s %-10s %-16s %-10s %-16s %-8s %-8s %-8s %-8s %s",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) "Object",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) "RX-Msgs",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) "RX-Bytes",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) "TX-Msgs",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) "TX-Bytes",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) "Recv-Q",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) "Rmem",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) "Send-Q",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) "Smem",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) "Status");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) /* XXX: pdsts header stuff here */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) seq_puts(seq, "\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) static void kcm_format_sock(struct kcm_sock *kcm, struct seq_file *seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) int i, int *len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) seq_printf(seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) " kcm-%-7u %-10llu %-16llu %-10llu %-16llu %-8d %-8d %-8d %-8s ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) kcm->index,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) kcm->stats.rx_msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) kcm->stats.rx_bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) kcm->stats.tx_msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) kcm->stats.tx_bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) kcm->sk.sk_receive_queue.qlen,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) sk_rmem_alloc_get(&kcm->sk),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) kcm->sk.sk_write_queue.qlen,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) "-");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) if (kcm->tx_psock)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) seq_printf(seq, "Psck-%u ", kcm->tx_psock->index);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) if (kcm->tx_wait)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) seq_puts(seq, "TxWait ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) if (kcm->tx_wait_more)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) seq_puts(seq, "WMore ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) if (kcm->rx_wait)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) seq_puts(seq, "RxWait ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) seq_puts(seq, "\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) static void kcm_format_psock(struct kcm_psock *psock, struct seq_file *seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) int i, int *len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) seq_printf(seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) " psock-%-5u %-10llu %-16llu %-10llu %-16llu %-8d %-8d %-8d %-8d ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) psock->index,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) psock->strp.stats.msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) psock->strp.stats.bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) psock->stats.tx_msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) psock->stats.tx_bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) psock->sk->sk_receive_queue.qlen,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) atomic_read(&psock->sk->sk_rmem_alloc),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) psock->sk->sk_write_queue.qlen,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) refcount_read(&psock->sk->sk_wmem_alloc));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) if (psock->done)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) seq_puts(seq, "Done ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) if (psock->tx_stopped)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) seq_puts(seq, "TxStop ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) if (psock->strp.stopped)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) seq_puts(seq, "RxStop ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) if (psock->tx_kcm)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) seq_printf(seq, "Rsvd-%d ", psock->tx_kcm->index);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) if (!psock->strp.paused && !psock->ready_rx_msg) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) if (psock->sk->sk_receive_queue.qlen) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) if (psock->strp.need_bytes)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) seq_printf(seq, "RxWait=%u ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) psock->strp.need_bytes);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) seq_printf(seq, "RxWait ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) if (psock->strp.paused)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) seq_puts(seq, "RxPause ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) if (psock->ready_rx_msg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) seq_puts(seq, "RdyRx ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) seq_puts(seq, "\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) static void
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) kcm_format_mux(struct kcm_mux *mux, loff_t idx, struct seq_file *seq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) int i, len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) struct kcm_sock *kcm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) struct kcm_psock *psock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) /* mux information */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) seq_printf(seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) "%-6s%-8s %-10llu %-16llu %-10llu %-16llu %-8s %-8s %-8s %-8s ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) "mux", "",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) mux->stats.rx_msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) mux->stats.rx_bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) mux->stats.tx_msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) mux->stats.tx_bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) "-", "-", "-", "-");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) seq_printf(seq, "KCMs: %d, Psocks %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) mux->kcm_socks_cnt, mux->psocks_cnt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) /* kcm sock information */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) i = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) spin_lock_bh(&mux->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) list_for_each_entry(kcm, &mux->kcm_socks, kcm_sock_list) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) kcm_format_sock(kcm, seq, i, &len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) i++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) i = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) list_for_each_entry(psock, &mux->psocks, psock_list) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) kcm_format_psock(psock, seq, i, &len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) i++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) spin_unlock_bh(&mux->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) static int kcm_seq_show(struct seq_file *seq, void *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) struct kcm_proc_mux_state *mux_state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) mux_state = seq->private;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) if (v == SEQ_START_TOKEN) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) mux_state->idx = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) kcm_format_mux_header(seq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) kcm_format_mux(v, mux_state->idx, seq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) mux_state->idx++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) static const struct seq_operations kcm_seq_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) .show = kcm_seq_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) .start = kcm_seq_start,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) .next = kcm_seq_next,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) .stop = kcm_seq_stop,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) static int kcm_stats_seq_show(struct seq_file *seq, void *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) struct kcm_psock_stats psock_stats;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) struct kcm_mux_stats mux_stats;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) struct strp_aggr_stats strp_stats;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) struct kcm_mux *mux;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) struct kcm_psock *psock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) struct net *net = seq->private;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) struct kcm_net *knet = net_generic(net, kcm_net_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) memset(&mux_stats, 0, sizeof(mux_stats));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) memset(&psock_stats, 0, sizeof(psock_stats));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) memset(&strp_stats, 0, sizeof(strp_stats));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) mutex_lock(&knet->mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) aggregate_mux_stats(&knet->aggregate_mux_stats, &mux_stats);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) aggregate_psock_stats(&knet->aggregate_psock_stats,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) &psock_stats);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) aggregate_strp_stats(&knet->aggregate_strp_stats,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) &strp_stats);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) list_for_each_entry(mux, &knet->mux_list, kcm_mux_list) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) spin_lock_bh(&mux->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) aggregate_mux_stats(&mux->stats, &mux_stats);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) aggregate_psock_stats(&mux->aggregate_psock_stats,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) &psock_stats);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) aggregate_strp_stats(&mux->aggregate_strp_stats,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) &strp_stats);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) list_for_each_entry(psock, &mux->psocks, psock_list) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) aggregate_psock_stats(&psock->stats, &psock_stats);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) save_strp_stats(&psock->strp, &strp_stats);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) spin_unlock_bh(&mux->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) mutex_unlock(&knet->mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) seq_printf(seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) "%-8s %-10s %-16s %-10s %-16s %-10s %-10s %-10s %-10s %-10s\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) "MUX",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) "RX-Msgs",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) "RX-Bytes",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) "TX-Msgs",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) "TX-Bytes",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) "TX-Retries",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) "Attach",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) "Unattach",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) "UnattchRsvd",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) "RX-RdyDrops");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) seq_printf(seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) "%-8s %-10llu %-16llu %-10llu %-16llu %-10u %-10u %-10u %-10u %-10u\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) "",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) mux_stats.rx_msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) mux_stats.rx_bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) mux_stats.tx_msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) mux_stats.tx_bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) mux_stats.tx_retries,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) mux_stats.psock_attach,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) mux_stats.psock_unattach_rsvd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) mux_stats.psock_unattach,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) mux_stats.rx_ready_drops);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) seq_printf(seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) "%-8s %-10s %-16s %-10s %-16s %-10s %-10s %-10s %-10s %-10s %-10s %-10s %-10s %-10s %-10s %-10s\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) "Psock",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) "RX-Msgs",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) "RX-Bytes",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) "TX-Msgs",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) "TX-Bytes",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) "Reserved",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) "Unreserved",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) "RX-Aborts",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) "RX-Intr",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) "RX-Unrecov",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) "RX-MemFail",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) "RX-NeedMor",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) "RX-BadLen",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) "RX-TooBig",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) "RX-Timeout",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) "TX-Aborts");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) seq_printf(seq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) "%-8s %-10llu %-16llu %-10llu %-16llu %-10llu %-10llu %-10u %-10u %-10u %-10u %-10u %-10u %-10u %-10u %-10u\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) "",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) strp_stats.msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) strp_stats.bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) psock_stats.tx_msgs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) psock_stats.tx_bytes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) psock_stats.reserved,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) psock_stats.unreserved,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) strp_stats.aborts,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) strp_stats.interrupted,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) strp_stats.unrecov_intr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) strp_stats.mem_fail,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) strp_stats.need_more_hdr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) strp_stats.bad_hdr_len,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) strp_stats.msg_too_big,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) strp_stats.msg_timeouts,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) psock_stats.tx_aborts);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) static int kcm_proc_init_net(struct net *net)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) if (!proc_create_net_single("kcm_stats", 0444, net->proc_net,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) kcm_stats_seq_show, NULL))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) goto out_kcm_stats;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) if (!proc_create_net("kcm", 0444, net->proc_net, &kcm_seq_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) sizeof(struct kcm_proc_mux_state)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) goto out_kcm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) out_kcm:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) remove_proc_entry("kcm_stats", net->proc_net);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) out_kcm_stats:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) static void kcm_proc_exit_net(struct net *net)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) remove_proc_entry("kcm", net->proc_net);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) remove_proc_entry("kcm_stats", net->proc_net);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) static struct pernet_operations kcm_net_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) .init = kcm_proc_init_net,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) .exit = kcm_proc_exit_net,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) int __init kcm_proc_init(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) return register_pernet_subsys(&kcm_net_ops);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) void __exit kcm_proc_exit(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) unregister_pernet_subsys(&kcm_net_ops);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) #endif /* CONFIG_PROC_FS */