OpenVPN
lzo.c
Go to the documentation of this file.
1/*
2 * OpenVPN -- An application to securely tunnel IP networks
3 * over a single 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-2025 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, see <https://www.gnu.org/licenses/>.
21 */
22
28#ifdef HAVE_CONFIG_H
29#include "config.h"
30#endif
31
32#include "syshead.h"
33
34#if defined(ENABLE_LZO)
35
36#include "comp.h"
37#include "error.h"
38#include "otime.h"
39
40#include "memdbg.h"
41
42
43static void
44lzo_compress_init(struct compress_context *compctx)
45{
46 msg(D_INIT_MEDIUM, "LZO compression initializing");
47 ASSERT(!(compctx->flags & COMP_F_SWAP));
48 compctx->wu.lzo.wmem_size = LZO_WORKSPACE;
49
50 int lzo_status = lzo_init();
51 if (lzo_status != LZO_E_OK)
52 {
53 msg(M_FATAL, "Cannot initialize LZO compression library (lzo_init() returns %d)",
54 lzo_status);
55 }
56 compctx->wu.lzo.wmem = (lzo_voidp)malloc(compctx->wu.lzo.wmem_size);
57 check_malloc_return(compctx->wu.lzo.wmem);
58}
59
60static void
61lzo_compress_uninit(struct compress_context *compctx)
62{
63 free(compctx->wu.lzo.wmem);
64 compctx->wu.lzo.wmem = NULL;
65}
66
67static void
68lzo_compress(struct buffer *buf, struct buffer work, struct compress_context *compctx,
69 const struct frame *frame)
70{
71 uint8_t *header = buf_prepend(buf, 1);
72 *header = NO_COMPRESS_BYTE;
73}
74
75static void
76lzo_decompress(struct buffer *buf, struct buffer work, struct compress_context *compctx,
77 const struct frame *frame)
78{
79 lzo_uint zlen = frame->buf.payload_size;
80 int err;
81 uint8_t c; /* flag indicating whether or not our peer compressed */
82
83 if (buf->len <= 0)
84 {
85 return;
86 }
87
89
90 c = *BPTR(buf);
91 ASSERT(buf_advance(buf, 1));
92
93 if (c == LZO_COMPRESS_BYTE) /* packet was compressed */
94 {
95 ASSERT(buf_safe(&work, zlen));
96 err = LZO_DECOMPRESS(BPTR(buf), BLEN(buf), BPTR(&work), &zlen, compctx->wu.lzo.wmem);
97 if (err != LZO_E_OK)
98 {
99 dmsg(D_COMP_ERRORS, "LZO decompression error: %d", err);
100 buf->len = 0;
101 return;
102 }
103
104 ASSERT(buf_safe(&work, zlen));
105 work.len = zlen;
106
107 dmsg(D_COMP, "LZO decompress %d -> %d", buf->len, work.len);
108 compctx->pre_decompress += buf->len;
109 compctx->post_decompress += work.len;
110
111 *buf = work;
112 }
113 else if (c == NO_COMPRESS_BYTE) /* packet was not compressed */
114 {
115 /* nothing to do */
116 }
117 else
118 {
119 dmsg(D_COMP_ERRORS, "Bad LZO decompression header byte: %d", c);
120 buf->len = 0;
121 }
122}
123
124const struct compress_alg lzo_alg = { "lzo", lzo_compress_init, lzo_compress_uninit, lzo_compress,
125 lzo_decompress };
126#endif /* ENABLE_LZO */
#define BPTR(buf)
Definition buffer.h:123
static bool buf_safe(const struct buffer *buf, size_t len)
Definition buffer.h:518
static bool buf_advance(struct buffer *buf, int size)
Definition buffer.h:616
static uint8_t * buf_prepend(struct buffer *buf, int size)
Definition buffer.h:604
#define BLEN(buf)
Definition buffer.h:126
static void check_malloc_return(void *p)
Definition buffer.h:1085
#define buf_init(buf, offset)
Definition buffer.h:209
#define COMP_F_SWAP
initial command byte is swapped with last byte in buffer to preserve payload alignment
Definition comp.h:40
#define D_COMP_ERRORS
Definition errlevel.h:60
#define D_COMP
Definition errlevel.h:165
#define D_INIT_MEDIUM
Definition errlevel.h:103
#define M_FATAL
Definition error.h:88
#define dmsg(flags,...)
Definition error.h:170
#define msg(flags,...)
Definition error.h:150
#define ASSERT(x)
Definition error.h:217
Wrapper structure for dynamically allocated memory.
Definition buffer.h:60
int len
Length in bytes of the actual content within the allocated memory.
Definition buffer.h:65
Packet geometry parameters.
Definition mtu.h:103
int payload_size
the maximum size that a payload that our buffers can hold from either tun device or network link.
Definition mtu.h:108
int headroom
the headroom in the buffer, this is choosen to allow all potential header to be added before the pack...
Definition mtu.h:114
struct frame::@8 buf