⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 inet.c

📁 7号信令功能代码,为开源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
#define TF_SCTP_OSTREAMS		(1<<25)#define TF_SCTP_ISTREAMS		(1<<26)#define TF_SCTP_COOKIE_INC		(1<<27)#define TF_SCTP_THROTTLE_ITVL		(1<<28)#define TF_SCTP_MAC_TYPE		(1<<29)#define TF_SCTP_HB			(1<<30)#define TF_SCTP_RTO			(1<<31)#define TF_SCTP_STATUS			(1<< 6)	/* FIXME */#define TF_SCTP_DEBUG			(1<< 7)	/* FIXME */#endif#define TM_OPT_SENDMSG	(	TF_IP_OPTIONS	\			|	TF_IP_TOS	\			|	TF_IP_TTL	\			|	TF_IP_DONTROUTE	\			|	TF_IP_PKTINFO	\			)#define _T_CHECK		1#define _T_NEGOTIATE		2#define _T_DEFAULT		3#define _T_CURRENT		4#define TF_CHECK		(1<<_T_CHECK)#define TF_NEGOTIATE		(1<<_T_NEGOTIATE)#define TF_DEFAULT		(1<<_T_DEFAULT)#define TF_CURRENT		(1<<_T_CURRENT)typedef struct ss_event {	struct sock *sk;		/* sock (child) for event */	int state;			/* state at time of event */} ss_event_t;STATIC lis_spin_lock_t ss_lock;		/* protects ss_opens lists */STATIC ss_t *ss_opens = NULL;#if 0/*  * for later when we support default destinations and default listeners  */STATIC ss_t *ss_dflt_dest = NULL;STATIC ss_t *ss_dflt_lstn = NULL;#endif/*  *  ========================================================================= * *  Socket Callbacks * *  ========================================================================= */STATIC void ss_state_change(struct sock *sk);STATIC void ss_write_space(struct sock *sk);STATIC void ss_error_report(struct sock *sk);STATIC void ss_data_ready(struct sock *sk, int len);STATIC voidss_socket_put(struct socket *sock){	struct sock *sk;	ensure(sock, return);	if ((sk = sock->sk)) {		write_lock(&sk->callback_lock);		{			ss_t *ss;			if ((ss = SOCK_PRIV(sk))) {				SOCK_PRIV(sk) = NULL;				ss->refcnt--;				sk->state_change = ss->cb_save.state_change;				sk->data_ready = ss->cb_save.data_ready;				sk->write_space = ss->cb_save.write_space;				sk->error_report = ss->cb_save.error_report;			} else				assure(ss);		}		write_unlock(&sock->sk->callback_lock);	} else		assure(sk);	sock_release(sock);}STATIC voidss_socket_get(struct socket *sock, ss_t * ss){	struct sock *sk;	ensure(sock, return);	sk = sock->sk;	ensure(sk, return);	write_lock(&sock->sk->callback_lock);	{		SOCK_PRIV(sk) = ss;		ss->refcnt++;		ss->cb_save.state_change = sk->state_change;		ss->cb_save.data_ready = sk->data_ready;		ss->cb_save.write_space = sk->write_space;		ss->cb_save.error_report = sk->error_report;		sk->state_change = ss_state_change;		sk->data_ready = ss_data_ready;		sk->write_space = ss_write_space;		sk->error_report = ss_error_report;#ifdef LINUX_2_4		sk->protinfo.af_inet.recverr = 1;#else		sk->ip_recverr = 1;#endif		ss->tcp_state = sk->state;	/* initialized tcp state */	}	write_unlock(&sock->sk->callback_lock);}/*  *  ========================================================================= * *  Locking * *  ========================================================================= */STATIC intss_trylockq(queue_t *q){	int res;	ss_t *ss = PRIV(q);	if (!(res = lis_spin_trylock(&ss->qlock))) {		if (q == ss->rq)			ss->rwait = q;		if (q == ss->wq)			ss->wwait = q;	}	return (res);}STATIC voidss_unlockq(queue_t *q){	ss_t *ss = PRIV(q);	lis_spin_unlock(&ss->qlock);	if (ss->rwait)		qenable(xchg(&ss->rwait, NULL));	if (ss->wwait)		qenable(xchg(&ss->wwait, NULL));}/*  *  ========================================================================= * *  Buffer Allocation * *  ========================================================================= *//*  *  BUFSRV calls service routine *  ------------------------------------------------------------------------- */STATIC voidss_bufsrv(long data){	queue_t *q = (queue_t *) data;	if (q) {		ss_t *ss = PRIV(q);		if (q == ss->rq)			if (ss->rbid) {				ss->rbid = 0;				ss->refcnt--;			}		if (q == ss->wq)			if (ss->wbid) {				ss->wbid = 0;				ss->refcnt--;			}		qenable(q);	}}/*  *  UNBUFCALL *  ------------------------------------------------------------------------- */STATIC voidss_unbufcall(queue_t *q){	ss_t *ss = PRIV(q);	if (ss->rbid) {		unbufcall(xchg(&ss->rbid, 0));		ss->refcnt--;	}	if (ss->wbid) {		unbufcall(xchg(&ss->wbid, 0));		ss->refcnt--;	}}/*  *  ALLOCB *  ------------------------------------------------------------------------- */STATIC mblk_t *ss_allocb(queue_t *q, size_t size, int prior){	mblk_t *mp;	if ((mp = allocb(size, prior)))		return (mp);	else {		ss_t *ss = PRIV(q);		if (q == ss->rq) {			if (!ss->rbid) {				ss->rbid = bufcall(size, prior, &ss_bufsrv, (long) q);				ss->refcnt++;			}			return (NULL);		}		if (q == ss->wq) {			if (!ss->wbid) {				ss->wbid = bufcall(size, prior, &ss_bufsrv, (long) q);				ss->refcnt++;			}			return (NULL);		}	}	swerr();	return (NULL);}#if 0/*  *  ESBALLOC *  ------------------------------------------------------------------------- */STATIC mblk_t *ss_esballoc(queue_t *q, unsigned char *base, size_t size, int prior, frtn_t *frtn){	mblk_t *mp;	if ((mp = esballoc(base, size, prior, frtn)))		return (mp);	else {		ss_t *ss = PRIV(q);		if (q == ss->rq) {			if (!ss->rbid) {				ss->rbid = esbbcall(prior, &ss_bufsrv, (long) q);				ss->refcnt++;			}			return (NULL);		}		if (q == ss->wq) {			if (!ss->wbid) {				ss->wbid = esbbcall(prior, &ss_bufsrv, (long) q);				ss->refcnt++;			}			return (NULL);		}		swerr();		return (NULL);	}}#endif/*  *  ========================================================================= * *  OPTION Handling * *  ========================================================================= */#define _T_ALIGN_SIZEOF(s) \	((sizeof((s)) + _T_ALIGN_SIZE - 1) & ~(_T_ALIGN_SIZE - 1))STATIC size_tss_opts_size(ss_t * ss, ss_opts_t * ops){	size_t len = 0;	const size_t hlen = sizeof(struct t_opthdr);	/* 32 bytes */	if (ops) {		if (ops->opt)			len += hlen + _T_ALIGN_SIZEOF(*(ops->opt));		if (ops->tos)			len += hlen + _T_ALIGN_SIZEOF(*(ops->tos));		if (ops->ttl)			len += hlen + _T_ALIGN_SIZEOF(*(ops->ttl));		if (ops->reuse)			len += hlen + _T_ALIGN_SIZEOF(*(ops->reuse));		if (ops->norte)			len += hlen + _T_ALIGN_SIZEOF(*(ops->norte));		if (ops->bcast)			len += hlen + _T_ALIGN_SIZEOF(*(ops->bcast));		if (ss->p.prot.protocol == T_INET_TCP) {			if (ops->nodly)				len += hlen + _T_ALIGN_SIZEOF(*(ops->nodly));			if (ops->mss)				len += hlen + _T_ALIGN_SIZEOF(*(ops->mss));			if (ops->alive)				len += hlen + _T_ALIGN_SIZEOF(*(ops->alive));		}		if (ss->p.prot.protocol == T_INET_UDP) {			if (ops->csum)				len += hlen + _T_ALIGN_SIZEOF(*(ops->csum));		}#if defined CONFIG_SCTP || defined CONFIG_SCTP_MODULE		if (ss->p.prot.protocol == T_INET_SCTP) {			if (ops->nodly)				len += hlen + _T_ALIGN_SIZEOF(*(ops->nodly));			if (ops->cork)				len += hlen + _T_ALIGN_SIZEOF(*(ops->cork));			if (ops->mss)				len += hlen + _T_ALIGN_SIZEOF(*(ops->mss));			if (ops->ppi)				len += hlen + _T_ALIGN_SIZEOF(*(ops->ppi));			if (ops->sid)				len += hlen + _T_ALIGN_SIZEOF(*(ops->sid));			if (ops->ssn)				len += hlen + _T_ALIGN_SIZEOF(*(ops->ssn));			if (ops->tsn)				len += hlen + _T_ALIGN_SIZEOF(*(ops->tsn));			if (ops->recvopt)				len += hlen + _T_ALIGN_SIZEOF(*(ops->recvopt));			if (ops->clife)				len += hlen + _T_ALIGN_SIZEOF(*(ops->clife));			if (ops->sack)				len += hlen + _T_ALIGN_SIZEOF(*(ops->sack));			if (ops->prtx)				len += hlen + _T_ALIGN_SIZEOF(*(ops->prtx));			if (ops->artx)				len += hlen + _T_ALIGN_SIZEOF(*(ops->artx));			if (ops->irtx)				len += hlen + _T_ALIGN_SIZEOF(*(ops->irtx));			if (ops->hitvl)				len += hlen + _T_ALIGN_SIZEOF(*(ops->hitvl));			if (ops->rtoinit)				len += hlen + _T_ALIGN_SIZEOF(*(ops->rtoinit));			if (ops->rtomin)				len += hlen + _T_ALIGN_SIZEOF(*(ops->rtomin));			if (ops->rtomax)				len += hlen + _T_ALIGN_SIZEOF(*(ops->rtomax));			if (ops->ostr)				len += hlen + _T_ALIGN_SIZEOF(*(ops->ostr));			if (ops->istr)				len += hlen + _T_ALIGN_SIZEOF(*(ops->istr));			if (ops->cinc)				len += hlen + _T_ALIGN_SIZEOF(*(ops->cinc));			if (ops->titvl)				len += hlen + _T_ALIGN_SIZEOF(*(ops->titvl));			if (ops->mac)				len += hlen + _T_ALIGN_SIZEOF(*(ops->mac));			if (ops->hb)				len += hlen + _T_ALIGN_SIZEOF(*(ops->hb));			if (ops->rto)				len += hlen + _T_ALIGN_SIZEOF(*(ops->rto));			if (ops->stat)				len += hlen + _T_ALIGN_SIZEOF(*(ops->stat));	/* FIXME add more */			if (ops->debug)				len += hlen + _T_ALIGN_SIZEOF(*(ops->debug));		}#endif	}	return (len);}STATIC voidss_build_opts(ss_t * ss, ss_opts_t * ops, unsigned char **p){	struct t_opthdr *oh;	const size_t hlen = sizeof(struct t_opthdr);	const size_t olen = hlen + sizeof(t_scalar_t);	if (ops) {		if (ops->opt) {			oh = ((typeof(oh)) * p)++;			oh->len = hlen + sizeof(struct ip_options);			oh->level = T_INET_IP;			oh->name = T_IP_OPTIONS;			oh->status = (ops->flags & TF_IP_OPTIONS) ? T_SUCCESS : T_FAILURE;			*((struct ip_options *) *p) = *(ops->opt);			*p += _T_ALIGN_SIZEOF(*ops->opt);		}		if (ops->tos) {			oh = ((typeof(oh)) * p)++;			oh->len = olen;			oh->level = T_INET_IP;			oh->name = T_IP_TOS;			oh->status = (ops->flags & TF_IP_TOS) ? T_SUCCESS : T_FAILURE;			*((t_scalar_t *) * p) = *(ops->tos);			*p += _T_ALIGN_SIZEOF(*ops->tos);		}		if (ops->ttl) {			oh = ((typeof(oh)) * p)++;			oh->len = olen;			oh->level = T_INET_IP;			oh->name = T_IP_TTL;			oh->status = (ops->flags & TF_IP_TTL) ? T_SUCCESS : T_FAILURE;			*((t_scalar_t *) * p) = *(ops->ttl);			*p += _T_ALIGN_SIZEOF(*ops->ttl);		}		if (ops->reuse) {			oh = ((typeof(oh)) * p)++;			oh->len = olen;			oh->level = T_INET_IP;			oh->name = T_IP_REUSEADDR;			oh->status = (ops->flags & TF_IP_REUSEADDR) ? T_SUCCESS : T_FAILURE;			*((t_scalar_t *) * p) = *(ops->reuse);			*p += _T_ALIGN_SIZEOF(*ops->reuse);		}		if (ops->norte) {			oh = ((typeof(oh)) * p)++;			oh->len = olen;			oh->level = T_INET_IP;			oh->name = T_IP_DONTROUTE;			oh->status = (ops->flags & TF_IP_DONTROUTE) ? T_SUCCESS : T_FAILURE;			*((t_scalar_t *) * p) = *(ops->norte);			*p += _T_ALIGN_SIZEOF(*ops->norte);		}		if (ops->bcast) {			oh = ((typeof(oh)) * p)++;			oh->len = olen;			oh->level = T_INET_IP;			oh->name = T_IP_BROADCAST;			oh->status = (ops->flags & TF_IP_BROADCAST) ? T_SUCCESS : T_FAILURE;			*((t_scalar_t *) * p) = *(ops->bcast);			*p += _T_ALIGN_SIZEOF(*ops->bcast);		}		if (ss->p.prot.protocol == T_INET_TCP) {			if (ops->nodly) {				oh = ((typeof(oh)) * p)++;				oh->len = olen;				oh->level = T_INET_TCP;				oh->name = T_TCP_NODELAY;				oh->status = (ops->flags & TF_TCP_NODELAY) ? T_SUCCESS : T_FAILURE;				*((t_scalar_t *) * p) = *(ops->nodly);				*p += _T_ALIGN_SIZEOF(*ops->nodly);			}			if (ops->mss) {				oh = ((typeof(oh)) * p)++;				oh->len = olen;				oh->level = T_INET_TCP;				oh->name = T_TCP_MAXSEG;				oh->status = (ops->flags & TF_TCP_MAXSEG) ? T_SUCCESS : T_FAILURE;				*((t_scalar_t *) * p) = *(ops->mss);				*p += _T_ALIGN_SIZEOF(*ops->mss);			}			if (ops->alive) {				oh = ((typeof(oh)) * p)++;				oh->len = olen;				oh->level = T_INET_TCP;				oh->name = T_TCP_KEEPALIVE;				oh->status =				    (ops->flags & TF_TCP_KEEPALIVE) ? T_SUCCESS : T_FAILURE;				*((t_scalar_t *) * p) = *(ops->alive);				*p += _T_ALIGN_SIZEOF(*ops->alive);			}		}		if (ss->p.prot.protocol == T_INET_UDP) {			if (ops->csum) {				oh = ((typeof(oh)) * p)++;				oh->len = olen;				oh->level = T_INET_UDP;				oh->name = T_UDP_CHECKSUM;				oh->status = (ops->flags & TF_UDP_CHECKSUM) ? T_SUCCESS : T_FAILURE;				*((t_scalar_t *) * p) = *(ops->csum);				*p += _T_ALIGN_SIZEOF(*ops->csum);			}		}	}}STATIC intss_parse_opts(ss_t * ss, ss_opts_t * ops, unsigned char *op, size_t len){	struct t_opthdr *oh;	for (oh = _T_OPT_FIRSTHDR_OFS(op, len, 0); oh; oh = _T_OPT_NEXTHDR_OFS(op, len, oh, 0)) {		switch (oh->level) {		case T_INET_IP:			switch (oh->name) {			case T_IP_OPTIONS:				ops->opt = (void *) _T_OPT_DATA_OFS(oh, 0);				ops->flags |= TF_IP_OPTIONS;				continue;			case T_IP_TOS:				ops->tos = (void *) _T_OPT_DATA_OFS(oh, 0);				ops->flags |= TF_IP_TOS;				continue;			case T_IP_TTL:				ops->ttl = (void *) _T_OPT_DATA_OFS(oh, 0);				ops->flags |= TF_IP_TTL;				continue;			case T_IP_REUSEADDR:				ops->reuse = (void *) _T_OPT_DATA_OFS(oh, 0);				ops->flags |= TF_IP_REUSEADDR;				continue;			case T_IP_DONTROUTE:				ops->norte = (void *) _T_OPT_DATA_OFS(oh, 0);				ops->flags |= TF_IP_DONTROUTE;				continue;			case T_IP_BROADCAST:

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -