diff --git a/bin/run_examples.sh b/bin/run_examples.sh index 22f2f8a..0c9a82e 100755 --- a/bin/run_examples.sh +++ b/bin/run_examples.sh @@ -8,6 +8,12 @@ root_path=$PWD build_path=$root_path/build examps=$root_path/examples +echo ~~~ Running Expression Intro ~~~ +$build_path/expr_intro.exe $examps/expr/expr_intro.mdesk +echo + +exit + # Setup a big list of files for a few of the examples big_list=() big_list+=("$examps/intro/hello_world.mdesk") @@ -27,10 +33,6 @@ echo ~~~ Running Error Generation Example ~~~ $build_path/user_errors.exe $examps/user_errors/user_errors.mdesk echo -echo ~~~ Running Expression Intro ~~~ -$build_path/expr_intro.exe $examps/expr/expr_intro.mdesk -echo - echo ~~~ Running C Like Expression ~~~ $build_path/expr_c_like.exe $examps/expr/expr_c_like.mdesk echo diff --git a/docs/metadesk_reference.mdesk b/docs/metadesk_reference.mdesk index 0fc3040..0bbd0e1 100644 --- a/docs/metadesk_reference.mdesk +++ b/docs/metadesk_reference.mdesk @@ -16,7 +16,7 @@ publish @def CodeLoc: {} @def StringGeneration: {} @def Map: {} -@def ExpressionParsingHelper: {} +@def ExpressionParser: {} @def CommandLineHelper: {} @def FileSystemHelper: {} @@ -58,8 +58,8 @@ main: @title "Map", @paste Map, - @title "Expression Parsing Helper", - @paste ExpressionParsingHelper, + @title "Expression Parser", + @paste ExpressionParser, @title "Command Line Helper", @paste CommandLineHelper, @@ -544,9 +544,68 @@ The @code node_count and @code total_size are automatically maintained by the he }; //////////////////////////////// -//~ Expression Parsing +//~ Expression Parser -// TODO(rjf): this API is not yet ready. +// TODO(allen): docs + +@send(ExpressionParser) +@enum MD_ExprOprKind: +{ + Null, + Prefix, + Postfix, + Binary, + BinaryRightAssociative, + COUNT, +}; + +@send(ExpressionParser) +@struct MD_ExprOpr: +{ + next: *MD_ExprOpr; + op_id: MD_u32; + kind: MD_ExprOprKind; + precedence: MD_u32; + string: MD_String8; + op_ptr: *void; +}; + +@send(ExpressionParser) +@struct MD_ExprOprList: +{ + first: *MD_ExprOpr; + last: *MD_ExprOpr; + count: MD_u64; +}; + +@send(ExpressionParser) +@struct MD_ExprOprTable: +{ + // opaque +}; + +@send(ExpressionParser) +@struct MD_Expr: +{ + parent: *MD_Expr; + left: *MD_Expr; + right: *MD_Expr; + op: *MD_ExprOpr; + md_node: *MD_Node; +}; + +@send(ExpressionParser) +@struct MD_ExprParseResult: +{ + expr: *MD_Expr; + errors: MD_MessageList; +}; + +@send(ExpressionParser) +@struct MD_ExprParseCtx: +{ + // opaque +}; //////////////////////////////// //~ String Generation Types @@ -2020,9 +2079,64 @@ MD_ParseWholeFile: } //////////////////////////////// -//~ Expression Parsing +//~ Expression Parser -// TODO +// TODO(allen): add docs + +@send(ExpressionParser) +@func MD_ExprOprPush: +{ +} + +@send(ExpressionParser) +@func MD_ExprBakeOprTableFromList: +{ +} + +@send(ExpressionParser) +@func MD_ExprOprFromKindString: +{ +} + +@send(ExpressionParser) +@func MD_ExprParse: +{ +} + +@send(ExpressionParser) +@func MD_Expr_NewLeaf: +{ +} + +@send(ExpressionParser) +@func MD_Expr_NewOpr: +{ +} + +@send(ExpressionParser) +@func MD_ExprParse_MakeContext: +{ +} + +@send(ExpressionParser) +@func MD_ExprParse_TopLevel: +{ +} + +@send(ExpressionParser) +@func MD_ExprParse_OprConsume: +{ +} + +@send(ExpressionParser) +@func MD_ExprParse_Atom: +{ +} + +@send(ExpressionParser) +@func MD_ExprParse_MinPrecedence: +{ +} //////////////////////////////// //~ Generation diff --git a/source/md.c b/source/md.c index f5b678e..bfb233e 100644 --- a/source/md.c +++ b/source/md.c @@ -3401,7 +3401,7 @@ MD_ExprSetBakeOperatorErrorHandler(MD_BakeOperatorErrorHandler handler){ } MD_FUNCTION MD_ExprOprTable -MD_ExprBakeOperatorTableFromList(MD_Arena *arena, MD_ExprOprList *list) +MD_ExprBakeOprTableFromList(MD_Arena *arena, MD_ExprOprList *list) { MD_ExprOprTable result = MD_ZERO_STRUCT; @@ -3486,7 +3486,7 @@ MD_ExprBakeOperatorTableFromList(MD_Arena *arena, MD_ExprOprList *list) // save error if(error_str.size != 0 && md_bake_operator_error_handler) { - md_bake_operator_error_handler(MD_MessageKind_Warning, error_str); + md_bake_operator_error_handler(MD_MessageKind_Warning, error_str); } // save list @@ -3558,7 +3558,7 @@ MD_Expr_NewLeaf(MD_Arena *arena, MD_Node *node) } MD_FUNCTION MD_Expr* -MD_Expr_NewOp(MD_Arena *arena, MD_ExprOpr *op, MD_Node *op_node, MD_Expr *l, MD_Expr *r) +MD_Expr_NewOpr(MD_Arena *arena, MD_ExprOpr *op, MD_Node *op_node, MD_Expr *l, MD_Expr *r) { MD_Expr *result = MD_PushArrayZero(arena, MD_Expr, 1); result->op = op; @@ -3694,7 +3694,7 @@ MD_ExprParse_Atom(MD_Arena *arena, MD_ExprParseCtx *ctx, MD_Node **iter, MD_ExprParse_MinPrecedence(arena, ctx, iter, first, opl, min_precedence); if(ctx->errors.max_message_kind == MD_MessageKind_Null) { - result = MD_Expr_NewOp(arena, op, node, sub_expr, 0); + result = MD_Expr_NewOpr(arena, op, node, sub_expr, 0); } } else if(MD_ExprParse_OprConsume(ctx, iter, opl, MD_ExprOprKind_Null, 1, &op)) diff --git a/source/md.h b/source/md.h index b8428a9..3a4425e 100644 --- a/source/md.h +++ b/source/md.h @@ -828,7 +828,6 @@ struct MD_ExprParseCtx } accel; #undef MD_POSTFIX_SETLIKE_OP_COUNT - // TODO(allen): different message list type here MD_MessageList errors; }; @@ -1157,8 +1156,8 @@ MD_FUNCTION void MD_ExprOprPush(MD_Arena *arena, MD_ExprOprList *l MD_String8 op_string, MD_u32 op_id, void *op_ptr); -MD_FUNCTION MD_ExprOprTable MD_ExprBakeOperatorTableFromList(MD_Arena *arena, - MD_ExprOprList *list); +MD_FUNCTION MD_ExprOprTable MD_ExprBakeOprTableFromList(MD_Arena *arena, + MD_ExprOprList *list); MD_FUNCTION MD_ExprOpr* MD_ExprOprFromKindString(MD_ExprOprTable *table, MD_ExprOprKind kind, MD_String8 s); @@ -1166,8 +1165,8 @@ MD_FUNCTION MD_ExprParseResult MD_ExprParse(MD_Arena *arena, MD_ExprOprTable *op MD_Node *first, MD_Node *one_past_last); MD_FUNCTION MD_Expr* MD_Expr_NewLeaf(MD_Arena *arena, MD_Node *node); -MD_FUNCTION MD_Expr* MD_Expr_NewOp(MD_Arena *arena, MD_ExprOpr *op, MD_Node *op_node, - MD_Expr *left, MD_Expr *right); +MD_FUNCTION MD_Expr* MD_Expr_NewOpr(MD_Arena *arena, MD_ExprOpr *op, MD_Node *op_node, + MD_Expr *left, MD_Expr *right); MD_FUNCTION MD_ExprParseCtx MD_ExprParse_MakeContext(MD_ExprOprTable *table); diff --git a/tests/expression_tests.c b/tests/expression_tests.c index b691cd1..00d645f 100644 --- a/tests/expression_tests.c +++ b/tests/expression_tests.c @@ -263,7 +263,7 @@ operator_array[Op_##name].op = (MD_ExprOpr){ .op_id = Op_##name, .kind = MD_Expr MD_Node *cast_node = MD_MakeNode(arena, MD_NodeKind_Main, cast, cast, 0); MD_Node *minus_node = MD_MakeNode(arena, MD_NodeKind_Main, minus, minus, 0); MD_Node *plus_node_bis = MD_MakeNode(arena, MD_NodeKind_Main, plus, plus, 0); - + MD_ExprSetBakeOperatorErrorHandler(bake_operator_error_handler); // NOTE: Wrong operator kind @@ -271,7 +271,7 @@ operator_array[Op_##name].op = (MD_ExprOpr){ .op_id = Op_##name, .kind = MD_Expr operator_list = (MD_ExprOprList){0}; MD_ExprOprPush(arena, &operator_list, MD_ExprOprKind_Null, 1, MD_S8Lit("+"), Op_Addition, plus_node); - op_table = MD_ExprBakeOperatorTableFromList(arena, &operator_list); + op_table = MD_ExprBakeOprTableFromList(arena, &operator_list); MD_Assert(global_max_message_kind == MD_MessageKind_Warning && global_message_list.node_count == 1); @@ -280,7 +280,7 @@ operator_array[Op_##name].op = (MD_ExprOpr){ .op_id = Op_##name, .kind = MD_Expr reset_global_messages(); MD_ExprOprPush(arena, &operator_list, MD_ExprOprKind_Prefix, 1, MD_S8Lit("()"), 23 /* arbitrary MD_ExprOprKind */, cast_node); - op_table = MD_ExprBakeOperatorTableFromList(arena, &operator_list); + op_table = MD_ExprBakeOprTableFromList(arena, &operator_list); MD_Assert(global_max_message_kind == MD_MessageKind_Warning && global_message_list.node_count == 1); @@ -291,7 +291,7 @@ operator_array[Op_##name].op = (MD_ExprOpr){ .op_id = Op_##name, .kind = MD_Expr Op_Addition, plus_node); MD_ExprOprPush(arena, &operator_list, MD_ExprOprKind_Binary, 1, MD_S8Lit("+"), Op_Addition, plus_node_bis); - op_table = MD_ExprBakeOperatorTableFromList(arena, &operator_list); + op_table = MD_ExprBakeOprTableFromList(arena, &operator_list); MD_Assert(global_max_message_kind == MD_MessageKind_Warning && global_message_list.node_count == 1); @@ -302,7 +302,7 @@ operator_array[Op_##name].op = (MD_ExprOpr){ .op_id = Op_##name, .kind = MD_Expr Op_Addition, plus_node); MD_ExprOprPush(arena, &operator_list, MD_ExprOprKind_Postfix, 1, MD_S8Lit("+"), Op_Addition, plus_node_bis); - op_table = MD_ExprBakeOperatorTableFromList(arena, &operator_list); + op_table = MD_ExprBakeOprTableFromList(arena, &operator_list); MD_Assert(global_max_message_kind == MD_MessageKind_Warning && global_message_list.node_count == 1); @@ -313,7 +313,7 @@ operator_array[Op_##name].op = (MD_ExprOpr){ .op_id = Op_##name, .kind = MD_Expr Op_Addition, plus_node); MD_ExprOprPush(arena, &operator_list, MD_ExprOprKind_BinaryRightAssociative, 1, MD_S8Lit("-"), Op_Addition, minus_node); - op_table = MD_ExprBakeOperatorTableFromList(arena, &operator_list); + op_table = MD_ExprBakeOprTableFromList(arena, &operator_list); MD_Assert(global_max_message_kind == MD_MessageKind_Warning && global_message_list.node_count == 1); @@ -322,7 +322,7 @@ operator_array[Op_##name].op = (MD_ExprOpr){ .op_id = Op_##name, .kind = MD_Expr operator_list = (MD_ExprOprList){0}; MD_ExprOprPush(arena, &operator_list, MD_ExprOprKind_Prefix, 1, MD_S8Lit("+ +"), 23 /* arbitrary MD_ExprOprKind */, plus_node); - op_table = MD_ExprBakeOperatorTableFromList(arena, &operator_list); + op_table = MD_ExprBakeOprTableFromList(arena, &operator_list); MD_Assert(global_max_message_kind == MD_MessageKind_Warning && global_message_list.node_count == 1); @@ -331,7 +331,7 @@ operator_array[Op_##name].op = (MD_ExprOpr){ .op_id = Op_##name, .kind = MD_Expr operator_list = (MD_ExprOprList){0}; MD_ExprOprPush(arena, &operator_list, MD_ExprOprKind_Prefix, 1, MD_S8Lit("123"), 23 /* arbitrary MD_ExprOprKind */, plus_node); - op_table = MD_ExprBakeOperatorTableFromList(arena, &operator_list); + op_table = MD_ExprBakeOprTableFromList(arena, &operator_list); MD_Assert(global_max_message_kind == MD_MessageKind_Warning && global_message_list.node_count == 1); } @@ -346,7 +346,7 @@ operator_array[Op_##name].op = (MD_ExprOpr){ .op_id = Op_##name, .kind = MD_Expr op, node); } - MD_ExprOprTable op_table = MD_ExprBakeOperatorTableFromList(arena, &operator_list); + MD_ExprOprTable op_table = MD_ExprBakeOprTableFromList(arena, &operator_list); // NOTE(mal): I'm trying something different for expression parser tests. Normally one would take the // output of MD_ExprParse and compare it against the expected output expression tree.