diff --git a/quickjs.c b/quickjs.c index 40c5d5589..8c00d951f 100644 --- a/quickjs.c +++ b/quickjs.c @@ -49450,7 +49450,7 @@ static JSValue js_set_isDisjointFrom(JSContext *ctx, JSValueConst this_val, if (JS_IsException(next)) goto exception; found = false; - do { + for (;;) { item = JS_IteratorNext(ctx, iter, next, 0, NULL, &done); if (JS_IsException(item)) goto exception; @@ -49459,7 +49459,12 @@ static JSValue js_set_isDisjointFrom(JSContext *ctx, JSValueConst this_val, item = map_normalize_key(ctx, item); found = (NULL != map_find_record(ctx, s, item)); JS_FreeValue(ctx, item); - } while (!found); + if (!found) + continue; + if (JS_IteratorClose(ctx, iter, /*is_exception_pending*/false) < 0) + goto exception; + break; + } } else { iter = js_create_map_iterator(ctx, this_val, 0, NULL, MAGIC_SET); if (JS_IsException(iter)) @@ -49576,7 +49581,7 @@ static JSValue js_set_isSupersetOf(JSContext *ctx, JSValueConst this_val, if (JS_IsException(next)) goto exception; found = true; - do { + for (;;) { item = JS_IteratorNext(ctx, iter, next, 0, NULL, &done); if (JS_IsException(item)) goto exception; @@ -49585,7 +49590,12 @@ static JSValue js_set_isSupersetOf(JSContext *ctx, JSValueConst this_val, item = map_normalize_key(ctx, item); found = (NULL != map_find_record(ctx, s, item)); JS_FreeValue(ctx, item); - } while (found); + if (found) + continue; + if (JS_IteratorClose(ctx, iter, /*is_exception_pending*/false) < 0) + goto exception; + break; + } fini: rval = found ? JS_TRUE : JS_FALSE; exception: diff --git a/tests/test_builtin.js b/tests/test_builtin.js index d228ec22b..039328c68 100644 --- a/tests/test_builtin.js +++ b/tests/test_builtin.js @@ -908,6 +908,48 @@ function test_weak_map() /* the WeakMap should be empty here */ } +function test_set() +{ + const iter = { + a: [4, 5, 6], + nextCalls: 0, + returnCalls: 0, + next() { + const done = this.nextCalls >= this.a.length + const value = this.a[this.nextCalls] + this.nextCalls++ + return {done, value} + }, + return() { + this.returnCalls++ + return this + }, + } + const setlike = { + size: iter.a.length, + has(v) { return iter.a.includes(v) }, + keys() { return iter }, + } + // set must be bigger than iter.a to hit iter.next and iter.return + assert(new Set([4,5,6,7]).isSupersetOf(setlike), true) + assert(iter.nextCalls, 4); + assert(iter.returnCalls, 0); + iter.nextCalls = iter.returnCalls = 0 + assert(new Set([0,1,2,3]).isSupersetOf(setlike), false) + assert(iter.nextCalls, 1); + assert(iter.returnCalls, 1); + iter.nextCalls = iter.returnCalls = 0 + // set must be bigger than iter.a to hit iter.next and iter.return + assert(new Set([4,5,6,7]).isDisjointFrom(setlike), false) + assert(iter.nextCalls, 1); + assert(iter.returnCalls, 1); + iter.nextCalls = iter.returnCalls = 0 + assert(new Set([0,1,2,3]).isDisjointFrom(setlike), true) + assert(iter.nextCalls, 4); + assert(iter.returnCalls, 0); + iter.nextCalls = iter.returnCalls = 0 +} + function test_weak_set() { var a, e; @@ -1103,6 +1145,7 @@ test_regexp(); test_symbol(); test_map(); test_weak_map(); +test_set(); test_weak_set(); test_generator(); test_proxy_iter();