Skip to content

Commit

Permalink
Many IR generation fixes
Browse files Browse the repository at this point in the history
- Corrected struct declarations
- Corrected function names
- Corrected function declarations
- Other fixes
  • Loading branch information
muit committed Feb 4, 2024
1 parent 369a3ca commit 7924ed5
Show file tree
Hide file tree
Showing 11 changed files with 105 additions and 41 deletions.
4 changes: 2 additions & 2 deletions Examples/Project/Welcome.rf
Original file line number Diff line number Diff line change
Expand Up @@ -166,8 +166,8 @@
"CNamespace": {
"0": "Welcome",
"1": "Print",
"10": "class",
"11": "struct"
"10": "in1",
"11": "in2"
},
"CParent": {
"0": [
Expand Down
2 changes: 1 addition & 1 deletion Extern/Pipe
2 changes: 1 addition & 1 deletion Libs/AST/Include/AST/Components/CNamespace.h
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@ namespace rift::ast
bool IsEmpty() const;
p::i32 Size() const;
bool Contains(const Namespace& other) const;
p::String ToString(bool isLocal = false) const;
p::String ToString(bool isLocal = false, char separator = '.') const;
p::Tag& First()
{
return scopes[0];
Expand Down
4 changes: 2 additions & 2 deletions Libs/AST/Include/AST/Utils/Namespaces.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,8 @@ namespace rift::ast

p::Tag GetName(p::TAccessRef<CNamespace> access, Id id);
p::Tag GetNameUnsafe(p::TAccessRef<CNamespace> access, Id id);
p::String GetFullName(
p::TAccessRef<CNamespace, CChild, CModule> access, Id id, bool localNamespace = false);
p::String GetFullName(p::TAccessRef<CNamespace, CChild, CModule> access, Id id,
bool localNamespace = false, char separator = '.');
} // namespace rift::ast


Expand Down
1 change: 1 addition & 0 deletions Libs/AST/Include/Compiler/CompilerConfig.h
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ namespace rift

OptimizationLevel optimization = OptimizationLevel::Two;

bool debug = true;
bool verbose = false;

Path buildPath;
Expand Down
12 changes: 8 additions & 4 deletions Libs/AST/Src/AST/Components/CNamespace.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -69,19 +69,23 @@ namespace rift::ast
return size;
}

p::String Namespace::ToString(bool isLocal) const
p::String Namespace::ToString(bool isLocal, char separator) const
{
p::String ns;
if (!isLocal)
{
ns.append("@");
const p::Tag firstScope = scopes[0];
if (!firstScope.IsNone())
{
ns.append(firstScope.AsString());
ns.append(".");
ns.push_back(separator);
}
}
else
{
ns.push_back('#');
}

for (p::i32 i = 1; i < scopeCount; ++i)
{
const p::Tag scope = scopes[i];
Expand All @@ -90,7 +94,7 @@ namespace rift::ast
break;
}
ns.append(scope.AsString());
ns.append(".");
ns.push_back(separator);
}

if (!ns.empty()) // Remove last dot
Expand Down
4 changes: 2 additions & 2 deletions Libs/AST/Src/AST/Utils/Namespaces.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -106,9 +106,9 @@ namespace rift::ast
}

p::String GetFullName(
TAccessRef<CNamespace, CChild, CModule> access, Id id, bool localNamespace)
TAccessRef<CNamespace, CChild, CModule> access, Id id, bool localNamespace, char separator)
{
return GetNamespace(access, id).ToString(localNamespace);
return GetNamespace(access, id).ToString(localNamespace, separator);
}

} // namespace rift::ast
58 changes: 48 additions & 10 deletions Libs/Backends/MIR/Compiler/Src/C2MIR.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -11,27 +11,65 @@ extern "C"

