Move ::Meta::Module::namespace into XS
[gitmo/Mouse.git] / xs-src / mouse_util.xs
CommitLineData
df6dd016 1#include "mouse.h"
2
3/* equivalent to "blessed($x) && $x->isa($klass)" */
4bool
5mouse_is_instance_of(pTHX_ SV* const sv, SV* const klass){
6 assert(sv);
7 assert(klass);
8
9 if(IsObject(sv) && SvOK(klass)){
10 bool ok;
11
12 ENTER;
13 SAVETMPS;
14
15 ok = SvTRUEx(mcall1s(sv, "isa", klass));
16
17 FREETMPS;
18 LEAVE;
19
20 return ok;
21 }
22
23 return FALSE;
24}
25
26
27bool
28mouse_is_class_loaded(pTHX_ SV * const klass){
29 HV *stash;
30 GV** gvp;
31 HE* he;
32
33 if (!(SvPOKp(klass) && SvCUR(klass))) { /* XXX: SvPOK does not work with magical scalars */
34 return FALSE;
35 }
36
37 stash = gv_stashsv(klass, FALSE);
38 if (!stash) {
39 return FALSE;
40 }
41
42 if (( gvp = (GV**)hv_fetchs(stash, "VERSION", FALSE) )) {
43 if(isGV(*gvp) && GvSV(*gvp) && SvOK(GvSV(*gvp))){
44 return TRUE;
45 }
46 }
47
48 if (( gvp = (GV**)hv_fetchs(stash, "ISA", FALSE) )) {
49 if(isGV(*gvp) && GvAV(*gvp) && av_len(GvAV(*gvp)) != -1){
50 return TRUE;
51 }
52 }
53
54 hv_iterinit(stash);
55 while(( he = hv_iternext(stash) )){
56 GV* const gv = (GV*)HeVAL(he);
57
58 if(isGV(gv)){
59 if(GvCVu(gv)){
60 return TRUE;
61 }
62 }
63 else if(SvOK(gv)){
64 return TRUE;
65 }
66 }
67 return FALSE;
68}
69
70
71SV *
72mouse_call0 (pTHX_ SV *const self, SV *const method)
73{
74 dSP;
75 SV *ret;
76
77 PUSHMARK(SP);
78 XPUSHs(self);
79 PUTBACK;
80
81 call_sv(method, G_SCALAR | G_METHOD);
82
83 SPAGAIN;
84 ret = POPs;
85 PUTBACK;
86
87 return ret;
88}
89
90SV *
91mouse_call1 (pTHX_ SV *const self, SV *const method, SV* const arg1)
92{
93 dSP;
94 SV *ret;
95
96 PUSHMARK(SP);
97 EXTEND(SP, 2);
98 PUSHs(self);
99 PUSHs(arg1);
100 PUTBACK;
101
102 call_sv(method, G_SCALAR | G_METHOD);
103
104 SPAGAIN;
105 ret = POPs;
106 PUTBACK;
107
108 return ret;
109}
110
43165725 111MAGIC*
112mouse_mg_find(pTHX_ SV* const sv, const MGVTBL* const vtbl, I32 const flags){
113 MAGIC* mg;
114
115 assert(sv != NULL);
116 for(mg = SvMAGIC(sv); mg; mg = mg->mg_moremagic){
117 if(mg->mg_virtual == vtbl){
118 return mg;
119 }
120 }
121
122 if(flags & MOUSEf_DIE_ON_FAIL){
123 croak("mouse_mg_find: no MAGIC found for %"SVf, sv_2mortal(newRV_inc(sv)));
124 }
125 return NULL;
126}