Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/prusa3d/PrusaSlicer.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authortamasmeszaros <meszaros.q@gmail.com>2019-10-03 13:20:02 +0300
committertamasmeszaros <meszaros.q@gmail.com>2019-10-03 13:31:25 +0300
commit23a7e77a81d997ae789c9c0bff31f889460d868a (patch)
tree6776ebc948f80c1464bbd1fa060da4db138c3918 /src
parent95e22d8fd4531b193d3bdc270c3932a275344fc9 (diff)
Eliminate some race conditions in sla support tree
Diffstat (limited to 'src')
-rw-r--r--src/libslic3r/SLA/SLASupportTreeBuilder.hpp49
-rw-r--r--src/libslic3r/SLA/SLASupportTreeBuildsteps.cpp50
2 files changed, 51 insertions, 48 deletions
diff --git a/src/libslic3r/SLA/SLASupportTreeBuilder.hpp b/src/libslic3r/SLA/SLASupportTreeBuilder.hpp
index 5ab42fa07..487e5cf94 100644
--- a/src/libslic3r/SLA/SLASupportTreeBuilder.hpp
+++ b/src/libslic3r/SLA/SLASupportTreeBuilder.hpp
@@ -208,11 +208,6 @@ struct Bridge {
const Vec3d &j2,
double r_mm = 0.8,
size_t steps = 45);
-
- Bridge(const Head &h,
- const Vec3d &j2,
- size_t steps = 45)
- : Bridge{h.junction_point(), j2, h.r_back_mm, steps} {}
};
// A bridge that spans from model surface to model surface with small connecting
@@ -310,12 +305,12 @@ public:
return m_heads.back();
}
- template<class...Args> Pillar& add_pillar(unsigned headid, Args&&... args)
+ template<class...Args> long add_pillar(long headid, Args&&... args)
{
std::lock_guard<Mutex> lk(m_mutex);
- assert(headid < m_head_indices.size());
- Head &head = m_heads[m_head_indices[headid]];
+ assert(headid >= 0 && headid < m_head_indices.size());
+ Head &head = m_heads[m_head_indices[size_t(headid)]];
m_pillars.emplace_back(head, std::forward<Args>(args)...);
Pillar& pillar = m_pillars.back();
@@ -325,7 +320,14 @@ public:
pillar.starts_from_head = true;
m_meshcache_valid = false;
- return m_pillars.back();
+ return pillar.id;
+ }
+
+ void add_pillar_base(long pid, double baseheight = 3, double radius = 2)
+ {
+ std::lock_guard<Mutex> lk(m_mutex);
+ assert(pid >= 0 && pid < m_pillars.size());
+ m_pillars[size_t(pid)].add_base(baseheight, radius);
}
void increment_bridges(const Pillar& pillar)
@@ -352,7 +354,7 @@ public:
return pillar.bridges;
}
- template<class...Args> Pillar& add_pillar(Args&&...args)
+ template<class...Args> long add_pillar(Args&&...args)
{
std::lock_guard<Mutex> lk(m_mutex);
m_pillars.emplace_back(std::forward<Args>(args)...);
@@ -360,7 +362,7 @@ public:
pillar.id = long(m_pillars.size() - 1);
pillar.starts_from_head = false;
m_meshcache_valid = false;
- return m_pillars.back();
+ return pillar.id;
}
const Pillar& head_pillar(unsigned headid) const
@@ -383,21 +385,21 @@ public:
return m_junctions.back();
}
- template<class...Args> const Bridge&
- add_bridge(const Vec3d &sp, const Vec3d &ep, double r, size_t steps = 45)
+ const Bridge& add_bridge(const Vec3d &s, const Vec3d &e, double r, size_t n = 45)
{
- return _add_bridge(m_bridges, sp, ep, r, steps);
+ return _add_bridge(m_bridges, s, e, r, n);
}
- template<class...Args>
- const Bridge& add_bridge(const Head &h, const Vec3d &endp, size_t steps = 45)
+ const Bridge& add_bridge(long headid, const Vec3d &endp, size_t s = 45)
{
std::lock_guard<Mutex> lk(m_mutex);
- m_bridges.emplace_back(h, endp, steps);
+ assert(headid >= 0 && headid < m_head_indices.size());
+
+ Head &h = m_heads[m_head_indices[size_t(headid)]];
+ m_bridges.emplace_back(h.junction_point(), endp, h.r_back_mm, s);
m_bridges.back().id = long(m_bridges.size() - 1);
- assert(h.id >= 0 && h.id < m_head_indices.size());
- m_heads[m_head_indices[size_t(h.id)]].bridge_id = m_bridges.back().id;
+ h.bridge_id = m_bridges.back().id;
m_meshcache_valid = false;
return m_bridges.back();
}
@@ -444,6 +446,15 @@ public:
return m_pillars[size_t(id)];
}
+ template<class T> inline IntegerOnly<T, Pillar&> pillar(T id)
+ {
+ std::lock_guard<Mutex> lk(m_mutex);
+ assert(id >= 0 && size_t(id) < m_pillars.size() &&
+ size_t(id) < std::numeric_limits<size_t>::max());
+
+ return m_pillars[size_t(id)];
+ }
+
const Pad& pad() const { return m_pad; }
// WITHOUT THE PAD!!!
diff --git a/src/libslic3r/SLA/SLASupportTreeBuildsteps.cpp b/src/libslic3r/SLA/SLASupportTreeBuildsteps.cpp
index 50571c11e..9b87aa469 100644
--- a/src/libslic3r/SLA/SLASupportTreeBuildsteps.cpp
+++ b/src/libslic3r/SLA/SLASupportTreeBuildsteps.cpp
@@ -508,15 +508,14 @@ bool SupportTreeBuildsteps::connect_to_nearpillar(const Head &head,
if (m_builder.bridgecount(nearpillar()) < m_cfg.max_bridges_on_pillar) {
// A partial pillar is needed under the starting head.
if(zdiff > 0) {
- m_builder.add_pillar(unsigned(head.id), bridgestart, r);
+ m_builder.add_pillar(head.id, bridgestart, r);
m_builder.add_junction(bridgestart, r);
+ m_builder.add_bridge(bridgestart, bridgeend, head.r_back_mm);
+ } else {
+ m_builder.add_bridge(head.id, bridgeend);
}
- auto &br = m_builder.add_bridge(bridgestart, bridgeend, r);
m_builder.increment_bridges(nearpillar());
- if (head.pillar_id == ID_UNSET)
- m_builder.head(unsigned(head.id)).bridge_id = br.id;
-
} else return false;
return true;
@@ -631,13 +630,11 @@ void SupportTreeBuildsteps::create_ground_pillar(const Vec3d &jp,
auto hit = bridge_mesh_intersect(endp, DOWN, radius);
if (!std::isinf(hit.distance())) abort_in_shame();
- Pillar &plr = m_builder.add_pillar(endp, pgnd, radius);
+ pillar_id = m_builder.add_pillar(endp, pgnd, radius);
if (can_add_base)
- plr.add_base(m_cfg.base_height_mm,
- m_cfg.base_radius_mm);
-
- pillar_id = plr.id;
+ m_builder.add_pillar_base(pillar_id, m_cfg.base_height_mm,
+ m_cfg.base_radius_mm);
}
m_builder.add_bridge(jp, endp, radius);
@@ -648,19 +645,17 @@ void SupportTreeBuildsteps::create_ground_pillar(const Vec3d &jp,
// prevent from queries of head_pillar() to have non-existing
// pillar when the head should have one.
if (head_id >= 0)
- m_builder.add_pillar(unsigned(head_id), jp, radius);
+ m_builder.add_pillar(head_id, jp, radius);
}
}
if (normal_mode) {
- Pillar &plr = head_id >= 0
- ? m_builder.add_pillar(unsigned(head_id), endp, radius)
- : m_builder.add_pillar(jp, endp, radius);
-
+ pillar_id = head_id >= 0 ? m_builder.add_pillar(head_id, endp, radius) :
+ m_builder.add_pillar(jp, endp, radius);
+
if (can_add_base)
- plr.add_base(m_cfg.base_height_mm, m_cfg.base_radius_mm);
-
- pillar_id = plr.id;
+ m_builder.add_pillar_base(pillar_id, m_cfg.base_height_mm,
+ m_cfg.base_radius_mm);
}
if(pillar_id >= 0) // Save the pillar endpoint in the spatial index
@@ -871,10 +866,8 @@ void SupportTreeBuildsteps::classify()
return d2d < 2 * m_cfg.base_radius_mm
&& d3d < m_cfg.max_bridge_length_mm;
};
-
- m_pillar_clusters = cluster(ground_head_indices,
- pointfn,
- predicate,
+
+ m_pillar_clusters = cluster(ground_head_indices, pointfn, predicate,
m_cfg.max_bridges_on_pillar);
}
@@ -965,7 +958,7 @@ void SupportTreeBuildsteps::routing_to_model()
{
head.transform();
Vec3d endp = head.junction_point() + dist * dir;
- m_builder.add_bridge(head, endp);
+ m_builder.add_bridge(head.id, endp);
m_builder.add_junction(endp, head.r_back_mm);
this->create_ground_pillar(endp, dir, head.r_back_mm);
@@ -1096,11 +1089,10 @@ void SupportTreeBuildsteps::routing_to_model()
center_hit.position() : hit.position();
head.transform();
-
- Pillar& pill = m_builder.add_pillar(unsigned(head.id),
- endp,
- head.r_back_mm);
-
+
+ long pillar_id = m_builder.add_pillar(head.id, endp, head.r_back_mm);
+ Pillar &pill = m_builder.pillar(pillar_id);
+
Vec3d taildir = endp - hitp;
double dist = distance(endp, hitp) + m_cfg.head_penetration_mm;
double w = dist - 2 * head.r_pin_mm - head.r_back_mm;
@@ -1310,7 +1302,7 @@ void SupportTreeBuildsteps::interconnect_pillars()
p.add_base(m_cfg.base_height_mm, m_cfg.base_radius_mm);
if (interconnect(pillar(), p)) {
- Pillar &pp = m_builder.add_pillar(p);
+ Pillar &pp = m_builder.pillar(m_builder.add_pillar(p));
m_pillar_index.insert(pp.endpoint(), unsigned(pp.id));
m_builder.add_junction(s, pillar().r);