* [net-next-2.6 PATCH 0/5] Phonet resource routing
@ 2010-09-15 22:29 Rémi Denis-Courmont
2010-09-15 22:30 ` [PATCH] Phonet: resource routing backend Rémi Denis-Courmont
2010-09-16 4:32 ` [net-next-2.6 PATCH 0/5] Phonet resource routing David Miller
0 siblings, 2 replies; 7+ messages in thread
From: Rémi Denis-Courmont @ 2010-09-15 22:29 UTC (permalink / raw)
To: netdev
Hello,
This patch series adds support for implement Phonet services ("servers") on
Linux. So far, this was only possible on the Phonet modem attached; i.e.
Linux processes could only act as a "client".
Comments welcome. (Or did I again miss the new feature deadline?)
Documentation/networking/phonet.txt | 16 +++
include/linux/phonet.h | 2
include/net/phonet/phonet.h | 5
include/net/phonet/pn_dev.h | 1
net/phonet/af_phonet.c | 17 +++
net/phonet/datagram.c | 13 ++
net/phonet/pn_dev.c | 2
net/phonet/socket.c | 185
++++++++++++++++++++++++++++++++++++
8 files changed, 241 insertions(+)
--
Rémi Denis-Courmont
http://www.remlab.net
http://fi.linkedin.com/in/remidenis
^ permalink raw reply [flat|nested] 7+ messages in thread* [PATCH] Phonet: resource routing backend 2010-09-15 22:29 [net-next-2.6 PATCH 0/5] Phonet resource routing Rémi Denis-Courmont @ 2010-09-15 22:30 ` Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: hook resource routing to userspace via ioctl()'s Rémi Denis-Courmont 2010-09-16 4:32 ` [net-next-2.6 PATCH 0/5] Phonet resource routing David Miller 1 sibling, 1 reply; 7+ messages in thread From: Rémi Denis-Courmont @ 2010-09-15 22:30 UTC (permalink / raw) To: netdev; +Cc: Rémi Denis-Courmont From: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> When both destination device and object are nul, Phonet routes the packet according to the resource field. In fact, this is the most common pattern when sending Phonet "request" packets. In this case, the packet is delivered to whichever endpoint (socket) has registered the resource. This adds a new table so that Linux processes can register their Phonet sockets to Phonet resources, if they have adequate privileges. (Namespace support is not implemented at the moment.) Signed-off-by: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> --- include/net/phonet/phonet.h | 5 ++ net/phonet/socket.c | 88 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 93 insertions(+), 0 deletions(-) diff --git a/include/net/phonet/phonet.h b/include/net/phonet/phonet.h index 7b11407..d5df797 100644 --- a/include/net/phonet/phonet.h +++ b/include/net/phonet/phonet.h @@ -54,6 +54,11 @@ void pn_sock_hash(struct sock *sk); void pn_sock_unhash(struct sock *sk); int pn_sock_get_port(struct sock *sk, unsigned short sport); +struct sock *pn_find_sock_by_res(struct net *net, u8 res); +int pn_sock_bind_res(struct sock *sock, u8 res); +int pn_sock_unbind_res(struct sock *sk, u8 res); +void pn_sock_unbind_all_res(struct sock *sk); + int pn_skb_send(struct sock *sk, struct sk_buff *skb, const struct sockaddr_pn *target); diff --git a/net/phonet/socket.c b/net/phonet/socket.c index 7c91f73..4c29a23 100644 --- a/net/phonet/socket.c +++ b/net/phonet/socket.c @@ -565,3 +565,91 @@ const struct file_operations pn_sock_seq_fops = { .release = seq_release_net, }; #endif + +static struct { + struct sock *sk[256]; +} pnres; + +/* + * Find and hold socket based on resource. + */ +struct sock *pn_find_sock_by_res(struct net *net, u8 res) +{ + struct sock *sk; + + if (!net_eq(net, &init_net)) + return NULL; + + rcu_read_lock(); + sk = rcu_dereference(pnres.sk[res]); + if (sk) + sock_hold(sk); + rcu_read_unlock(); + return sk; +} + +static DEFINE_MUTEX(resource_mutex); + +int pn_sock_bind_res(struct sock *sk, u8 res) +{ + int ret = -EADDRINUSE; + + if (!net_eq(sock_net(sk), &init_net)) + return -ENOIOCTLCMD; + if (!capable(CAP_SYS_ADMIN)) + return -EPERM; + if (pn_socket_autobind(sk->sk_socket)) + return -EAGAIN; + + mutex_lock(&resource_mutex); + if (pnres.sk[res] == NULL) { + sock_hold(sk); + rcu_assign_pointer(pnres.sk[res], sk); + ret = 0; + } + mutex_unlock(&resource_mutex); + return ret; +} + +int pn_sock_unbind_res(struct sock *sk, u8 res) +{ + int ret = -ENOENT; + + if (!capable(CAP_SYS_ADMIN)) + return -EPERM; + + mutex_lock(&resource_mutex); + if (pnres.sk[res] == sk) { + rcu_assign_pointer(pnres.sk[res], NULL); + ret = 0; + } + mutex_unlock(&resource_mutex); + + if (ret == 0) { + synchronize_rcu(); + sock_put(sk); + } + return ret; +} + +void pn_sock_unbind_all_res(struct sock *sk) +{ + unsigned res, match = 0; + + mutex_lock(&resource_mutex); + for (res = 0; res < 256; res++) { + if (pnres.sk[res] == sk) { + rcu_assign_pointer(pnres.sk[res], NULL); + match++; + } + } + mutex_unlock(&resource_mutex); + + if (match == 0) + return; + synchronize_rcu(); + while (match > 0) { + sock_put(sk); + match--; + } +} -- 1.7.0.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH] Phonet: hook resource routing to userspace via ioctl()'s 2010-09-15 22:30 ` [PATCH] Phonet: resource routing backend Rémi Denis-Courmont @ 2010-09-15 22:30 ` Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: look up the resource routing table when forwarding Rémi Denis-Courmont 0 siblings, 1 reply; 7+ messages in thread From: Rémi Denis-Courmont @ 2010-09-15 22:30 UTC (permalink / raw) To: netdev; +Cc: Rémi Denis-Courmont From: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> I wish we could use something cleaner, such as bind(). But that would not work since resource subscription is orthogonal/in addition to the normal object ID allocated via bind(). This is similar to multicasting which also uses ioctl()'s. Signed-off-by: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> --- include/linux/phonet.h | 2 ++ net/phonet/datagram.c | 13 +++++++++++++ net/phonet/socket.c | 1 + 3 files changed, 16 insertions(+), 0 deletions(-) diff --git a/include/linux/phonet.h b/include/linux/phonet.h index 76edadf..85e14a8 100644 --- a/include/linux/phonet.h +++ b/include/linux/phonet.h @@ -47,6 +47,8 @@ /* ioctls */ #define SIOCPNGETOBJECT (SIOCPROTOPRIVATE + 0) +#define SIOCPNADDRESOURCE (SIOCPROTOPRIVATE + 14) +#define SIOCPNDELRESOURCE (SIOCPROTOPRIVATE + 15) /* Phonet protocol header */ struct phonethdr { diff --git a/net/phonet/datagram.c b/net/phonet/datagram.c index 1bd38db..2f03238 100644 --- a/net/phonet/datagram.c +++ b/net/phonet/datagram.c @@ -52,6 +52,19 @@ static int pn_ioctl(struct sock *sk, int cmd, unsigned long arg) answ = skb ? skb->len : 0; release_sock(sk); return put_user(answ, (int __user *)arg); + + case SIOCPNADDRESOURCE: + case SIOCPNDELRESOURCE: { + u32 res; + if (get_user(res, (u32 __user *)arg)) + return -EFAULT; + if (res >= 256) + return -EINVAL; + if (cmd == SIOCPNADDRESOURCE) + return pn_sock_bind_res(sk, res); + else + return pn_sock_unbind_res(sk, res); + } } return -ENOIOCTLCMD; diff --git a/net/phonet/socket.c b/net/phonet/socket.c index 4c29a23..d4f41af 100644 --- a/net/phonet/socket.c +++ b/net/phonet/socket.c @@ -158,6 +158,7 @@ void pn_sock_unhash(struct sock *sk) spin_lock_bh(&pnsocks.lock); sk_del_node_init(sk); spin_unlock_bh(&pnsocks.lock); + pn_sock_unbind_all_res(sk); } EXPORT_SYMBOL(pn_sock_unhash); -- 1.7.0.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH] Phonet: look up the resource routing table when forwarding 2010-09-15 22:30 ` [PATCH] Phonet: hook resource routing to userspace via ioctl()'s Rémi Denis-Courmont @ 2010-09-15 22:30 ` Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: list subscribed resources via proc_fs Rémi Denis-Courmont 0 siblings, 1 reply; 7+ messages in thread From: Rémi Denis-Courmont @ 2010-09-15 22:30 UTC (permalink / raw) To: netdev; +Cc: Rémi Denis-Courmont From: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> Signed-off-by: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> --- net/phonet/af_phonet.c | 17 +++++++++++++++++ 1 files changed, 17 insertions(+), 0 deletions(-) diff --git a/net/phonet/af_phonet.c b/net/phonet/af_phonet.c index 73aee7f..fd95beb 100644 --- a/net/phonet/af_phonet.c +++ b/net/phonet/af_phonet.c @@ -251,6 +251,16 @@ int pn_skb_send(struct sock *sk, struct sk_buff *skb, else if (phonet_address_lookup(net, daddr) == 0) { dev = phonet_device_get(net); skb->pkt_type = PACKET_LOOPBACK; + } else if (pn_sockaddr_get_object(target) == 0) { + /* Resource routing (small race until phonet_rcv()) */ + struct sock *sk = pn_find_sock_by_res(net, + target->spn_resource); + if (sk) { + sock_put(sk); + dev = phonet_device_get(net); + skb->pkt_type = PACKET_LOOPBACK; + } else + dev = phonet_route_output(net, daddr); } else dev = phonet_route_output(net, daddr); @@ -383,6 +393,13 @@ static int phonet_rcv(struct sk_buff *skb, struct net_device *dev, goto out; } + /* resource routing */ + if (pn_sockaddr_get_object(&sa) == 0) { + struct sock *sk = pn_find_sock_by_res(net, sa.spn_resource); + if (sk) + return sk_receive_skb(sk, skb, 0); + } + /* check if we are the destination */ if (phonet_address_lookup(net, pn_sockaddr_get_addr(&sa)) == 0) { /* Phonet packet input */ -- 1.7.0.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH] Phonet: list subscribed resources via proc_fs 2010-09-15 22:30 ` [PATCH] Phonet: look up the resource routing table when forwarding Rémi Denis-Courmont @ 2010-09-15 22:30 ` Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: resource routing documentation Rémi Denis-Courmont 0 siblings, 1 reply; 7+ messages in thread From: Rémi Denis-Courmont @ 2010-09-15 22:30 UTC (permalink / raw) To: netdev; +Cc: Rémi Denis-Courmont From: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> Signed-off-by: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> --- include/net/phonet/pn_dev.h | 1 + net/phonet/pn_dev.c | 2 + net/phonet/socket.c | 96 +++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 99 insertions(+), 0 deletions(-) diff --git a/include/net/phonet/pn_dev.h b/include/net/phonet/pn_dev.h index 2d16783..13649eb 100644 --- a/include/net/phonet/pn_dev.h +++ b/include/net/phonet/pn_dev.h @@ -57,5 +57,6 @@ struct net_device *phonet_route_output(struct net *net, u8 daddr); #define PN_NO_ADDR 0xff extern const struct file_operations pn_sock_seq_fops; +extern const struct file_operations pn_res_seq_fops; #endif diff --git a/net/phonet/pn_dev.c b/net/phonet/pn_dev.c index d0a4294..947038d 100644 --- a/net/phonet/pn_dev.c +++ b/net/phonet/pn_dev.c @@ -373,6 +373,7 @@ int __init phonet_device_init(void) if (err) return err; + proc_net_fops_create(&init_net, "pnresource", 0, &pn_res_seq_fops); register_netdevice_notifier(&phonet_device_notifier); err = phonet_netlink_register(); if (err) @@ -385,6 +386,7 @@ void phonet_device_exit(void) rtnl_unregister_all(PF_PHONET); unregister_netdevice_notifier(&phonet_device_notifier); unregister_pernet_device(&phonet_net_ops); + proc_net_remove(&init_net, "pnresource"); } int phonet_route_add(struct net_device *dev, u8 daddr) diff --git a/net/phonet/socket.c b/net/phonet/socket.c index d4f41af..6bf6e3c 100644 --- a/net/phonet/socket.c +++ b/net/phonet/socket.c @@ -654,3 +654,99 @@ void pn_sock_unbind_all_res(struct sock *sk) match--; } } + +#ifdef CONFIG_PROC_FS +static struct sock **pn_res_get_idx(struct seq_file *seq, loff_t pos) +{ + struct net *net = seq_file_net(seq); + unsigned i; + + if (!net_eq(net, &init_net)) + return NULL; + + for (i = 0; i < 256; i++) { + if (pnres.sk[i] == NULL) + continue; + if (!pos) + return pnres.sk + i; + pos--; + } + return NULL; +} + +static struct sock **pn_res_get_next(struct seq_file *seq, struct sock **sk) +{ + struct net *net = seq_file_net(seq); + unsigned i; + + BUG_ON(!net_eq(net, &init_net)); + + for (i = (sk - pnres.sk) + 1; i < 256; i++) + if (pnres.sk[i]) + return pnres.sk + i; + return NULL; +} + +static void *pn_res_seq_start(struct seq_file *seq, loff_t *pos) + __acquires(resource_mutex) +{ + mutex_lock(&resource_mutex); + return *pos ? pn_res_get_idx(seq, *pos - 1) : SEQ_START_TOKEN; +} + +static void *pn_res_seq_next(struct seq_file *seq, void *v, loff_t *pos) +{ + struct sock **sk; + + if (v == SEQ_START_TOKEN) + sk = pn_res_get_idx(seq, 0); + else + sk = pn_res_get_next(seq, v); + (*pos)++; + return sk; +} + +static void pn_res_seq_stop(struct seq_file *seq, void *v) + __releases(resource_mutex) +{ + mutex_unlock(&resource_mutex); +} + +static int pn_res_seq_show(struct seq_file *seq, void *v) +{ + int len; + + if (v == SEQ_START_TOKEN) + seq_printf(seq, "%s%n", "rs uid inode", &len); + else { + struct sock **psk = v; + struct sock *sk = *psk; + + seq_printf(seq, "%02X %5d %lu%n", + psk - pnres.sk, sock_i_uid(sk), sock_i_ino(sk), &len); + } + seq_printf(seq, "%*s\n", 63 - len, ""); + return 0; +} + +static const struct seq_operations pn_res_seq_ops = { + .start = pn_res_seq_start, + .next = pn_res_seq_next, + .stop = pn_res_seq_stop, + .show = pn_res_seq_show, +}; + +static int pn_res_open(struct inode *inode, struct file *file) +{ + return seq_open_net(inode, file, &pn_res_seq_ops, + sizeof(struct seq_net_private)); +} + +const struct file_operations pn_res_seq_fops = { + .owner = THIS_MODULE, + .open = pn_res_open, + .read = seq_read, + .llseek = seq_lseek, + .release = seq_release_net, +}; +#endif -- 1.7.0.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH] Phonet: resource routing documentation 2010-09-15 22:30 ` [PATCH] Phonet: list subscribed resources via proc_fs Rémi Denis-Courmont @ 2010-09-15 22:30 ` Rémi Denis-Courmont 0 siblings, 0 replies; 7+ messages in thread From: Rémi Denis-Courmont @ 2010-09-15 22:30 UTC (permalink / raw) To: netdev; +Cc: Rémi Denis-Courmont From: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> Signed-off-by: Rémi Denis-Courmont <remi.denis-courmont@nokia.com> --- Documentation/networking/phonet.txt | 16 ++++++++++++++++ 1 files changed, 16 insertions(+), 0 deletions(-) diff --git a/Documentation/networking/phonet.txt b/Documentation/networking/phonet.txt index 6e8ce09..cf76608 100644 --- a/Documentation/networking/phonet.txt +++ b/Documentation/networking/phonet.txt @@ -112,6 +112,22 @@ However, connect() and getpeername() are not supported, as they did not seem useful with Phonet usages (could be added easily). +Resource subscription +--------------------- + +A Phonet datagram socket can be subscribed to any number of 8-bits +Phonet resources, as follow: + + uint32_t res = 0xXX; + ioctl(fd, SIOCPNADDRESOURCE, &res); + +Subscription is similarly cancelled using the SIOCPNDELRESOURCE I/O +control request, or when the socket is closed. + +Note that no more than one socket can be subcribed to any given +resource at a time. If not, ioctl() will return EBUSY. + + Phonet Pipe protocol -------------------- -- 1.7.0.4 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* Re: [net-next-2.6 PATCH 0/5] Phonet resource routing 2010-09-15 22:29 [net-next-2.6 PATCH 0/5] Phonet resource routing Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: resource routing backend Rémi Denis-Courmont @ 2010-09-16 4:32 ` David Miller 1 sibling, 0 replies; 7+ messages in thread From: David Miller @ 2010-09-16 4:32 UTC (permalink / raw) To: remi; +Cc: netdev From: Rémi Denis-Courmont <remi@remlab.net> Date: Thu, 16 Sep 2010 00:29:35 +0200 > This patch series adds support for implement Phonet services ("servers") on > Linux. So far, this was only possible on the Phonet modem attached; i.e. > Linux processes could only act as a "client". > > Comments welcome. (Or did I again miss the new feature deadline?) All applied to net-next-2.6, but please properly number your patches in your subject lines next time. ^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2010-09-16 4:32 UTC | newest] Thread overview: 7+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2010-09-15 22:29 [net-next-2.6 PATCH 0/5] Phonet resource routing Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: resource routing backend Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: hook resource routing to userspace via ioctl()'s Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: look up the resource routing table when forwarding Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: list subscribed resources via proc_fs Rémi Denis-Courmont 2010-09-15 22:30 ` [PATCH] Phonet: resource routing documentation Rémi Denis-Courmont 2010-09-16 4:32 ` [net-next-2.6 PATCH 0/5] Phonet resource routing David Miller
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).