Skip to content

Commit 8cfd042

Browse files
committed
cgt: use pimpl to simplify the public interface
Signed-off-by: Matt Liberty <[email protected]>
1 parent 1706fa8 commit 8cfd042

File tree

6 files changed

+208
-148
lines changed

6 files changed

+208
-148
lines changed

src/cgt/include/cgt/ClockGating.h

Lines changed: 5 additions & 124 deletions
Original file line numberDiff line numberDiff line change
@@ -3,48 +3,13 @@
33

44
#pragma once
55

6-
#include <cstddef>
7-
#include <filesystem>
86
#include <memory>
9-
#include <optional>
10-
#include <string>
11-
#include <vector>
127

13-
#include "cgt/NetworkBuilder.h"
14-
#include "cgt/RandomBits.h"
158
#include "db_sta/dbSta.hh"
16-
#include "utl/deleter.h"
17-
#include "utl/unique_name.h"
18-
19-
namespace abc {
20-
using Abc_Ntk_t = struct Abc_Ntk_t_;
21-
using Abc_Obj_t = struct Abc_Obj_t_;
22-
using Vec_Ptr_t = struct Vec_Ptr_t_;
23-
} // namespace abc
24-
25-
namespace utl {
26-
class Logger;
27-
}
28-
29-
namespace odb {
30-
class dbDatabase;
31-
} // namespace odb
32-
33-
namespace sta {
34-
class dbSta;
35-
} // namespace sta
36-
37-
namespace cut {
38-
39-
class AbcLibrary;
40-
class AbcLibraryFactory;
41-
42-
} // namespace cut
9+
#include "utl/Logger.h"
4310

4411
namespace cgt {
4512

46-
using utl::Logger;
47-
4813
class ClockGating
4914
{
5015
public:
@@ -54,97 +19,13 @@ class ClockGating
5419
// Main function that performs the clock gating process
5520
void run();
5621

57-
void setMinInstances(size_t min_instances) { min_instances_ = min_instances; }
58-
void setMaxCover(size_t max_cover) { max_cover_ = max_cover; }
22+
void setMinInstances(int min_instances);
23+
void setMaxCover(int max_cover);
5924
void setDumpDir(const char* dir);
6025

6126
private:
62-
// Searches for a minimal set of nets that can form a gating condition for the
63-
// given instances. The given range of candidate nets (begin-end) is divided
64-
// in two. If the first half can form a gating condition, the second half is
65-
// dropped from the list. Otherwise, the second half is recursed into.
66-
// Finally, the first half is recursed into.
67-
void searchClockGates(sta::Instance* instance,
68-
std::vector<sta::Net*>& good_gate_conds,
69-
std::vector<sta::Net*>::iterator begin,
70-
std::vector<sta::Net*>::iterator end,
71-
abc::Abc_Ntk_t& abc_network_ref,
72-
bool clk_enable);
73-
// Exports a part of the network that contains the given instances and nets to
74-
// ABC.
75-
utl::UniquePtrWithDeleter<abc::Abc_Ntk_t> exportToAbc(
76-
sta::Instance* instance,
77-
const std::vector<sta::Net*>& nets);
78-
// Constructs an ABC network that will be used for testing if the given nets
79-
// are correct gating conditions.
80-
utl::UniquePtrWithDeleter<abc::Abc_Ntk_t> makeTestNetwork(
81-
sta::Instance* instance,
82-
const std::vector<sta::Net*>& gate_cond_nets,
83-
abc::Abc_Ntk_t& abc_network_ref,
84-
bool clk_enable);
85-
// Performs a random simulation test on the given network and returns true if
86-
// no counterexample for the given gating conditions was found.
87-
bool simulationTest(abc::Abc_Ntk_t* abc_network,
88-
const std::string& combined_gate_name);
89-
// Performs a SAT test on the given network and returns true if it is NOT
90-
// satisfiable (the given nets are correct gating conditions).
91-
bool satTest(abc::Abc_Ntk_t* abc_network,
92-
const std::string& combined_gate_name);
93-
// Returns true if the given gating conditions are correct for the given
94-
// clocked instances.
95-
bool isCorrectClockGate(sta::Instance* instance,
96-
const std::vector<sta::Net*>& gate_cond_nets,
97-
abc::Abc_Ntk_t& abc_network,
98-
bool clk_enable);
99-
// Inserts a clock gate for the given clocked instances with the given gating
100-
// conditions into the network.
101-
void insertClockGate(const std::vector<sta::Instance*>& instances,
102-
const std::vector<sta::Net*>& gate_cond_nets,
103-
bool clk_enable);
104-
105-
void dump(const char* name);
106-
void dumpAbc(const char* name, abc::Abc_Ntk_t* network);
107-
108-
std::filesystem::path getNetworkGraphvizDumpPath(const char* name);
109-
std::filesystem::path getAbcGraphvizDumpPath(const char* name);
110-
std::filesystem::path getAbcVerilogDumpPath(const char* name);
111-
std::filesystem::path getDumpDir();
112-
113-
// Minimum number of instances that should be gated by one clock gate.
114-
size_t min_instances_ = 10;
115-
// Maximum number of nets that form the initial gating condition set for each
116-
// instance.
117-
size_t max_cover_ = 100;
118-
119-
// Path where dump files should be created.
120-
std::optional<std::filesystem::path> dump_dir_;
121-
122-
// Debug counters and run time measurements
123-
size_t dump_counter_ = 0;
124-
size_t rejected_sim_count_ = 0;
125-
size_t rejected_sat_count_ = 0;
126-
size_t accepted_count_ = 0;
127-
double reuse_check_time_ = 0;
128-
double search_time_ = 0;
129-
double exist_check_time_ = 0;
130-
double network_export_time_ = 0;
131-
double network_build_time_ = 0;
132-
double sim_time_ = 0;
133-
double sat_time_ = 0;
134-
135-
// For unique instance names
136-
utl::UniqueName unique_name_cond_;
137-
utl::UniqueName unique_name_cond_not_;
138-
utl::UniqueName unique_name_gate_;
139-
// Generates random bits (for random simulation).
140-
RandomBits rand_bits_;
141-
// Helper for inserting new instances/nets into a network.
142-
NetworkBuilder network_builder_;
143-
144-
Logger* logger_ = nullptr;
145-
sta::dbSta* sta_ = nullptr;
146-
std::unique_ptr<cut::AbcLibraryFactory> abc_factory_;
147-
std::unique_ptr<cut::AbcLibrary> abc_library_;
27+
class Impl;
28+
std::unique_ptr<Impl> impl_;
14829
};
14930

15031
} // namespace cgt

