CocoaVNA History

0.9.4 2013.02.xx


The textured window style has been turned off, yielding a more up-to-date appearance and eliminating an odd artifact near the bottoms of those windows.

The Integrate sweep mode applies an exponential smoothing filter to multiple measurements at each frequency. The smoothing factor was 0.5; it is now 0.1. The consequence is increased smoothing, but more sweeps are needed to see the full effect when there is random noise in the measurements.

Misfeatures fixed

Being very focused on S21 measurement accuracy, I added data dumps at various steps in the instrument phase detector calibration method and plotted the values using pro Fit. The transmission data plot (linear-in-frequency cable phase model minus measurement) showed a suspicious discontinuity in slope near +90° and I spent two days scouring the code looking for an explanation. I did find an instance of a classic C mistake: abs() was used instead of fabs(), resulting in silent truncation of a double value and causing a small indexing error. I was unable to eliminate the discontinuity, but it is small enough that I decided to ignore it.

New frequency sweep documents were not adopting the span limits and step size of the default fixture calibration file.

0.9.3 2012.03.02


Over the past several months I have used cocoaVNA extensively while constructing a modified version of the W1FV 9-element receive array. John’s design combines three elements in a phased-array; the array pattern and directivity are quite sensitive to the combiner weights so I’ve been measuring S21 between the combiner output port and the three antenna ports for various implementations of the combiner. After a while, I realized that the odd (far from analytic predictions) and inconsistent (different from day-to-day) results might not be due to my meager construction skills, but rather to trouble with the measurements. So, I met with W1FV and we did the S21 measurements with his AIM VNA. Those measurements confirmed my suspicions (and that my combiner was actually pretty darn close to optimal weights).

About this time, I decided to redo the instrument calibration for my VNA; it failed at the step which processes response data for the transmission amplitude detector. W1FV returned to me a second TAPR VNA that I had loaned to him; that one failed calibration at the same step. [John reported that he had similar S21 measurement issues with the loaned VNA using the TAPR Windows software.]

I purchased a third TAPR VNA from Ten-Tec in February. Out-of-the-box it failed instrument calibration at the same step. I verified that it also failed using the TAPR software and sent it back for servicing. It came back with “no problems found.” I ran the cocoaVNA instrument calibration procedure and it succeeded. I ran instrument calibration on each the two defective VNAs and it succeeded in both cases. Clearly something I had changed in cocoaVNA had a beneficial effect. However, that cannot explain the calibration failures on the Windows, since the VNA firmware is loaded each time the instrument is powered on.

What changed in cocoaVNA? See below. I believe that code which attempted to set the amplitude and frequency of the parked VNA signal was the miscreant. I knew that code wasn’t working, and removed the feature, restoring the original park settings: minimum amplitude at 200 kHz. I’m pretty sure that the bogus code was causing the VNA to overheat; I’ve noticed that the case is much cooler than before.


Removed broken code relating to setting preferences for frequency and amplitude of the VNA output signal when not scanning (“park” mode).

Converted all code to 10.7+ 64-bit with ARC memory management and fixed all issues reported by the Xcode 4.3 Analyzer.

Added separate preferences for S11 and S21 phase plot ranges.

The reference impedance for fixture calibration is now always 50 + j 0.

Reorganized the items in the Settings drawer for Sweep documents.

Tracked down the meaning of an obscure USB error code and added to VNA comms error handling.

Added series and parallel RLC to Sweep document marker table.

Added marker table layout memory.

Added marker table column visibility menu (right-click on the table header row).

Added -activateIgnoringOtherApps. Thanks W7AY.]

Misfeatures fixed

Corrected code that was attempting to post alerts in a background thread.

S11 color preferences wasn’t being remembered.

VNA sweep progress bar was showing incorrect state when sweep ended.

Changing the reference impedance was applying a wrong transformation to the S11 data when plotted on the Smith chart. Now, for example, choosing 75Ω as the reference impedance plots measurements for a 75Ω termination at the center of the chart.

Changing the reference impedance wasn’t affecting the derived SWR values.

0.9.2 2010.03.22

Misfeatures fixed