namespace rift::MIR
{
void InitCToMIROptions(c2mir_options& options)
struct OptionsData
{
int inclP, ldirP = FALSE; /* to remove an uninitialized warning */
TArray<const char*> headers;
TArray<c2mir_macro_command> definitions;
};

options.message_file = stderr;
options.debug_p = options.verbose_p = options.ignore_warnings_p = FALSE;
options.asm_p = options.object_p = options.no_prepro_p = options.prepro_only_p = FALSE;
options.syntax_only_p = options.pedantic_p = FALSE;
void InitCToMIROptions(
const CompilerConfig& config, OptionsData& optionsData, c2mir_options& options)
{
// Fill defaults
options.message_file = stderr;
options.debug_p = false;
options.verbose_p = false;
options.ignore_warnings_p = false;
options.no_prepro_p = false;
options.prepro_only_p = false;
options.syntax_only_p = false;
options.pedantic_p = false;
options.asm_p = false;
options.object_p = false;
options.module_num = 0;
options.prepro_output_file = nullptr;
options.output_file_name = nullptr;

options.macro_commands = nullptr;
options.macro_commands_num = 0;
options.macro_commands = nullptr;

options.include_dirs_num = 0;
options.include_dirs = nullptr;

// Fill from config
// options.debug_p = config.debug;
options.verbose_p = config.verbose;

if (options.output_file_name == nullptr && options.prepro_only_p)
{
options.prepro_output_file = stdout;
}

// TODO: Fill headers. No headers needed for now
// TODO: Fill definitions. No definitions needed for now

options.include_dirs_num = optionsData.headers.Size();
options.include_dirs = optionsData.headers.Data();
options.macro_commands_num = optionsData.definitions.Size();
options.macro_commands = optionsData.definitions.Data();
}

void CToMIR(Compiler& compiler, MIR_context* ctx)
{
c2mir_init(ctx);

auto moduleIds = p::FindAllIdsWith<ast::CModule>(compiler.ast);

OptionsData optionsData;
c2mir_options options;
InitCToMIROptions(options);
InitCToMIROptions(compiler.config, optionsData, options);

for (ast::Id moduleId : FindAllIdsWith<ast::CModule>(compiler.ast))
for (ast::Id moduleId : moduleIds)
{
p::Tag name = ast::GetModuleName(compiler.ast, moduleId);
auto& mirModule = compiler.ast.Get<CMIRModule>(moduleId);
Expand All @@ -46,7 +84,7 @@ namespace rift::MIR
{
auto getCode = [](void* data) -> p::i32 {
auto* codeLeft = static_cast<StringView*>(data);
if (codeLeft->size() > 0)
if (codeLeft->size() > -1)
{
*codeLeft = Strings::RemoveFromStart(*codeLeft, 1);
return *codeLeft->data();
Expand Down
50 changes: 33 additions & 17 deletions Libs/Backends/MIR/Compiler/Src/IRGeneration.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,19 @@

#include "IRGeneration.h"

#include "Pipe/Core/String.h"
#include "Pipe/Core/StringView.h"

#include <AST/Utils/ModuleUtils.h>
#include <AST/Utils/Namespaces.h>
#include <AST/Utils/Statements.h>
#include <Compiler/Compiler.h>
#include <Pipe/Core/String.h>
#include <Pipe/Core/StringView.h>


namespace rift::MIR
{
const p::TSet<p::Tag> CGenerator::reservedNames{"class", "struct"};


void GenerateC(Compiler& compiler)
{
MIRAccess access{compiler.ast};
Expand Down Expand Up @@ -163,20 +165,27 @@ namespace rift::MIR
const auto& var = access.Get<const ast::CDeclVariable>(memberId);

const Tag memberName = ast::GetName(access, memberId);
if (auto* irType = access.TryGet<const CMIRType>(var.typeId))
auto* irType = access.TryGet<const CMIRType>(var.typeId);
if (!irType) [[unlikely]]
{
Strings::FormatTo(membersCode, "{} {};\n", irType->value, memberName);
const Tag typeName = ast::GetName(access, id);
compiler.Error(Strings::Format(
"Variable '{}' in struct '{}' has an invalid type", memberName, typeName));
}
else
else if (reservedNames.Contains(memberName)) [[unlikely]]
{
const Tag typeName = ast::GetName(access, id);
compiler.Error(Strings::Format(
"Variable '{}' in struct '{}' has an invalid type", memberName, typeName));
"Variable name '{}' not allowed in struct '{}' ", memberName, typeName));
}
else
{
Strings::FormatTo(membersCode, "{} {};\n", irType->value, memberName);
}
}

const auto& type = access.Get<const CMIRType>(id);
Strings::FormatTo(*code, "typedef struct {0} {0} {{\n{1}}}\n", type.value, membersCode);
Strings::FormatTo(*code, "struct {0} {{\n{1}}};\n", type.value, membersCode);
}
code->push_back('\n');
}
Expand All @@ -190,7 +199,7 @@ namespace rift::MIR
auto& signature = access.Add<CMIRFunctionSignature>(id).value;

signature.append("void ");
const p::String name = useFullName ? ast::GetFullName(access, id)
const p::String name = useFullName ? ast::GetFullName(access, id, false, '_')
: p::String{ast::GetName(access, id).AsString()};
signature.append(name);
signature.push_back('(');
Expand All @@ -210,19 +219,26 @@ namespace rift::MIR
auto* exprId = access.TryGet<const ast::CExprTypeId>(inputId);
const auto* irType =
exprId ? access.TryGet<const CMIRType>(exprId->id) : nullptr;
if (irType) [[likely]]
{
Strings::FormatTo(signature, "{0} {1}, ", inputName, irType->value);
}
else
if (!irType) [[unlikely]]
{
const String functionName = ast::GetFullName(access, id);
compiler.Error(Strings::Format(
"Input '{}' in function '{}' has an invalid type. Using i32 instead.",
inputName, functionName));
}
else if (reservedNames.Contains(inputName)) [[unlikely]]
{
const String functionName = ast::GetFullName(access, id);
compiler.Error(
Strings::Format("Input name '{}' not allowed in function '{}' ",
inputName, functionName));
}
else
{
Strings::FormatTo(signature, "{0} {1}, ", irType->value, inputName);
}
}
Strings::RemoveCharFromEnd(signature, ',');
Strings::RemoveFromEnd(signature, ", ");
}
signature.push_back(')');

Expand Down Expand Up @@ -309,7 +325,7 @@ namespace rift::MIR
if (!Ensure(access.Has<const CMIRFunctionSignature>(functionId)))
{
compiler.Error(Strings::Format(
"Call to an invalid function: '{}'", ast::GetName(access, functionId)));
"Call to an invalid function: '{}'", ast::GetFullName(access, functionId)));
return;
}

