Source code for bag3_digital.schematic.digital_db_top

# SPDX-License-Identifier: Apache-2.0
# Copyright 2019 Blue Cheetah Analog Design Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

# -*- coding: utf-8 -*-

from typing import Dict, Any, Sequence, Tuple, Optional, Mapping

import pkg_resources
from pathlib import Path

from pybag.enum import TermType

from bag.design.module import Module
from bag.design.database import ModuleDB
from bag.util.immutable import Param


# noinspection PyPep8Naming
[docs]class bag3_digital__digital_db_top(Module): """Module for library bag3_digital cell digital_db_top. Fill in high level description here. """
[docs] yaml_file = pkg_resources.resource_filename(__name__, str(Path('netlist_info', 'digital_db_top.yaml')))
def __init__(self, database: ModuleDB, params: Param, **kwargs: Any) -> None: Module.__init__(self, self.yaml_file, database, params, **kwargs) @classmethod
[docs] def get_params_info(cls) -> Dict[str, str]: return dict( buf_params='Buffer parameters.', dut_lib='DUT library name.', dut_cell='DUT cell name.', dut_conns='DUT connection dictionary.', source_load_params='Source load params for keeping wrapper interface common', dut_params='DUT design parameters.', dut_load='Flag for using the DUT as a load', dut_m='How many of the dut to use as a load', dut_load_conns='DUT load connections', in_pin_list='Input pin list for exporting internal signals as inputs', out_pin_list='Output pin list for exporting internal signals as outputs', sup_pin_list='Supply pin list.', no_conns='List of non-connected nets',
) @classmethod
[docs] def get_default_param_values(cls) -> Dict[str, Any]: return dict( dut_conns={}, dut_params=None, source_load_params=None, dut_load=False, dut_m=0, dut_load_conns={}, in_pin_list=None, out_pin_list=None, sup_pin_list=None, no_conns=[],
)
[docs] def design(self, buf_params: Sequence[Tuple[Any, ...]], dut_lib: str, dut_cell: str, in_pin_list: Optional[Sequence[str]], out_pin_list: Optional[Sequence[str]], sup_pin_list: Optional[Sequence[str]], dut_conns: Mapping[str, str], dut_params: Optional[Param], dut_load: bool, dut_m: int, source_load_params: Optional[Sequence[Mapping[str, Any]]], dut_load_conns: Mapping[str, Any], no_conns: Sequence[str]) -> None: self.design_sources_and_loads(source_load_params) if buf_params: array_inst_names = ['XBUF%s' % x for x in range(0, len(buf_params))] self.array_instance('XBUF', inst_name_list=array_inst_names) for entry, name in zip(buf_params, array_inst_names): input_net = '' output_net = '' has_input = False has_output = False cur_length = len(entry) if cur_length == 1: cur_params = entry[0] elif cur_length == 2: cur_params, input_net = entry has_input = True elif cur_length == 3: cur_params, input_net, output_net = entry has_input = True has_output = True else: raise ValueError('In design method of digital_db_top, ' f'entry is too long! {entry}') self.instances[name].design(**cur_params) if has_input: self.reconnect_instance_terminal(name, 'in', input_net) if has_output: if isinstance(output_net, Mapping): self.reconnect_instance(name, ((k, v) for k, v in output_net.items())) else: self.reconnect_instance_terminal(name, 'out', output_net) else: self.delete_instance('XBUF') dut_static = dut_params is None self.replace_instance_master('XDUT', dut_lib, dut_cell, static=dut_static, keep_connections=True) if not dut_static: self.instances['XDUT'].design(**dut_params) if dut_load: # need to use the DUT as a load for itself dut_name_list = ['XDUT%s' % x for x in range(0, dut_m + 1)] self.array_instance('XDUT', dut_name_list) self.reconnect_instance('XDUT0', ((k, v) for k, v in dut_conns.items())) for i in range(1, dut_m + 1): self.reconnect_instance('XDUT%s' % i, ((k, v) for k, v in dut_load_conns.items())) else: self.reconnect_instance('XDUT', ((k, v) for k, v in dut_conns.items())) if in_pin_list is not None: has_in = False for cur_in in in_pin_list: if cur_in == 'in': has_in = True else: self.add_pin(cur_in, TermType.input) if not has_in: self.remove_pin('in') if out_pin_list is not None: has_out = False for cur_out in out_pin_list: if cur_out == 'out': has_out = True else: self.add_pin(cur_out, TermType.output) if not has_out: self.remove_pin('out') if sup_pin_list is not None: has_vdd = has_vss = False for cur_sup in sup_pin_list: if cur_sup == 'VDD': has_vdd = True elif cur_sup == 'VSS': has_vss = True else: self.add_pin(cur_sup, TermType.inout) if not has_vdd: self.remove_pin('VDD') if not has_vss: self.remove_pin('VSS') if no_conns: self.rename_instance('Xnc', f'Xnc<{len(no_conns) - 1}:0>', [('noConn', ','.join(no_conns))]) else: self.delete_instance('Xnc')