X-Git-Url: http://git.shadowcat.co.uk/gitweb/gitweb.cgi?a=blobdiff_plain;f=xs-src%2FMouse.xs;fp=xs-src%2FMouse.xs;h=74ef11349448e4c07733dcb1baac4a13e27622c6;hb=6fd8aa82f783628e6dfb8accf73d93ebd59ece85;hp=b3d411c1e8029dfa8c10033f27d0b3934a35787f;hpb=00a0078593fd8d931aa698c75eb4e38da3f97a23;p=gitmo%2FMouse.git diff --git a/xs-src/Mouse.xs b/xs-src/Mouse.xs index b3d411c..74ef113 100644 --- a/xs-src/Mouse.xs +++ b/xs-src/Mouse.xs @@ -238,11 +238,38 @@ mouse_buildargs(pTHX_ SV* metaclass, SV* const klass, I32 ax, I32 items) { } static void +mouse_report_unmatched_keys(pTHX_ SV* const meta, AV* const attrs, HV* const args) { + HV* const attr_map = newHV_mortal(); + I32 const len = AvFILLp(attrs) + 1; + I32 i; + SV* const unknown = newSVpvs_flags("", SVs_TEMP); + HE* he; + + for(i = 0; i < len; i++){ + SV* const attr = MOUSE_av_at(attrs, i); + (void)hv_store_ent(attr_map, mcall0(attr, mouse_name), &PL_sv_yes, 0U); + } + + hv_iterinit(args); + while((he = hv_iternext(args))){ + SV* const key = hv_iterkeysv(he); + if(!hv_exists_ent(attr_map, key, 0U)){ + sv_catpvf(unknown, " %"SVf",", key); + } + } + SvCUR(unknown)--; /* chop "," */ + mouse_throw_error(meta, NULL, + "Unknown attribute init_arg passed to the constructor of %"SVf": %"SVf, + mcall0(meta, mouse_name), unknown); +} + +static void mouse_class_initialize_object(pTHX_ SV* const meta, SV* const object, HV* const args, bool const ignore_triggers) { AV* const xc = mouse_get_xc(aTHX_ meta); AV* const attrs = MOUSE_xc_attrall(xc); I32 len = AvFILLp(attrs) + 1; I32 i; + I32 used = 0; AV* triggers_queue = NULL; assert(meta || object); @@ -281,6 +308,8 @@ mouse_class_initialize_object(pTHX_ SV* const meta, SV* const object, HV* const av_push(triggers_queue, (SV*)pair); } + + used++; } else { /* no init arg */ if(flags & (MOUSEf_ATTR_HAS_DEFAULT | MOUSEf_ATTR_HAS_BUILDER)){ @@ -305,6 +334,10 @@ mouse_class_initialize_object(pTHX_ SV* const meta, SV* const object, HV* const } } + if(used < HvUSEDKEYS(args)){ + mouse_report_unmatched_keys(aTHX_ meta, attrs, args); + } + if(MOUSE_xc_flags(xc) & MOUSEf_XC_IS_ANON){ set_slot(object, newSVpvs_flags("__METACLASS__", SVs_TEMP), meta); }