aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lgc.c6
-rw-r--r--ltm.c2
-rw-r--r--lvm.c9
-rw-r--r--testes/strings.lua17
4 files changed, 28 insertions, 6 deletions
diff --git a/lgc.c b/lgc.c
index a775b6e5..60f042c7 100644
--- a/lgc.c
+++ b/lgc.c
@@ -594,10 +594,10 @@ static void traversestrongtable (global_State *g, Table *h) {
594*/ 594*/
595static int getmode (global_State *g, Table *h) { 595static int getmode (global_State *g, Table *h) {
596 const TValue *mode = gfasttm(g, h->metatable, TM_MODE); 596 const TValue *mode = gfasttm(g, h->metatable, TM_MODE);
597 if (mode == NULL || !ttisshrstring(mode)) 597 if (mode == NULL || !ttisstring(mode))
598 return 0; /* ignore non-(short)string modes */ 598 return 0; /* ignore non-string modes */
599 else { 599 else {
600 const char *smode = getshrstr(tsvalue(mode)); 600 const char *smode = getstr(tsvalue(mode));
601 const char *weakkey = strchr(smode, 'k'); 601 const char *weakkey = strchr(smode, 'k');
602 const char *weakvalue = strchr(smode, 'v'); 602 const char *weakvalue = strchr(smode, 'v');
603 return ((weakkey != NULL) << 1) | (weakvalue != NULL); 603 return ((weakkey != NULL) << 1) | (weakvalue != NULL);
diff --git a/ltm.c b/ltm.c
index 92a03e71..8d64235e 100644
--- a/ltm.c
+++ b/ltm.c
@@ -287,7 +287,7 @@ void luaT_getvararg (CallInfo *ci, StkId ra, TValue *rc) {
287 return; 287 return;
288 } 288 }
289 } 289 }
290 else if (ttisshrstring(rc)) { /* short-string value? */ 290 else if (ttisstring(rc)) { /* string value? */
291 size_t len; 291 size_t len;
292 const char *s = getlstr(tsvalue(rc), len); 292 const char *s = getlstr(tsvalue(rc), len);
293 if (len == 1 && s[0] == 'n') { /* key is "n"? */ 293 if (len == 1 && s[0] == 'n') { /* key is "n"? */
diff --git a/lvm.c b/lvm.c
index 2a9fb67a..2c868c21 100644
--- a/lvm.c
+++ b/lvm.c
@@ -657,6 +657,11 @@ int luaV_equalobj (lua_State *L, const TValue *t1, const TValue *t2) {
657#define tostring(L,o) \ 657#define tostring(L,o) \
658 (ttisstring(o) || (cvt2str(o) && (luaO_tostring(L, o), 1))) 658 (ttisstring(o) || (cvt2str(o) && (luaO_tostring(L, o), 1)))
659 659
660/*
661** Check whether object is a short empty string to optimize concatenation.
662** (External strings can be empty too; they will be concatenated like
663** non-empty ones.)
664*/
660#define isemptystr(o) (ttisshrstring(o) && tsvalue(o)->shrlen == 0) 665#define isemptystr(o) (ttisshrstring(o) && tsvalue(o)->shrlen == 0)
661 666
662/* copy strings in stack from top - n up to top - 1 to buffer */ 667/* copy strings in stack from top - n up to top - 1 to buffer */
@@ -691,8 +696,8 @@ void luaV_concat (lua_State *L, int total) {
691 setobjs2s(L, top - 2, top - 1); /* result is second op. */ 696 setobjs2s(L, top - 2, top - 1); /* result is second op. */
692 } 697 }
693 else { 698 else {
694 /* at least two non-empty string values; get as many as possible */ 699 /* at least two string values; get as many as possible */
695 size_t tl = tsslen(tsvalue(s2v(top - 1))); 700 size_t tl = tsslen(tsvalue(s2v(top - 1))); /* total length */
696 TString *ts; 701 TString *ts;
697 /* collect total length and number of strings */ 702 /* collect total length and number of strings */
698 for (n = 1; n < total && tostring(L, s2v(top - n - 1)); n++) { 703 for (n = 1; n < total && tostring(L, s2v(top - n - 1)); n++) {
diff --git a/testes/strings.lua b/testes/strings.lua
index 46912d43..84ff1154 100644
--- a/testes/strings.lua
+++ b/testes/strings.lua
@@ -540,6 +540,23 @@ else
540 assert(y == x) 540 assert(y == x)
541 local z = T.externstr(x) -- external allocated long string 541 local z = T.externstr(x) -- external allocated long string
542 assert(z == y) 542 assert(z == y)
543
544 local e = T.externstr("") -- empty external string
545 assert(e .. "x" == "x" and "x" .. e == "x")
546 assert(e .. e == "" and #e == 0)
547
548 -- external string as the "n" key in vararg table
549 local n = T.externstr("n")
550 local n0 = T.externstr("n\0")
551 local function aux (...t) assert(t[n0] == nil); return t[n] end
552 assert(aux(10, 20, 30) == 3)
553
554 -- external string as mode in weak table
555 local t = setmetatable({}, {__mode = T.externstr("kv")})
556 t[{}] = {}
557 assert(next(t))
558 collectgarbage()
559 assert(next(t) == nil)
543end 560end
544 561
545print('OK') 562print('OK')