diff options
| author | 2025-06-17 10:34:01 +0200 | |
|---|---|---|
| committer | 2025-06-17 10:34:01 +0200 | |
| commit | 3a8dcfa8b8ee6311cc6426e12580cfd179d3eb1d (patch) | |
| tree | 023a849c3a5ea9b492e7c8d235ad12742277c6fe | |
| parent | bd4fc32bace9ee9727243ddf59f0066d5aa5e0a4 (diff) | |
forbid too long arrays & strings
| -rw-r--r-- | pez.c | 19 | ||||
| -rw-r--r-- | pez.h | 1 |
2 files changed, 18 insertions, 2 deletions
@@ -500,6 +500,8 @@ splittable64(uint64_t x) /* Objects */ /***********/ +#define FX_MAX_INT 0x7FFFF + static Proto * newproto(PezContext *cx, const char *file, const char *name, int line) { @@ -738,6 +740,10 @@ box_str(PezContext *cx, Val *pv, const char *s, int len) pv->r = r; return 1; } + if (len > FX_MAX_INT) { + cx->err = PEZ_ETooBig; + return 0; + } TRY(slot = strpool_lookup(cx, s, len)); if (!*slot) { Str *o = newobj(cx, PEZ_TString, sizeof(Str) + len + 1); @@ -762,10 +768,14 @@ sizeofstr(Str *str) static Array * newarr(PezContext *cx, uint cap) { - Array *arr = newobj(cx, PEZ_TArray, sizeof *arr); - if (!arr) { + Array *arr; + if (cap > FX_MAX_INT) { + cx->err = PEZ_ETooBig; return NULL; } + arr = newobj(cx, PEZ_TArray, sizeof *arr); + if (!arr) + return NULL; if (cap) { if (!push(cx, box_obj(arr))) { // gc keep cxfree(cx, arr, sizeof *arr); @@ -785,6 +795,10 @@ arrpushn(PezContext *cx, Array *arr, Val *src, uint n) if (cx->gccanrun && (cx->dbg & DBGstressgc)) { gc(cx); } + if (arr->len + n > FX_MAX_INT) { + cx->err = PEZ_ETooBig; + return 0; + } if (arr->len + n - 1 >= arr->cap) { uint newcap = (arr->len + n - 1) * 2; Val *new; @@ -4455,6 +4469,7 @@ pez_geterr(PezContext *cx) case PEZ_ENoMem: return "out of memory"; case PEZ_ESyntax: return cx->errstr; case PEZ_ERuntime: return cx->errstr; + case PEZ_ETooBig: return "object too big"; } return NULL; } @@ -28,6 +28,7 @@ typedef enum PezError { PEZ_ENoMem, PEZ_ESyntax, PEZ_ERuntime, + PEZ_ETooBig, } PezError; typedef struct PezContext PezContext; |