# Accurately measuring cable length with NanoVNA

**Update: **Now you can plot the impedance vs. distance/time plot. Click here to learn the concept.

**Original Post:** Having a VNA opens up so many possibilities. Just last week, I reviewed the nanoVNA and found to be an interesting device to have. Having handled expensive Vector Network analyzers (VNA) in the past and present, my excitement grew tremendously to compare it with the Keysight FieldFox N9952A 50GHz VNA. After achieving comparable results, my happiness knew no bounds because I knew I was going to be able to develop and test the RF circuits at my home without needing to take them to my workplace. The Time domain reflectometry (TDR) measurement on the FieldFox happens to be one of my favourites. I even use TDR regularly for various test cases. One of the test-cases is one-port cable length measurement.

In this article, we will go through some mathematics on deriving TDR response with VNA data. Further, I will explain to you a few use-cases where accurate cable length measurement comes handy. Of course, I will provide you with a shabbily written Python script in this article for you to try all this at home.

## Deriving Time response from Return loss

Remember that the VNA does its measurements in the frequency domain. The X-axis represents the frequency whereas the Y-axis represents the magnitude of return loss or insertion loss in dB. We all know the basic relation of frequency and time.

\( F = \frac{1}{t}\)

If we transform the frequency domain data into the time domain, we should see the time domain nature of our measurement. In order to understand this, we need to understand the concept of return loss. Imagine, you have an open-ended coaxial cable connected to your radio transmitter. If you happen you transmit through this open cable, the entire signal is going to propagate to the end of the cable and reflect back towards your transmitter.

As we all know, VSWR of an open or short circuit cable is always very high. In terms of return loss, we are going to see 0dB on our charts. So, if return loss tells us about the reflected signal, it should also tell us some information about the source of reflection. The answer to this lies in the phase of the return signal. By using the magnitude and phase of the signal measured throughout the frequency sweep, we can compute the distance from where reflection occurred.

### A little math

A few of you might know that Discrete Fourier transform (DFT) helps us visualize our signals in the frequency domain. The waterfall or the spectrum that you see with the help of RTL-SDR uses Fast Fourier Transform, commonly known as FFT (A faster DFT algorithm). In short, Fourier transform helps us transform our time-domain signal into the frequency domain. In the case of our VNA measurements, our return loss data is already in the frequency domain. How do we work from there? We have inverse Fourier transform that will transform frequency domain data back into the time domain representation.

We will use exactly that principle in our little experiment here.

\( \text {Return Loss} \stackrel { \mathcal{IFFT}} {\rightarrow} \text {Time Domain reponse}\)

The maximum cable length that we can measure depends on the frequency step size. For example, the nanoVNA can only measure 101 points in any given frequency span. If we set the frequency span starting with 10MHz and ending at 295MHz, the frequency step size is going to be 2.82MHz.

\(\Delta F = \frac{\text{Stop Frequency – Start Frequency}}{\text{Number of points}} \)

\(\text{Therefore, } \Delta F = \frac{\text{295MHz – 10MHz}}{\text{101}} = 2.82MHz \)

Now that we know the frequency step size, we can calculate the maximum reflection time we can measure.

\(\text{Maximum reflection time} = \frac{1}{\Delta F} = \frac{1}{\text{2.82MHz}} = 354.6 ns\)

### Converting time to distance

The result of the above equation comes out in terms of few hundred nanoseconds. Remember, we are still talking in terms of time and frequency. We still need to calculate the maximum cable length. The maximum cable length will differ from cable to cable. This is because the signal travels at different velocities in different types of cables. For example, the signal travels at a speed of 83% of speed of light. In case of RG405, the signal travels at a speed of 70.3% speed of light. This velocity of propagation is denoted mathematically as \(v_p\).

\(\text{Therefore, maximum cable length }= v_p \times \mathcal{c} \)

There’s nothing to be afraid of. We are all familiar with the relation of \(\text{speed, distance & time}\).

