diff options
-rw-r--r-- | lapi.c | 17 | ||||
-rw-r--r-- | llex.c | 52 | ||||
-rw-r--r-- | lobject.c | 20 | ||||
-rw-r--r-- | lobject.h | 5 |
4 files changed, 50 insertions, 44 deletions
@@ -1,5 +1,5 @@ | |||
1 | /* | 1 | /* |
2 | ** $Id: lapi.c,v 2.205 2014/04/15 16:32:49 roberto Exp roberto $ | 2 | ** $Id: lapi.c,v 2.206 2014/04/29 18:14:16 roberto Exp roberto $ |
3 | ** Lua API | 3 | ** Lua API |
4 | ** See Copyright Notice in lua.h | 4 | ** See Copyright Notice in lua.h |
5 | */ | 5 | */ |
@@ -334,17 +334,12 @@ LUA_API int lua_compare (lua_State *L, int index1, int index2, int op) { | |||
334 | 334 | ||
335 | 335 | ||
336 | LUA_API int lua_strtonum (lua_State *L, const char *s, size_t len) { | 336 | LUA_API int lua_strtonum (lua_State *L, const char *s, size_t len) { |
337 | lua_Integer i; lua_Number n; | 337 | if (!luaO_str2num(s, len, L->top)) |
338 | if (luaO_str2int(s, len, &i)) { /* try as an integer */ | ||
339 | setivalue(L->top, i); | ||
340 | } | ||
341 | else if (luaO_str2d(s, len, &n)) { /* else try as a float */ | ||
342 | setfltvalue(L->top, n); | ||
343 | } | ||
344 | else | ||
345 | return 0; /* conversion failed */ | 338 | return 0; /* conversion failed */ |
346 | api_incr_top(L); | 339 | else { |
347 | return 1; | 340 | api_incr_top(L); |
341 | return 1; | ||
342 | } | ||
348 | } | 343 | } |
349 | 344 | ||
350 | 345 | ||
@@ -1,5 +1,5 @@ | |||
1 | /* | 1 | /* |
2 | ** $Id: llex.c,v 2.73 2014/02/06 15:59:24 roberto Exp roberto $ | 2 | ** $Id: llex.c,v 2.74 2014/02/14 15:23:51 roberto Exp roberto $ |
3 | ** Lexical Analyzer | 3 | ** Lexical Analyzer |
4 | ** See Copyright Notice in lua.h | 4 | ** See Copyright Notice in lua.h |
5 | */ | 5 | */ |
@@ -196,10 +196,12 @@ static int check_next (LexState *ls, const char *set) { | |||
196 | ** change all characters 'from' in buffer to 'to' | 196 | ** change all characters 'from' in buffer to 'to' |
197 | */ | 197 | */ |
198 | static void buffreplace (LexState *ls, char from, char to) { | 198 | static void buffreplace (LexState *ls, char from, char to) { |
199 | size_t n = luaZ_bufflen(ls->buff); | 199 | if (from != to) { |
200 | char *p = luaZ_buffer(ls->buff); | 200 | size_t n = luaZ_bufflen(ls->buff); |
201 | while (n--) | 201 | char *p = luaZ_buffer(ls->buff); |
202 | if (p[n] == from) p[n] = to; | 202 | while (n--) |
203 | if (p[n] == from) p[n] = to; | ||
204 | } | ||
203 | } | 205 | } |
204 | 206 | ||
205 | 207 | ||
@@ -208,17 +210,17 @@ static void buffreplace (LexState *ls, char from, char to) { | |||
208 | #endif | 210 | #endif |
209 | 211 | ||
210 | 212 | ||
211 | #define buff2d(b,e) luaO_str2d(luaZ_buffer(b), luaZ_bufflen(b) - 1, e) | 213 | #define buff2num(b,o) luaO_str2num(luaZ_buffer(b), luaZ_bufflen(b) - 1, o) |
212 | 214 | ||
213 | /* | 215 | /* |
214 | ** in case of format error, try to change decimal point separator to | 216 | ** in case of format error, try to change decimal point separator to |
215 | ** the one defined in the current locale and check again | 217 | ** the one defined in the current locale and check again |
216 | */ | 218 | */ |
217 | static void trydecpoint (LexState *ls, SemInfo *seminfo) { | 219 | static void trydecpoint (LexState *ls, TValue *o) { |
218 | char old = ls->decpoint; | 220 | char old = ls->decpoint; |
219 | ls->decpoint = getlocaledecpoint(); | 221 | ls->decpoint = getlocaledecpoint(); |
220 | buffreplace(ls, old, ls->decpoint); /* try new decimal separator */ | 222 | buffreplace(ls, old, ls->decpoint); /* try new decimal separator */ |
221 | if (!buff2d(ls->buff, &seminfo->r)) { | 223 | if (!buff2num(ls->buff, o)) { |
222 | /* format error with correct decimal point: no more options */ | 224 | /* format error with correct decimal point: no more options */ |
223 | buffreplace(ls, ls->decpoint, '.'); /* undo change (for error message) */ | 225 | buffreplace(ls, ls->decpoint, '.'); /* undo change (for error message) */ |
224 | lexerror(ls, "malformed number", TK_FLT); | 226 | lexerror(ls, "malformed number", TK_FLT); |
@@ -228,11 +230,11 @@ static void trydecpoint (LexState *ls, SemInfo *seminfo) { | |||
228 | 230 | ||
229 | /* LUA_NUMBER */ | 231 | /* LUA_NUMBER */ |
230 | /* | 232 | /* |
231 | ** this function is quite liberal in what it accepts, as 'luaO_str2d' | 233 | ** this function is quite liberal in what it accepts, as 'luaO_str2num' |
232 | ** will reject ill-formed numerals. 'isf' means the numeral is not | 234 | ** will reject ill-formed numerals. |
233 | ** an integer (it has a dot or an exponent). | ||
234 | */ | 235 | */ |
235 | static int read_numeral (LexState *ls, SemInfo *seminfo, int isf) { | 236 | static int read_numeral (LexState *ls, SemInfo *seminfo) { |
237 | TValue obj; | ||
236 | const char *expo = "Ee"; | 238 | const char *expo = "Ee"; |
237 | int first = ls->current; | 239 | int first = ls->current; |
238 | lua_assert(lisdigit(ls->current)); | 240 | lua_assert(lisdigit(ls->current)); |
@@ -240,29 +242,25 @@ static int read_numeral (LexState *ls, SemInfo *seminfo, int isf) { | |||
240 | if (first == '0' && check_next(ls, "Xx")) /* hexadecimal? */ | 242 | if (first == '0' && check_next(ls, "Xx")) /* hexadecimal? */ |
241 | expo = "Pp"; | 243 | expo = "Pp"; |
242 | for (;;) { | 244 | for (;;) { |
243 | if (check_next(ls, expo)) { /* exponent part? */ | 245 | if (check_next(ls, expo)) /* exponent part? */ |
244 | check_next(ls, "+-"); /* optional exponent sign */ | 246 | check_next(ls, "+-"); /* optional exponent sign */ |
245 | isf = 1; | ||
246 | } | ||
247 | if (lisxdigit(ls->current)) | 247 | if (lisxdigit(ls->current)) |
248 | save_and_next(ls); | 248 | save_and_next(ls); |
249 | else if (ls->current == '.') { | 249 | else if (ls->current == '.') |
250 | save_and_next(ls); | 250 | save_and_next(ls); |
251 | isf = 1; | ||
252 | } | ||
253 | else break; | 251 | else break; |
254 | } | 252 | } |
255 | save(ls, '\0'); | 253 | save(ls, '\0'); |
256 | if (!isf) { | 254 | buffreplace(ls, '.', ls->decpoint); /* follow locale for decimal point */ |
257 | if (!luaO_str2int(luaZ_buffer(ls->buff), luaZ_bufflen(ls->buff) - 1, | 255 | if (!buff2num(ls->buff, &obj)) /* format error? */ |
258 | &seminfo->i)) | 256 | trydecpoint(ls, &obj); /* try to update decimal point separator */ |
259 | lexerror(ls, "malformed number", TK_INT); | 257 | if (ttisinteger(&obj)) { |
258 | seminfo->i = ivalue(&obj); | ||
260 | return TK_INT; | 259 | return TK_INT; |
261 | } | 260 | } |
262 | else { | 261 | else { |
263 | buffreplace(ls, '.', ls->decpoint); /* follow locale for decimal point */ | 262 | lua_assert(ttisfloat(&obj)); |
264 | if (!buff2d(ls->buff, &seminfo->r)) /* format error? */ | 263 | seminfo->r = fltvalue(&obj); |
265 | trydecpoint(ls, seminfo); /* try to update decimal point separator */ | ||
266 | return TK_FLT; | 264 | return TK_FLT; |
267 | } | 265 | } |
268 | } | 266 | } |
@@ -530,11 +528,11 @@ static int llex (LexState *ls, SemInfo *seminfo) { | |||
530 | else return TK_CONCAT; /* '..' */ | 528 | else return TK_CONCAT; /* '..' */ |
531 | } | 529 | } |
532 | else if (!lisdigit(ls->current)) return '.'; | 530 | else if (!lisdigit(ls->current)) return '.'; |
533 | else return read_numeral(ls, seminfo, 1); | 531 | else return read_numeral(ls, seminfo); |
534 | } | 532 | } |
535 | case '0': case '1': case '2': case '3': case '4': | 533 | case '0': case '1': case '2': case '3': case '4': |
536 | case '5': case '6': case '7': case '8': case '9': { | 534 | case '5': case '6': case '7': case '8': case '9': { |
537 | return read_numeral(ls, seminfo, 0); | 535 | return read_numeral(ls, seminfo); |
538 | } | 536 | } |
539 | case EOZ: { | 537 | case EOZ: { |
540 | return TK_EOS; | 538 | return TK_EOS; |
@@ -1,5 +1,5 @@ | |||
1 | /* | 1 | /* |
2 | ** $Id: lobject.c,v 2.81 2014/04/27 14:41:11 roberto Exp roberto $ | 2 | ** $Id: lobject.c,v 2.82 2014/04/29 18:14:16 roberto Exp roberto $ |
3 | ** Some generic functions over Lua objects | 3 | ** Some generic functions over Lua objects |
4 | ** See Copyright Notice in lua.h | 4 | ** See Copyright Notice in lua.h |
5 | */ | 5 | */ |
@@ -254,7 +254,7 @@ static lua_Number lua_strx2number (const char *s, char **endptr) { | |||
254 | /* }====================================================== */ | 254 | /* }====================================================== */ |
255 | 255 | ||
256 | 256 | ||
257 | int luaO_str2d (const char *s, size_t len, lua_Number *result) { | 257 | static int l_str2d (const char *s, size_t len, lua_Number *result) { |
258 | char *endptr; | 258 | char *endptr; |
259 | if (strpbrk(s, "nN")) /* reject 'inf' and 'nan' */ | 259 | if (strpbrk(s, "nN")) /* reject 'inf' and 'nan' */ |
260 | return 0; | 260 | return 0; |
@@ -268,7 +268,7 @@ int luaO_str2d (const char *s, size_t len, lua_Number *result) { | |||
268 | } | 268 | } |
269 | 269 | ||
270 | 270 | ||
271 | int luaO_str2int (const char *s, size_t len, lua_Integer *result) { | 271 | static int l_str2int (const char *s, size_t len, lua_Integer *result) { |
272 | const char *ends = s + len; | 272 | const char *ends = s + len; |
273 | lua_Unsigned a = 0; | 273 | lua_Unsigned a = 0; |
274 | int empty = 1; | 274 | int empty = 1; |
@@ -298,6 +298,20 @@ int luaO_str2int (const char *s, size_t len, lua_Integer *result) { | |||
298 | } | 298 | } |
299 | 299 | ||
300 | 300 | ||
301 | int luaO_str2num (const char *s, size_t len, TValue *o) { | ||
302 | lua_Integer i; lua_Number n; | ||
303 | if (l_str2int(s, len, &i)) { /* try as an integer */ | ||
304 | setivalue(o, i); | ||
305 | } | ||
306 | else if (l_str2d(s, len, &n)) { /* else try as a float */ | ||
307 | setfltvalue(o, n); | ||
308 | } | ||
309 | else | ||
310 | return 0; /* conversion failed */ | ||
311 | return 1; /* success */ | ||
312 | } | ||
313 | |||
314 | |||
301 | int luaO_utf8esc (char *buff, unsigned int x) { | 315 | int luaO_utf8esc (char *buff, unsigned int x) { |
302 | int n = 1; /* number of bytes put in buffer (backwards) */ | 316 | int n = 1; /* number of bytes put in buffer (backwards) */ |
303 | if (x < 0x80) /* ascii? */ | 317 | if (x < 0x80) /* ascii? */ |
@@ -1,5 +1,5 @@ | |||
1 | /* | 1 | /* |
2 | ** $Id: lobject.h,v 2.86 2014/02/19 13:52:42 roberto Exp roberto $ | 2 | ** $Id: lobject.h,v 2.87 2014/04/29 18:14:16 roberto Exp roberto $ |
3 | ** Type definitions for Lua objects | 3 | ** Type definitions for Lua objects |
4 | ** See Copyright Notice in lua.h | 4 | ** See Copyright Notice in lua.h |
5 | */ | 5 | */ |
@@ -500,8 +500,7 @@ LUAI_FUNC int luaO_utf8esc (char *buff, unsigned int x); | |||
500 | LUAI_FUNC int luaO_ceillog2 (unsigned int x); | 500 | LUAI_FUNC int luaO_ceillog2 (unsigned int x); |
501 | LUAI_FUNC void luaO_arith (lua_State *L, int op, const TValue *p1, | 501 | LUAI_FUNC void luaO_arith (lua_State *L, int op, const TValue *p1, |
502 | const TValue *p2, TValue *res); | 502 | const TValue *p2, TValue *res); |
503 | LUAI_FUNC int luaO_str2d (const char *s, size_t len, lua_Number *result); | 503 | LUAI_FUNC int luaO_str2num (const char *s, size_t len, TValue *o); |
504 | LUAI_FUNC int luaO_str2int (const char *s, size_t len, lua_Integer *result); | ||
505 | LUAI_FUNC int luaO_hexavalue (int c); | 504 | LUAI_FUNC int luaO_hexavalue (int c); |
506 | LUAI_FUNC const char *luaO_pushvfstring (lua_State *L, const char *fmt, | 505 | LUAI_FUNC const char *luaO_pushvfstring (lua_State *L, const char *fmt, |
507 | va_list argp); | 506 | va_list argp); |