Support more complex function return types

This commit is contained in:
Doyle 2019-02-26 23:23:43 +11:00
parent a325ea6130
commit f2cbbc3a8c
3 changed files with 130 additions and 74 deletions

View File

@ -951,16 +951,82 @@ b32 ConsumeConstIdentifier(CPPTokeniser *tokeniser)
b32 result = false; b32 result = false;
for (CPPToken peek_token = CPPTokeniser_PeekToken(tokeniser); for (CPPToken peek_token = CPPTokeniser_PeekToken(tokeniser);
IsIdentifierToken(peek_token, STR_LITERAL("const")); IsIdentifierToken(peek_token, STR_LITERAL("const"));
) peek_token = CPPTokeniser_PeekToken(tokeniser))
{ {
result = true; result = true;
CPPTokeniser_NextToken(tokeniser); CPPTokeniser_NextToken(tokeniser);
peek_token = CPPTokeniser_PeekToken(tokeniser);
} }
return result; return result;
} }
b32 ParseCPPVariableType(CPPTokeniser *tokeniser, StringLiteral *type)
{
CPPToken token = CPPTokeniser_NextToken(tokeniser);
if (!ExpectToken(token, CPPTokenType::Identifier))
return false;
char *var_type_start = token.str;
ConsumeConstIdentifier(tokeniser);
//
// Parse Template If Any
//
StringLiteral template_expr = {};
{
CPPToken peek_token = CPPTokeniser_PeekToken(tokeniser);
if (peek_token.type == CPPTokenType::LessThan)
{
token = CPPTokeniser_NextToken(tokeniser);
int template_depth = 1;
while (template_depth != 0 && token.type != CPPTokenType::EndOfStream)
{
token = CPPTokeniser_NextToken(tokeniser);
if (token.type == CPPTokenType::LessThan)
template_depth++;
else if (token.type == CPPTokenType::GreaterThan)
template_depth--;
}
if (template_depth == 0)
{
char *expr_start = peek_token.str + 1;
char *expr_end = token.str - 1;
int expr_len = static_cast<int>(expr_end - expr_start);
template_expr.str = expr_start;
template_expr.len = expr_len;
}
}
}
int total_asterisks_count = ConsumeAsterisks(tokeniser);
if (ConsumeConstIdentifier(tokeniser))
{
total_asterisks_count += ConsumeAsterisks(tokeniser);
ConsumeConstIdentifier(tokeniser);
}
CPPToken var_name = CPPTokeniser_PeekToken(tokeniser);
if (!ExpectToken(var_name, CPPTokenType::Identifier))
return false;
char *var_type_end = var_name.str;
if (type)
{
type->str = var_type_start;
type->len = static_cast<int>(var_type_end - var_type_start);
// NOTE(doyle): Remove space(s) at the end of the return type if
// any, because we parse the function type weirdly by getting the
// identifier for the function name and looking one token back.
while (type->len >= 1 && CharIsWhitespace(type->str[type->len - 1]))
type->len--;
}
return true;
};
// NOTE(doyle): Doesn't parse the ending semicolon so we can reuse this function for parsing function arguments // NOTE(doyle): Doesn't parse the ending semicolon so we can reuse this function for parsing function arguments
CPPDeclLinkedList<CPPVariableDecl> *ParseCPPTypeAndVariableDecl(CPPTokeniser *tokeniser, b32 parse_function_param) CPPDeclLinkedList<CPPVariableDecl> *ParseCPPTypeAndVariableDecl(CPPTokeniser *tokeniser, b32 parse_function_param)
{ {
@ -1205,15 +1271,6 @@ void ParseCPPStruct(CPPTokeniser *tokeniser)
tokeniser->indent_level--; tokeniser->indent_level--;
CPPTokeniser_SprintfToFile(tokeniser, "}\n\n"); CPPTokeniser_SprintfToFile(tokeniser, "}\n\n");
} }
//
// Write User Annotated Metadata Getter Functions
//
{
}
int break_here = 5;
(void)break_here;
} }
void SkipFunctionParam(CPPTokeniser *tokeniser) void SkipFunctionParam(CPPTokeniser *tokeniser)
@ -1310,21 +1367,25 @@ void ParseCPPInspectPrototype(CPPTokeniser *tokeniser)
// Grab return type token // Grab return type token
{ {
token = CPPTokeniser_PeekToken(tokeniser); token = CPPTokeniser_PeekToken(tokeniser);
if (!ExpectToken(token, CPPTokenType::Identifier)) if (!ExpectToken(token, CPPTokenType::Identifier)) return;
return; if (!ParseCPPVariableType(tokeniser, &return_type)) return;
token = CPPTokeniser_NextToken(tokeniser);
return_type = StringLiteral(token.str, token.len);
} }
// Grab function name token // Grab function name token
{ {
token = CPPTokeniser_PeekToken(tokeniser); token = CPPTokeniser_PeekToken(tokeniser);
if (!ExpectToken(token, CPPTokenType::Identifier)) if (!ExpectToken(token, CPPTokenType::Identifier)) return;
return;
token = CPPTokeniser_NextToken(tokeniser); char *name_start = token.str;
function_name = StringLiteral(token.str, token.len); while (token.type != CPPTokenType::OpenParen && token.type != CPPTokenType::EndOfStream)
{
CPPTokeniser_NextToken(tokeniser);
token = CPPTokeniser_PeekToken(tokeniser);
}
if (!ExpectToken(token, CPPTokenType::OpenParen)) return;
char *name_end = token.str;
function_name = StringLiteral(name_start, static_cast<int>(name_end - name_start));
} }
token = CPPTokeniser_PeekToken(tokeniser); token = CPPTokeniser_PeekToken(tokeniser);
@ -1369,15 +1430,22 @@ void ParseCPPInspectPrototype(CPPTokeniser *tokeniser)
} }
} }
if (return_type.str[return_type.len-1] == '*') // NOTE(doyle): Align the pointer to the name
CPPTokeniser_SprintfToFile(tokeniser, "%.*s%.*s(", return_type.len, return_type.str, function_name.len, function_name.str);
else
CPPTokeniser_SprintfToFile(tokeniser, "%.*s %.*s(", return_type.len, return_type.str, function_name.len, function_name.str); CPPTokeniser_SprintfToFile(tokeniser, "%.*s %.*s(", return_type.len, return_type.str, function_name.len, function_name.str);
for (CPPDeclLinkedList<CPPVariableDecl> const *param_link = param_list; param_link; param_link = param_link->next)
for (CPPDeclLinkedList<CPPVariableDecl> *param_link = param_list; param_link; param_link = param_link->next)
{ {
// TODO(doyle): HACK. We should parse ptrs into the CPPVariableDecl, fixed size arrays into the name and const-ness into the type // TODO(doyle): HACK. We should parse ptrs into the CPPVariableDecl, fixed size arrays into the name and const-ness into the type
CPPVariableDecl const *decl = &param_link->value; CPPVariableDecl *decl = &param_link->value;
StringLiteral *type = &decl->type;
StringLiteral *name = &decl->name;
char *name_start = type->str + (type->len + 1);
char *name_end = name->str + name->len;
auto hack_decl_name = StringLiteral(name_start, static_cast<int>(name_end - name_start));
char *name_start = decl->type.str + (decl->type.len + 1);
char *name_end = decl->name.str + decl->name.len;
StringLiteral hack_decl_name = StringLiteral(name_start, static_cast<int>(name_end - name_start));
CPPTokeniser_SprintfToFileNoIndenting(tokeniser, "%.*s %.*s", decl->type.len, decl->type.str, hack_decl_name.len, hack_decl_name.str); CPPTokeniser_SprintfToFileNoIndenting(tokeniser, "%.*s %.*s", decl->type.len, decl->type.str, hack_decl_name.len, hack_decl_name.str);
if (decl->default_value.len > 0) if (decl->default_value.len > 0)
CPPTokeniser_SprintfToFileNoIndenting(tokeniser, " = %.*s", decl->default_value.len, decl->default_value.str); CPPTokeniser_SprintfToFileNoIndenting(tokeniser, " = %.*s", decl->default_value.len, decl->default_value.str);

View File

@ -1,29 +1,16 @@
DQN_INSPECT enum struct OpenGLShader DQN_INSPECT enum struct EnumWithMetadata
{ {
Invalid, Rect DQN_INSPECT_META(FilePath = "Rect.vert", FilePath2 = "Rect.frag"),
Rect DQN_INSPECT_META(VertexShaderFilePath = "Rect.vert", FragmentShaderFilePath = "Rect.frag"),
Text DQN_INSPECT_META(VertexShaderFilePath = "Text.vert", FragmentShaderFilePath = "Text.frag"),
Count, Count,
}; };
#if 0
#define EXAMPLE_MACRO \
X(EndOfStream, "End Of Stream") \
X(Hash, "#")
#define MAXIMUM_MACRO(a, b) (a > b) ? (a) : (b)
#endif
struct V3 { float test; }; struct V3 { float test; };
struct V4 { float test; }; struct V4 { float test; };
template <typename T, int Size> template <typename T, int Size>
struct Array struct Array { T data[Size]; };
{
T data[Size];
};
DQN_INSPECT struct OpenGLState DQN_INSPECT struct SampleStruct
{ {
// #if 0 // #if 0
// #endif // #endif
@ -46,8 +33,11 @@ DQN_INSPECT struct OpenGLState
int *********const j, k, ******l, *m; int *********const j, k, ******l, *m;
}; };
DQN_INSPECT_GENERATE_PROTOTYPE(texture = nullptr, size = {}, depth_test = false, type = 1, user_msg = "Hello world") DQN_INSPECT_GENERATE_PROTOTYPE(b = {}, c = nullptr, e = false, f = 1, g = "Hello world")
void RenderRect(V3 pos, V2 size, char const *texture, bool depth_test, int type, char *user_msg) void Function1(int a, float b, char const *c, bool e, int f, char *g) { }
{
(void)pos; void(size); (void)texture; (void)depth_test; DQN_INSPECT_GENERATE_PROTOTYPE()
} void *Function2() { }
DQN_INSPECT_GENERATE_PROTOTYPE()
Array<int const *, 3> const *const Function3() { }

View File

@ -7,32 +7,28 @@
#ifndef DQN_INSPECT_DQNINSPECT_TESTDATA_H #ifndef DQN_INSPECT_DQNINSPECT_TESTDATA_H
#define DQN_INSPECT_DQNINSPECT_TESTDATA_H #define DQN_INSPECT_DQNINSPECT_TESTDATA_H
char const *DqnInspect_OpenGLShader_Strings[] = {"Invalid", "Rect", "Text", "Count", }; char const *DqnInspect_EnumWithMetadata_Strings[] = {"Rect", "Count", };
char const *DqnInspect_EnumString(OpenGLShader val) char const *DqnInspect_EnumString(EnumWithMetadata val)
{ {
if (val == OpenGLShader::Invalid) return DqnInspect_OpenGLShader_Strings[0]; // "Invalid" if (val == EnumWithMetadata::Rect) return DqnInspect_EnumWithMetadata_Strings[0]; // "Rect"
if (val == OpenGLShader::Rect) return DqnInspect_OpenGLShader_Strings[1]; // "Rect" if (val == EnumWithMetadata::Count) return DqnInspect_EnumWithMetadata_Strings[1]; // "Count"
if (val == OpenGLShader::Text) return DqnInspect_OpenGLShader_Strings[2]; // "Text"
if (val == OpenGLShader::Count) return DqnInspect_OpenGLShader_Strings[3]; // "Count"
return nullptr; return nullptr;
} }
char const *DqnInspect_VertexShaderFilePathMetadata(OpenGLShader val) char const *DqnInspect_FilePathMetadata(EnumWithMetadata val)
{ {
if (val == OpenGLShader::Rect) return "Rect.vert"; if (val == EnumWithMetadata::Rect) return "Rect.vert";
if (val == OpenGLShader::Text) return "Text.vert";
return nullptr; return nullptr;
} }
char const *DqnInspect_FragmentShaderFilePathMetadata(OpenGLShader val) char const *DqnInspect_FilePath2Metadata(EnumWithMetadata val)
{ {
if (val == OpenGLShader::Rect) return "Rect.frag"; if (val == EnumWithMetadata::Rect) return "Rect.frag";
if (val == OpenGLShader::Text) return "Text.frag";
return nullptr; return nullptr;
} }
DqnInspect_StructMemberMetadata const DqnInspect_OpenGLState_ebo_StructMemberMetadata[] = DqnInspect_StructMemberMetadata const DqnInspect_SampleStruct_ebo_StructMemberMetadata[] =
{ {
{ {
DqnInspect_StructMemberMetadataType::String, DqnInspect_StructMemberMetadataType::String,
@ -40,7 +36,7 @@ DqnInspect_StructMemberMetadata const DqnInspect_OpenGLState_ebo_StructMemberMet
}, },
}; };
DqnInspect_StructMemberMetadata const DqnInspect_OpenGLState_vao_StructMemberMetadata[] = DqnInspect_StructMemberMetadata const DqnInspect_SampleStruct_vao_StructMemberMetadata[] =
{ {
{ {
DqnInspect_StructMemberMetadataType::String, DqnInspect_StructMemberMetadataType::String,
@ -52,7 +48,7 @@ DqnInspect_StructMemberMetadata const DqnInspect_OpenGLState_vao_StructMemberMet
}, },
}; };
DqnInspect_StructMemberMetadata const DqnInspect_OpenGLState_draw_color_StructMemberMetadata[] = DqnInspect_StructMemberMetadata const DqnInspect_SampleStruct_draw_color_StructMemberMetadata[] =
{ {
{ {
DqnInspect_StructMemberMetadataType::String, DqnInspect_StructMemberMetadataType::String,
@ -60,7 +56,7 @@ DqnInspect_StructMemberMetadata const DqnInspect_OpenGLState_draw_color_StructMe
}, },
}; };
DqnInspect_StructMember const DqnInspect_OpenGLState_StructMembers[] = DqnInspect_StructMember const DqnInspect_SampleStruct_StructMembers[] =
{ {
{ {
STR_AND_LEN("Array"), STR_AND_LEN("lights"), STR_AND_LEN("Array"), STR_AND_LEN("lights"),
@ -95,7 +91,7 @@ DqnInspect_StructMember const DqnInspect_OpenGLState_StructMembers[] =
{ {
STR_AND_LEN("int"), STR_AND_LEN("ebo"), STR_AND_LEN("int"), STR_AND_LEN("ebo"),
nullptr, 0, // template_expr and template_expr_len nullptr, 0, // template_expr and template_expr_len
DqnInspect_OpenGLState_ebo_StructMemberMetadata, 1, DqnInspect_SampleStruct_ebo_StructMemberMetadata, 1,
0 // array_dimensions 0 // array_dimensions
}, },
{ {
@ -107,13 +103,13 @@ DqnInspect_StructMember const DqnInspect_OpenGLState_StructMembers[] =
{ {
STR_AND_LEN("int"), STR_AND_LEN("vao"), STR_AND_LEN("int"), STR_AND_LEN("vao"),
nullptr, 0, // template_expr and template_expr_len nullptr, 0, // template_expr and template_expr_len
DqnInspect_OpenGLState_vao_StructMemberMetadata, 2, DqnInspect_SampleStruct_vao_StructMemberMetadata, 2,
0 // array_dimensions 0 // array_dimensions
}, },
{ {
STR_AND_LEN("V4"), STR_AND_LEN("draw_color"), STR_AND_LEN("V4"), STR_AND_LEN("draw_color"),
nullptr, 0, // template_expr and template_expr_len nullptr, 0, // template_expr and template_expr_len
DqnInspect_OpenGLState_draw_color_StructMemberMetadata, 1, DqnInspect_SampleStruct_draw_color_StructMemberMetadata, 1,
0 // array_dimensions 0 // array_dimensions
}, },
{ {
@ -214,21 +210,23 @@ DqnInspect_StructMember const DqnInspect_OpenGLState_StructMembers[] =
}, },
}; };
DqnInspect_Struct const DqnInspect_OpenGLState_Struct = DqnInspect_Struct const DqnInspect_SampleStruct_Struct =
{ {
STR_AND_LEN("OpenGLState"), STR_AND_LEN("SampleStruct"),
DqnInspect_OpenGLState_StructMembers, // members DqnInspect_SampleStruct_StructMembers, // members
ARRAY_COUNT(DqnInspect_OpenGLState_StructMembers) // members_len ARRAY_COUNT(DqnInspect_SampleStruct_StructMembers) // members_len
}; };
DqnInspect_Struct const *DqnInspect_GetStruct(OpenGLState const *val) DqnInspect_Struct const *DqnInspect_GetStruct(SampleStruct const *val)
{ {
(void)val; (void)val;
DqnInspect_Struct const *result = &DqnInspect_OpenGLState_Struct; DqnInspect_Struct const *result = &DqnInspect_SampleStruct_Struct;
return result; return result;
} }
void RenderRect(V3 pos, V2 size = {}, char const *texture = nullptr, bool depth_test = false, int type = 1, char *user_msg = "Hello world"); void Function1(int a, float b = {}, char const *c = nullptr, bool e = false, int f = 1, char *g = "Hello world");
void *Function2();
Array<int const *, 3> const *const Function3();
#endif // DQN_INSPECT_DQNINSPECT_TESTDATA_H #endif // DQN_INSPECT_DQNINSPECT_TESTDATA_H