Many of you may know that both PSoC1 and PSoC3/5 devices have PGAs (Programmable Gain Amplifiers). These are handy devices allowing you to either select the system gain during design time or during run time. The gain for these PGAs is controlled by calling one of the API function calls. Sometimes it would be nice to be able to control the PGA's gain with a digital signal. With PSoC 3 and 5, there is a way to do this by making use of the handy internal opamps. There are a couple of ways to do this using different combinations of pins and analog muxes.
This first option is the simplest, using the internal opamp, a couple of external resistors, and some GPIO pins. If the signal you want to amplify is referenced to Vss, you can use GPIO pins in the open-drain, drive low mode to select one of N resistors. The diagram below shows an example of how to use three GPIO pins and four external resistors to provide eight selectable gain combinations. The LUT (Look Up Table) controls the the gain selection by what ever means that is required by your application.
Another option is to use a hardware mux to select the feedback resistor. This allows you to select a reference other than Vss. In the diagram below, the VDAC8 is used to generate the reference voltage which is then buffered with another opamp. The disadvantage for this design, is that to maintain gain accuracy the resistors should be as large as possible to wash out the affect of the analog mux switch resistance. Each analog switch in the hardware analog mux is about 200 ohms, so the external resistors should be above 10K or more. The gain for this option is the same as the first, it provides 2^N gain combinations where N is the number of pins and resistors used for gain control.
A third topology eliminates the issue with switch resistance. The analog mux is used to select the tap point along a string of external series resistors. Since the current through the mux switches is just that of the opamp input, the 200 ohm switch resistance can be ignored. The disadvantage, is that one pin is required for each gain setting you want to select, therefore using more pins. As with the other two options the gain can be controlled purely with digital signals.
If we add a window comparator to one of theses examples, a simple AGC (Automatic Gain Control) can be implemented. The LUT in this example uses the comparator outputs to determine if the gain should be increased, decreased, or remained the same.