entity ForInpAndGate is
port( a: in std_logic;
b: in std_logic;
c: in std_logic;
d: in std_logic;
o: out std_logic;
);
end ForInpAndGate;
architecture behavioral of ForInpAndGate is begin
process(a, b, c, d) begin
o <= a & b & c & d;
end process;
end behavioral;
I don't think it's too much worse, and I do like some features of VHDL, such as it being strongly typed and having typed enums.
It was originally developed to verify processor designs at DEC (Alpha etc.).
Unfortunately all the other features of system verilog are onl y implemented in commercial tools. I believe the Xilinx Vivado tools support most of it, the others are not really affordable if you are not at an academic institution (Modelsim/the Synopsis tools).
I'm not sure why the output is passed in at the start (I'm guessing it's like an out parameter in C#) and I don't understand what @(*) is, but that's surprisingly readable.
It's exactly like an out parameter. HDL modules tend to have a lot more outputs, partly because you can't easily group them into structures.
The main things that trip people up in Verilog coming from programming are the difference between synthesis and simulation, and the intrinsic parallelism with the two kinds of assignment operator.
There are all kinds of idioms that are syntactically valid Verilog that cannot be compiled to hardware. Usually you only use these while constructing a "testbench" to drive the simulated hardware.
There are also two kinds of assignment: = and <=. So for example, starting with a being set to 1 and b being set to zero:
b = a;
c = b+1;
results in c being set to 2.
always @(posedge clk)
b <= a;
c <= b+1;
end
results in b being set to a and c being set to 1: the value of b on the previous cycle plus 1. It also causes flip-flops to be inferred to hold b and c.
(Note that <= behaves differently depending on what's in the sensitivity list, which is also potentially very confusing!)
If I were still doing HDL design I'd advance my plan for modern object(bus)-orientated friendly HDL..
The output isn't really "passed in". Verilog doesn't have an idea of variables, it replaces what traditionally might be variables with "ports" (think the pins on a chip). So, input and output ports must all be defined as part of the module declaration.
The @(*) syntax is what's called the sensitivity list, it's saying that the state of the module should be recalculated whenever any of the inputs change. Other possible values might include something like @(posedge clk) if you have a clock signal called "clk" and you only want the outputs of the module to update on the rising edge of the clock signal. This is dramatically oversimplifying the insanely complex world of HDL, but it's ultimately not /that/ hard if you know your computer architecture fundamentals.
Verilog isn't a programming language. It is a hardware description language. It is used to describe the behavior of hardware. The output isn't "passed" out at the beginning. Rather, That line is indicates that there is an output and what it's name is. The @() indicates a sensitivity list. The block below is evaluated whenever the states of any signal in the sensitivity list are changed. The * is a wildcard character and signifies any signal in the block below. That feature was added in Verilog2001. Before that, you had to manually list any signal you wanted in the sensitivity list.
Nitpick: Verilog is a programming language (see especially testbenches) with syntax and a runtime geared towards modeling hardware. It allows simple creation of lightweight shared-everything threads (called processes, confusingly, and they are not OS threads or processes, they are local to the language runtime) which are used to model concurrent hardware. It has its own built-in scheduler that decides when to run each thread. It has numerous synchronization methods and events (wait, @, #12ns, etc.) in addition to plain-old shared memory that threads use to coordinate with each other, and block and trigger thread execution. When modeling digital circuits a single shared-memory variable, usually named clock or clk, is the one variable most of these threads synchronize to.
Mostly hardware designers get away without thinking about all those above details in those terms, but sometimes you get bit by them (race-conditions between threads can occur, sadly) and it helps to understand it.
All programming is modeling of some sort or another.
You can write Verilog as schematic-like description, but there is a higher-level of modeling supported by synthesis tools that doesn't look quite so netlist like.
This may be confirmation bias but I feel like since the Megaprocessor thread[1] I'm noticing an increase in hardware-simulation related posts. Can't think of them all off the top of my head, but see also:
I didn't know about them though. My project's inspiration is due to the fact that I love JS and had a computer system architecture course wherein I learnt VHDL.
I felt that the NodeJS Events API could probably help me simulate a `signal` driven system and thus, I started experimenting :)
Since nodejs is single threaded, you'll get the best results with synchronous logic. Even asynchronous systems are difficult to design in real life, so it's not a bad idea to use nodejs.
Looks like a cool project. And since it's based on javascript, it shouldn't be too difficult to add a graphical interface, so the system could be driven primarily by graphics instead of using text only. A graphical interface would vastly improve on productivity and open up hardware design to more than just hardware engineers. Heck, this might give FPGAs a boost in popularity.