<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://cpudev.org/w/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Demindiro</id>
	<title>CPUdev wiki - User contributions [en]</title>
	<link rel="self" type="application/atom+xml" href="https://cpudev.org/w/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Demindiro"/>
	<link rel="alternate" type="text/html" href="https://cpudev.org/wiki/Special:Contributions/Demindiro"/>
	<updated>2026-04-25T19:18:46Z</updated>
	<subtitle>User contributions</subtitle>
	<generator>MediaWiki 1.36.1</generator>
	<entry>
		<id>https://cpudev.org/w/index.php?title=File:Transport-triggered_architecture_example.png&amp;diff=36</id>
		<title>File:Transport-triggered architecture example.png</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=File:Transport-triggered_architecture_example.png&amp;diff=36"/>
		<updated>2025-05-03T21:54:34Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Demindiro uploaded a new version of File:Transport-triggered architecture example.png&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;An example of a TTA.&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=File:Transport-triggered_architecture_example.png&amp;diff=35</id>
		<title>File:Transport-triggered architecture example.png</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=File:Transport-triggered_architecture_example.png&amp;diff=35"/>
		<updated>2025-05-03T21:52:39Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Demindiro uploaded a new version of File:Transport-triggered architecture example.png&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;An example of a TTA.&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Transport_triggered_architecture&amp;diff=34</id>
		<title>Transport triggered architecture</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Transport_triggered_architecture&amp;diff=34"/>
		<updated>2025-05-03T21:49:42Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Created page with &amp;quot;A &amp;#039;&amp;#039;&amp;#039;Transport triggered architecture&amp;#039;&amp;#039;&amp;#039; (&amp;#039;&amp;#039;&amp;#039;TTA&amp;#039;&amp;#039;&amp;#039;) is a one instruction set computer which only moves data between various function units. It is a very minimal, simple a...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A &amp;#039;&amp;#039;&amp;#039;Transport triggered architecture&amp;#039;&amp;#039;&amp;#039; (&amp;#039;&amp;#039;&amp;#039;TTA&amp;#039;&amp;#039;&amp;#039;) is a [[one instruction set computer]] which only moves data between various function units. It is a very minimal, simple and flexible type of architecture.&lt;br /&gt;
&lt;br /&gt;
A typical TTA consists of one or more transport buses, with various units attached to these buses. Each instruction configures the source and destination, i.e. moves data over the buses.&lt;br /&gt;
Certain data movements may trigger an attached unit to perform an action, hence &amp;#039;&amp;#039;transport triggered&amp;#039;&amp;#039;.&lt;br /&gt;
&lt;br /&gt;
TTAs expose a lot of microarchitectural details which are otherwise abstracted in more typical architectures. Due to this, (assembly) code written for a specific TTA tends to be non-portable.&lt;br /&gt;
&lt;br /&gt;
[[File:Transport-triggered architecture example.png|thumb|An example of a TTA. Note that many more configurations are possible, including with multiple transport buses.]]&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=File:Transport-triggered_architecture_example.png&amp;diff=33</id>
		<title>File:Transport-triggered architecture example.png</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=File:Transport-triggered_architecture_example.png&amp;diff=33"/>
		<updated>2025-05-03T21:47:40Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;An example of a TTA.&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=User:Demindiro/Ramblings/Massively_concurrent_Stack-Stack-Machine&amp;diff=32</id>
		<title>User:Demindiro/Ramblings/Massively concurrent Stack-Stack-Machine</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=User:Demindiro/Ramblings/Massively_concurrent_Stack-Stack-Machine&amp;diff=32"/>
		<updated>2025-04-05T12:45:35Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Dump of a potentially silly idea&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;#039;&amp;#039;&amp;#039;Out-of-Order Execution&amp;#039;&amp;#039;&amp;#039; and &amp;#039;&amp;#039;&amp;#039;Simultaneous Multi-Threading&amp;#039;&amp;#039;&amp;#039; has been on my mind for a while, with many ideas on how to address it best. Below is one of my ideas in text form.&lt;br /&gt;
&lt;br /&gt;
== Latency, OoOE, SMT and architectural state ==&lt;br /&gt;
&lt;br /&gt;
As transistors shrink, processors get faster and faster. However, for practical it is still necessary to communicate with external components such as DRAM. Processor speed improves much faster than the latency between processor and external components. Nowadays processor are so large even latency with on-chip cache is a significant factor.&lt;br /&gt;
&lt;br /&gt;
Most high-performance processors address these challenges with out-of-order execution: instructions later in the stream can be executed ahead of earlier instructions so long they do not depend on them.&lt;br /&gt;
Enabling OoOE requires several large and fast structures. How far a processor core can execute ahead depends entirely on the size of these structures.&lt;br /&gt;
&lt;br /&gt;
Another technique is simultaneous multi-threading: one processor core can evaluate multiple instruction streams simultaneously. Hence, if one stream is blocked on long-latency instructions, the other can continue being evaluated.&lt;br /&gt;
SMT allows sharing execution resources but requires duplicating &amp;#039;&amp;#039;&amp;#039;architectural state&amp;#039;&amp;#039;&amp;#039;, in particular registers. Depending on the complexity of the core, this may be a large or small cost. In particular, advanced OoOE processors tend to have at least 2-way SMT, with the extra state consuming a relatively small amount of die space.&lt;br /&gt;
&lt;br /&gt;
SMT is not always beneficial: most (all?) implementations try to ensure fair scheduling, interleaving instructions from all streams. This may leads to cache thrashing and severely degrade the performance of some applications. On the other hand, it will perform much better than only OoOE if threads are often stalled waiting on memory operations to finish.&lt;br /&gt;
&lt;br /&gt;
What if we could mitigate the cache thrashing? An interesting analogy is &amp;#039;&amp;#039;&amp;#039;fair&amp;#039;&amp;#039;&amp;#039; versus &amp;#039;&amp;#039;&amp;#039;unfair&amp;#039;&amp;#039;&amp;#039; mutexes: unfair mutexes tend to lead to higher throughput by allowing threads with data already in cache to continue executing, significantly improving cache utilization. On the other hand, it may cause unpredictable delays for certain tasks, which is why fair mutexes, at least by default, are often preferred.&lt;br /&gt;
&lt;br /&gt;
If (user) applications had explicit control over SMT then perhaps it would be practical to have &amp;quot;unfair&amp;quot; scheduling for SMT too, reducing cache thrashing. But what should the interface look like? Ideally there would be no arbitrary limits on the amount of threads an application can schedule at once.&lt;br /&gt;
The most significant limit here is the amount of architectural state: having too much both bloats a core and makes task switching costlier, as more state needs to be (explicitly) saved to memory.&lt;br /&gt;
&lt;br /&gt;
What if we required only the absolute minimum amount of state?&lt;br /&gt;
&lt;br /&gt;
== Stack machines and stack of tasks ==&lt;br /&gt;
&lt;br /&gt;
A stack machine requires only a tiny amount of state: a program counter and a stack pointer is sufficient. This makes switching tasks very cheap.&lt;br /&gt;
&lt;br /&gt;
On the other hand, it requires very frequent access to memory, specifically the stack. This makes OoOE impractical. However, with massive and cheap concurrency the need for OoOE might be avoided altogether.&lt;br /&gt;
&lt;br /&gt;
How can we achieve this massive concurrency? We can use a stack of tasks that are ready to run. The top-most entries are removed from the stack if the processor is able to schedule them. Tasks that are waiting on a operation remain in internal processor state.&lt;br /&gt;
&lt;br /&gt;
Since tasks have very little architectural state it is cheap to implement the fork-join paradigm: push a pointer to a stack and an instruction address and off it goes! (TODO: what about joins? And how to cheaply allocate new stack space? Would a bump allocator + copying GC work? Or an arena?)&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Hardware_Description_Language&amp;diff=31</id>
		<title>Hardware Description Language</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Hardware_Description_Language&amp;diff=31"/>
		<updated>2025-03-22T11:29:43Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: /* List of HDLs */ Add Calyx&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A &amp;lt;strong&amp;gt;hardware description language&amp;lt;/strong&amp;gt;, or &amp;lt;strong&amp;gt;HDL&amp;lt;/strong&amp;gt;, is a tool to describe the behavior of electronic circuits.&lt;br /&gt;
