Fixed some crashes occurring when giving invalid arguments to functions

master
Marc Gilleron 2021-07-19 19:04:52 +01:00
parent 149eb2a873
commit 52aa4963ea
8 changed files with 58 additions and 12 deletions

View File

@ -148,6 +148,28 @@ bool ProgramGraph::disconnect(PortLocation src, PortLocation dst) {
return true;
}
bool ProgramGraph::is_input_port_valid(PortLocation loc) const {
Node *node = try_get_node(loc.node_id);
if (node == nullptr) {
return false;
}
if (loc.port_index >= node->inputs.size()) {
return false;
}
return true;
}
bool ProgramGraph::is_output_port_valid(PortLocation loc) const {
Node *node = try_get_node(loc.node_id);
if (node == nullptr) {
return false;
}
if (loc.port_index >= node->outputs.size()) {
return false;
}
return true;
}
ProgramGraph::Node *ProgramGraph::get_node(uint32_t id) const {
auto it = _nodes.find(id);
CRASH_COND(it == _nodes.end());

View File

@ -58,6 +58,8 @@ public:
bool can_connect(PortLocation src, PortLocation dst) const;
void connect(PortLocation src, PortLocation dst);
bool disconnect(PortLocation src, PortLocation dst);
bool is_input_port_valid(PortLocation loc) const;
bool is_output_port_valid(PortLocation loc) const;
bool has_path(uint32_t p_src_node_id, uint32_t p_dst_node_id) const;
void find_dependencies(std::vector<uint32_t> nodes_to_process, std::vector<uint32_t> &out_order) const;

View File

@ -47,36 +47,44 @@ static ProgramGraph::Node *create_node_internal(ProgramGraph &graph,
}
uint32_t VoxelGeneratorGraph::create_node(NodeTypeID type_id, Vector2 position, uint32_t id) {
ERR_FAIL_COND_V(!VoxelGraphNodeDB::get_singleton()->is_valid_type_id(type_id), ProgramGraph::NULL_ID);
const ProgramGraph::Node *node = create_node_internal(_graph, type_id, position, id);
ERR_FAIL_COND_V(node == nullptr, ProgramGraph::NULL_ID);
return node->id;
}
void VoxelGeneratorGraph::remove_node(uint32_t node_id) {
ERR_FAIL_COND(_graph.try_get_node(node_id) == nullptr);
_graph.remove_node(node_id);
emit_changed();
}
bool VoxelGeneratorGraph::can_connect(
uint32_t src_node_id, uint32_t src_port_index, uint32_t dst_node_id, uint32_t dst_port_index) const {
return _graph.can_connect(
ProgramGraph::PortLocation{ src_node_id, src_port_index },
ProgramGraph::PortLocation{ dst_node_id, dst_port_index });
const ProgramGraph::PortLocation src_port{ src_node_id, src_port_index };
const ProgramGraph::PortLocation dst_port{ dst_node_id, dst_port_index };
ERR_FAIL_COND_V(!_graph.is_output_port_valid(src_port), false);
ERR_FAIL_COND_V(!_graph.is_input_port_valid(dst_port), false);
return _graph.can_connect(src_port, dst_port);
}
void VoxelGeneratorGraph::add_connection(
uint32_t src_node_id, uint32_t src_port_index, uint32_t dst_node_id, uint32_t dst_port_index) {
_graph.connect(
ProgramGraph::PortLocation{ src_node_id, src_port_index },
ProgramGraph::PortLocation{ dst_node_id, dst_port_index });
const ProgramGraph::PortLocation src_port{ src_node_id, src_port_index };
const ProgramGraph::PortLocation dst_port{ dst_node_id, dst_port_index };
ERR_FAIL_COND(!_graph.is_output_port_valid(src_port));
ERR_FAIL_COND(!_graph.is_input_port_valid(dst_port));
_graph.connect(src_port, dst_port);
emit_changed();
}
void VoxelGeneratorGraph::remove_connection(
uint32_t src_node_id, uint32_t src_port_index, uint32_t dst_node_id, uint32_t dst_port_index) {
_graph.disconnect(
ProgramGraph::PortLocation{ src_node_id, src_port_index },
ProgramGraph::PortLocation{ dst_node_id, dst_port_index });
const ProgramGraph::PortLocation src_port{ src_node_id, src_port_index };
const ProgramGraph::PortLocation dst_port{ dst_node_id, dst_port_index };
ERR_FAIL_COND(!_graph.is_output_port_valid(src_port));
ERR_FAIL_COND(!_graph.is_input_port_valid(dst_port));
_graph.disconnect(src_port, dst_port);
emit_changed();
}
@ -1322,6 +1330,7 @@ int VoxelGeneratorGraph::_b_get_node_type_count() const {
}
Dictionary VoxelGeneratorGraph::_b_get_node_type_info(int type_id) const {
ERR_FAIL_COND_V(!VoxelGraphNodeDB::get_singleton()->is_valid_type_id(type_id), Dictionary());
return VoxelGraphNodeDB::get_singleton()->get_type_info_dict(type_id);
}

View File

@ -74,6 +74,7 @@ public:
static const char *get_category_name(Category category);
int get_type_count() const { return _types.size(); }
bool is_valid_type_id(int type_id) const { return type_id >= 0 && type_id < _types.size(); }
const NodeType &get_type(uint32_t id) const { return _types[id]; }
Dictionary get_type_info_dict(uint32_t id) const;
bool try_get_type_id_from_name(const String &name, VoxelGeneratorGraph::NodeTypeID &out_type_id) const;

View File

@ -26,6 +26,9 @@ void VoxelLibrary::set_voxel_count(unsigned int type_count) {
int VoxelLibrary::get_voxel_index_from_name(StringName name) const {
for (size_t i = 0; i < _voxel_types.size(); ++i) {
const Ref<Voxel> &v = _voxel_types[i];
if (v.is_null()) {
continue;
}
if (v->get_voxel_name() == name) {
return i;
}

View File

@ -84,7 +84,9 @@ private:
static void _bind_methods();
private:
std::vector<Ref<Voxel> > _voxel_types;
// There can be null entries. A vector is used because there should be no more than 65,536 items,
// and in practice the intented use case rarely goes over a few hundreds
std::vector<Ref<Voxel>> _voxel_types;
int _atlas_size = 16;
bool _needs_baking = true;
bool _bake_tangents = true;

View File

@ -207,6 +207,11 @@ Ref<ArrayMesh> VoxelMesherTransvoxel::build_transition_mesh(Ref<VoxelBuffer> vox
ERR_FAIL_COND_V(voxels.is_null(), Ref<ArrayMesh>());
if (voxels->is_uniform(VoxelBuffer::CHANNEL_SDF)) {
// Uniform SDF won't produce any surface
return Ref<ArrayMesh>();
}
// TODO We need to output transition meshes through the generic interface, they are part of the result
// For now we can't support proper texture indices in this specific case
Transvoxel::DefaultTextureIndicesData default_texture_indices_data;

View File

@ -54,7 +54,7 @@ bool VoxelInstanceLibraryItem::is_persistent() const {
}
void VoxelInstanceLibraryItem::set_mesh(Ref<Mesh> mesh, int mesh_lod_index) {
ERR_FAIL_INDEX(mesh_lod_index, VoxelInstancer::MAX_LOD);
ERR_FAIL_INDEX(mesh_lod_index, _mesh_lods.size());
if (_mesh_lods[mesh_lod_index] == mesh) {
return;
}
@ -78,7 +78,7 @@ int VoxelInstanceLibraryItem::get_mesh_lod_count() const {
}
Ref<Mesh> VoxelInstanceLibraryItem::get_mesh(int mesh_lod_index) const {
ERR_FAIL_INDEX_V(mesh_lod_index, VoxelInstancer::MAX_LOD, Ref<Mesh>());
ERR_FAIL_INDEX_V(mesh_lod_index, _mesh_lods.size(), Ref<Mesh>());
return _mesh_lods[mesh_lod_index];
}
@ -143,6 +143,8 @@ static VisualServer::ShadowCastingSetting node_to_visual_server_enum(GeometryIns
}
void VoxelInstanceLibraryItem::setup_from_template(Node *root) {
ERR_FAIL_COND(root == nullptr);
_collision_shapes.clear();
PhysicsBody *physics_body = Object::cast_to<PhysicsBody>(root);