src/cgt/src/ClockGating.cpp

Lines changed: 52 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
#include <utility>
2020
#include <vector>
2121

22+
#include "ClockGatingImpl.h"
2223
#include "base/abc/abc.h"
2324
#include "base/io/ioAbc.h"
2425
#include "base/main/abcapis.h"
@@ -63,14 +64,42 @@ extern void Abc_FrameSetLibGen(void* pLib);
6364

6465
namespace cgt {
6566

66-
ClockGating::ClockGating(utl::Logger* const logger, sta::dbSta* const sta)
67+
ClockGating::ClockGating(utl::Logger* logger, sta::dbSta* open_sta)
68+
: impl_(std::make_unique<Impl>(logger, open_sta))
69+
{
70+
}
71+
72+
ClockGating::~ClockGating() = default;
73+
74+
void ClockGating::run()
75+
{
76+
impl_->run();
77+
}
78+
79+
void ClockGating::setMinInstances(int min_instances)
80+
{
81+
impl_->setMinInstances(min_instances);
82+
}
83+
84+
void ClockGating::setMaxCover(int max_cover)
85+
{
86+
impl_->setMaxCover(max_cover);
87+
}
88+
89+
void ClockGating::setDumpDir(const char* dir)
90+
{
91+
}
92+
93+
//////////////////////////////////////////////////
94+
95+
ClockGating::Impl::Impl(utl::Logger* const logger, sta::dbSta* const sta)
6796
: logger_(logger),
6897
sta_(sta),
6998
abc_factory_(std::make_unique<cut::AbcLibraryFactory>(logger_))
7099
{
71100
}
72101

73-
ClockGating::~ClockGating() = default;
102+
ClockGating::Impl::~Impl() = default;
74103

75104
// Dumps the given network as GraphViz.
76105
static void dumpGraphviz(sta::dbNetwork* const network,
@@ -204,7 +233,7 @@ static sta::Pin* getClockPin(sta::dbNetwork* const network,
204233
return nullptr;
205234
}
206235

207-
void ClockGating::setDumpDir(const char* const dir)
236+
void ClockGating::Impl::setDumpDir(const char* const dir)
208237
{
209238
if (*dir == '\0') {
210239
return;
@@ -343,7 +372,7 @@ static std::string combinedInstanceNames(
343372
return result;
344373
}
345374

346-
void ClockGating::run()
375+
void ClockGating::Impl::run()
347376
{
348377
debugPrint(logger_,
349378
CGT,
@@ -387,7 +416,7 @@ void ClockGating::run()
387416
if (!cell) {
388417
continue;
389418
}
390-
size_t num_regs
419+
int num_regs
391420
= std::count_if(cell->sequentials().begin(),
392421
cell->sequentials().end(),
393422
[](const auto* seq) { return seq->isRegister(); });
@@ -403,13 +432,13 @@ void ClockGating::run()
403432
delete inst_iter;
404433
}
405434

406-
using AcceptedIndex = size_t;
435+
using AcceptedIndex = int;
407436
std::unordered_map<sta::Net*, std::vector<AcceptedIndex>> net_to_accepted;
408437
std::vector<
409438
std::tuple<std::vector<sta::Net*>, std::vector<sta::Instance*>, bool>>
410439
accepted_gates;
411440

412-
for (size_t i = 0; i < instances.size(); i++) {
441+
for (int i = 0; i < instances.size(); i++) {
413442
auto instance = instances[i];
414443
if (i % 100 == 0) {
415444
logger_->info(CGT, 3, "Clock gating instance {}/{}", i, instances.size());
@@ -650,14 +679,14 @@ static std::vector<sta::Net*> except(
650679
return result;
651680
}
652681

653-
void ClockGating::searchClockGates(sta::Instance* const instance,
682+
void ClockGating::Impl::searchClockGates(sta::Instance* const instance,
654683
std::vector<sta::Net*>& good_gate_conds,
655684
const std::vector<sta::Net*>::iterator begin,
656685
const std::vector<sta::Net*>::iterator end,
657686
abc::Abc_Ntk_t& abc_network,
658687
const bool clk_enable)
659688
{
660-
size_t half_len = (end - begin) / 2;
689+
int half_len = (end - begin) / 2;
661690
if (half_len == 0) {
662691
return;
663692
}
@@ -915,7 +944,7 @@ static abc::Abc_Obj_t* regDataFunctionToAbc(sta::dbNetwork* const network,
915944
return obj_stack.back();
916945
}
917946

918-
utl::UniquePtrWithDeleter<abc::Abc_Ntk_t> ClockGating::makeTestNetwork(
947+
utl::UniquePtrWithDeleter<abc::Abc_Ntk_t> ClockGating::Impl::makeTestNetwork(
919948
sta::Instance* const instance,
920949
const std::vector<sta::Net*>& gate_cond_nets,
921950
abc::Abc_Ntk_t& abc_network_ref,
@@ -1075,7 +1104,7 @@ utl::UniquePtrWithDeleter<abc::Abc_Ntk_t> ClockGating::makeTestNetwork(
10751104
}
10761105
}
10771106

1078-
bool ClockGating::simulationTest(abc::Abc_Ntk_t* const abc_network,
1107+
bool ClockGating::Impl::simulationTest(abc::Abc_Ntk_t* const abc_network,
10791108
const std::string& combined_gate_name)
10801109
{
10811110
DebugScopedTimer timer(
@@ -1114,7 +1143,7 @@ bool ClockGating::simulationTest(abc::Abc_Ntk_t* const abc_network,
11141143
return true;
11151144
}
11161145

1117-
bool ClockGating::satTest(abc::Abc_Ntk_t* const abc_network,
1146+
bool ClockGating::Impl::satTest(abc::Abc_Ntk_t* const abc_network,
11181147
const std::string& combined_gate_name)
11191148
{
11201149
DebugScopedTimer timer(
@@ -1145,7 +1174,7 @@ bool ClockGating::satTest(abc::Abc_Ntk_t* const abc_network,
11451174
return true;
11461175
}
11471176

1148-
bool ClockGating::isCorrectClockGate(
1177+
bool ClockGating::Impl::isCorrectClockGate(
11491178
sta::Instance* const instance,
11501179
const std::vector<sta::Net*>& gate_cond_nets,
11511180
abc::Abc_Ntk_t& abc_network_ref,
@@ -1186,7 +1215,7 @@ bool ClockGating::isCorrectClockGate(
11861215
return true;
11871216
}
11881217

1189-
void ClockGating::insertClockGate(const std::vector<sta::Instance*>& instances,
1218+
void ClockGating::Impl::insertClockGate(const std::vector<sta::Instance*>& instances,
11901219
const std::vector<sta::Net*>& gate_cond_nets,
11911220
const bool clk_enable)
11921221
{
@@ -1206,7 +1235,7 @@ void ClockGating::insertClockGate(const std::vector<sta::Instance*>& instances,
12061235
std::vector<sta::Instance*> new_instances;
12071236

12081237
auto gate_cond_net = gate_cond_nets[0];
1209-
for (size_t i = 1; i < gate_cond_nets.size(); i++) {
1238+
for (int i = 1; i < gate_cond_nets.size(); i++) {
12101239
auto inst_name = unique_name_cond_.GetUniqueName("clk_gate_cond_");
12111240
auto inst_builder = clk_enable ? network_builder_.makeOr(inst_name)
12121241
: network_builder_.makeAnd(inst_name);
@@ -1227,7 +1256,7 @@ void ClockGating::insertClockGate(const std::vector<sta::Instance*>& instances,
12271256
assert(clk_pin);
12281257
auto clk_net = network->net(clk_pin);
12291258
auto clocks = network->clkNetwork()->clocks(clk_pin);
1230-
for (size_t i = 1; i < instances.size(); i++) {
1259+
for (int i = 1; i < instances.size(); i++) {
12311260
auto clk_pin = getClockPin(network, instances[i]);
12321261
assert(clk_pin);
12331262
if (*sta_->clkNetwork()->clocks(clk_pin) != *clocks) {
@@ -1274,7 +1303,7 @@ void ClockGating::insertClockGate(const std::vector<sta::Instance*>& instances,
12741303
}
12751304
}
12761305

1277-
UniquePtrWithDeleter<abc::Abc_Ntk_t> ClockGating::exportToAbc(
1306+
UniquePtrWithDeleter<abc::Abc_Ntk_t> ClockGating::Impl::exportToAbc(
12781307
sta::Instance* const instance,
12791308
const std::vector<sta::Net*>& nets)
12801309
{
@@ -1346,7 +1375,7 @@ UniquePtrWithDeleter<abc::Abc_Ntk_t> ClockGating::exportToAbc(
13461375
return abc_network;
13471376
}
13481377

1349-
void ClockGating::dump(const char* const name)
1378+
void ClockGating::Impl::dump(const char* const name)
13501379
{
13511380
if (!dump_dir_) {
13521381
return;
@@ -1358,7 +1387,7 @@ void ClockGating::dump(const char* const name)
13581387
dump_counter_++;
13591388
}
13601389

1361-
void ClockGating::dumpAbc(const char* const name, abc::Abc_Ntk_t* const network)
1390+
void ClockGating::Impl::dumpAbc(const char* const name, abc::Abc_Ntk_t* const network)
13621391
{
13631392
if (!dump_dir_) {
13641393
return;
@@ -1386,26 +1415,26 @@ void ClockGating::dumpAbc(const char* const name, abc::Abc_Ntk_t* const network)
13861415
dump_counter_++;
13871416
}
13881417

1389-
std::filesystem::path ClockGating::getNetworkGraphvizDumpPath(
1418+
std::filesystem::path ClockGating::Impl::getNetworkGraphvizDumpPath(
13901419
const char* const name)
13911420
{
13921421
return getDumpDir()
13931422
/ (std::to_string(dump_counter_) + "_openroad_" + name + ".dot");
13941423
}
13951424

1396-
std::filesystem::path ClockGating::getAbcGraphvizDumpPath(
1425+
std::filesystem::path ClockGating::Impl::getAbcGraphvizDumpPath(
13971426
const char* const name)
13981427
{
13991428
return getDumpDir()
14001429
/ (std::to_string(dump_counter_) + "_abc_" + name + ".dot");
14011430
}
14021431

1403-
std::filesystem::path ClockGating::getAbcVerilogDumpPath(const char* const name)
1432+
std::filesystem::path ClockGating::Impl::getAbcVerilogDumpPath(const char* const name)
14041433
{
14051434
return getDumpDir() / (std::to_string(dump_counter_) + "_abc_" + name + ".v");
14061435
}
14071436

1408-
std::filesystem::path ClockGating::getDumpDir()
1437+
std::filesystem::path ClockGating::Impl::getDumpDir()
14091438
{
14101439
if (dump_dir_) {
14111440
return *dump_dir_;

0 commit comments

Comments
 (0)