Commit c0425a42 authored by Christoph Hellwig's avatar Christoph Hellwig Committed by David S. Miller

net: add a new bind_add method

The SCTP protocol allows to bind multiple address to a socket.  That
feature is currently only exposed as a socket option.  Add a bind_add
method struct proto that allows to bind additional addresses, and
switch the dlm code to use the method instead of going through the
socket option from kernel space.
Signed-off-by: default avatarChristoph Hellwig <hch@lst.de>
Acked-by: default avatarMarcelo Ricardo Leitner <marcelo.leitner@gmail.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 05bfd366
...@@ -882,6 +882,7 @@ static void writequeue_entry_complete(struct writequeue_entry *e, int completed) ...@@ -882,6 +882,7 @@ static void writequeue_entry_complete(struct writequeue_entry *e, int completed)
static int sctp_bind_addrs(struct connection *con, uint16_t port) static int sctp_bind_addrs(struct connection *con, uint16_t port)
{ {
struct sockaddr_storage localaddr; struct sockaddr_storage localaddr;
struct sockaddr *addr = (struct sockaddr *)&localaddr;
int i, addr_len, result = 0; int i, addr_len, result = 0;
for (i = 0; i < dlm_local_count; i++) { for (i = 0; i < dlm_local_count; i++) {
...@@ -889,13 +890,9 @@ static int sctp_bind_addrs(struct connection *con, uint16_t port) ...@@ -889,13 +890,9 @@ static int sctp_bind_addrs(struct connection *con, uint16_t port)
make_sockaddr(&localaddr, port, &addr_len); make_sockaddr(&localaddr, port, &addr_len);
if (!i) if (!i)
result = kernel_bind(con->sock, result = kernel_bind(con->sock, addr, addr_len);
(struct sockaddr *)&localaddr,
addr_len);
else else
result = kernel_setsockopt(con->sock, SOL_SCTP, result = sock_bind_add(con->sock->sk, addr, addr_len);
SCTP_SOCKOPT_BINDX_ADD,
(char *)&localaddr, addr_len);
if (result < 0) { if (result < 0) {
log_print("Can't bind to %d addr number %d, %d.\n", log_print("Can't bind to %d addr number %d, %d.\n",
......
...@@ -1156,7 +1156,9 @@ struct proto { ...@@ -1156,7 +1156,9 @@ struct proto {
int (*sendpage)(struct sock *sk, struct page *page, int (*sendpage)(struct sock *sk, struct page *page,
int offset, size_t size, int flags); int offset, size_t size, int flags);
int (*bind)(struct sock *sk, int (*bind)(struct sock *sk,
struct sockaddr *uaddr, int addr_len); struct sockaddr *addr, int addr_len);
int (*bind_add)(struct sock *sk,
struct sockaddr *addr, int addr_len);
int (*backlog_rcv) (struct sock *sk, int (*backlog_rcv) (struct sock *sk,
struct sk_buff *skb); struct sk_buff *skb);
...@@ -2698,4 +2700,6 @@ void sock_set_reuseaddr(struct sock *sk); ...@@ -2698,4 +2700,6 @@ void sock_set_reuseaddr(struct sock *sk);
void sock_set_reuseport(struct sock *sk); void sock_set_reuseport(struct sock *sk);
void sock_set_sndtimeo(struct sock *sk, s64 secs); void sock_set_sndtimeo(struct sock *sk, s64 secs);
int sock_bind_add(struct sock *sk, struct sockaddr *addr, int addr_len);
#endif /* _SOCK_H */ #endif /* _SOCK_H */
...@@ -3712,3 +3712,11 @@ bool sk_busy_loop_end(void *p, unsigned long start_time) ...@@ -3712,3 +3712,11 @@ bool sk_busy_loop_end(void *p, unsigned long start_time)
} }
EXPORT_SYMBOL(sk_busy_loop_end); EXPORT_SYMBOL(sk_busy_loop_end);
#endif /* CONFIG_NET_RX_BUSY_POLL */ #endif /* CONFIG_NET_RX_BUSY_POLL */
int sock_bind_add(struct sock *sk, struct sockaddr *addr, int addr_len)
{
if (!sk->sk_prot->bind_add)
return -EOPNOTSUPP;
return sk->sk_prot->bind_add(sk, addr, addr_len);
}
EXPORT_SYMBOL(sock_bind_add);
...@@ -1052,6 +1052,18 @@ static int sctp_setsockopt_bindx(struct sock *sk, ...@@ -1052,6 +1052,18 @@ static int sctp_setsockopt_bindx(struct sock *sk,
return err; return err;
} }
static int sctp_bind_add(struct sock *sk, struct sockaddr *addrs,
int addrlen)
{
int err;
lock_sock(sk);
err = sctp_setsockopt_bindx_kernel(sk, addrs, addrlen,
SCTP_BINDX_ADD_ADDR);
release_sock(sk);
return err;
}
static int sctp_connect_new_asoc(struct sctp_endpoint *ep, static int sctp_connect_new_asoc(struct sctp_endpoint *ep,
const union sctp_addr *daddr, const union sctp_addr *daddr,
const struct sctp_initmsg *init, const struct sctp_initmsg *init,
...@@ -9620,6 +9632,7 @@ struct proto sctp_prot = { ...@@ -9620,6 +9632,7 @@ struct proto sctp_prot = {
.sendmsg = sctp_sendmsg, .sendmsg = sctp_sendmsg,
.recvmsg = sctp_recvmsg, .recvmsg = sctp_recvmsg,
.bind = sctp_bind, .bind = sctp_bind,
.bind_add = sctp_bind_add,
.backlog_rcv = sctp_backlog_rcv, .backlog_rcv = sctp_backlog_rcv,
.hash = sctp_hash, .hash = sctp_hash,
.unhash = sctp_unhash, .unhash = sctp_unhash,
...@@ -9662,6 +9675,7 @@ struct proto sctpv6_prot = { ...@@ -9662,6 +9675,7 @@ struct proto sctpv6_prot = {
.sendmsg = sctp_sendmsg, .sendmsg = sctp_sendmsg,
.recvmsg = sctp_recvmsg, .recvmsg = sctp_recvmsg,
.bind = sctp_bind, .bind = sctp_bind,
.bind_add = sctp_bind_add,
.backlog_rcv = sctp_backlog_rcv, .backlog_rcv = sctp_backlog_rcv,
.hash = sctp_hash, .hash = sctp_hash,
.unhash = sctp_unhash, .unhash = sctp_unhash,
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment