
Addressing
As mentioned earlier, each memory cell has its unique address, which is the guarantee of the uniqueness of each cell. An address is usually represented in a hexadecimal form because it's shorter and it's faster to convert to binary rather than decimal numbers. A program that is loaded into virtual memory operates and sees logical addresses. These addresses, also called virtual addresses, are fake and provided by the OS, which translates them to physical addresses when needed. To optimize the translation, the CPU provides Translation Lookaside Buffer, a part of its Memory Management Unit (MMU). Translation Lookaside Buffer caches recent translations of virtual addresses to physical addresses. So the efficient address translation is a software/hardware task. We will dive into the address structure and translation details in Chapter 5, Memory Management and Smart Pointers.
The length of the address defines the size of total the memory that can be operated by the system. When you encounter statements such as a 32 bits system or a 64 bits system, it actually means the length of the address, that is, the address is 32 bits or 64 bits long. The longer the address, the bigger the memory. To make things clear, let's compare an 8 bits long address with a 32 bits long one. As agreed earlier, each memory cell is able to store 1 byte of data and has a unique address. If the address length is 8 bits, the address of the first memory cell is all zeros— 0000 0000. The address of the next cell is greater by one, that is, it's 0000 0001, and so on.
The biggest value that can be represented by 8 bits is 1111 1111. So, how many memory cells can be represented with an address length of 8 bits? This question is worth answering in more detail. How many different values can be represented by 1 bit? Two! Why so? Because 1 bit can represent either 1 or 0. How many different values can be represented by 2 bits? Well, 00 is one value, 01 is another value, 10, and finally, 11. So, four different values in total can be represented by 2 bits. Let's make a table:
We can see a pattern here. Each position (each bit) in a number can have two values, so we can calculate the number of different values represented by N bits by finding 2N; therefore, the number of different values represented by 8 bits is 28 = 256. This means that an 8 bits system can address up to 256 memory cells. On the other hand, a 32-bit system is able to address 232 = 4 294 967 296 memory cells, each storing 1 byte of data, that is, storing 4294967296 * 1 byte = 4 GB of data.