diff options
-rw-r--r-- | lpvm.c | 17 |
1 files changed, 13 insertions, 4 deletions
@@ -80,16 +80,25 @@ typedef struct Stack { | |||
80 | ** array, it is simpler to ensure the array always has at least one free | 80 | ** array, it is simpler to ensure the array always has at least one free |
81 | ** slot upfront and check its size later.) | 81 | ** slot upfront and check its size later.) |
82 | */ | 82 | */ |
83 | |||
84 | /* new size in number of elements cannot overflow integers, and new | ||
85 | size in bytes cannot overflow size_t. */ | ||
86 | #define MAXNEWSIZE \ | ||
87 | (((size_t)INT_MAX) <= (~(size_t)0 / sizeof(Capture)) ? \ | ||
88 | ((size_t)INT_MAX) : (~(size_t)0 / sizeof(Capture))) | ||
89 | |||
83 | static Capture *growcap (lua_State *L, Capture *capture, int *capsize, | 90 | static Capture *growcap (lua_State *L, Capture *capture, int *capsize, |
84 | int captop, int n, int ptop) { | 91 | int captop, int n, int ptop) { |
85 | if (*capsize - captop > n) | 92 | if (*capsize - captop > n) |
86 | return capture; /* no need to grow array */ | 93 | return capture; /* no need to grow array */ |
87 | else { /* must grow */ | 94 | else { /* must grow */ |
88 | Capture *newc; | 95 | Capture *newc; |
89 | int newsize = captop + n + 1; /* minimum size needed */ | 96 | unsigned int newsize = captop + n + 1; /* minimum size needed */ |
90 | if (newsize < INT_MAX/((int)sizeof(Capture) * 2)) | 97 | if (newsize < MAXNEWSIZE / 2) |
91 | newsize *= 2; /* twice that size, if not too big */ | 98 | newsize *= 2; /* twice that size, if not too big */ |
92 | else if (newsize >= INT_MAX/((int)sizeof(Capture))) | 99 | else if (newsize < (MAXNEWSIZE / 9) * 8) |
100 | newsize += newsize / 8; /* else, try 9/8 that size */ | ||
101 | else | ||
93 | luaL_error(L, "too many captures"); | 102 | luaL_error(L, "too many captures"); |
94 | newc = (Capture *)lua_newuserdata(L, newsize * sizeof(Capture)); | 103 | newc = (Capture *)lua_newuserdata(L, newsize * sizeof(Capture)); |
95 | memcpy(newc, capture, captop * sizeof(Capture)); | 104 | memcpy(newc, capture, captop * sizeof(Capture)); |
@@ -329,7 +338,7 @@ const char *match (lua_State *L, const char *o, const char *s, const char *e, | |||
329 | case IFailTwice: | 338 | case IFailTwice: |
330 | assert(stack > getstackbase(L, ptop)); | 339 | assert(stack > getstackbase(L, ptop)); |
331 | stack--; | 340 | stack--; |
332 | /* go through */ | 341 | /* FALLTHROUGH */ |
333 | case IFail: | 342 | case IFail: |
334 | fail: { /* pattern failed: try to backtrack */ | 343 | fail: { /* pattern failed: try to backtrack */ |
335 | do { /* remove pending calls */ | 344 | do { /* remove pending calls */ |