npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

digitaljs

v0.13.1

Published

Digital logic simulator

Downloads

204

Readme

DigitalJS

This project is a digital circuit simulator implemented in Javascript. It is designed to simulate circuits synthesized by hardware design tools like Yosys (Github repo here), and it has a companion project yosys2digitaljs, which converts Yosys output files to DigitalJS. It is also intended to be a teaching tool, therefore readability and ease of inspection is one of top concerns for the project.

You can try it out online. The web app is a separate Github project.

Usage

You can use DigitalJS in your project by installing it from NPM:

npm install digitaljs

Or you can use the Webpack bundle directly.

To simulate a circuit represented using the JSON input format (described later) and display it on a div named #paper, you need to run the following JS code (see running example):

// create the simulation object
const circuit = new digitaljs.Circuit(input_goes_here);
// display on #paper
const paper = circuit.displayOn($('#paper'));
// activate real-time simulation
circuit.start();

Input format

Circuits are represented using JSON. The top-level object has three keys, devices, connectors and subcircuits. Under devices is a list of all devices forming the circuit, represented as an object, where keys are (unique and internal) device names. Each device has a number of properties, which are represented by an object. A mandatory property is type, which specifies the type of the device. Example device:

"dev1": {
    "type": "And",
    "label": "AND1"
}

Under connectors is a list of connections between device ports, represented as an array of objects with two keys, from and to. Both keys map to an object with two keys, id and port; the first corresponds to a device name, and the second -- to a valid port name for the device. A connection must lead from an output port to an input port, and the bitwidth of both ports must be equal. Example connection:

{
    "from": {
        "id": "dev1",
        "port": "out"
    },
    "to": {
        "id": "dev2",
        "port": "in"
    }
}

Under subcircuits is a list of subcircuit definitions, represented as an object, where keys are unique subcircuit names. A subcircuit name can be used as a celltype for a device of type Subcircuit; this instantiates the subcircuit. A subcircuit definition follows the representation of whole circuits, with the exception that subcircuits cannot (currently) define their own subcircuits. A subcircuit can include Input and Output devices, these are mapped to ports on a subcircuit instance.

