Skip to content

Commit a837fde

Browse files
committed
Codegen: Add Raw::getImmediateChild and Synth::isSynth
1 parent 000f33f commit a837fde

File tree

3 files changed

+78
-1
lines changed

3 files changed

+78
-1
lines changed

misc/codegen/templates/ql_db.mustache

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,9 +29,70 @@ module Raw {
2929
{{type}} {{getter}}({{#is_indexed}}int index{{/is_indexed}}) {
3030
{{tablename}}({{#tableparams}}{{^first}}, {{/first}}{{param}}{{/tableparams}})
3131
}
32+
{{#is_indexed}}
33+
int getNumberOf{{plural}}() {
34+
result = count(int i | {{tablename}}(this, i, _))
35+
}
36+
{{/is_indexed}}
3237
{{/synth}}
3338
{{/properties}}
3439
}
3540

41+
42+
{{#final}}
43+
private Element getImmediateChildOf{{name}}({{name}} e, int index) {
44+
{{^has_children}}none(){{/has_children}}
45+
{{#has_children}}
46+
{{! n is the base offset 0, for ease of generation }}
47+
{{! n<child> is constructed to be strictly greater than the indexes for <child> children }}
48+
exists(int n{{#all_children}}, int n{{property.singular}}{{/all_children}} |
49+
n = 0
50+
{{#all_children}}
51+
{{#property}}
52+
{{#synth}}
53+
and
54+
n{{singular}} = n{{prev}}
55+
{{/synth}}
56+
{{^synth}}
57+
{{! n<child> is defined on top of the previous definition }}
58+
{{! for single and optional properties it adds 1 (regardless of whether the optional property exists) }}
59+
{{! for repeated it adds 1 + the maximum index (which works for repeated optional as well) }}
60+
and
61+
n{{singular}} = n{{prev}} {{^is_repeated}}+ 1{{/is_repeated}}{{#is_repeated}}+ e.getNumberOf{{plural}}(){{/is_repeated}}
62+
{{/synth}}
63+
{{/property}}
64+
{{/all_children}} and (
65+
none()
66+
{{#all_children}}
67+
{{#property}}
68+
{{^synth}}
69+
or
70+
{{#is_repeated}}
71+
result = e.get{{singular}}(index - n{{prev}})
72+
{{/is_repeated}}
73+
{{^is_repeated}}
74+
index = n{{prev}} and result = e.get{{singular}}()
75+
{{/is_repeated}}
76+
{{/synth}}
77+
{{/property}}
78+
{{/all_children}}
79+
))
80+
{{/has_children}}
81+
}
82+
{{/final}}
83+
3684
{{/classes}}
85+
86+
pragma[nomagic]
87+
Element getImmediateChild(Element e, int index) {
88+
// why does this look more complicated than it should?
89+
// * none() simplifies generation, as we can append `or ...` without a special case for the first item
90+
none()
91+
{{#classes}}
92+
{{#final}}
93+
or
94+
result = getImmediateChildOf{{name}}(e, index)
95+
{{/final}}
96+
{{/classes}}
97+
}
3798
}

misc/codegen/templates/ql_parent.mustache

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ private module Impl {
2323
{{! for single and optional properties it adds 1 (regardless of whether the optional property exists) }}
2424
{{! for repeated it adds 1 + the maximum index (which works for repeated optional as well) }}
2525
and
26-
n{{singular}} = n{{prev}} + 1{{#is_repeated}}+ max(int i | i = -1 or exists(e.get{{#type_is_hideable}}Immediate{{/type_is_hideable}}{{singular}}(i)) | i){{/is_repeated}}
26+
n{{singular}} = n{{prev}} {{^is_repeated}}+ 1{{/is_repeated}}{{#is_repeated}}+ {{#type_is_hideable}}max(int i | i = 0 or exists(e.getImmediate{{singular}}(i)) | i){{/type_is_hideable}}{{^type_is_hideable}}e.getNumberOf{{plural}}(){{/type_is_hideable}}{{/is_repeated}}
2727
{{/property}}
2828
{{/all_children}} and (
2929
none()

misc/codegen/templates/ql_synth_types.mustache

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,9 +32,25 @@ module Synth {
3232
{{/root}}
3333
{{/non_final_classes}}
3434

35+
/**
36+
* INTERNAL: Do not use.
37+
*
38+
* Holds if `e` is synthetic, that is, `e` cannot be converted to a raw element.
39+
*/
40+
predicate isSynth(T{{root}} e) {
41+
none()
42+
{{#final_classes}}
43+
{{#is_fresh_synth}}
44+
or
45+
e instanceof T{{name}}
46+
{{/is_fresh_synth}}
47+
{{/final_classes}}
48+
}
49+
3550
{{#final_classes}}
3651
/**
3752
* INTERNAL: Do not use.
53+
*
3854
* Converts a raw element to a synthesized `T{{name}}`, if possible.
3955
*/
4056
T{{name}} convert{{name}}FromRaw(Raw::Element e) {

0 commit comments

Comments
 (0)