\(speed = \frac{distance}{time}\)

Now, try to relate this with the equation stated previously to compute maximum cable length.

Our basics are now clear, so we should be fine to proceed with handling the actual data from the VNA.

Now, how do we get access to our return loss data? Like we saw in our previous nanoVNA review, we will make use of the nanoVNA Windows application here. Make sure that you calibrate your device before proceeding further. Again, if you wish to know how to calibrate nanoVNA, head back here. Now, coming back to our main question, how do we access return loss data? The windows application allows us to save a touchstone S-parameter file. It is marked as “S1P” on one of the buttons. We shall use this feature to retrieve the data.

## The setup

Before we move any further, let me explain the setup.

All you need is your nanoVNA kit and a piece of cable with a connector on one end that can be attached to the VNA. Oh, you will also need a PC to run the VNA application and the python script.

As indicated above, calibrate your VNA and connect a piece of cable to the VNA port. Make sure that the other end of the cable is left open and not connected anywhere.

Now, click the “Save S1P” button to save the one port return loss measurement.

## The python script

I wrote a little script that does the following things:

- Read the S1P file and get S-parameter data \(S_{\text{11}}\)
- Get the frequency step size. \(\Delta F\)
- Calculate maximum reflection time and in turn, calculate maximum distance measurable
- Transform \(S_{\text{11}}\) from frequency domain to time domain using Inverse Fast Fourier Transform
- Find the peak in time data and corresponding time at which it occurred. This peak corresponds to the reflection occurring from the open end of the cable
- Compute the distance by multiplying \(v_p\) with time.

For everyone’s relief, I am attaching the entire script here.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
import skrf as rf import matplotlib.pyplot as plt from scipy import constants import numpy as np raw_points = 101 NFFT = 16384 PROPAGATION_SPEED = 70.3 #For RG405 _prop_speed = PROPAGATION_SPEED/100 cable = rf.Network('cable_open_2.s1p') s11 = cable.s[:, 0, 0] window = np.blackman(raw_points) s11 = window * s11 td = np.abs(np.fft.ifft(s11, NFFT)) #Calculate maximum time axis t_axis = np.linspace(0, 1/cable.frequency.step, NFFT) d_axis = constants.speed_of_light * _prop_speed * t_axis #find the peak and distance pk = np.max(td) idx_pk = np.where(td == pk)[0] print(d_axis[idx_pk[0]]/2) # Plot time response plt.plot(d_axis, td) plt.xlabel("Distance (m)") plt.ylabel("Magnitude") plt.title("Return loss Time domain") plt.show() |

## Real Results

Everyone must be looking forward to watching this section of the article. I tested this script by connecting a small 36 inches of RG405 cable which comes to approximately 0.91 meters. The velocity factor for RG405 cable is 70.3% which is set in the code at line 8. After doing all sort of computation, line 25 prints out the distance in meters.

Comparing the actual cable length which is 0.91 meters and then looking at our results gives me great satisfaction. The error is quite small and it could even be due to calibration or temperature drift. Of course, an error of 3cm is unacceptable if you are working in the GHz range and you shouldn’t be even using this instrument in the first place.

Let us measure another cable, this time a LMR200. Now, the exact length of cable we are about to test is unknown to me. According to the markings on the cable, it should be somewhere in the range of 9.5 to 10 meters.

The most noticeable change on the graph is the shifted peak. Our source of reflection, which is the open end of the cable extended further due to a larger cable length. The time taken by the signal to traverse through the cable is much more. On the other hand, our script computed the cable length and it matches our expectation. Considering an error of 3cm based on our previous measurement of a shorter cable, we can say that this reading is totally ACCEPTABLE! Our expectation of the cable length was somewhere between 9.5 meters to 10 meters and our script computed the length as 9.639 meters!

## Where do I plan to use this?