Device types

  • Unary gates: Not, Repeater
    • Attributes: bits (natural number)
    • Inputs: in (bits-bit)
    • Outputs: out (bits-bit)
  • N-ary gates: And, Nand, Or, Nor, Xor, Xnor
    • Attributes: bits (natural number), inputs (natural number, default 2)
    • Inputs: in1, in2 ... inN (bits-bit, N = inputs)
    • Outputs: out (bits-bit)
  • Reducing gates: AndReduce, NandReduce, OrReduce, NorReduce, XorReduce, XnorReduce
    • Attributes: bits (natural number)
    • Inputs: in (bits-bit)
    • Outputs: out (1-bit)
  • Bit shifts: ShiftLeft, ShiftRight
    • Attributes: bits.in1, bits.in2 and bits.out (natural number), signed.in1, signed.in2, signed.out and fillx (boolean)
    • Inputs: in1 (bits.in1-bit), in2 (bits.in2-bit)
    • Outputs: out (bits.out-bit)
  • Comparisons: Eq, Ne, Lt, Le, Gt, Ge
    • Attributes: bits.in1 and bits.in2 (natural number), signed.in1 and signed.in2 (boolean)
    • Inputs: in1 (bits.in1-bit), in2 (bits.in2-bit)
    • Outputs: out (1-bit)
  • Number constant: Constant
    • Attributes: constant (binary string)
    • Outputs: out (constant.length-bit)
  • Unary arithmetic: Negation, UnaryPlus
    • Attributes: bits.in and bits.out (natural number), signed (boolean)
    • Inputs: in (bits.in-bit)
    • Outputs: out (bits.out-bit)
  • Binary arithmetic: Addition, Subtraction, Multiplication, Division, Modulo, Power
    • Attributes: bits.in1, bits.in2 and bits.out (natural number), signed.in1 and signed.in2 (boolean)
    • Inputs: in1 (bits.in1-bit), in2 (bits.in2-bit)
    • Outputs: out (bits.out-bit)
  • Multiplexer: Mux
    • Attributes: bits.in, bits.sel (natural number)
    • Inputs: in0 ... inN (bits.in-bit, N = 2**bits.sel-1), sel (bits.sel-bit)
    • Outputs: out (bits.in-bit)
  • One-hot multiplexer: Mux1Hot
    • Attributes: bits.in, bits.sel (natural number)
    • Inputs: in0 ... inN (bits.in-bit, N = bits.sel), sel (bits.sel-bit)
    • Outputs: out (bits.in-bit)
  • Sparse multiplexer: MuxSparse
    • Attributes: bits.in, bits.sel (natural number), inputs (list of natural numbers), default_input (optional boolean)
    • Inputs: in0 ... inN (bits.in-bit, N = inputs.length, +1 if default_input is true)
    • Outputs: out (bits.in-bit)
  • D flip-flop: Dff
    • Attributes: bits (natural number), polarity.clock, polarity.arst, polarity.srst, polarity.aload, polarity.set, polarity.clr, polarity.enable, enable_srst (optional booleans), initial (optional binary string), arst_value, srst_value (optional binary string), no_data (optional boolean)
    • Inputs: in (bits-bit), clk (1-bit, if polarity.clock is present), arst (1-bit, if polarity.arst is present), srst (1-bit, if polarity.srst is present), en (1-bit, if polarity.enable is present), set (1-bit, if polarity.set is present), clr (1-bit, if polarity.clr is present), ain (bits-bit, if polarity.aload is present), aload (1-bit, if polarity.aload is present)
    • Outputs: out (bits-bit)
  • Memory: Memory
    • Attributes: bits, abits, words, offset (natural number), rdports (array of read port descriptors), wrports (array of write port descriptors), memdata (memory contents description)
    • Read port descriptor attributes: enable_polarity, clock_polarity, arst_polarity, srst_polarity (optional booleans), init_value, arst_value, srst_value (optional binary strings), transparent, collision (optional booleans or arrays of booleans)
    • Write port descriptor attributes: enable_polarity, clock_polarity, no_bit_enable (optional booleans)
    • Inputs (per read port): rdKaddr (abits-bit), rdKen (1-bit, if enable_polarity is present), rdKclk (1-bit, if clock_polarity is present), rdKarst (1-bit, if arst_polarity is present), rdKsrst (1-bit, if srst_polarity is present)
    • Outputs (per read port): rdKdata (bits-bit)
    • Inputs (per write port): wrKaddr (abits-bit), wrKdata (bits-bit), wrKen (1-bit (when no_bit_enable is true) or bits-bit (otherwise), if enable_polarity is present), wrKclk (1-bit, if clock_polarity is present)
  • Clock source: Clock
    • Outputs: out (1-bit)
  • Button input: Button
    • Outputs: out (1-bit)
  • Lamp output: Lamp
    • Inputs: in (1-bit)
  • Number input: NumEntry
    • Attributes: bits (natural number), numbase (string)
    • Outputs: out (bits-bit)
  • Number output: NumDisplay
    • Attributes: bits (natural number), numbase (string)
    • Inputs: in (bits-bit)
  • Subcircuit input: Input
    • Attributes: bits (natural number)
    • Outputs: out (bits-bit)
  • Subcircuit output: Output
    • Attributes: bits (natural number)
    • Inputs: in (bits-bit)
  • 7 segment display output: Display7
    • Inputs: bits (8-bit only - most significant bit controls decimal point LED)
  • Bus grouping: BusGroup
    • Attributes: groups (array of natural numbers)
    • Inputs: in0 (groups[0]-bit) ... inN (groups[N]-bit)
    • Outputs: out (sum-of-groups-bit)
  • Bus ungrouping: BusUngroup
    • Attributes: groups (array of natural numbers)
    • Inputs: in (sum-of-groups-bit)
    • Outputs: out0 (groups[0]-bit) ... outN (groups[N]-bit)
  • Bus slicing: BusSlice
    • Attributes: slice.first, slice.count, slice.total (natural number)
    • Inputs: in (slice.total-bit)
    • Outputs: out (slice.count-bit)
  • Zero- and sign-extension: ZeroExtend, SignExtend
    • Attributes: extend.input, extend.output (natural number)
    • Inputs: in (extend.input-bit)
    • Outputs: out (extend.output-bit)
  • Finite state machines: FSM
    • Attributes: bits.in, bits.out, states, init_state, current_state (natural number), trans_table (array of transition descriptors)
    • Transition descriptor attributes: ctrl_in, ctrl_out (binary strings), state_in, state_out (natural numbers)
    • Inputs: clk (1-bit), arst (1-bit), in (bits.in-bit)
    • Outputs: out (bits.out-bit)

TODO

Some ideas for further developing the simulator.

  • Use JointJS elementTools for configuring/removing gates.
  • RAM/ROM import/export for Verilog format and Intel HEX.
  • Framebuffer element with character/bitmap display.
  • More editing capability: adding and removing blocks, modifying some of blocks' properties.
  • Undo-redo capability.
  • Saving and loading circuits, including layout and state.
  • Generic handling of negation for unary/binary gates (negation on inputs/outputs) for better clarity.
  • SVG export.
  • Verilog export.
  • Smartphone and tablet compatible UI.