net/kcm/kcmsock.c

Source file repositories/reference/linux-study-clean/net/kcm/kcmsock.c

File Facts

System
Linux kernel
Corpus path
net/kcm/kcmsock.c
Extension
.c
Size
43545 bytes
Lines
1951
Domain
Networking Core
Bucket
Sockets, Protocols, Packet Path, And Network Policy
Inferred role
Networking Core: operation-table or driver-model contract
Status
pattern implementation candidate

Why This File Exists

Networking stack implementation surface: socket APIs, protocol dispatch, packet flow, routing, filtering, and network namespaces.

Dependency Surface

Detected Declarations

Annotated Snippet

static const struct proto_ops kcm_dgram_ops = {
	.family =	PF_KCM,
	.owner =	THIS_MODULE,
	.release =	kcm_release,
	.bind =		sock_no_bind,
	.connect =	sock_no_connect,
	.socketpair =	sock_no_socketpair,
	.accept =	sock_no_accept,
	.getname =	sock_no_getname,
	.poll =		datagram_poll,
	.ioctl =	kcm_ioctl,
	.listen =	sock_no_listen,
	.shutdown =	sock_no_shutdown,
	.setsockopt =	kcm_setsockopt,
	.getsockopt_iter = kcm_getsockopt,
	.sendmsg =	kcm_sendmsg,
	.recvmsg =	kcm_recvmsg,
	.mmap =		sock_no_mmap,
	.splice_eof =	kcm_splice_eof,
};

static const struct proto_ops kcm_seqpacket_ops = {
	.family =	PF_KCM,
	.owner =	THIS_MODULE,
	.release =	kcm_release,
	.bind =		sock_no_bind,
	.connect =	sock_no_connect,
	.socketpair =	sock_no_socketpair,
	.accept =	sock_no_accept,
	.getname =	sock_no_getname,
	.poll =		datagram_poll,
	.ioctl =	kcm_ioctl,
	.listen =	sock_no_listen,
	.shutdown =	sock_no_shutdown,
	.setsockopt =	kcm_setsockopt,
	.getsockopt_iter = kcm_getsockopt,
	.sendmsg =	kcm_sendmsg,
	.recvmsg =	kcm_recvmsg,
	.mmap =		sock_no_mmap,
	.splice_eof =	kcm_splice_eof,
	.splice_read =	kcm_splice_read,
};

/* Create proto operation for kcm sockets */
static int kcm_create(struct net *net, struct socket *sock,
		      int protocol, int kern)
{
	struct kcm_net *knet = net_generic(net, kcm_net_id);
	struct sock *sk;
	struct kcm_mux *mux;

	switch (sock->type) {
	case SOCK_DGRAM:
		sock->ops = &kcm_dgram_ops;
		break;
	case SOCK_SEQPACKET:
		sock->ops = &kcm_seqpacket_ops;
		break;
	default:
		return -ESOCKTNOSUPPORT;
	}

	if (protocol != KCMPROTO_CONNECTED)
		return -EPROTONOSUPPORT;

	sk = sk_alloc(net, PF_KCM, GFP_KERNEL, &kcm_proto, kern);
	if (!sk)
		return -ENOMEM;

	/* Allocate a kcm mux, shared between KCM sockets */
	mux = kmem_cache_zalloc(kcm_muxp, GFP_KERNEL);
	if (!mux) {
		sk_free(sk);
		return -ENOMEM;
	}

	spin_lock_init(&mux->lock);
	spin_lock_init(&mux->rx_lock);
	INIT_LIST_HEAD(&mux->kcm_socks);
	INIT_LIST_HEAD(&mux->kcm_rx_waiters);
	INIT_LIST_HEAD(&mux->kcm_tx_waiters);

	INIT_LIST_HEAD(&mux->psocks);
	INIT_LIST_HEAD(&mux->psocks_ready);
	INIT_LIST_HEAD(&mux->psocks_avail);

	mux->knet = knet;

	/* Add new MUX to list */
	mutex_lock(&knet->mutex);

Annotation

Implementation Notes