&lt;br /&gt;
While intended for simulation, most (all?) HDLs are also usable to synthesize physical circuits. However, beware some languages support constructs that cannot actually be translated to a physical circuit.&lt;br /&gt;
&lt;br /&gt;
The most common HDL is [[Verilog]], followed by [[VHDL]]. Many other HDLs are translated to Verilog under the hood.&lt;br /&gt;
&lt;br /&gt;
== Simulation ==&lt;br /&gt;
&lt;br /&gt;
[[Verilator]]&lt;br /&gt;
&lt;br /&gt;
== Synthesis ==&lt;br /&gt;
&lt;br /&gt;
[[Yosys]]&lt;br /&gt;
&lt;br /&gt;
== List of HDLs ==&lt;br /&gt;
&lt;br /&gt;
This list is incomplete. Feel free to add more entries.&lt;br /&gt;
&lt;br /&gt;
{|class=&amp;quot;wikitable sortable&amp;quot;&lt;br /&gt;
|+ Caption text&lt;br /&gt;
|-&lt;br /&gt;
! Name !! Simulation !! Synthesis !! Allows non-synthesizable constructs&lt;br /&gt;
|-&lt;br /&gt;
| [https://calyxir.org/ Calyx]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://www.chisel-lang.org/ Chisel]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://clash-lang.org/ Clash]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://www.myhdl.org/ MyHDL]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://rust-hdl.org/ RustHDL]&lt;br /&gt;
| Yes&lt;br /&gt;
| Yes&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://github.com/SpinalHDL/SpinalHDL SpinalHDL]&lt;br /&gt;
| Yes&lt;br /&gt;
| Yes&lt;br /&gt;
| ?&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
=== External references ===&lt;br /&gt;
&lt;br /&gt;
* [https://github.com/drom/awesome-hdl Awesome Hardware Description Languages] - a list of HDLs and associated tools&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Hardware_Description_Language&amp;diff=30</id>
		<title>Hardware Description Language</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Hardware_Description_Language&amp;diff=30"/>
		<updated>2025-03-21T20:55:27Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: /* List of HDLs */ replace &amp;quot;type system&amp;quot; with &amp;quot;allows non-synthesizable constructs&amp;quot;, which is the more interesting property.&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A &amp;lt;strong&amp;gt;hardware description language&amp;lt;/strong&amp;gt;, or &amp;lt;strong&amp;gt;HDL&amp;lt;/strong&amp;gt;, is a tool to describe the behavior of electronic circuits.&lt;br /&gt;
&lt;br /&gt;
While intended for simulation, most (all?) HDLs are also usable to synthesize physical circuits. However, beware some languages support constructs that cannot actually be translated to a physical circuit.&lt;br /&gt;
&lt;br /&gt;
The most common HDL is [[Verilog]], followed by [[VHDL]]. Many other HDLs are translated to Verilog under the hood.&lt;br /&gt;
&lt;br /&gt;
== Simulation ==&lt;br /&gt;
&lt;br /&gt;
[[Verilator]]&lt;br /&gt;
&lt;br /&gt;
== Synthesis ==&lt;br /&gt;
&lt;br /&gt;
[[Yosys]]&lt;br /&gt;
&lt;br /&gt;
== List of HDLs ==&lt;br /&gt;
&lt;br /&gt;
This list is incomplete. Feel free to add more entries.&lt;br /&gt;
&lt;br /&gt;
{|class=&amp;quot;wikitable sortable&amp;quot;&lt;br /&gt;
|+ Caption text&lt;br /&gt;
|-&lt;br /&gt;
! Name !! Simulation !! Synthesis !! Allows non-synthesizable constructs&lt;br /&gt;
|-&lt;br /&gt;
| [https://www.chisel-lang.org/ Chisel]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://clash-lang.org/ Clash]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://www.myhdl.org/ MyHDL]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://rust-hdl.org/ RustHDL]&lt;br /&gt;
| Yes&lt;br /&gt;
| Yes&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://github.com/SpinalHDL/SpinalHDL SpinalHDL]&lt;br /&gt;
| Yes&lt;br /&gt;
| Yes&lt;br /&gt;
| ?&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
=== External references ===&lt;br /&gt;
&lt;br /&gt;
* [https://github.com/drom/awesome-hdl Awesome Hardware Description Languages] - a list of HDLs and associated tools&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Hardware_Description_Language&amp;diff=29</id>
		<title>Hardware Description Language</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Hardware_Description_Language&amp;diff=29"/>
		<updated>2025-03-21T20:53:07Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: /* List of HDLs */ sortable table + feature matrix&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A &amp;lt;strong&amp;gt;hardware description language&amp;lt;/strong&amp;gt;, or &amp;lt;strong&amp;gt;HDL&amp;lt;/strong&amp;gt;, is a tool to describe the behavior of electronic circuits.&lt;br /&gt;
&lt;br /&gt;
While intended for simulation, most (all?) HDLs are also usable to synthesize physical circuits. However, beware some languages support constructs that cannot actually be translated to a physical circuit.&lt;br /&gt;
&lt;br /&gt;
The most common HDL is [[Verilog]], followed by [[VHDL]]. Many other HDLs are translated to Verilog under the hood.&lt;br /&gt;
&lt;br /&gt;
== Simulation ==&lt;br /&gt;
&lt;br /&gt;
[[Verilator]]&lt;br /&gt;
&lt;br /&gt;
== Synthesis ==&lt;br /&gt;
&lt;br /&gt;
[[Yosys]]&lt;br /&gt;
&lt;br /&gt;
== List of HDLs ==&lt;br /&gt;
&lt;br /&gt;
This list is incomplete. Feel free to add more entries.&lt;br /&gt;
&lt;br /&gt;
{|class=&amp;quot;wikitable sortable&amp;quot;&lt;br /&gt;
|+ Caption text&lt;br /&gt;
|-&lt;br /&gt;
! Name !! Simulation !! Synthesis !! Type system&lt;br /&gt;
|-&lt;br /&gt;
| [https://www.chisel-lang.org/ Chisel]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://clash-lang.org/ Clash]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://www.myhdl.org/ MyHDL]&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
| ?&lt;br /&gt;
|-&lt;br /&gt;
| [https://rust-hdl.org/ RustHDL]&lt;br /&gt;
| Yes&lt;br /&gt;
| Yes&lt;br /&gt;
| Static, strong&lt;br /&gt;
|-&lt;br /&gt;
| [https://github.com/SpinalHDL/SpinalHDL SpinalHDL]&lt;br /&gt;
| Yes&lt;br /&gt;
| Yes&lt;br /&gt;
| Static, strong&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
=== External references ===&lt;br /&gt;
&lt;br /&gt;
* [https://github.com/drom/awesome-hdl Awesome Hardware Description Languages] - a list of HDLs and associated tools&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Hardware_Description_Language&amp;diff=28</id>
		<title>Hardware Description Language</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Hardware_Description_Language&amp;diff=28"/>
		<updated>2025-03-21T20:35:46Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Created page with &amp;quot;A &amp;lt;strong&amp;gt;hardware description language&amp;lt;/strong&amp;gt;, or &amp;lt;strong&amp;gt;HDL&amp;lt;/strong&amp;gt;, is a tool to describe the behavior of electronic circuits.  While intended for simulation, most (all...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A &amp;lt;strong&amp;gt;hardware description language&amp;lt;/strong&amp;gt;, or &amp;lt;strong&amp;gt;HDL&amp;lt;/strong&amp;gt;, is a tool to describe the behavior of electronic circuits.&lt;br /&gt;
&lt;br /&gt;
While intended for simulation, most (all?) HDLs are also usable to synthesize physical circuits. However, beware some languages support constructs that cannot actually be translated to a physical circuit.&lt;br /&gt;
&lt;br /&gt;
The most common HDL is [[Verilog]], followed by [[VHDL]]. Many other HDLs are translated to Verilog under the hood.&lt;br /&gt;
&lt;br /&gt;
== Simulation ==&lt;br /&gt;
&lt;br /&gt;
[[Verilator]]&lt;br /&gt;
&lt;br /&gt;
== Synthesis ==&lt;br /&gt;
&lt;br /&gt;
[[Yosys]]&lt;br /&gt;
&lt;br /&gt;
== List of HDLs ==&lt;br /&gt;
&lt;br /&gt;
This list is incomplete. Feel free to add more entries.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;em&amp;gt;Please keep the list alphabetic.&amp;lt;/em&amp;gt;&lt;br /&gt;
&lt;br /&gt;
* [https://www.chisel-lang.org/ Chisel]&lt;br /&gt;
* [https://clash-lang.org/ Clash]&lt;br /&gt;
* [https://www.myhdl.org/ MyHDL]&lt;br /&gt;
* [https://rust-hdl.org/ RustHDL]&lt;br /&gt;
* [https://github.com/SpinalHDL/SpinalHDL SpinalHDL]&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
=== External references ===&lt;br /&gt;
&lt;br /&gt;
* [https://github.com/drom/awesome-hdl Awesome Hardware Description Languages] - a list of HDLs and associated tools&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Instruction_encoding&amp;diff=26</id>
		<title>Instruction encoding</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Instruction_encoding&amp;diff=26"/>
		<updated>2025-03-19T20:34:00Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Hardwired zero register&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;There are many different ways to encode instructions, all with their own tradeoffs.&lt;br /&gt;
&lt;br /&gt;
== Considerations ==&lt;br /&gt;
&lt;br /&gt;
=== Fixed-width or variable-length ===&lt;br /&gt;
&lt;br /&gt;
Even among variable-length ISAs there is a broad spectrum in complexity. For example, x86 is notorious for being difficult to decode. In contrast, RISC-V is also variable-length but trivial to decode.&lt;br /&gt;
&lt;br /&gt;
=== Instruction density ===&lt;br /&gt;
&lt;br /&gt;
Large instructions can encode many things but have poor density, while smaller instructions have good density but may not be able to encode many things.&lt;br /&gt;
&lt;br /&gt;
Of particular note is the amount of directly addressable registers: a larger amount of registers requires more bits to encode, leaving less to encode other things.&lt;br /&gt;
&lt;br /&gt;
=== Instruction formats ===&lt;br /&gt;
&lt;br /&gt;
To reduce decoding complexity it is wise to define a few fixed formats, which all instructions should be defined in terms of.&lt;br /&gt;
&lt;br /&gt;
== Techniques ==&lt;br /&gt;
&lt;br /&gt;
=== Variable-length encoding ===&lt;br /&gt;
&lt;br /&gt;
To keep decoding variable-length instructions simple one can use a fixed prefix of a few bits.&lt;br /&gt;
&lt;br /&gt;
For example, an ISA with 8, 16 and 24-bit instructions could be encoded as:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
        23    16  15     8  7      0&lt;br /&gt;
 8-bit                      xxxxxxx0&lt;br /&gt;
16-bit            xxxxxxxx  xxxxxx01&lt;br /&gt;
24-bit  xxxxxxxx  xxxxxxxx  xxxxx011&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Hardwired zero register ===&lt;br /&gt;
&lt;br /&gt;
A substantial amount of instructions can be omitted by having a register which always reads 0.&lt;br /&gt;
&lt;br /&gt;
=== Implicit destination registers ===&lt;br /&gt;
&lt;br /&gt;
Instead of having explicitly named registers, one can instead have a queue of registers and address source registers relative to the &amp;quot;instruction distance&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
Aside from being useful for out-of-order processors, this also avoids the need to encode a destination, freeing bits for other purposes.&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Pipelining&amp;diff=24</id>
		<title>Pipelining</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Pipelining&amp;diff=24"/>
		<updated>2025-03-19T19:39:43Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Fix example clockrate&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A limiting factor in CPU performance is transistor &amp;#039;&amp;#039;&amp;#039;propagation delay&amp;#039;&amp;#039;&amp;#039;: the amount of time it takes for a signal to traverse from start to end.&lt;br /&gt;
Hence, reducing the delay before a signal can hit a storage cell allows increasing clock speed.&lt;br /&gt;
&lt;br /&gt;
For example, take the time profile a naive CPU design which executes a single instruction per cycle, at 0.33MHz:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
             0µs    1µs    2µs    3µs    4µs    5µs    6µs    7µs    8µs    9µs&lt;br /&gt;
add x1,x5    |--------------------|&lt;br /&gt;
ror x2,x4                         |--------------------|&lt;br /&gt;
xor x1,x3                                              |--------------------|&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
By splitting instruction fetch, decode, and execute into separate stages we might be able to increase the clock rate to 1.00MHz:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
             0µs    1µs    2µs    3µs    4µs    5µs    6µs    7µs    8µs    9µs&lt;br /&gt;
add x1,x5    |--IF--|--ID--|--EX--|&lt;br /&gt;
ror x2,x4                         |--IF--|--ID--|--EX--|&lt;br /&gt;
xor x1,x3                                              |--IF--|--ID--|--EX--|&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Note that the fetch, decode and execute stages are independent. We can overlap these stages...:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
             0µs    1µs    2µs    3µs    4µs    5µs    6µs    7µs    8µs    9µs&lt;br /&gt;
add x1,x5    |--IF--|--ID--|--EX--|&lt;br /&gt;
ror x2,x4           |--IF--|--ID--|--EX--|&lt;br /&gt;
xor x1,x3                  |--IF--|--ID--|--EX--|&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
... reducing total execution time from 9µs to 5µs!&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Pipelining&amp;diff=23</id>
		<title>Pipelining</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Pipelining&amp;diff=23"/>
		<updated>2025-03-18T20:30:09Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Draft&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A limiting factor in CPU performance is transistor &amp;#039;&amp;#039;&amp;#039;propagation delay&amp;#039;&amp;#039;&amp;#039;: the amount of time it takes for a signal to traverse from start to end.&lt;br /&gt;
Hence, reducing the delay before a signal can hit a storage cell allows increasing clock speed.&lt;br /&gt;
&lt;br /&gt;
For example, take the time profile a naive CPU design which executes a single instruction per cycle, at 0.5MHz:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
             0µs    1µs    2µs    3µs    4µs    5µs    6µs    7µs    8µs    9µs&lt;br /&gt;
add x1,x5    |--------------------|&lt;br /&gt;
ror x2,x4                         |--------------------|&lt;br /&gt;
xor x1,x3                                              |--------------------|&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
By splitting instruction fetch, decode, and execute into separate stages we might be able to increase the clock rate to 1.5MHz:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
             0µs    1µs    2µs    3µs    4µs    5µs    6µs    7µs    8µs    9µs&lt;br /&gt;
add x1,x5    |--IF--|--ID--|--EX--|&lt;br /&gt;
ror x2,x4                         |--IF--|--ID--|--EX--|&lt;br /&gt;
xor x1,x3                                              |--IF--|--ID--|--EX--|&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Note that the fetch, decode and execute stages are independent. We can overlap these stages...:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
             0µs    1µs    2µs    3µs    4µs    5µs    6µs    7µs    8µs    9µs&lt;br /&gt;
add x1,x5    |--IF--|--ID--|--EX--|&lt;br /&gt;
ror x2,x4           |--IF--|--ID--|--EX--|&lt;br /&gt;
xor x1,x3                  |--IF--|--ID--|--EX--|&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
... reducing total execution time from 9µs to 5µs!&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=RISC_vs_CISC&amp;diff=22</id>
		<title>RISC vs CISC</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=RISC_vs_CISC&amp;diff=22"/>
		<updated>2025-03-18T20:12:26Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Draft&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Contemporary usage of the terms RISC and CISC is muddy, but originally referred to the amount of operations a single instruction could (or should) do.&lt;br /&gt;
&lt;br /&gt;
For example, swapping values between a register and a memory location on a RISC machine may be done as:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
ld.w  x3,[x2]    ; 1 cycle&lt;br /&gt;
st.w  [x2],x1    ; 1 cycle&lt;br /&gt;
mv    x1,x3      ; 1 cycle&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Whereas on a CISC machine it might be done as:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
xchg  x1,[x2]    ; 3 cycles&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
RISC cores tend to be smaller and simpler, allowing higher clock speeds to be achieved. CISC cores tend to be more complex but usually have better code density.&lt;br /&gt;
&lt;br /&gt;
In practice, modern ISAs are a hybrid between the two approaches, with both simple and complex instructions.&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Instruction_encoding&amp;diff=21</id>
		<title>Instruction encoding</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Instruction_encoding&amp;diff=21"/>
		<updated>2025-03-18T19:59:37Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Draft&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;There are many different ways to encode instructions, all with their own tradeoffs.&lt;br /&gt;
&lt;br /&gt;
== Considerations ==&lt;br /&gt;
&lt;br /&gt;
=== Fixed-width or variable-length ===&lt;br /&gt;
&lt;br /&gt;
Even among variable-length ISAs there is a broad spectrum in complexity. For example, x86 is notorious for being difficult to decode. In contrast, RISC-V is also variable-length but trivial to decode.&lt;br /&gt;
&lt;br /&gt;
=== Instruction density ===&lt;br /&gt;
&lt;br /&gt;
Large instructions can encode many things but have poor density, while smaller instructions have good density but may not be able to encode many things.&lt;br /&gt;
&lt;br /&gt;
Of particular note is the amount of directly addressable registers: a larger amount of registers requires more bits to encode, leaving less to encode other things.&lt;br /&gt;
&lt;br /&gt;
=== Instruction formats ===&lt;br /&gt;
&lt;br /&gt;
To reduce decoding complexity it is wise to define a few fixed formats, which all instructions should be defined in terms of.&lt;br /&gt;
&lt;br /&gt;
== Techniques ==&lt;br /&gt;
&lt;br /&gt;
=== Variable-length encoding ===&lt;br /&gt;
&lt;br /&gt;
To keep decoding variable-length instructions simple one can use a fixed prefix of a few bits.&lt;br /&gt;
&lt;br /&gt;
For example, an ISA with 8, 16 and 24-bit instructions could be encoded as:&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
        23    16  15     8  7      0&lt;br /&gt;
 8-bit                      xxxxxxx0&lt;br /&gt;
16-bit            xxxxxxxx  xxxxxx01&lt;br /&gt;
24-bit  xxxxxxxx  xxxxxxxx  xxxxx011&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Implicit destination registers ===&lt;br /&gt;
&lt;br /&gt;
Instead of having explicitly named registers, one can instead have a queue of registers and address source registers relative to the &amp;quot;instruction distance&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
Aside from being useful for out-of-order processors, this also avoids the need to encode a destination, freeing bits for other purposes.&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=File:Alu.png&amp;diff=20</id>
		<title>File:Alu.png</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=File:Alu.png&amp;diff=20"/>
		<updated>2023-02-27T19:10:35Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Demindiro uploaded a new version of File:Alu.png&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Symbolic representation of an ALU&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=ALU&amp;diff=19</id>
		<title>ALU</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=ALU&amp;diff=19"/>
		<updated>2023-02-27T18:06:47Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: /* Overview */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;An ALU (Arithmetic Logic Unit) is a circuit for performing various integer operations.&lt;br /&gt;
It is an essential component of any CPU.&lt;br /&gt;
&lt;br /&gt;
It does not perform operations on floating point numbers, which is handled by a [[FPU]] instead.&lt;br /&gt;
&lt;br /&gt;
= Overview =&lt;br /&gt;
&lt;br /&gt;
[[File:Alu.png|thumb]]&lt;br /&gt;
&lt;br /&gt;
A typical ALU has:&lt;br /&gt;
&lt;br /&gt;
* 2 integer inputs.&lt;br /&gt;
* 1 integer output.&lt;br /&gt;
* 1 opcode selection input.&lt;br /&gt;
* 1 status input.&lt;br /&gt;
* 1 status output.&lt;br /&gt;
&lt;br /&gt;
The status signal is used to indicate carry/overflow/...&lt;br /&gt;
&lt;br /&gt;
An ALU may have more than 2 inputs. For example, fused multiply-add requires 3 input operands.&lt;br /&gt;
Likewise, an ALU may have more than 1 output, e.g. to calculate both quotient and remainder in one operation.&lt;br /&gt;
&lt;br /&gt;
= Common operations =&lt;br /&gt;
&lt;br /&gt;
== Bitwise AND, OR, XOR ==&lt;br /&gt;
&lt;br /&gt;
These operations simply involve wiring each bit to the corresponding gate.&lt;br /&gt;
&lt;br /&gt;
== Shift/rotate left/right ==&lt;br /&gt;
&lt;br /&gt;
Shifting or rotating a number by a fixed amount of bits simply involves wiring each input bit to its corresponding output bit.&lt;br /&gt;
&lt;br /&gt;
Shifting by a variable amount is trickier, especially for large numbers.&lt;br /&gt;
Using a single multiplexer will require an excessive amount of wires and gates to support every possible rotation.&lt;br /&gt;
&lt;br /&gt;
A sequence multiple small multiplexers can be used, each shifting the number by &amp;lt;code&amp;gt;x * 2&amp;lt;sup&amp;gt;y&amp;lt;/sup&amp;gt;&amp;lt;/code&amp;gt;.&lt;br /&gt;
While this is slower it saves a lot on gates.&lt;br /&gt;
&lt;br /&gt;
 # Right shifter for 8 bits numbers.&lt;br /&gt;
 s4 = y[2] ? (x &amp;gt;&amp;gt; 4) : x&lt;br /&gt;
 s2 = y[1] ? (s4 &amp;gt;&amp;gt; 2) : s4&lt;br /&gt;
 s1 = y[0] ? (s2 &amp;gt;&amp;gt; 1) : s2&lt;br /&gt;
&lt;br /&gt;
== Addition ==&lt;br /&gt;
&lt;br /&gt;
An adder is composed of multiple 1-bit adders.&lt;br /&gt;
Each of these 1-bit adders has &amp;#039;&amp;#039;three&amp;#039;&amp;#039; inputs and &amp;#039;&amp;#039;two&amp;#039;&amp;#039; outputs.&lt;br /&gt;
&lt;br /&gt;
The addition of two 1-bit numbers has a 2-bit result.&lt;br /&gt;
The high bit is called the &amp;#039;&amp;#039;&amp;#039;carry&amp;#039;&amp;#039;&amp;#039;.&lt;br /&gt;
For multi-bit adder this carry is &amp;#039;&amp;#039;carried&amp;#039;&amp;#039; to the next 1-bit adder.&lt;br /&gt;
&lt;br /&gt;
The LSb (&amp;lt;code&amp;gt;out&amp;lt;/code&amp;gt;) can be calculated by XORing all three input bits together.&lt;br /&gt;
The MSb (&amp;lt;code&amp;gt;carry_out&amp;lt;/code&amp;gt;) can be calculated by testing whether two or more bits are 1.&lt;br /&gt;
&lt;br /&gt;
 out = in_a ^ in_b ^ carry_in&lt;br /&gt;
 carry_out = (in_a &amp;amp; in_b) | (in_b &amp;amp; carry_in) | (carry_in &amp;amp; in_a)&lt;br /&gt;
&lt;br /&gt;
Note that:&lt;br /&gt;
* &amp;lt;code&amp;gt;(x &amp;amp; z) | (y &amp;amp; z) = (x | y) &amp;amp; z&amp;lt;/code&amp;gt;&lt;br /&gt;
* &amp;lt;code&amp;gt;x | y = (x ^ y) | (x &amp;amp; y)&amp;lt;/code&amp;gt;&lt;br /&gt;
* &amp;lt;code&amp;gt;x &amp;amp; !x = 1&amp;lt;/code&amp;gt;&lt;br /&gt;
&lt;br /&gt;
From which follows:&lt;br /&gt;
&lt;br /&gt;
    (in_a &amp;amp; in_b) | (in_b &amp;amp; carry_in) | (carry_in &amp;amp; in_a)&lt;br /&gt;
  = (in_a &amp;amp; in_b) | ((in_a | in_b) &amp;amp; carry_in)&lt;br /&gt;
  = (in_a &amp;amp; in_b) | (((in_a ^ in_b) | (in_a &amp;amp; in_b)) &amp;amp; carry_in)&lt;br /&gt;
  = (in_a &amp;amp; in_b) | ((in_a ^ in_b) &amp;amp; carry_in) | ((in_a &amp;amp; in_b) &amp;amp; carry_in)&lt;br /&gt;
  = (in_a &amp;amp; in_b) | ((in_a ^ in_b) &amp;amp; carry_in)&lt;br /&gt;
&lt;br /&gt;
Hence we can save a few gates by using the result of &amp;lt;code&amp;gt;in_a ^ in_b&amp;lt;/code&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 t = in_a ^ in_b&lt;br /&gt;
 out = t ^ carry_in&lt;br /&gt;
 carry_out = (in_a &amp;amp; in_b) | (t &amp;amp; carry_in)&lt;br /&gt;
&lt;br /&gt;
=== Faster addition ===&lt;br /&gt;
&lt;br /&gt;
While chaining 1-bit adders is a cheap &amp;amp; easy way to implement a multi-bit adder,&lt;br /&gt;
it is also slow as the signal must propagate from the lowest to the highest bit.&lt;br /&gt;
To speed this up a &amp;#039;&amp;#039;carry-lookahead&amp;#039;&amp;#039; is used.&lt;br /&gt;
&lt;br /&gt;
This lookahead computes the carry for multiple bits up,&lt;br /&gt;
which allows using multiple small multi-bit adders in parallel.&lt;br /&gt;
&lt;br /&gt;
Suppose that &amp;lt;code&amp;gt;g = x &amp;amp; y&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;p = x ^ y&amp;lt;/code&amp;gt;, then:&lt;br /&gt;
&lt;br /&gt;
 c = (x &amp;amp; y) | ((x ^ y) &amp;amp; z) = g | (p &amp;amp; z)&lt;br /&gt;
&lt;br /&gt;
Since we chain each 1-bit adder:&lt;br /&gt;
&lt;br /&gt;
 c1 = g0 | (p0 &amp;amp; c0)&lt;br /&gt;
 c2 = g1 | (p1 &amp;amp; c1)&lt;br /&gt;
 c3 = g2 | (p2 &amp;amp; c2)&lt;br /&gt;
 ...&lt;br /&gt;
&lt;br /&gt;
If we fully work out &amp;lt;code&amp;gt;c&amp;lt;/code&amp;gt; on the right side of each expression we get:&lt;br /&gt;
&lt;br /&gt;
 c1 = g0 | (p0 &amp;amp; c0)&lt;br /&gt;
 c2 = g1 | (p1 &amp;amp; c1)&lt;br /&gt;
    = g1 | (p1 &amp;amp; (g0 | (p0 &amp;amp; c0)))&lt;br /&gt;
    = g1 | (p1 &amp;amp; g0) | (p1 &amp;amp; p0 &amp;amp; c0)&lt;br /&gt;
 c3 = g2 | (p2 &amp;amp; c1)&lt;br /&gt;
    = g2 | (p2 &amp;amp; (g1 | (p1 &amp;amp; g0) | (p1 &amp;amp; p0 &amp;amp; c0)))&lt;br /&gt;
    = g2 | (p2 &amp;amp; g1) | (p2 &amp;amp; p1 &amp;amp; g0) | (p2 &amp;amp; p1 &amp;amp; p0 &amp;amp; c0)&lt;br /&gt;
 ...&lt;br /&gt;
&lt;br /&gt;
We can group the &amp;lt;code&amp;gt;p&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;g&amp;lt;/code&amp;gt; signals:&lt;br /&gt;
&lt;br /&gt;
 P = ... p2 &amp;amp; p1 &amp;amp; p0&lt;br /&gt;
 G = ... (... p2 &amp;amp; g1) | (... p2 &amp;amp; p1 &amp;amp; g0)&lt;br /&gt;
&lt;br /&gt;
And calculate the final carry signal:&lt;br /&gt;
&lt;br /&gt;
 C = G | (P &amp;amp; c0)&lt;br /&gt;
&lt;br /&gt;
=== Addition in HDLs &amp;amp; simulators ===&lt;br /&gt;
&lt;br /&gt;
Note that most HDLs &amp;amp; simulators already provide a component for performing addition.&lt;br /&gt;
This component should be preferred as it can be synthesized more efficiently than a manual implementation&lt;br /&gt;
(e.g. by using built-in adders or other components in FPGAs, such as Xilinx&amp;#039;s CARRY4).&lt;br /&gt;
&lt;br /&gt;
== Subtraction ==&lt;br /&gt;
&lt;br /&gt;
For two-complements arithmetic subtraction can be done with &amp;lt;code&amp;gt;a - b = a + (-b)&amp;lt;/code&amp;gt;.&lt;br /&gt;
&amp;lt;code&amp;gt;-b&amp;lt;/code&amp;gt; is equivalent to &amp;lt;code&amp;gt;~b + 1&amp;lt;/code&amp;gt;, i.e. apply bitwise NOT to &amp;lt;code&amp;gt;b&amp;lt;/code&amp;gt; and add 1.&lt;br /&gt;
Adding 1 can be done by setting the carry high.&lt;br /&gt;
&lt;br /&gt;
== Equality ==&lt;br /&gt;
&lt;br /&gt;
The cheapest way to test for equality is by using bitwise XOR:&lt;br /&gt;
if two numbers are equal, their XOR is 0.&lt;br /&gt;
If not, it is nonzero.&lt;br /&gt;
Then do a bitwise OR of all bits. If 1, the numbers are not equal.&lt;br /&gt;
&lt;br /&gt;
== Less Than ==&lt;br /&gt;
&lt;br /&gt;
For unsigned arithmetic a Less Than test can be done with a subtraction and checking the carry bit.&lt;br /&gt;
&lt;br /&gt;
::&amp;#039;&amp;#039;&amp;#039;TODO&amp;#039;&amp;#039;&amp;#039; signed arithmetic requires checking carry and high bit IIRC?&lt;br /&gt;
&lt;br /&gt;
== Multiplication ==&lt;br /&gt;
&lt;br /&gt;
== Division ==&lt;br /&gt;
&lt;br /&gt;
= Pitfalls =&lt;br /&gt;
&lt;br /&gt;
== Division operation in Verilog, VHDL et al. ==&lt;br /&gt;
&lt;br /&gt;
It may be tempting to use the division operator directly (e.g. &amp;lt;code&amp;gt;alu_o = alu_a / alu_b&amp;lt;/code&amp;gt;).&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Do not do this&amp;#039;&amp;#039;&amp;#039; as it will generate a huge and slow combinatorial circuit.&lt;br /&gt;
&lt;br /&gt;
Instead do each part of the division step by step, one step per clock cycle.&lt;br /&gt;
&lt;br /&gt;
= See Also =&lt;br /&gt;
&lt;br /&gt;
* [[Binary arithmetic]]&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=File:Alu.png&amp;diff=18</id>
		<title>File:Alu.png</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=File:Alu.png&amp;diff=18"/>
		<updated>2023-02-27T17:58:37Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Symbolic representation of an ALU&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=ALU&amp;diff=17</id>
		<title>ALU</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=ALU&amp;diff=17"/>
		<updated>2023-02-18T15:33:55Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: First draft of ALU page.&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;An ALU (Arithmetic Logic Unit) is a circuit for performing various integer operations.&lt;br /&gt;
It is an essential component of any CPU.&lt;br /&gt;
&lt;br /&gt;
It does not perform operations on floating point numbers, which is handled by a [[FPU]] instead.&lt;br /&gt;
&lt;br /&gt;
= Overview =&lt;br /&gt;
&lt;br /&gt;
= Common operations =&lt;br /&gt;
&lt;br /&gt;
== Bitwise AND, OR, XOR ==&lt;br /&gt;
&lt;br /&gt;
These operations simply involve wiring each bit to the corresponding gate.&lt;br /&gt;
&lt;br /&gt;
== Shift/rotate left/right ==&lt;br /&gt;
&lt;br /&gt;
Shifting or rotating a number by a fixed amount of bits simply involves wiring each input bit to its corresponding output bit.&lt;br /&gt;
&lt;br /&gt;
Shifting by a variable amount is trickier, especially for large numbers.&lt;br /&gt;
Using a single multiplexer will require an excessive amount of wires and gates to support every possible rotation.&lt;br /&gt;
&lt;br /&gt;
A sequence multiple small multiplexers can be used, each shifting the number by &amp;lt;code&amp;gt;x * 2&amp;lt;sup&amp;gt;y&amp;lt;/sup&amp;gt;&amp;lt;/code&amp;gt;.&lt;br /&gt;
While this is slower it saves a lot on gates.&lt;br /&gt;
&lt;br /&gt;
 # Right shifter for 8 bits numbers.&lt;br /&gt;
 s4 = y[2] ? (x &amp;gt;&amp;gt; 4) : x&lt;br /&gt;
 s2 = y[1] ? (s4 &amp;gt;&amp;gt; 2) : s4&lt;br /&gt;
 s1 = y[0] ? (s2 &amp;gt;&amp;gt; 1) : s2&lt;br /&gt;
&lt;br /&gt;
== Addition ==&lt;br /&gt;
&lt;br /&gt;
An adder is composed of multiple 1-bit adders.&lt;br /&gt;
Each of these 1-bit adders has &amp;#039;&amp;#039;three&amp;#039;&amp;#039; inputs and &amp;#039;&amp;#039;two&amp;#039;&amp;#039; outputs.&lt;br /&gt;
&lt;br /&gt;
The addition of two 1-bit numbers has a 2-bit result.&lt;br /&gt;
The high bit is called the &amp;#039;&amp;#039;&amp;#039;carry&amp;#039;&amp;#039;&amp;#039;.&lt;br /&gt;
For multi-bit adder this carry is &amp;#039;&amp;#039;carried&amp;#039;&amp;#039; to the next 1-bit adder.&lt;br /&gt;
&lt;br /&gt;
The LSb (&amp;lt;code&amp;gt;out&amp;lt;/code&amp;gt;) can be calculated by XORing all three input bits together.&lt;br /&gt;
The MSb (&amp;lt;code&amp;gt;carry_out&amp;lt;/code&amp;gt;) can be calculated by testing whether two or more bits are 1.&lt;br /&gt;
&lt;br /&gt;
 out = in_a ^ in_b ^ carry_in&lt;br /&gt;
 carry_out = (in_a &amp;amp; in_b) | (in_b &amp;amp; carry_in) | (carry_in &amp;amp; in_a)&lt;br /&gt;
&lt;br /&gt;
Note that:&lt;br /&gt;
* &amp;lt;code&amp;gt;(x &amp;amp; z) | (y &amp;amp; z) = (x | y) &amp;amp; z&amp;lt;/code&amp;gt;&lt;br /&gt;
* &amp;lt;code&amp;gt;x | y = (x ^ y) | (x &amp;amp; y)&amp;lt;/code&amp;gt;&lt;br /&gt;
* &amp;lt;code&amp;gt;x &amp;amp; !x = 1&amp;lt;/code&amp;gt;&lt;br /&gt;
&lt;br /&gt;
From which follows:&lt;br /&gt;
&lt;br /&gt;
    (in_a &amp;amp; in_b) | (in_b &amp;amp; carry_in) | (carry_in &amp;amp; in_a)&lt;br /&gt;
  = (in_a &amp;amp; in_b) | ((in_a | in_b) &amp;amp; carry_in)&lt;br /&gt;
  = (in_a &amp;amp; in_b) | (((in_a ^ in_b) | (in_a &amp;amp; in_b)) &amp;amp; carry_in)&lt;br /&gt;
  = (in_a &amp;amp; in_b) | ((in_a ^ in_b) &amp;amp; carry_in) | ((in_a &amp;amp; in_b) &amp;amp; carry_in)&lt;br /&gt;
  = (in_a &amp;amp; in_b) | ((in_a ^ in_b) &amp;amp; carry_in)&lt;br /&gt;
&lt;br /&gt;
Hence we can save a few gates by using the result of &amp;lt;code&amp;gt;in_a ^ in_b&amp;lt;/code&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 t = in_a ^ in_b&lt;br /&gt;
 out = t ^ carry_in&lt;br /&gt;
 carry_out = (in_a &amp;amp; in_b) | (t &amp;amp; carry_in)&lt;br /&gt;
&lt;br /&gt;
=== Faster addition ===&lt;br /&gt;
&lt;br /&gt;
While chaining 1-bit adders is a cheap &amp;amp; easy way to implement a multi-bit adder,&lt;br /&gt;
it is also slow as the signal must propagate from the lowest to the highest bit.&lt;br /&gt;
To speed this up a &amp;#039;&amp;#039;carry-lookahead&amp;#039;&amp;#039; is used.&lt;br /&gt;
&lt;br /&gt;
This lookahead computes the carry for multiple bits up,&lt;br /&gt;
which allows using multiple small multi-bit adders in parallel.&lt;br /&gt;
&lt;br /&gt;
Suppose that &amp;lt;code&amp;gt;g = x &amp;amp; y&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;p = x ^ y&amp;lt;/code&amp;gt;, then:&lt;br /&gt;
&lt;br /&gt;
 c = (x &amp;amp; y) | ((x ^ y) &amp;amp; z) = g | (p &amp;amp; z)&lt;br /&gt;
&lt;br /&gt;
Since we chain each 1-bit adder:&lt;br /&gt;
&lt;br /&gt;
 c1 = g0 | (p0 &amp;amp; c0)&lt;br /&gt;
 c2 = g1 | (p1 &amp;amp; c1)&lt;br /&gt;
 c3 = g2 | (p2 &amp;amp; c2)&lt;br /&gt;
 ...&lt;br /&gt;
&lt;br /&gt;
If we fully work out &amp;lt;code&amp;gt;c&amp;lt;/code&amp;gt; on the right side of each expression we get:&lt;br /&gt;
&lt;br /&gt;
 c1 = g0 | (p0 &amp;amp; c0)&lt;br /&gt;
 c2 = g1 | (p1 &amp;amp; c1)&lt;br /&gt;
    = g1 | (p1 &amp;amp; (g0 | (p0 &amp;amp; c0)))&lt;br /&gt;
    = g1 | (p1 &amp;amp; g0) | (p1 &amp;amp; p0 &amp;amp; c0)&lt;br /&gt;
 c3 = g2 | (p2 &amp;amp; c1)&lt;br /&gt;
    = g2 | (p2 &amp;amp; (g1 | (p1 &amp;amp; g0) | (p1 &amp;amp; p0 &amp;amp; c0)))&lt;br /&gt;
    = g2 | (p2 &amp;amp; g1) | (p2 &amp;amp; p1 &amp;amp; g0) | (p2 &amp;amp; p1 &amp;amp; p0 &amp;amp; c0)&lt;br /&gt;
 ...&lt;br /&gt;
&lt;br /&gt;
We can group the &amp;lt;code&amp;gt;p&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;g&amp;lt;/code&amp;gt; signals:&lt;br /&gt;
&lt;br /&gt;
 P = ... p2 &amp;amp; p1 &amp;amp; p0&lt;br /&gt;
 G = ... (... p2 &amp;amp; g1) | (... p2 &amp;amp; p1 &amp;amp; g0)&lt;br /&gt;
&lt;br /&gt;
And calculate the final carry signal:&lt;br /&gt;
&lt;br /&gt;
 C = G | (P &amp;amp; c0)&lt;br /&gt;
&lt;br /&gt;
=== Addition in HDLs &amp;amp; simulators ===&lt;br /&gt;
&lt;br /&gt;
Note that most HDLs &amp;amp; simulators already provide a component for performing addition.&lt;br /&gt;
This component should be preferred as it can be synthesized more efficiently than a manual implementation&lt;br /&gt;
(e.g. by using built-in adders or other components in FPGAs, such as Xilinx&amp;#039;s CARRY4).&lt;br /&gt;
&lt;br /&gt;
== Subtraction ==&lt;br /&gt;
&lt;br /&gt;
For two-complements arithmetic subtraction can be done with &amp;lt;code&amp;gt;a - b = a + (-b)&amp;lt;/code&amp;gt;.&lt;br /&gt;
&amp;lt;code&amp;gt;-b&amp;lt;/code&amp;gt; is equivalent to &amp;lt;code&amp;gt;~b + 1&amp;lt;/code&amp;gt;, i.e. apply bitwise NOT to &amp;lt;code&amp;gt;b&amp;lt;/code&amp;gt; and add 1.&lt;br /&gt;
Adding 1 can be done by setting the carry high.&lt;br /&gt;
&lt;br /&gt;
== Equality ==&lt;br /&gt;
&lt;br /&gt;
The cheapest way to test for equality is by using bitwise XOR:&lt;br /&gt;
if two numbers are equal, their XOR is 0.&lt;br /&gt;
If not, it is nonzero.&lt;br /&gt;
Then do a bitwise OR of all bits. If 1, the numbers are not equal.&lt;br /&gt;
&lt;br /&gt;
== Less Than ==&lt;br /&gt;
&lt;br /&gt;
For unsigned arithmetic a Less Than test can be done with a subtraction and checking the carry bit.&lt;br /&gt;
&lt;br /&gt;
::&amp;#039;&amp;#039;&amp;#039;TODO&amp;#039;&amp;#039;&amp;#039; signed arithmetic requires checking carry and high bit IIRC?&lt;br /&gt;
&lt;br /&gt;
== Multiplication ==&lt;br /&gt;
&lt;br /&gt;
== Division ==&lt;br /&gt;
&lt;br /&gt;
= Pitfalls =&lt;br /&gt;
&lt;br /&gt;
== Division operation in Verilog, VHDL et al. ==&lt;br /&gt;
&lt;br /&gt;
It may be tempting to use the division operator directly (e.g. &amp;lt;code&amp;gt;alu_o = alu_a / alu_b&amp;lt;/code&amp;gt;).&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Do not do this&amp;#039;&amp;#039;&amp;#039; as it will generate a huge and slow combinatorial circuit.&lt;br /&gt;
&lt;br /&gt;
Instead do each part of the division step by step, one step per clock cycle.&lt;br /&gt;
&lt;br /&gt;
= See Also =&lt;br /&gt;
&lt;br /&gt;
* [[Binary arithmetic]]&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Binary_arithmetic&amp;diff=16</id>
		<title>Binary arithmetic</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Binary_arithmetic&amp;diff=16"/>
		<updated>2023-02-18T13:32:04Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: First draft. Written under the assumption that readers are not familiar with binary arithmetic yet, so heavy on examples.&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;As the name digital implies, digital computers work on on bits with a value of either 0 or 1.&lt;br /&gt;
Accordingly, all operations, including arithmetic, operate on 0 or 1 values.&lt;br /&gt;
&lt;br /&gt;
Numbers that consists only of 0 or 1s are called &amp;#039;&amp;#039;&amp;#039;binary&amp;#039;&amp;#039;&amp;#039; or &amp;#039;&amp;#039;&amp;#039;base2&amp;#039;&amp;#039;&amp;#039; numbers.&lt;br /&gt;
Binary numbers are often suffixed with a subscript 2, for example 1011011&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
= Converting between decimal and binary =&lt;br /&gt;
&lt;br /&gt;
== Decimal as a sum of powers of 10 ==&lt;br /&gt;
&lt;br /&gt;
Any decimal number can be written as a sum of power of 10s.&lt;br /&gt;
For example:&lt;br /&gt;
&lt;br /&gt;
* 42 = 4*10&amp;lt;sup&amp;gt;1&amp;lt;/sup&amp;gt; + 4*10&amp;lt;sup&amp;gt;0&amp;lt;/sup&amp;gt;&lt;br /&gt;
* 57005 = 5*10&amp;lt;sup&amp;gt;4&amp;lt;/sup&amp;gt; + 7*10&amp;lt;sup&amp;gt;3&amp;lt;/sup&amp;gt; + 0*10&amp;lt;sup&amp;gt;2&amp;lt;/sup&amp;gt; + 0*10&amp;lt;sup&amp;gt;1&amp;lt;/sup&amp;gt; + 5*10&amp;lt;sup&amp;gt;0&amp;lt;/sup&amp;gt;&lt;br /&gt;
* 48.879 = 4*10&amp;lt;sup&amp;gt;1&amp;lt;/sup&amp;gt; + 8*10&amp;lt;sup&amp;gt;0&amp;lt;/sup&amp;gt; + 8*10&amp;lt;sup&amp;gt;-1&amp;lt;/sup&amp;gt; + 7*10&amp;lt;sup&amp;gt;-2&amp;lt;/sup&amp;gt; + 9*10&amp;lt;sup&amp;gt;-3&amp;lt;/sup&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Binary numbers can be written in the same way though with powers of 2 instead of 10.&lt;br /&gt;
&lt;br /&gt;
== Converting from binary to decimal ==&lt;br /&gt;
&lt;br /&gt;
* 1010&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt; = 1*2&amp;lt;sup&amp;gt;3&amp;lt;/sup&amp;gt; + 0*2&amp;lt;sup&amp;gt;2&amp;lt;/sup&amp;gt; + 1*2&amp;lt;sup&amp;gt;1&amp;lt;/sup&amp;gt; + 0*2&amp;lt;sup&amp;gt;0&amp;lt;/sup&amp;gt; = 8 + 2 = 10&lt;br /&gt;
* 100.01&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt; = 2&amp;lt;sup&amp;gt;2&amp;lt;/sup&amp;gt; + 2&amp;lt;sup&amp;gt;-2&amp;lt;/sup&amp;gt; = 4 + 1/4 = 4.25&lt;br /&gt;
&lt;br /&gt;
== Converting from decimal to binary ==&lt;br /&gt;
&lt;br /&gt;
# Divide the decimal number by 2.&lt;br /&gt;
# Append the remainder to the &amp;#039;&amp;#039;left&amp;#039;&amp;#039; of the binary number.&lt;br /&gt;
# Repeat with quotient as dividend until it is 0.&lt;br /&gt;
&lt;br /&gt;
For example:&lt;br /&gt;
&lt;br /&gt;
* 29 = 11101&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
** 29 / 2 = 14, remainder 1&lt;br /&gt;
** 14 / 2 = 7, remainder 0&lt;br /&gt;
** 7 / 2 = 3, remainder 1&lt;br /&gt;
** 3 / 2 = 1, remainder 1&lt;br /&gt;
** 1 / 2 = 0, remainder 1&lt;br /&gt;
&lt;br /&gt;
The same technique can be used for rational numbers.&lt;br /&gt;
&lt;br /&gt;
# First multiply by some power of 2 to convert it to an integer.&lt;br /&gt;
# Apply above procedure.&lt;br /&gt;
# Divide by the same power of 2 to get the correct result.&lt;br /&gt;
&lt;br /&gt;
= Mathematical operations =&lt;br /&gt;
&lt;br /&gt;
The same techniques used for addition, multiplication ... used for decimal numbers can also be used for binary numbers.&lt;br /&gt;
&lt;br /&gt;
== Addition &amp;amp; subtraction ==&lt;br /&gt;
&lt;br /&gt;
   22       10110&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
 + 19     + 10011&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
 ----     --------&lt;br /&gt;
   41      101001&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Multiplication ==&lt;br /&gt;
&lt;br /&gt;
   12         1100&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
 *  5       *  101&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
 ----       -------&lt;br /&gt;
   10         1100&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
 + 50            0&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
 ----     + 110000&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
   60     ---------&lt;br /&gt;
             111100&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Division ==&lt;br /&gt;
&lt;br /&gt;
   372 | 5        101110100 | 101&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
 - 35  +----    - 101       +---------&lt;br /&gt;
 ----  | 74     -----       | 1001010&amp;lt;sub&amp;gt;2&amp;lt;/sub&amp;gt;&lt;br /&gt;
    22 |            01      |&lt;br /&gt;
  - 20 |         -   0      |&lt;br /&gt;
  ---- |         -----      |&lt;br /&gt;
     2 |             11     |&lt;br /&gt;
                  -   0     |&lt;br /&gt;
                  -----     |&lt;br /&gt;
                     110    |&lt;br /&gt;
                   - 101    |&lt;br /&gt;
                   -----    |&lt;br /&gt;
                       11   |&lt;br /&gt;
                    -   0   |&lt;br /&gt;
                    -----   |&lt;br /&gt;
                       110  |&lt;br /&gt;
                     - 101  |&lt;br /&gt;
                     -----  |&lt;br /&gt;
                         10 |&lt;br /&gt;
                      -   0 |&lt;br /&gt;
                      ----- |&lt;br /&gt;
                         10 |&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=Ethernet&amp;diff=15</id>
		<title>Ethernet</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=Ethernet&amp;diff=15"/>
		<updated>2023-02-17T20:39:26Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: Quick draft of Ethernet page&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Ethernet is a &amp;#039;&amp;#039;wired&amp;#039;&amp;#039; protocol for connecting many devices in a network such that they can transfer data between each other.&lt;br /&gt;
It defines both the physical layers (10BASE-T, 100BASE-TX ...) as well the data format of an Ethernet packet &amp;amp; frame.&lt;br /&gt;
&lt;br /&gt;
= Ethernet packet &amp;amp; frame =&lt;br /&gt;
&lt;br /&gt;
There are two major formats of ethernet &amp;#039;&amp;#039;packets&amp;#039;&amp;#039;:&lt;br /&gt;
the regular variant which supports MTUs (Maximum Transmission Unit) of up to 1500 bytes&lt;br /&gt;
and &amp;quot;jumbo frames&amp;quot;, which support MTUs of up to 9000 bytes.&lt;br /&gt;
The latter are only supported for gigabit links and higher.&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Note:&amp;#039;&amp;#039;&amp;#039; each byte is transmitted starting from its LSb to its MSb.&lt;br /&gt;
&lt;br /&gt;
== Ethernet packet ==&lt;br /&gt;
&lt;br /&gt;
Every Ethernet packet starts with a preamble.&lt;br /&gt;
This preamble is a repeated pattern of &amp;lt;code&amp;gt;01010101&amp;lt;/code&amp;gt; bits (hex: &amp;lt;code&amp;gt;0x55&amp;lt;/code&amp;gt;).&lt;br /&gt;
This pattern is used to synchronize the clock as well as signal to the receiver a frame is about to be transmitted.&lt;br /&gt;
The preamble consists of 7 bytes.&lt;br /&gt;
&lt;br /&gt;
Immediately followed after the preamble is the SFD (Start Frame Delimiter).&lt;br /&gt;
This byte has the value &amp;lt;code&amp;gt;01110101&amp;lt;/code&amp;gt; (&amp;lt;code&amp;gt;0xd5&amp;lt;/code&amp;gt;) and indicates the start of the Ethernet Frame.&lt;br /&gt;
&lt;br /&gt;
After the Ethernet Frame there is an IPG (InterPacket Gap) of 12 bytes during which no data is sent whatsoever.&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
|+ Ethernet packet&lt;br /&gt;
|-&lt;br /&gt;
! Preamble !! SFD !! Ethernet frame !! IPG&lt;br /&gt;
|-&lt;br /&gt;
| 0x55, 7 times || 0xd5 || ... || 12 bytes of nothing&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
== Ethernet frame ==&lt;br /&gt;
&lt;br /&gt;
An Ethernet frame is at least 64 bytes long.&lt;br /&gt;
&lt;br /&gt;
Each frame ends with a FCS (Frame Check Sequence) which is a CRC32 of all preceding frame data.&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
|+ Ethernet frame&lt;br /&gt;
|-&lt;br /&gt;
! Destination MAC address !! Source MAC address !! EtherType !! Payload !! FCS&lt;br /&gt;
|-&lt;br /&gt;
| 6 bytes || 6 bytes || 2 bytes || At least 46 bytes || 4 bytes&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
The &amp;quot;EtherType&amp;quot; &amp;lt;code&amp;gt;0x8100&amp;lt;/code&amp;gt; indicate a 802.1Q tag is present, in which case the format is as follows:&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
|+ Ethernet frame with 802.1Q tag&lt;br /&gt;
|-&lt;br /&gt;
! Destination MAC address !! Source MAC address !! 802.1Q tag !! EtherType !! Payload !! FCS&lt;br /&gt;
|-&lt;br /&gt;
| 6 bytes || 6 bytes || 4 bytes || 2 bytes || At least 42 bytes || 4 bytes&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
The &amp;quot;real&amp;quot; EtherType is located right after the tag.&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
|+ 802.1Q tag&lt;br /&gt;
|-&lt;br /&gt;
! TPID !! TCI&lt;br /&gt;
|-&lt;br /&gt;
| 0x8100 || ...&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
= Interfaces =&lt;br /&gt;
&lt;br /&gt;
There are various types of interfaces to interact with Ethernet controllers.&lt;br /&gt;
&lt;br /&gt;
== Media Independent Interface (MII) ==&lt;br /&gt;
&lt;br /&gt;
The MII is the most common type of interface. Several variants exists for higher speeds or lower pin count.&lt;br /&gt;
&lt;br /&gt;
=== Standard ===&lt;br /&gt;
&lt;br /&gt;
The standard MII interfaces supports 10BASE-T and 100BASE-TX.&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
|+ MII pins&lt;br /&gt;
|-&lt;br /&gt;
! Pin(s) !! Description&lt;br /&gt;
|-&lt;br /&gt;
| TX_CLK || Transmission clock. Must be used when sending data.&lt;br /&gt;
|-&lt;br /&gt;
| TXD[0:3] || 4 bits of data to transmit if TX_EN is high.&lt;br /&gt;
|-&lt;br /&gt;
| TX_EN || When high, transmit data.&lt;br /&gt;
|-&lt;br /&gt;
| TX_ER || When high, force a transmission error.&lt;br /&gt;
|-&lt;br /&gt;
| RX_CLK || Receive clock. Must be used when receiving data.&lt;br /&gt;
|-&lt;br /&gt;
| RXD[0:3] || 4 bits of received data when RX_DV is high.&lt;br /&gt;
|-&lt;br /&gt;
| RX_DV || Whether data is currently being received.&lt;br /&gt;
|-&lt;br /&gt;
| RX_ER || Whether an error occured during reception.&lt;br /&gt;
|-&lt;br /&gt;
| CRS || Carrier sense. TODO&lt;br /&gt;
|-&lt;br /&gt;
| COL || Collision detect. TODO&lt;br /&gt;
|-&lt;br /&gt;
| MDIO&lt;br /&gt;
|-&lt;br /&gt;
| MDC&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
When receiving or sending data, the &amp;#039;&amp;#039;&amp;#039;high&amp;#039;&amp;#039;&amp;#039; nibble (4 bits) is sent first, then the low nibble.&lt;br /&gt;
&lt;br /&gt;
It is possible some bytes of the preamble may be missing on reception. This may happen if the controller detects the signal late.&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=UART&amp;diff=14</id>
		<title>UART</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=UART&amp;diff=14"/>
		<updated>2023-02-17T16:32:09Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: First draft of UART page&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;UART (Universal Asynchronous Receiver-Transmitter) is a simple protocol for exchanging data between two devices. It uses one line for transmitting and one receiving data.&lt;br /&gt;
&lt;br /&gt;
= Clock rate &amp;amp; encoding =&lt;br /&gt;
&lt;br /&gt;
The clock rate &amp;amp; encoding must be configured beforehand on both devices, as UART does not provide a way to negotiate settings.&lt;br /&gt;
&lt;br /&gt;
There are several ways to encode the data.&lt;br /&gt;
The encoding is usually indicated as &amp;lt;code&amp;gt;&amp;amp;lt;Hz&amp;amp;gt; &amp;amp;lt;data bits&amp;amp;gt;&amp;amp;lt;parity&amp;amp;gt;&amp;amp;lt;stop bits&amp;amp;gt;&amp;lt;/code&amp;gt;&lt;br /&gt;
&lt;br /&gt;
For example, &amp;lt;code&amp;gt;9600 8N1&amp;lt;/code&amp;gt; indicates a clock of 9600Hz with 8 data bits, no parity bit and 1 stop bit. &amp;lt;code&amp;gt;38400 7E2&amp;lt;/code&amp;gt; indicates a clock of 38400Hz, 7 data bits, 1 even parity bit and 2 stop bits.&lt;br /&gt;
&lt;br /&gt;
The parity bit is used for error detection. It can detect a single bit flip during transmission.&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
|+ Parity bit encodings&lt;br /&gt;
|-&lt;br /&gt;
! Letter !! Description&lt;br /&gt;
|-&lt;br /&gt;
| N || No parity bit&lt;br /&gt;
|-&lt;br /&gt;
| E || Even parity bit. 0 if even amount of data bits with value of 1, otherwise 1.&lt;br /&gt;
|-&lt;br /&gt;
| O || Odd parity bit. 1 if even amount of data bits with value of 1, otherwise 0.&lt;br /&gt;
|-&lt;br /&gt;
| M || Mark. TODO&lt;br /&gt;
|-&lt;br /&gt;
| P || Space. TODO&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
By default (&amp;#039;&amp;#039;&amp;#039;idle&amp;#039;&amp;#039;&amp;#039;), the line must be pulled high. When data is about to be transmitted, the line must be pulled low (&amp;#039;&amp;#039;&amp;#039;start&amp;#039;&amp;#039;&amp;#039;). Then the &amp;#039;&amp;#039;&amp;#039;data&amp;#039;&amp;#039;&amp;#039; and &amp;#039;&amp;#039;&amp;#039;parity&amp;#039;&amp;#039;&amp;#039; bits must be sent. Finally, the &amp;#039;&amp;#039;&amp;#039;stop&amp;#039;&amp;#039;&amp;#039; bit(s) must be sent which will pull the line high, completing the transaction.&lt;br /&gt;
&lt;br /&gt;
[[File:UART state machine &amp;amp; waveform example.png]]&lt;br /&gt;
&lt;br /&gt;
= Tools =&lt;br /&gt;
&lt;br /&gt;
On Linux, you can use minicom to communicate with a UART-enabled device. It allows you to configure the encoding &amp;amp; data rate and save the settings to a file.&lt;br /&gt;
&lt;br /&gt;
If the device is connected over USB, it will show up as &amp;lt;code&amp;gt;/dev/ttyUSBX&amp;lt;/code&amp;gt;, where X is some integer.&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
	<entry>
		<id>https://cpudev.org/w/index.php?title=File:UART_state_machine_%26_waveform_example.png&amp;diff=13</id>
		<title>File:UART state machine &amp; waveform example.png</title>
		<link rel="alternate" type="text/html" href="https://cpudev.org/w/index.php?title=File:UART_state_machine_%26_waveform_example.png&amp;diff=13"/>
		<updated>2023-02-17T16:29:01Z</updated>

		<summary type="html">&lt;p&gt;Demindiro: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;UART state machine &amp;amp; waveform example&lt;/div&gt;</summary>
		<author><name>Demindiro</name></author>
	</entry>
</feed>