staticint __sock_create(struct net *net,int family,int type,int protocol, structsocket**res,int kern) { int err; structsocket*sock; conststruct net_proto_family *pf;
/* * Check protocol is in range */ if(family < 0 || family >= NPROTO) return-EAFNOSUPPORT; if(type < 0 || type >= SOCK_MAX) return-EINVAL;
/* * Skip some codes */
}
首先这个函数,先对family和type进行检查,查看是否超出正常范围。
/* Compatibility.
This uglymoron is moved from INET layer to here to avoid deadlock in module load. */ if(family ==PF_INET&& type ==SOCK_PACKET){ staticint warned; if(!warned){ warned = 1; printk(KERN_INFO "%s uses obsolete (PF_INET,SOCK_PACKET)\n", current->comm); } family =PF_PACKET; }
/* * Allocate the socket and allow the family to set things up. if * the protocol is 0, the family is instructed to select an appropriate * default. */ sock = sock_alloc(); if(!sock){ if(net_ratelimit()) printk(KERN_WARNING "socket: no more sockets\n"); return-ENFILE;/* Not exactly a match, but its the closest posix thing */ }
/* * We will call the ->create function, that possibly is in a loadable * module, so we have to bump that loadable module refcnt first. */ if(!try_module_get(pf->owner)) goto out_release;
/* Now protected by module ref count */ rcu_read_unlock();
/* * Now to bump the refcnt of the [loadable] module that owns this * socket at sock_release time we decrement its refcnt. */ if(!try_module_get(sock->ops->owner)) goto out_module_busy;
/* * Now that we're done with the ->create function, the [loadable] * module can have its refcnt decremented */ module_put(pf->owner); err = security_socket_post_create(sock, family, type, protocol, kern); if(err) goto out_sock_release; *res = sock;