Repository: jerryscript-project/jerryscript
File: jerry-core/ecma/builtin-objects/ecma-builtin-array-prototype.c (C)

Code before:
                                                                      len,
                                                                      &start)))
  {
    return ECMA_VALUE_ERROR;
  }

  /* 7. */
  if (ecma_is_value_undefined (arg2))
  {
    end = len;
  }
  else
  {
    /* 7. part 2, 8.*/
    if (ECMA_IS_VALUE_ERROR (ecma_builtin_helper_array_index_normalize (arg2,
                                                                        len,
                                                                        &end)))
    {
      return ECMA_VALUE_ERROR;
    }
  }

  JERRY_ASSERT (start <= len && end <= len);

  bool use_fast_path = ecma_op_object_is_fast_array (obj_p);
  uint32_t copied_length = (uint32_t) JERRY_MAX ((int32_t) (end - start), 0);
#if ENABLED (JERRY_ES2015)
  ecma_value_t new_array = ecma_op_array_species_create (obj_p, copied_length);

  if (ECMA_IS_VALUE_ERROR (new_array))
  {
    return new_array;
  }
  use_fast_path &= ecma_op_object_is_fast_array (ecma_get_object_from_value (new_array));
#else /* !ENABLED (JERRY_ES2015) */
  ecma_value_t new_array = ecma_op_create_array_object (NULL, 0, false);
  JERRY_ASSERT (!ECMA_IS_VALUE_ERROR (new_array));
#endif /* ENABLED (JERRY_ES2015) */

  ecma_object_t *new_array_p = ecma_get_object_from_value (new_array);

  /* 9. */
  uint32_t n = 0;

  if (use_fast_path && copied_length > 0)
  {
    ecma_extended_object_t *ext_from_obj_p = (ecma_extended_object_t *) obj_p;

    if (ext_from_obj_p->u.array.u.hole_count < ECMA_FAST_ARRAY_HOLE_ONE)
    {
      ecma_extended_object_t *ext_to_obj_p = (ecma_extended_object_t *) new_array_p;

Review comment (bug):
This can result in an incorrect value in some cases. `end = 4294967295` and `start = 0` will be considered negative, and will result in zero. We should do `(end > start) ? end - start : 0` instead.

Code after:
                                                                      len,
                                                                      &start)))
  {
    return ECMA_VALUE_ERROR;
  }

  /* 7. */
  if (ecma_is_value_undefined (arg2))
  {
    end = len;
  }
  else
  {
    /* 7. part 2, 8.*/
    if (ECMA_IS_VALUE_ERROR (ecma_builtin_helper_array_index_normalize (arg2,
                                                                        len,
                                                                        &end)))
    {
      return ECMA_VALUE_ERROR;
    }
  }

  JERRY_ASSERT (start <= len && end <= len);

  bool use_fast_path = ecma_op_object_is_fast_array (obj_p);
  uint32_t copied_length = (end > start) ? end - start : 0;
#if ENABLED (JERRY_ES2015)
  ecma_value_t new_array = ecma_op_array_species_create (obj_p, copied_length);

  if (ECMA_IS_VALUE_ERROR (new_array))
  {
    return new_array;
  }
  use_fast_path &= ecma_op_object_is_fast_array (ecma_get_object_from_value (new_array));
#else /* !ENABLED (JERRY_ES2015) */
  ecma_value_t new_array = ecma_op_create_array_object (NULL, 0, false);
  JERRY_ASSERT (!ECMA_IS_VALUE_ERROR (new_array));
#endif /* ENABLED (JERRY_ES2015) */

  ecma_object_t *new_array_p = ecma_get_object_from_value (new_array);

  /* 9. */
  uint32_t n = 0;

  if (use_fast_path && copied_length > 0)
  {
    ecma_extended_object_t *ext_from_obj_p = (ecma_extended_object_t *) obj_p;

    if (ext_from_obj_p->u.array.u.hole_count < ECMA_FAST_ARRAY_HOLE_ONE)
    {
      ecma_extended_object_t *ext_to_obj_p = (ecma_extended_object_t *) new_array_p;