When you are constructing antenna arrays, the feed cable length needs to be precise. This is required so that the antennas are phased correctly and in turn operate as expected. Without relying on expensive equipment, I can now do cable length matching sitting at home.

Our little script can also work to find faulty cables. Distance to fault can be known by looking at the graph and observing the measurements carefully.

Additionally, we can also figure out bad, faulty connectors by looking at the time domain graph. Badly soldered connectors are quite common and sometimes hard to spot but not anymore with TDR!

Having a nanoVNA surely opens many avenues for hobbyists. I am hoping that once enough people get their hands on this device, we will start to see so many other interesting experiments starting to pop-up over the internet. Not to forget, we might even see a FULL 2-port VNA pop up someday which could be affordable by hobbyists like me.

Awesome Salil. You should post to the NanoVNA group on groups.io as well.

cheers,

Vince

I guess you already did! Thanks 🙂

Excellent article Salil.

I have spent the last 9 month building a UWB tester. UWB measures Time Of Flight and thus distance. So obviously I simulate distance using RF switches and different length cables. A delay box. There’s a few other goodies in the tester part. But anyway

This page shows me how I can use a piece of $70 equipment to characterize both my cables, and my delay boxes. The delay is not just the cables, but also the switches which are eval boards, and splitters, and attenuator.

I’m operating at 6.5GHz which is a little higher than 300MHz, but I’m guessing propagation delay will only change a few % going up to 6.5GHz. I’ll be able to verify or benchmark thatanyway against a 12GHz or better VNA.

So Salil you talked me into buying 3 not 1.

Super! You could try going slightly higher on the nanoVNA, like 500-600MHz but I preferred staying below 300MHz because thats where this instrument performs the best.

Coś tu nie tak 🙁

nie mogę dołączyć jpg swoich wyników ale są one zupełnie inne.

Szukaj “Adam Puszczański” w grupie “Krótkofalowcy na FB. Język polski.

Tranlate – przyda się

Thanks for the script 🙂

I added it to the reverse-engineered NanoVNASharp from Roger Clark.

https://zs1sci.com/blog/nanovna-tdr/

Thanks again for your script and the great post!

Amazing work ZS1SCI! I went through your post and really loved the automation. I will surely download from your repo and try it out on my PC.

Is s11 complex or real? Please give me a test data file like “cable_open_2.s1p”.

It is complex.

But I got real S11 from E5071c . The Img part was zero. Please give me the data file so that i can varify that . Thank you very much.

I have uploaded my S1p Files here: https://drive.google.com/open?id=1tvyq0WUUgdyOoqCcmBzno5r9hHbNvpGq

I‘m sorry. In our country we can’t open this website. So I have to bother you to email this file to me. My email is zxf123465@163.com. If having more information about FDR/TDR, please teach me. Thanks a lot.

!S – Parameter data, F S11

10000000 0.886622058 75.806693108

How to translate to 0.21739453+0.85955703j

Dear nuclearrambo :

I used E5071C to get S11 data like below. The cable lenght is 30cm, one port connected the VNA, another port was open.

Using the S11 data to calculate the distance I got the wrong result. Please tell me why, thank you very much.

# MHz S RI R 50

!freq ReS11 ImS11

10.000 0.00 0.00

11.900 -0.01 0.00

13.800 -0.01 0.00

15.700 -0.02 0.00

17.600 -0.01 0.00

19.500 -0.01 0.00

21.400 -0.02 0.00

23.300 -0.01 0.00

25.200 -0.03 0.00

27.100 -0.03 0.00

29.000 -0.04 0.00

30.900 -0.04 0.00

32.800 -0.04 0.00

34.700 -0.04 0.00

36.600 -0.06 0.00

38.500 -0.04 0.00

40.400 -0.05 0.00

42.300 -0.06 0.00

44.200 -0.07 0.00

46.100 -0.08 0.00

48.000 -0.08 0.00

49.900 -0.09 0.00

51.800 -0.09 0.00

53.700 -0.12 0.00

