/*
Copyright (C) 2004, The Perl Foundation.
$Id: undef.pmc 16275 2006-12-28 01:20:44Z particle $

=head1 NAME

src/pmc/undef.pmc - Generic undefined value

=head1 DESCRIPTION

This is Parrot's generic undef type. This PMC has no defined value.
It returns a numeric value of 0, a boolean of false, and an empty string.
When assigned a number, integer, or string it morphs to a Number,
Integer, or String PMC respectively, and when assigned a generic PMC
it morphs into a PMC of the passed-in type and does a same-type assignment
from there.

=head2 Methods

=over 4

=cut

*/

#include "parrot/parrot.h"
#define UNDEF_STRING_CLASS enum_class_String

pmclass Undef extends default no_ro {

  void set_pmc(PMC* other) {
    VTABLE_morph(INTERP, SELF, enum_class_Ref);
    VTABLE_set_pmc(INTERP, SELF, other);
  }

  void assign_pmc(PMC* other) {
    VTABLE_morph(INTERP, SELF, other->vtable->base_type);
    /* don't want to call set_pmc if we're assigning an Undef to an Undef */
    if (other->vtable->base_type != enum_class_Undef)
        VTABLE_set_pmc(INTERP, SELF, other);
  }

  void morph(INTVAL new_type) {
    pmc_reuse(INTERP, SELF, new_type, 0);
  }

  INTVAL get_integer() {
    return 0;
  }

  INTVAL defined() {
    return 0;
  }

  void set_integer_native(INTVAL value) {
    VTABLE_morph(INTERP, SELF, enum_class_Integer);
    VTABLE_set_integer_native(INTERP, SELF, value);
  }

  FLOATVAL get_number() {
    return 0.0;
  }

  void set_number_native(FLOATVAL value) {
    VTABLE_morph(INTERP, SELF, enum_class_Float);
    VTABLE_set_number_native(INTERP, SELF, value);
  }

  STRING* get_string() {
    return string_make_empty(INTERP,enum_stringrep_one,0);
  }

  void set_string_native(STRING *value) {
    VTABLE_morph(INTERP, SELF, UNDEF_STRING_CLASS);
    VTABLE_set_string_native(INTERP, SELF, value);
  }

  INTVAL get_bool() {
    return 0;
  }

  void share() {
    /* see src/pmc/integer.pmc */
  }

  PMC* share_ro() {
    if (PObj_is_PMC_shared_TEST(SELF)) {
        return SELF;
    }
    else {
        return pt_shared_fixup(INTERP, SELF);
    }
  }

  PMC* clone() {
      return pmc_new(INTERP, SELF->vtable->base_type);
  }
}

/*

=back

=cut

*/


/*
 * Local variables:
 *   c-file-style: "parrot"
 * End:
 * vim: expandtab shiftwidth=4:
 */
