Introducing getters/setters for ecma_object_t structure.
This commit is contained in:
+164
-59
@@ -39,22 +39,140 @@ static ecma_object_t *ecma_gc_objects_lists[ ECMA_GC_GEN_COUNT ];
|
||||
static void ecma_gc_mark (ecma_object_t *object_p, ecma_gc_gen_t maximum_gen_to_traverse);
|
||||
static void ecma_gc_sweep (ecma_object_t *object_p);
|
||||
|
||||
/**
|
||||
* Get GC reference counter of the object.
|
||||
*/
|
||||
static uint32_t
|
||||
ecma_gc_get_object_refs (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
return object_p->gc_info.refs;
|
||||
} /* ecma_gc_get_object_refs */
|
||||
|
||||
/**
|
||||
* Set GC reference counter of the object.
|
||||
*/
|
||||
static void
|
||||
ecma_gc_set_object_refs (ecma_object_t *object_p, /**< object */
|
||||
uint32_t refs) /**< new reference counter */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
object_p->gc_info.refs = refs & ((1u << CONFIG_ECMA_REFERENCE_COUNTER_WIDTH) - 1);
|
||||
|
||||
JERRY_ASSERT (object_p->gc_info.refs == refs);
|
||||
} /* ecma_gc_set_object_refs */
|
||||
|
||||
/**
|
||||
* Get GC generation of the object.
|
||||
*/
|
||||
static ecma_gc_gen_t
|
||||
ecma_gc_get_object_generation (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
return object_p->gc_info.generation;
|
||||
} /* ecma_gc_get_object_generation */
|
||||
|
||||
/**
|
||||
* Set GC generation of the object.
|
||||
*/
|
||||
static void
|
||||
ecma_gc_set_object_generation (ecma_object_t *object_p, /**< object */
|
||||
ecma_gc_gen_t generation) /**< generation */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
JERRY_ASSERT (generation < ECMA_GC_GEN_COUNT);
|
||||
|
||||
object_p->gc_info.generation = generation;
|
||||
} /* ecma_gc_set_object_generation */
|
||||
|
||||
/**
|
||||
* Get next object in list of objects with same generation.
|
||||
*/
|
||||
static ecma_object_t*
|
||||
ecma_gc_get_object_next (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
return ECMA_GET_POINTER (object_p->gc_info.next_cp);
|
||||
} /* ecma_gc_get_object_next */
|
||||
|
||||
/**
|
||||
* Set next object in list of objects with same generation.
|
||||
*/
|
||||
static void
|
||||
ecma_gc_set_object_next (ecma_object_t *object_p, /**< object */
|
||||
ecma_object_t *next_object_p) /**< next object */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
ECMA_SET_POINTER (object_p->gc_info.next_cp, next_object_p);
|
||||
} /* ecma_gc_set_object_next */
|
||||
|
||||
/**
|
||||
* Get visited flag of the object.
|
||||
*/
|
||||
static bool
|
||||
ecma_gc_is_object_visited (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
return object_p->gc_info.visited;
|
||||
} /* ecma_gc_is_object_visited */
|
||||
|
||||
/**
|
||||
* Set visited flag of the object.
|
||||
*/
|
||||
static void
|
||||
ecma_gc_set_object_visited (ecma_object_t *object_p, /**< object */
|
||||
bool is_visited) /**< flag value */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
object_p->gc_info.visited = is_visited;
|
||||
} /* ecma_gc_set_object_visited */
|
||||
|
||||
/**
|
||||
* Get may_ref_younger_objects flag of the object.
|
||||
*/
|
||||
static bool
|
||||
ecma_gc_is_object_may_ref_younger_objects (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
return object_p->gc_info.may_ref_younger_objects;
|
||||
} /* ecma_gc_is_object_may_ref_younger_objects */
|
||||
|
||||
/**
|
||||
* Set may_ref_younger_objects flag of the object.
|
||||
*/
|
||||
static void
|
||||
ecma_gc_set_object_may_ref_younger_objects (ecma_object_t *object_p, /**< object */
|
||||
bool is_may_ref_younger_objects) /**< flag value */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
object_p->gc_info.may_ref_younger_objects = is_may_ref_younger_objects;
|
||||
} /* ecma_gc_set_object_may_ref_younger_objects */
|
||||
|
||||
/**
|
||||
* Initialize GC information for the object
|
||||
*/
|
||||
void
|
||||
ecma_init_gc_info (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
object_p->gc_info.refs = 1;
|
||||
ecma_gc_set_object_refs (object_p, 1);
|
||||
|
||||
object_p->gc_info.generation = ECMA_GC_GEN_0;
|
||||
ECMA_SET_POINTER(object_p->gc_info.next, ecma_gc_objects_lists[ ECMA_GC_GEN_0 ]);
|
||||
ecma_gc_set_object_generation (object_p, ECMA_GC_GEN_0);
|
||||
ecma_gc_set_object_next (object_p, ecma_gc_objects_lists[ ECMA_GC_GEN_0 ]);
|
||||
ecma_gc_objects_lists[ ECMA_GC_GEN_0 ] = object_p;
|
||||
|
||||
/* Should be set to false at the beginning of garbage collection */
|
||||
object_p->gc_info.visited = true;
|
||||
ecma_gc_set_object_visited (object_p, true);
|
||||
|
||||
object_p->gc_info.may_ref_younger_objects = false;
|
||||
ecma_gc_set_object_may_ref_younger_objects (object_p, false);
|
||||
} /* ecma_init_gc_info */
|
||||
|
||||
/**
|
||||
@@ -63,18 +181,7 @@ ecma_init_gc_info (ecma_object_t *object_p) /**< object */
|
||||
void
|
||||
ecma_ref_object (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT(object_p != NULL);
|
||||
object_p->gc_info.refs++;
|
||||
|
||||
/**
|
||||
* Check that value was not overflowed
|
||||
*/
|
||||
JERRY_ASSERT(object_p->gc_info.refs > 0);
|
||||
|
||||
if (unlikely (object_p->gc_info.refs == 0))
|
||||
{
|
||||
JERRY_UNREACHABLE();
|
||||
}
|
||||
ecma_gc_set_object_refs (object_p, ecma_gc_get_object_refs (object_p) + 1);
|
||||
} /* ecma_ref_object */
|
||||
|
||||
/**
|
||||
@@ -83,10 +190,8 @@ ecma_ref_object (ecma_object_t *object_p) /**< object */
|
||||
void
|
||||
ecma_deref_object (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT(object_p != NULL);
|
||||
JERRY_ASSERT(object_p->gc_info.refs > 0);
|
||||
|
||||
object_p->gc_info.refs--;
|
||||
JERRY_ASSERT(ecma_gc_get_object_refs (object_p) > 0);
|
||||
ecma_gc_set_object_refs (object_p, ecma_gc_get_object_refs (object_p) - 1);
|
||||
} /* ecma_deref_object */
|
||||
|
||||
/**
|
||||
@@ -119,9 +224,9 @@ ecma_gc_update_may_ref_younger_object_flag_by_object (ecma_object_t *obj_p, /**<
|
||||
return;
|
||||
}
|
||||
|
||||
if (ref_obj_p->gc_info.generation < obj_p->gc_info.generation)
|
||||
if (ecma_gc_get_object_generation (ref_obj_p) < ecma_gc_get_object_generation (obj_p))
|
||||
{
|
||||
obj_p->gc_info.may_ref_younger_objects = true;
|
||||
ecma_gc_set_object_may_ref_younger_objects (obj_p, true);
|
||||
}
|
||||
} /* ecma_gc_update_may_ref_younger_object_flag_by_object */
|
||||
|
||||
@@ -146,17 +251,17 @@ ecma_gc_mark (ecma_object_t *object_p, /**< start object */
|
||||
{
|
||||
JERRY_ASSERT(object_p != NULL);
|
||||
|
||||
object_p->gc_info.visited = true;
|
||||
ecma_gc_set_object_visited (object_p, true);
|
||||
|
||||
bool does_reference_object_to_traverse = false;
|
||||
|
||||
if (object_p->is_lexical_environment)
|
||||
if (ecma_is_lexical_environment (object_p))
|
||||
{
|
||||
ecma_object_t *lex_env_p = ECMA_GET_POINTER(object_p->u.lexical_environment.outer_reference_p);
|
||||
ecma_object_t *lex_env_p = ecma_get_lex_env_outer_reference (object_p);
|
||||
if (lex_env_p != NULL
|
||||
&& lex_env_p->gc_info.generation <= maximum_gen_to_traverse)
|
||||
&& ecma_gc_get_object_generation (lex_env_p) <= maximum_gen_to_traverse)
|
||||
{
|
||||
if (!lex_env_p->gc_info.visited)
|
||||
if (!ecma_gc_is_object_visited (lex_env_p))
|
||||
{
|
||||
ecma_gc_mark (lex_env_p, ECMA_GC_GEN_COUNT);
|
||||
}
|
||||
@@ -166,11 +271,11 @@ ecma_gc_mark (ecma_object_t *object_p, /**< start object */
|
||||
}
|
||||
else
|
||||
{
|
||||
ecma_object_t *proto_p = ECMA_GET_POINTER(object_p->u.object.prototype_object_p);
|
||||
ecma_object_t *proto_p = ecma_get_object_prototype (object_p);
|
||||
if (proto_p != NULL
|
||||
&& proto_p->gc_info.generation <= maximum_gen_to_traverse)
|
||||
&& ecma_gc_get_object_generation (proto_p) <= maximum_gen_to_traverse)
|
||||
{
|
||||
if (!proto_p->gc_info.visited)
|
||||
if (!ecma_gc_is_object_visited (proto_p))
|
||||
{
|
||||
ecma_gc_mark (proto_p, ECMA_GC_GEN_COUNT);
|
||||
}
|
||||
@@ -179,7 +284,7 @@ ecma_gc_mark (ecma_object_t *object_p, /**< start object */
|
||||
}
|
||||
}
|
||||
|
||||
for (ecma_property_t *property_p = ECMA_GET_POINTER(object_p->properties_p), *next_property_p;
|
||||
for (ecma_property_t *property_p = ecma_get_property_list (object_p), *next_property_p;
|
||||
property_p != NULL;
|
||||
property_p = next_property_p)
|
||||
{
|
||||
@@ -195,9 +300,9 @@ ecma_gc_mark (ecma_object_t *object_p, /**< start object */
|
||||
{
|
||||
ecma_object_t *value_obj_p = ECMA_GET_POINTER(value.value);
|
||||
|
||||
if (value_obj_p->gc_info.generation <= maximum_gen_to_traverse)
|
||||
if (ecma_gc_get_object_generation (value_obj_p) <= maximum_gen_to_traverse)
|
||||
{
|
||||
if (!value_obj_p->gc_info.visited)
|
||||
if (!ecma_gc_is_object_visited (value_obj_p))
|
||||
{
|
||||
ecma_gc_mark (value_obj_p, ECMA_GC_GEN_COUNT);
|
||||
}
|
||||
@@ -216,9 +321,9 @@ ecma_gc_mark (ecma_object_t *object_p, /**< start object */
|
||||
|
||||
if (getter_obj_p != NULL)
|
||||
{
|
||||
if (getter_obj_p->gc_info.generation <= maximum_gen_to_traverse)
|
||||
if (ecma_gc_get_object_generation (getter_obj_p) <= maximum_gen_to_traverse)
|
||||
{
|
||||
if (!getter_obj_p->gc_info.visited)
|
||||
if (!ecma_gc_is_object_visited (getter_obj_p))
|
||||
{
|
||||
ecma_gc_mark (getter_obj_p, ECMA_GC_GEN_COUNT);
|
||||
}
|
||||
@@ -229,9 +334,9 @@ ecma_gc_mark (ecma_object_t *object_p, /**< start object */
|
||||
|
||||
if (setter_obj_p != NULL)
|
||||
{
|
||||
if (setter_obj_p->gc_info.generation <= maximum_gen_to_traverse)
|
||||
if (ecma_gc_get_object_generation (setter_obj_p) <= maximum_gen_to_traverse)
|
||||
{
|
||||
if (!setter_obj_p->gc_info.visited)
|
||||
if (!ecma_gc_is_object_visited (setter_obj_p))
|
||||
{
|
||||
ecma_gc_mark (setter_obj_p, ECMA_GC_GEN_COUNT);
|
||||
}
|
||||
@@ -278,9 +383,9 @@ ecma_gc_mark (ecma_object_t *object_p, /**< start object */
|
||||
{
|
||||
ecma_object_t *obj_p = ECMA_GET_POINTER(property_value);
|
||||
|
||||
if (obj_p->gc_info.generation <= maximum_gen_to_traverse)
|
||||
if (ecma_gc_get_object_generation (obj_p) <= maximum_gen_to_traverse)
|
||||
{
|
||||
if (!obj_p->gc_info.visited)
|
||||
if (!ecma_gc_is_object_visited (obj_p))
|
||||
{
|
||||
ecma_gc_mark (obj_p, ECMA_GC_GEN_COUNT);
|
||||
}
|
||||
@@ -299,7 +404,7 @@ ecma_gc_mark (ecma_object_t *object_p, /**< start object */
|
||||
|
||||
if (!does_reference_object_to_traverse)
|
||||
{
|
||||
object_p->gc_info.may_ref_younger_objects = false;
|
||||
ecma_gc_set_object_may_ref_younger_objects (object_p, false);
|
||||
}
|
||||
} /* ecma_gc_mark */
|
||||
|
||||
@@ -310,10 +415,10 @@ void
|
||||
ecma_gc_sweep (ecma_object_t *object_p) /**< object to free */
|
||||
{
|
||||
JERRY_ASSERT(object_p != NULL
|
||||
&& !object_p->gc_info.visited
|
||||
&& object_p->gc_info.refs == 0);
|
||||
&& !ecma_gc_is_object_visited (object_p)
|
||||
&& ecma_gc_get_object_refs (object_p) == 0);
|
||||
|
||||
for (ecma_property_t *property = ECMA_GET_POINTER(object_p->properties_p),
|
||||
for (ecma_property_t *property = ecma_get_property_list (object_p),
|
||||
*next_property_p;
|
||||
property != NULL;
|
||||
property = next_property_p)
|
||||
@@ -339,9 +444,9 @@ ecma_gc_run (ecma_gc_gen_t max_gen_to_collect) /**< maximum generation to run co
|
||||
{
|
||||
for (ecma_object_t *obj_iter_p = ecma_gc_objects_lists[ gen_id ];
|
||||
obj_iter_p != NULL;
|
||||
obj_iter_p = ECMA_GET_POINTER(obj_iter_p->gc_info.next))
|
||||
obj_iter_p = ecma_gc_get_object_next (obj_iter_p))
|
||||
{
|
||||
obj_iter_p->gc_info.visited = false;
|
||||
ecma_gc_set_object_visited (obj_iter_p, false);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -351,10 +456,10 @@ ecma_gc_run (ecma_gc_gen_t max_gen_to_collect) /**< maximum generation to run co
|
||||
{
|
||||
for (ecma_object_t *obj_iter_p = ecma_gc_objects_lists[ gen_id ];
|
||||
obj_iter_p != NULL;
|
||||
obj_iter_p = ECMA_GET_POINTER(obj_iter_p->gc_info.next))
|
||||
obj_iter_p = ecma_gc_get_object_next (obj_iter_p))
|
||||
{
|
||||
if (obj_iter_p->gc_info.refs > 0
|
||||
&& !obj_iter_p->gc_info.visited)
|
||||
if (ecma_gc_get_object_refs (obj_iter_p) > 0
|
||||
&& !ecma_gc_is_object_visited (obj_iter_p))
|
||||
{
|
||||
ecma_gc_mark (obj_iter_p, ECMA_GC_GEN_COUNT);
|
||||
}
|
||||
@@ -368,9 +473,9 @@ ecma_gc_run (ecma_gc_gen_t max_gen_to_collect) /**< maximum generation to run co
|
||||
{
|
||||
for (ecma_object_t *obj_iter_p = ecma_gc_objects_lists[ gen_id ];
|
||||
obj_iter_p != NULL;
|
||||
obj_iter_p = ECMA_GET_POINTER(obj_iter_p->gc_info.next))
|
||||
obj_iter_p = ecma_gc_get_object_next (obj_iter_p))
|
||||
{
|
||||
if (obj_iter_p->gc_info.may_ref_younger_objects > 0)
|
||||
if (ecma_gc_is_object_may_ref_younger_objects (obj_iter_p))
|
||||
{
|
||||
ecma_gc_mark (obj_iter_p, max_gen_to_collect);
|
||||
}
|
||||
@@ -391,15 +496,15 @@ ecma_gc_run (ecma_gc_gen_t max_gen_to_collect) /**< maximum generation to run co
|
||||
obj_iter_p != NULL;
|
||||
obj_iter_p = obj_next_p)
|
||||
{
|
||||
obj_next_p = ECMA_GET_POINTER(obj_iter_p->gc_info.next);
|
||||
obj_next_p = ecma_gc_get_object_next (obj_iter_p);
|
||||
|
||||
if (!obj_iter_p->gc_info.visited)
|
||||
if (!ecma_gc_is_object_visited (obj_iter_p))
|
||||
{
|
||||
ecma_gc_sweep (obj_iter_p);
|
||||
|
||||
if (likely (obj_prev_p != NULL))
|
||||
{
|
||||
ECMA_SET_POINTER(obj_prev_p->gc_info.next, obj_next_p);
|
||||
ecma_gc_set_object_next (obj_prev_p, obj_next_p);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -410,10 +515,10 @@ ecma_gc_run (ecma_gc_gen_t max_gen_to_collect) /**< maximum generation to run co
|
||||
{
|
||||
obj_prev_p = obj_iter_p;
|
||||
|
||||
if (obj_iter_p->gc_info.generation != ECMA_GC_GEN_COUNT - 1)
|
||||
if (ecma_gc_get_object_generation (obj_iter_p) != ECMA_GC_GEN_COUNT - 1)
|
||||
{
|
||||
/* the object will be promoted to next generation */
|
||||
obj_iter_p->gc_info.generation++;
|
||||
ecma_gc_set_object_generation (obj_iter_p, ecma_gc_get_object_generation (obj_iter_p) + 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -431,7 +536,7 @@ ecma_gc_run (ecma_gc_gen_t max_gen_to_collect) /**< maximum generation to run co
|
||||
/* promoting to next generation */
|
||||
if (gen_last_obj_p[ gen_to_promote ] != NULL)
|
||||
{
|
||||
ECMA_SET_POINTER(gen_last_obj_p[ gen_to_promote ]->gc_info.next, ecma_gc_objects_lists[ gen_to_promote + 1 ]);
|
||||
ecma_gc_set_object_next (gen_last_obj_p [gen_to_promote], ecma_gc_objects_lists[ gen_to_promote + 1 ]);
|
||||
ecma_gc_objects_lists[ gen_to_promote + 1 ] = ecma_gc_objects_lists[ gen_to_promote ];
|
||||
ecma_gc_objects_lists[ gen_to_promote ] = NULL;
|
||||
}
|
||||
@@ -451,9 +556,9 @@ ecma_gc_run (ecma_gc_gen_t max_gen_to_collect) /**< maximum generation to run co
|
||||
{
|
||||
for (ecma_object_t *obj_iter_p = ecma_gc_objects_lists[ gen_id ];
|
||||
obj_iter_p != NULL;
|
||||
obj_iter_p = ECMA_GET_POINTER(obj_iter_p->gc_info.next))
|
||||
obj_iter_p = ecma_gc_get_object_next (obj_iter_p))
|
||||
{
|
||||
JERRY_ASSERT(obj_iter_p->gc_info.generation == gen_id);
|
||||
JERRY_ASSERT(ecma_gc_get_object_generation (obj_iter_p) == gen_id);
|
||||
}
|
||||
}
|
||||
#endif /* !JERRY_NDEBUG */
|
||||
|
||||
@@ -302,7 +302,7 @@ typedef struct
|
||||
/**
|
||||
* Compressed pointer to next object in the global list of objects with same generation.
|
||||
*/
|
||||
unsigned int next : ECMA_POINTER_FIELD_WIDTH;
|
||||
unsigned int next_cp : ECMA_POINTER_FIELD_WIDTH;
|
||||
|
||||
/**
|
||||
* Marker that is set if the object was visited during graph traverse.
|
||||
@@ -366,7 +366,7 @@ typedef enum
|
||||
typedef struct ecma_object_t
|
||||
{
|
||||
/** Compressed pointer to property list */
|
||||
unsigned int properties_p : ECMA_POINTER_FIELD_WIDTH;
|
||||
unsigned int properties_cp : ECMA_POINTER_FIELD_WIDTH;
|
||||
|
||||
/** Flag indicating whether it is a general object (false)
|
||||
or a lexical environment (true) */
|
||||
@@ -390,7 +390,7 @@ typedef struct ecma_object_t
|
||||
unsigned int type : 3;
|
||||
|
||||
/** Compressed pointer to prototype object (ecma_object_t) */
|
||||
unsigned int prototype_object_p : ECMA_POINTER_FIELD_WIDTH;
|
||||
unsigned int prototype_object_cp : ECMA_POINTER_FIELD_WIDTH;
|
||||
} __packed object;
|
||||
|
||||
/**
|
||||
@@ -404,7 +404,7 @@ typedef struct ecma_object_t
|
||||
unsigned int type : 1;
|
||||
|
||||
/** Compressed pointer to outer lexical environment */
|
||||
unsigned int outer_reference_p : ECMA_POINTER_FIELD_WIDTH;
|
||||
unsigned int outer_reference_cp : ECMA_POINTER_FIELD_WIDTH;
|
||||
} __packed lexical_environment;
|
||||
|
||||
} __packed u;
|
||||
|
||||
@@ -373,7 +373,8 @@ ecma_make_throw_completion_value (ecma_value_t value) /**< value */
|
||||
ecma_completion_value_t
|
||||
ecma_make_throw_obj_completion_value (ecma_object_t *exception_p) /**< an object */
|
||||
{
|
||||
JERRY_ASSERT(exception_p != NULL && !exception_p->is_lexical_environment);
|
||||
JERRY_ASSERT(exception_p != NULL
|
||||
&& !ecma_is_lexical_environment (exception_p));
|
||||
|
||||
ecma_value_t exception = ecma_make_object_value (exception_p);
|
||||
|
||||
|
||||
@@ -42,11 +42,11 @@ ecma_create_object (ecma_object_t *prototype_object_p, /**< pointer to prototybe
|
||||
ecma_object_t *object_p = ecma_alloc_object ();
|
||||
ecma_init_gc_info (object_p);
|
||||
|
||||
object_p->properties_p = ECMA_NULL_POINTER;
|
||||
object_p->properties_cp = ECMA_NULL_POINTER;
|
||||
object_p->is_lexical_environment = false;
|
||||
|
||||
object_p->u.object.extensible = is_extensible;
|
||||
ECMA_SET_POINTER(object_p->u.object.prototype_object_p, prototype_object_p);
|
||||
ECMA_SET_POINTER(object_p->u.object.prototype_object_cp, prototype_object_p);
|
||||
object_p->u.object.type = type;
|
||||
|
||||
return object_p;
|
||||
@@ -71,9 +71,9 @@ ecma_create_decl_lex_env (ecma_object_t *outer_lexical_environment_p) /**< outer
|
||||
new_lexical_environment_p->is_lexical_environment = true;
|
||||
new_lexical_environment_p->u.lexical_environment.type = ECMA_LEXICAL_ENVIRONMENT_DECLARATIVE;
|
||||
|
||||
new_lexical_environment_p->properties_p = ECMA_NULL_POINTER;
|
||||
new_lexical_environment_p->properties_cp = ECMA_NULL_POINTER;
|
||||
|
||||
ECMA_SET_POINTER(new_lexical_environment_p->u.lexical_environment.outer_reference_p, outer_lexical_environment_p);
|
||||
ECMA_SET_POINTER(new_lexical_environment_p->u.lexical_environment.outer_reference_cp, outer_lexical_environment_p);
|
||||
|
||||
return new_lexical_environment_p;
|
||||
} /* ecma_create_decl_lex_env */
|
||||
@@ -94,7 +94,7 @@ ecma_create_object_lex_env (ecma_object_t *outer_lexical_environment_p, /**< out
|
||||
bool provide_this) /**< provideThis flag */
|
||||
{
|
||||
JERRY_ASSERT(binding_obj_p != NULL
|
||||
&& !binding_obj_p->is_lexical_environment);
|
||||
&& !ecma_is_lexical_environment (binding_obj_p));
|
||||
|
||||
ecma_object_t *new_lexical_environment_p = ecma_alloc_object ();
|
||||
ecma_init_gc_info (new_lexical_environment_p);
|
||||
@@ -102,9 +102,9 @@ ecma_create_object_lex_env (ecma_object_t *outer_lexical_environment_p, /**< out
|
||||
new_lexical_environment_p->is_lexical_environment = true;
|
||||
new_lexical_environment_p->u.lexical_environment.type = ECMA_LEXICAL_ENVIRONMENT_OBJECTBOUND;
|
||||
|
||||
new_lexical_environment_p->properties_p = ECMA_NULL_POINTER;
|
||||
new_lexical_environment_p->properties_cp = ECMA_NULL_POINTER;
|
||||
|
||||
ECMA_SET_POINTER(new_lexical_environment_p->u.lexical_environment.outer_reference_p, outer_lexical_environment_p);
|
||||
ECMA_SET_POINTER(new_lexical_environment_p->u.lexical_environment.outer_reference_cp, outer_lexical_environment_p);
|
||||
|
||||
ecma_property_t *provide_this_prop_p = ecma_create_internal_property (new_lexical_environment_p,
|
||||
ECMA_INTERNAL_PROPERTY_PROVIDE_THIS);
|
||||
@@ -119,6 +119,114 @@ ecma_create_object_lex_env (ecma_object_t *outer_lexical_environment_p, /**< out
|
||||
return new_lexical_environment_p;
|
||||
} /* ecma_create_object_lex_env */
|
||||
|
||||
/**
|
||||
* Check if the object is lexical environment.
|
||||
*/
|
||||
bool
|
||||
ecma_is_lexical_environment (ecma_object_t *object_p) /**< object or lexical environment */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
return object_p->is_lexical_environment;
|
||||
} /* ecma_is_lexical_environment */
|
||||
|
||||
/**
|
||||
* Get value of [[Extensible]] object's internal property.
|
||||
*/
|
||||
bool
|
||||
ecma_get_object_extensible (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
JERRY_ASSERT (!ecma_is_lexical_environment (object_p));
|
||||
|
||||
return object_p->u.object.extensible;
|
||||
} /* ecma_get_object_extensible */
|
||||
|
||||
/**
|
||||
* Set value of [[Extensible]] object's internal property.
|
||||
*/
|
||||
void
|
||||
ecma_set_object_extensible (ecma_object_t *object_p, /**< object */
|
||||
bool is_extensible) /**< value of [[Extensible]] */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
JERRY_ASSERT (!ecma_is_lexical_environment (object_p));
|
||||
|
||||
object_p->u.object.extensible = is_extensible;
|
||||
} /* ecma_set_object_extensible */
|
||||
|
||||
/**
|
||||
* Get object's internal implementation-defined type.
|
||||
*/
|
||||
ecma_object_type_t
|
||||
ecma_get_object_type (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
JERRY_ASSERT (!ecma_is_lexical_environment (object_p));
|
||||
|
||||
return object_p->u.object.type;
|
||||
} /* ecma_get_object_type */
|
||||
|
||||
/**
|
||||
* Set object's internal implementation-defined type.
|
||||
*/
|
||||
void
|
||||
ecma_set_object_type (ecma_object_t *object_p, /**< object */
|
||||
ecma_object_type_t type) /**< type */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
JERRY_ASSERT (!ecma_is_lexical_environment (object_p));
|
||||
|
||||
object_p->u.object.type = type;
|
||||
} /* ecma_set_object_type */
|
||||
|
||||
/**
|
||||
* Get object's prototype.
|
||||
*/
|
||||
ecma_object_t*
|
||||
ecma_get_object_prototype (ecma_object_t *object_p) /**< object */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
JERRY_ASSERT (!ecma_is_lexical_environment (object_p));
|
||||
|
||||
return (ecma_object_t*) ECMA_GET_POINTER (object_p->u.object.prototype_object_cp);
|
||||
} /* ecma_get_object_prototype */
|
||||
|
||||
/**
|
||||
* Get type of lexical environment.
|
||||
*/
|
||||
ecma_lexical_environment_type_t
|
||||
ecma_get_lex_env_type (ecma_object_t *object_p) /**< lexical environment */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
JERRY_ASSERT (ecma_is_lexical_environment (object_p));
|
||||
|
||||
return (ecma_lexical_environment_type_t) object_p->u.lexical_environment.type;
|
||||
} /* ecma_get_lex_env_type */
|
||||
|
||||
/**
|
||||
* Get outer reference of lexical environment.
|
||||
*/
|
||||
ecma_object_t*
|
||||
ecma_get_lex_env_outer_reference (ecma_object_t *object_p) /**< lexical environment */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
JERRY_ASSERT (ecma_is_lexical_environment (object_p));
|
||||
|
||||
return (ecma_object_t*) ECMA_GET_POINTER (object_p->u.lexical_environment.outer_reference_cp);
|
||||
} /* ecma_get_lex_env_outer_reference */
|
||||
|
||||
/**
|
||||
* Get object's/lexical environment's property list.
|
||||
*/
|
||||
ecma_property_t*
|
||||
ecma_get_property_list (ecma_object_t *object_p) /**< object or lexical environment */
|
||||
{
|
||||
JERRY_ASSERT (object_p != NULL);
|
||||
|
||||
return (ecma_property_t*) ECMA_GET_POINTER (object_p->properties_cp);
|
||||
} /* ecma_get_property_list */
|
||||
|
||||
/**
|
||||
* Create internal property in an object and link it into
|
||||
* the object's properties' linked-list (at start of the list).
|
||||
@@ -133,9 +241,9 @@ ecma_create_internal_property (ecma_object_t *object_p, /**< the object */
|
||||
|
||||
new_property_p->type = ECMA_PROPERTY_INTERNAL;
|
||||
|
||||
ecma_property_t *list_head_p = ECMA_GET_POINTER(object_p->properties_p);
|
||||
ecma_property_t *list_head_p = ECMA_GET_POINTER(object_p->properties_cp);
|
||||
ECMA_SET_POINTER(new_property_p->next_property_p, list_head_p);
|
||||
ECMA_SET_NON_NULL_POINTER(object_p->properties_p, new_property_p);
|
||||
ECMA_SET_NON_NULL_POINTER(object_p->properties_cp, new_property_p);
|
||||
|
||||
new_property_p->u.internal_property.type = property_id;
|
||||
new_property_p->u.internal_property.value = ECMA_NULL_POINTER;
|
||||
@@ -158,7 +266,7 @@ ecma_find_internal_property (ecma_object_t *object_p, /**< object descriptor */
|
||||
JERRY_ASSERT(property_id != ECMA_INTERNAL_PROPERTY_PROTOTYPE
|
||||
&& property_id != ECMA_INTERNAL_PROPERTY_EXTENSIBLE);
|
||||
|
||||
for (ecma_property_t *property_p = ECMA_GET_POINTER(object_p->properties_p);
|
||||
for (ecma_property_t *property_p = ecma_get_property_list (object_p);
|
||||
property_p != NULL;
|
||||
property_p = ECMA_GET_POINTER(property_p->next_property_p))
|
||||
{
|
||||
@@ -221,10 +329,10 @@ ecma_create_named_data_property (ecma_object_t *obj_p, /**< object */
|
||||
|
||||
prop_p->u.named_data_property.value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_UNDEFINED);
|
||||
|
||||
ecma_property_t *list_head_p = ECMA_GET_POINTER(obj_p->properties_p);
|
||||
ecma_property_t *list_head_p = ECMA_GET_POINTER(obj_p->properties_cp);
|
||||
|
||||
ECMA_SET_POINTER(prop_p->next_property_p, list_head_p);
|
||||
ECMA_SET_NON_NULL_POINTER(obj_p->properties_p, prop_p);
|
||||
ECMA_SET_NON_NULL_POINTER(obj_p->properties_cp, prop_p);
|
||||
|
||||
return prop_p;
|
||||
} /* ecma_create_named_data_property */
|
||||
@@ -260,9 +368,9 @@ ecma_create_named_accessor_property (ecma_object_t *obj_p, /**< object */
|
||||
prop_p->u.named_accessor_property.enumerable = enumerable;
|
||||
prop_p->u.named_accessor_property.configurable = configurable;
|
||||
|
||||
ecma_property_t *list_head_p = ECMA_GET_POINTER(obj_p->properties_p);
|
||||
ecma_property_t *list_head_p = ECMA_GET_POINTER(obj_p->properties_cp);
|
||||
ECMA_SET_POINTER(prop_p->next_property_p, list_head_p);
|
||||
ECMA_SET_NON_NULL_POINTER(obj_p->properties_p, prop_p);
|
||||
ECMA_SET_NON_NULL_POINTER(obj_p->properties_cp, prop_p);
|
||||
|
||||
return prop_p;
|
||||
} /* ecma_create_named_accessor_property */
|
||||
@@ -280,7 +388,7 @@ ecma_find_named_property (ecma_object_t *obj_p, /**< object to find property in
|
||||
JERRY_ASSERT(obj_p != NULL);
|
||||
JERRY_ASSERT(name_p != NULL);
|
||||
|
||||
for (ecma_property_t *property_p = ECMA_GET_POINTER(obj_p->properties_p);
|
||||
for (ecma_property_t *property_p = ecma_get_property_list (obj_p);
|
||||
property_p != NULL;
|
||||
property_p = ECMA_GET_POINTER(property_p->next_property_p))
|
||||
{
|
||||
@@ -469,7 +577,7 @@ void
|
||||
ecma_delete_property (ecma_object_t *obj_p, /**< object */
|
||||
ecma_property_t *prop_p) /**< property */
|
||||
{
|
||||
for (ecma_property_t *cur_prop_p = ECMA_GET_POINTER(obj_p->properties_p), *prev_prop_p = NULL, *next_prop_p;
|
||||
for (ecma_property_t *cur_prop_p = ECMA_GET_POINTER(obj_p->properties_cp), *prev_prop_p = NULL, *next_prop_p;
|
||||
cur_prop_p != NULL;
|
||||
prev_prop_p = cur_prop_p, cur_prop_p = next_prop_p)
|
||||
{
|
||||
@@ -481,7 +589,7 @@ ecma_delete_property (ecma_object_t *obj_p, /**< object */
|
||||
|
||||
if (prev_prop_p == NULL)
|
||||
{
|
||||
ECMA_SET_POINTER(obj_p->properties_p, next_prop_p);
|
||||
ECMA_SET_POINTER(obj_p->properties_cp, next_prop_p);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
@@ -157,6 +157,15 @@ extern ecma_object_t* ecma_create_decl_lex_env (ecma_object_t *outer_lexical_env
|
||||
extern ecma_object_t* ecma_create_object_lex_env (ecma_object_t *outer_lexical_environment_p,
|
||||
ecma_object_t *binding_obj_p,
|
||||
bool provide_this);
|
||||
extern bool ecma_is_lexical_environment (ecma_object_t *object_p);
|
||||
extern bool ecma_get_object_extensible (ecma_object_t *object_p);
|
||||
extern void ecma_set_object_extensible (ecma_object_t *object_p, bool is_extensible);
|
||||
extern ecma_object_type_t ecma_get_object_type (ecma_object_t *object_p);
|
||||
extern void ecma_set_object_type (ecma_object_t *object_p, ecma_object_type_t type);
|
||||
extern ecma_object_t* ecma_get_object_prototype (ecma_object_t *object_p);
|
||||
extern ecma_lexical_environment_type_t ecma_get_lex_env_type (ecma_object_t *object_p);
|
||||
extern ecma_object_t *ecma_get_lex_env_outer_reference (ecma_object_t *object_p);
|
||||
extern ecma_property_t *ecma_get_property_list (ecma_object_t *object_p);
|
||||
|
||||
extern ecma_property_t* ecma_create_internal_property (ecma_object_t *object_p,
|
||||
ecma_internal_property_id_t property_id);
|
||||
|
||||
Reference in New Issue
Block a user