aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorXin Long <lucien.xin@gmail.com>2016-04-14 03:35:32 -0400
committerDavid S. Miller <davem@davemloft.net>2016-04-15 17:29:36 -0400
commitcb2050a7b8131a9a9f3f97276df1feaae8987dc8 (patch)
treef79ff0f83cf164245f5312bafc30ce933e04b99c
parent626d16f50f39bb9c44f98fd256cae2b864900a01 (diff)
sctp: export some functions for sctp_diag in inet_diag
inet_diag_msg_common_fill is used to fill the diag msg common info, we need to use it in sctp_diag as well, so export it. inet_diag_msg_attrs_fill is used to fill some common attrs info between sctp diag and tcp diag. v2->v3: - do not need to define and export inet_diag_get_handler any more. cause all the functions in it are in sctp_diag.ko, we just call them in sctp_diag.ko. - add inet_diag_msg_attrs_fill to make codes clear. Signed-off-by: Xin Long <lucien.xin@gmail.com> Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r--net/ipv4/inet_diag.c67
1 files changed, 41 insertions, 26 deletions
diff --git a/net/ipv4/inet_diag.c b/net/ipv4/inet_diag.c
index bd591eb81ec9..70212bddf0f8 100644
--- a/net/ipv4/inet_diag.c
+++ b/net/ipv4/inet_diag.c
@@ -66,7 +66,7 @@ static void inet_diag_unlock_handler(const struct inet_diag_handler *handler)
66 mutex_unlock(&inet_diag_table_mutex); 66 mutex_unlock(&inet_diag_table_mutex);
67} 67}
68 68
69static void inet_diag_msg_common_fill(struct inet_diag_msg *r, struct sock *sk) 69void inet_diag_msg_common_fill(struct inet_diag_msg *r, struct sock *sk)
70{ 70{
71 r->idiag_family = sk->sk_family; 71 r->idiag_family = sk->sk_family;
72 72
@@ -89,6 +89,7 @@ static void inet_diag_msg_common_fill(struct inet_diag_msg *r, struct sock *sk)
89 r->id.idiag_dst[0] = sk->sk_daddr; 89 r->id.idiag_dst[0] = sk->sk_daddr;
90 } 90 }
91} 91}
92EXPORT_SYMBOL_GPL(inet_diag_msg_common_fill);
92 93
93static size_t inet_sk_attr_size(void) 94static size_t inet_sk_attr_size(void)
94{ 95{
@@ -104,13 +105,50 @@ static size_t inet_sk_attr_size(void)
104 + 64; 105 + 64;
105} 106}
106 107
108int inet_diag_msg_attrs_fill(struct sock *sk, struct sk_buff *skb,
109 struct inet_diag_msg *r, int ext,
110 struct user_namespace *user_ns)
111{
112 const struct inet_sock *inet = inet_sk(sk);
113
114 if (nla_put_u8(skb, INET_DIAG_SHUTDOWN, sk->sk_shutdown))
115 goto errout;
116
117 /* IPv6 dual-stack sockets use inet->tos for IPv4 connections,
118 * hence this needs to be included regardless of socket family.
119 */
120 if (ext & (1 << (INET_DIAG_TOS - 1)))
121 if (nla_put_u8(skb, INET_DIAG_TOS, inet->tos) < 0)
122 goto errout;
123
124#if IS_ENABLED(CONFIG_IPV6)
125 if (r->idiag_family == AF_INET6) {
126 if (ext & (1 << (INET_DIAG_TCLASS - 1)))
127 if (nla_put_u8(skb, INET_DIAG_TCLASS,
128 inet6_sk(sk)->tclass) < 0)
129 goto errout;
130
131 if (((1 << sk->sk_state) & (TCPF_LISTEN | TCPF_CLOSE)) &&
132 nla_put_u8(skb, INET_DIAG_SKV6ONLY, ipv6_only_sock(sk)))
133 goto errout;
134 }
135#endif
136
137 r->idiag_uid = from_kuid_munged(user_ns, sock_i_uid(sk));
138 r->idiag_inode = sock_i_ino(sk);
139
140 return 0;
141errout:
142 return 1;
143}
144EXPORT_SYMBOL_GPL(inet_diag_msg_attrs_fill);
145
107int inet_sk_diag_fill(struct sock *sk, struct inet_connection_sock *icsk, 146int inet_sk_diag_fill(struct sock *sk, struct inet_connection_sock *icsk,
108 struct sk_buff *skb, const struct inet_diag_req_v2 *req, 147 struct sk_buff *skb, const struct inet_diag_req_v2 *req,
109 struct user_namespace *user_ns, 148 struct user_namespace *user_ns,
110 u32 portid, u32 seq, u16 nlmsg_flags, 149 u32 portid, u32 seq, u16 nlmsg_flags,
111 const struct nlmsghdr *unlh) 150 const struct nlmsghdr *unlh)
112{ 151{
113 const struct inet_sock *inet = inet_sk(sk);
114 const struct tcp_congestion_ops *ca_ops; 152 const struct tcp_congestion_ops *ca_ops;
115 const struct inet_diag_handler *handler; 153 const struct inet_diag_handler *handler;
116 int ext = req->idiag_ext; 154 int ext = req->idiag_ext;
@@ -135,32 +173,9 @@ int inet_sk_diag_fill(struct sock *sk, struct inet_connection_sock *icsk,
135 r->idiag_timer = 0; 173 r->idiag_timer = 0;
136 r->idiag_retrans = 0; 174 r->idiag_retrans = 0;
137 175
138 if (nla_put_u8(skb, INET_DIAG_SHUTDOWN, sk->sk_shutdown)) 176 if (inet_diag_msg_attrs_fill(sk, skb, r, ext, user_ns))
139 goto errout; 177 goto errout;
140 178
141 /* IPv6 dual-stack sockets use inet->tos for IPv4 connections,
142 * hence this needs to be included regardless of socket family.
143 */
144 if (ext & (1 << (INET_DIAG_TOS - 1)))
145 if (nla_put_u8(skb, INET_DIAG_TOS, inet->tos) < 0)
146 goto errout;
147
148#if IS_ENABLED(CONFIG_IPV6)
149 if (r->idiag_family == AF_INET6) {
150 if (ext & (1 << (INET_DIAG_TCLASS - 1)))
151 if (nla_put_u8(skb, INET_DIAG_TCLASS,
152 inet6_sk(sk)->tclass) < 0)
153 goto errout;
154
155 if (((1 << sk->sk_state) & (TCPF_LISTEN | TCPF_CLOSE)) &&
156 nla_put_u8(skb, INET_DIAG_SKV6ONLY, ipv6_only_sock(sk)))
157 goto errout;
158 }
159#endif
160
161 r->idiag_uid = from_kuid_munged(user_ns, sock_i_uid(sk));
162 r->idiag_inode = sock_i_ino(sk);
163
164 if (ext & (1 << (INET_DIAG_MEMINFO - 1))) { 179 if (ext & (1 << (INET_DIAG_MEMINFO - 1))) {
165 struct inet_diag_meminfo minfo = { 180 struct inet_diag_meminfo minfo = {
166 .idiag_rmem = sk_rmem_alloc_get(sk), 181 .idiag_rmem = sk_rmem_alloc_get(sk),