xref: /linux/drivers/block/zram/backend_lz4hc.c (revision 52c7b4e2ba508a924c991e681db534e66a851adf)
1 #include <linux/kernel.h>
2 #include <linux/lz4.h>
3 #include <linux/slab.h>
4 #include <linux/vmalloc.h>
5 
6 #include "backend_lz4hc.h"
7 
8 struct lz4hc_ctx {
9 	void *mem;
10 	s32 level;
11 };
12 
13 static void lz4hc_destroy(void *ctx)
14 {
15 	struct lz4hc_ctx *zctx = ctx;
16 
17 	vfree(zctx->mem);
18 	kfree(zctx);
19 }
20 
21 static void *lz4hc_create(struct zcomp_params *params)
22 {
23 	struct lz4hc_ctx *ctx;
24 
25 	ctx = kzalloc(sizeof(*ctx), GFP_KERNEL);
26 	if (!ctx)
27 		return NULL;
28 
29 	if (params->level != ZCOMP_PARAM_NO_LEVEL)
30 		ctx->level = params->level;
31 	else
32 		ctx->level = LZ4HC_DEFAULT_CLEVEL;
33 
34 	ctx->mem = vmalloc(LZ4HC_MEM_COMPRESS);
35 	if (!ctx->mem)
36 		goto error;
37 
38 	return ctx;
39 error:
40 	lz4hc_destroy(ctx);
41 	return NULL;
42 }
43 
44 static int lz4hc_compress(void *ctx, struct zcomp_req *req)
45 {
46 	struct lz4hc_ctx *zctx = ctx;
47 	int ret;
48 
49 	ret = LZ4_compress_HC(req->src, req->dst, req->src_len, req->dst_len,
50 			      zctx->level, zctx->mem);
51 	if (!ret)
52 		return -EINVAL;
53 	req->dst_len = ret;
54 	return 0;
55 }
56 
57 static int lz4hc_decompress(void *ctx, struct zcomp_req *req)
58 {
59 	int ret;
60 
61 	ret = LZ4_decompress_safe(req->src, req->dst, req->src_len,
62 				  req->dst_len);
63 	if (ret < 0)
64 		return -EINVAL;
65 	return 0;
66 }
67 
68 const struct zcomp_ops backend_lz4hc = {
69 	.compress	= lz4hc_compress,
70 	.decompress	= lz4hc_decompress,
71 	.create_ctx	= lz4hc_create,
72 	.destroy_ctx	= lz4hc_destroy,
73 	.name		= "lz4hc",
74 };
75