From the bowels of the Wi-Fi village, I bring you the next presenter that has nothing to do with Wi-Fi. Thanks, Defcon. It's been five years we've been in the wireless village and they still haven't updated a goddamn thing. But it's great to be here anyway with Robert Gilduda, who I've known for about three, four years now and I just learned how to pronounce his name. So this is the fine gentleman who's been a very integral part of BladeRF from the beginning and a couple other projects that were stolen from them and just re-released. But it was basically his work anyway. So he's going to talk about designing an automatic game control. And if you are here and you are interested in this, you are sitting too far away. Come and bask in this fine gentleman's glory. Get close enough to smell him because it's actually quite nice. So without further ado, designing an automatic game control. And hopefully... Hopefully you can use that to pick up some, I don't know, traffic to the military base. Thanks. Yeah, so out of curiosity, who here is familiar with software-defined radios and what they do and what they are and how they work? All right, cool. Who here has an SDR that they've... Actually, better yet, who's familiar with automatic game control? Okay, I'm going to teach all you guys why you might want an automatic game control in your software-defined radio in this talk. Currently, the BladeRF does not have it. Or as of about a month ago, the BladeRF did not have an automatic game control, but now it does if you check release 2017-07. Who has checked it out and played with it by any chance? Anyone in the audience? All right, well, there's a blog post that's imminent, and it's been imminent. For the past couple of months, so, yeah, maybe this will motivate me to release the blog post, but, yeah. So, introduction. Who am I? I'm the owner of Nuon. We're about four people now. I have sort of like a small team of software, hardware, and RF engineers. My interests and that of everyone else on my team include software, hardware, and RF engineering. I'm kind of assuming that's not a surprise to anyone. I have a background in DSP, specifically telecoms, so telecommunications, like building modems and having wireless. Okay. Radios talk to one another. And acoustics. I did my master's degree in voice processing, so speaker recognition as opposed to speech recognition. So I can build things that identify who a speaker is as opposed to what they're saying. I have about six years of experience building enterprise network equipment. I worked on a pretty big publicly traded company's Wave 1, Wave 2 enterprise AC access points. And I've been a long-time information security. I've been coming to DEF CON since 08, and I've only missed one year since. So, the Blade RF. If, who here has a Blade RF? Who here has a Blade RF on them? All right. So, basically, the Blade RF is a USB 3.0 software-defined radio. We designed it in Orcad, like, about four and a half years ago. It's got, like, about 300 components. We use Cadence for the layout. As you can see, that's, like, the pretty little layout graph. You can see it up there. The design is mostly, like, an eight-layer PCB with five-by-five mil, or five-mil thick traces of five-mil spacing. It's an FR-4 TG material. So pretty much, like, commodity consumer-grade materials. The cool thing is we kind of went overboard with the amount of simulations and design that we put into building this radio. So we used a lot of HSPICE simulations. We used the Agilent ADS and Genesis. We got sort of an interesting license from them that they gave us. It's a 2.5D field solver that we were able to simulate sort of what happens to the RF traces on one side of the board when you're sending USB 3.0 super speed traces on the other side of the board. So back about four years ago or so, Intel had an advisory paper that's like, hey, if you're running USB 3.0, you're going to have to have a super speed trace on the other side So if you're running USB 3.0, you might end up knocking out your 2.4 gigahertz band radio receivers that are in your laptop. So we did a bunch of simulations just to make sure that there was no emanating, like, wideband 2.4 gigahertz noise coming from the Blade RF's super speed traces. So the architecture of the Blade RF is basically a Cypress FX3 USB 3.0 transceiver chip. It's a single-core chip. Which essentially just has a USB 3.0 super speed peripheral side on one side, and then this general-purpose 32-bit bus GPIF on the other side. The GPIF is a, again, a 32-bit parallel bus that can run up to 100 megahertz. So it's capable of transferring up to about 400 megabytes of raw data per second. So when you multiply the Blade RF's maximum sampling rate, which is 40 mega samples, so it's 40 mega samples, receive and transmit, and an I and Q pair for each sample, you kind of notice that you can't fit into a USB 2.0 throughput constraint. So that's why we decided to go with USB 3.0. And, um, that provides us ample bandwidth to be able to do full duplex 40 megahertz channels, 28 filtered and instantaneous. And still have a bit of extra bandwidth to spare. So. So that extra bandwidth goes to things like the metadata. Has anyone used timestamping, like the timestamping functionality or the scheduled tuning functionality within BladeRF? I know we've only had like about 50 people that have actually asked us about that, and I'm wondering if one of you 50s in the audience or in this room at the moment. No one, all right. So the general purpose chip is then hooked up to an FPGA, which sort of acts as like the glue logic between the USB3 transceiver chip and the LMS602D transceiver chip, which is sort of like an all-in-one RF to bits chip. Essentially it has the amplifiers, the mixers, the low-pass filters, and the impedance matching circuitry, and the data converters like the ADCs and DACs all built into one single chip. So essentially on one side of the chip, you hook up a ballon, and on the other side of the chip, you have your 12 bits of I and Q data coming out as actual physical pins. So you hook those up to an FPGA, you do a little bit of buffering inside of the FPGA, you do some additional signal conditioning and processing, and then you shove things into the USB3 transceiver, and all of a sudden you're collecting RF samples and pushing them into a host computer and doing processing and software. Hence the software-defined radio aspect of this whole chip. So that's the whole project. The frequency range of the device is about 300 megahertz to 3.8 gigahertz. Some devices go a little bit lower, some go a little bit higher, but that's the range that we feel comfortable guaranteeing. And yeah, it's a full-duplex, 12-bit, 40-megasample, quadrature sampling device. On it, though, the LMS602D doesn't have the ability to create its own reference clocks, so the sampling clock is created by an SI5338 synthesizer chip. So this chip is able to create very clean reference clocks between like 100 kilohertz and 200 megahertz. So that's sort of, when you go and type like set sample rate 20M in BladeRF command line, that's the chip that's doing the 20 megahertz. And it's feeding it to the LMS chip and also to the FPGA, and then the LMS's ADC uses that chip and that reference clock to digitize the incoming RF signal that it sees, and eventually all those come out on the digital side of the LMS chip and go into the FPGA. The synthesizer chip also feeds the LOs, which are the local oscillators, on the BladeRF, so you can kind of think of radio receivers as sort of this like house of cards. So if you have a really weak foundation, in the quality of your signals, it's gonna propagate, like the poor quality of your signals is gonna propagate through everything. So the SI5338 has, is also the reference for the local oscillator, which is used to tune the device across the RF range. So internal to the LMS6 chip, there's an LO, which is again, the local oscillator, which essentially defines which channel you are on. Question? Do you have an external LO port on the BladeRF? We do not have an external LO port. No, there is a transverter board, the thing that takes RF, mixes it down to 300 megahertz, or mixes everything below 300 megahertz up to 1200 megahertz, and then this transceiver chip is able to see 1200 megahertz, but what you're actually seeing coming in from the antenna is below 300 megahertz. So this is sort of like the rough architecture, of soft-refined radios, sort of the idea is having flexible RF hardware, so signal conditioning things such as LNAs, PAs, filters, LOs, modulators, and demodulators, feeding into digital to analog converters, and ultimately going through the rest of the DSP chain, and usually, I mean, you guys will probably run things like GQRX, so the processing side is kind of light on the FPGA, and what you're feeding into your programs is something like I and Q samples, and then seeing the raw spectrum in GQRX or GR phosphor. But some people do some additional things in the FPGA, such as having channelizers, having actual modems, having equalizers, and some other signal conditioning things, such as DC. You can see an IQ phase imbalance correction going on inside of the FPGA, and then those things get passed up instead of raw samples. So this is the LNA6's block diagram. We're gonna constantly kind of come back to this, because it's kind of important in designing an automatic gain control, because as you guys can see here, there's really no feedback loop. So RF comes in. So RF comes in. So RF comes in. So RF comes in. You have an LNA, you have your mixer, you have your VGAs, your LPFs, and kind of whatever you set those values to, they won't adjust based off of the signal that's coming in. So there's a reason for, yeah, here we go. So, give me just one second. Yeah, so incoming signals that you deal with regularly, kind of, when they hit the antenna, they come in anywhere between minus 25 dBm, which is pretty loud for something, and they can come in as low as minus 110 dBm. So that's 85 dB of range. As I said before, the Blade RF has a 12-bit A-to-D. So 12 bits only kind of gives you about 72 dB worth of static range. So your static range is how much range can you see at any one given moment without adjusting your gains. So what that means is with 85 dB of range, if you're tuned in to being able to hear a signal that's, or with 72 dB of range, if you're tuned in to something as hot as being able to hear something that comes in at like minus 5 dBm, the quietest thing that you'll be able to hear is something that comes at minus 65 dBm. But there's also a fair amount of signal that you're not gonna be able to see. So if you have like a 10 dB SNR signal that comes in like minus 65 dB, like you need your sensitivity to go down to minus 75 dB. So, yeah. So yeah, a 12-bit ADC does not have the ability to simultaneously listen to minus 25 dBm and minus 100 dBm signal without drowning one of them out. And generally, you can't drown out the louder signal because it's going to end up completely swapping your front end. So, again, this is known as static range. Oh, nothing. All right, it's good. So, what can we do to extend that 72 dB worth of static range? Well, going back to this, we see that there's a fair number of gain stages. I don't know, does this show up? Yeah, oh man. So yeah, there's the LNA stage, which there are three of. I'm having some difficulty. Figuring out where my pointer is. Right, so these are three different LNAs. The reason why the LMS chip has three different LNAs is because it has sort of like a low-band LNA and a high-band LNA, and then a wide-band LNA. The wide-band LNA has slightly worse noise figure performance than the banded LNAs. So, on the BladeRF, we use both LNA one and two and kind of just leave the wide-band LNA unpopulated, because it's 1.4 gigahertz. But then, once you go through the mixer, everything is at baseband. So, at this point, you are down at zero IF, which basically means that the frequency range of what you're looking has been mixed down and is now sitting right square at zero hertz. So, the RX VGA and the RX low-pass filter, and the RX VGA2 don't really have a requirement to be banded, because they're all basically working with signals that are lower than 50 megahertz. So. So, how can we have a device listen to things that might come in at minus 110 dBm, and also minus 25 dBm? Well, they can't, one assumption is that, you know, they can't occur simultaneously. Like, that's physically impossible, because if you adjust your gains so that you can hear the minus 110 dBm signal, when that minus 25 dBm signal is going to come in, it's going to blow out your front end. But if you tune your receiver so that you can hear the minus 25 dBm signal without clipping, you're just not going to hear that minus 110 dBm signal. So, how about packets? Because packets generally don't tend to have that great of a variation through them. So, if you're 100 kilometers away and transmitting something, your signals for the entire duration of one of your like 100 millisecond packets, or however long of a packet these point-to-point link systems use, won't change that much. So, it'll probably definitely come in at minus, say like 95 dBm for the duration of the entire packet. So, one thing that could be done is to change the gains of the amplifiers on a per packet basis by adjusting the RF front ends gains. So, the LNA has a 0 to 6 dB range. The RXVGA1 amplifier has a 5 dB to 30 dB amplification range. And RXVGA2 has a 0 dB to 30 dB amplification range. So, if you add all of these up, you have about 66 dB worth of dynamic range. Because you're able to adjust those knobs on the fly. As opposed to the static range, which is defined by the amount of bits that exist in your data converter. So, if you add the two up, the 66 dB worth of dynamic range. So, you can think of the dynamic range as centering or moving the static range up and down across different power levels. So, with the 66 dB of dynamic range and the 72 dB worth of static range. So, the static range from the A to D, you essentially have 138 dB worth of sensitivity. That's a lot. So, right. Going back to this thing, there's the LNA, there's the RXVGA, and there's the RXVGA2. The question is, which ones do we adjust first? Do we adjust the larger one because it gives us more control or do we adjust the smaller one because of something else? Is there some weird reason? Well, when looking at a signal that you're receiving, what will happen is that a signal will deflect from the noise floor by what I like to call the signal level. So, that's your minus say like 85 dBm when you read a signal. The thing is that on top of the pedestal, so like the noise floor, is something known as the SNR. But below that, there's a little bit of noise as well because transmitters don't perfectly transmit signal. They can't transmit signals without some additional noise. So, the deflection from the noise floor is not purely signal. There's also some noise in there. Generally though, transmitters are really good at transmitting signal as opposed to noise. But through different channels, through different mediums and even cosmic rays and whatnot, that SNR will shrink from what it was when it left the transmitter. And a bunch of the transmitted signal that it sends will turn into noise. So. So, what you want to do, oh, there's also another thing. In the receiver, once you start doing things to the signal, so like once you start amplifying it, once you start doing impedance matching, you're going to be moving this noise bar up more and more and more. So, what you want to do is as soon as the signal comes in, you want to move the signal level as far away from the thermal noise floor and from this noise level as quickly as possible. Because the more things, the more components you put your signal through, the more of the SNR you're going to lose. So, you can have an amplifier that gives you 10 dB of gain, but it has a 1 dB noise factor. So, that means that even though this thing moves up 10 spaces, this gap narrows by 1 dB. So, you could actually end up losing all your signal by going through a really poor signal. So, that's what LNAs are good for. The LNAs are good for moving the signal level or the SNR part of the signal level away from the noise floor and away from the noise by just like a tiny little amount. So, then all the subsequent amplification that occurs in an RF chain don't take away from the SNR part of the signal. So, I kind of clued you guys in as like what the strategy here is. What you want to do is you want to have a signal that's, like, So, what you want to do is to first turn the gain up on the LNA. So, once your LNA is no longer able, so assume that you cut, you have, like, a really weak signal coming in and you know it's there. What you want to do is you want to tune the LNA all the way up and see if your signal is within range. If it's not within range, then you go to the next amplifier in the chain, which in this case is the RXVGA1. Once you've saturated your RXVGA1, you can go on to RXVGAT1, RXVGAT2, and by that point you have, if you max all those out and there's no signal there, you are basically sampling the thermal noise floor of the universe. Because with 138 dB, there's, your signal has now gone below the noise floor. So, these are LIME's recommendations for how you should implement an AGC, or implement a gain strategy for depending, depending on where your signal is, where your signal comes in. They kind of give a table of about six different gain settings, but AGCs should be fast. Like, an AGC shouldn't have to, like, go through four different stages writing three different registers for every single gain setting. Because if you do that, you're wasting precious time on a signal. So, 802.11, for example, only has a, about eight microseconds in which time your AGC has to lock. So, if you have, you know, if your gains are on the opposite end of where the signal is actually coming in, you're going to spend a long time traversing that gain table to figure out which gain setting works. So, I kind of decided to not follow this table just because it was kind of tedious, and I'm not quite sure that the linearity was all that great. So, I came up with my own gains. I came up with a gain setting, which I dubbed high gain, which is the LNA being set to maximum, which is 6 dB of gain. The RXVGA1 being set to 30 dB of gain, and the RXVGA2 being set to 15 dB of gain. Actually, I probably should have started this on the other end. So, the low gain starts with an LNA gain of 3, an RXVGA gain of 12, and an RXVGA gain 2 of 0. So, that's for the lowest gain setting required. That means, like, these signals are incredibly hot because they have to be set to maximum. They range from minus 30 dBm to minus 17 dBm, which essentially is like what you would expect if you had a Wi-Fi transmitter sitting on top of a Blade RF. So, you don't really need much amplification to be able to hear a signal that's being transmitted by something that's sitting directly on top of your SDR. But, say for example, you start moving the Wi-Fi transmitter away from the device, and you're about 50 feet away. Now, your signal probably will come in at around like minus 40 dBm. So, in that scenario, you want to compensate for the loss of received signal strength by bumping RXVGA1 from 12 to 30 dB. So, that gives you an additional 18 dB of gain. Ultimately, if you move the transmitter so far away that it's now coming in at minus 70 dBm, you might want to bump all of your gains up quite a bit. But, the thing that I decided to come up with, is, so this table has an interesting quality to it. It's that out of the three gain settings, only two change between each of the gain settings. So, the reason why this is important is because the LMS6 has a spy controller that is used to control the gains with. So, changing any of the gains requires you to issue a spy command. So, that spy command takes some amount of time. And, because I wanted my AGC to be fast, I decided to come up with a strategy where just only two registers were being written to every time you went from like low to mid, or mid to high, or in any other direction. The group delay is like about three microseconds. And, that's sort of what I decided to have. Okay. So, that's what I calibrated the IIR to. Yeah. So, now that we know the gains, how do we make this automatic? Well, as I said, the starting condition, or the starting configuration for a device should be maximum gain. Because if you have a weak signal that's coming in, and your gains are turned down low, you're going to miss it. So, you can't have your AGC start out with a low gain setting. But, you can. But, you can start out with a high gain setting. So, what happens in that case is if you need to adjust your gains, you will end up having a signal that comes in that's very hot that will end up clipping your front end. So, it's much easier to detect a front end that's been clipped than to detect a signal that you don't have the proper amplification to see. So, the AGC puts the transceiver into a very high gain state, and then adjusts the gains depending on an algorithm that I'm going to discuss in a bit. So, the AGC calculates an instantaneous power of the incoming signal. So, power with quadrature is basically the square root of I squared plus Q squared. The problem, though, is if you kind of decide to make a decision based off of, like, one sample's power, you're going to be changing gains all the time. So, you're going to be changing gains all the time. So, this is kind of synonymous with, like, a home thermometer. So, if, like, a home thermometer doesn't have something known as hysteresis, which is once you go past a certain level, you don't want to turn the AC off as soon as it hits, like, 70.1 degrees. Yeah, you don't want the AC to turn off as soon as it hits 69.9 degrees and then turn back on as soon as it hits 70.01 degrees because it will continue going between the two very quickly. And... Yeah. Yeah. Exactly. So, what you want to do is potentially lower the temperature at which the AC turns off and turns on again, so then you have a bigger window of time in between when you need to turn the AC off and on. So, the same thing applies to soft-refined radios. So, the best way to not make a quick rash judgment call on... What gain you should be at based off of one sample, you will probably want to do a bit of averaging. And an IIR is probably the cheapest way of doing averaging in FPGAs because basically what you do is you take the last sum, you divide it in half, and then you add half of the new power. So, in HDL or in synthesized HDL, this is not that many gates. Uh... . . . So how vaguely do we want that? Uh... So, some things that AGC will miss. So, you can adjust the IIR... . . You can do it because... . . That looks nice. . . . . . . Um, right, there is no perfect AGC, so you will, yeah, those are configurable and the source code is available, so you can put in different numbers, but I found empirically that these things happen to work the best. So some of the other problems that occur with AGCs is, I mentioned group delay. Group delay basically means that because the speed of electricity is finite, if you adjust the LNA settings, it still takes some amount of time for the RF signal that was amplified with the new gain settings to propagate all the way through the chain. So the total group delay for the LMS6 chip is about three microseconds. So that's basically going from the RF antenna all the way to the digital INQ signal. So that's basically going from the RF antenna all the way to the digital INQ signal. If you add two LNA signals to the RF signal, which were digitized by the AGC, it's actually not that bad, but it adds a little bit to the amount of time that you have to, oh, I'm sorry. The group delay is one microsecond, because the settling time of the AGC is three microseconds. So, it still, the group delay makes it so that AGC works a little bit more slowly. So, essentially the way that you implement this in HDL is by just waiting for a certain number of cycles and samples to pass before you start up your IIR again, and those cycles come up before even your IIR and you're back on your again, because once you switch your gain settings, you want to wipe away the previous average and start with a new average, and then very quickly converge on a new average and figure out if that did anything for the gain. One interesting thing that can be done, though, is generally the group delay has like a sort of an exponential decay function to it once you update the amplifier settings. So that means that if you're in the highest gain setting and you have a signal that's very close to you and you only go to the mid setting, you don't need to wait for the group delay to completely settle before you can realize that, oh, this thing will continue blowing at my front end transceiver even in the mid setting. So halfway through the group delay and settling time of going from the high gain setting to the mid gain setting, you can kind of make a decision like, this is still way, way too high. This is way too hot, and go straight to the lowest gain setting. So, yeah, that's the signal is very hot and shortcut settling time that I was just talking about. And how do you test this? I guess you can kind of test it over the air and maybe have some like Wi-Fi access point or some Bluetooth transceiver that you bring close to your radio, but then you don't know exactly what the received strength is. You don't know what a number of different things are. So the best way to test this is using a vector signal generator. Some vector signal generators have the ability to sweep both amplitude and frequency and all sorts of other things in between. So with this vector signal generator, I basically had it sweep from, what is it, from minus 25 dBm or from minus 100 dBm to minus 25 dBm at 3 dBm increments. So I can capture this on a host computer, and kind of just see what happens to the BladeRF's front end as this VSG is sweeping through the whole range. And, oh, this is, so this is what happens when you run this through GQRX. Basically, somewhere at around this point, you are clipping. So your sine waves will look sort of more like square waves. And by the end here, you are basically dealing with an analog square wave, which is not at all what's being transmitted. And that's sort of what's causing this splattered spectrum to show up, up at the top. So if you're not familiar with GQRX, this sort of like dull line that exists at the top is the highest peak that GQRX has seen. So it holds the peak of the highest signal that it has seen at that frequency. So what happens if you run this same setup through the BladeRF's AGC? That's what it looks like. So you might notice a couple of differences. One of them is that the spectrum no longer splatters. So what, at around this point, started being spectrum splattering is now sort of no longer existent. But an interesting thing that you will notice is that the background color kind of does change between the gain settings. So just, as a heads up, this gain setting is the highest gain setting because that's what the AGC starts off at. As the gain increases from the VSG, it causes the BladeRF to go into the medium gain state. And once the medium gain state's received range is exceeded, the BladeRF then goes into the lowest gain setting. So as it's tuning down its gains, depending on the signal that comes in, you actually notice that the background noise floor is actually decreasing as well. Because when you have your LNA gain, RXVGA1 and RXVGA2 turn all the way high, you're also amplifying a lot of thermal noise. So that's sort of what you see here. This deeper blue that you see on the peripheral here is actually from the thermal noise floor. So as you turn the gains down, you actually start getting a much higher difference between the peak of the signal and the bottom of the pedestal. So this is another demonstration of sweeping both frequency and power with the VSG. So basically, I configured the VSG so at 827 MHz, it outputs a minus 70 BBM tone. And then at 830 MHz, it outputs a minus 25 BBM tone. So it just kind of helps visualize which signal it's sending. Because sometimes it's kind of hard to figure out what fundamental tone is being sent when you're clipping kind of like this. So in the waterfall here, in GQRX, the Y coordinate is essentially time and then the X coordinate is frequency. So at some point, I just decided to click hardware AGC and enable the hardware AGC and all of a sudden, the Blade RF was no longer clipping when a minus 25 BBM signal came in. Because remember at minus, or at 830 MHz, you have minus 25 BBM signal coming in. And prior to the AGC being enabled, there's just a lot of frequency splattering going on. So at this point, I kind of want to cut to a short video demo because I could not bring a 80 pound VSG with me to Vegas in one piece for cheap. Give me just one second. Whoops. One second. Oh. . Yeah, so this is the VSG. It was configured to go from minus 25 BBM to minus, or from minus 100 BBM to minus 25 BBM at... No visual? Oh, shit. Uh... I don't know what happened. Just in one sec. . Uh... Oh, okay. Cool. There we go. Right. So this is, again, the same picture of the VSG that's configured from minus 100 BBM to minus 25 BBM with three BBM steps. So essentially, that's 26 step points with two-second dwell time. So that means that every two seconds, the VSG is going to go up about 3 dB of power. And here's sort of what the... Oops. That is not what it should have jumped to. And here's sort of what a side-by-side comparison between the two looks like. So two Blade RFs running side-by-side with the same signal being split to both of them. And the one on the left, well, the one on the left did not have the AGC, and the one on the right does have the AGC. But it'll become apparent. I mean, you can kind of see the signal deflecting from the pedestal. So just a quick note. This pedestal thing that you see here is the filtered bandwidth of the device. So when you saw the different bandwidth on Blade RF, it actually has analog filters, like LPF filters, that will filter the incoming signal. So even though you're sampling at 40 mega samples, you won't have 40 megahertz worth of bandwidth, because if you're using a 28 megahertz LPF, you're basically going to have the 28 megahertz centered around zero. So that means that on either end, you're going to have about 6 megahertz worth of additional oversampling, where the interesting thing is you can actually see the thermal noise floor, because this noise is from the gain stages adding their own noise into the incoming signal. This is what I had mentioned when I had said there's a noise factor being added by amplifiers in the chain. So one other interesting thing to keep in mind is that in signal processing and in telecom, what is important isn't the strength of the incoming signal. What is important, however, is the SNR of the signal. So a quick visual in this whole thing to kind of gauge what the SNR of a signal is, is what the difference between the noise floor and the peak of the incoming signal is, because this difference is a rough indicator of SNR, minus some additional noise that I mentioned about before. So as this demo, or once I resume this demo, just kind of take a look at both the left side and the right side and compare the difference between the peak of the pedestal and the peak of the signal, and see what happens between a capture that is done with the AGC versus one that is done without the AGC. And let me just go back to the beginning real quick. Oh yeah, so the left is no AGC and the right is with the AGC. Probably should have sped this up a bit. So yeah, at the moment, they still kind of look identical, and in like about, oh, there we go. The right side is now in the mid stage. And the left side is now starting to see clipping. And yeah, you can kind of see the difference between the left side and the right side. The right side still maintains a very healthy distance between the top of the signal and the top of the pedestal, whereas the left side is just completely washed. Basically, the left side has no signal remaining. There might be like a couple of dB worth of SNR left on the left side, but the right side is kind of looking at about 60, 70 dB worth of SNR. So that there is, whoops. That there is a visual representation of what it means to have an AGC. And let me just finish this up real quick. Yeah. So the AGC is actually written on, is written in VHDL, and it runs on the FPGA just because of the timing requirement that is needed to make these quick decisions of when to adjust gains. So the AGC source code is available in the Git repo, and you can compile it yourselves. You can download the Core to 16, and now 17, web edition. It's basically free, and it compiles BladeRF code pretty quickly and pretty easily. Some of the things that had to be implemented in HDL to make this whole core work is a spy bus arbiter. So because the AGC core is separate from the NEOS core, which is this little embedded processor that libUSB and the host processor communicate with to honor your gain settings and your sampling rate settings, there needs to be a way of having the two synchronize on who is able to communicate with the LMS6 chip. So this is a standard use case for something known as a bus arbiter. So a bus arbiter is sort of a little core that listens to who has requests to use a resource, and then only grants one of the requesters access to that resource. So I implemented a priority round robin bus arbiter for the spy bus that both the NEOS processor and the AGC use, giving the AGC a higher priority. So if you're in BladeRF command line doing something like peak LMS6 something, that command will stall until the AGC finishes its whatever it's doing. It's very unlikely that the two will ever happen at the same time, but every so often they will happen, and that's what the bus arbiter protects against. So I wonder if there's enough resolution to see what's going on here, but basically the left side, that over there is the request column. So when there's a request coming in, the arbiter then acts it, or wait, no, yeah, the arbiter gives it permission to proceed there, and then the requester, so in this case like the AGC, would hold the request line high all the way through the time that it's done, and then it would release the resource back to the arbiter by indicating that it had finished doing what it needed to do. In this case, issuing spy commands to the LMS6. So just to quickly go through this, a couple of interesting things that popped up in implementing this AGC is the fact that as you're changing gains, the amplification units, so like the RXVGA2 and RXVGA1 will have like their own bias voltages and analog signal conditioning that they need to be able to work the way that they're intended to work. So that kind of leaks into the ADC. So if you change RXVGA2, the center mean value of I and Q will change based off of your primarily RXVGA2 settings, then secondarily based on your RXVGA1 settings, and also a little bit based off of your LNA gain settings. So the problem that this causes is that that DC mean error, or that, yeah, that DC mean error can trick an ADC into thinking that there's actually a signal there. Because if you adjust your gain, and now you've adjusted RXVGA2, and RXVGA2 introduces a DC spike into your signal, you now think that that's an incoming signal, and that'll cause you to think that there's still a very hot signal coming in. So if you go from your high gain setting to your mid gain setting, and you see a DC spike, you might be tempted to go into the lowest gain setting because there's something there. Fortunately though, DC gain setting settings are kind of easy to characterize, and we've already done that with libblade RF. But in version one of the DC cal table, we only calibrated gains at a very specific, or we calculated DC corrections and DC mean errors for one specific gain setting. So for the AGC to work well, I decided to calculate the mean error at all three points, the low, the mid, and the high gain settings. So by being able to know what those gain settings are, you can kind of come up with a strategy of creating something known as a DC, or something that I dubbed the DC lookup table mux. So the AGC will tell the rest of the FPGA fabric which gain setting it's in, be it high, mid, or low. And then based off of what you found out when you calibrated the blade RF using the command line, or libblade RF's DC calibration utility, libblade RF loads in, the appropriate gain settings, and also loads the appropriate mean error values, and then lets the FPGA subtract out the error that exists based off of which gain setting the AGC has moved the LMS6 to. So then the AGC works in collaboration with libblade RF and the LMS6 to figure out exactly what it should be subtracting out, so that it can understand what the real signal is as opposed to sort of just a random DC spike. And this is signal tap capture. If you guys have used signal tap, or if you haven't used signal tap, this is what it looks like. These are raw HDL signals that exist in a live FPGA that you can pull out via JTAG. So when I mentioned the gain lookup table, there's a I and Q tuple corrective for the high, mid, and the low gain settings, and these are loaded by libblade RF from a calibration file, and they're sent over into the FPGA. The FPGA caches this value, and then the AGC tells the FPGA's correction block which gain setting it's currently at. So in this case, the FPGA is telling the DC, or it's telling the rest of the FPGA that it is in the, what is it, in the mid gain setting. So in this case, the DC lookup table, or the MUX for the DC lookup table, picks the mid value correction, which is two and 21, and puts that into the DC correction block. So the DC mean error is subtracted out from the incoming signal, and the AGC is able to get its best understanding of the incoming signal. And that's it. Questions? What's up? Oh yeah, so it's not only for the AGC now, it's for everything. So I kind of made sort of like interpolating function. Actually, I extended John's interpolating function so that it works across settings that haven't exactly been calibrated. But yeah, your blade RF's DC spikes should be a thing of the past now. Well, actually, they should be reduced by about 50%, but they're still kind of there. But that's the case with all zero IF SDRs. Like, there's no SDR out there that doesn't have a DC spike. All right. Yeah. . It's not the best LNA out there. It's kind of high. So that LNA by itself has like a, you know, like about a two to three BB noise figure. It's on chip. It's a single integrated MMIC. You kind of get what you pay for. So, yep. So yeah, it's like about three microseconds when the FPGA is doing everything. If you were to do it on the host side, I don't know if you could even do it, because some of these packets that come in over the air are so short, you would not be able to close the feedback loop by sending USB packets, going into a user mode program, doing some calculation, and then sending back the appropriate things. Like, the turnaround time to go over USB is probably on the order of several tens of milliseconds. So you're already looking at something that's like tens of thousands to potentially even 100 times slower than doing things in the FPGA. Yeah, so generally, telecom engineers will come up with a synchronization and preamble section of a packet that allows AGCs to lock on to the incoming packet. So you will end up missing part of your packet while the AGC comes in and locks into the incoming signal. So protocols just have that factored in. You're not going to pick... You're not going to be able to pick up the very first incoming sample, but you're going to be able to pick up, like, the 17th incoming sample. But there's enough redundancy, purposely built-in redundancy there, that you're not actually missing data. You're just missing parts of a preamble that were inserted there for you to purposely have time to have your AGC lock onto it. All right. Cool. Thanks, everyone. I'm going to give this back to Rick.