So this is actually a very difficult question. It highly depends on the specific system used.
So first we have to clarify some naming issues:
Reading the book, I've came to understand that there are atleast 2 clocks in the whole system. One is the System Clock which makes one of the lines within the Control Bus go HIGH and LOW periodically. The CPU also has it's own Internal Clock which controls the operations which are done by the CPU. Now the Internal Clock should be in sync with the System Clock for the whole system to make sense which means the control line (which oscillates between low and high) should be connected to the CPU so that both the clock combine and act like a single clock.
As you pointed out these clocks act as a "single" clock. So are these actually different clocks / clock domains? This highly depends on who you ask and with which requirements you look at it.
There are several relations, 2 clocks can be in with each other:
- The same clock. I will identify 2 clocks as the same clock if they have the same frequency, phase etc and are generated by the same clock source. For the designers of the system, these 2 clocks might be differnet becasue these have two separate wires etc. But with a higher perspecitve, they are the same.
- Synchronous clocks. Synchronous clocks must no be generated from the same clock sources but have a fixed phase / frequency relation to each other.
- Asynchronous clocks. The two clocks are generated by different sources that do no share a common reference and do not have a guaranteed fixed phase and frequency relation.
- In reality, even the same clock line will have different clock phases at different points on the wire, due to signal propagation delays. Clocks with the same frequency but unknown phases are called mesochronous.
So even inside a single microchip, the same clock can become mesochronous when routed to different locations with different distances. This is a real problem but I will ignore this in the further discussion.
So starting with the simplest case, there is only a single clock necessary for a computer system to operate. Although if it is used for your CPU, memory etc. and might have different names at specific points in the system, it stays the same clock.
Many simple microcontroller systems, especially small 8 bit controllers, only have a single clock. The CPU, RAM, and all the interfaces run on this clock. This is cheap and easy. And if the system is small enough you don't get severe problems by routing this clock to all places.
I've attached the clock tree of an STM32F4 microcontroller.
This is still not a full "computer" like your PC, but looking at it, you can see, it's a mess. I won't go into much detail on how this works but we can observe some interesting things.
The squares on the left represent pyhsical Pins on the microcontroller's package and are used to get clocks in and out of the system.
So we can see, that this specific microcontroller which is not bigger than a coin:
already has teh follwoing clock sources:
- LSE OSC 32.768 kHz. An externally provided clock for real time clock applications
- HSE OSC 4-26 MHz An externally provided clock which is used to derive most clocks in the system
- I2S_CKIN A special clock for the Audio part of the system. Audio application require specific frequencies due to precision reasons or weird sample rates like 44.1 kHz which are not easily dividable from other clocks
- Ethernet PHY. Most Ethernet applications require a good 100 / 50 / 25 MHz clock
- USB Phy. Clock for the USB system
- LSI OSC. An internal 32.768 lHz osciallator
- HSI OSC. An internal oscillator to provice 16 MHz
Compared to a whole PC, this system is rather small and easy. It is just this small single chip. But it already hass 7 different primary clock sources that "generate clocks out of the blue". Either externally provided, or internally generated.
Usually on-chip clock sources have the advantage of being cheap (no external stuff required) and being available very early on system start. But most ways of generating clocks on a chip are not very precise. Many of these clocks have high temperature drifts and large manufacturing spread. So if a precise clock is required, most chips require an external clock to be provided from e.g. a crystal oscillator that derives its output from the machanical oscillation of an actual crystal.
This is the reason why this chip e.g. has an internal 16 MHz oscillator but also provides a way to feed an external Oscillator. If precision is of secondary concern the internal one can be used to optimize for cost.
Looking further into this system, we can see, that the clock inputs are spread all over the place. I want to move your attention to the PLL blocks. A PLL (Phase Locked Loop) is essentially a fancy way to generate a clock signal dependent on a reference clock. And the fancy thing is, that the generated output clock can have a different frequency than the reference clock. I won't go into details on how this works. There's plenty of explaination on the net on this topic.
So a PLL is a way to generate new clocks based on a reference clock with a specific frequency / pahse relation compared to an reference clock. These PLLs are usally used internally of semiconductors to either achieve variable clocking and/or higher clock frequencies that otherwise would be difficult to route over a board.
Using PLLs and Clock dividers this system uses the input clocks for generating different clocks.
Essentially this system can use a single 16 MHz internal clock generator to provide a 168 MHz CPU clock (via an PLL), an 48 MHz clock for its USB module via another PLL, several lower clocks for its periphjeral modules, like UART, that are divided form the 168 MHz system clock.
As you can see, we only need one clock source to derive several mesochronous clocks from this via PLLs and clock dividers.
This is a common practice most moder semiconductors use.
Going back to your question:
Essentially there is only a single main clock source needed in a computer system. If different clock frequencies are needed to speed up several parts of the system, these clocks can be generated via PLLs from this base clock.
If slower clocks are required, these can be easily divided.
However, different use cases require different clocks with different specification regarding precision and stability.
- All communication, that doesn't transmit the clock, requires somewhat precise clocking as the receiver has to either regenerate the clock from the received data or has its own clock that needs to be as close as possible to the one of the transmitter. This includes all wireless transmission. Most WiFi cards will have an onboard clock gerneration of the 2.4 GHz / 5 GHz clocks used for the modulation. But also other technologies like SATA, Ethernet, USB etc. do not share a common clock between receiver and transmitter and therefore precise generation and/or clock recovery is necessary.
- The DDR memory inside a PC is usually clocked at a different speed than the CPU and most importantly this is not as frequently changed as the CPU clock. Most likely the memory clock is derived via one of the described means from a common clock source as the CPU clock.
- Audio requires special clocks for the specific sample rates that are common. A 192 KHz sample clock is easier to be generated from a 12.288 MHz crystal than from a 8 MHz reference.
- PCIe (usually) uses a 100 MHz reference clock that is send to the cards so they can internally generate a higher clock frequency for PCIe based on this clock. It is generated by the root complex of the PCIe e.g. your CPU or chipset. Providing a reference clock ensures, that all connected devices can generate a clock that is very precise compared to each other but does not need to be absolutely precise.
- Digital video like HDMI, DVI etc. transmits a pixel clock in the cable.
As you can see, there are easily several hundreds of differnet clocks in a modern computer system. However, in some cases these hundreds of clocks are only derived from a hand full of primary clock sources.
So far we only looked at how many clocks there are in a system. And we came to the conclusion: A ton... So how are these synchronized:
This highly depends on the relationship of the different clocks.
- If carefully designed synchronous clocks of the same frequency do not require any synchronization at all.
- A slower clock that trasnmits data to a faster clock with a fixed clock and phase ratio (derived from the same reference using a PLL) might also not need a synchronization, as the faster clock is capable of processing all data coming from the slower clock and the cahnges of the source clock domain are guaranteed not to violate the setup and hold requirements of the flip flops in the destination domain due to the fixed phase and frequency relationship.
Problems arise when the clocks are asynchronous or mesosynchronous. As you've pointed out, these can run "out of sync" with each other. So a special clock domain crossing mechanism needs to be installed. There are several ways of ensuring this. I recommend searching the net regarding clock domain crossing (CDC) and synchroinization. The short answer is: All clock domain crossings require the synchronization of the signals into the destination clock. This is usually done by using 2 or more Flip-Flops clocked by the destination clock to sample the input signals.
For one bit wide signals this is already sufficient. Of course you would have to ensure by design that the signal is held stable in the source domain for long enough so that the target domain is able to capture it. This is especially problematic going from faster to slower clocks.
However, if multiple signals e.g a data bus needs to cross a clock domain, the signals cannot be simply synchronized bit by bit, as differnet routing delays and flip flop manufacturing tolerances etc. can lead to wrong sampling of the value in the destination clock domain if sampled right at the change.
One way of circumventing this is to proved the data in the source clock domain and toggle a qualifier signal. The data is synchronized by a signle flip flop in the destination domain and the qualifier signal is synchronized by 2 or more flip flops in the destination. Therefore, it is ensured, that once the toggling qualifier signal is fully synchronized into the destination domain, the data is also synchronized. Data and qulaifier need to be stbale during this process. Either by a fixed timing or by providing a feedback signal from the destination to the source.
As you can see, clock domain crossing is
- Requires time -> Can actually severely impact performance and latencies
- Is notoriously difficult to debug in anything goes wrong. Therefore, special care needs to be given when designing these crossings, so that they are functional.