diff --git a/README.md b/README.md index f381b18d3..192316ac4 100644 --- a/README.md +++ b/README.md @@ -88,10 +88,14 @@ Advanced capabilities include: ## Getting Started -See the [setup documentation](setup.md), then work through building a mechanical keyboard (including subcircuit layout replication) in the [getting started tutorial](getting-started.md). -**Setup tl;dr**: install from pip, published as `edg`: `pip install edg`. -You will need a Java 11+ JRE / JDK, to run the Scala-based core compiler. +``` +pip install edg +``` + +On first run, the system will automatically download a compatible Java runtime for the core compiler. + +Then, work through building a mechanical keyboard (including subcircuit layout replication) in the [getting started tutorial](getting-started.md). Also check out the [reference documentation](reference.md) for a concise list of capabilities. diff --git a/edg/core/ScalaCompilerInterface.py b/edg/core/ScalaCompilerInterface.py index 47cfffc07..25c91ada6 100644 --- a/edg/core/ScalaCompilerInterface.py +++ b/edg/core/ScalaCompilerInterface.py @@ -1,8 +1,10 @@ +from pathlib import Path from typing import Optional, Any, Type, Iterable, Union, Dict, List, Tuple import os import subprocess import sys +import jdk from .. import edgir from .. import edgrpc @@ -88,12 +90,40 @@ def get_connected_block_ports(self, link_port: edgir.LocalPath) -> Optional[List class ScalaCompilerInstance: kDevRelpath = "../../compiler/target/scala-2.13/edg-compiler-assembly-0.1-SNAPSHOT.jar" kPrecompiledRelpath = "resources/edg-compiler-precompiled.jar" + kJreVersion = 17 + kInstallJrePath = Path.home() / ".edg" / f"jre-{kJreVersion}" def __init__(self) -> None: self.process: Optional[Any] = None def check_started(self) -> None: if self.process is None: + installed = False + java_bin: Optional[Path] = None + while java_bin is None: + if self.kInstallJrePath.exists(): + items = [ + item + for item in self.kInstallJrePath.iterdir() + if item.is_dir() and ("jre" in item.name or "jdk" in item.name) + ] + if len(items) > 0: + if len(items) != 1: + raise RuntimeError(f"Expected one JRE in {self.kInstallJrePath}, delete extras and re-run.") + java_bin_path = items[0] / "bin" + if not java_bin_path.exists() or not java_bin_path.is_dir(): + raise RuntimeError(f"Expected JRE bin folder {java_bin_path} to exist.") + java_exe = "java.exe" if os.name == "nt" else "java" + java_bin = java_bin_path / java_exe + + if java_bin is None: + if installed: + raise RuntimeError("Internal error, failed to install JRE") + print("Installing JRE for compiler core...") + self.kInstallJrePath.mkdir(parents=True, exist_ok=True) + jdk.install(str(self.kJreVersion), path=str(self.kInstallJrePath), jre=True) + installed = True + dev_path = os.path.join(os.path.dirname(__file__), self.kDevRelpath) precompiled_path = os.path.join(os.path.dirname(__file__), self.kPrecompiledRelpath) if os.path.exists(dev_path): @@ -105,7 +135,7 @@ def check_started(self) -> None: raise ValueError(f"No EDG Compiler JAR found") self.process = subprocess.Popen( - ["java", "-jar", jar_path], stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE + [str(java_bin), "-jar", jar_path], stdin=subprocess.PIPE, stdout=subprocess.PIPE ) def compile( diff --git a/getting-started.md b/getting-started.md index 7509d91cd..23d26d3f1 100644 --- a/getting-started.md +++ b/getting-started.md @@ -52,10 +52,12 @@ You can also write custom links and ports, though this will be unnecessary for m ### Setup -Instructions for setting up the IDE and compiler are in the [setup document](setup.md). -The rest of this tutorial requires that you have this `edg` package (available on `pip`) installed. +``` +pip install edg +``` +On first run, the system will automatically download a compatible Java runtime for the core compiler. ### Reference Document While this getting started guide is meant to be self-contained, you may also find the [reference document](reference.md) helpful, especially as you build designs outside this tutorial. @@ -74,7 +76,10 @@ Specifically, it: - provides schematic-like graphical edit actions to insert HDL The graphical edit actions have significant limitations (and probably bugs / unhandled edge cases) compared to the full HDL and are best suited for simple designs or as a learning tool. -**Consider it more of a tech demonstrator and proof-of-concept** but do give it a try. +It sees only minimal maintenance. +**Consider it more of a tech demonstrator and proof-of-concept**. + +If you want to try it, see its [README](https://github.com/BerkeleyHCI/edg-ide/blob/main/README.md) for setup instructions. ![Annotated IDE screen](docs/ide/overview.png) diff --git a/pyproject.toml b/pyproject.toml index 4d20f0bf6..b60a76eb9 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta" [project] name = "edg" -version = "0.5.0" +version = "0.5.1" description = "Hardware description language for circuit boards" readme = "README.md" authors = [{ name = "Ducky", email = "richard.lin@berkeley.edu" }] @@ -22,6 +22,7 @@ dependencies = [ "Deprecated==1.2.14", "typing_extensions >= 4.4.0", "pydantic == 2.8.2", + "install-jdk == 1.1.0", ] requires-python = ">=3.9" @@ -45,6 +46,10 @@ strict = true implicit_reexport = true +[[tool.mypy.overrides]] +module = ["jdk"] +ignore_missing_imports = true + [[tool.mypy.overrides]] module = ["edg.edgir.*", "edg.edgrpc.*"] # generated code ignore_errors = true diff --git a/setup.md b/setup.md deleted file mode 100644 index 6bbd20106..000000000 --- a/setup.md +++ /dev/null @@ -1,64 +0,0 @@ -# Setup - -## HDL Core Setup -_These are the instructions to set up the HDL core, both for command-line compilation as well as using the IDE (requires additional setup in the next section)._ -_Runs natively on Windows, Linux, and Mac._ - -1. Make sure you are using Python 3.9 (or later). -2. If you do not have a Java JDK installed, download and install one. - An open-source one is [Eclipse Temurin](https://adoptium.net/temurin/releases/?version=17). - Java 11 (or later) is required. -
Determining Java version - - _This is probably not necessary unless you suspect you're running an outdated Java version, most will probably have Java 11+ installed._ - - On the command line, run `java --version`. - If Java is installed, you'll get something like: - - ``` - openjdk 17.0.4.1 2022-08-12 - OpenJDK Runtime Environment Temurin-17.0.4.1+1 (build 17.0.4.1+1) - OpenJDK 64-Bit Server VM Temurin-17.0.4.1+1 (build 17.0.4.1+1, mixed mode, sharing) - ``` - - The above is an example of a JDK at Java 17. - Version reporting formats are not standardized, for example Oracle's Java 8 may report as `Oracle Corporation Java 1.8.0_351`. -
- -3. Install the Python package using the package manager: - `pip install edg` - - -## IDE Setup -An IDE is available as a PyCharm plugin. -It only sees basic maintenance but still works. -It currently must be built and run from source, but as a Scala / sbt project with fully managed dependencies, this should be pretty straightforward. - -Over the basic Python command-line interface, the IDE provides block diagram visualization, block compilation caching, and an experimental mixed graphical + textual editing interface for the HDL. - -1. Download [sbt](https://www.scala-sbt.org/download.html), the Scala build tool. -2. Download or clone the IDE plugin sources from https://github.com/BerkeleyHCI/edg-ide. - - If using command line git: make sure to initialize submodules: `git submodule update --init --recursive`. - - If using GitHub Desktop: it should automatically clone submodules for you. -3. In the `edg-ide` directory, run `sbt runIDE`. - sbt will automatically fetch dependencies, compile the plugin, and start the IDE with the plugin enabled. - - The first run may take a while. -
Resolving common errors - - - If you get an error along the lines of - `sbt.librarymanagement.ResolveException: Error downloading edgcompiler:edgcompiler_2.13:0.1.0-SNAPSHOT` - or `not found: [...]/edgcompiler/edgcompiler_2.13/0.1.0-SNAPSHOT/edgcompiler_2.13-0.1.0-SNAPSHOT.pom`, - this is because the PolymorphicBlocks submodule hasn't been cloned. - See the section above for instructions. - The IDE plugin includes the HDL compiler as part of its build and requires the PolymorphicBlocks codebase. - - If you get an error along the lines of `[error] ...: value strip is not a member of String`, - this is because your Java version is pre-11. - See the section above for instructions to install a more recent JDK. -
-4. Within the IDE, create a new Python project. - - The location can be anywhere. - - The default environment type of Virtualenv is fine. - - **Make sure to check "inherit global site-packages"**, so that the pip-installed package will be visible. -5. You may need to disable slow operations assertion if you're getting a lot of "Slow operations are prohibited on EDT" errors. - - Go to Tools > Internal Actions > Registry (or Ctrl+Shift+A), find the item `idea.slow.operations.assertion`, and untick it. - - Background: more recent versions of PyCharm seem to be stricter and noisier about what can be called on the GUI (EDT) thread.