1. 21 10月, 2010 1 次提交
  2. 15 10月, 2010 1 次提交
    • A
      llseek: automatically add .llseek fop · 6038f373
      Arnd Bergmann 提交于
      All file_operations should get a .llseek operation so we can make
      nonseekable_open the default for future file operations without a
      .llseek pointer.
      
      The three cases that we can automatically detect are no_llseek, seq_lseek
      and default_llseek. For cases where we can we can automatically prove that
      the file offset is always ignored, we use noop_llseek, which maintains
      the current behavior of not returning an error from a seek.
      
      New drivers should normally not use noop_llseek but instead use no_llseek
      and call nonseekable_open at open time.  Existing drivers can be converted
      to do the same when the maintainer knows for certain that no user code
      relies on calling seek on the device file.
      
      The generated code is often incorrectly indented and right now contains
      comments that clarify for each added line why a specific variant was
      chosen. In the version that gets submitted upstream, the comments will
      be gone and I will manually fix the indentation, because there does not
      seem to be a way to do that using coccinelle.
      
      Some amount of new code is currently sitting in linux-next that should get
      the same modifications, which I will do at the end of the merge window.
      
      Many thanks to Julia Lawall for helping me learn to write a semantic
      patch that does all this.
      
      ===== begin semantic patch =====
      // This adds an llseek= method to all file operations,
      // as a preparation for making no_llseek the default.
      //
      // The rules are
      // - use no_llseek explicitly if we do nonseekable_open
      // - use seq_lseek for sequential files
      // - use default_llseek if we know we access f_pos
      // - use noop_llseek if we know we don't access f_pos,
      //   but we still want to allow users to call lseek
      //
      @ open1 exists @
      identifier nested_open;
      @@
      nested_open(...)
      {
      <+...
      nonseekable_open(...)
      ...+>
      }
      
      @ open exists@
      identifier open_f;
      identifier i, f;
      identifier open1.nested_open;
      @@
      int open_f(struct inode *i, struct file *f)
      {
      <+...
      (
      nonseekable_open(...)
      |
      nested_open(...)
      )
      ...+>
      }
      
      @ read disable optional_qualifier exists @
      identifier read_f;
      identifier f, p, s, off;
      type ssize_t, size_t, loff_t;
      expression E;
      identifier func;
      @@
      ssize_t read_f(struct file *f, char *p, size_t s, loff_t *off)
      {
      <+...
      (
         *off = E
      |
         *off += E
      |
         func(..., off, ...)
      |
         E = *off
      )
      ...+>
      }
      
      @ read_no_fpos disable optional_qualifier exists @
      identifier read_f;
      identifier f, p, s, off;
      type ssize_t, size_t, loff_t;
      @@
      ssize_t read_f(struct file *f, char *p, size_t s, loff_t *off)
      {
      ... when != off
      }
      
      @ write @
      identifier write_f;
      identifier f, p, s, off;
      type ssize_t, size_t, loff_t;
      expression E;
      identifier func;
      @@
      ssize_t write_f(struct file *f, const char *p, size_t s, loff_t *off)
      {
      <+...
      (
        *off = E
      |
        *off += E
      |
        func(..., off, ...)
      |
        E = *off
      )
      ...+>
      }
      
      @ write_no_fpos @
      identifier write_f;
      identifier f, p, s, off;
      type ssize_t, size_t, loff_t;
      @@
      ssize_t write_f(struct file *f, const char *p, size_t s, loff_t *off)
      {
      ... when != off
      }
      
      @ fops0 @
      identifier fops;
      @@
      struct file_operations fops = {
       ...
      };
      
      @ has_llseek depends on fops0 @
      identifier fops0.fops;
      identifier llseek_f;
      @@
      struct file_operations fops = {
      ...
       .llseek = llseek_f,
      ...
      };
      
      @ has_read depends on fops0 @
      identifier fops0.fops;
      identifier read_f;
      @@
      struct file_operations fops = {
      ...
       .read = read_f,
      ...
      };
      
      @ has_write depends on fops0 @
      identifier fops0.fops;
      identifier write_f;
      @@
      struct file_operations fops = {
      ...
       .write = write_f,
      ...
      };
      
      @ has_open depends on fops0 @
      identifier fops0.fops;
      identifier open_f;
      @@
      struct file_operations fops = {
      ...
       .open = open_f,
      ...
      };
      
      // use no_llseek if we call nonseekable_open
      ////////////////////////////////////////////
      @ nonseekable1 depends on !has_llseek && has_open @
      identifier fops0.fops;
      identifier nso ~= "nonseekable_open";
      @@
      struct file_operations fops = {
      ...  .open = nso, ...
      +.llseek = no_llseek, /* nonseekable */
      };
      
      @ nonseekable2 depends on !has_llseek @
      identifier fops0.fops;
      identifier open.open_f;
      @@
      struct file_operations fops = {
      ...  .open = open_f, ...
      +.llseek = no_llseek, /* open uses nonseekable */
      };
      
      // use seq_lseek for sequential files
      /////////////////////////////////////
      @ seq depends on !has_llseek @
      identifier fops0.fops;
      identifier sr ~= "seq_read";
      @@
      struct file_operations fops = {
      ...  .read = sr, ...
      +.llseek = seq_lseek, /* we have seq_read */
      };
      
      // use default_llseek if there is a readdir
      ///////////////////////////////////////////
      @ fops1 depends on !has_llseek && !nonseekable1 && !nonseekable2 && !seq @
      identifier fops0.fops;
      identifier readdir_e;
      @@
      // any other fop is used that changes pos
      struct file_operations fops = {
      ... .readdir = readdir_e, ...
      +.llseek = default_llseek, /* readdir is present */
      };
      
      // use default_llseek if at least one of read/write touches f_pos
      /////////////////////////////////////////////////////////////////
      @ fops2 depends on !fops1 && !has_llseek && !nonseekable1 && !nonseekable2 && !seq @
      identifier fops0.fops;
      identifier read.read_f;
      @@
      // read fops use offset
      struct file_operations fops = {
      ... .read = read_f, ...
      +.llseek = default_llseek, /* read accesses f_pos */
      };
      
      @ fops3 depends on !fops1 && !fops2 && !has_llseek && !nonseekable1 && !nonseekable2 && !seq @
      identifier fops0.fops;
      identifier write.write_f;
      @@
      // write fops use offset
      struct file_operations fops = {
      ... .write = write_f, ...
      +	.llseek = default_llseek, /* write accesses f_pos */
      };
      
      // Use noop_llseek if neither read nor write accesses f_pos
      ///////////////////////////////////////////////////////////
      
      @ fops4 depends on !fops1 && !fops2 && !fops3 && !has_llseek && !nonseekable1 && !nonseekable2 && !seq @
      identifier fops0.fops;
      identifier read_no_fpos.read_f;
      identifier write_no_fpos.write_f;
      @@
      // write fops use offset
      struct file_operations fops = {
      ...
       .write = write_f,
       .read = read_f,
      ...
      +.llseek = noop_llseek, /* read and write both use no f_pos */
      };
      
      @ depends on has_write && !has_read && !fops1 && !fops2 && !has_llseek && !nonseekable1 && !nonseekable2 && !seq @
      identifier fops0.fops;
      identifier write_no_fpos.write_f;
      @@
      struct file_operations fops = {
      ... .write = write_f, ...
      +.llseek = noop_llseek, /* write uses no f_pos */
      };
      
      @ depends on has_read && !has_write && !fops1 && !fops2 && !has_llseek && !nonseekable1 && !nonseekable2 && !seq @
      identifier fops0.fops;
      identifier read_no_fpos.read_f;
      @@
      struct file_operations fops = {
      ... .read = read_f, ...
      +.llseek = noop_llseek, /* read uses no f_pos */
      };
      
      @ depends on !has_read && !has_write && !fops1 && !fops2 && !has_llseek && !nonseekable1 && !nonseekable2 && !seq @
      identifier fops0.fops;
      @@
      struct file_operations fops = {
      ...
      +.llseek = noop_llseek, /* no read or write fn */
      };
      ===== End semantic patch =====
      Signed-off-by: NArnd Bergmann <arnd@arndb.de>
      Cc: Julia Lawall <julia@diku.dk>
      Cc: Christoph Hellwig <hch@infradead.org>
      6038f373
  3. 09 9月, 2010 1 次提交
    • N
      net: remove address space warnings in net/socket.c · fb8621bb
      Namhyung Kim 提交于
      Casts __kernel to __user pointer require __force markup, so add it. Also
      sock_get/setsockopt() takes @optval and/or @optlen arguments as user pointers
      but were taking kernel pointers, use new variables 'uoptval' and/or 'uoptlen'
      to fix it. These remove following warnings from sparse:
      
       net/socket.c:1922:46: warning: cast adds address space to expression (<asn:1>)
       net/socket.c:3061:61: warning: incorrect type in argument 4 (different address spaces)
       net/socket.c:3061:61:    expected char [noderef] <asn:1>*optval
       net/socket.c:3061:61:    got char *optval
       net/socket.c:3061:69: warning: incorrect type in argument 5 (different address spaces)
       net/socket.c:3061:69:    expected int [noderef] <asn:1>*optlen
       net/socket.c:3061:69:    got int *optlen
       net/socket.c:3063:67: warning: incorrect type in argument 4 (different address spaces)
       net/socket.c:3063:67:    expected char [noderef] <asn:1>*optval
       net/socket.c:3063:67:    got char *optval
       net/socket.c:3064:45: warning: incorrect type in argument 5 (different address spaces)
       net/socket.c:3064:45:    expected int [noderef] <asn:1>*optlen
       net/socket.c:3064:45:    got int *optlen
       net/socket.c:3078:61: warning: incorrect type in argument 4 (different address spaces)
       net/socket.c:3078:61:    expected char [noderef] <asn:1>*optval
       net/socket.c:3078:61:    got char *optval
       net/socket.c:3080:67: warning: incorrect type in argument 4 (different address spaces)
       net/socket.c:3080:67:    expected char [noderef] <asn:1>*optval
       net/socket.c:3080:67:    got char *optval
      Signed-off-by: NNamhyung Kim <namhyung@gmail.com>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      fb8621bb
  4. 19 8月, 2010 1 次提交
  5. 19 7月, 2010 2 次提交
  6. 04 6月, 2010 1 次提交
    • E
      From abbffa2aa9bd6f8df16d0d0a102af677510d8b9a Mon Sep 17 00:00:00 2001 · c6d409cf
      Eric Dumazet 提交于
      From: Eric Dumazet <eric.dumazet@gmail.com>
      Date: Thu, 3 Jun 2010 04:29:41 +0000
      Subject: [PATCH 2/3] net: net/socket.c and net/compat.c cleanups
      
      cleanup patch, to match modern coding style.
      Signed-off-by: NEric Dumazet <eric.dumazet@gmail.com>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      ---
       net/compat.c |   47 ++++++++---------
       net/socket.c |  165 ++++++++++++++++++++++++++++------------------------------
       2 files changed, 102 insertions(+), 110 deletions(-)
      
      diff --git a/net/compat.c b/net/compat.c
      index 1cf7590..63d260e 100644
      --- a/net/compat.c
      +++ b/net/compat.c
      @@ -81,7 +81,7 @@ int verify_compat_iovec(struct msghdr *kern_msg, struct iovec *kern_iov,
       	int tot_len;
      
       	if (kern_msg->msg_namelen) {
      -		if (mode==VERIFY_READ) {
      +		if (mode == VERIFY_READ) {
       			int err = move_addr_to_kernel(kern_msg->msg_name,
       						      kern_msg->msg_namelen,
       						      kern_address);
      @@ -354,7 +354,7 @@ static int do_set_attach_filter(struct socket *sock, int level, int optname,
       static int do_set_sock_timeout(struct socket *sock, int level,
       		int optname, char __user *optval, unsigned int optlen)
       {
      -	struct compat_timeval __user *up = (struct compat_timeval __user *) optval;
      +	struct compat_timeval __user *up = (struct compat_timeval __user *)optval;
       	struct timeval ktime;
       	mm_segment_t old_fs;
       	int err;
      @@ -367,7 +367,7 @@ static int do_set_sock_timeout(struct socket *sock, int level,
       		return -EFAULT;
       	old_fs = get_fs();
       	set_fs(KERNEL_DS);
      -	err = sock_setsockopt(sock, level, optname, (char *) &ktime, sizeof(ktime));
      +	err = sock_setsockopt(sock, level, optname, (char *)&ktime, sizeof(ktime));
       	set_fs(old_fs);
      
       	return err;
      @@ -389,11 +389,10 @@ asmlinkage long compat_sys_setsockopt(int fd, int level, int optname,
       				char __user *optval, unsigned int optlen)
       {
       	int err;
      -	struct socket *sock;
      +	struct socket *sock = sockfd_lookup(fd, &err);
      
      -	if ((sock = sockfd_lookup(fd, &err))!=NULL)
      -	{
      -		err = security_socket_setsockopt(sock,level,optname);
      +	if (sock) {
      +		err = security_socket_setsockopt(sock, level, optname);
       		if (err) {
       			sockfd_put(sock);
       			return err;
      @@ -453,7 +452,7 @@ static int compat_sock_getsockopt(struct socket *sock, int level, int optname,
       int compat_sock_get_timestamp(struct sock *sk, struct timeval __user *userstamp)
       {
       	struct compat_timeval __user *ctv =
      -			(struct compat_timeval __user*) userstamp;
      +			(struct compat_timeval __user *) userstamp;
       	int err = -ENOENT;
       	struct timeval tv;
      
      @@ -477,7 +476,7 @@ EXPORT_SYMBOL(compat_sock_get_timestamp);
       int compat_sock_get_timestampns(struct sock *sk, struct timespec __user *userstamp)
       {
       	struct compat_timespec __user *ctv =
      -			(struct compat_timespec __user*) userstamp;
      +			(struct compat_timespec __user *) userstamp;
       	int err = -ENOENT;
       	struct timespec ts;
      
      @@ -502,12 +501,10 @@ asmlinkage long compat_sys_getsockopt(int fd, int level, int optname,
       				char __user *optval, int __user *optlen)
       {
       	int err;
      -	struct socket *sock;
      +	struct socket *sock = sockfd_lookup(fd, &err);
      
      -	if ((sock = sockfd_lookup(fd, &err))!=NULL)
      -	{
      -		err = security_socket_getsockopt(sock, level,
      -							   optname);
      +	if (sock) {
      +		err = security_socket_getsockopt(sock, level, optname);
       		if (err) {
       			sockfd_put(sock);
       			return err;
      @@ -557,7 +554,7 @@ struct compat_group_filter {
      
       int compat_mc_setsockopt(struct sock *sock, int level, int optname,
       	char __user *optval, unsigned int optlen,
      -	int (*setsockopt)(struct sock *,int,int,char __user *,unsigned int))
      +	int (*setsockopt)(struct sock *, int, int, char __user *, unsigned int))
       {
       	char __user	*koptval = optval;
       	int		koptlen = optlen;
      @@ -640,12 +637,11 @@ int compat_mc_setsockopt(struct sock *sock, int level, int optname,
       	}
       	return setsockopt(sock, level, optname, koptval, koptlen);
       }
      -
       EXPORT_SYMBOL(compat_mc_setsockopt);
      
       int compat_mc_getsockopt(struct sock *sock, int level, int optname,
       	char __user *optval, int __user *optlen,
      -	int (*getsockopt)(struct sock *,int,int,char __user *,int __user *))
      +	int (*getsockopt)(struct sock *, int, int, char __user *, int __user *))
       {
       	struct compat_group_filter __user *gf32 = (void *)optval;
       	struct group_filter __user *kgf;
      @@ -681,7 +677,7 @@ int compat_mc_getsockopt(struct sock *sock, int level, int optname,
       	    __put_user(interface, &kgf->gf_interface) ||
       	    __put_user(fmode, &kgf->gf_fmode) ||
       	    __put_user(numsrc, &kgf->gf_numsrc) ||
      -	    copy_in_user(&kgf->gf_group,&gf32->gf_group,sizeof(kgf->gf_group)))
      +	    copy_in_user(&kgf->gf_group, &gf32->gf_group, sizeof(kgf->gf_group)))
       		return -EFAULT;
      
       	err = getsockopt(sock, level, optname, (char __user *)kgf, koptlen);
      @@ -714,21 +710,22 @@ int compat_mc_getsockopt(struct sock *sock, int level, int optname,
       		copylen = numsrc * sizeof(gf32->gf_slist[0]);
       		if (copylen > klen)
       			copylen = klen;
      -	        if (copy_in_user(gf32->gf_slist, kgf->gf_slist, copylen))
      +		if (copy_in_user(gf32->gf_slist, kgf->gf_slist, copylen))
       			return -EFAULT;
       	}
       	return err;
       }
      -
       EXPORT_SYMBOL(compat_mc_getsockopt);
      
       /* Argument list sizes for compat_sys_socketcall */
       #define AL(x) ((x) * sizeof(u32))
      -static unsigned char nas[20]={AL(0),AL(3),AL(3),AL(3),AL(2),AL(3),
      -				AL(3),AL(3),AL(4),AL(4),AL(4),AL(6),
      -				AL(6),AL(2),AL(5),AL(5),AL(3),AL(3),
      -				AL(4),AL(5)};
      +static unsigned char nas[20] = {
      +	AL(0), AL(3), AL(3), AL(3), AL(2), AL(3),
      +	AL(3), AL(3), AL(4), AL(4), AL(4), AL(6),
      +	AL(6), AL(2), AL(5), AL(5), AL(3), AL(3),
      +	AL(4), AL(5)
      +};
       #undef AL
      
       asmlinkage long compat_sys_sendmsg(int fd, struct compat_msghdr __user *msg, unsigned flags)
      @@ -827,7 +824,7 @@ asmlinkage long compat_sys_socketcall(int call, u32 __user *args)
       					  compat_ptr(a[4]), compat_ptr(a[5]));
       		break;
       	case SYS_SHUTDOWN:
      -		ret = sys_shutdown(a0,a1);
      +		ret = sys_shutdown(a0, a1);
       		break;
       	case SYS_SETSOCKOPT:
       		ret = compat_sys_setsockopt(a0, a1, a[2],
      diff --git a/net/socket.c b/net/socket.c
      index 367d547..b63c051 100644
      --- a/net/socket.c
      +++ b/net/socket.c
      @@ -124,7 +124,7 @@ static int sock_fasync(int fd, struct file *filp, int on);
       static ssize_t sock_sendpage(struct file *file, struct page *page,
       			     int offset, size_t size, loff_t *ppos, int more);
       static ssize_t sock_splice_read(struct file *file, loff_t *ppos,
      -			        struct pipe_inode_info *pipe, size_t len,
      +				struct pipe_inode_info *pipe, size_t len,
       				unsigned int flags);
      
       /*
      @@ -162,7 +162,7 @@ static const struct net_proto_family *net_families[NPROTO] __read_mostly;
        *	Statistics counters of the socket lists
        */
      
      -static DEFINE_PER_CPU(int, sockets_in_use) = 0;
      +static DEFINE_PER_CPU(int, sockets_in_use);
      
       /*
        * Support routines.
      @@ -309,9 +309,9 @@ static int init_inodecache(void)
       }
      
       static const struct super_operations sockfs_ops = {
      -	.alloc_inode =	sock_alloc_inode,
      -	.destroy_inode =sock_destroy_inode,
      -	.statfs =	simple_statfs,
      +	.alloc_inode	= sock_alloc_inode,
      +	.destroy_inode	= sock_destroy_inode,
      +	.statfs		= simple_statfs,
       };
      
       static int sockfs_get_sb(struct file_system_type *fs_type,
      @@ -411,6 +411,7 @@ int sock_map_fd(struct socket *sock, int flags)
      
       	return fd;
       }
      +EXPORT_SYMBOL(sock_map_fd);
      
       static struct socket *sock_from_file(struct file *file, int *err)
       {
      @@ -422,7 +423,7 @@ static struct socket *sock_from_file(struct file *file, int *err)
       }
      
       /**
      - *	sockfd_lookup	- 	Go from a file number to its socket slot
      + *	sockfd_lookup - Go from a file number to its socket slot
        *	@fd: file handle
        *	@err: pointer to an error code return
        *
      @@ -450,6 +451,7 @@ struct socket *sockfd_lookup(int fd, int *err)
       		fput(file);
       	return sock;
       }
      +EXPORT_SYMBOL(sockfd_lookup);
      
       static struct socket *sockfd_lookup_light(int fd, int *err, int *fput_needed)
       {
      @@ -540,6 +542,7 @@ void sock_release(struct socket *sock)
       	}
       	sock->file = NULL;
       }
      +EXPORT_SYMBOL(sock_release);
      
       int sock_tx_timestamp(struct msghdr *msg, struct sock *sk,
       		      union skb_shared_tx *shtx)
      @@ -586,6 +589,7 @@ int sock_sendmsg(struct socket *sock, struct msghdr *msg, size_t size)
       		ret = wait_on_sync_kiocb(&iocb);
       	return ret;
       }
      +EXPORT_SYMBOL(sock_sendmsg);
      
       int kernel_sendmsg(struct socket *sock, struct msghdr *msg,
       		   struct kvec *vec, size_t num, size_t size)
      @@ -604,6 +608,7 @@ int kernel_sendmsg(struct socket *sock, struct msghdr *msg,
       	set_fs(oldfs);
       	return result;
       }
      +EXPORT_SYMBOL(kernel_sendmsg);
      
       static int ktime2ts(ktime_t kt, struct timespec *ts)
       {
      @@ -664,7 +669,6 @@ void __sock_recv_timestamp(struct msghdr *msg, struct sock *sk,
       		put_cmsg(msg, SOL_SOCKET,
       			 SCM_TIMESTAMPING, sizeof(ts), &ts);
       }
      -
       EXPORT_SYMBOL_GPL(__sock_recv_timestamp);
      
       inline void sock_recv_drops(struct msghdr *msg, struct sock *sk, struct sk_buff *skb)
      @@ -720,6 +724,7 @@ int sock_recvmsg(struct socket *sock, struct msghdr *msg,
       		ret = wait_on_sync_kiocb(&iocb);
       	return ret;
       }
      +EXPORT_SYMBOL(sock_recvmsg);
      
       static int sock_recvmsg_nosec(struct socket *sock, struct msghdr *msg,
       			      size_t size, int flags)
      @@ -752,6 +757,7 @@ int kernel_recvmsg(struct socket *sock, struct msghdr *msg,
       	set_fs(oldfs);
       	return result;
       }
      +EXPORT_SYMBOL(kernel_recvmsg);
      
       static void sock_aio_dtor(struct kiocb *iocb)
       {
      @@ -774,7 +780,7 @@ static ssize_t sock_sendpage(struct file *file, struct page *page,
       }
      
       static ssize_t sock_splice_read(struct file *file, loff_t *ppos,
      -			        struct pipe_inode_info *pipe, size_t len,
      +				struct pipe_inode_info *pipe, size_t len,
       				unsigned int flags)
       {
       	struct socket *sock = file->private_data;
      @@ -887,7 +893,7 @@ static ssize_t sock_aio_write(struct kiocb *iocb, const struct iovec *iov,
        */
      
       static DEFINE_MUTEX(br_ioctl_mutex);
      -static int (*br_ioctl_hook) (struct net *, unsigned int cmd, void __user *arg) = NULL;
      +static int (*br_ioctl_hook) (struct net *, unsigned int cmd, void __user *arg);
      
       void brioctl_set(int (*hook) (struct net *, unsigned int, void __user *))
       {
      @@ -895,7 +901,6 @@ void brioctl_set(int (*hook) (struct net *, unsigned int, void __user *))
       	br_ioctl_hook = hook;
       	mutex_unlock(&br_ioctl_mutex);
       }
      -
       EXPORT_SYMBOL(brioctl_set);
      
       static DEFINE_MUTEX(vlan_ioctl_mutex);
      @@ -907,7 +912,6 @@ void vlan_ioctl_set(int (*hook) (struct net *, void __user *))
       	vlan_ioctl_hook = hook;
       	mutex_unlock(&vlan_ioctl_mutex);
       }
      -
       EXPORT_SYMBOL(vlan_ioctl_set);
      
       static DEFINE_MUTEX(dlci_ioctl_mutex);
      @@ -919,7 +923,6 @@ void dlci_ioctl_set(int (*hook) (unsigned int, void __user *))
       	dlci_ioctl_hook = hook;
       	mutex_unlock(&dlci_ioctl_mutex);
       }
      -
       EXPORT_SYMBOL(dlci_ioctl_set);
      
       static long sock_do_ioctl(struct net *net, struct socket *sock,
      @@ -1047,6 +1050,7 @@ out_release:
       	sock = NULL;
       	goto out;
       }
      +EXPORT_SYMBOL(sock_create_lite);
      
       /* No kernel lock held - perfect */
       static unsigned int sock_poll(struct file *file, poll_table *wait)
      @@ -1147,6 +1151,7 @@ call_kill:
       	rcu_read_unlock();
       	return 0;
       }
      +EXPORT_SYMBOL(sock_wake_async);
      
       static int __sock_create(struct net *net, int family, int type, int protocol,
       			 struct socket **res, int kern)
      @@ -1265,11 +1270,13 @@ int sock_create(int family, int type, int protocol, struct socket **res)
       {
       	return __sock_create(current->nsproxy->net_ns, family, type, protocol, res, 0);
       }
      +EXPORT_SYMBOL(sock_create);
      
       int sock_create_kern(int family, int type, int protocol, struct socket **res)
       {
       	return __sock_create(&init_net, family, type, protocol, res, 1);
       }
      +EXPORT_SYMBOL(sock_create_kern);
      
       SYSCALL_DEFINE3(socket, int, family, int, type, int, protocol)
       {
      @@ -1474,7 +1481,8 @@ SYSCALL_DEFINE4(accept4, int, fd, struct sockaddr __user *, upeer_sockaddr,
       		goto out;
      
       	err = -ENFILE;
      -	if (!(newsock = sock_alloc()))
      +	newsock = sock_alloc();
      +	if (!newsock)
       		goto out_put;
      
       	newsock->type = sock->type;
      @@ -1861,8 +1869,7 @@ SYSCALL_DEFINE3(sendmsg, int, fd, struct msghdr __user *, msg, unsigned, flags)
       	if (MSG_CMSG_COMPAT & flags) {
       		if (get_compat_msghdr(&msg_sys, msg_compat))
       			return -EFAULT;
      -	}
      -	else if (copy_from_user(&msg_sys, msg, sizeof(struct msghdr)))
      +	} else if (copy_from_user(&msg_sys, msg, sizeof(struct msghdr)))
       		return -EFAULT;
      
       	sock = sockfd_lookup_light(fd, &err, &fput_needed);
      @@ -1964,8 +1971,7 @@ static int __sys_recvmsg(struct socket *sock, struct msghdr __user *msg,
       	if (MSG_CMSG_COMPAT & flags) {
       		if (get_compat_msghdr(msg_sys, msg_compat))
       			return -EFAULT;
      -	}
      -	else if (copy_from_user(msg_sys, msg, sizeof(struct msghdr)))
      +	} else if (copy_from_user(msg_sys, msg, sizeof(struct msghdr)))
       		return -EFAULT;
      
       	err = -EMSGSIZE;
      @@ -2191,10 +2197,10 @@ SYSCALL_DEFINE5(recvmmsg, int, fd, struct mmsghdr __user *, mmsg,
       /* Argument list sizes for sys_socketcall */
       #define AL(x) ((x) * sizeof(unsigned long))
       static const unsigned char nargs[20] = {
      -	AL(0),AL(3),AL(3),AL(3),AL(2),AL(3),
      -	AL(3),AL(3),AL(4),AL(4),AL(4),AL(6),
      -	AL(6),AL(2),AL(5),AL(5),AL(3),AL(3),
      -	AL(4),AL(5)
      +	AL(0), AL(3), AL(3), AL(3), AL(2), AL(3),
      +	AL(3), AL(3), AL(4), AL(4), AL(4), AL(6),
      +	AL(6), AL(2), AL(5), AL(5), AL(3), AL(3),
      +	AL(4), AL(5)
       };
      
       #undef AL
      @@ -2340,6 +2346,7 @@ int sock_register(const struct net_proto_family *ops)
       	printk(KERN_INFO "NET: Registered protocol family %d\n", ops->family);
       	return err;
       }
      +EXPORT_SYMBOL(sock_register);
      
       /**
        *	sock_unregister - remove a protocol handler
      @@ -2366,6 +2373,7 @@ void sock_unregister(int family)
      
       	printk(KERN_INFO "NET: Unregistered protocol family %d\n", family);
       }
      +EXPORT_SYMBOL(sock_unregister);
      
       static int __init sock_init(void)
       {
      @@ -2490,13 +2498,13 @@ static int dev_ifconf(struct net *net, struct compat_ifconf __user *uifc32)
       		ifc.ifc_req = NULL;
       		uifc = compat_alloc_user_space(sizeof(struct ifconf));
       	} else {
      -		size_t len =((ifc32.ifc_len / sizeof (struct compat_ifreq)) + 1) *
      -			sizeof (struct ifreq);
      +		size_t len = ((ifc32.ifc_len / sizeof(struct compat_ifreq)) + 1) *
      +			sizeof(struct ifreq);
       		uifc = compat_alloc_user_space(sizeof(struct ifconf) + len);
       		ifc.ifc_len = len;
       		ifr = ifc.ifc_req = (void __user *)(uifc + 1);
       		ifr32 = compat_ptr(ifc32.ifcbuf);
      -		for (i = 0; i < ifc32.ifc_len; i += sizeof (struct compat_ifreq)) {
      +		for (i = 0; i < ifc32.ifc_len; i += sizeof(struct compat_ifreq)) {
       			if (copy_in_user(ifr, ifr32, sizeof(struct compat_ifreq)))
       				return -EFAULT;
       			ifr++;
      @@ -2516,9 +2524,9 @@ static int dev_ifconf(struct net *net, struct compat_ifconf __user *uifc32)
       	ifr = ifc.ifc_req;
       	ifr32 = compat_ptr(ifc32.ifcbuf);
       	for (i = 0, j = 0;
      -             i + sizeof (struct compat_ifreq) <= ifc32.ifc_len && j < ifc.ifc_len;
      -	     i += sizeof (struct compat_ifreq), j += sizeof (struct ifreq)) {
      -		if (copy_in_user(ifr32, ifr, sizeof (struct compat_ifreq)))
      +	     i + sizeof(struct compat_ifreq) <= ifc32.ifc_len && j < ifc.ifc_len;
      +	     i += sizeof(struct compat_ifreq), j += sizeof(struct ifreq)) {
      +		if (copy_in_user(ifr32, ifr, sizeof(struct compat_ifreq)))
       			return -EFAULT;
       		ifr32++;
       		ifr++;
      @@ -2567,7 +2575,7 @@ static int compat_siocwandev(struct net *net, struct compat_ifreq __user *uifr32
       	compat_uptr_t uptr32;
       	struct ifreq __user *uifr;
      
      -	uifr = compat_alloc_user_space(sizeof (*uifr));
      +	uifr = compat_alloc_user_space(sizeof(*uifr));
       	if (copy_in_user(uifr, uifr32, sizeof(struct compat_ifreq)))
       		return -EFAULT;
      
      @@ -2601,9 +2609,9 @@ static int bond_ioctl(struct net *net, unsigned int cmd,
       			return -EFAULT;
      
       		old_fs = get_fs();
      -		set_fs (KERNEL_DS);
      +		set_fs(KERNEL_DS);
       		err = dev_ioctl(net, cmd, &kifr);
      -		set_fs (old_fs);
      +		set_fs(old_fs);
      
       		return err;
       	case SIOCBONDSLAVEINFOQUERY:
      @@ -2710,9 +2718,9 @@ static int compat_sioc_ifmap(struct net *net, unsigned int cmd,
       		return -EFAULT;
      
       	old_fs = get_fs();
      -	set_fs (KERNEL_DS);
      +	set_fs(KERNEL_DS);
       	err = dev_ioctl(net, cmd, (void __user *)&ifr);
      -	set_fs (old_fs);
      +	set_fs(old_fs);
      
       	if (cmd == SIOCGIFMAP && !err) {
       		err = copy_to_user(uifr32, &ifr, sizeof(ifr.ifr_name));
      @@ -2734,7 +2742,7 @@ static int compat_siocshwtstamp(struct net *net, struct compat_ifreq __user *uif
       	compat_uptr_t uptr32;
       	struct ifreq __user *uifr;
      
      -	uifr = compat_alloc_user_space(sizeof (*uifr));
      +	uifr = compat_alloc_user_space(sizeof(*uifr));
       	if (copy_in_user(uifr, uifr32, sizeof(struct compat_ifreq)))
       		return -EFAULT;
      
      @@ -2750,20 +2758,20 @@ static int compat_siocshwtstamp(struct net *net, struct compat_ifreq __user *uif
       }
      
       struct rtentry32 {
      -	u32   		rt_pad1;
      +	u32		rt_pad1;
       	struct sockaddr rt_dst;         /* target address               */
       	struct sockaddr rt_gateway;     /* gateway addr (RTF_GATEWAY)   */
       	struct sockaddr rt_genmask;     /* target network mask (IP)     */
      -	unsigned short  rt_flags;
      -	short           rt_pad2;
      -	u32   		rt_pad3;
      -	unsigned char   rt_tos;
      -	unsigned char   rt_class;
      -	short           rt_pad4;
      -	short           rt_metric;      /* +1 for binary compatibility! */
      +	unsigned short	rt_flags;
      +	short		rt_pad2;
      +	u32		rt_pad3;
      +	unsigned char	rt_tos;
      +	unsigned char	rt_class;
      +	short		rt_pad4;
      +	short		rt_metric;      /* +1 for binary compatibility! */
       	/* char * */ u32 rt_dev;        /* forcing the device at add    */
      -	u32   		rt_mtu;         /* per route MTU/Window         */
      -	u32   		rt_window;      /* Window clamping              */
      +	u32		rt_mtu;         /* per route MTU/Window         */
      +	u32		rt_window;      /* Window clamping              */
       	unsigned short  rt_irtt;        /* Initial RTT                  */
       };
      
      @@ -2793,29 +2801,29 @@ static int routing_ioctl(struct net *net, struct socket *sock,
      
       	if (sock && sock->sk && sock->sk->sk_family == AF_INET6) { /* ipv6 */
       		struct in6_rtmsg32 __user *ur6 = argp;
      -		ret = copy_from_user (&r6.rtmsg_dst, &(ur6->rtmsg_dst),
      +		ret = copy_from_user(&r6.rtmsg_dst, &(ur6->rtmsg_dst),
       			3 * sizeof(struct in6_addr));
      -		ret |= __get_user (r6.rtmsg_type, &(ur6->rtmsg_type));
      -		ret |= __get_user (r6.rtmsg_dst_len, &(ur6->rtmsg_dst_len));
      -		ret |= __get_user (r6.rtmsg_src_len, &(ur6->rtmsg_src_len));
      -		ret |= __get_user (r6.rtmsg_metric, &(ur6->rtmsg_metric));
      -		ret |= __get_user (r6.rtmsg_info, &(ur6->rtmsg_info));
      -		ret |= __get_user (r6.rtmsg_flags, &(ur6->rtmsg_flags));
      -		ret |= __get_user (r6.rtmsg_ifindex, &(ur6->rtmsg_ifindex));
      +		ret |= __get_user(r6.rtmsg_type, &(ur6->rtmsg_type));
      +		ret |= __get_user(r6.rtmsg_dst_len, &(ur6->rtmsg_dst_len));
      +		ret |= __get_user(r6.rtmsg_src_len, &(ur6->rtmsg_src_len));
      +		ret |= __get_user(r6.rtmsg_metric, &(ur6->rtmsg_metric));
      +		ret |= __get_user(r6.rtmsg_info, &(ur6->rtmsg_info));
      +		ret |= __get_user(r6.rtmsg_flags, &(ur6->rtmsg_flags));
      +		ret |= __get_user(r6.rtmsg_ifindex, &(ur6->rtmsg_ifindex));
      
       		r = (void *) &r6;
       	} else { /* ipv4 */
       		struct rtentry32 __user *ur4 = argp;
      -		ret = copy_from_user (&r4.rt_dst, &(ur4->rt_dst),
      +		ret = copy_from_user(&r4.rt_dst, &(ur4->rt_dst),
       					3 * sizeof(struct sockaddr));
      -		ret |= __get_user (r4.rt_flags, &(ur4->rt_flags));
      -		ret |= __get_user (r4.rt_metric, &(ur4->rt_metric));
      -		ret |= __get_user (r4.rt_mtu, &(ur4->rt_mtu));
      -		ret |= __get_user (r4.rt_window, &(ur4->rt_window));
      -		ret |= __get_user (r4.rt_irtt, &(ur4->rt_irtt));
      -		ret |= __get_user (rtdev, &(ur4->rt_dev));
      +		ret |= __get_user(r4.rt_flags, &(ur4->rt_flags));
      +		ret |= __get_user(r4.rt_metric, &(ur4->rt_metric));
      +		ret |= __get_user(r4.rt_mtu, &(ur4->rt_mtu));
      +		ret |= __get_user(r4.rt_window, &(ur4->rt_window));
      +		ret |= __get_user(r4.rt_irtt, &(ur4->rt_irtt));
      +		ret |= __get_user(rtdev, &(ur4->rt_dev));
       		if (rtdev) {
      -			ret |= copy_from_user (devname, compat_ptr(rtdev), 15);
      +			ret |= copy_from_user(devname, compat_ptr(rtdev), 15);
       			r4.rt_dev = devname; devname[15] = 0;
       		} else
       			r4.rt_dev = NULL;
      @@ -2828,9 +2836,9 @@ static int routing_ioctl(struct net *net, struct socket *sock,
       		goto out;
       	}
      
      -	set_fs (KERNEL_DS);
      +	set_fs(KERNEL_DS);
       	ret = sock_do_ioctl(net, sock, cmd, (unsigned long) r);
      -	set_fs (old_fs);
      +	set_fs(old_fs);
      
       out:
       	return ret;
      @@ -2993,11 +3001,13 @@ int kernel_bind(struct socket *sock, struct sockaddr *addr, int addrlen)
       {
       	return sock->ops->bind(sock, addr, addrlen);
       }
      +EXPORT_SYMBOL(kernel_bind);
      
       int kernel_listen(struct socket *sock, int backlog)
       {
       	return sock->ops->listen(sock, backlog);
       }
      +EXPORT_SYMBOL(kernel_listen);
      
       int kernel_accept(struct socket *sock, struct socket **newsock, int flags)
       {
      @@ -3022,24 +3032,28 @@ int kernel_accept(struct socket *sock, struct socket **newsock, int flags)
       done:
       	return err;
       }
      +EXPORT_SYMBOL(kernel_accept);
      
       int kernel_connect(struct socket *sock, struct sockaddr *addr, int addrlen,
       		   int flags)
       {
       	return sock->ops->connect(sock, addr, addrlen, flags);
       }
      +EXPORT_SYMBOL(kernel_connect);
      
       int kernel_getsockname(struct socket *sock, struct sockaddr *addr,
       			 int *addrlen)
       {
       	return sock->ops->getname(sock, addr, addrlen, 0);
       }
      +EXPORT_SYMBOL(kernel_getsockname);
      
       int kernel_getpeername(struct socket *sock, struct sockaddr *addr,
       			 int *addrlen)
       {
       	return sock->ops->getname(sock, addr, addrlen, 1);
       }
      +EXPORT_SYMBOL(kernel_getpeername);
      
       int kernel_getsockopt(struct socket *sock, int level, int optname,
       			char *optval, int *optlen)
      @@ -3056,6 +3070,7 @@ int kernel_getsockopt(struct socket *sock, int level, int optname,
       	set_fs(oldfs);
       	return err;
       }
      +EXPORT_SYMBOL(kernel_getsockopt);
      
       int kernel_setsockopt(struct socket *sock, int level, int optname,
       			char *optval, unsigned int optlen)
      @@ -3072,6 +3087,7 @@ int kernel_setsockopt(struct socket *sock, int level, int optname,
       	set_fs(oldfs);
       	return err;
       }
      +EXPORT_SYMBOL(kernel_setsockopt);
      
       int kernel_sendpage(struct socket *sock, struct page *page, int offset,
       		    size_t size, int flags)
      @@ -3083,6 +3099,7 @@ int kernel_sendpage(struct socket *sock, struct page *page, int offset,
      
       	return sock_no_sendpage(sock, page, offset, size, flags);
       }
      +EXPORT_SYMBOL(kernel_sendpage);
      
       int kernel_sock_ioctl(struct socket *sock, int cmd, unsigned long arg)
       {
      @@ -3095,33 +3112,11 @@ int kernel_sock_ioctl(struct socket *sock, int cmd, unsigned long arg)
      
       	return err;
       }
      +EXPORT_SYMBOL(kernel_sock_ioctl);
      
       int kernel_sock_shutdown(struct socket *sock, enum sock_shutdown_cmd how)
       {
       	return sock->ops->shutdown(sock, how);
       }
      -
      -EXPORT_SYMBOL(sock_create);
      -EXPORT_SYMBOL(sock_create_kern);
      -EXPORT_SYMBOL(sock_create_lite);
      -EXPORT_SYMBOL(sock_map_fd);
      -EXPORT_SYMBOL(sock_recvmsg);
      -EXPORT_SYMBOL(sock_register);
      -EXPORT_SYMBOL(sock_release);
      -EXPORT_SYMBOL(sock_sendmsg);
      -EXPORT_SYMBOL(sock_unregister);
      -EXPORT_SYMBOL(sock_wake_async);
      -EXPORT_SYMBOL(sockfd_lookup);
      -EXPORT_SYMBOL(kernel_sendmsg);
      -EXPORT_SYMBOL(kernel_recvmsg);
      -EXPORT_SYMBOL(kernel_bind);
      -EXPORT_SYMBOL(kernel_listen);
      -EXPORT_SYMBOL(kernel_accept);
      -EXPORT_SYMBOL(kernel_connect);
      -EXPORT_SYMBOL(kernel_getsockname);
      -EXPORT_SYMBOL(kernel_getpeername);
      -EXPORT_SYMBOL(kernel_getsockopt);
      -EXPORT_SYMBOL(kernel_setsockopt);
      -EXPORT_SYMBOL(kernel_sendpage);
      -EXPORT_SYMBOL(kernel_sock_ioctl);
       EXPORT_SYMBOL(kernel_sock_shutdown);
      +
      --
      1.7.0.4
      c6d409cf
  7. 24 5月, 2010 1 次提交
    • H
      cls_cgroup: Store classid in struct sock · f8451725
      Herbert Xu 提交于
      Up until now cls_cgroup has relied on fetching the classid out of
      the current executing thread.  This runs into trouble when a packet
      processing is delayed in which case it may execute out of another
      thread's context.
      
      Furthermore, even when a packet is not delayed we may fail to
      classify it if soft IRQs have been disabled, because this scenario
      is indistinguishable from one where a packet unrelated to the
      current thread is processed by a real soft IRQ.
      
      In fact, the current semantics is inherently broken, as a single
      skb may be constructed out of the writes of two different tasks.
      A different manifestation of this problem is when the TCP stack
      transmits in response of an incoming ACK.  This is currently
      unclassified.
      
      As we already have a concept of packet ownership for accounting
      purposes in the skb->sk pointer, this is a natural place to store
      the classid in a persistent manner.
      
      This patch adds the cls_cgroup classid in struct sock, filling up
      an existing hole on 64-bit :)
      
      The value is set at socket creation time.  So all sockets created
      via socket(2) automatically gains the ID of the thread creating it.
      Whenever another process touches the socket by either reading or
      writing to it, we will change the socket classid to that of the
      process if it has a valid (non-zero) classid.
      
      For sockets created on inbound connections through accept(2), we
      inherit the classid of the original listening socket through
      sk_clone, possibly preceding the actual accept(2) call.
      
      In order to minimise risks, I have not made this the authoritative
      classid.  For now it is only used as a backup when we execute
      with soft IRQs disabled.  Once we're completely happy with its
      semantics we can use it as the sole classid.
      
      Footnote: I have rearranged the error path on cls_group module
      creation.  If we didn't do this, then there is a window where
      someone could create a tc rule using cls_group before the cgroup
      subsystem has been registered.
      Signed-off-by: NHerbert Xu <herbert@gondor.apana.org.au>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      f8451725
  8. 18 5月, 2010 1 次提交
  9. 02 5月, 2010 1 次提交
    • E
      net: sock_def_readable() and friends RCU conversion · 43815482
      Eric Dumazet 提交于
      sk_callback_lock rwlock actually protects sk->sk_sleep pointer, so we
      need two atomic operations (and associated dirtying) per incoming
      packet.
      
      RCU conversion is pretty much needed :
      
      1) Add a new structure, called "struct socket_wq" to hold all fields
      that will need rcu_read_lock() protection (currently: a
      wait_queue_head_t and a struct fasync_struct pointer).
      
      [Future patch will add a list anchor for wakeup coalescing]
      
      2) Attach one of such structure to each "struct socket" created in
      sock_alloc_inode().
      
      3) Respect RCU grace period when freeing a "struct socket_wq"
      
      4) Change sk_sleep pointer in "struct sock" by sk_wq, pointer to "struct
      socket_wq"
      
      5) Change sk_sleep() function to use new sk->sk_wq instead of
      sk->sk_sleep
      
      6) Change sk_has_sleeper() to wq_has_sleeper() that must be used inside
      a rcu_read_lock() section.
      
      7) Change all sk_has_sleeper() callers to :
        - Use rcu_read_lock() instead of read_lock(&sk->sk_callback_lock)
        - Use wq_has_sleeper() to eventually wakeup tasks.
        - Use rcu_read_unlock() instead of read_unlock(&sk->sk_callback_lock)
      
      8) sock_wake_async() is modified to use rcu protection as well.
      
      9) Exceptions :
        macvtap, drivers/net/tun.c, af_unix use integrated "struct socket_wq"
      instead of dynamically allocated ones. They dont need rcu freeing.
      
      Some cleanups or followups are probably needed, (possible
      sk_callback_lock conversion to a spinlock for example...).
      Signed-off-by: NEric Dumazet <eric.dumazet@gmail.com>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      43815482
  10. 01 5月, 2010 1 次提交
  11. 22 4月, 2010 1 次提交
    • E
      fasync: RCU and fine grained locking · 989a2979
      Eric Dumazet 提交于
      kill_fasync() uses a central rwlock, candidate for RCU conversion, to
      avoid cache line ping pongs on SMP.
      
      fasync_remove_entry() and fasync_add_entry() can disable IRQS on a short
      section instead during whole list scan.
      
      Use a spinlock per fasync_struct to synchronize kill_fasync_rcu() and
      fasync_{remove|add}_entry(). This spinlock is IRQ safe, so sock_fasync()
      doesnt need its own implementation and can use fasync_helper(), to
      reduce code size and complexity.
      
      We can remove __kill_fasync() direct use in net/socket.c, and rename it
      to kill_fasync_rcu().
      Signed-off-by: NEric Dumazet <eric.dumazet@gmail.com>
      Cc: Paul E. McKenney <paulmck@linux.vnet.ibm.com>
      Cc: Lai Jiangshan <laijs@cn.fujitsu.com>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      989a2979
  12. 07 4月, 2010 1 次提交
  13. 30 3月, 2010 1 次提交
    • T
      include cleanup: Update gfp.h and slab.h includes to prepare for breaking... · 5a0e3ad6
      Tejun Heo 提交于
      include cleanup: Update gfp.h and slab.h includes to prepare for breaking implicit slab.h inclusion from percpu.h
      
      percpu.h is included by sched.h and module.h and thus ends up being
      included when building most .c files.  percpu.h includes slab.h which
      in turn includes gfp.h making everything defined by the two files
      universally available and complicating inclusion dependencies.
      
      percpu.h -> slab.h dependency is about to be removed.  Prepare for
      this change by updating users of gfp and slab facilities include those
      headers directly instead of assuming availability.  As this conversion
      needs to touch large number of source files, the following script is
      used as the basis of conversion.
      
        http://userweb.kernel.org/~tj/misc/slabh-sweep.py
      
      The script does the followings.
      
      * Scan files for gfp and slab usages and update includes such that
        only the necessary includes are there.  ie. if only gfp is used,
        gfp.h, if slab is used, slab.h.
      
      * When the script inserts a new include, it looks at the include
        blocks and try to put the new include such that its order conforms
        to its surrounding.  It's put in the include block which contains
        core kernel includes, in the same order that the rest are ordered -
        alphabetical, Christmas tree, rev-Xmas-tree or at the end if there
        doesn't seem to be any matching order.
      
      * If the script can't find a place to put a new include (mostly
        because the file doesn't have fitting include block), it prints out
        an error message indicating which .h file needs to be added to the
        file.
      
      The conversion was done in the following steps.
      
      1. The initial automatic conversion of all .c files updated slightly
         over 4000 files, deleting around 700 includes and adding ~480 gfp.h
         and ~3000 slab.h inclusions.  The script emitted errors for ~400
         files.
      
      2. Each error was manually checked.  Some didn't need the inclusion,
         some needed manual addition while adding it to implementation .h or
         embedding .c file was more appropriate for others.  This step added
         inclusions to around 150 files.
      
      3. The script was run again and the output was compared to the edits
         from #2 to make sure no file was left behind.
      
      4. Several build tests were done and a couple of problems were fixed.
         e.g. lib/decompress_*.c used malloc/free() wrappers around slab
         APIs requiring slab.h to be added manually.
      
      5. The script was run on all .h files but without automatically
         editing them as sprinkling gfp.h and slab.h inclusions around .h
         files could easily lead to inclusion dependency hell.  Most gfp.h
         inclusion directives were ignored as stuff from gfp.h was usually
         wildly available and often used in preprocessor macros.  Each
         slab.h inclusion directive was examined and added manually as
         necessary.
      
      6. percpu.h was updated not to include slab.h.
      
      7. Build test were done on the following configurations and failures
         were fixed.  CONFIG_GCOV_KERNEL was turned off for all tests (as my
         distributed build env didn't work with gcov compiles) and a few
         more options had to be turned off depending on archs to make things
         build (like ipr on powerpc/64 which failed due to missing writeq).
      
         * x86 and x86_64 UP and SMP allmodconfig and a custom test config.
         * powerpc and powerpc64 SMP allmodconfig
         * sparc and sparc64 SMP allmodconfig
         * ia64 SMP allmodconfig
         * s390 SMP allmodconfig
         * alpha SMP allmodconfig
         * um on x86_64 SMP allmodconfig
      
      8. percpu.h modifications were reverted so that it could be applied as
         a separate patch and serve as bisection point.
      
      Given the fact that I had only a couple of failures from tests on step
      6, I'm fairly confident about the coverage of this conversion patch.
      If there is a breakage, it's likely to be something in one of the arch
      headers which should be easily discoverable easily on most builds of
      the specific arch.
      Signed-off-by: NTejun Heo <tj@kernel.org>
      Guess-its-ok-by: NChristoph Lameter <cl@linux-foundation.org>
      Cc: Ingo Molnar <mingo@redhat.com>
      Cc: Lee Schermerhorn <Lee.Schermerhorn@hp.com>
      5a0e3ad6
  14. 27 3月, 2010 1 次提交
  15. 17 12月, 2009 5 次提交
  16. 02 12月, 2009 1 次提交
  17. 12 11月, 2009 2 次提交
    • A
      net/atm: move all compat_ioctl handling to atm/ioctl.c · 805003a4
      Arnd Bergmann 提交于
      We have two implementations of the compat_ioctl handling for ATM, the
      one that we have had for ages in fs/compat_ioctl.c and the one added to
      net/atm/ioctl.c by David Woodhouse. Unfortunately, both versions are
      incomplete, and in practice we use a very confusing combination of the
      two.
      
      For ioctl numbers that have the same identifier on 32 and 64 bit systems,
      we go directly through the compat_ioctl socket operation, for those that
      
      differ, we do a conversion in fs/compat_ioctl.c.
      
      This patch moves both variants into the vcc_compat_ioctl() function,
      while preserving the current behaviour. It also kills off the COMPATIBLE_IOCTL
      definitions that we never use here.
      Doing it this way is clearly not a good solution, but I hope it is a
      step into the right direction, so that someone is able to clean up this
      mess for real.
      Signed-off-by: NArnd Bergmann <arnd@arndb.de>
      Cc: Eric Dumazet <eric.dumazet@gmail.com>
      Cc: David Woodhouse <dwmw2@infradead.org>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      805003a4
    • A
      net/compat: fix dev_ifsioc emulation corner cases · a2116ed2
      Arnd Bergmann 提交于
      Handling for SIOCSHWTSTAMP is broken on architectures
      with a split user/kernel address space like s390,
      because it passes a real user pointer while using
      set_fs(KERNEL_DS).
      A similar problem might arise the next time somebody
      adds code to dev_ifsioc.
      
      Split up dev_ifsioc into three separate functions for
      SIOCSHWTSTAMP, SIOC*IFMAP and all other numbers so
      we can get rid of set_fs in all potentially affected
      cases.
      Signed-off-by: NArnd Bergmann <arnd@arndb.de>
      Cc: Patrick Ohly <patrick.ohly@intel.com>
      Cc: David S. Miller <davem@davemloft.net>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      a2116ed2
  18. 09 11月, 2009 2 次提交
  19. 07 11月, 2009 3 次提交
    • A
      net, compat_ioctl: handle more ioctls correctly · 9177efd3
      Arnd Bergmann 提交于
      The MII ioctls and SIOCSIFNAME need to go through ifsioc conversion,
      which they never did so far. Some others are not implemented in the
      native path, so we can just return -EINVAL directly.
      
      Add IFSLAVE ioctls to the EINVAL list and move it to the end to
      optimize the code path for the common case.
      Signed-off-by: NArnd Bergmann <arnd@arndb.de>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      9177efd3
    • A
      compat: move sockios handling to net/socket.c · 6b96018b
      Arnd Bergmann 提交于
      This removes the original socket compat_ioctl code
      from fs/compat_ioctl.c and converts the code from the copy
      in net/socket.c into a single function. We add a few cycles
      of runtime to compat_sock_ioctl() with the long switch()
      statement, but gain some cycles in return by simplifying
      the call chain to get there.
      
      Due to better inlining, save 1.5kb of object size in the
      process, and enable further savings:
      
      before:
         text    data     bss     dec     hex filename
        13540   18008    2080   33628    835c obj/fs/compat_ioctl.o
        14565     636      40   15241    3b89 obj/net/socket.o
      
      after:
         text    data     bss     dec     hex filename
         8916   15176    2080   26172    663c obj/fs/compat_ioctl.o
        20725     636      40   21401    5399 obj/net/socket.o
      Signed-off-by: NArnd Bergmann <arnd@arndb.de>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      6b96018b
    • A
      net: copy socket ioctl code to net/socket.h · 7a229387
      Arnd Bergmann 提交于
      This makes an identical copy of the socket compat_ioctl code
      from fs/compat_ioctl.c to net/socket.c, as a preparation
      for moving the functionality in a way that can be easily
      reviewed.
      
      The code is hidden inside of #if 0 and gets activated in the
      patch that will make it work.
      Signed-off-by: NArnd Bergmann <arnd@arndb.de>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      7a229387
  20. 06 11月, 2009 1 次提交
  21. 13 10月, 2009 2 次提交
    • A
      net: Introduce recvmmsg socket syscall · a2e27255
      Arnaldo Carvalho de Melo 提交于
      Meaning receive multiple messages, reducing the number of syscalls and
      net stack entry/exit operations.
      
      Next patches will introduce mechanisms where protocols that want to
      optimize this operation will provide an unlocked_recvmsg operation.
      
      This takes into account comments made by:
      
      . Paul Moore: sock_recvmsg is called only for the first datagram,
        sock_recvmsg_nosec is used for the rest.
      
      . Caitlin Bestler: recvmmsg now has a struct timespec timeout, that
        works in the same fashion as the ppoll one.
      
        If the underlying protocol returns a datagram with MSG_OOB set, this
        will make recvmmsg return right away with as many datagrams (+ the OOB
        one) it has received so far.
      
      . Rémi Denis-Courmont & Steven Whitehouse: If we receive N < vlen
        datagrams and then recvmsg returns an error, recvmmsg will return
        the successfully received datagrams, store the error and return it
        in the next call.
      
      This paves the way for a subsequent optimization, sk_prot->unlocked_recvmsg,
      where we will be able to acquire the lock only at batch start and end, not at
      every underlying recvmsg call.
      Signed-off-by: NArnaldo Carvalho de Melo <acme@redhat.com>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      a2e27255
    • N
      net: Generalize socket rx gap / receive queue overflow cmsg · 3b885787
      Neil Horman 提交于
      Create a new socket level option to report number of queue overflows
      
      Recently I augmented the AF_PACKET protocol to report the number of frames lost
      on the socket receive queue between any two enqueued frames.  This value was
      exported via a SOL_PACKET level cmsg.  AFter I completed that work it was
      requested that this feature be generalized so that any datagram oriented socket
      could make use of this option.  As such I've created this patch, It creates a
      new SOL_SOCKET level option called SO_RXQ_OVFL, which when enabled exports a
      SOL_SOCKET level cmsg that reports the nubmer of times the sk_receive_queue
      overflowed between any two given frames.  It also augments the AF_PACKET
      protocol to take advantage of this new feature (as it previously did not touch
      sk->sk_drops, which this patch uses to record the overflow count).  Tested
      successfully by me.
      
      Notes:
      
      1) Unlike my previous patch, this patch simply records the sk_drops value, which
      is not a number of drops between packets, but rather a total number of drops.
      Deltas must be computed in user space.
      
      2) While this patch currently works with datagram oriented protocols, it will
      also be accepted by non-datagram oriented protocols. I'm not sure if thats
      agreeable to everyone, but my argument in favor of doing so is that, for those
      protocols which aren't applicable to this option, sk_drops will always be zero,
      and reporting no drops on a receive queue that isn't used for those
      non-participating protocols seems reasonable to me.  This also saves us having
      to code in a per-protocol opt in mechanism.
      
      3) This applies cleanly to net-next assuming that commit
      97775007 (my af packet cmsg patch) is reverted
      Signed-off-by: NNeil Horman <nhorman@tuxdriver.com>
      Signed-off-by: NEric Dumazet <eric.dumazet@gmail.com>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      3b885787
  22. 08 10月, 2009 1 次提交
    • J
      wext: refactor · 3d23e349
      Johannes Berg 提交于
      Refactor wext to
       * split out iwpriv handling
       * split out iwspy handling
       * split out procfs support
       * allow cfg80211 to have wireless extensions compat code
         w/o CONFIG_WIRELESS_EXT
      
      After this, drivers need to
       - select WIRELESS_EXT	- for wext support
       - select WEXT_PRIV	- for iwpriv support
       - select WEXT_SPY	- for iwspy support
      
      except cfg80211 -- which gets new hooks in wext-core.c
      and can then get wext handlers without CONFIG_WIRELESS_EXT.
      
      Wireless extensions procfs support is auto-selected
      based on PROC_FS and anything that requires the wext core
      (i.e. WIRELESS_EXT or CFG80211_WEXT).
      Signed-off-by: NJohannes Berg <johannes@sipsolutions.net>
      Signed-off-by: NJohn W. Linville <linville@tuxdriver.com>
      3d23e349
  23. 07 10月, 2009 1 次提交
    • E
      net: speedup sk_wake_async() · bcdce719
      Eric Dumazet 提交于
      An incoming datagram must bring into cpu cache *lot* of cache lines,
      in particular : (other parts omitted (hash chains, ip route cache...))
      
      On 32bit arches :
      
      offsetof(struct sock, sk_rcvbuf)       =0x30    (read)
      offsetof(struct sock, sk_lock)         =0x34   (rw)
      
      offsetof(struct sock, sk_sleep)        =0x50 (read)
      offsetof(struct sock, sk_rmem_alloc)   =0x64   (rw)
      offsetof(struct sock, sk_receive_queue)=0x74   (rw)
      
      offsetof(struct sock, sk_forward_alloc)=0x98   (rw)
      
      offsetof(struct sock, sk_callback_lock)=0xcc    (rw)
      offsetof(struct sock, sk_drops)        =0xd8 (read if we add dropcount support, rw if frame dropped)
      offsetof(struct sock, sk_filter)       =0xf8    (read)
      
      offsetof(struct sock, sk_socket)       =0x138 (read)
      
      offsetof(struct sock, sk_data_ready)   =0x15c   (read)
      
      
      We can avoid sk->sk_socket and socket->fasync_list referencing on sockets
      with no fasync() structures. (socket->fasync_list ptr is probably already in cache
      because it shares a cache line with socket->wait, ie location pointed by sk->sk_sleep)
      
      This avoids one cache line load per incoming packet for common cases (no fasync())
      
      We can leave (or even move in a future patch) sk->sk_socket in a cold location
      Signed-off-by: NEric Dumazet <eric.dumazet@gmail.com>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      bcdce719
  24. 01 10月, 2009 1 次提交
  25. 29 9月, 2009 1 次提交
    • A
      net: Add explicit bound checks in net/socket.c · 47379052
      Arjan van de Ven 提交于
      The sys_socketcall() function has a very clever system for the copy
      size of its arguments. Unfortunately, gcc cannot deal with this in
      terms of proving that the copy_from_user() is then always in bounds.
      This is the last (well 9th of this series, but last in the kernel) such
      case around.
      
      With this patch, we can turn on code to make having the boundary provably
      right for the whole kernel, and detect introduction of new security
      accidents of this type early on.
      Signed-off-by: NArjan van de Ven <arjan@linux.intel.com>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      47379052
  26. 23 9月, 2009 1 次提交
  27. 22 9月, 2009 1 次提交
  28. 15 9月, 2009 1 次提交
  29. 14 8月, 2009 1 次提交
  30. 05 4月, 2009 1 次提交
    • E
      socket: use percpu_add() while updating sockets_in_use · 4e69489a
      Eric Dumazet 提交于
      sock_alloc() currently uses following code to update sockets_in_use
      
      get_cpu_var(sockets_in_use)++;
      put_cpu_var(sockets_in_use);
      
      This translates to :
      
      c0436274:       b8 01 00 00 00          mov    $0x1,%eax
      c0436279:       e8 42 40 df ff          call   c022a2c0 <add_preempt_count>
      c043627e:       bb 20 4f 6a c0          mov    $0xc06a4f20,%ebx
      c0436283:       e8 18 ca f0 ff          call   c0342ca0 <debug_smp_processor_id>
      c0436288:       03 1c 85 60 4a 65 c0    add    -0x3f9ab5a0(,%eax,4),%ebx
      c043628f:       ff 03                   incl   (%ebx)
      c0436291:       b8 01 00 00 00          mov    $0x1,%eax
      c0436296:       e8 75 3f df ff          call   c022a210 <sub_preempt_count>
      c043629b:       89 e0                   mov    %esp,%eax
      c043629d:       25 00 e0 ff ff          and    $0xffffe000,%eax
      c04362a2:       f6 40 08 08             testb  $0x8,0x8(%eax)
      c04362a6:       75 07                   jne    c04362af <sock_alloc+0x7f>
      c04362a8:       8d 46 d8                lea    -0x28(%esi),%eax
      c04362ab:       5b                      pop    %ebx
      c04362ac:       5e                      pop    %esi
      c04362ad:       c9                      leave
      c04362ae:       c3                      ret
      c04362af:       e8 cc 5d 09 00          call   c04cc080 <preempt_schedule>
      c04362b4:       8d 74 26 00             lea    0x0(%esi,%eiz,1),%esi
      c04362b8:       eb ee                   jmp    c04362a8 <sock_alloc+0x78>
      
      While percpu_add(sockets_in_use, 1) translates to a single instruction :
      
      c0436275:   64 83 05 20 5f 6a c0    addl   $0x1,%fs:0xc06a5f20
      Signed-off-by: NEric Dumazet <dada1@cosmosbay.com>
      Signed-off-by: NDavid S. Miller <davem@davemloft.net>
      4e69489a