6#include <clang-c/CXString.h>
7#include <clang-c/Index.h>
13#include <util/emitx.h>
14#include <util/is_kernel.h>
17#include <attr/storage_class.h>
19#include <ae2f/c90/StdBool.h>
20#include <spirv/unified1/spirv.h>
22static enum CXChildVisitResult emit_count_fn_wrdgroup_attr(CXCursor h_cur, CXCursor h_parent, CXClientData wr_data) {
26 ATTR_KIND = clang_getCursorSpelling(h_cur);
27 if((NIDDLE = strstr(ATTR_KIND.data,
"reqd_work_group_size"))) {
28 sscanf(NIDDLE,
"reqd_work_group_size ( %u , %u , %u )"
34 clang_disposeString(ATTR_KIND);
35 return CXChildVisit_Break;
36 }
else if ((NIDDLE = strstr(ATTR_KIND.data,
"aclspv_wrkgroup_size"))) {
37 sscanf(NIDDLE,
"aclspv_wrkgroup_size ( %u , %u , %u )"
43 clang_disposeString(ATTR_KIND);
44 return CXChildVisit_Break;
47 clang_disposeString(ATTR_KIND);
48 return CXChildVisit_Recurse;
52static enum CXChildVisitResult emit_count_fn_execmodel_attr(CXCursor h_cur, CXCursor h_parent, CXClientData wr_data) {
56 ATTR_KIND = clang_getCursorSpelling(h_cur);
57 if((NIDDLE = strstr(ATTR_KIND.data,
"aclspv_execmodel"))) {
58 sscanf(NIDDLE,
"aclspv_execmodel ( %u )"
62 clang_disposeString(ATTR_KIND);
63 return CXChildVisit_Break;
66 clang_disposeString(ATTR_KIND);
67 return CXChildVisit_Recurse;
71static enum CXChildVisitResult emit_iter_entry_point(CXCursor h_cur, CXCursor h_parent, CXClientData CTX) {
73 unless(h_cur.kind == CXCursor_CompoundStmt && h_parent.kind == CXCursor_FunctionDecl)
74 return CXChildVisit_Recurse;
76 if(util_is_kernel(h_parent)) {
77 const CXString NAME = clang_getCursorSpelling(h_parent);
78 unsigned XYZ[3] = { 1, 1, 1 };
79 unsigned EXEC_MODEL = SpvExecutionModelGLCompute;
83 CTX->m_err = ACLSPV_COMPILE_ALLOC_FAILED;
85 clang_visitChildren(h_parent, emit_count_fn_execmodel_attr, &EXEC_MODEL);
87 if(EXEC_MODEL == SpvExecutionModelGLCompute || EXEC_MODEL == SpvExecutionModelKernel)
88 clang_visitChildren(h_parent, emit_count_fn_wrdgroup_attr, XYZ);
91 int ARGC = clang_Cursor_getNumArguments(h_parent);
95 CXCursor ARG = clang_Cursor_getArgument(h_parent, (
unsigned)ARGI);
97 clang_visitChildren(ARG, attr_storage_class, &STORAGE);
99 if(STORAGE == SpvStorageClassInput || STORAGE == SpvStorageClassOutput) {
106#define THIS_ENTRY_POINT ((util_entp_t* ae2f_restrict)CTX->m_fnlist.m_entp.m_p)[CTX->m_tmp.m_w0]
118 &
CTX->m_section.m_entp
119 ,
CTX->m_count.m_entp
120 , SpvOpEntryPoint, 0)))
122 unless((
CTX->m_count.m_entp = util_emit_wrd(
123 &
CTX->m_section.m_entp
124 ,
CTX->m_count.m_entp
127 unless((
CTX->m_count.m_entp = util_emit_wrd(
128 &
CTX->m_section.m_entp
129 ,
CTX->m_count.m_entp
132 unless((
CTX->m_count.m_entp = util_emit_str(
133 &
CTX->m_section.m_entp
134 ,
CTX->m_count.m_entp
140 while(IO_IDX < IOCOUNT) {
141 unless((
CTX->m_count.m_entp = util_emit_wrd(
142 &
CTX->m_section.m_entp
143 ,
CTX->m_count.m_entp
152 ,
CTX->m_count.m_entp - POS - 1
156 if(EXEC_MODEL == SpvExecutionModelGLCompute || EXEC_MODEL == SpvExecutionModelKernel)
158 &
CTX->m_section.m_execmode
159 ,
CTX->m_count.m_execmode
162 , SpvExecutionModeLocalSize
163 , XYZ[0], XYZ[1], XYZ[2]
166#if !defined(NDEBUG) || !NDEBUG
167 POS =
CTX->m_count.m_name;
169 unless((
CTX->m_count.m_name = util_emit_wrd(&
CTX->m_section.m_name,
CTX->m_count.m_name
171 unless((
CTX->m_count.m_name = util_emit_str(&
CTX->m_section.m_name,
CTX->m_count.m_name, NAME.data)))
goto LBL_ABRT;
174 CTX->m_err = ACLSPV_COMPILE_OK;
177 clang_disposeString(NAME);
178 return CXChildVisit_Continue;
182 clang_disposeString(NAME);
183 return CXChildVisit_Break;
185#define THIS_FUNCTION ((util_fn_t* ae2f_restrict)CTX->m_fnlist.m_fn.m_p)[CTX->m_tmp.m_w1]
190#undef THIS_ENTRY_POINT
192 return CXChildVisit_Continue;
195static enum CXChildVisitResult emit_count_fn(CXCursor h_cur, CXCursor h_parent, CXClientData h_ctx) {
199 unless(h_cur.kind == CXCursor_CompoundStmt && h_parent.kind == CXCursor_FunctionDecl)
200 return CXChildVisit_Recurse;
202 if(util_is_kernel(h_parent)) {
203 ++
CTX->m_fnlist.m_num_entp;
205 ++
CTX->m_fnlist.m_num_fn;
208 return CXChildVisit_Continue;
#define ae2f_WhenCXX(a)
Appears when the current language is C.
#define ae2f_WhenC(a)
Appears when the current language is C++.
#define unless(a)
Invokes when condition is false.
#define ae2f_extern
Suggests the existence of external variable or function, in naming of C. [non-mangling].
#define ACLSPV_ABI_DECL
Declaration as ABI.
#define ae2f_assume(a)
tells the compiler that value if a is false, below this keyword is not expected to be reached.
#define ae2f_unexpected_but_if(a)
#define ae2f_ccpure
Keyword as [[pure]] on C23.
#define ae2f_expected_but_else(a)
#define ae2f_expected_if(a)
#define ae2f_ccconst
Keyword as [[const]] on C23..
#define ae2f_noexcept
marker that this function does not throw something.
#define ae2f_restrict
Keyword as restrict on C99.
#define ae2f_expected_not(a)
expectes a as false.
#define ae2f_unreachable()
tells the compiler that below this keyword is not expected to be reached.
#define ae2f_inline
inline
#define ae2f_expected(a)
expectes a as true.
#define util_emitx_type_pointer(h_wrds, c_wrdcount, c_retid, c_storage_class, c_elm_type_id)
#define get_buf_from_scale(h_alloc, c_scale)
#define aclspv_opcode_t
integer as operation code
aclspv_wrd_t aclspv_wrdcount_t
the integer type represents the number of word.
#define ACLSPV_MASK_OPCODE
mask for opcode
#define aclspv_wrd_t
integer as word
#define ACLSPV_MASK_NOPRNDS
mask for number of operands
x_aclspv_vec m_scale_vars
aclspv_wrdcount_t m_num_type_uniques
x_aclspv_vec m_cursors
cache for cursors for parsing one function for its use see util/cursor.h
x_aclspv_vec m_constant_cache
x_aclspv_vec m_ret
word count for m_ret
aclspv_wrd_t m_is_logical
when on, ignores m_is_buffer_64.
aclspv_wrdcount_t m_num_cursor
number of m_cursors. for its use see util/cursor.h
x_aclspv_vec m_type_uniques
cache for complex types which needs to be stored somewhere for its use see util/type_unique....
util_bind_unified m_unified
#define mk_noprnds(c_num_opprm)
#define emit_opcode(h_wrds, c_wrdcount, c_opcode, c_num_opprm_opt)
try emit opcode with num_opprm
#define sz_to_count(c_sz)
byte size to word count
#define get_wrd_of_vec(vec)
get word buffer from vector
aclspv_wrdcount_t spvsz_t
#define count_to_sz(c_count)
word count to byte size
#define set_oprnd_count_for_opcode(cr_wrd, c_num_opprm)
#define opcode_to_wrd(c_opcode, c_num_opprm)