xref: /netbsd-src/usr.sbin/btpand/packet.c (revision 02f520acc7e0811cc2b77eb4be217c4c8625187f)
1*02f520acSplunky /*	$NetBSD: packet.c,v 1.2 2009/05/02 20:07:51 plunky Exp $	*/
21fc74d21Splunky 
31fc74d21Splunky /*-
41fc74d21Splunky  * Copyright (c) 2008 Iain Hibbert
51fc74d21Splunky  * All rights reserved.
61fc74d21Splunky  *
71fc74d21Splunky  * Redistribution and use in source and binary forms, with or without
81fc74d21Splunky  * modification, are permitted provided that the following conditions
91fc74d21Splunky  * are met:
101fc74d21Splunky  * 1. Redistributions of source code must retain the above copyright
111fc74d21Splunky  *    notice, this list of conditions and the following disclaimer.
121fc74d21Splunky  * 2. Redistributions in binary form must reproduce the above copyright
131fc74d21Splunky  *    notice, this list of conditions and the following disclaimer in the
141fc74d21Splunky  *    documentation and/or other materials provided with the distribution.
151fc74d21Splunky  *
161fc74d21Splunky  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
171fc74d21Splunky  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
181fc74d21Splunky  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
191fc74d21Splunky  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
201fc74d21Splunky  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
211fc74d21Splunky  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
221fc74d21Splunky  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
231fc74d21Splunky  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
241fc74d21Splunky  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
251fc74d21Splunky  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
261fc74d21Splunky  */
271fc74d21Splunky 
281fc74d21Splunky #include <sys/cdefs.h>
29*02f520acSplunky __RCSID("$NetBSD: packet.c,v 1.2 2009/05/02 20:07:51 plunky Exp $");
301fc74d21Splunky 
311fc74d21Splunky #include "btpand.h"
321fc74d21Splunky 
331fc74d21Splunky packet_t *
packet_alloc(channel_t * chan)341fc74d21Splunky packet_alloc(channel_t *chan)
351fc74d21Splunky {
361fc74d21Splunky 	packet_t *pkt;
371fc74d21Splunky 
381fc74d21Splunky 	pkt = malloc(sizeof(packet_t) + chan->mru);
391fc74d21Splunky 	if (pkt == NULL) {
401fc74d21Splunky 		log_err("%s() failed: %m", __func__);
411fc74d21Splunky 		return NULL;
421fc74d21Splunky 	}
431fc74d21Splunky 
441fc74d21Splunky 	memset(pkt, 0, sizeof(packet_t));
451fc74d21Splunky 	STAILQ_INIT(&pkt->extlist);
461fc74d21Splunky 	pkt->ptr = pkt->buf;
471fc74d21Splunky 
481fc74d21Splunky 	pkt->chan = chan;
491fc74d21Splunky 	chan->refcnt++;
501fc74d21Splunky 
511fc74d21Splunky 	return pkt;
521fc74d21Splunky }
531fc74d21Splunky 
541fc74d21Splunky void
packet_free(packet_t * pkt)551fc74d21Splunky packet_free(packet_t *pkt)
561fc74d21Splunky {
571fc74d21Splunky 	exthdr_t *eh;
581fc74d21Splunky 
591fc74d21Splunky 	if (pkt->refcnt-- > 0)
601fc74d21Splunky 		return;
611fc74d21Splunky 
621fc74d21Splunky 	while ((eh = STAILQ_FIRST(&pkt->extlist)) != NULL) {
631fc74d21Splunky 		STAILQ_REMOVE_HEAD(&pkt->extlist, next);
641fc74d21Splunky 		free(eh);
651fc74d21Splunky 	}
661fc74d21Splunky 
671fc74d21Splunky 	pkt->chan->refcnt--;
681fc74d21Splunky 	if (pkt->chan->refcnt == 0)
691fc74d21Splunky 		channel_free(pkt->chan);
701fc74d21Splunky 
711fc74d21Splunky 	free(pkt);
721fc74d21Splunky }
731fc74d21Splunky 
741fc74d21Splunky void
packet_adj(packet_t * pkt,size_t size)751fc74d21Splunky packet_adj(packet_t *pkt, size_t size)
761fc74d21Splunky {
771fc74d21Splunky 
78*02f520acSplunky 	assert(pkt->refcnt == 0);
79*02f520acSplunky 	assert(pkt->len >= size);
801fc74d21Splunky 
811fc74d21Splunky 	pkt->ptr += size;
821fc74d21Splunky 	pkt->len -= size;
831fc74d21Splunky }
841fc74d21Splunky 
851fc74d21Splunky pkthdr_t *
pkthdr_alloc(packet_t * pkt)861fc74d21Splunky pkthdr_alloc(packet_t *pkt)
871fc74d21Splunky {
881fc74d21Splunky 	pkthdr_t *ph;
891fc74d21Splunky 
901fc74d21Splunky 	ph = malloc(sizeof(pkthdr_t));
911fc74d21Splunky 	if (ph == NULL) {
921fc74d21Splunky 		log_err("%s() failed: %m", __func__);
931fc74d21Splunky 		return NULL;
941fc74d21Splunky 	}
951fc74d21Splunky 
961fc74d21Splunky 	ph->data = pkt;
971fc74d21Splunky 	pkt->refcnt++;
981fc74d21Splunky 
991fc74d21Splunky 	return ph;
1001fc74d21Splunky }
1011fc74d21Splunky 
1021fc74d21Splunky void
pkthdr_free(pkthdr_t * ph)1031fc74d21Splunky pkthdr_free(pkthdr_t *ph)
1041fc74d21Splunky {
1051fc74d21Splunky 
1061fc74d21Splunky 	packet_free(ph->data);
1071fc74d21Splunky 	free(ph);
1081fc74d21Splunky }
109