Hi everyone, I spend a lot of time mashingĀ
away at a keyboard, trying to tell theĀ Ā computer what I would like it to do. EvenĀ
my oddly shaped computer (that constantlyĀ Ā gets teased for looking like a trash can) isĀ
unbelievably good at following instructions.Ā Ā Unfortunately Iām not so good at giving them,Ā
so the results are inevitably a little wonky,Ā Ā but nevertheless itās always been such aĀ
mysterious thing to me, that this inanimate lumpĀ Ā of metal and sand and whatever else, arranged inĀ
an some extremely clever way, is able to do maths,Ā Ā and logic and remember things, and ultimatelyĀ
allows us to create pretty much anything weĀ Ā set our minds to. Itās kinda bizarre, and IādĀ
really like to understand better how it works. So hereās a little circuit with a lightĀ
and two switches A and B, and clearly,Ā Ā the light can only go on if I close both of theseĀ
switches. Already this is a kind of simple logic:Ā Ā weāre testing if two conditions are true:Ā
switch A is closed, AND switch B is closed.Ā Ā If we represent an open switch withĀ
a zero, and closed switch with a 1,Ā Ā these are the different configurations we couldĀ
have, and hereās the output: 0 meaning the lightĀ Ā would be off, and 1 meaning itād be on. SinceĀ
thatās only the case when A AND B are 1, thisĀ Ā is known as the logical AND operation. This kindĀ
of table, by the way, is called a truth table. Hereās a bit of a different circuit ā this timeĀ
we only have 1 switch, and even though itās open,Ā Ā the light is currently on. If I close the switch,Ā
now the light will go off, because weāve createdĀ Ā an easier path for the current to travel. So weāreĀ
essentially inverting the input: if the state ofĀ Ā the switch is 0, the output is 1 and vice versa,Ā
and this is known as the logical NOT operation. Now Iāve been controlling these switchesĀ
with my fingers, which computers sadly lack,Ā Ā so in the very early days, electromagnetsĀ
were used to open and close the switches,Ā Ā but this was kinda clunky and slow, so then cameĀ
fancier technologies like vacuum tubes and finallyĀ Ā transistors. As a tiny example of what transistorsĀ
do, this is essentially that same NOT thing fromĀ Ā before, just setup on a breadboard, and with aĀ
transistor in the place of the paperclip switch. If we think of the current flowing in thisĀ
circuit, it would look something like this.Ā Ā It canāt flow through the transistor at theĀ
moment, because its currently acting as anĀ Ā open switch. However, if we send power to to theĀ
middle pin of the transistor, establishing a smallĀ Ā flow of current like this, the fancy physics ofĀ
the transistor will make it act like a closedĀ Ā switch instead, allowing the main current to flowĀ
through it like so. Like before, the light hasĀ Ā turned off because weāve created a much easierĀ
path for the current to take. So essentially,Ā Ā the transistor is a switch, which we can open andĀ
close with electricity instead of our fingers. ### Simulation
Iād love to one day try and build a simpleĀ Ā computer out of components like this ā which isĀ
what Ben Eater has done in his very cool 8bitĀ Ā breadboard computer series, but thatās a littleĀ
intimidating for me at the moment, so instead IāveĀ Ā made a simplified and abstracted little simulationĀ
where we have our two logical building blocks:Ā Ā AND and NOT, and we can play around and tryĀ
figure some stuff out. So on the left hereĀ Ā are some inputs, which can be turned on and off,Ā
or we can also think of it as true and false, orĀ Ā 1 and 0, it doesnāt really matter ā but Iāll wireĀ
these up to the inputs of the AND gate, and if youĀ Ā recall my sophisticated circuitry from earlier,Ā
the two inputs simply control whether theseĀ Ā switches are open or closed, which should achievedĀ
used transistors, not paperclips of course.Ā Ā Now Iāll connect the result of this ANDĀ
operation up to my output node over here,Ā Ā and so this will only light up if both inputs areĀ
on. Letās get the NOT gate participating as well,Ā Ā so Iāll connect it up over here, and wireĀ
the result of THAT to the output instead.Ā Ā So the output is now inverted: itās off whenĀ
both inputs are on, but in all other cases itsĀ Ā on. Hereās a truth table for this thing weāve justĀ
built, and it actually has a name: this is the NOTĀ Ā AND, or rather ā NAND gate. If I click on thisĀ
Create button down here, itāll package that upĀ Ā into its own little chip, and we now have a nandĀ
gate to mess about with. I guess this is a goodĀ Ā moment to mention NAND2Tetris, which along withĀ
Benās videos is a fantastic free resource IāveĀ Ā been using to learn more about this stuff. So IĀ
recommend checking that out if youāre interested. Anyway, to take this a little further weĀ
could maybe try inverting both of the inputsĀ Ā before feeding them into the nand gate, and letāsĀ
see what that does. So with both inputs off,Ā Ā the output is off, if I turn either of themĀ
on, the output goes on, and if both are on,Ā Ā the output is still on. So weāve created whatāsĀ
called an OR gate, and Iāll turn that into itsĀ Ā own little chip as well, because it seems prettyĀ
useful. And here is the truth table for that. All right, letās take a moment to think aboutĀ
something thatās pretty important to computers:Ā Ā numbers. In the decimal system that we know and love,Ā
there are 10 digits, zero through nine,Ā Ā and if we want to go higher than that,Ā
we need to add another place to the left,Ā Ā where each digit actually represents 10Ā
times as much as those in the previous spot.Ā Ā And we can have as many places as we need, soĀ
here would be 100s, then thousands, and so on. With electronics though, itās easier to workĀ
with just two digits, because they can beĀ Ā naturally represented with a low voltageĀ
or a high voltage. So the binary systemĀ Ā works in the exact same way as the decimalĀ
system, its just that once we reach one,Ā Ā weāve already run out of digits, andĀ
so we increment the place to the left.Ā Ā Because thereāre only two digits in binary:Ā
0 and 1, each place is worth 2x more thanĀ Ā the last. So if the first place is worth 1, thenĀ
this place is worth 2, then 4, then 8 and so on.Ā Ā So letās say we want to figure out what thisĀ
sequence: 1101 would be in decimal. Well,Ā Ā we can write it out as 8x1 + 4x1 +Ā
2x0 + 1 x 1. And that comes out to 13. Alright, now what Iād like to do is designĀ
something thatās able to add 2 binary numbersĀ Ā together. So letās work through a quick exampleĀ
by hand, say we want to add these two together:Ā Ā starting on the right here, 1 + 1 is is two, whichĀ
in binary is 10. So Iāll write the zero down here,Ā Ā and then carry the one over up here, becauseĀ
weāll need to add it together with these other twoĀ Ā to figure out what goes in this spot.Ā
By the way, this part that we wrote downĀ Ā here straight away Iāll refer to as the sumĀ
bit, and this one up here is the carry bit.Ā Ā Anyway, letās continue 1 + 1 is 2, plus the carryĀ
is gives us 3 in decimal, or 11 in binary. SoĀ Ā Iāll write one over here - thatās the sum bit, andĀ
carry the other one over to the left. Now we haveĀ Ā 0 plus 1, plus the carry bit is 2 again,Ā
so Iāll put 0 down here, and 1 up here.Ā Ā Thisāll just give us 1, so Iāll write that downĀ
here. Then 0 plus 0 is just 0, and finally,Ā Ā 1 plus 0 is one. In case you care to know,Ā
what weāve just calculated here is 35 + 7. Itās a little daunting to try start thinking aboutĀ
how we can wire our logic gates together to do allĀ Ā of this, so letās start small with adding togetherĀ
just two single bits. For example, if weāre addingĀ Ā a zero and a zero together, then naturally bothĀ
the carry bit and the sum bit will be zero.Ā But, if the first bit is zero and the second isĀ
one, or the other way around, then the carry bitĀ Ā will be zero and the sum bit will will be 1.
Finally if both bits are 1,Ā Ā then the carry will be 1, and the sum bit willĀ
be zero. So if we look at the carry column here,Ā Ā it might look familiar, because itās actuallyĀ
an exact match with the AND operation.Ā Ā The sum column on the other hand doesnāt matchĀ
exactly with anything weāve already seen, but itāsĀ Ā quite close to the OR gate we created earlier, itĀ
just has a 0 in this last spot instead of a 1. So,Ā Ā letās take that OR gate as a starting point,Ā
and we just need to turn the output to a zeroĀ Ā when both inputs are one. So Iām going to take aĀ
nand gate, and connect it up here, and this willĀ Ā check if both inputs are one, and then invert theĀ
result, so that itās outputting zero in that case.Ā Ā We can then use an AND gate to test if either ofĀ
the inputs, but not both of them, is one. LetāsĀ Ā test this quickly. With both inputs off, or zero,Ā
the output is zero. With just a single inputĀ Ā set to one, the output is one, but cruciallyĀ
when both inputs are one, the output will beĀ Ā zero again. This operation has a special name asĀ
well, itās called an exclusive OR. XOR for short. Okay, so I now have an empty chip with two inputs,Ā
which we want to add together, and two outputs:Ā Ā the sum bit, and the carry bit. So, we can useĀ
our new xor gate to calculate the sum bit ofĀ Ā the two inputs, and then remember that if bothĀ
inputs are 1, then the carry bit should be one,Ā Ā and so as we saw, we can simply use an AND gateĀ
to test for that. So thatās everything we needĀ Ā to add two bits together, but of course in some ofĀ
the steps we actually had 3 bits we needed to addĀ Ā together, because there was a carry bit from theĀ
previous step to deal with. And in fact we couldĀ Ā think of these other places as having zero in theĀ
carry spot, so really weāre always adding 3 bitsĀ Ā together. So, Iāll introduce a third input to theĀ
chip over here for the carry input, and we need toĀ Ā add this to the sum of the first two bits which weĀ
calculated up here. So, we can simply use anotherĀ Ā XOR gate, and Iāll wire that up to that carryĀ
input, and to the sum of the first two inputs. Weāll then need a second AND gate as well,Ā
because if sum of the first two bits is 1,Ā Ā AND the carry input is one, then weāllĀ
need to carry 1 to the next step.Ā Ā So if either of our two AND gates detect thatĀ
we should be carrying one to the next step, thenĀ Ā weāll want to output one to the carryĀ
output, which Iāll do using an OR gate. Letās check that this is working properly. SoĀ
with all of the inputs off, or zero, both theĀ Ā sum and carry output bits should be zero. Then,Ā
if any single input is 1, the sum should be 1, andĀ Ā the carry should be zero. So far, so good. Next,Ā
if any two inputs are 1, then the sum bit shouldĀ Ā be zero, and the carry should be 1. And finally,Ā
if all three inputs are 1, the sum should be 1,Ā Ā and the carry should be 1. And it looks like itsĀ
all working, so Iāll give it a name, and then whatĀ Ā Iād like to do is take this ADDER weāve made, andĀ
construct a 4BIT ADDER, capable of taking theseĀ Ā two 4-bit numbers that we have here as our inputs,Ā
and calculating the 4bit sum as the output.Ā Ā Iāve added little displays by the way toĀ
tell us what all these values are in decimal,Ā just so itās a bit easier toĀ
tell if this thing is working. Weāll need four adders to construct this,Ā
and Iāll wire each one up to the outputs.Ā Ā Then thereās a carry input here, just in caseĀ
we want to string two 4bit adders together toĀ Ā make an 8bit adder, for example, so that canĀ
go into the carry input of the first adder,Ā Ā and then its carry output goes intoĀ
the carry input of the next one,Ā Ā and so on down the chain. Finally IāllĀ
need to connect up the two 4bit inputs. Letās test this out, so right now we have 0 +Ā
0 = 0, which is a good start. Let me try 1 + 1,Ā Ā I believe 2 is correct! 5 + 1 is 6, and 7 + 1 isĀ
8. So, it looks like we can add numbers together,Ā Ā which is pretty cool. Of course with just 4 bits,Ā
if we try do 15 + 1 for example, it will overflowĀ Ā to zero because we donāt have enough bits to storeĀ
16, and the carry bit will light up over here. If we want to extend this to handle subtraction,Ā
weāll need a way to represent negative numbersĀ Ā in binary. I always assumed that this last spotĀ
was used to indicate the āsignā of the number.Ā Ā So what we have here would be positive 7, and thisĀ Ā would be -7. But of course youād expect that ifĀ
we added 7 to negative 7, weād end up with 0,Ā Ā but thatās clearly not the case here. So one wayĀ
we could try thinking about this, is what would weĀ Ā have to add to 7, in order to get 0 as the result?
Well in order to get a zero in the first spot,Ā Ā this would need to be a one, becauseĀ
remember 1 + 1 gives us a sum bit of zero.Ā Ā Of course we also now have to carry 1 to theĀ
next spot. So now we know that there should beĀ Ā a zero here, so that weāll again have 1+1 givingĀ
us zero for our sum bit. And a carry of 1. SoĀ Ā we can deduce that there should be a zero hereĀ
as well, and we can continue like this, to endĀ Ā up with all zeros for our 4 bits. There is a oneĀ
that ends up over here, but since weāre workingĀ Ā with just four bits, that can be discarded.Ā
So weāve figured out that -7 must be 1001Ā That might seem weird, but it actually makesĀ
some sense if we think of this last spot as theĀ Ā -8 place, because then we could write this out asĀ
-8 x 1 + 4 x 0 + 2 x 0 + 1 x 1. Which gives us -7.Ā Ā Letās start at zero and see whatĀ
it looks like now if we count up.Ā Ā So as you can see seven is now theĀ
largest number we can have with 4 bits,Ā Ā and then it flips over to the smallest number,Ā
-8. And from there we have -7, -6, -5, -4, -3, -2,Ā Ā and finally all ones would be -1. So itās aĀ
bit of a funky system, but it allows us to addĀ Ā negative and positive numbers together withoutĀ
any fuss, so itās totally worth the weirdness. Thereās actually a simple two-stepĀ
procedure for making any positiveĀ Ā number negative. Take the number positive 6Ā
for example, 0110 in binary. The first stepĀ Ā is to invert all the bits, so where thereās aĀ
zero we write a 1, and vice versa, giving us 1001.Ā Ā At this point if we were to add these two togetherĀ
weād obviously get all ones. We want it to beĀ Ā all zeros though. And we saw a few minutes agoĀ
that if we take this, and just add one to it,Ā Ā weāll end up with zero for the 4 bits weāreĀ
interested in. This tells us that clearly ourĀ Ā inverted number is just one too little to giveĀ
us all zeros. So the second step, as you mightĀ Ā predict, is to take the inverted number, andĀ
add one to it. So in this case weād take 1001Ā Ā and add one, giving us 1010. And if we look backĀ
at the number wheel, that is indeed negative six. So, using that 4bit adder we built, we can ofĀ
course add these two 4bit numbers together, butĀ Ā if this subtract signal over here is on, then IĀ
want to subtract the second number from the first,Ā Ā which we can do by making the second numberĀ
negative. And remember we do that by invertingĀ Ā the bits, and then adding one. So to invert theĀ
bits, we need something that looks at the subtractĀ Ā signal, and if thatās off, the input bit shouldĀ
be unchanged, but if the subtract signal is on,Ā Ā then the bit should be inverted. This tableĀ
actually matches the Exclusive OR we made earlier,Ā Ā so we can just use 4 of those to invert theseĀ
4 bits only if the subtract signal is on. The last step of negating a number wasĀ
to add one, so we can just feed theĀ Ā subtract signal into the carry input of theĀ
adder, and thatāll do that for us. Alright,Ā Ā Iāll quickly go ahead and wire up the restĀ
of the inputs, and then output the result.Ā Ā I also have these 3 extra outputs, and these areĀ
just for flagging some stuff about the result.Ā Ā This one over here for example tells us if theĀ
result was zero, and we can test for that like so.Ā Ā This other output tells us if the resultĀ
was negative, which is true if ourĀ Ā -8 bit is set to one. And finally thereāsĀ
the carry, which I can just take from her.Ā Ā So these flags just give us some information aboutĀ
the result, whichāll be useful to us later on.Ā Ā Letās test if this actually doing what we want, soĀ
Iāll try doing 3 + 4, and thatās 7 so we havenātĀ Ā broken addition at least. Now Iāll try turningĀ
on the subtract signal, so weāre now doingĀ Ā 3 + negative 4, which is the same thing as sayingĀ
3 minus 4, and the result is indeed negative 1,Ā Ā so thatās good. Let me try negative 2 - 4, andĀ
that gives us negative 6. Letās see if it canĀ Ā handle subtracting a negative number, so Iāll tryĀ
negative 2 minus negative 4. Even that seems toĀ Ā work, we get positive 2. I want to test one lastĀ
thing - adding two negative numbers together.Ā Ā And once again, the maths checks out. So thisĀ
is going to be our Arithmetic and logic unit.Ā Ā Although to be honest it doesnāt actually do anyĀ
logic, that would just be things like doing theĀ Ā AND operation on the inputs and outputtingĀ
that for example, but we can expand thisĀ Ā later if necessary. For now Iāll call it ALU forĀ
short, and package it up into a tiny little chip. So thatās going to be all for this first episode,Ā
I hope you found it interesting. In the next one IĀ Ā want to look at how memory works, Iām very curiousĀ
to learn more about that. Until then, cheers!
What software are you using to simulate those circuits? I want it!
Ben Eaters videos, which he mentioned, are so satisfying. I'd definitely recommend them. I ended up grabbing a circuit simulator and was able to follow along with some parts of it.
https://eater.net/8bit/
That was the best explanation of Two's Complement I've ever seen. The first time I learned about it I just kind of faked my understanding and I could see how it worked so I just went with it. But this explanation really made it clear why we use it.
This is a fantastic book if you want to know more
Computer Systems: A Programmers Perspective https://archive.org/details/ComputerSystems/
For those who want more, nand2tetris goes through all the wys from transistors to building playing a tetris game, from scratch. It's an amazing resource and I cannot reccomend it enough.
https://www.nand2tetris.org
For those of you who already know how to code but want more in depth content, destroy all software has many utterly amazing Screencasts showing simplified versions of many complex topics, like compilers, allocates, etc. I am actually going to use that as a Christmas wishlist item for myself.
https://www.destroyallsoftware.com/screencasts
Ok when do we get to
segmentation fault
and blue screens?Cat power.
for those interested in a similar software to follow along.
theres Logisim (no longver beign developed) http://www.cburch.com/logisim/index.html
Who are you ,so wise in ways of science?