55.600 -0.13 0.00

57.500 -0.13 0.00

59.400 -0.15 0.00

61.300 -0.17 0.00

63.200 -0.19 0.00

65.100 -0.22 0.00

67.000 -0.23 0.00

68.900 -0.23 0.00

70.800 -0.25 0.00

72.700 -0.26 0.00

74.600 -0.28 0.00

76.500 -0.28 0.00

78.400 -0.29 0.00

80.300 -0.31 0.00

82.200 -0.32 0.00

84.100 -0.34 0.00

86.000 -0.36 0.00

87.900 -0.36 0.00

89.800 -0.36 0.00

91.700 -0.36 0.00

93.600 -0.38 0.00

95.500 -0.40 0.00

97.400 -0.42 0.00

99.300 -0.45 0.00

101.200 -0.45 0.00

103.100 -0.45 0.00

105.000 -0.44 0.00

106.900 -0.42 0.00

108.800 -0.40 0.00

110.700 -0.41 0.00

112.600 -0.38 0.00

114.500 -0.39 0.00

116.400 -0.38 0.00

118.300 -0.40 0.00

120.200 -0.41 0.00

122.100 -0.40 0.00

124.000 -0.41 0.00

125.900 -0.42 0.00

127.800 -0.42 0.00

129.700 -0.42 0.00

131.600 -0.43 0.00

133.500 -0.43 0.00

135.400 -0.44 0.00

137.300 -0.45 0.00

139.200 -0.45 0.00

141.100 -0.46 0.00

143.000 -0.46 0.00

144.900 -0.45 0.00

146.800 -0.47 0.00

148.700 -0.48 0.00

150.600 -0.46 0.00

152.500 -0.47 0.00

154.400 -0.48 0.00

156.300 -0.48 0.00

158.200 -0.49 0.00

160.100 -0.46 0.00

162.000 -0.49 0.00

163.900 -0.49 0.00

165.800 -0.49 0.00

167.700 -0.49 0.00

169.600 -0.50 0.00

171.500 -0.50 0.00

173.400 -0.51 0.00

175.300 -0.49 0.00

177.200 -0.52 0.00

179.100 -0.52 0.00

181.000 -0.51 0.00

182.900 -0.50 0.00

184.800 -0.53 0.00

186.700 -0.52 0.00

188.600 -0.52 0.00

190.500 -0.53 0.00

192.400 -0.53 0.00

194.300 -0.53 0.00

196.200 -0.54 0.00

198.100 -0.54 0.00

200.000 -0.55 0.00

Hi Salil,

If there is a load like for example 50 Ohms, is it possible to modify the script to use

the 2nd peak of the plot from the source, so we can have the distance from the

source to the load?

Thanks,

neb

It is possible but I didn’t quite get what you want to do exactly.

Hi Salil,

The issue was resolved by recalibrating my nanoVNA.

Anyway, with regards to your other script with impedance plot, can

we compute for the Impedance of the load from the plot? I use Z_Load = step_response_Z [idx_pk [0]] ,

is this correct or not?

Thanks,

neb

Another use for this would be to calculate velocity factor from known lengths of cable and once you’ve the velocity factor I think adding a known load would allow the measurement of cable impedance.

Please help me to run this script under the windows power shell ! I don’t know how to make this !

Can we use this meter to measure the balance cable left in a drum , progressively reducing as one starts cutting and using .

Thanks

sarma

Yes you can do that for sure. The new firmware comes with the TDR feature. You can do this measurement on the nanovna itself.

Hello,

Have a look at the new 3GHz NanoVNA V2 aka S-A-A V2. Has transform built in and the source is fundamental not harmonic based.

https://groups.io/g/NanoVNA-V2

I bought mine with the better cable set from http://www.randl.com IIRC about 70.00 USD

W3OHM

I will be reviewing it this weekend!

Have you tried a script to reverse the computation, knowing the exact length of the cable and determining its velocity factor?