OpenVPN
mbuf.c
Go to the documentation of this file.
1 /*
2  * OpenVPN -- An application to securely tunnel IP networks
3  * over a single TCP/UDP port, with support for SSL/TLS-based
4  * session authentication and key exchange,
5  * packet encryption, packet authentication, and
6  * packet compression.
7  *
8  * Copyright (C) 2002-2023 OpenVPN Inc <sales@openvpn.net>
9  *
10  * This program is free software; you can redistribute it and/or modify
11  * it under the terms of the GNU General Public License version 2
12  * as published by the Free Software Foundation.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License along
20  * with this program; if not, write to the Free Software Foundation, Inc.,
21  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
22  */
23 
24 #ifdef HAVE_CONFIG_H
25 #include "config.h"
26 #endif
27 
28 #include "syshead.h"
29 
30 #include "buffer.h"
31 #include "error.h"
32 #include "integer.h"
33 #include "misc.h"
34 #include "mbuf.h"
35 
36 #include "memdbg.h"
37 
38 struct mbuf_set *
39 mbuf_init(unsigned int size)
40 {
41  struct mbuf_set *ret;
42  ALLOC_OBJ_CLEAR(ret, struct mbuf_set);
43  ret->capacity = adjust_power_of_2(size);
44  ALLOC_ARRAY(ret->array, struct mbuf_item, ret->capacity);
45  return ret;
46 }
47 
48 void
49 mbuf_free(struct mbuf_set *ms)
50 {
51  if (ms)
52  {
53  int i;
54  for (i = 0; i < (int) ms->len; ++i)
55  {
56  struct mbuf_item *item = &ms->array[MBUF_INDEX(ms->head, i, ms->capacity)];
57  mbuf_free_buf(item->buffer);
58  }
59  free(ms->array);
60  free(ms);
61  }
62 }
63 
64 struct mbuf_buffer *
65 mbuf_alloc_buf(const struct buffer *buf)
66 {
67  struct mbuf_buffer *ret;
68  ALLOC_OBJ(ret, struct mbuf_buffer);
69  ret->buf = clone_buf(buf);
70  ret->refcount = 1;
71  ret->flags = 0;
72  return ret;
73 }
74 
75 void
77 {
78  if (mb)
79  {
80  if (--mb->refcount <= 0)
81  {
82  free_buf(&mb->buf);
83  free(mb);
84  }
85  }
86 }
87 
88 void
89 mbuf_add_item(struct mbuf_set *ms, const struct mbuf_item *item)
90 {
91  ASSERT(ms);
92  if (ms->len == ms->capacity)
93  {
94  struct mbuf_item rm;
95  ASSERT(mbuf_extract_item(ms, &rm));
97  msg(D_MULTI_DROPPED, "MBUF: mbuf packet dropped");
98  }
99 
100  ASSERT(ms->len < ms->capacity);
101 
102  ms->array[MBUF_INDEX(ms->head, ms->len, ms->capacity)] = *item;
103  if (++ms->len > ms->max_queued)
104  {
105  ms->max_queued = ms->len;
106  }
107  ++item->buffer->refcount;
108 }
109 
110 bool
111 mbuf_extract_item(struct mbuf_set *ms, struct mbuf_item *item)
112 {
113  bool ret = false;
114  if (ms)
115  {
116  while (ms->len)
117  {
118  *item = ms->array[ms->head];
119  ms->head = MBUF_INDEX(ms->head, 1, ms->capacity);
120  --ms->len;
121  if (item->instance) /* ignore dereferenced instances */
122  {
123  ret = true;
124  break;
125  }
126  }
127  }
128  return ret;
129 }
130 
131 struct multi_instance *
133 {
134  struct multi_instance *ret = NULL;
135  if (ms)
136  {
137  int i;
138  for (i = 0; i < (int) ms->len; ++i)
139  {
140  struct mbuf_item *item = &ms->array[MBUF_INDEX(ms->head, i, ms->capacity)];
141  if (item->instance)
142  {
143  ret = item->instance;
144  break;
145  }
146  }
147  }
148  return ret;
149 }
150 
151 void
153 {
154  if (ms)
155  {
156  int i;
157  for (i = 0; i < (int) ms->len; ++i)
158  {
159  struct mbuf_item *item = &ms->array[MBUF_INDEX(ms->head, i, ms->capacity)];
160  if (item->instance == mi)
161  {
162  mbuf_free_buf(item->buffer);
163  item->buffer = NULL;
164  item->instance = NULL;
165  msg(D_MBUF, "MBUF: dereferenced queued packet");
166  }
167  }
168  }
169 }
mbuf_extract_item
bool mbuf_extract_item(struct mbuf_set *ms, struct mbuf_item *item)
Definition: mbuf.c:111
multi_instance
Server-mode state structure for one single VPN tunnel.
Definition: multi.h:101
error.h
mbuf_set
Definition: mbuf.h:56
mbuf_peek_dowork
struct multi_instance * mbuf_peek_dowork(struct mbuf_set *ms)
Definition: mbuf.c:132
mbuf_buffer::refcount
int refcount
Definition: mbuf.h:44
clone_buf
struct buffer clone_buf(const struct buffer *buf)
Definition: buffer.c:115
D_MBUF
#define D_MBUF
Definition: errlevel.h:99
ASSERT
#define ASSERT(x)
Definition: error.h:201
mbuf_add_item
void mbuf_add_item(struct mbuf_set *ms, const struct mbuf_item *item)
Definition: mbuf.c:89
ALLOC_OBJ
#define ALLOC_OBJ(dptr, type)
Definition: buffer.h:1061
mbuf_set::len
unsigned int len
Definition: mbuf.h:59
misc.h
mbuf_free
void mbuf_free(struct mbuf_set *ms)
Definition: mbuf.c:49
mbuf.h
adjust_power_of_2
static size_t adjust_power_of_2(size_t u)
Definition: integer.h:168
mbuf_set::max_queued
unsigned int max_queued
Definition: mbuf.h:61
mbuf_item::instance
struct multi_instance * instance
Definition: mbuf.h:53
mbuf_buffer::buf
struct buffer buf
Definition: mbuf.h:43
buffer
Wrapper structure for dynamically allocated memory.
Definition: buffer.h:60
mbuf_item
Definition: mbuf.h:50
buffer.h
syshead.h
mbuf_set::head
unsigned int head
Definition: mbuf.h:58
mbuf_alloc_buf
struct mbuf_buffer * mbuf_alloc_buf(const struct buffer *buf)
Definition: mbuf.c:65
MBUF_INDEX
#define MBUF_INDEX(head, offset, size)
Definition: mbuf.h:39
mbuf_buffer
Definition: mbuf.h:41
mbuf_buffer::flags
unsigned int flags
Definition: mbuf.h:47
free_buf
void free_buf(struct buffer *buf)
Definition: buffer.c:183
D_MULTI_DROPPED
#define D_MULTI_DROPPED
Definition: errlevel.h:101
mbuf_free_buf
void mbuf_free_buf(struct mbuf_buffer *mb)
Definition: mbuf.c:76
mbuf_set::capacity
unsigned int capacity
Definition: mbuf.h:60
ALLOC_OBJ_CLEAR
#define ALLOC_OBJ_CLEAR(dptr, type)
Definition: buffer.h:1066
config.h
mbuf_item::buffer
struct mbuf_buffer * buffer
Definition: mbuf.h:52
mbuf_dereference_instance
void mbuf_dereference_instance(struct mbuf_set *ms, struct multi_instance *mi)
Definition: mbuf.c:152
memdbg.h
ALLOC_ARRAY
#define ALLOC_ARRAY(dptr, type, n)
Definition: buffer.h:1072
mbuf_init
struct mbuf_set * mbuf_init(unsigned int size)
Definition: mbuf.c:39
mbuf_set::array
struct mbuf_item * array
Definition: mbuf.h:62
msg
#define msg(flags,...)
Definition: error.h:150
integer.h