Retain line numbers for semantic analysis and fix checking redefinitions

Signed-off-by: Username404-59 <w.iron.zombie@gmail.com>
This commit is contained in:
Username404-59 2025-01-01 02:21:57 +01:00
parent 91c1ae0611
commit af9f76ee72
Signed by: Username404-59
GPG Key ID: 7AB361FBB257A5D1
3 changed files with 26 additions and 5 deletions

View File

@ -21,18 +21,28 @@ struct SemanticAnalyser final: public Tasking {
return tree; return tree;
} }
private: private:
unordered_task_map getTaskMapInstance() final { // TODO Include line in error messages unordered_task_map getTaskMapInstance() final {
using namespace StandardComponents; using namespace StandardComponents;
return { return {
make_nonlocal_task(Function, make_nonlocal_task(Function,
if (index > 0 and any_of(parsedTree.cbegin(), parsedTree.cbegin() + index + 1, [&parseComponent](const component_ptr& pointer){ if (index > 0 and any_of(parsedTree.cbegin(), parsedTree.cbegin() + index, [&parseComponent](const component_ptr& pointer){
if (pointer->getId() != typeid(Reference)) { if (pointer->getId() != typeid(Reference)) {
string_view ptr_name;
try { try {
return dynamic_cast<NamedIdentifier<true>&>(*pointer).name == parseComponent.name; ptr_name = dynamic_cast<NamedIdentifier<true>&>(*pointer).name;
} catch (const bad_cast&) {}; } catch (const bad_cast&) {
try {
ptr_name = dynamic_cast<NamedIdentifier<false>&>(*pointer).name;
} catch (const bad_cast&) {
return false;
}
};
if (ptr_name == parseComponent.name) {
return true;
}
} }
return false; return false;
})) { error(parseComponent.name + " has already been defined previously"); } })) { error(parseComponent.name + " has already been defined previously", parseComponent.line); }
), ),
share_task(Function, Class), share_task(Function, Class),
share_task(Function, Define<true>), share_task(Function, Define<true>),

View File

@ -24,6 +24,7 @@ template<bool disallow_reserved>
struct NamedIdentifier: virtual ParseComponent { struct NamedIdentifier: virtual ParseComponent {
struct identifier_reserved_exception: exception {}; struct identifier_reserved_exception: exception {};
const string name; const string name;
unsigned long line = 0;
explicit NamedIdentifier(const string_view nameText): name(nameText) { explicit NamedIdentifier(const string_view nameText): name(nameText) {
if (disallow_reserved and reserved(name)) { if (disallow_reserved and reserved(name)) {
throw identifier_reserved_exception(); throw identifier_reserved_exception();

View File

@ -184,6 +184,16 @@ namespace Parser {
} catch (const NamedIdentifier<true>::identifier_reserved_exception&) { } catch (const NamedIdentifier<true>::identifier_reserved_exception&) {
parsingError(current, " is a reserved identifier", true); parsingError(current, " is a reserved identifier", true);
} }
if (!parseTree.empty()) {
const component_ptr& last = parseTree[parseTree.size() - 1];
try {
dynamic_cast<NamedIdentifier<true>&>(*last).line = current.line;
} catch (const bad_cast&) {
try {
dynamic_cast<NamedIdentifier<false>&>(*last).line = current.line;
} catch (const bad_cast&) {}
}
}
} }
return parseTree; return parseTree;
} }