diff options
Diffstat (limited to 'generic/viaduct/fabulous/validity_check.h')
-rw-r--r-- | generic/viaduct/fabulous/validity_check.h | 127 |
1 files changed, 127 insertions, 0 deletions
diff --git a/generic/viaduct/fabulous/validity_check.h b/generic/viaduct/fabulous/validity_check.h new file mode 100644 index 00000000..43291f6e --- /dev/null +++ b/generic/viaduct/fabulous/validity_check.h @@ -0,0 +1,127 @@ +/* + * nextpnr -- Next Generation Place and Route + * + * Copyright (C) 2021-22 gatecat <gatecat@ds0.me> + * + * Permission to use, copy, modify, and/or distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + */ +#ifndef VALIDITY_CHECKING_H +#define VALIDITY_CHECKING_H + +#include "fab_cfg.h" +#include "fab_defs.h" +#include "sso_array.h" + +#include "nextpnr.h" + +NEXTPNR_NAMESPACE_BEGIN + +// The validity checking engine for the fabulous configurable CLB + +// data that we tag onto cells for fast lookup, so we aren't doing slow hash map accesses in the inner-loop-critical +// validity checking code +struct ControlSig +{ + ControlSig() : net(), invert(false){}; + ControlSig(IdString net, bool invert) : net(net), invert(invert){}; + IdString net; + bool invert; + bool operator==(const ControlSig &other) const { return net == other.net && invert == other.invert; } + bool operator!=(const ControlSig &other) const { return net != other.net || invert != other.invert; } +}; + +struct CellTags +{ + struct + { + SSOArray<IdString, MAX_LUTK> lut_inputs; // for checking fracturable LUTs + bool carry_used = false; + const NetInfo *lut_out = nullptr; + // ... + } comb; // data for LUTs, or the LUT part of combined LUT+FF cells + struct + { + ControlSig clk, sr, en; + bool ff_used = false; + bool async = false; + bool latch = false; + const NetInfo *d = nullptr, *q = nullptr; + } ff; // data for FFs, or the FF part of combined LUT+FF cells +}; + +// map between cell and tags, using the flat_index that viaduct defines for this purpose +struct CellTagger +{ + std::vector<CellTags> data; + const CellTags &get(const CellInfo *ci) const { return data.at(ci->flat_index); } + void assign_for(const Context *ctx, const FabricConfig &cfg, const CellInfo *ci); +}; + +// we need to add some extra data to CLB bels to track what they do, so we can update CLBState accordingly +struct BelFlags +{ + enum BlockType : uint8_t + { + BLOCK_OTHER, + BLOCK_CLB, + // ... + } block = BlockType::BLOCK_OTHER; + enum FuncType : uint8_t + { + FUNC_LC_COMB, + FUNC_FF, + FUNC_MUX, + FUNC_OTHER, + } func; + uint8_t index; + // ... +}; + +// state of a CLB, for fast bel->cell lookup +// TODO: add valid/dirty tracking for incremental validity re-checking, important once we have bigger/more complex CLBs +// (cf. xilinx/intel arches in nextpnr) +struct CLBState +{ + explicit CLBState(const LogicConfig &cfg); + // In combined-LC mode (LC bel contains LUT and FF), this indexes the entire LC bel to cell. In separate mode, this + // indexes the combinational part (LUT or LUT+carry only). + std::unique_ptr<CellInfo *[]> lc_comb; + // In split-LC mode only, this maps FF bel (in CLB) index to cell + std::unique_ptr<CellInfo *[]> ff; + // If there is (a) separate mux bel(s), map them to cells + std::unique_ptr<CellInfo *[]> mux; + bool check_validity(const LogicConfig &cfg, const CellTagger &cell_data); +}; + +struct BlockTracker +{ + Context *ctx; + const FabricConfig &cfg; + std::vector<BelFlags> bel_data; + + BlockTracker(Context *ctx, const FabricConfig &cfg) : ctx(ctx), cfg(cfg){}; + void set_bel_type(BelId bel, BelFlags::BlockType block, BelFlags::FuncType func, uint8_t index); + void update_bel(BelId bel, CellInfo *old_cell, CellInfo *new_cell); + struct TileData + { + std::unique_ptr<CLBState> clb; + // ... + }; + std::vector<std::vector<TileData>> tiles; + bool check_validity(BelId bel, const FabricConfig &cfg, const CellTagger &cell_data); +}; + +NEXTPNR_NAMESPACE_END + +#endif |