Line | Branch | Exec | Source |
---|---|---|---|
1 | #include "gwion_util.h" | ||
2 | #include "gwion_ast.h" | ||
3 | #include "gwion_env.h" | ||
4 | #include "vm.h" | ||
5 | #include "gwion.h" | ||
6 | #include "object.h" | ||
7 | #include "operator.h" | ||
8 | #include "traverse.h" | ||
9 | #include "parse.h" | ||
10 | #include "object.h" | ||
11 | #include "instr.h" | ||
12 | #include "import.h" | ||
13 | #include "tmpl_info.h" | ||
14 | |||
15 | 6824 | ANN static inline m_str tmpl_get(struct tmpl_info *info, m_str str) { | |
16 | 6824 | const m_str tmp = (m_str)vector_at(&info->type, info->index); | |
17 | 6824 | strcpy(str, tmp); | |
18 | 6824 | return str + vector_at(&info->size, info->index); | |
19 | } | ||
20 | |||
21 | 3412 | ANN static void template_name(struct tmpl_info *info, m_str s) { | |
22 | 3412 | m_str str = s; | |
23 | 3412 | const m_uint size = info->index = vector_size(&info->type) - 1; | |
24 | 3412 | str = tmpl_get(info, str); | |
25 | 3412 | *str++ = ':'; | |
26 | 3412 | *str++ = '['; | |
27 |
2/2✓ Branch 0 taken 3412 times.
✓ Branch 1 taken 3412 times.
|
6824 | for (info->index = 0; info->index < size; ++info->index) { |
28 | 3412 | str = tmpl_get(info, str); | |
29 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 3412 times.
|
3412 | if (info->index < size - 1) |
30 | ✗ | *str++ = ','; | |
31 | else | ||
32 | 3412 | *str++ = ']'; | |
33 | } | ||
34 | 3412 | *str = '\0'; | |
35 | 3412 | } | |
36 | |||
37 | 6824 | ANN static inline size_t tmpl_set(struct tmpl_info *info, const m_str str) { | |
38 | 6824 | vector_add(&info->type, (vtype)str); | |
39 | 6824 | const size_t len = strlen(str); | |
40 | 6824 | vector_add(&info->size, len); | |
41 | 6824 | return len; | |
42 | } | ||
43 | |||
44 | 3412 | ANN static ssize_t template_size(const Env env, struct tmpl_info *info) { | |
45 |
1/2✗ Branch 1 not taken.
✓ Branch 2 taken 3412 times.
|
3412 | DECL_OB(const m_str, str, |
46 | = tl2str(env->gwion, info->td->types, info->td->pos)); | ||
47 | 3412 | const size_t tmpl_sz = tmpl_set(info, str); | |
48 | 3412 | const m_str base = !is_func(env->gwion, info->base) | |
49 | 3412 | ? mstrdup(env->gwion->mp, info->base->name) | |
50 |
1/2✓ Branch 0 taken 3412 times.
✗ Branch 1 not taken.
|
3412 | : type2str(env->gwion, info->base, info->td->pos); |
51 | 3412 | return tmpl_sz + tmpl_set(info, base) + 4; | |
52 | } | ||
53 | |||
54 | 3412 | ANEW ANN static Symbol _template_id(const Env env, struct tmpl_info *const info, | |
55 | 3412 | const size_t sz) { | |
56 | 3412 | char name[sz]; | |
57 | 3412 | template_name(info, name); | |
58 | 3412 | return insert_symbol(name); | |
59 | } | ||
60 | |||
61 | 3412 | ANEW ANN static Symbol template_id(const Env env, | |
62 | struct tmpl_info *const info) { | ||
63 | 3412 | vector_init(&info->type); | |
64 | 3412 | vector_init(&info->size); | |
65 | 3412 | ssize_t sz = template_size(env, info); | |
66 |
1/2✓ Branch 0 taken 3412 times.
✗ Branch 1 not taken.
|
3412 | const Symbol sym = sz > GW_ERROR ? _template_id(env, info, sz) : NULL; |
67 |
2/2✓ Branch 1 taken 6824 times.
✓ Branch 2 taken 3412 times.
|
10236 | for (m_uint i = 0; i < vector_size(&info->type); ++i) |
68 | 6824 | mp_free2(env->gwion->mp, vector_at(&info->size, i), | |
69 | (m_str)vector_at(&info->type, i)); | ||
70 | 3412 | vector_release(&info->type); | |
71 | 3412 | vector_release(&info->size); | |
72 | 3412 | return sym; | |
73 | } | ||
74 | |||
75 | 3412 | ANN static m_bool template_match(Specialized_List sl, Type_List tl) { | |
76 | // uint32_t i = 0; | ||
77 | // while ((call = call->next)) i++; | ||
78 | //&& (base = base->next)) | ||
79 | // while ((call = call->next) && (base = base->next)) | ||
80 | // ; | ||
81 | // return i = base->len ? GW_OK : GW_ERROR; | ||
82 | // return !call ? GW_OK : GW_ERROR; | ||
83 | 3412 | return tl->len >= sl->len; | |
84 | } | ||
85 | |||
86 | 3412 | ANN static Type _tmpl_exists(const Env env, const Symbol name) { | |
87 |
4/4✓ Branch 0 taken 3353 times.
✓ Branch 1 taken 59 times.
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 3352 times.
|
3412 | if (env->class_def && name == insert_symbol(env->class_def->name)) |
88 | 1 | return env->class_def; | |
89 |
4/4✓ Branch 1 taken 2091 times.
✓ Branch 2 taken 1320 times.
✓ Branch 3 taken 44 times.
✓ Branch 4 taken 1276 times.
|
3411 | return nspc_lookup_type1(env->curr, name) ?: env->context ? nspc_lookup_type1(env->context->nspc, name) : NULL; |
90 | } | ||
91 | |||
92 | 3412 | ANN Type tmpl_exists(const Env env, struct tmpl_info *const info) { | |
93 |
1/2✗ Branch 1 not taken.
✓ Branch 2 taken 3412 times.
|
3412 | if (template_match(info->list, info->td->types) < 0) // invalid template |
94 | ✗ | ERR_N(info->td->pos, _("invalid template types number")); | |
95 |
1/2✓ Branch 0 taken 3412 times.
✗ Branch 1 not taken.
|
3412 | if (!info->name) |
96 | 3412 | info->name = template_id(env, info); | |
97 | 3412 | return _tmpl_exists(env, info->name); | |
98 | } | ||
99 | |||
100 | 663 | ANN bool tmpl_global(const Env env, Type_List tl) { | |
101 |
2/2✓ Branch 0 taken 673 times.
✓ Branch 1 taken 662 times.
|
1335 | for(uint32_t i = 0; i < tl->len; i++) { |
102 | 673 | Type_Decl *td = *mp_vector_at(tl, Type_Decl*, i); | |
103 | 673 | const Type t = known_type(env, td); | |
104 |
3/4✓ Branch 0 taken 673 times.
✗ Branch 1 not taken.
✓ Branch 3 taken 1 times.
✓ Branch 4 taken 672 times.
|
673 | if(!t || !type_global(env, t)) |
105 | 1 | return false; | |
106 | } | ||
107 | 662 | return true; | |
108 | } | ||
109 |