Skip to content

Instantly share code, notes, and snippets.

@lexborisov
Created April 8, 2019 13:10
Show Gist options
  • Save lexborisov/b48b2e20d022e7b5b77fba486fee6a43 to your computer and use it in GitHub Desktop.
Save lexborisov/b48b2e20d022e7b5b77fba486fee6a43 to your computer and use it in GitHub Desktop.
# HG changeset patch
# User Alexander Borisov <alexander.borisov@nginx.com>
# Date 1554724440 -10800
# Mon Apr 08 14:54:00 2019 +0300
# Node ID 09bdcce827b438029c612c87d2e663fee6ad5797
# Parent 7dba758fda64edab90d80a7b44f4a29fc3ce5f91
Added walk of prototypes chain during iteration over an object.
This closes #33 issue on Github.
diff -r 7dba758fda64 -r 09bdcce827b4 njs/njs_vm.c
--- a/njs/njs_vm.c Fri Apr 05 17:49:22 2019 +0300
+++ b/njs/njs_vm.c Mon Apr 08 14:54:00 2019 +0300
@@ -10,8 +10,9 @@
struct njs_property_next_s {
- int32_t index;
- nxt_lvlhsh_each_t lhe;
+ int32_t index;
+ nxt_lvlhsh_each_t lhe;
+ njs_object_t *object;
};
@@ -757,7 +758,9 @@
vm->retval.data.u.next = next;
nxt_lvlhsh_each_init(&next->lhe, &njs_object_hash_proto);
+
next->index = -1;
+ next->object = object->data.u.object;
if (njs_is_array(object) && object->data.u.array->length != 0) {
next->index = 0;
@@ -818,7 +821,7 @@
}
for ( ;; ) {
- prop = nxt_lvlhsh_each(&object->data.u.object->hash, &next->lhe);
+ prop = nxt_lvlhsh_each(&next->object->hash, &next->lhe);
if (prop == NULL) {
break;
@@ -831,6 +834,14 @@
}
}
+ if (next->object->__proto__ != NULL) {
+ next->object = next->object->__proto__;
+
+ nxt_lvlhsh_each_init(&next->lhe, &njs_object_hash_proto);
+
+ return 0;
+ }
+
nxt_mp_free(vm->mem_pool, next);
} else if (njs_is_external(object)) {
diff -r 7dba758fda64 -r 09bdcce827b4 njs/test/njs_unit_test.c
--- a/njs/test/njs_unit_test.c Fri Apr 05 17:49:22 2019 +0300
+++ b/njs/test/njs_unit_test.c Mon Apr 08 14:54:00 2019 +0300
@@ -7567,6 +7567,27 @@
{ nxt_string("Object.prototype.__proto__.f()"),
nxt_string("TypeError: cannot get property \"f\" of undefined") },
+ { nxt_string("var o1 = Object.create(null); o1.one = 1;"
+ "var o2 = Object.create(o1); o2.two = 2;"
+ "var o3 = Object.create(o2); o3.three = 3;"
+ "var res = [];"
+ "for (var val in o3) res.push(val); res"),
+ nxt_string("three,two,one") },
+
+ { nxt_string("var o1 = Object.create(null); o1.one = 1;"
+ "var o2 = Object.create(o1);"
+ "var o3 = Object.create(o2); o3.three = 3;"
+ "var res = [];"
+ "for (var val in o3) res.push(val); res"),
+ nxt_string("three,one") },
+
+ { nxt_string("var o1 = Object.create(null); o1.one = 1;"
+ "var o2 = Object.create(o1);"
+ "var o3 = Object.create(o2);"
+ "var res = [];"
+ "for (var val in o3) res.push(val); res"),
+ nxt_string("one") },
+
{ nxt_string("Object.prototype.toString.call(Object.prototype)"),
nxt_string("[object Object]") },
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment