shithub: libmujs

Download patch

ref: 789f30b58766186e4200feb001fab67635c7da86
parent: a09d8697dba2aeb41a1628635a87e9d32b8b7bc4
author: Tor Andersson <tor.andersson@artifex.com>
date: Mon Jan 25 09:38:15 EST 2021

Bug 703376: Don't allow creating new properties on transient objects.

--- a/jsrun.c
+++ b/jsrun.c
@@ -551,7 +551,7 @@
 		js_pushundefined(J);
 }
 
-static void jsR_setproperty(js_State *J, js_Object *obj, const char *name)
+static void jsR_setproperty(js_State *J, js_Object *obj, const char *name, int transient)
 {
 	js_Value *value = stackidx(J, -1);
 	js_Property *ref;
@@ -616,8 +616,14 @@
 	}
 
 	/* Property not found on this object, so create one */
-	if (!ref || !own)
+	if (!ref || !own) {
+		if (transient) {
+			if (J->strict)
+				js_typeerror(J, "cannot create property '%s' on transient object", name);
+			return;
+		}
 		ref = jsV_setproperty(J, obj, name);
+	}
 
 	if (ref) {
 		if (!(ref->atts & JS_READONLY))
@@ -778,7 +784,7 @@
 
 void js_setregistry(js_State *J, const char *name)
 {
-	jsR_setproperty(J, J->R, name);
+	jsR_setproperty(J, J->R, name, 0);
 	js_pop(J, 1);
 }
 
@@ -794,7 +800,7 @@
 
 void js_setglobal(js_State *J, const char *name)
 {
-	jsR_setproperty(J, J->G, name);
+	jsR_setproperty(J, J->G, name, 0);
 	js_pop(J, 1);
 }
 
@@ -816,7 +822,7 @@
 
 void js_setproperty(js_State *J, int idx, const char *name)
 {
-	jsR_setproperty(J, js_toobject(J, idx), name);
+	jsR_setproperty(J, js_toobject(J, idx), name, !js_isobject(J, idx));
 	js_pop(J, 1);
 }
 
@@ -918,7 +924,7 @@
 	} while (E);
 	if (J->strict)
 		js_referenceerror(J, "assignment to undeclared variable '%s'", name);
-	jsR_setproperty(J, J->G, name);
+	jsR_setproperty(J, J->G, name, 0);
 }
 
 static int js_delvar(js_State *J, const char *name)
@@ -1351,6 +1357,7 @@
 	unsigned int ux, uy;
 	int ix, iy, okay;
 	int b;
+	int transient;
 
 	savestrict = J->strict;
 	J->strict = F->strict;
@@ -1461,7 +1468,7 @@
 		case OP_INITPROP:
 			obj = js_toobject(J, -3);
 			str = js_tostring(J, -2);
-			jsR_setproperty(J, obj, str);
+			jsR_setproperty(J, obj, str, 0);
 			js_pop(J, 2);
 			break;
 
@@ -1496,7 +1503,8 @@
 		case OP_SETPROP:
 			str = js_tostring(J, -2);
 			obj = js_toobject(J, -3);
-			jsR_setproperty(J, obj, str);
+			transient = !js_isobject(J, -3);
+			jsR_setproperty(J, obj, str, transient);
 			js_rot3pop2(J);
 			break;
 
@@ -1503,7 +1511,8 @@
 		case OP_SETPROP_S:
 			str = ST[*pc++];
 			obj = js_toobject(J, -2);
-			jsR_setproperty(J, obj, str);
+			transient = !js_isobject(J, -2);
+			jsR_setproperty(J, obj, str, transient);
 			js_rot2pop1(J);
 			break;