Introduction
I’ve built my very first computer and I want to overclock my processor. It is mostly for fun, though I am a rare user who actually uses their cpu to the max on regular occasions (I do programming for both work and fun). Since I received a Raspberry Pi for Christmas (hurray!) I decided to learn how to do this with my Pi first. For anyone up on their current computer component knowledge, my built computer has an Intel i5-4690k and a Z97 chipset mobo. I imagine overclocking should be very simple due to the volume of literature written on the subject and the fact that many teenagers can do this (no offense teenagers). But! We will follow the same problem solving strategies as always. My first pass is to google, find instructions, follow them, win. To make this more interesting though, I also would like to understand one deeper concept about overclocking so I will try to find something neat about the subject.
So what is overclocking? Some people seem to think you are changing the internal clock speed of the processor (wrong) while others think you are changing a multiplier (most people don’t know what that is other than what it does) of the processor’s clock (kinda wrong). First, CPUs don’t have clocks (read the first sentence of that article). Let’s establish that. The motherboard has one clock (just a simple oscillator) which the whole system of memory modules, CPUs, etc use for timing. But all of these components run off of different frequencies! Even worse, the base clock is often a dozen MHz or so and we need over two orders of magnitude higher frequencies (remember that clock speed listed on your CPU? Somewhere between 2-4GHz). How can we use this simple clock for something this complex?
Theory
As a mathematical problem, this is actually easy to solve. I have a signal of the form where A is the amplitude (digital processors sometimes run at roughly 1.5V or, like the raspberry pi, a default of 1.2V), f is some periodic function (for instance, a sine wave is the function but for digital circuits we use binary logic, that is, a square function), is the angular frequency, t is time, and is some constant phase offset. The most boring term, , can actually be the most useful for linear circuitry. Imagine , and then imagine we have a magical device which can duplicate that signal and then offset it by . By XORing the two signals, we can generate a signal of double the frequency (see here, let phi be so that you get T/4). This would be a multiplier of 2, since I’ve doubled the frequency.
Another way of approaching the problem is to actually write out for a square wave: Notice the square wave already has the necessary harmonics of the individual sine waves. So, you could bandpass filter your square wave for the desired frequency, but then it would be a sine wave of much lower amplitude. The trick is to then reamplify it and then re-gate it to turn it back into a square wave. The problem here is your signal better be very clean or else the resulting intensity of your frequency multiplied wave will fluctuate wildly. Also, there is a large waste of signal as the other harmonics are thrown away (luckily clocks don’t use much energy to begin with). There, solved!
Well this is fine and dandy if you want integer harmonics, but as anyone who’s overclocked their system can tell you, you can even do non-integer multiples of the base frequency! How on earth? This concept is far removed from my daily life, so I may not understand all of the details, but it appears as if the trick is to do a time-averaged set of integer harmonic multipliers whose result is a non-integer harmonic multiplier. I get my information from this Texas Instruments PLL designer’s guide (I’ll define PLL in the next section). Of importance is page 32. It describes the “Fractional-N Accumulator,” a device which switches the multiplier from N to N+1 for however many reference frequency cycles is needed for the time average of the divider to be the fraction specified. As an example, page 32 describes a reference frequency of 480kHz (pretend this is the externally supplied oscillator on your motherboard) that can be multiplied by 2000 (the thing you change for overclocking) to make 960MHz (pretend this is your desired CPU frequency). But what if you wanted 960.03MHz? You would have to multiply your reference frequency by 2000.0625! So since you don’t have access to non-integer multipliers, you can “fake it” by doing a time average between a multiplier of 2000 and 2001. As described in the TI PLL guide, you would do 15 reference cycles of 2000 and then 1 reference cycle of 2001 to achieve this. These two multipliers, or prescalers, are known as “Dual-modulus Prescalers.”
Implementation
So how do I actually overclock my processor? I know that I need to change the prescalers (or multipliers, or dividers, etc) but where is that? It isn’t on the CPU, and it isn’t on the clock. It’s on something called a “Phase-Locked Loop.” It is the device which amplifies harmonics, as well as doing a variety of other tasks such as locking the multiplied frequency onto the input frequency (so it doesn’t drift) and providing different multipliers for different components. As an example of what I’ve described, I’ve taken pictures of my raspberry pi and my motherboard for reference.
Figure 1: The oscillator on a raspberry pi. It runs at 19.2 MHz while the CPU runs at ~700MHz!
Figure 2: The “Mobile DRAM” module by Samsung which most likely holds the processors, memory, and the pll, all in one package. A spec sheet for this device has NOT been published by Samsung.
The first figure is the oscillator the Pi uses as its reference clock. The second is the processor/ram/pll/etc., which is an all-in-one chip produced by Samsung. Samsung isn’t known for their open-source products (which is funny considering a recent CES statement by Samsung… starts at ~50 seconds in) but I was able to infer that the chip contained a pll inside of it. First piece of evidence, the oscillator from my first figure connects directly to the chip. See this wonderful PCB schematic of the Pi and (after taking a million years to load the image) hover your mouse over the words “BCM2835 OSC.” Second, there is no chip with enough pinouts other than the ethernet/usb chip and the Samsung one to be a pll (pll’s often have a bunch of pinouts). Third, the Samsung chip is a Mobile DRAM chip, and this page claims another chip, the Graphics DRAM chip, has a pll onboard (just ctl-F pll on the page), which leads me to believe that the MDRAM chip may also. I can’t say with 100% certainty since Samsung hasn’t released the spec sheet for the MDRAM.
So finally, how do I overclock the pi? In keeping with my philosophy, I shall link the reader to where I learned about this rather than steal their post. Even at first glance, you should notice it is trivial! They (the shadowing Raspberry Pi overlords) have really held your hand for this. You just need to change some lines in the /boot/config.txt file. At the bottom of the configuration file, you only need to uncomment #arm_freq=800 (or write your own number, though beware…). As stated at the top of this configuration file (or from the link I just provided), there are many more options one can put into this file. Also, keep in mind, the higher you go with the arm_freq number, the more likely it is you will need to overvolt your system. So, like in the linked instructables, you may need to add a line like “over_voltage” to the config file. And just to make things easier, if you hate config files, there’s a hand-holding configuration utility (simply type “sudo raspi-config”) that can overclock for you! That is, it has some overclocking presets that it writes into the aforementioned config file that are likely to work. I say likely, because part of the “fun” of overclocking is that you need to find a balance between clock frequency and voltage level. Processors are all different and what works for one may not work for others. The values chosen are most likely averages over many devices that have a high likelihood of working. So! If you run this and it doesn’t work, just start messing around with the overvolt numbers in the config file and it might (should?) work out for you. Oh, this is also the reason many people benchmark their settings. Just because you wrote all those numbers down doesn’t mean you will get those numbers. If you really want to know what your system is capable of, again, follow the instructables I linked as the writer tells you how to benchmark your settings.
The final question I had was why changing voltages should affect speeds. At least mathematically, the two were completely decoupled, right? Well, according to this wikipedia page, it turns out that physics is important here! Hurrah, I love physics! So the idea here is that all nodes of electronic chips have an unchanging innate capacitance. This varies from chip to chip, but it always exists. So you can imagine running current across a junction and watching the voltage on a good oscilloscope (good in this sense would be one which does not add a noticeable resistance or capacitance to the circuit it is measuring). For human speeds, it looks instantaneous, but if I zoom in, I can see a characteristic rise time associated with the current, voltage and capacitance. Now, if I start changing that signal really quickly, the rise time might be on the order of the periodicity of the frequency! That is, my signal wouldn’t look square anymore and would instead start getting curvy. That would be bad since I may start missing data and my logic gating would be inconsistent (this would translate to a blue screen of death or some other crash). So, I can’t change the capacitance and the frequency is the thing I want to increase, so the only variable left is the voltage. By increasing the voltage, I can speed up the rise time, and thus I can continue increasing the frequency. Of course, if I do this too much, my CPU will get hot, so overclocking is often a case of “How low can I make my voltage for a wanted frequency while still maintaining stability?”
tl;dr
- Either uncomment the line in /boot/config.txt which says “arm_freq” and write your own number (remembering that you may need to overvolt your system with a line of the form “over_voltage=X” where X is a number from -16 to 8, each of which is 0.025V), or just type “sudo raspi-config” and choose overclock and whichever setting you want, then restart.