Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ __pycache__

examples/*/*.net
examples/*/*.edg
examples/*/*.compiled.json
examples/*/*.pdf
examples/*/gerbers
/*.net
Expand Down
11 changes: 6 additions & 5 deletions compiler/src/main/scala/edg/compiler/Compiler.scala
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@ class AssignNamer() {
}

object Compiler {
final val kExpectedProtoVersion = 9
final val kExpectedProtoVersion = 10
}

/** Compiler for a particular design, with an associated library to elaborate references from.
Expand Down Expand Up @@ -1191,16 +1191,16 @@ class Compiler private (
val link = resolveLink(path).asInstanceOf[wir.Link]

// TODO refactor this out, ConnectedLink needs to be centralized
def setConnectedLink(portPath: DesignPath, port: PortLike): Unit = (port: @unchecked) match {
def setConnectedLink(portSuffix: Seq[String], port: PortLike): Unit = (port: @unchecked) match {
case _: wir.Port =>
constProp.setConnectedLink(path, portPath)
constProp.setConnectedLink(path, portSuffix)
case port: wir.PortArray =>
port.getPorts.foreach { case (subPortName, subPort) =>
setConnectedLink(portPath + subPortName, subPort)
setConnectedLink(portSuffix ++ Seq(subPortName), subPort)
}
}
for ((portName, port) <- link.getPorts) {
setConnectedLink(path + portName, port)
setConnectedLink(Seq(portName), port)
}

// Queue up sub-trees that need elaboration
Expand Down Expand Up @@ -1703,5 +1703,6 @@ class Compiler private (
def getParamType(param: IndirectDesignPath): Option[Class[_ <: ExprValue]] = constProp.getType(param)
def getParamValue(param: IndirectDesignPath): Option[ExprValue] = constProp.getValue(param)
def getAllSolved: Map[IndirectDesignPath, ExprValue] = constProp.getAllSolved
def getAllConnections: Map[DesignPath, DesignPath] = constProp.getAllConnections
def getConnectedLink(port: DesignPath): Option[DesignPath] = constProp.getConnectedLink(port)
}
13 changes: 12 additions & 1 deletion compiler/src/main/scala/edg/compiler/CompilerServerMain.scala
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,16 @@ object CompilerServerMain {
}.toSeq
}

private def constPropConnectionToConnection(vals: Map[DesignPath, DesignPath])
: Seq[edgcompiler.CompilerResult.Connection] = {
vals.map { case (block, link) =>
edgcompiler.CompilerResult.Connection(
blockPort = Some(block.asIndirect.toLocalPath),
linkPort = Some(link.asIndirect.toLocalPath)
)
}.toSeq
}

def compile(request: CompilerRequest, library: PythonInterfaceLibrary): CompilerResult = {
try {
val refinements = Refinements(request.getRefinements)
Expand All @@ -52,7 +62,8 @@ object CompilerServerMain {
val result = edgcompiler.CompilerResult(
design = Some(compiled),
errors = errors.map(_.toIr),
solvedValues = constPropToSolved(compiler.getAllSolved)
solvedValues = constPropToSolved(compiler.getAllSolved),
connections = constPropConnectionToConnection(compiler.getAllConnections)
)
result
} catch {
Expand Down
22 changes: 16 additions & 6 deletions compiler/src/main/scala/edg/compiler/ConstProp.scala
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,9 @@ object ConnectedLinkResult {
case class MissingConnectedLink(port: DesignPath) extends ConnectedLinkResult
}

// for port connectivity, stores both the link path and the port (on the link) path
case class ConnectedLinkPort(linkPath: DesignPath, portSuffix: Seq[String])

/** Parameter propagation, evaluation, and resolution associated with a single design. General philosophy: this should
* not refer to any particular design instance, so the design can continue to be transformed (though those
* transformations must be strictly additive with regards to assignments and assertions)
Expand All @@ -48,7 +51,7 @@ class ConstProp() {
// Undeclared parameters cannot have values set, but can be forced (though the value is not effective until declared)
private val paramTypes = mutable.HashMap[IndirectDesignPath, Class[_ <: ExprValue]]()

private val connectedLink = DependencyGraph[ConnectedLinkRecord, DesignPath]() // tracks the port -> link paths
private val connectedLink = DependencyGraph[ConnectedLinkRecord, ConnectedLinkPort]() // tracks the port -> link paths

// Params that have a forced/override value, so they arent over-assigned.
private val forcedParams = mutable.Set[IndirectDesignPath]()
Expand Down Expand Up @@ -80,7 +83,7 @@ class ConstProp() {
case Some((connected, postfix)) =>
connectedLink.getValue(ConnectedLinkRecord.ConnectedLink(connected)) match {
case Some(connectedLinkPath) =>
resolveConnectedLink(connectedLinkPath.asIndirect ++ postfix)
resolveConnectedLink(connectedLinkPath.linkPath.asIndirect ++ postfix)
case None =>
ConnectedLinkResult.MissingConnectedLink(connected)
}
Expand All @@ -104,7 +107,7 @@ class ConstProp() {
params.setValue(port.asIndirect + IndirectStep.ConnectedLink, BooleanValue(false)) // dummy value
case _ => throw new IllegalArgumentException()
}
connectedLink.setValue(ready, DesignPath())
connectedLink.setValue(ready, ConnectedLinkPort(DesignPath(), Seq()))
}

var readyList = Iterable[IndirectDesignPath]()
Expand Down Expand Up @@ -163,8 +166,9 @@ class ConstProp() {
update()
}

def setConnectedLink(linkPath: DesignPath, portPath: DesignPath): Unit = {
connectedLink.setValue(ConnectedLinkRecord.ConnectedLink(portPath), linkPath)
def setConnectedLink(linkPath: DesignPath, portSuffix: Seq[String]): Unit = {
val portPath = linkPath ++ portSuffix
connectedLink.setValue(ConnectedLinkRecord.ConnectedLink(portPath), ConnectedLinkPort(linkPath, portSuffix))
params.setValue(portPath.asIndirect + IndirectStep.ConnectedLink, BooleanValue(false)) // dummy value

update()
Expand Down Expand Up @@ -274,7 +278,7 @@ class ConstProp() {
}

def getConnectedLink(port: DesignPath): Option[DesignPath] = {
connectedLink.getValue(ConnectedLinkRecord.ConnectedLink(port))
connectedLink.getValue(ConnectedLinkRecord.ConnectedLink(port)).map(_.linkPath)
}

/** Returns the type (as a class of ExprValue) of a parameter.
Expand All @@ -292,6 +296,12 @@ class ConstProp() {

def getAllSolved: Map[IndirectDesignPath, ExprValue] = params.toMap

def getAllConnections: Map[DesignPath, DesignPath] = connectedLink.toMap.collect {
case (ConnectedLinkRecord.ConnectedLink(towardsBlockPort), ConnectedLinkPort(linkPath, linkPortSuffix))
if towardsBlockPort != (linkPath ++ linkPortSuffix) =>
towardsBlockPort -> (linkPath ++ linkPortSuffix)
}

def getErrors: Seq[ExprError] = {
paramErrors.flatMap { case (target, errors) =>
errors.map(error => ExprError(target, error.msg))
Expand Down
15 changes: 12 additions & 3 deletions edg/BoardCompiler.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
from contextlib import suppress
from typing import Type, Optional, Tuple

from .core import Block, ScalaCompiler, CompiledDesign
from .core import Block, ScalaCompiler, CompiledDesign, CompiledDesignExportTransform
from .electronics_model.NetlistBackend import NetlistBackend # imported separately b/c mypy confuses with the modules
from .electronics_model.SvgPcbBackend import SvgPcbBackend
from .electronics_model.RefdesRefinementPass import RefdesRefinementPass
Expand All @@ -21,6 +21,7 @@ def compile_board(design: Type[Block], target_dir_name: Optional[Tuple[str, str]
netlist_filename = os.path.join(target_dir, f"{target_name}.net")
bom_filename = os.path.join(target_dir, f"{target_name}.csv")
svgpcb_filename = os.path.join(target_dir, f"{target_name}.svgpcb.js")
compiled_json_filename = os.path.join(target_dir, f"{target_name}.compiled.json")

with suppress(FileNotFoundError):
os.remove(design_filename)
Expand All @@ -30,6 +31,8 @@ def compile_board(design: Type[Block], target_dir_name: Optional[Tuple[str, str]
os.remove(bom_filename)
with suppress(FileNotFoundError):
os.remove(svgpcb_filename)
with suppress(FileNotFoundError):
os.remove(compiled_json_filename)

compiled = ScalaCompiler.compile(design, ignore_errors=True)
compiled.append_values(RefdesRefinementPass().run(compiled))
Expand All @@ -46,6 +49,7 @@ def compile_board(design: Type[Block], target_dir_name: Optional[Tuple[str, str]
netlist_all = NetlistBackend().run(compiled)
bom_all = GenerateBom().run(compiled)
svgpcb_all = SvgPcbBackend().run(compiled)
compiled_json = CompiledDesignExportTransform(compiled).transform()
assert len(netlist_all) == 1

if target_dir_name is not None:
Expand All @@ -56,8 +60,13 @@ def compile_board(design: Type[Block], target_dir_name: Optional[Tuple[str, str]
bom_file.write(bom_all[0][1])

if svgpcb_all:
with open(svgpcb_filename, "w", encoding="utf-8") as bom_file:
bom_file.write(svgpcb_all[0][1])
with open(svgpcb_filename, "w", encoding="utf-8") as svgpcb_file:
svgpcb_file.write(svgpcb_all[0][1])

with open(compiled_json_filename, "w", encoding="utf-8") as compiled_json_file:
compiled_json_file.write(
CompiledDesignExportTransform.postprocess_serialized_json(compiled_json.model_dump_json(indent=2))
)

return compiled

Expand Down
Loading
Loading