Move source reading into a function

This commit is contained in:
Eugen Wissner 2025-04-18 08:51:47 +02:00
parent 1cd44508c3
commit c99237fd9c
Signed by: belka
GPG Key ID: A27FDC1E8EE902C0
8 changed files with 133 additions and 26 deletions

62
boot/dependency.cc Normal file
View File

@ -0,0 +1,62 @@
/* Dependency graph analysis.
Copyright (C) 2025 Free Software Foundation, Inc.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#include "elna/boot/dependency.h"
#include "elna/boot/driver.h"
#include "parser.hh"
namespace elna::boot
{
dependency_graph::dependency_graph()
{
}
dependency_graph::dependency_graph(error_list&& errors)
: m_errors(std::move(errors))
{
}
bool dependency_graph::has_errors() const
{
return !errors().empty();
}
const error_list& dependency_graph::errors() const
{
return m_errors;
}
dependency_graph read_sources(std::istream& entry_point, const char *entry_path)
{
driver parse_driver{ entry_path };
lexer tokenizer(entry_point);
yy::parser parser(tokenizer, parse_driver);
if (parser())
{
return dependency_graph(std::move(parse_driver.errors()));
}
else
{
dependency_graph outcome;
outcome.modules.emplace_back(std::move(parse_driver.tree));
return outcome;
}
}
}

View File

@ -43,6 +43,7 @@ elna_OBJS = \
elna/elna-tree.o \ elna/elna-tree.o \
elna/elna-builtins.o \ elna/elna-builtins.o \
elna/ast.o \ elna/ast.o \
elna/dependency.o \
elna/driver.o \ elna/driver.o \
elna/lexer.o \ elna/lexer.o \
elna/parser.o \ elna/parser.o \

View File

@ -100,7 +100,7 @@ namespace elna::gcc
} }
std::deque<std::unique_ptr<boot::error>> do_semantic_analysis(const char *path, std::deque<std::unique_ptr<boot::error>> do_semantic_analysis(const char *path,
std::unique_ptr<boot::program>& ast, std::shared_ptr<boot::symbol_table> info_table, const std::unique_ptr<boot::program>& ast, std::shared_ptr<boot::symbol_table> info_table,
std::shared_ptr<symbol_table> symbols, std::unordered_map<std::string, tree>& unresolved) std::shared_ptr<symbol_table> symbols, std::unordered_map<std::string, tree>& unresolved)
{ {
boot::declaration_visitor declaration_visitor(path, info_table); boot::declaration_visitor declaration_visitor(path, info_table);

View File

@ -29,12 +29,11 @@ along with GCC; see the file COPYING3. If not see
#include "langhooks-def.h" #include "langhooks-def.h"
#include <fstream> #include <fstream>
#include "elna/boot/driver.h" #include "elna/boot/dependency.h"
#include "elna/gcc/elna-tree.h" #include "elna/gcc/elna-tree.h"
#include "elna/gcc/elna-generic.h" #include "elna/gcc/elna-generic.h"
#include "elna/gcc/elna-diagnostic.h" #include "elna/gcc/elna-diagnostic.h"
#include "elna/gcc/elna-builtins.h" #include "elna/gcc/elna-builtins.h"
#include "parser.hh"
tree elna_global_trees[ELNA_TI_MAX]; tree elna_global_trees[ELNA_TI_MAX];
hash_map<nofree_string_hash, tree> *elna_global_decls = nullptr; hash_map<nofree_string_hash, tree> *elna_global_decls = nullptr;
@ -71,35 +70,36 @@ static void elna_parse_file(const char *filename)
{ {
fatal_error(UNKNOWN_LOCATION, "cannot open filename %s: %m", filename); fatal_error(UNKNOWN_LOCATION, "cannot open filename %s: %m", filename);
} }
elna::boot::dependency_graph outcome = elna::boot::read_sources(file, filename);
elna::boot::driver driver{ filename }; std::shared_ptr<elna::boot::symbol_table> info_table = elna::boot::builtin_symbol_table();
elna::boot::lexer lexer(file); std::shared_ptr<elna::gcc::symbol_table> symbol_table = elna::gcc::builtin_symbol_table();
yy::parser parser(lexer, driver);
linemap_add(line_table, LC_ENTER, 0, filename, 1); linemap_add(line_table, LC_ENTER, 0, filename, 1);
if (parser()) if (outcome.has_errors())
{ {
elna::gcc::report_errors(driver.errors()); elna::gcc::report_errors(outcome.errors());
} }
else else
{ {
std::shared_ptr<elna::boot::symbol_table> info_table = elna::boot::builtin_symbol_table(); for (const std::unique_ptr<elna::boot::program>& module_tree : outcome.modules)
std::shared_ptr<elna::gcc::symbol_table> symbol_table = elna::gcc::builtin_symbol_table(); {
std::unordered_map<std::string, tree> unresolved; std::unordered_map<std::string, tree> unresolved;
auto semantic_errors = elna::gcc::do_semantic_analysis(filename, driver.tree, auto semantic_errors = elna::gcc::do_semantic_analysis(filename, module_tree,
info_table, symbol_table, unresolved); info_table, symbol_table, unresolved);
if (semantic_errors.empty()) if (semantic_errors.empty())
{ {
elna::gcc::generic_visitor generic_visitor{ symbol_table, std::move(unresolved) }; elna::gcc::generic_visitor generic_visitor{ symbol_table, std::move(unresolved) };
generic_visitor.visit(driver.tree.get()); generic_visitor.visit(module_tree.get());
} }
else else
{ {
elna::gcc::report_errors(semantic_errors); elna::gcc::report_errors(semantic_errors);
} }
} }
}
linemap_add(line_table, LC_LEAVE, 0, NULL, 0); linemap_add(line_table, LC_LEAVE, 0, NULL, 0);
} }

View File

@ -0,0 +1,41 @@
/* Dependency graph analysis.
Copyright (C) 2025 Free Software Foundation, Inc.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#pragma once
#include <fstream>
#include "elna/boot/result.h"
#include "elna/boot/ast.h"
namespace elna::boot
{
class dependency_graph
{
error_list m_errors;
public:
std::vector<std::unique_ptr<program>> modules;
bool has_errors() const;
const error_list& errors() const;
dependency_graph();
explicit dependency_graph(error_list&& errors);
};
dependency_graph read_sources(std::istream& entry_point, const char *entry_path);
}

View File

@ -61,17 +61,19 @@ namespace elna::boot
std::size_t column() const; std::size_t column() const;
}; };
using error_list = typename std::deque<std::unique_ptr<error>>;
class error_container class error_container
{ {
protected: protected:
std::deque<std::unique_ptr<error>> m_errors; error_list m_errors;
error_container(const char *input_file); error_container(const char *input_file);
public: public:
const char *input_file; const char *input_file;
std::deque<std::unique_ptr<error>>& errors(); error_list& errors();
template<typename T, typename... Args> template<typename T, typename... Args>
void add_error(Args... arguments) void add_error(Args... arguments)
@ -102,5 +104,4 @@ namespace elna::boot
T proper_type{}; T proper_type{};
bool no_return{ false }; bool no_return{ false };
}; };
} }

View File

@ -15,6 +15,8 @@ You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */ <http://www.gnu.org/licenses/>. */
#pragma once
#include <string> #include <string>
#include <unordered_map> #include <unordered_map>
#include <memory> #include <memory>

View File

@ -34,7 +34,7 @@ along with GCC; see the file COPYING3. If not see
namespace elna::gcc namespace elna::gcc
{ {
std::deque<std::unique_ptr<boot::error>> do_semantic_analysis(const char *path, std::deque<std::unique_ptr<boot::error>> do_semantic_analysis(const char *path,
std::unique_ptr<boot::program>& ast, std::shared_ptr<boot::symbol_table> info_table, const std::unique_ptr<boot::program>& ast, std::shared_ptr<boot::symbol_table> info_table,
std::shared_ptr<symbol_table> symbols, std::unordered_map<std::string, tree>& unresolved); std::shared_ptr<symbol_table> symbols, std::unordered_map<std::string, tree>& unresolved);
tree handle_symbol(const std::string& symbol_name, std::shared_ptr<boot::alias_type> reference, tree handle_symbol(const std::string& symbol_name, std::shared_ptr<boot::alias_type> reference,
std::shared_ptr<symbol_table> symbols, std::unordered_map<std::string, tree>& unresolved, std::shared_ptr<symbol_table> symbols, std::unordered_map<std::string, tree>& unresolved,