Expand Down Expand Up @@ -343,7 +359,7 @@ namespace rift::MIR

// auto* customMainFunction = access.Get<const CIRFunction>(functionId).instance;

code->append("void main() {\nMain();\nreturn 0;\n}\n");
code->append("int main() {\nProject_Main_Main();\nreturn 0;\n}\n");
}

ast::Id CGenerator::FindMainFunction(p::TView<ast::Id> functionIds)
Expand Down
4 changes: 4 additions & 0 deletions Libs/Backends/MIR/Compiler/Src/IRGeneration.h
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
#include <AST/Components/Tags/CInvalid.h>
#include <AST/Id.h>
#include <Components/Declarations.h>
#include <Pipe/Core/Set.h>
#include <PipeECS.h>


Expand All @@ -34,10 +35,13 @@ namespace rift::MIR

struct CGenerator
{
static const p::TSet<p::Tag> reservedNames;

Compiler& compiler;
MIRAccess access;
p::String* code = nullptr;


void GenerateModule(ast::Id moduleId);

void BindNativeTypes();
Expand Down
5 changes: 3 additions & 2 deletions Libs/Editor/Src/Panels/FileExplorerPanel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -400,8 +400,9 @@ namespace rift::Editor
}
UI::InputText("##newname", renameBuffer, ImGuiInputTextFlags_AutoSelectAll);

const StringView parsedNewName = Strings::RemoveFromEnd(renameBuffer, ".rf");
const bool nameIsEmpty = parsedNewName.empty();
const StringView parsedNewName =
Strings::RemoveFromEnd(p::StringView{renameBuffer}, ".rf");
const bool nameIsEmpty = parsedNewName.empty();
const Id sameNameFuncId =
ast::FindChildByName(ast, p::GetIdParent(ast, item.id), Tag{parsedNewName});
if (nameIsEmpty || (!IsNone(sameNameFuncId) && item.id != sameNameFuncId))
Expand Down

0 comments on commit 7924ed5

Please sign in to comment.