Added missing TimeDomainReflectometryDocument:hasMeasurements method, used for menu item enabling. Led to crash at exit.

Repaired broken drag gestures in the TimeDomainReflectometryDocument content, which translate the trace left and right. They were also translating the window. Required changing the view subclass to return YES for the isOpaque method, which then exposed a drawing issue – the drawRect method now fills the content region with white.

Added labels to the frequency span and step fields in the FrequencySweepDocument window. Removed custom formatters for start and stop fields. Modified custom formatter for step field to handle value in kHz instead of MHz. Added “full” special value to step field (that field recognizes band names like “10m”, as well as “hf” and “full,” as shortcuts for setting start, step and stop fields as a group). Set default for new windows to “hf.” Added tooltips to all three fields. Modified window tab ordering: first tab focuses the chart type popup, then cycle through toolbar items, then frequency fields, then Run button. I think this will fix a value formatting issue in the start field noted by W7AY.

Replaced number of steps field with frequency step size field in the Fixture Calibration window, for consistency with frequency specification in other places. Previous fixture calibration files should work, although they will exhibit “odd” frequency step sizes.

Now set the frequency span and step fields from fixture data when a new fixture file is loaded into a Frequency Sweep window. Typically, attempting to collect sweep measurements outside the range of the fixture data leads to very quick sweeps with no results.

0.9.1 2010.03.17

New features

Added the Full Measurement window, opened via a new button on the tool bar of the Frequency Sweep window. Use the window as a guide for capturing the complete S matrix for a DUT, which requires collecting forward measurements as usual, and reverse measurements with the DUT connections interchanged.

Added a Reverse Measurements checkbox to the Frequency Sweep window. When checked, S11 and S21 and all derived quantities are taken from the array of reverse measurements. That is, the displayed S11 is S22, and the displayed S21 is S12. This was easy to implement; I’ll add distinct displays for forward and reverse data if users complain (loudly).

