📄 schematic.java
字号:
/* -*- tab-width: 4 -*- * * Electric(tm) VLSI Design System * * File: Schematic.java * * Copyright (c) 2004 Sun Microsystems and Static Free Software * * Electric(tm) is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or * (at your option) any later version. * * Electric(tm) is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with Electric(tm); see the file COPYING. If not, write to * the Free Software Foundation, Inc., 59 Temple Place, Suite 330, * Boston, Mass 02111-1307, USA. */package com.sun.electric.tool.drc;import com.sun.electric.database.geometry.EPoint;import com.sun.electric.database.hierarchy.Cell;import com.sun.electric.database.hierarchy.Export;import com.sun.electric.database.hierarchy.View;import com.sun.electric.database.network.Netlist;import com.sun.electric.database.network.Network;import com.sun.electric.database.network.NetworkTool;import com.sun.electric.database.prototype.NodeProto;import com.sun.electric.database.prototype.PortProto;import com.sun.electric.database.text.Name;import com.sun.electric.database.topology.ArcInst;import com.sun.electric.database.topology.Connection;import com.sun.electric.database.topology.Geometric;import com.sun.electric.database.topology.NodeInst;import com.sun.electric.database.topology.PortInst;import com.sun.electric.database.topology.RTBounds;import com.sun.electric.database.variable.ElectricObject;import com.sun.electric.database.variable.Variable;import com.sun.electric.technology.PrimitiveNode;import com.sun.electric.technology.technologies.Artwork;import com.sun.electric.technology.technologies.Generic;import com.sun.electric.technology.technologies.Schematics;import com.sun.electric.tool.user.ErrorLogger;import java.awt.geom.Point2D;import java.awt.geom.Rectangle2D;import java.util.ArrayList;import java.util.HashMap;import java.util.HashSet;import java.util.Iterator;import java.util.List;import java.util.Map;import java.util.Set;/** * Class to do schematic design-rule checking. * Examines artwork of a schematic for sensibility. */public class Schematic{ // Cells, nodes and arcs private static Set<ElectricObject> nodesChecked = new HashSet<ElectricObject>(); private static ErrorLogger errorLogger = null; private static Map<Geometric,List<Variable>> newVariables = new HashMap<Geometric,List<Variable>>(); public static ErrorLogger doCheck(ErrorLogger errorLog, Cell cell, Geometric[] geomsToCheck) { nodesChecked.clear(); newVariables.clear(); errorLogger = errorLog; // null when it comes from the regression if (errorLogger == null) errorLogger = DRC.getDRCErrorLogger(false, false, null); checkSchematicCellRecursively(cell, geomsToCheck); errorLogger.termLogging(true); DRC.addDRCUpdate(0, null, null, null, null, newVariables); return(errorLogger); } private static Cell isACellToCheck(Geometric geo) { if (geo instanceof NodeInst) { NodeInst ni = (NodeInst)geo; // ignore documentation icon if (ni.isIconOfParent()) return null; if (!ni.isCellInstance()) return null; Cell subCell = (Cell)ni.getProto(); Cell contentsCell = subCell.contentsView(); if (contentsCell == null) contentsCell = subCell; if (nodesChecked.contains(contentsCell)) return null; return contentsCell; } return null; } private static void checkSchematicCellRecursively(Cell cell, Geometric[] geomsToCheck) { nodesChecked.add(cell); // ignore if not a schematic if (!cell.isSchematic() && cell.getTechnology() != Schematics.tech()) return; // recursively check contents in case of hierchically checking if (geomsToCheck == null) { for(Iterator<NodeInst> it = cell.getNodes(); it.hasNext(); ) { NodeInst ni = it.next(); Cell contentsCell = isACellToCheck(ni); if (contentsCell != null) checkSchematicCellRecursively(contentsCell, geomsToCheck); } } else { for (Geometric geo : geomsToCheck) { Cell contentsCell = isACellToCheck(geo); if (contentsCell != null) checkSchematicCellRecursively(contentsCell, geomsToCheck); } } // now check this cell System.out.println("Checking schematic " + cell); ErrorGrouper eg = new ErrorGrouper(cell); checkSchematicCell(cell, false, geomsToCheck, eg); } private static class ErrorGrouper { private boolean inited; private int cellIndex; private Cell cell; private static int cellIndexCounter = 0; ErrorGrouper(Cell cell) { inited = false; cellIndex = cellIndexCounter++; this.cell = cell; } public int getSortKey() { if (!inited) { inited = true; errorLogger.setGroupName(cellIndex, cell.getName()); } return cellIndex; } } private static void checkSchematicCell(Cell cell, boolean justThis, Geometric[] geomsToCheck, ErrorGrouper eg) { int initialErrorCount = errorLogger.getNumErrors(); Netlist netlist = NetworkTool.getUserNetlist(cell); // Normal hierarchically geometry if (geomsToCheck == null) { for(Iterator<NodeInst> it = cell.getNodes(); it.hasNext(); ) { NodeInst ni = it.next(); if (!ni.isCellInstance() && ni.getProto().getTechnology() == Generic.tech()) continue; schematicDoCheck(netlist, ni, eg); } for(Iterator<ArcInst> it = cell.getArcs(); it.hasNext(); ) { ArcInst ai = it.next(); schematicDoCheck(netlist, ai, eg); } } else { for (Geometric geo : geomsToCheck) schematicDoCheck(netlist, geo, eg); } int errorCount = errorLogger.getNumErrors(); int thisErrors = errorCount - initialErrorCount; String indent = " "; if (justThis) indent = ""; if (thisErrors == 0) System.out.println(indent + "No errors found"); else System.out.println(indent + thisErrors + " errors found"); if (justThis) errorLogger.termLogging(true); } /** * Method to add all variables of a given NodeInst that must be added after Schematics DRC job is done. */ private static void addVariable(NodeInst ni, Variable var) { List<Variable> list = newVariables.get(ni); if (list == null) // first time { list = new ArrayList<Variable>(); newVariables.put(ni, list); } list.add(var); } /** * Method to check schematic object "geom". */ private static void schematicDoCheck(Netlist netlist, Geometric geom, ErrorGrouper eg) { // Checked already if (nodesChecked.contains(geom)) return; nodesChecked.add(geom); Cell cell = geom.getParent(); if (geom instanceof NodeInst) { NodeInst ni = (NodeInst)geom; NodeProto np = ni.getProto(); // check for bus pins that don't connect to any bus arcs if (np == Schematics.tech().busPinNode) { // proceed only if it has no exports on it if (!ni.hasExports()) { // must not connect to any bus arcs boolean found = false; for(Iterator<Connection> it = ni.getConnections(); it.hasNext(); ) { Connection con = it.next(); if (con.getArc().getProto() == Schematics.tech().bus_arc) { found = true; break; } } if (!found) { errorLogger.logError("Bus pin does not connect to any bus arcs", geom, cell, null, eg.getSortKey()); return; } } // flag bus pin if more than 1 wire is connected int i = 0; for(Iterator<Connection> it = ni.getConnections(); it.hasNext(); ) { Connection con = it.next(); if (con.getArc().getProto() == Schematics.tech().wire_arc) i++; } if (i > 1) { List<Geometric> geomList = new ArrayList<Geometric>(); geomList.add(geom); for(Iterator<Connection> it = ni.getConnections(); it.hasNext(); ) { Connection con = it.next(); if (con.getArc().getProto() == Schematics.tech().wire_arc) i++; geomList.add(con.getArc()); } errorLogger.logError("Wire arcs cannot connect through a bus pin", geomList, null, cell, eg.getSortKey());
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -