record: an application for capturing data from an HP CMS (Merlin) monitor
George B. Moody (email@example.com)
Warning: Although you are welcome to use record in your
own projects if you are able to do so, be aware that the necessary hardware
may be both expensive and difficult or impossible to obtain, and that the task
of recompiling record for use with currently manufactured hardware
is complicated by the need for proprietary libraries and compilers that
may also be both expensive and difficult or impossible to obtain. Since I no
longer have the CMS monitor that I used for development of record,
I am not able to test alternative hardware or software configurations; you
are on your own!
A (non-free) alternative to record is the Data
Acquisition Interface for CMS Patient Monitors available as an optional
module for Dataplore
(proprietary software for analysis of signals and time series, available for
GNU/Linux or MS-Windows). This software allows the use of a single serial port
at up to 38400 baud, which limits the number of signals that can be recorded
from the monitor. A newer version of this software, TrendFace, is specified to work at 115200 baud, allowing
more signals to be recorded simultaneously.
A (non-free) alternative to record is the Data Acquisition Interface for CMS Patient Monitors available as an optional module for Dataplore (proprietary software for analysis of signals and time series, available for GNU/Linux or MS-Windows). This software allows the use of a single serial port at up to 38400 baud, which limits the number of signals that can be recorded from the monitor. A newer version of this software, TrendFace, is specified to work at 115200 baud, allowing more signals to be recorded simultaneously.
record is an MS-DOS application that determines what signals and measurements are available from a Hewlett-Packard (Agilent/Philips) Merlin (a.k.a. CMS or Component Monitoring System) patient monitor, and then logs all of the available data to disk continuously until it is stopped by the user. The monitor contains up to eight plug-in modules for monitoring physiologic signals (ECG, respiration, pressures, temperature, gases, etc.), and can be reconfigured by the user by inserting or removing modules at any time without restarting the monitor. record, however, determines only which signals and measurements are available at the time it is started, and does not attempt to keep track of modules added later. Signals and measurements are considered available only if the associated module and the transducer are connected and the parameter is turned on; note that a signal or measurement need not be displayed on the monitor screen to be available (in fact, record cannot determine what subset of available parameters is being displayed).
In order to use record, the Merlin monitor must be equipped with at least one, and ideally two, serial interface cards. These are available as options from HP (Agilent, now Philips Medical Systems; most Merlin monitors are not equipped with these cards). Each card supports two serial lines, one at speeds up to 38400 baud, and the second at speeds up to 9600 baud (other possibilities are described below).
I wrote record in order to gather real-time patient data for the MIMIC (Multi-parameter Intelligent Monitoring for Intensive Care) Database project. The currently completed portion of the MIMIC Database (about 200 patient-days) is freely available via PhysioNet.
If you find record useful, please let me know how you are using it, by e-mail to firstname.lastname@example.org.
You may download record in precompiled form or in source form from this site. The precompiled version requires a DigiBoard PC/4e or compatible `smart' serial card (recommended, see below). With minor modifications to the sources, you can compile a version of record that can be used with the PC's standard serial ports (not recommended in most cases, since they cannot keep up with the Merlin's output) or with other smart serial cards. (Note that you should not do this just to save money -- in order to recompile the sources, you will need to buy subroutine libraries from Greenleaf Software, as well as Borland or Turbo C if you don't have one of these already; the DigiBoard card will be less expensive if you can obtain one.)
If you wish to use the precompiled version, download record.exe and record.ini, and save both of them in a directory somewhere in your MS-DOS execution path.
It is not necessary to compile record unless you wish to modify it.
record has been successfully compiled using Turbo C/C++ 3.0 and Borland C/C++ 4.0. Earlier versions of these compilers may work as well, but will require recompiling the external libraries as well as the program source. It should be fairly easy to port record to Microsoft C (all of the libraries it uses can be compiled by Microsoft C/C++ compilers without changes; this program uses Borland/Turbo-specific functions for screen output, for far heap memory allocation, and for checking the available disk space, but close equivalents are provided with Microsoft C).
To recompile record using Borland or Turbo make, follow the instructions in the makefile. (You should download not only record.c, but also all of the other files within the src directory, in order to do this.) record makes use of three external libraries:
- The MECIF library (mecif.lib), version A.01.10, originally available as Part No. M1046-9220C (Dec. 1992) from Hewlett-Packard (Agilent Heathcare Solutions Group, now part of Philips Medical Systems). This library contains functions that support serial communication between the PC and the HP CMS monitor. This software package is provided with the CMS RS-232 card, on an MS-DOS diskette (containing the library itself in source and binary forms, various header (.h) files, a demonstration program, and documentation files), and is accompanied by a manual titled "HP Component Monitoring System RS-232 Computer Interface Programming Guide (Option #J13)", referred to below as the HP Guide. A gzip-compressed tar archive of the contents of the MS-DOS diskette may be downloaded from here, by permission of the author and Philips Medical Systems. The original version of the MECIF library uses the standard PC serial ports, which are not suitable for high-bandwidth applications. To produce an enhanced version that can use a `smart' serial interface such as the Digiboard PC/4e (recommended), copy the MECIF library sources from the MS-DOS diskette to a directory on your hard drive, then copy the makefile and rs232g.c into the same directory, then follow the instructions in the makefile to build the library.
- The Greenleaf CommLib library (gfcl.lib), version 4.0, available from Greenleaf Software, sysFire LLC, Forest Park Gardens, Suite 309, 9550 Forest Lane, Dallas, TX 75243 USA (telephone: 1 800 523 9830 (USA/Canada only), or +1 214 349 3005). This library contains functions invoked by rs232g.c (see above) that support low-level serial communications using many different types of PC serial ports, including "smart" serial cards; this program does not call any CommLib functions directly. The package includes MS-DOS diskettes (containing the library in source form, various header files, and example programs), and a manual titled "Greenleaf CommLib 4.0 Reference", referred to in record.c as the CommLib manual. The sources can be compiled by many popular C compilers, including those from Borland and Microsoft; specify the primary compiler to be used when ordering CommLib, and the package will also include precompiled versions of the library for use with that compiler and various memory models. Be sure to use gfcl.lib (the large memory model version) with record. CommLib is required in order to use the enhanced version of the MECIF library described above; it is not required in order to use the Hewlett-Packard version. Although executable programs built using CommLib may be distributed without restriction, gfcl.lib may not be.
- The WFDB library (dbl.lib), version 9.0 or later, provided here in C source form and in binary form for Turbo C/C++ 3.0 and Borland C/C++ 4.0. This library includes functions that record uses to create files of received data in a compact, portable, binary format. The WFDB Programmer's Guide, referred to in record.c as the DB Guide, describes how to use this library. Be sure to use dbl.lib (the large memory model version) with record.
It is possible to compile record using the version of mecif.lib provided on the HP diskette and without using CommLib, and to use it with the standard PC serial ports (COM1 and COM2). The use of the revised MECIF library as described above, the CommLib library, and a `smart' serial card is strongly recommended as an alternative, permitting reliable operation at top speed while logging data to local drives. Without the use of CommLib and a smart serial card, record is limited to logging data to network drives. (Characters arrive at 260 microsecond intervals on each of the 38400 baud serial lines. Serial interrupts are locked out for several milliseconds during local disk writes. Without a smart card, characters that arrive while writing to the disk are lost. Although the MECIF protocol incorporates limited error detection, there is no provision for error correction or retransmission of lost messages. Lacking a smart serial card, it is possible to log data to a network drive, since the network interface accepts data at PC bus speeds, avoiding the local disk's interrupt latency.) This operating mode has been tested using a 3Com Etherlink III Ethernet interface card, with Sun PC-NFS networking software used to access the network drives.
The executable version of record provided here has been compiled for use with the DigiBoard PC/4e (or PC/8i) board, manufactured by Digi International, 11001 Bren Road East, Minnetonka, MN 55343 USA (telephone: 1 800 344 4273 (USA/Canada only) or +1 952 912 3444). Other serial devices supported by CommLib (hence the revised MECIF library) include smart cards from Arnet and Star Gate; a one-line change in rs232g.c is required in order to recompile a version of mecif.lib for use with any of these cards. Unfortunately, none of the smart serial cards supported by CommLib is still manufactured, so you will need to find a used card (frequently offered for sale on www.ebay.com) or else find a newer model that is supported by CommLib, or else devise a way to use another smart serial card without the use of CommLib. If you succeed, please tell me about it. The enhanced MECIF library also incorporates more robust error-recovery that avoids the need to reboot the monitor in the event of interrupted transmissions, a problem that occurs regularly when using the original version of mecif.lib from the diskette.
To use record:
- Connect the HP monitor to the PC using standard serial printer cables (see the wiring diagram on page 2-2 of the HP Guide). Up to four lines may be used.
- Turn on both the monitor and the PC.
- Run the program by typing
record FILE(where FILE is the name of a configuration file such as record.ini).
- Enter the data requested (patient name and ID). Note that this information is recorded only in the index file (see below), and not in the logged data files.
- Once recording has begun, use the monitor's controls to generate a set of calibration pulses. These will be needed to calibrate the recorded signals later on.
record checks the available serial lines and sets the speeds of the PC's ports to match those of the monitor. The best results will be obtained using the highest available speeds, permitting the maximum amount of data to be retrieved. If the total available bandwidth is insufficient to permit the monitor to transmit all signals and measurements, record attempts to obtain as many signals as possible, and then as many measurements as possible using the remaining bandwidth. If record is used routinely in a setting in which the bandwidth is insufficient, it may be worth modifying the code to permit the user to select which signals and measurements are to be recorded.
The monitor may have one or two RS232 serial cards installed in it (two are necessary in order to provide suffficient bandwidth to acquire all signals in most cases). Each RS232 card provides two ports. The lower ports are designated ports 1 and 3, and support communications at 9600, 19200, and 38400 baud; the upper ports (2 and 4) are restricted to 9600 baud (or 19200 baud if the lower port on the same card is not running at 38400 baud). The TX/RX order should be Low/High for all connected ports. These settings cannot be changed from the PC; refer to the HP Guide (pp. 2-4 to 2-9) for information on changing them using the monitor's controls.
The following baud rate settings are recommended (choose the first set that works from the list):
Port 1 Port 2 Port 3 Port 4 38400 9600 38400 9600 * maximum bandwidth 38400 38400 ** maximum bandwidth with only two lines 19200 19200 19200 19200 * use with modems or long cables if 38400 baud can't be used 38400 9600 maximum bandwidth with only one RS232 card 38400 maximum bandwidth with only one line
* Note that the revised MECIF library must be used in order to make use of three or four ports (the standard library supports only two). In some monitor configurations, the use of three or four ports fails for unknown reasons (apparently not related to record or to the PC hardware). For this reason, the default configuration (**) uses only ports 1 and 3.
Any of the first three choices provides sufficient bandwidth in most cases.
If you are using a version of record compiled for use with a DigiBoard PC/4e or PC/8i serial card, connections should be made using ports P1, P2, P3, and P4 (which should be configured as COM5, COM6, COM7, and COM8) of the DigiBoard interface, and the DigiBoard driver (currently xidos5.sys) should be loaded. Otherwise, use the PC serial ports COM1 and COM2 (depending on your hardware, COM3 and COM4 may or may not be usable as well). It makes no difference which PC port is connected to which monitor port.
For details on setting options in record, see record.ini, which is a sample configuration file. record sets its options using the first available source from the following:
- a file named on the command line (for example, record myconfig.ini)
- a file named in the environment variable RCONFIG (for example, by the command `set RCONFIG=c:\record\myconfig.ini')
- a file named record.ini found in the same directory as record.exe
- the compiled-in defaults shown in record.c
Thus a file named on the command line takes precedence over a file named in RCONFIG, and so on.
About the output
Each time it runs, record reads and updates an `index file'. The index file may be named in the configuration file (by default, it is record.idx in the same directory as record.exe). The index file is a text file. Each line in it contains data for one run of record. The first field of each line is the run index number.
The run index number is the name of the directory in which the log files for this run are collected (see below). By default, this directory is placed in c:\, but any other location may be specified using the configuration file. If space on the drive containing the log directory becomes nearly exhausted, and a `spillover' directory (presumably on a different drive) has been specified in the configuration file, record switches to that directory. Only one `spillover' directory may be specified; if none is specified, record does not use a `spillover' directory. When almost all of the available space has been used, record exits (it avoids writing on the last few blocks).
The log files contain the data retrieved from the monitor. At regular intervals (10 minutes by default), record closes the current set of log files and opens a new set; this strategy limits the amount of data lost if there is an interruption in power or other system failure. Each set of log files is identified by a five-digit sequence number contained within the names of the files. The first three characters of the file name are the index number (modulo 1000), and the next five are the sequence number (beginning with 00001). (In the unlikely event that more than 99,999 sets of log files are created, the index number is incremented and the files continue to be generated in numerical order.) The suffix (.dat, .al, or .nu) indicates what type of data will be found in the file (sampled signals, annotations of alarms and signal connections/disconnections, or numerics). An ASCII header (.hea) file accompanies each set, and contains the date and time (from the system clock) at which the files in the set were created, along with information necessary to read the .dat and .al files using DB application programs (such as view for MS-DOS, wview for MS-Windows, and wave for Linux, SunOS, and Solaris; visit our web site to obtain these applications, or to obtain details of the file formats if you wish to write your own programs for reading record output files).
Generally, log files of different types will have different lengths, but all log files of any given type should have approximately the same length, with the following exceptions:
- The last file of each type may be shorter than the others.
- If alarms or `inop' conditions occur, the corresponding .al and .txt files will be longer than the others.
- If a module was removed from the monitor during the run, the log files obtained during that period may be shorter than the others.
- Log files open when messages were lost may be shorter than the others.
Except for the first case, careful attention should be paid to any log files that differ significantly in length from others of the same type.
record also logs its run-time errors in an error log (by default, record.log, in the same directory as record.exe). The error log should be consulted after each run.
Creating a composite (multi-segment) record from a set of output files
Although record saves its output in segments that are (by default) 10 minutes in length, you may wish to concatenate the segments for ease of access by other software, as we have done for the MIMIC database. This process is quite simple and fast (though the description below is a bit long), and does not require any significant additional disk space (the data files need not be copied).
You can use other software available from PhysioNet to create a composite record from the log files generated by record. The following instructions assume that you have collected the log files in a directory named NNN, where NNN is record's `run number', and that you are running Linux (or Solaris, or SunOS); it is possible to do most of what is described below under MS-DOS or MS-Windows, with minor modifications (see the documentation available on PhysioNet, in particular the WFDB Applications Guide, for details).
- Determine the number of segments in each record:
cd NNN ls | tailThe output from `ls | tail' will look something like this:
NNN00122.hea NNN00122.txt NNN00123.al NNN00123.dat NNN00123.hea NNN00123.txt NNN00124.al NNN00124.dat NNN00124.hea NNN00124.txtNote the segment number of the last segment (124 in the example above). Use this number as shown in this command:
wfdbcollate NNN 1 124 -a alPay careful attention to any warnings or error messages that appear! In most cases, you will see a message of the form:
warning (init): record NNN00XXX duration differs from that of previously opened recordwhere XXX is the segment number of the last segment. This is harmless, and may be ignored. On the other hand, if dbcollate reports that the sampling frequency is incorrect for the last segment, delete the files for the last segment (`rm *124.*' in the example), and run dbcollate again (`dbcollate NNN 1 123 -a al' in this case). This problem may occur in some cases when the last segment could not be properly finished by record.
- Use wave to view the
wave -r NNN
- Locate the recorded calibration signals.
- Use wave's View panel to set the time scale to 125 mm/sec and the amplitude scale to 40 mm/mV; check `Markers' in the top row, and choose `attached to signals' from the `Show annotations' menu, then click on `Redraw'. Once you have found the calibration signals, enable annotation editing (using the `Edit' menu button), then place `N' labels (or other annotations of your choice) at matching points on the calibration pulses for each ECG signal (the pulses for the other signals can't be aligned, so ignore them). It's best to make more than one set of measurements. Now select `Analyze' from wave's `File' menu, and click on `List annotations'.
- Examine the output of `rdann' (it appears in the `Analysis
commands' window; click on `Show command window' if you don't
see it). It will appear something like this:
[08:12:02.784 01/12/1994] 2348 N 0 0 0 [08:12:02.784 01/12/1994] 2348 N 0 2 0 [08:12:02.848 01/12/1994] 2356 N 0 1 0 [08:12:03.712 01/12/1994] 2464 N 0 0 0 [08:12:03.712 01/12/1994] 2464 N 0 2 0 [08:12:03.776 01/12/1994] 2472 N 0 1 0Each row of output corresponds to a single annotation. The second column from the right indicates which signal each annotation is associated with (0, 1, or 2), and the column to the left of the N codes shows the exact time in samples of the annotation. In this example, there are two sets of annotations, and in each set, the signal 1 annotation occurs 8 samples later than those for signals 0 and 2. The units of skew for ECG signals are 1/4 of a sample interval; thus the skew for signal 1 is 32 (= 8 * 4). (By definition, the signal for which the calibration pulse is observed earliest has a skew of zero; this may not always be signal 0, however.) Because of the way the HP monitor transmits data, we can be quite certain that all skews will be multiples of 16; the largest skew I have observed is 64. In most cases, two signals are already synchronized and only the third has a non-zero skew, most often either 16 or 32 as in this example.
- Determine the skews for each ECG signal, then exit from wave and
run skewedit to correct for the measured skews. In this example,
this would be done by
skewedit NNN 0 32 0where NNN is the record name, and the arguments that follow it are the skews for signals 0, 1, and 2. When running skewedit, any trailing zeroes may be omitted from the argument list (thus `skewedit NNN 0 32' is equivalent to the command above). After running skewedit, open the record again using wave and verify that you have corrected the skew properly. (Note that skewedit always sets the absolute skew, so if you need to make further adjustments, add any corrections to the previous skews.)
- Reopen the record using wave and calibrate any signals that can be
calibrated. Locate the calibration signals. Set wave's signal list
so that it includes only those signals that are to be calibrated. Mark (with
`<' and '>' markers) a segment that contains both the
low-amplitude and the high-amplitude regions of the calibration signals. Click
on `Calibrate', and answer any questions that appear in the command
window. Reopen the record and check that the signals have been calibrated
properly. Repeat this step as necessary.
Note that the calibration signals for ECGs are 2 mV peak-to-peak, and that the most common calibration steps for the ABP signal are 0, 30, 60, 120, and 180 mmHg (there is at least one other ABP calibration signal with usable steps of 60 and 0 mmHg only).
- Clean up the directory in which you have been working:
rm -f NNN.wave* chmod 444 *
The first of these commands removes any annotation files you created while measuring and correcting for skew, and the last command sets all of the data files to read-only mode.
If you would like help understanding, using, or downloading content, please see our Frequently Asked Questions.
If you have any comments, feedback, or particular questions regarding this page, please send them to the webmaster.
Comments and issues can also be raised on PhysioNet's GitHub page.
Updated Friday, 10 July 2015 at 18:25 EEST