File Coverage

lib/XS/Parse/Keyword.xs
Criterion Covered Total %
statement 14 45 31.1
branch 0 4 0.0
condition n/a
subroutine n/a
pod n/a
total 14 49 28.5


line stmt bran cond sub pod time code
1             /* You may distribute under the terms of either the GNU General Public License
2             * or the Artistic License (the same terms as Perl itself)
3             *
4             * (C) Paul Evans, 2021 -- leonerd@leonerd.org.uk
5             */
6              
7             #define PERL_NO_GET_CONTEXT
8              
9             #include "EXTERN.h"
10             #include "perl.h"
11             #include "XSUB.h"
12              
13             #include "XSParseKeyword.h"
14             #include "XSParseInfix.h"
15              
16             #include "keyword.h"
17             #include "infix.h"
18              
19             /* v0 hooks lacked wrapper_func_name */
20             struct XSParseInfixHooks_v0 {
21             U32 flags;
22             enum XSParseInfixClassification cls;
23              
24             const char *permit_hintkey;
25             bool (*permit) (pTHX_ void *hookdata);
26              
27             OP *(*new_op)(pTHX_ U32 flags, OP *lhs, OP *rhs, void *hookdata);
28             OP *(*ppaddr)(pTHX);
29             };
30              
31 0           static void XSParseInfix_register_v0(pTHX_ const char *opname, const struct XSParseInfixHooks_v0 *hooks_v0, void *hookdata)
32             {
33 0           warn("XSParseInfix ABI version 0 is deprecated and will soon be removed");
34              
35             struct XSParseInfixHooks *hooks;
36 0           Newx(hooks, 1, struct XSParseInfixHooks);
37              
38 0           hooks->flags = hooks_v0->flags | (1<<15); /* NO_PARSEDATA */
39 0           hooks->cls = hooks_v0->cls;
40              
41 0           hooks->wrapper_func_name = NULL;
42              
43 0           hooks->permit_hintkey = hooks_v0->permit_hintkey;
44 0           hooks->permit = hooks_v0->permit;
45 0           hooks->new_op = (OP *(*)(pTHX_ U32, OP *, OP *, SV **, void *))hooks_v0->new_op;
46 0           hooks->ppaddr = hooks_v0->ppaddr;
47 0           hooks->parse = NULL;
48              
49 0           XSParseInfix_register(aTHX_ opname, hooks, hookdata);
50 0           }
51              
52             /* v1 hooks.newop did not pass parsedata */
53             struct XSParseInfixHooks_v1 {
54             U16 flags;
55             U8 lhs_flags, rhs_flags;
56             enum XSParseInfixClassification cls;
57              
58             const char *wrapper_func_name;
59              
60             const char *permit_hintkey;
61             bool (*permit) (pTHX_ void *hookdata);
62              
63             OP *(*new_op)(pTHX_ U32 flags, OP *lhs, OP *rhs, void *hookdata);
64             OP *(*ppaddr)(pTHX);
65              
66             OP *(*parse_rhs)(pTHX_ void *hookdata);
67             };
68              
69 0           static void XSParseInfix_register_v1(pTHX_ const char *opname, const struct XSParseInfixHooks_v1 *hooks_v1, void *hookdata)
70             {
71 0 0         if(hooks_v1->rhs_flags & XPI_OPERAND_CUSTOM)
72 0           croak("XPI_OPERAND_CUSTOM is no longer supported");
73 0 0         if(hooks_v1->parse_rhs)
74 0           croak("XSParseInfixHooks.parse_rhs is no longer supported");
75              
76             struct XSParseInfixHooks *hooks;
77 0           Newx(hooks, 1, struct XSParseInfixHooks);
78              
79 0           hooks->flags = hooks_v1->flags | (1<<15) /* NO_PARSEDATA */;
80 0           hooks->lhs_flags = hooks_v1->lhs_flags;
81 0           hooks->rhs_flags = hooks_v1->rhs_flags;
82 0           hooks->cls = hooks_v1->cls;
83              
84 0           hooks->wrapper_func_name = hooks_v1->wrapper_func_name;
85              
86 0           hooks->permit_hintkey = hooks_v1->permit_hintkey;
87 0           hooks->permit = hooks_v1->permit;
88 0           hooks->new_op = (OP *(*)(pTHX_ U32, OP *, OP *, SV **, void *))hooks_v1->new_op;
89 0           hooks->ppaddr = hooks_v1->ppaddr;
90 0           hooks->parse = NULL;
91              
92 0           XSParseInfix_register(aTHX_ opname, hooks, hookdata);
93 0           }
94              
95             MODULE = XS::Parse::Keyword PACKAGE = XS::Parse::Keyword
96              
97             BOOT:
98             /* legacy version0 support */
99 22           sv_setiv(*hv_fetchs(PL_modglobal, "XS::Parse::Keyword/ABIVERSION", 1), XSPARSEKEYWORD_ABI_VERSION);
100              
101             /* newer versions */
102 22           sv_setiv(*hv_fetchs(PL_modglobal, "XS::Parse::Keyword/ABIVERSION_MIN", 1), 1);
103 22           sv_setiv(*hv_fetchs(PL_modglobal, "XS::Parse::Keyword/ABIVERSION_MAX", 1), XSPARSEKEYWORD_ABI_VERSION);
104              
105 22           sv_setuv(*hv_fetchs(PL_modglobal, "XS::Parse::Keyword/register()@1", 1), PTR2UV(&XSParseKeyword_register_v1));
106 22           sv_setuv(*hv_fetchs(PL_modglobal, "XS::Parse::Keyword/register()@2", 1), PTR2UV(&XSParseKeyword_register_v2));
107              
108 22           XSParseKeyword_boot(aTHX);
109              
110              
111 22           sv_setiv(*hv_fetchs(PL_modglobal, "XS::Parse::Infix/ABIVERSION_MIN", 1), 0);
112 22           sv_setiv(*hv_fetchs(PL_modglobal, "XS::Parse::Infix/ABIVERSION_MAX", 1), XSPARSEINFIX_ABI_VERSION);
113              
114 22           sv_setuv(*hv_fetchs(PL_modglobal, "XS::Parse::Infix/parse()@2", 1), PTR2UV(&XSParseInfix_parse));
115 22           sv_setuv(*hv_fetchs(PL_modglobal, "XS::Parse::Infix/new_op()@0", 1), PTR2UV(&XSParseInfix_new_op));
116 22           sv_setuv(*hv_fetchs(PL_modglobal, "XS::Parse::Infix/register()@0", 1), PTR2UV(&XSParseInfix_register_v0));
117 22           sv_setuv(*hv_fetchs(PL_modglobal, "XS::Parse::Infix/register()@1", 1), PTR2UV(&XSParseInfix_register_v1));
118 22           sv_setuv(*hv_fetchs(PL_modglobal, "XS::Parse::Infix/register()@2", 1), PTR2UV(&XSParseInfix_register));
119              
120 22           XSParseInfix_boot(aTHX);