diff --git a/src/db/db/dbRegionProcessors.cc b/src/db/db/dbRegionProcessors.cc index 9ba85b006..63fcdea3b 100644 --- a/src/db/db/dbRegionProcessors.cc +++ b/src/db/db/dbRegionProcessors.cc @@ -170,12 +170,45 @@ contour_to_edges (const db::Polygon::contour_type &contour, PolygonToEdgeProcess int s1 = db::vprod_sign (*p0 - *pm1, *p1 - *p0); int s2 = db::vprod_sign (*p1 - *p0, *p2 - *p1); - if (mode == PolygonToEdgeProcessor::All || - (mode == PolygonToEdgeProcessor::Convex && s1 < 0 && s2 < 0) || - (mode == PolygonToEdgeProcessor::Concave && s1 > 0 && s2 > 0) || - (mode == PolygonToEdgeProcessor::StepOut && s1 > 0 && s2 < 0) || - (mode == PolygonToEdgeProcessor::StepIn && s1 < 0 && s2 > 0) || - (mode == PolygonToEdgeProcessor::Step && s1 * s2 < 0)) { + bool take = true; + + switch (mode) { + case PolygonToEdgeProcessor::All: + default: + break; + case PolygonToEdgeProcessor::Convex: + take = s1 < 0 && s2 < 0; + break; + case PolygonToEdgeProcessor::NotConvex: + take = ! (s1 < 0 && s2 < 0); + break; + case PolygonToEdgeProcessor::Concave: + take = s1 > 0 && s2 > 0; + break; + case PolygonToEdgeProcessor::NotConcave: + take = ! (s1 > 0 && s2 > 0); + break; + case PolygonToEdgeProcessor::StepOut: + take = s1 > 0 && s2 < 0; + break; + case PolygonToEdgeProcessor::NotStepOut: + take = ! (s1 > 0 && s2 < 0); + break; + case PolygonToEdgeProcessor::StepIn: + take = s1 < 0 && s2 > 0; + break; + case PolygonToEdgeProcessor::NotStepIn: + take = ! (s1 < 0 && s2 > 0); + break; + case PolygonToEdgeProcessor::Step: + take = s1 * s2 < 0; + break; + case PolygonToEdgeProcessor::NotStep: + take = ! (s1 * s2 < 0); + break; + } + + if (take) { result.push_back (db::Edge (*p0, *p1)); } diff --git a/src/db/db/dbRegionProcessors.h b/src/db/db/dbRegionProcessors.h index 9cfc96fc5..08553ca25 100644 --- a/src/db/db/dbRegionProcessors.h +++ b/src/db/db/dbRegionProcessors.h @@ -293,7 +293,8 @@ class DB_PUBLIC PolygonToEdgeProcessor : public db::PolygonToEdgeProcessorBase { public: - enum EdgeMode { All = 0, Convex, Concave, StepIn, StepOut, Step }; + enum EdgeMode { All = 0, Convex, Concave, StepIn, StepOut, Step, + NotConvex, NotConcave, NotStepIn, NotStepOut, NotStep }; PolygonToEdgeProcessor (EdgeMode mode = All); diff --git a/src/db/db/gsiDeclDbRegion.cc b/src/db/db/gsiDeclDbRegion.cc index b51b1f4e9..2e16558ed 100644 --- a/src/db/db/gsiDeclDbRegion.cc +++ b/src/db/db/gsiDeclDbRegion.cc @@ -3258,17 +3258,32 @@ gsi::Enum decl_EdgeMode ("db", "EdgeMode", gsi::enum_const ("Concave", db::PolygonToEdgeProcessor::Concave, "@brief Selects only concave edges\n" ) + + gsi::enum_const ("NotConcave", db::PolygonToEdgeProcessor::NotConcave, + "@brief Selects only edges which are not concave\n" + ) + gsi::enum_const ("Convex", db::PolygonToEdgeProcessor::Convex, "@brief Selects only convex edges\n" ) + + gsi::enum_const ("NotConvex", db::PolygonToEdgeProcessor::NotConvex, + "@brief Selects only edges which are not convex\n" + ) + gsi::enum_const ("Step", db::PolygonToEdgeProcessor::Step, "@brief Selects only step edges leading inside or outside\n" ) + + gsi::enum_const ("NotStep", db::PolygonToEdgeProcessor::NotStep, + "@brief Selects only edges which are not steps\n" + ) + gsi::enum_const ("StepIn", db::PolygonToEdgeProcessor::StepIn, "@brief Selects only step edges leading inside\n" ) + + gsi::enum_const ("NotStepIn", db::PolygonToEdgeProcessor::NotStepIn, + "@brief Selects only edges which are not steps leading inside\n" + ) + gsi::enum_const ("StepOut", db::PolygonToEdgeProcessor::StepOut, "@brief Selects only step edges leading outside\n" + ) + + gsi::enum_const ("NotStepOut", db::PolygonToEdgeProcessor::NotStepOut, + "@brief Selects only edges which are not steps leading outside\n" ), "@brief This class represents the edge mode type for \\Region#edges.\n" "\n" diff --git a/src/drc/drc/built-in-macros/_drc_complex_ops.rb b/src/drc/drc/built-in-macros/_drc_complex_ops.rb index 9950da2e9..93a659a95 100644 --- a/src/drc/drc/built-in-macros/_drc_complex_ops.rb +++ b/src/drc/drc/built-in-macros/_drc_complex_ops.rb @@ -1014,6 +1014,13 @@ CODE # out = in.drc(primary.edges(convex)) # @/code # + # In addition, "not_.." variants are available which selects edges + # not qualifying for the specific mode: + # + # @code + # out = in.drc(primary.edges(not_convex)) + # @/code + # # The mode argument is ignored when translating other objects than # polygons. diff --git a/src/drc/drc/built-in-macros/_drc_engine.rb b/src/drc/drc/built-in-macros/_drc_engine.rb index 3714a325b..e7289f3f6 100644 --- a/src/drc/drc/built-in-macros/_drc_engine.rb +++ b/src/drc/drc/built-in-macros/_drc_engine.rb @@ -259,22 +259,42 @@ module DRC DRCEdgeMode::new(RBA::EdgeMode::Convex) end + def not_convex + DRCEdgeMode::new(RBA::EdgeMode::NotConvex) + end + def concave DRCEdgeMode::new(RBA::EdgeMode::Concave) end + def not_concave + DRCEdgeMode::new(RBA::EdgeMode::NotConcave) + end + def step_in DRCEdgeMode::new(RBA::EdgeMode::StepIn) end + def not_step_in + DRCEdgeMode::new(RBA::EdgeMode::NotStepIn) + end + def step_out DRCEdgeMode::new(RBA::EdgeMode::StepOut) end + def not_step_out + DRCEdgeMode::new(RBA::EdgeMode::NotStepOut) + end + def step DRCEdgeMode::new(RBA::EdgeMode::Step) end + def not_step + DRCEdgeMode::new(RBA::EdgeMode::NotStep) + end + def padding_zero DRCDensityPadding::new(:zero) end diff --git a/src/drc/drc/built-in-macros/_drc_layer.rb b/src/drc/drc/built-in-macros/_drc_layer.rb index 5d0409e2a..fc722810a 100644 --- a/src/drc/drc/built-in-macros/_drc_layer.rb +++ b/src/drc/drc/built-in-macros/_drc_layer.rb @@ -3409,7 +3409,14 @@ CODE # out = in.edges(convex) # @/code # - # This feature is only available for polygon layers. + # In addition, "not_.." variants are available which selects edges + # not qualifying for the specific mode: + # + # @code + # out = in.edges(not_convex) + # @/code + # + # The mode argument is only available for polygon layers. # # The following images show the effect of the mode argument: # diff --git a/testdata/drc/drcSimpleTests_92.drc b/testdata/drc/drcSimpleTests_92.drc index 5894b4c93..7187fe7aa 100644 --- a/testdata/drc/drcSimpleTests_92.drc +++ b/testdata/drc/drcSimpleTests_92.drc @@ -19,6 +19,12 @@ l2.edges(step).output(103, 0) l2.edges(step_in).output(104, 0) l2.edges(step_out).output(105, 0) +l2.edges(not_convex).output(111, 0) +l2.edges(not_concave).output(112, 0) +l2.edges(not_step).output(113, 0) +l2.edges(not_step_in).output(114, 0) +l2.edges(not_step_out).output(115, 0) + l2.drc(primary.edges).output(200, 0) l2.drc(primary.edges(convex)).output(201, 0) l2.drc(primary.edges(concave)).output(202, 0) @@ -26,4 +32,9 @@ l2.drc(primary.edges(step)).output(203, 0) l2.drc(primary.edges(step_in)).output(204, 0) l2.drc(primary.edges(step_out)).output(205, 0) +l2.drc(primary.edges(not_convex)).output(211, 0) +l2.drc(primary.edges(not_concave)).output(212, 0) +l2.drc(primary.edges(not_step)).output(213, 0) +l2.drc(primary.edges(not_step_in)).output(214, 0) +l2.drc(primary.edges(not_step_out)).output(215, 0) diff --git a/testdata/drc/drcSimpleTests_au92.gds b/testdata/drc/drcSimpleTests_au92.gds index 2ce998226..26068b9b3 100644 Binary files a/testdata/drc/drcSimpleTests_au92.gds and b/testdata/drc/drcSimpleTests_au92.gds differ diff --git a/testdata/drc/drcSimpleTests_au92d.gds b/testdata/drc/drcSimpleTests_au92d.gds index 77d0297d8..775f8f9fa 100644 Binary files a/testdata/drc/drcSimpleTests_au92d.gds and b/testdata/drc/drcSimpleTests_au92d.gds differ