//>>*************************************************************************** // UNCLASSIFIED // // COPYRIGHT 2017 RAYTHEON MISSILE SYSTEMS // ALL RIGHTS RESERVED // This data was developed pursuant to Contract Number HQ0147-12-C-0004/1088370 // with the US Government. The US Government's rights in and to this // copyrighted data are as specified in DFAR 252.227-7013 // which was made part of the above contract. // // Distribution Statement: D -Distribution authorized to the DoD and DoD // contractors only based on Critical Technology Requirements, May 2001. // Other requests shall be referred to PEO THEATER AIR DEFENSE (PMS 422). // Warning: - This document contains technical data whose export is restricted // by the Arms Export Control Act (Title 22, U.S.C.) or Export // Administration Act of 1979, as amended (Title 50, U.S.C.). Violations // of these laws are subject to severe criminal penalties. Disseminate in // accordance with provisions of DoD 5230.25. // Destruction Notice: - For unclassified, limited distribution information, // destroy by any method that will prevent disclosure of contents or // reconstruction of the document. Classified information, destroy in // accordance with DoD-5220.22-M or OPNAVINST 5510.1h. //>>*************************************************************************** using System; using System.Text; using System.Threading; using NLog; using Raytheon.Common; namespace Raytheon.Instruments { /// /// A class for controlling a scope via ZBind Teradyne Library /// public class ScopeZBind : IOscilloScope { #region PrivateMembers // Maximum number of channels provided by scope. private readonly string _address; private IntPtr _handle; private State _state; private SelfTestResult _selfTestResult; private string _name; private readonly ILogger _logger; private readonly IConfigurationManager _configurationManager; private readonly IConfiguration _configuration; #endregion #region PrivateFunctions /// /// The Finalizer which will release resources if required /// ~ScopeZBind() { Dispose(false); } /// /// Dispose of this object /// /// protected virtual void Dispose(bool disposing) { if (disposing) { if (_state == State.Ready) { Reset(); ScopeZBindNativeMethods.zbind_remove(_handle); _state = State.Uninitialized; } } } #endregion #region PublicFunctions /// /// ScopeZBind factory constructor /// /// /// /// public ScopeZBind(string deviceName, IConfigurationManager configurationManager) { Name = deviceName; _logger = LogManager.GetLogger($"{this.GetType().Name} - {deviceName}"); _configurationManager = configurationManager; _configuration = _configurationManager.GetConfiguration(Name); _address = _configuration.GetConfigurationValue("ScopeZBind", "Address", ""); _state = State.Uninitialized; _selfTestResult = SelfTestResult.Unknown; } /// /// /// /// /// public ScopeZBind(string deviceName, string address) { _name = deviceName; _logger = LogManager.GetLogger($"{this.GetType().Name} - {deviceName}"); _address = address; _state = State.Uninitialized; _selfTestResult = SelfTestResult.Unknown; } /// /// /// /// public bool ClearErrors() { throw new NotImplementedException(); } /// /// /// /// /// Horizontal /// /// /// Verticle Voltage Scale /// public void ConfigureChannel(int channelNumber, double timePerDivison, double timeOffset, double voltageOffset, double voltageScale, string inputImpedance) { const int SWEEP_POINTS = 2000; Reset(); IOWrite("INP1 ON"); IOWrite("INP2 ON"); IOWrite("SENSe:SWEep:POINts " + SWEEP_POINTS.ToString()); // Options defined in zScopeM IOWrite("SENSe:SWEep:TIME " + timePerDivison.ToString()); // SWEEP_TIME.ToString()); // In seconds IOWrite("SWE:OFFS:TIME 0.0"); IOWrite("AVER:STAT 0"); IOWrite("INIT:CONT 0"); IOWrite("SWE:MODE NORM"); IOWrite("VOLT1:RANG:OFFS " + voltageOffset.ToString()); IOWrite("VOLT1:RANG:PTP " + voltageScale.ToString()); // 10 division on screen so V/Div will be 1/10th of input IOWrite("INP1:FILT 0"); // start wave form collection IOWrite("INIT"); Thread.Sleep(1000); } /// /// /// public string DetailedStatus { get { return "This is a Teradyne ZBind Scope"; } } /// /// /// public bool DisplayEnabled { get { throw new NotImplementedException(); } set { throw new NotImplementedException(); } } /// /// Dispose of this objects resources /// public void Dispose() { Dispose(true); GC.SuppressFinalize(this); } /// /// /// public bool FrontPanelEnabled { get { throw new NotImplementedException(); } set { throw new NotImplementedException(); } } /// /// /// /// public bool HasItTriggered() { // Did not find support for this in the API, just return true return true; } /// /// /// public InstrumentMetadata Info { get { throw new NotImplementedException(); } } /// /// /// public void Initialize() { // if we have not yet been initialized, go ahead and create the socket if (_state == State.Uninitialized) { int ZT_LAN = 0x0004; int err = ScopeZBindNativeMethods.zbind_add(_address, ZT_LAN, out _handle); // check for errors if (err != 0) { throw new Exception("ScopeZBind:Initialize() - Scope " + _name + " returned error code: " + err.ToString()); } // reset the scope Reset(); // we already connected to the instrument in the constructor _state = State.Ready; } else { throw new Exception("expected the state of System " + _name + " to be Uninitialized, state was: " + _state.ToString()); } } /// /// /// /// /// public string IOQuery(string command) { // send the command IOWrite(command, false); // read from the response StringBuilder rspStr = new StringBuilder(512); int err = ScopeZBindNativeMethods.zbind_receive(_handle, 0, "%[ -~]", rspStr); // check for errors if (err != 0) { throw new Exception("ScopeZBind:IOQuery() - Scope " + _name + " returned error code: " + err.ToString()); } return rspStr.ToString(); } /// /// /// /// public void IOWrite(string command, bool shallWeCheckForError = true) { int err = ScopeZBindNativeMethods.zbind_send(_handle, 0, command); // check for errors if (shallWeCheckForError == true) { if (err != 0) { throw new Exception("ScopeZBind:IOWrite() - Scope " + _name + " returned error code: " + err.ToString()); } } // wait a bit for processing Thread.Sleep(50); } /// /// /// /// public double MeasureFallTime(int channelNumber) { throw new NotImplementedException(); } /// /// /// /// /// public double MeasureFrequency(int channelNumber) { IOWrite("INIT"); IOWrite("SENSe:SWEep:MODE NORM"); string enableCommand = "SENSe:INPut" + channelNumber.ToString() + ":STATe 1"; IOWrite(enableCommand); // stop the waveform IOWrite("ABORt"); // wait a bit for the wave form to settle Thread.Sleep(1000); // The scope will respond with a string like "60.6575321, 0" string response = IOQuery("MEASure:VOLTage:FREQuency? INPut" + channelNumber.ToString()); double result = Double.Parse(response.Split(Convert.ToChar(","))[0], System.Globalization.NumberStyles.Float); return result; } /// /// /// /// public double MeasureMaxVoltage(int channelNumber) { throw new NotImplementedException(); } /// /// /// /// public double MeasureMinVoltage(int channelNumber) { throw new NotImplementedException(); } /// /// /// /// public double MeasurePulseWidth(int channelNumber) { throw new NotImplementedException(); } /// /// /// /// public double MeasureRiseTime(int channelNumber) { throw new NotImplementedException(); } /// /// /// /// public double MeasureVoltageLevel(int channelNumber) { throw new NotImplementedException(); } /// /// /// public string Name { get { return _name; } set { _name = value; } } /// /// /// public SelfTestResult SelfTestResult { get { return _selfTestResult; } } /// /// /// public State Status { get { return _state; } } /// /// /// /// public SelfTestResult PerformSelfTest() { throw new NotImplementedException(); } /// /// /// public void Reset() { // Resets the oscilloscope string command = "*RST"; IOWrite(command); // just a swag Thread.Sleep(3000); } /// /// /// public void SaveImage(string fileName) { throw new NotImplementedException(); } /// /// /// public void SetupTrigger(bool useRisingEdge, int channelNumber, double triggerLevel) { IOWrite("TRIG:TYPE EDGE"); IOWrite("TRIG:SOUR INP1"); IOWrite("TRIG:INP1:LEV " + triggerLevel.ToString()); if (useRisingEdge == true) { IOWrite("TRIG:SLOP POS"); } else { IOWrite("TRIG:SLOP NEG"); } } /// /// /// public void Shutdown() { string errorMsg = ""; if (_state == State.Ready) { try { //Reset System Reset(); } catch (Exception err) { errorMsg += err.Message + " "; } _state = State.Uninitialized; } // the stream was created in the constructor, dispose of it here try { int err = ScopeZBindNativeMethods.zbind_remove(_handle); // check for errors if (err != 0) { throw new Exception("ScopeZBind:Shutdown() - Scope " + _name + " returned error code: " + err.ToString()); } } catch (Exception err) { errorMsg += err.Message + " "; } if (errorMsg != "") { throw new Exception("System " + _name + " Had an error: " + errorMsg); } } #endregion } }