Coverage Report

Created: 2025-07-11 06:33

/src/testdir/tests/capi/lua_load_test.cc
Line
Count
Source (jump to first uncovered line)
1
/*
2
 * SPDX-License-Identifier: ISC
3
 *
4
 * Copyright 2023, Sergey Bronnikov.
5
 */
6
7
#include <assert.h>
8
#include <string.h>
9
10
#if defined(__cplusplus)
11
extern "C" {
12
#endif /* defined(__cplusplus) */
13
14
#include "lua.h"
15
#include "lualib.h"
16
#include "lauxlib.h"
17
18
#if defined(__cplusplus)
19
} /* extern "C" */
20
#endif /* defined(__cplusplus) */
21
22
#include <fuzzer/FuzzedDataProvider.h>
23
24
typedef struct {
25
  FuzzedDataProvider *fdp;
26
} dt;
27
28
static const char *
29
Reader(lua_State *L, void *data, size_t *size)
30
902k
{
31
902k
  dt *test_data = (dt *)data;
32
902k
  static char *buf = NULL;
33
34
902k
  FuzzedDataProvider *fdp = test_data->fdp;
35
902k
  uint8_t max_str_size = fdp->ConsumeIntegral<uint8_t>();
36
902k
  if (fdp->remaining_bytes() < max_str_size)
37
872
    return NULL;
38
902k
  auto str = fdp->ConsumeRandomLengthString(max_str_size);
39
902k
  *size = str.size();
40
41
902k
  free(buf);
42
902k
  buf = (char *)malloc(*size);
43
902k
  assert(buf);
44
902k
  memcpy(buf, str.c_str(), *size);
45
46
902k
  return buf;
47
902k
}
48
49
extern "C" int
50
LLVMFuzzerTestOneInput(const uint8_t *data, size_t size)
51
3.41k
{
52
3.41k
  lua_State *L = luaL_newstate();
53
3.41k
  if (L == NULL)
54
0
    return 0;
55
56
3.41k
  luaL_openlibs(L);
57
58
3.41k
  FuzzedDataProvider fdp(data, size);
59
3.41k
  dt test_data;
60
3.41k
  test_data.fdp = &fdp;
61
62
#if LUA_VERSION_NUM == 501
63
  int res = lua_load(L, Reader, &test_data, "libFuzzer");
64
#else /* Lua 5.3+ */
65
3.41k
  const char *mode = "t";
66
3.41k
  int res = lua_load(L, Reader, &test_data, "libFuzzer", mode);
67
3.41k
#endif /* LUA_VERSION_NUM */
68
3.41k
  if (res == LUA_OK) {
69
2.61k
    lua_pcall(L, 0, 0, 0);
70
2.61k
  }
71
72
3.41k
  lua_settop(L, 0);
73
3.41k
  lua_close(L);
74
75
3.41k
  return 0;
76
3.41k
}