mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-09-18 22:33:33 +00:00
Add file offset to instance reference errors so that they are picked up by ifcopenshell.validate
This commit is contained in:
@@ -46,13 +46,6 @@ namespace {
|
|||||||
template<typename Variant, typename T>
|
template<typename Variant, typename T>
|
||||||
constexpr bool is_type_in_variant_v = is_type_in_variant<Variant, T>::value;
|
constexpr bool is_type_in_variant_v = is_type_in_variant<Variant, T>::value;
|
||||||
|
|
||||||
struct InstanceReference {
|
|
||||||
int v;
|
|
||||||
operator int() const {
|
|
||||||
return v;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
template <typename Fn>
|
template <typename Fn>
|
||||||
void dispatch_token(int instance_id, int attribute_id, IfcParse::Token t, IfcParse::declaration* decl, Fn fn) {
|
void dispatch_token(int instance_id, int attribute_id, IfcParse::Token t, IfcParse::declaration* decl, Fn fn) {
|
||||||
if (t.type == IfcParse::Token_BINARY) {
|
if (t.type == IfcParse::Token_BINARY) {
|
||||||
@@ -75,7 +68,7 @@ namespace {
|
|||||||
} else if (t.type == IfcParse::Token_FLOAT) {
|
} else if (t.type == IfcParse::Token_FLOAT) {
|
||||||
fn(IfcParse::TokenFunc::asFloat(t));
|
fn(IfcParse::TokenFunc::asFloat(t));
|
||||||
} else if (t.type == IfcParse::Token_IDENTIFIER) {
|
} else if (t.type == IfcParse::Token_IDENTIFIER) {
|
||||||
fn(IfcParse::reference_or_simple_type{ InstanceReference{ IfcParse::TokenFunc::asIdentifier(t) } });
|
fn(IfcParse::reference_or_simple_type{ IfcParse::InstanceReference{ IfcParse::TokenFunc::asIdentifier(t), t.startPos } });
|
||||||
} else if (t.type == IfcParse::Token_INT) {
|
} else if (t.type == IfcParse::Token_INT) {
|
||||||
fn(IfcParse::TokenFunc::asInt(t));
|
fn(IfcParse::TokenFunc::asInt(t));
|
||||||
} else if (t.type == IfcParse::Token_STRING) {
|
} else if (t.type == IfcParse::Token_STRING) {
|
||||||
|
|||||||
@@ -66,7 +66,15 @@ class IFC_PARSE_API file_open_status {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef boost::variant<int, IfcUtil::IfcBaseClass*> reference_or_simple_type;
|
struct InstanceReference {
|
||||||
|
int v;
|
||||||
|
size_t file_offset;
|
||||||
|
operator int() const {
|
||||||
|
return v;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef boost::variant<InstanceReference, IfcUtil::IfcBaseClass*> reference_or_simple_type;
|
||||||
typedef std::list<std::pair<MutableAttributeValue, boost::variant<reference_or_simple_type, std::vector<reference_or_simple_type>, std::vector<std::vector<reference_or_simple_type>>>>> unresolved_references;
|
typedef std::list<std::pair<MutableAttributeValue, boost::variant<reference_or_simple_type, std::vector<reference_or_simple_type>, std::vector<std::vector<reference_or_simple_type>>>>> unresolved_references;
|
||||||
|
|
||||||
struct parse_context {
|
struct parse_context {
|
||||||
|
|||||||
@@ -1423,10 +1423,10 @@ void IfcFile::initialize_(IfcParse::IfcSpfStream* s) {
|
|||||||
const auto& ref = p.first.name_;
|
const auto& ref = p.first.name_;
|
||||||
const auto& refattr = p.first.index_;
|
const auto& refattr = p.first.index_;
|
||||||
if (auto* v = boost::get<reference_or_simple_type>(&p.second)) {
|
if (auto* v = boost::get<reference_or_simple_type>(&p.second)) {
|
||||||
if (auto* name = boost::get<int>(v)) {
|
if (auto* name = boost::get<InstanceReference>(v)) {
|
||||||
entity_by_id_t::const_iterator it = byid_.find(*name);
|
entity_by_id_t::const_iterator it = byid_.find(*name);
|
||||||
if (it == byid_.end()) {
|
if (it == byid_.end()) {
|
||||||
Logger::Error("Instance reference #" + std::to_string(*name) + " used by instance #" + std::to_string(ref) + " at attribute index " + std::to_string(refattr) + " not found");
|
Logger::Error("Instance reference #" + std::to_string(*name) + " used by instance #" + std::to_string(ref) + " at attribute index " + std::to_string(refattr) + " not found at offset " + std::to_string(name->file_offset));
|
||||||
} else {
|
} else {
|
||||||
byid_[p.first.name_]->data().storage_.set(p.first.index_, it->second);
|
byid_[p.first.name_]->data().storage_.set(p.first.index_, it->second);
|
||||||
}
|
}
|
||||||
@@ -1437,10 +1437,10 @@ void IfcFile::initialize_(IfcParse::IfcSpfStream* s) {
|
|||||||
aggregate_of_instance::ptr instances(new aggregate_of_instance);
|
aggregate_of_instance::ptr instances(new aggregate_of_instance);
|
||||||
instances->reserve(v->size());
|
instances->reserve(v->size());
|
||||||
for (const auto& vi : *v) {
|
for (const auto& vi : *v) {
|
||||||
if (auto* name = boost::get<int>(&vi)) {
|
if (auto* name = boost::get<InstanceReference>(&vi)) {
|
||||||
entity_by_id_t::const_iterator it = byid_.find(*name);
|
entity_by_id_t::const_iterator it = byid_.find(*name);
|
||||||
if (it == byid_.end()) {
|
if (it == byid_.end()) {
|
||||||
Logger::Error("Instance reference #" + std::to_string(*name) + " used by instance #" + std::to_string(ref) + " at attribute index " + std::to_string(refattr) + " not found");
|
Logger::Error("Instance reference #" + std::to_string(*name) + " used by instance #" + std::to_string(ref) + " at attribute index " + std::to_string(refattr) + " not found at offset " + std::to_string(name->file_offset));
|
||||||
} else {
|
} else {
|
||||||
instances->push(it->second);
|
instances->push(it->second);
|
||||||
}
|
}
|
||||||
@@ -1454,10 +1454,10 @@ void IfcFile::initialize_(IfcParse::IfcSpfStream* s) {
|
|||||||
for (const auto& vi : *v) {
|
for (const auto& vi : *v) {
|
||||||
std::vector<IfcUtil::IfcBaseClass*> inner;
|
std::vector<IfcUtil::IfcBaseClass*> inner;
|
||||||
for (const auto& vii : vi) {
|
for (const auto& vii : vi) {
|
||||||
if (auto* name = boost::get<int>(&vii)) {
|
if (auto* name = boost::get<InstanceReference>(&vii)) {
|
||||||
entity_by_id_t::const_iterator it = byid_.find(*name);
|
entity_by_id_t::const_iterator it = byid_.find(*name);
|
||||||
if (it == byid_.end()) {
|
if (it == byid_.end()) {
|
||||||
Logger::Error("Instance reference #" + std::to_string(*name) + " used by instance #" + std::to_string(ref) + " at attribute index " + std::to_string(refattr) + " not found");
|
Logger::Error("Instance reference #" + std::to_string(*name) + " used by instance #" + std::to_string(ref) + " at attribute index " + std::to_string(refattr) + " not found at offset " + std::to_string(name->file_offset));
|
||||||
} else {
|
} else {
|
||||||
inner.push_back(it->second);
|
inner.push_back(it->second);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user