Skip to content

Commit edb50ad

Browse files
committed
Bug 706057: Fix use-after-free in getOwnPropertyDescriptor.
getOwnPropertyDescriptor should create the descriptor object by using [[DefineOwnProperty]], and not by looking through the prototype chain where it may invoke getters and setters on the Object.prototype. If there exists an Object.prototype.get property with a setter, that method is invoked when it shouldn't. A malicious getter here can delete the property currently being processed in getOwnPropertyDescriptor, and we'll end up with a use-after-free bug. Avoid this problem by following the spec and use js_defproperty rather than js_setproperty to define own properties in getOwnPropertyDescriptor and related functions.
1 parent bf4ac94 commit edb50ad

File tree

1 file changed

+7
-7
lines changed

1 file changed

+7
-7
lines changed

Diff for: jsobject.c

+7-7
Original file line numberDiff line numberDiff line change
@@ -134,25 +134,25 @@ static void O_getOwnPropertyDescriptor(js_State *J)
134134
js_newobject(J);
135135
if (!ref->getter && !ref->setter) {
136136
js_pushvalue(J, ref->value);
137-
js_setproperty(J, -2, "value");
137+
js_defproperty(J, -2, "value", 0);
138138
js_pushboolean(J, !(ref->atts & JS_READONLY));
139-
js_setproperty(J, -2, "writable");
139+
js_defproperty(J, -2, "writable", 0);
140140
} else {
141141
if (ref->getter)
142142
js_pushobject(J, ref->getter);
143143
else
144144
js_pushundefined(J);
145-
js_setproperty(J, -2, "get");
145+
js_defproperty(J, -2, "get", 0);
146146
if (ref->setter)
147147
js_pushobject(J, ref->setter);
148148
else
149149
js_pushundefined(J);
150-
js_setproperty(J, -2, "set");
150+
js_defproperty(J, -2, "set", 0);
151151
}
152152
js_pushboolean(J, !(ref->atts & JS_DONTENUM));
153-
js_setproperty(J, -2, "enumerable");
153+
js_defproperty(J, -2, "enumerable", 0);
154154
js_pushboolean(J, !(ref->atts & JS_DONTCONF));
155-
js_setproperty(J, -2, "configurable");
155+
js_defproperty(J, -2, "configurable", 0);
156156
}
157157
}
158158

@@ -248,7 +248,7 @@ static void ToPropertyDescriptor(js_State *J, js_Object *obj, const char *name,
248248
}
249249
if (js_hasproperty(J, -1, "value")) {
250250
hasvalue = 1;
251-
js_setproperty(J, -3, name);
251+
js_defproperty(J, -3, name, 0);
252252
}
253253

254254
if (!writable) atts |= JS_READONLY;

0 commit comments

Comments
 (0)