Object-Pad

 view release on metacpan or  search on metacpan

lib/Object/Pad.xs  view on Meta::CPAN

          funcs.permit_hintkey = SvPV_nolen(kwval);
          break;

        case 1: /* apply */
          funcdata.apply_cb = kwval;
          break;

        case 2: /* no_value */
          if(SvTRUE(kwval))
            funcs.flags |= OBJECTPAD_FLAG_ATTR_NO_VALUE;
          break;

        case 3: /* must_value */
          if(SvTRUE(kwval))
            funcs.flags |= OBJECTPAD_FLAG_ATTR_MUST_VALUE;
          break;
      }
    }

    if((funcs.flags & OBJECTPAD_FLAG_ATTR_NO_VALUE) &&
       (funcs.flags & OBJECTPAD_FLAG_ATTR_MUST_VALUE))
       croak("Cannot register a FieldAttr with both 'no_value' and 'must_value'");

    struct FieldHookFuncs *_funcs;
    Newxz(_funcs, 1, struct FieldHookFuncs);
    Copy(&funcs, _funcs, 1, struct FieldHookFuncs);
    if(_funcs->permit_hintkey)
      _funcs->permit_hintkey = savepv(_funcs->permit_hintkey);

    struct CustomFieldHookData *_funcdata;
    Newxz(_funcdata, 1, struct CustomFieldHookData);
    Copy(&funcdata, _funcdata, 1, struct CustomFieldHookData);
    if(_funcdata->apply_cb)
      _funcdata->apply_cb = newSVsv(_funcdata->apply_cb);

    register_field_attribute(savepv(SvPV_nolen(name)), _funcs, _funcdata);
  }

MODULE = Object::Pad    PACKAGE = Object::Pad::MetaFunctions

SV *
metaclass(SV *obj)
  CODE:
  {
    if(!SvROK(obj) || !SvOBJECT(SvRV(obj)))
      croak("Expected an object reference to metaclass");

    HV *stash = SvSTASH(SvRV(obj));

    GV **gvp = (GV **)hv_fetchs(stash, "META", 0);
    if(!gvp)
      croak("Unable to find ClassMeta for %" HEKf, HEKfARG(HvNAME_HEK(stash)));

    RETVAL = newSVsv(GvSV(*gvp));
  }
  OUTPUT:
    RETVAL

void
deconstruct_object(SV *obj)
  PPCODE:
  {
    if(!SvROK(obj) || !SvOBJECT(SvRV(obj)))
      croak("Expected an object reference to deconstruct_object");

    ClassMeta *classmeta = mop_get_class_for_stash(SvSTASH(SvRV(obj)));

    SV *fieldstore = get_obj_fieldstore(obj, classmeta->repr, true);

    U32 retcount = 0;

    PUSHs(sv_mortalcopy(classmeta->name));
    retcount++;

    PUTBACK;

    while(classmeta) {
      retcount += deconstruct_object_class(fieldstore, classmeta, 0);

      AV *roles = classmeta->cls.direct_roles;
      U32 nroles = av_count(roles);
      for(U32 i = 0; i < nroles; i++) {
        RoleEmbedding *embedding = MUST_ROLEEMBEDDING(AvARRAY(roles)[i]);

        retcount += deconstruct_object_class(fieldstore, embedding->rolemeta, embedding->offset);
      }

      classmeta = classmeta->cls.supermeta;
    }

    SPAGAIN;
    XSRETURN(retcount);
  }

SV *
ref_field(SV *fieldname, SV *obj)
  CODE:
  {
    SV *want_classname = NULL, *want_fieldname;

    if(!SvROK(obj) || !SvOBJECT(SvRV(obj)))
      croak("Expected an object reference to ref_field");

    SvGETMAGIC(fieldname);

    char *s = SvPV_nolen(fieldname);
    char *dotpos;
    if((dotpos = strchr(s, '.'))) {
      U32 flags = SvUTF8(fieldname) ? SVf_UTF8 : 0;
      want_classname = newSVpvn_flags(s, dotpos - s, flags);
      want_fieldname = newSVpvn_flags(dotpos + 1, strlen(dotpos + 1), flags);
    }
    else {
      want_fieldname = SvREFCNT_inc(fieldname);
    }

    SAVEFREESV(want_classname);
    SAVEFREESV(want_fieldname);

    ClassMeta *classmeta = mop_get_class_for_stash(SvSTASH(SvRV(obj)));



( run in 1.079 second using v1.01-cache-2.11-cpan-5511b514fd6 )