Added a Save S Matrix command to the File menu, which writes a text file containing some header lines (marked with # prefix) and lines at each measurement frequency containing tab-delimited fields for frequency and the four complex elements of the S matrix. The format of the complex values is like “-1.331E-02 +2.500E-03j”, intended to support easy ingest by Matlab or Octave. Thanks W6ODJ and W7AY for motivating these additions.

Twiddled window appearances (turned on the Texture attribute).

Known misfeatures

The remark about Reverse Measurements above does not apply to Group Delay, because I was too lazy to create separate arrays. The value shown corresponds to whatever was the last measurement run state.

0.9 2010.03.14


Created separate frequency grids for instrument and fixture calibration. The instrument calibration grid remains fixed at the prior settings. The fixture calibration grid can be changed from the defaults when performing the calibration, and subsequent frequency sweep measurements with that fixture are limited to the frequency range of the calibration grid. This is (apparently) the technique used by the AIM VNA to handle connections between VNA and DUT with rapidly-varying frequency characteristics, such as bandpass filters used to suppress out-of-band interference when measuring HF antenna systems. Thanks W6ODJ and W7AY.

0.8 2009.07.18


Added keyboard shortcuts, ⌘⬆ and ⌘⬇, for incrementing and decrementing the current marker frequency.

Misfeatures fixed

IMPORTANT: fixed (finally) a bug that affected instrument calibration. The symptom was unphysical jumps in S11 and S21, particularly phase. You should trash existing calibration files and redo both instrument and fixture calibrations. I introduced this bug when converting Tom’s code to Objective-C, long ago.

0.7.1 2008.12.20


Added Export… item in File menu. Generates a text file with five header lines and a sequence of records describing each measurement in the current Frequency Sweep document. The measurement record has five fields: frequency (integer, Hz), S11 and S21 magnitudes (real, dB), S11 and S21 phase (real, degrees).

0.7 2008.12.20


Added Sweep Level preference for setting output level in range [-75, 0] dBm.

Modified TDR Settings, adding an “electrical degrees at specified frequency” choice, and changing arbitrary velocity factor field to a popup list of common coaxial cable types.

Added Notes panel to both TDR and Frequency Sweep documents. Arbitrary text entered in the panel is saved with the document.

Misfeatures fixed

Fixed a bug that made Park Level preference value not persistent. Park Level and Sweep Level do not seem to be working; let me know if you need this functionality.

0.6 2008.09.28


Increased sample density for the ham-band presets. Presets are pre-defined start, step, stop sets, entered by typing a band name, such as “160m” in the step size field.

Added a preset named “hf.”

Prepended plot symbols to vertical axis labels for rectangular plots.

Added a note at top right corner of S21 plot when measurements are possibly corrupted by external signals, which may leak into the RECEIVE port if the DUT is poorly shielded. Uses an algorithm by N5EG added to VNAR3 beta 2.1.6; thanks Tom!

Updated VNA target firmware to version 0.9.2.

Misfeatures fixed

Fixed a cosmetic off-by-one bugs in progress numerical displays.

Fixed a bug that stalls cocoaVNA with no alert message when the transmission detector amplitude calibration fails.

Fixed a bug that warned about start frequency less than 0.02 MHz instead of 0.2 MHz.

Fixed a bug that limited the range of the S21 magnitude axis to [1, 32]. The range is now unconstrained.

Fixed a bug that “lost” changes to vertical axis ranges in the settings drawer for 2D plots when, for example, a plot was changed or another plot attribute preference like symbol color was changed.

0.5 2008.07.21


Added a rudimentary Apple Help Book, based on circa 2005 templates by Andy Matuschak. If I have the time, energy, ability, (and, most of all, the stimulus), I’ll attempt to make the book more Leopard-like, and add finer-grained topics and many more links.

Deleted duplicate information on the web site, so that I don’t have to maintain it.

0.4 2008.07.18


Changed the upper frequency limit to 120 MHz from 100 MHz.

Made the frequency fields on the Sweep tab of the Preferences window somewhat more convenient, by better choice of units, and somewhat less fussy, by moving the units suffix to a separate label.

Simplified instrument calibration by combining and reordering steps.

Elaborated fixture calibration instructions, noting that steps can be performed in any order.

Visually compared cocoaVNA against TAPR software (VNAR3 2.1.2), with 50Ω SMA 3m out 1m back fixture. 50Ω termination on 3m cable; Impedance OK. Open 3m cable; S11 OK. Shorted 3m cable; S11 OK. 10dB pad as DUT; S21 OK. 40dB pad as DUT; S21 OK. 8m (electrical) length of RG6, open at far end, attached to 3m cable; S11 OK, TDR OK. “OK” means that traces have no obvious differences for sweeps from 0.2 MHz to 120 MHz. The cocoaVNA results are slightly closer to theoretical values, probably due to longer warmup and/or more careful fixture calibration.

Misfeatures fixed

Fixed a bug affecting Smith chart background color when box width was less that box height.

Fixed a bug that incorrectly marked fresh Frequency Sweep documents as changed.

Fixed a bug that failed to remove the “out” cable length when using the Time Domain Reflectometry feature.

Fixed a bug failing to reset measure button to Run at end of sweep in the Time Domain Reflectometry window..

Fixed a cosmetic bug failing to right-justify Settings button in Time Domain Reflectometry toolbar.

0.3.8 2008.07.14


Added deglitching of error data in directional coupler ripple calibration, per algorithm added in VNAR3 Beta 2.1.3.

Added rectangular chart axis limit settings to the Frequency Sweep window. They are initialized from preferences for new documents. Changing the settings for a document affects only that document, and the changes are persistent.

Misfeatures fixed

Changed the TDR scaling so that all “distance” readouts are one-way. The time readout was two-way.

Reverted the directional coupler magnitude correction to the form used in VNAR3 after consulting with N5EG. The implementation does not contradict the comment.

Fixed a bug: misspelled key in unarchiving the diffQDelayNs Detector ivar.

Fixed a bug: Detector name ivar not set, but used to distinguish between reflection detector and transmission detector.

Fixed a bug: failed to delete “/2.0” when replacing Math::Pi / 2.0 with M_PI_2. All of these bugs affected instrument calibration, this one was the most significant. Results now compare well with the TAPR software for a section of RG6 open at the far end.

Modified progress bar and status text updating in the Frequency Sweep window so that they properly reflect the true sweep status.

Fixed an initialization issue that generated random garbage on the rectangular plots before a sweep was run.

Updated web pages to fix glitches introduced by MobileMe. Grrr. Some of the web pages need updating, especially preferences and documentation for rectangular charts.

0.3.7 2008.06.17


Added display of the current instrument name to the Fixture Calibration window.

Fiddled with cosmetics of Frequency Sweep window layout.

Misfeatures fixed

DirectionalCoupler class had a bug that caused it to forget whether or not it had been calibrated. Fixed, but with no apparent effect on cocoaVNA results; puzzlement.

Reimplemented the Use Fixture Correction checkbox feature. The results makes sense for S21 (must run sweep to update group delay), and for s11 after all the bug fixes below. Qualitatively tested for open, short, terminated to-DUT cable, and for DUT = 40 dB pad. Thanks AA7QU.

Tracked down several porting bugs affecting calibration, including typos and an egregious programming mistake in referencing elements of multi-dimensional C arrays. Also found one possible mistake in the VNAR3 source code (implementation contradicts comment). Much of this was masked by fixture calibration, which evidently has the power to cover large mistakes in instrument calibration. The Use Fixture Corrections checkbox in the Settings drawer now results in the expected effects on the Smith Chart display.

Updated the alert text for the case of coupler ripple calibration failure. But one hopes that the above repairs will make this alert very rare.

0.3.6 2008.06.15


Revised the default color scheme, using the set of six “Bright” colors from Keynote 08: brightBlue for first data set, brightGreen for second data set (in charts that have two traces), brightYellow for markers, brightOrange for the cursor, brightRed for the Smith Chart grid. brightViolet is not used. Text is black, and background is the window background color.

Made cosmetic adjustments to the Frequency Sweep window: smaller minimum height, wasted white space at bottom of markers table reduced, better initial column widths in markers table.

Now display chart axis captions by drawing them instead of using text fields, to prevent flashing and support rotating the y axis captions.

Added tiny-type display of current instrument and fixture calibration names at lower left on all charts. The fixture calibration is not (yet?) affected by the Use Fixture Calibration check box. Removed the fixture file name string from the shelf in the Frequency Sweep window.

Added display of markers to charts. The appearance is somewhat different than for the Smith Chart: the cursor marker is not distinguished from others by color, and the selected marker is not distinguished from others by size. Instead, all markers have the same color, and they are drawn at twice the size of the data point markers. Dragging the cursor slider moves the cursor marker along the data trace(s) as one would expect.

Refactored the chart controller code to place as much as possible of the boilerplate code in a base class.

Modified PHGraph to call a delegate method at the end of drawRect.

Added a square symbol to PHGraph.

Implemented Group Delay algorithm and chart. The algorithm is brute force and slows things down with large apertures. For now, leave the aperture preference value at 1 unless you need the smoothing.

Added units to fields in Preferences and redid the layout. Needs more work.

Reworded the instrument calibration phases, now 6, to describe what to do instead of describing the end result. For now, two of the phases have two “Run” buttons. Thanks W7AY.

Similarly reworded the fixture calibration phases.

Added a “do you want to save” alert to fixture calibration.

Reimplemented the circle symbol drawing code in PHPoint drawWithContext using NSBezierPath. This cured horribly slow drawing behavior and cursor response with many points (900) in the frequency sweep. Thanks Shark, which led me right to the bottleneck.

Trashed the Instrument singleton. Replaced with Instrument instances embedded in Fixture instances, which is much cleaner because a particular fixture cal data set can only be used with the instrument cal data set that was in effect when the fixture cal was created. Documents contain (one) Fixture, which contains its Instrument. Tidy. Thanks AA7QU.

Added a beep at the end of each calibration step.

Misfeatures fixed

Color preference changes for the new chart types were not being applied to existing charts.

New chart types did not draw for documents opened from a file.

Color preference for S21 phase data was broken.

Reference impedance ivar of Fixture was not initialized, causing impedance computation to return 0 + j 0 when “Use Fixture File” is unchecked.

Cursor slider was stuck as left end when start frequency was greater than stop frequency.

The status string for step 7 of instrument calibration was printing garbage. Thanks W7AY.

The status string and progress bar for step 8 of instrument calibration were not reset properly when the step finished. Thanks W7AY.

The dirty bit for the instrument calibration window wasn’t reset on save, causing an extraneous alert when closing the window.

Progress bar and status were not being reset when fixture calibration steps completed. Thanks W7AY.

An alert identifying a particular calibration failure was not appearing when it should have.

0.3.5 2008.06.06


Removed the restriction that Start Frequency must be less than Stop Frequency. There is no reason why you can’t sweep “backwards” if you want to.

Added Impedance Chart, SWR Chart, S11 Chart, and S21 Chart. They have basic preferences for axes ranges and data marker colors, and no interactivity other than the PHGraph context menu. Posted as-is to get feedback.

0.3.4 2008.06.05


Revamped data structures and logic so that running sweeps in the Frequency Sweep window draws each measurement point as it is acquired or updated.The Time Domain Reflectometry window can’t do this, because it needs the complete set of measurements to compute the time-domain trace. In the Accurate mode sweeps, there is a deglitch step at the end of each sweep that may cause any of the measurement points to “squirm” on the display. This change also makes it possible to rerun a measurement without trashing existing markers. Small issue: the “m of n” and progress bars do not always show the correct values at the end of a sweep.

Changed the “Measure/Stop” buttons in the Frequency Sweep and Time Domain Reflectometry windows to true toggle buttons reading Run and Stop. Small issue: if pressing Run fails (no VNA for example), the button state remains as Stop. Press it once to return to Run state, then again to retry a run.

Redid the Sweep Mode settings controls in the Frequency Sweep window’s drawer and in Preferences to better reflect the 5 kinds of sweeps.

Added S11, S21, and Group Delay columns to the Markers table. Removed Return Loss as it’s the same things as the magnitude of S11. Implemented computations for the S11 and S21 columns.

Changed “Reflection” to “Frequency Sweep” everywhere, generalizing for additional types of displays.

Added a Chart chooser popup menu to the shelf in the Frequency Sweep window, populated with: Smith Chart, Impedance Chart, SWR Chart, Impedance Chart, S11 Chart, S21 Chart, Group Delay. Implemented view switching and refactored code to the new architecture.

Changed from specifying number of frequencies to specifying frequency step size. Now users can create scans with ridiculously large number of frequencies. There is no alert; the label on the progress bar immediately shows how many frequencies are being swept, and users can “recover” easily by pressing the Stop button.

Move various computational methods for extracting things like SWR from S11 to the Measurement class.

The above code changes also allow creating a single-frequency scan by setting the stop frequency equal to the start frequency. Previously, the minimum number of steps was 2.

Removed sweep frequency fields from drawer, replacing them with direct-entry fields in the Frequency Sweep window. Attached a new custom “Frequency” formatter to each of those fields.

Added recognition of strings like “160m” in the step size field to set all three fields to span an amateur radio band, for each of the bands 160m through 6m.

The VNA device is always transmitting when it is turned on. Added preferences to set the “park” frequency and level to place that signal where it doesn’t interfere with other measurements. Defaults to 200 KHz at -75 dBm. Changes do not take effect until either a measurement is run or cocoaVNA is restarted.

Replaced the green checkmark and red X images denoting whether or not a calibration step has been completed by checkbox images on the run buttons, in the Instrument Calibration and Fixture Calibration windows.

Misfeatures fixed

Fixed a bug: the cursor frequency slider wasn’t changing position when the frequency in the first row of the Markers table was edited.

In PostScript beginpage: add the origin of the superview’s frame to the transformation so that the chart draws inside the superview (an NSBox now).

0.3.3 2008.06.01

Relocated the fixture name labels from the bottoms of the Reflection and TDR document windows to their respective shelfs.

Revised internal logic so that the algorithms executed by Measure and Step button presses are safely serialized when a button is pressed (in any window) while another algorithm is already running.

Added a measurement status label just above each progress bar. It reads “unavailable” if the VNA device is not responding, “ready” if the VNA is responding, or something like “m of n samples” if the VNA is busy. When running calibration steps in the Instrument Calibration or Fixture Calibration windows, the status labels in document windows read “busy.” Thanks W7AY.

Fixed rather too many grammatical errors and some confusing content in the documentation. Thanks W2RU.

0.3.2 2008.05.31


Added Use Fixture File checkbox in Reflection Document settings to toggle between no fixture corrections and corrections using the document’s fixture calibration file.

Created distinct icons for instrument and fixture calibration files.

Added General preferences tab with settings for default instrument calibration file and for default fixture calibration file. Changing the instrument default applies immediately. Changing the fixture default affects only new documents.

Now save measurements, frequency grid, and fixture data in document files. These are now stand-alone files; before the files referenced the fixture file by path and loading would fail if that fixture file wasn’t found.

Added SetAsDefault convenience buttons to Calibration windows. They are enabled after a calibration is completed and saved, as a shortcut to choosing the new files in Preferences.


Massively refactored code for saving and loading all file types to use keyed archives. cocoaVNA can no longer use files from the Windows app, and cannot use files created by earlier versions of cocoaVNA. This change greatly improves maintainability and allows to add new items to files with backward and forward compatibility.

Modified internals to support user-selectable instrument calibration file.

Refactored a class based on Windows app architecture to cleanly separate Instrument and Fixture calibration data and methods.

Added cursorFrequency ivar to FrequencyGrid and eliminated a great deal of fragile logic in ReflectionDocument by using KVO.

Misfeatures fixed

Fixed a stumbled-upon bug where a static array was dimensioned 260 instead of 360. No clue how this ever worked.

0.3.1 not released

Added Load Cal buttons to document toolbars. These do the same thing as the Load Fixture Calibration item in the file menu (for open documents): change the fixture calibration file used by the document.

0.3.0 2008.05.28


Added Time Domain Reflectometry function. Printing works, although the chart is rather plain-looking.

Added distinct icons for each document type and for the application.

Replaced sheets with drawings for document-specific settings. Drawer visibility is toggled via items on the VNA menu, or by buttons on the (new) toolbars. I found it awkward to open sheet, change setting, close sheet, Measure.

Major redo of code relating to fixture calibration to eliminate many conversions back and forth between two doubles and one double complex. Fixture calibration file format has changed, again.

Misfeatures fixed

Fixed crash in very last step (Save) of Instrument Calibration function. Thanks AA7QU.

Now save detector.ica file, which is the output of the Instrument Calibration function, in the cocoaVNA application support folder instead of in the application bundle. This avoids a potential crash trying to write to a read-only volume when, for example, the application is run from a read-only dmg.

Post an alert when the VNA is not accessible or not responding, when opening either of the calibration windows, and do not open the windows. Before this fix, cocoaVNA crashed when a step was executed. Thanks AA7QU.

Cleaned up, I hope, change tracking in Reflection documents, and fixed some initialization order issues in reading Reflection document files.

0.2.0 2008.05.25


Added arbitrary reference load impedance to fixture calibration. Automatically affects computation of impedances from reflection coefficients (S11). Motivation was analyzing 75Ω systems, but works for any frequency-independent load impedance. Fixture calibration file format is changed; previous files are unusable.

Moved the Fixture Calibration status icons to the right of the step buttons to mimic the Instrument Calibration window.

Allow saving fixture calibration file after first three steps are completed. Currently cocoaVNA doesn’t need the calibration data collected by step 4, which applies for S21 measurements.

Misfeatures fixed

Document dirty state tracking was too aggressive. Now document is not marked dirty right after it is loaded.

Sweep Settings window was inaccessible after the first time it was closed and did not show the document’s settings when opened. Changed to a document-modal sheet. This UI isn’t quite appropriate, but does at least make the connection between settings and document very clear. Modified the sheet to a textured panel to mimic the other cocoaVNA “utility” windows. The shortcut key for the sheet Done button is esc.

0.1 2008.05.20

First release.