summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMartin Burnicki <martin.burnicki@meinberg.de>2017-04-25 12:00:00 +0200
committerMartin Burnicki <martin.burnicki@meinberg.de>2017-04-25 12:00:00 +0200
commit2e95ddd6c5bd57d495e4305d55efc0dc0f2ba658 (patch)
treee1832878d77573154d55e84ebf34a4015326a154
parent8f723519051654b6e765123ed90260fc25df0f79 (diff)
downloadmbgtools-fbsd-2e95ddd6c5bd57d495e4305d55efc0dc0f2ba658.tar.gz
mbgtools-fbsd-2e95ddd6c5bd57d495e4305d55efc0dc0f2ba658.zip
Update some files to current versionsmbgtools-fbsd-dev-2017-04-25
-rwxr-xr-xMakefile85
-rwxr-xr-xREADME143
-rwxr-xr-xmbgclock/Makefile37
-rwxr-xr-xmbgclock/mbgclock_main.c9
-rwxr-xr-xmbgctrl/Makefile21
-rwxr-xr-xmbgctrl/mbgctrl.c1150
-rwxr-xr-xmbgfasttstamp/Makefile13
-rwxr-xr-xmbgfasttstamp/mbgfasttstamp.c38
-rwxr-xr-xmbggpscap/Makefile15
-rwxr-xr-xmbggpscap/mbggpscap.c54
-rwxr-xr-xmbghrtime/Makefile13
-rwxr-xr-xmbghrtime/mbghrtime.c38
-rwxr-xr-xmbgirigcfg/Makefile14
-rwxr-xr-xmbgirigcfg/mbgirigcfg.c129
-rwxr-xr-xmbglib/bsd/pci_bsd.h2
-rwxr-xr-xmbglib/bsd/rsrc_bsd.c2
-rwxr-xr-xmbglib/bsd/rsrc_bsd.h2
-rwxr-xr-xmbglib/common/cfg_hlp.c1747
-rwxr-xr-xmbglib/common/cfg_hlp.h1480
-rwxr-xr-xmbglib/common/charcode.h275
-rwxr-xr-xmbglib/common/chk_time_info.c55
-rwxr-xr-xmbglib/common/chk_time_info.h5
-rwxr-xr-xmbglib/common/cmp_time_util.c287
-rwxr-xr-xmbglib/common/cmp_time_util.h87
-rwxr-xr-xmbglib/common/ctrydttm.c111
-rwxr-xr-xmbglib/common/ctrydttm.h24
-rwxr-xr-xmbglib/common/deviohlp.c1736
-rwxr-xr-xmbglib/common/deviohlp.h449
-rwxr-xr-xmbglib/common/gpsdefs.h18220
-rwxr-xr-xmbglib/common/gpsutils.c362
-rwxr-xr-xmbglib/common/gpsutils.h177
-rwxr-xr-xmbglib/common/lan_util.c1492
-rwxr-xr-xmbglib/common/lan_util.h616
-rwxr-xr-xmbglib/common/macioctl.h396
-rwxr-xr-xmbglib/common/mbg_arch.h42
-rwxr-xr-xmbglib/common/mbg_cof.h88
-rwxr-xr-xmbglib/common/mbg_daemonize.c231
-rwxr-xr-xmbglib/common/mbg_daemonize.h77
-rwxr-xr-xmbglib/common/mbg_pidfile.c334
-rwxr-xr-xmbglib/common/mbg_pidfile.h124
-rwxr-xr-xmbglib/common/mbg_tgt.h476
-rwxr-xr-xmbglib/common/mbgddmsg.h215
-rwxr-xr-xmbglib/common/mbgdevio.c6780
-rwxr-xr-xmbglib/common/mbgdevio.h5045
-rwxr-xr-xmbglib/common/mbgerror.c733
-rwxr-xr-xmbglib/common/mbgerror.h512
-rwxr-xr-xmbglib/common/mbggeo.h135
-rwxr-xr-xmbglib/common/mbgioctl.h400
-rwxr-xr-xmbglib/common/mbgklist.h304
-rwxr-xr-xmbglib/common/mbgmktm.c86
-rwxr-xr-xmbglib/common/mbgmktm.h28
-rwxr-xr-xmbglib/common/mbgmutex.h9
-rwxr-xr-xmbglib/common/mbgpccyc.h25
-rwxr-xr-xmbglib/common/mbgsystm.c60
-rwxr-xr-xmbglib/common/mbgsystm.h509
-rwxr-xr-xmbglib/common/mbgtime.h350
-rwxr-xr-xmbglib/common/mbgutil.c462
-rwxr-xr-xmbglib/common/mbgutil.h102
-rwxr-xr-xmbglib/common/myutil.h47
-rwxr-xr-xmbglib/common/ntp_shm.c14
-rwxr-xr-xmbglib/common/ntp_shm.h42
-rwxr-xr-xmbglib/common/parmgps.c242
-rwxr-xr-xmbglib/common/parmgps.h142
-rwxr-xr-xmbglib/common/parmpcps.c115
-rwxr-xr-xmbglib/common/parmpcps.h163
-rwxr-xr-xmbglib/common/pci_asic.h266
-rwxr-xr-xmbglib/common/pcidefs.h33
-rwxr-xr-xmbglib/common/pcpsdefs.h1999
-rwxr-xr-xmbglib/common/pcpsdev.h851
-rwxr-xr-xmbglib/common/pcpsdrvr.c1386
-rwxr-xr-xmbglib/common/pcpsdrvr.h235
-rwxr-xr-xmbglib/common/pcpslstr.c250
-rwxr-xr-xmbglib/common/pcpslstr.h310
-rwxr-xr-xmbglib/common/pcpsmktm.c30
-rwxr-xr-xmbglib/common/pcpsmktm.h38
-rwxr-xr-xmbglib/common/pcpsutil.c162
-rwxr-xr-xmbglib/common/pcpsutil.h101
-rwxr-xr-xmbglib/common/ptp_util.h190
-rwxr-xr-xmbglib/common/str_util.c449
-rwxr-xr-xmbglib/common/str_util.h269
-rwxr-xr-xmbglib/common/timeutil.c172
-rwxr-xr-xmbglib/common/timeutil.h136
-rwxr-xr-xmbglib/common/toolutil.c394
-rwxr-xr-xmbglib/common/toolutil.h62
-rwxr-xr-xmbglib/common/usbdefs.h351
-rwxr-xr-xmbglib/common/words.h371
-rwxr-xr-xmbglib/common/xdevfeat.c1556
-rwxr-xr-xmbglib/common/xdevfeat.h892
-rwxr-xr-xmbgsetsystime/Makefile27
-rwxr-xr-xmbgsetsystime/mbgsetsystime.c290
-rwxr-xr-xmbgshowsignal/Makefile13
-rwxr-xr-xmbgshowsignal/mbgshowsignal.c36
-rwxr-xr-xmbgstatus/Makefile25
-rwxr-xr-xmbgstatus/mbgstatus.c562
-rwxr-xr-xmbgsvcd/BSDmakefile34
-rwxr-xr-xmbgsvcd/Makefile39
-rwxr-xr-xmbgsvcd/mbgsvcd.c95
-rwxr-xr-xmbgversion.h8
-rwxr-xr-xmbgxhrtime/Makefile13
-rwxr-xr-xmbgxhrtime/mbgxhrtime.c36
100 files changed, 47194 insertions, 11663 deletions
diff --git a/Makefile b/Makefile
index 1d0c59c..6aef3ad 100755
--- a/Makefile
+++ b/Makefile
@@ -1,13 +1,21 @@
#########################################################################
#
-# $Id: Makefile 1.1.1.8 2011/11/24 11:25:00 martin TEST $
+# $Id: Makefile 1.1.1.13 2016/08/10 13:46:22 martin TEST $
#
# Description:
# Makefile for mbgtools which recurses into the subdirectories.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.1.1.13 2016/08/10 13:46:22 martin
+# *** empty log message ***
+# Revision 1.1.1.12 2016/08/10 11:31:37 martin
+# Support quiet build.
+# Revision 1.1.1.11 2014/04/23 14:56:46 martin
+# Revision 1.1.1.10 2014/02/05 11:44:48 martin
+# Revision 1.1.1.9 2013/07/23 11:08:31 martin
+# Link against libutil.
# Revision 1.1.1.8 2011/11/24 11:25:00 martin
# Revision 1.1.1.7 2011/07/06 13:25:06 martin
# Revision 1.1.1.6 2011/03/25 11:05:55 martin
@@ -23,6 +31,21 @@
#
#########################################################################
+V ?= 0 # set to 1 to build verbosely
+
+# The lines below make the build output non-verbose by default.
+# Call make with parameter "V=1" to get verbose output.
+.if $(V) != 0
+ Q :=
+ QM :=
+ vecho = @true
+.else
+ Q := @
+ QM := -s
+ vecho = @echo
+.endif
+
+
.ifndef prefix
prefix := /usr/local
.endif
@@ -156,17 +179,24 @@ SUBDIRS += mbggpscap
SUBDIRS += mbghrtime
SUBDIRS += mbgfasttstamp
# SUBDIRS += mbgxhrtime ## not yet tested
-SUBDIRS += test/mbgtestcalrec
-# SUBDIRS += test/mbgtestio
-# SUBDIRS += test/mbgtestmmio
-# SUBDIRS += test/mbgtestxhrt
-# SUBDIRS += test/mbgchksystime
+
+SUBDIRS += test/mbgchksystime
+## SUBDIRS += test/mbgclock-test
+SUBDIRS += test/mbgcmptime
+SUBDIRS += test/mbgreadtime
+SUBDIRS += test/mbgtcrcal
+##SUBDIRS += test/mbgtestcalrec
+SUBDIRS += test/mbgtestio
+SUBDIRS += test/mbgtestsettime
+SUBDIRS += test/mbg_ucap
+
SUBDIRS += mbgclock
.PHONY: all clean distclean install uninstall
all clean distclean install uninstall:
@for dir in $(SUBDIRS); do \
if test -f $$dir/Makefile; then \
+ echo "Making $@ in $$dir"; \
/bin/sh -c "cd $$dir; $(MAKE) $@"; \
fi \
done
@@ -175,6 +205,7 @@ all clean distclean install uninstall:
refclocks kernel_config
dev dev-nodes dev-clean suse_symvers probe ins rm test reload check \
refclocks kernel_config:
+ @echo "Making $(MAKECMDGOALS) in $@"
@cd mbgclock && make $@
.PHONY: cleanreload
@@ -216,7 +247,6 @@ make_as_root = $(call run_as_root, make $(1))
# not building a kernel module
CFLAGS += -Wall
-## CFLAGS += -W
.ifdef DEBUG
CFLAGS += -DDEBUG=$(DEBUG)
@@ -231,20 +261,14 @@ CFLAGS += -Wall
CFLAGS += -I.
CFLAGS += -I$(BASEDIR)
-CFLAGS += $(foreach dir,$(MBGLIB_DIRS),-I$(MBGLIB)/$(dir))
-#########
+# foreach doesn't seem to work under FreeBSD :-(
+# CFLAGS += $(foreach dir,$(MBGLIB_DIRS),-I$(MBGLIB)/$(dir))
CFLAGS += -I$(BASEDIR)/mbglib/common
CFLAGS += -I$(BASEDIR)/mbglib/bsd
-
-# Use all CFLAGS defined above also for C++ files.
-CXXFLAGS += $(CFLAGS)
-
-# Additional C++-only compiler flags.
-## CXXFLAGS += -Wno-deprecated
-
-
-LDFLAGS += $(foreach dir,$(SO_SUBDIRS),-L $(BASEDIR)/$(dir) )
+LDFLAGS += -lutil
+# foreach doesn't seem to work under FreeBSD :-(
+# LDFLAGS += $(foreach dir,$(SO_SUBDIRS),-L $(BASEDIR)/$(dir) )
SO_MAJOR_VERSION = 1
@@ -276,6 +300,7 @@ SO_MINOR_VERSION = 0
.endif
.endif
+CXXFLAGS = $(CFLAGS)
.PHONY: all
@@ -298,8 +323,8 @@ VPATH = $(BASEDIR)/mbglib/common:$(BASEDIR)/mbglib/bsd
# Check whether thread affinity is supported by the installed pthread library.
# Newer versions of glibc/pthread (at least glibc 2.5) supports this natively.
# Older versions of glibc/pthread (e.g. glibc 2.3) may not support this natively
- # but may provide a NPTL (New Posix Thread Library) library located under separate
- # include and lib paths. We try to detect NPTL and add those paths to the search
+ # but may provide a NPTL (New Posix Thread Library) library located under separate
+ # include and lib paths. We try to detect NPTL and add those paths to the search
# paths only if USE_NTPL has been defined e.g. on the make command line.
# Check whether pthread_getaffinity is supported by the standard pthread.h
@@ -355,12 +380,22 @@ VPATH = $(BASEDIR)/mbglib/common:$(BASEDIR)/mbglib/bsd
## $(warning $(INFO) EXTRA_CFLAGS=$(EXTRA_CFLAGS))
## $(warning $(INFO) MAKECMDGOALS = $(MAKECMDGOALS))
+
+.c.o:
+ $(vecho) " $(CC) ${.IMPSRC}"
+ $(Q)$(CC) $(CPPFLAGS) $(CFLAGS) -o ${.TARGET} -c ${.IMPSRC}
+
+
+
$(TARGET): $(OBJS)
- $(CC) -o $@ $(OBJS) $(LDFLAGS)
+ $(vecho) " Linking $@"
+ $(Q)$(CC) -o $@ $(OBJS) $(LDFLAGS)
.ifdef SO_TARGET_LIBNAME
ln -sf $(TARGET) $(SO_TARGET_LIBNAME)
.endif
+
+
.PHONY: install
install: $(EXT_INSTALL)
.ifdef XXX #.ifneq ($(UID),0)
@@ -429,8 +464,8 @@ gui_uninstall:
.ifdef XXX #.ifneq ($(UID),0)
$(call make_as_root, $@)
.else
- rm -rf $(DESTDIR)$(prefix)/share/$(TARGET)
- rm -f $(DESTDIR)$(prefix)/share/applications/$(TARGET).desktop
+ $(Q)rm -rf $(DESTDIR)$(prefix)/share/$(TARGET)
+ $(Q)rm -f $(DESTDIR)$(prefix)/share/applications/$(TARGET).desktop
.endif
CLEAN_FILES += *.o
@@ -441,10 +476,10 @@ CLEAN_FILES += $(TARGET)
.PHONY: clean
clean:
.ifdef CLEAN_FILES
- rm -f $(CLEAN_FILES)
+ $(Q)rm -f $(CLEAN_FILES)
.endif
.ifdef CLEAN_DIRS
- rm -rf $(CLEAN_DIRS)
+ $(Q)rm -rf $(CLEAN_DIRS)
.endif
diff --git a/README b/README
index be98f6d..23fcf0f 100755
--- a/README
+++ b/README
@@ -1,48 +1,8 @@
-$Id: README 1.1.1.2 2011/07/06 13:24:57 martin TEST $
+$Id: README 1.1.1.4 2017/04/25 19:53:10 martin TEST $
-This is the README file for mbgtools-fbsd-dev-2011-02-04
+This is the README file for mbgtools-fbsd-dev-2017-04-25
--------------------------------------------------------
-
------------------------------------------------------------------------------
-Oh, that's usually in /boot/loader.conf
-
-From the loader.conf(5) manual page:
-
- *_load If set to ``YES'', that module will be loaded. If no name
- is defined (see below), the module's name is taken to be
- the same as the prefix.
-
-
-So, mbgclock_load="YES" in /boot/loader.conf ought to work.
-
------------------------------------------------------------------------------
-
-
-/boot/loader.conf:
-mbgclock_load="YES"
-
-/etc/rc.conf:
-mbgsvcd_enable="YES"
-
-cat /boot/loader.conf | sed -e "s/[SUCHPATTERN]/[ERSETZEN]/g" > /boot/loader.new
-
-grep "mbgclock_load=" && IS_THERE=YES || IS_THERE=NO
-
-grep -v "mbgclock_load=" > /boot/loader.new
-
-
------------------------------------------------------------------------------
-
-copy mbgsvcd script to /etc/rc.d/
-
------------------------------------------------------------------------------
-
-
-
-
-
-
Please send comments and required modifications to
Meinberg support <support@meinberg.de>
@@ -61,42 +21,41 @@ Contents
1. Notes and description
------------------------
-This driver package has been implemented for FreeBSD 8.1
-on standard PCs (i386 architecture) and on Intel/AMD 64 bit
-systems (amd64 architecture).
-
-Unless the BSD kernel API calls have changed the driver should
-also work properly under earlier versions of FreeBSD. However,
-other target platforms than i386 and amd64 are not yet supported.
+The driver package supports all PCI card types manufactured by Meinberg
+which have been introduced up to the release date of this driver version.
-The driver supports all PCI cards manufactured by Meinberg which
-have been shipped up to the release date of this driver version.
+The driver should compile fine under FreeBSD 8.1 through 12, and eventually
+on older versions. Supported platforms are x86 and amd64.
-This version of the driver package should compile fine
-under FreeBSD 8.1 for kernels 2.6.x, .
+2. Driver files and programs
+----------------------------
+mbgtools for FreeBSD is based on Meinberg's common driver library mbglib
+and implements the following programs each of which can be found in
+its own subdirectory:
2. Driver files and programs
----------------------------
mbgtools for Linux is based on Meinberg's common driver library mbglib
and implements the following programs each of which can be found in
-its own subdirectory:
+its own subdirectory.
+
+Each of the user space programs can be run with parameter '-?' to show
+the supported parameters.
mbgclock.ko
A kernel module which implements the device driver.
-mbgstatus
- This program prints some status information for a device. The
- kind of information to be printed depends on the specific type
- of the card.
-
mbgsvcd
+ The Meinberg Service Daemon which needs to be started to feed the
+ timestamps from the device(s) to the NTP daemon's shared memory driver.
+
This program periodically calls the kernel driver to retrieve
time stamps of both the system time and the PCI card as close
as possible after each other, and feeds the time stamp pairs
- into a shared memory segment compatible with the NTP daemon ntpd.
- This enables ntpd to use up to 4 PCI card(s) as refererence time
+ into a shared memory segment compatible with the NTP daemon, ntpd.
+ This allows ntpd to use up to 4 PCI card(s) as refererence time
source, if configured accordingly.
Usually the program runs as daemon, but using the -f parameter
@@ -108,14 +67,17 @@ mbgsvcd
is actually disciplined, even if the system time is disciplined
by some other means.
+mbgstatus
+ This program prints some status information for a device. The
+ kind of information to be printed depends on the specific type
+ of the card. One or more parameters '-v' increase verbosity.
+
mbgctrl
This program can be used to do some basic configuration of a card.
- Run mbgctrl -? to get a list of valid options.
mbgirigcfg
This program can be used to check and configure IRIG settings of
cards which provide an IRIG input or output.
- Type "mbgirigcfg -h" for help.
mbgsetsystime
This program reads the time from a device and sets the system time.
@@ -124,15 +86,15 @@ mbgsetsystime
NTP daemon starts). The program should not be run if NTP is active
and controls the system time since NTP achieves a higher accuracy.
-mbgdcfmod
+mbgshowsignal
This program displays the modulation (i.e. the second marks) of a
- received longwave signal, e.g. from DCF77.
+ received longwave signal, e.g. from DCF77, if supported by the device.
mbggpscap
This example program reads time capture events from a card's time
- capture buffer. This works only with cards which provide time capture
- inputs, and the DIP switches on those cards must be set up properly
- to enable time capturing.
+ capture buffer. This works only with cards that provide time capture
+ inputs, and the DIP switches on those cards must have been set up
+ properly to enable time capturing.
mbghrtime
This example program checks whether a card supports high-resolution
@@ -141,8 +103,9 @@ mbghrtime
mbgfasttstamp
This examle program demonstrates how to read high resolution time stamps
from a card very much faster than mbghrtime. However, this works only
- with cards which support memory mapped I/O.
- As of this writing this applies to the GPS170PEX only.
+ with cards that support memory mapped I/O.
+ Current PCI Express cards support this feature, but older PCI cards may
+ not.
mbgxhrtime
This example program also shows how to get time stamps faster than
@@ -191,7 +154,7 @@ simply type
to compile the utility programs first, then the kernel module.
If *any* error or warning messages are displayed then please
-report to Meinberg.
+report to Meinberg <support@meinberg.de>.
@@ -233,7 +196,31 @@ used accordingly.
-4. Using the driver with NTP
+4. Making sure programs are loaded after boot
+---------------------------------------------
+
+First we need to make sure that the kernel module is loaded automatically
+at boot time.
+
+Edit or create the text file /boot/loader.conf and add the following line:
+
+mbgclock_load="YES"
+
+
+If ntpd is to use the PCI card as reference time source make sure
+the mbgsvcd daemon is started. Run the following command to copy
+the service control script to the appropriate directory:
+
+cp scripts/mbgsvcd /etc/rc.d/
+
+
+Then edit the text file /etc/rc.conf and add the following line:
+
+mbgsvcd_enable="YES"
+
+
+
+5. Using the driver with NTP
----------------------------
The NTP daemon can be configured to use up to 4 Meinberg PCI cards
as reference time source to discipline the system time. In order to
@@ -284,15 +271,3 @@ By default this installs the NTP binaries under /usr/local rather than /usr/sbin
so be sure the right instance of ntpd is started on reboot or when you run the
"service ntpd start" command.
------------------------------------------------------------------------------------
-Recompile ntpd with modified configuration (FreeBSD 5.3):
-
-root# cd /usr/ports/net/ntp/
-root# vi Makefile
-
-Add line:
- CONFIGURE_ARGS+= --enable-MEINBERG
-
-root# make install clean
-
-
diff --git a/mbgclock/Makefile b/mbgclock/Makefile
index e7362bc..6b441ec 100755
--- a/mbgclock/Makefile
+++ b/mbgclock/Makefile
@@ -1,7 +1,7 @@
#########################################################################
#
-# $Id: Makefile 1.1.1.6 2011/07/06 13:24:29 martin TEST $
+# $Id: Makefile 1.1.1.8 2016/08/10 11:32:05 martin TEST $
#
# Description:
# Makefile for mbgclock driver to support Meinberg bus level
@@ -9,6 +9,10 @@
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.1.1.8 2016/08/10 11:32:05 martin
+# *** empty log message ***
+# Revision 1.1.1.7 2015/09/18 14:52:59 martin
+# *** empty log message ***
# Revision 1.1.1.6 2011/07/06 13:24:29 martin
# Revision 1.1.1.5 2011/05/06 14:12:02 martin
# Revision 1.1.1.4 2011/02/03 14:10:39 martin
@@ -23,28 +27,31 @@
#
#########################################################################
-KMOD= mbgclock
+KMOD = mbgclock
-MBGLIB= ../mbglib
-MBGLIB_COMMON= $(MBGLIB)/common
-MBGLIB_BSD= $(MBGLIB)/bsd
+MBGLIB = ../mbglib
+MBGLIB_COMMON = $(MBGLIB)/common
+MBGLIB_BSD = $(MBGLIB)/bsd
.PATH: $(MBGLIB_COMMON) $(MBGLIB_BSD)
-CFLAGS= -I.. -I$(MBGLIB_COMMON) -I$(MBGLIB_BSD)
+CFLAGS += -I..
+CFLAGS += -I$(MBGLIB_COMMON)
+CFLAGS += -I$(MBGLIB_BSD)
+
.ifdef DEBUG
-CFLAGS+= -D DEBUG=$(DEBUG)
+ CFLAGS += -D DEBUG=$(DEBUG)
.endif
-SRCS= mbgclock_main.c
-SRCS+= pcpsdrvr.c
-SRCS+= identdec.c
-SRCS+= rsrc_bsd.c
-SRCS+= device_if.h bus_if.h pci_if.h
+SRCS = mbgclock_main.c
+SRCS += pcpsdrvr.c
+SRCS += identdec.c
+SRCS += rsrc_bsd.c
+SRCS += device_if.h bus_if.h pci_if.h
-CLEANFILES= *~
-CLEANFILES+= machine
-CLEANFILES+= @
+CLEANFILES = *~
+CLEANFILES += machine
+CLEANFILES += @
.include <bsd.kmod.mk>
diff --git a/mbgclock/mbgclock_main.c b/mbgclock/mbgclock_main.c
index 61d0bf4..b99da6c 100755
--- a/mbgclock/mbgclock_main.c
+++ b/mbgclock/mbgclock_main.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgclock_main.c 1.1.1.13 2011/11/01 09:08:33 martin TEST $
+ * $Id: mbgclock_main.c 1.1.1.14 2015/01/16 09:53:54 martin TEST $
*
* Description:
* Main file for for mbgclock driver to support Meinberg bus level
@@ -14,6 +14,9 @@
*
* -----------------------------------------------------------------------
* $Log: mbgclock_main.c $
+ * Revision 1.1.1.14 2015/01/16 09:53:54 martin
+ * Use "struct thread" instead of obsolete "d_thread_t" type.
+ * Reported by John Baldwin and George Neville-Neil (FreeBSD bug #196692).
* Revision 1.1.1.13 2011/11/01 09:08:33 martin
* Revision 1.1.1.12 2011/10/05 10:38:06 martin
* Unified handling of program version information.
@@ -135,7 +138,7 @@ void set_dev_connected( PCPS_DDEV *pddev, int state )
* attach routine when we create the /dev entry.
*/
int
-mbgclock_open( struct cdev *dev, int oflags, int devtype, d_thread_t *td )
+mbgclock_open( struct cdev *dev, int oflags, int devtype, struct thread *td )
{
struct mbgclock_softc *psc = dev->si_drv1;
PCPS_DDEV *pddev = psc->pddev;
@@ -152,7 +155,7 @@ mbgclock_open( struct cdev *dev, int oflags, int devtype, d_thread_t *td )
int
-mbgclock_close( struct cdev *dev, int fflag, int devtype, d_thread_t *td )
+mbgclock_close( struct cdev *dev, int fflag, int devtype, struct thread *td )
{
struct mbgclock_softc *psc = dev->si_drv1;
PCPS_DDEV *pddev = psc->pddev;
diff --git a/mbgctrl/Makefile b/mbgctrl/Makefile
index e26af30..1383cd1 100755
--- a/mbgctrl/Makefile
+++ b/mbgctrl/Makefile
@@ -1,13 +1,22 @@
#########################################################################
#
-# $Id: Makefile 1.7.1.3 2011/09/26 15:50:00 martin TEST $
+# $Id: Makefile 1.7.1.8 2016/07/15 14:06:51 martin TEST $
#
# Description:
# Makefile for mbgctrl.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.7.1.8 2016/07/15 14:06:51 martin
+# Added new module timeutil.o.
+# Revision 1.7.1.7 2015/10/27 15:07:37 martin
+# Removed obsolete object modules.
+# Revision 1.7.1.6 2015/08/31 14:22:53 martin
+# Revision 1.7.1.5 2015/07/14 15:07:19 martin
+# Added object module mbgerror.o.
+# Revision 1.7.1.4 2014/04/28 13:19:51 martin
+# Added module cfg_hlp.o.
# Revision 1.7.1.3 2011/09/26 15:50:00 martin
# Updated for use with latest base Makefile.
# Added modules devio_hlp and lan_util.
@@ -38,12 +47,14 @@ MBGDEVIO_SIMPLE = 0
OBJS = $(TARGET).o
OBJS += mbgdevio.o
-OBJS += deviohlp.o
+OBJS += mbgutil.o
+OBJS += timeutil.o
+OBJS += str_util.o
OBJS += toolutil.o
+OBJS += mbgerror.o
+OBJS += cfg_hlp.o
+OBJS += deviohlp.o
OBJS += gpsutils.o
-OBJS += pcpsutil.o
-OBJS += parmgps.o
-OBJS += parmpcps.o
OBJS += lan_util.o
BASEDIR := ..
diff --git a/mbgctrl/mbgctrl.c b/mbgctrl/mbgctrl.c
index 36c808b..b3930fd 100755
--- a/mbgctrl/mbgctrl.c
+++ b/mbgctrl/mbgctrl.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgctrl.c 1.22.1.14 2012/12/12 10:44:35 martin TEST $
+ * $Id: mbgctrl.c 1.22.1.14.1.4 2017/02/08 11:41:20 martin TEST $
*
* Description:
* Main file for mbgctrl program which sends commands and
@@ -9,6 +9,16 @@
*
* -----------------------------------------------------------------------
* $Log: mbgctrl.c $
+ * Revision 1.22.1.14.1.4 2017/02/08 11:41:20 martin
+ * Basic support for programmable pulse outputs, including pulse shift feature.
+ * Revision 1.22.1.14.1.3 2017/01/30 16:15:08 martin
+ * Enhanced PTP configuration.
+ * Fixed a bug where PTP unicast master configuration wasn't saved.
+ * Cleanup.
+ * Revision 1.22.1.14.1.2 2016/08/09 15:56:21 martin
+ * Account for modified library functions.
+ * Revision 1.22.1.14.1.1 2015/12/17 12:01:28 martin
+ * Fixed a compiler warning 'set but not used'.
* Revision 1.22.1.14 2012/12/12 10:44:35 martin
* Fixed wording of some message.
* Revision 1.22.1.13 2012/12/05 16:13:37 martin
@@ -114,14 +124,14 @@
#include <deviohlp.h>
#include <pcpsmktm.h>
#include <pcpsutil.h>
-#include <parmpcps.h>
-#include <parmgps.h>
+#include <cfg_hlp.h>
#include <myutil.h>
#include <gpsutils.h>
#include <cnv_wday.h>
#include <toolutil.h>
+#include <ptp_util.h>
#include <lan_util.h>
-//##+++++++++++++++++++++ #include <ptpdflts.h>
+#include <str_util.h>
// include system headers
#include <stdio.h>
@@ -141,7 +151,11 @@ static const char *pname = "mbgctrl";
static char *dev_name;
static int err_unicast_nsupp;
-static const char str_unknown[] = "(unknown)";
+
+static const char str_empty[] = "";
+static const char str_spc_not[] = " not";
+static const char str_spc_not_supp[] = " (not supported)";
+static const char str_spc_wildcard[] = " (wildcard)";
static TZDL tzdl_utc = DEFAULT_TZDL_UTC;
static TZDL tzdl_cet_cest = DEFAULT_TZDL_CET_CEST_EN;
@@ -153,10 +167,16 @@ static const char tz_info_cet_cest[] = TZ_INFO_CET_CEST_EN;
static const char tz_info_eet_eest[] = TZ_INFO_EET_EEST_EN;
static const char *mode_names[N_STR_MODE] = DEFAULT_ENG_MODE_NAMES;
-static const char *time_scale_name[N_MBG_TIME_SCALE] = MBG_TIME_SCALE_STRS;
+
+static const char *time_scale_names[N_MBG_TIME_SCALE] = MBG_TIME_SCALE_STRS;
#define _get_time_scale_name( _i ) \
- ( ( (_i) < N_MBG_TIME_SCALE ) ? time_scale_name[_i] : str_unknown )
+ ( ( (_i) < N_MBG_TIME_SCALE ) ? time_scale_names[_i] : str_unknown )
+
+static const char * const pout_mode_names_eng[N_POUT_MODES] = DEFAULT_ENG_POUT_NAMES;
+
+#define _get_pout_mode_name( _i ) \
+ ( ( (_i) < N_POUT_MODES ) ? pout_mode_names_eng[_i] : str_unknown )
static const char no_gps_cmd[] = "does not support GPS commands";
@@ -170,6 +190,94 @@ static const char no_ptp[] = "does not provide PTP";
static const char no_cab_len[] = "does not support antenna signal delay compensation";
+
+/**
+ * @brief A type used to pass print control flags to functions
+ *
+ * @see ::CTRL_FLAG_MASKS
+ */
+typedef int CTRL_FLAGS;
+
+
+/**
+ * @brief flag masks used with ::CTRL_FLAGS
+ *
+ * @see ::CTRL_FLAGS
+ */
+enum CTRL_FLAG_MASKS
+{
+ CTRL_PRINT_ALL = 0x01,
+ CTRL_PRINT_NEWLINES = 0x02,
+ CTRL_PRINT_IDX = 0x04,
+ CTRL_PRINT_ERR = 0x08,
+ CTRL_PRINT_PLUS = 0x10,
+ CTRL_NOT_SUPP = 0x20
+};
+
+
+struct OPT_HANDLER_SPEC_S;
+
+typedef int HELP_FNC( MBG_DEV_HANDLE, const PCPS_DEV *, const struct OPT_HANDLER_SPEC_S *, CTRL_FLAGS );
+typedef int SET_FNC( MBG_DEV_HANDLE, const char *, int );
+typedef int SHOW_FNC( MBG_DEV_HANDLE, const struct OPT_HANDLER_SPEC_S *, const PCPS_DEV *, const char * );
+
+typedef struct OPT_HANDLER_SPEC_S
+{
+ const char *cmd_name;
+ MBG_CHK_SUPP_FNC *chk_supp_fnc;
+ HELP_FNC *help_fnc;
+ SET_FNC *set_fnc;
+ SHOW_FNC *show_fnc;
+ const char *cmd_info;
+ const char *not_supp_msg;
+ uint32_t flags; ///< see ::OPT_FLAG_MASKS
+
+} OPT_HANDLER_SPEC;
+
+
+enum OPT_FLAG_BITS
+{
+ OPT_SUPP_CMD_IDX_BIT, ///< e.g. COM0=, COM1=, etc. vs. TZ=
+ N_OPT_FLAG_BITS
+};
+
+enum OPT_FLAG_MASKS
+{
+ OPT_SUPP_CMD_IDX = ( 1UL << OPT_SUPP_CMD_IDX_BIT ) ///< see ::OPT_SUPP_CMD_IDX_BIT
+};
+
+OPT_HANDLER_SPEC ohs_pout =
+{
+ "POUT", // cmd_name
+ NULL, // chk_supp_fnc
+ NULL, // help_fnc
+ NULL, // set_fnc
+ NULL, // show_fnc
+ NULL, // cmd_info
+ NULL, // not_supp_msg
+ OPT_SUPP_CMD_IDX // flags
+};
+
+
+
+typedef struct
+{
+ int indent_1;
+ int indent_2;
+ int indent_3;
+ int comm_col_x;
+} INDENTS;
+
+const INDENTS usage_indents = { 2, 4, 6, 30 };
+const INDENTS usage_indents_detailed = { 4, 6, 8, 30 };
+const INDENTS show_indents = { 2, 4, 0, 0 };
+
+
+#define SHOW_INDENT_1 " "
+#define SHOW_INDENT_2 " "
+
+
+
typedef struct
{
const char *name;
@@ -220,6 +328,7 @@ static const char *nw_prot_short[] = PTP_NW_PROT_STRS_SHORT;
static const char *ptp_roles[] = PTP_ROLE_STRS;
static const char *ptp_roles_short[] = PTP_ROLE_STRS_SHORT;
+static const PTP_CLOCK_ID clock_id_wildcard = PTP_CLOCK_ID_WILDCARD;
//##+++++++++++++++++++
// If unicast is not supported for a PTP device then the device is definitely
@@ -231,6 +340,194 @@ static const char *ptp_roles_short[] = PTP_ROLE_STRS_SHORT;
( ( (_i) < N_PTP_ROLES ) ? ptp_roles_short[_i] : str_unknown )
+static const char pout_name_mode[] = "MODE";
+static const char pout_name_len[] = "LEN";
+static const char pout_name_inv[] = "INV";
+static const char pout_name_ois[] = "OIS";
+static const char pout_name_shift[] = "SHIFT";
+
+
+
+
+
+static /*HDR*/
+__attribute__( ( format( printf, 4, 5 ) ) )
+int usage_line( const INDENTS *p_ind, const OPT_HANDLER_SPEC *p_opt,
+ const char *cmd_parm, const char *cmd_comment_fmt, ... )
+{
+ int n = 0;
+
+ // print left margin, if not 0
+ if ( p_ind->indent_1 )
+ n += printf( "%*s", p_ind->indent_1, str_empty );
+
+ // print command name
+ if ( p_opt )
+ n += printf( "%s", p_opt->cmd_name );
+
+ // print the command parameters, if specified
+ if ( cmd_parm )
+ {
+ if ( p_opt && ( p_opt->flags & OPT_SUPP_CMD_IDX ) )
+ n+= printf( "%s", "<n>" );
+
+ n += printf( "=%s", cmd_parm );
+ }
+
+ // print command comment which can be a format string
+ // expecting additional parameters
+ if ( cmd_comment_fmt )
+ {
+ va_list arg_list;
+
+ // indent the comment string
+ if ( p_ind->indent_2 )
+ {
+ int w = p_ind->indent_2 - n;
+
+ while ( w < 0 )
+ w += 8;
+
+ n += printf( "%*s", w, str_empty );
+ }
+
+ va_start( arg_list, cmd_comment_fmt );
+ n += vprintf( cmd_comment_fmt, arg_list );
+ va_end( arg_list );
+ }
+
+ n += printf( "\n" );
+
+ return n;
+
+} // usage_line
+
+
+
+static /*HDR*/
+int print_indent( int i )
+{
+ int n = printf( "%*s", i, str_empty );
+
+ return n;
+
+} // print_indent
+
+
+
+static /*HDR*/
+__attribute__( ( format( printf, 2, 3 ) ) )
+int usage_note( int indent, const char *fmt, ... )
+{
+ // print left margin, if not 0
+ int n = print_indent( indent );
+
+ if ( fmt )
+ {
+ va_list arg_list;
+
+ va_start( arg_list, fmt );
+ n += vprintf( fmt, arg_list );
+ n += printf( "\n" );
+ va_end( arg_list );
+ }
+
+ return n;
+
+} // usage_note
+
+
+
+typedef const char *(STR_FNC)( int idx );
+
+
+static /*HDR*/
+void print_bit_mask_list( const char *info_1, const char *info_2, uint32_t supp_mask,
+ int n_known, const char * const names[], STR_FNC *s_fnc,
+ int inst_idx, CTRL_FLAGS ctrl_flags, const INDENTS *p_ind )
+{
+ const char *str_s_fnc = s_fnc ? s_fnc( inst_idx ) : str_empty;
+
+ print_indent( p_ind->indent_2 );
+
+ if ( ctrl_flags & CTRL_PRINT_ALL )
+ {
+ supp_mask = ( 1UL << n_known ) - 1;
+
+ if ( supp_mask )
+ printf( "Known %s%s: ", info_1, str_s_fnc );
+ else
+ printf( "No %s%s known.", info_1, str_s_fnc );
+ }
+ else
+ {
+ if ( supp_mask )
+ {
+ printf( "%s", info_1 );
+
+ if ( info_2 )
+ printf( " %s", info_2 );
+
+ #if defined( DEBUG )
+ printf( " (%04lX)", (ulong) supp_mask );
+ #endif
+
+ printf( ":" );
+ }
+ else
+ {
+ printf( "No %s.", info_1 );
+
+ if ( info_2 )
+ printf( " %s", info_2 );
+
+ printf( "." );
+ }
+ }
+
+
+ if ( supp_mask )
+ {
+ int n_printed = 0;
+ int i;
+ const char *str_sep = ( ctrl_flags & CTRL_PRINT_PLUS ) ? "+" : ", ";
+
+ for ( i = 0; i < n_known; i++ )
+ {
+ const char *cp;
+
+ if ( ( supp_mask & ( 1UL << i ) ) == 0 )
+ continue;
+
+ if ( names )
+ cp = names[i];
+ else
+ if ( s_fnc )
+ cp = s_fnc( i );
+ else
+ cp = str_empty;
+
+ if ( ctrl_flags & ( CTRL_PRINT_NEWLINES | CTRL_PRINT_IDX ) )
+ {
+ printf( "\n" );
+ print_indent( p_ind->indent_3 );
+
+ if ( ctrl_flags & CTRL_PRINT_IDX )
+ printf( "%i: ", i );
+
+ printf( "%s", cp );
+ }
+ else
+ printf( "%s%s", n_printed ? str_sep : str_empty, cp );
+
+ n_printed++;
+ }
+ }
+
+ printf( "\n" );
+
+} // print_bit_mask_list
+
static /*HDR*/
@@ -401,9 +698,33 @@ int show_lan_intf( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, const char *info )
static /*HDR*/
+const char *intv_str( int i )
+{
+ static char s[20];
+
+ int abs_i = abs( i );
+ ulong ul;
+
+ // Currently the valid range is [-7:+7]
+ if ( abs_i > 7 )
+ return str_empty;
+
+ ul = 1UL << abs_i;
+
+ snprintf_safe( s, sizeof( s ), " (%s%lu s)", ( i < 0 ) ? "1/" : str_empty, ul );
+
+ return s;
+
+} // intv_str
+
+
+
+static /*HDR*/
int show_ptp_cfg( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, const char *info )
{
ALL_PTP_CFG_INFO all_ptp_cfg_info;
+ PTP_CFG_INFO *pi = &all_ptp_cfg_info.ptp_cfg_info;
+ PTP_CFG_SETTINGS *ps = &pi->settings;
char ws[256];
int unicast_supported;
int idx;
@@ -413,19 +734,23 @@ int show_ptp_cfg( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, const char *info )
if ( mbg_ioctl_err( rc, "mbg_get_all_ptp_cfg_info" ) )
return rc;
- unicast_supported = ( all_ptp_cfg_info.ptp_cfg_info.supp_flags & PTP_CFG_MSK_SUPPORT_PTP_UNICAST ) != 0;
+ unicast_supported = ( pi->supp_flags & PTP_CFG_MSK_SUPPORT_PTP_UNICAST ) != 0;
printf( "\nPTP configuration:\n");
- idx = all_ptp_cfg_info.ptp_cfg_info.settings.ptp_role;
+ idx = ps->ptp_role;
printf( " PTP Role : %s (%s)\n", _ptp_role_name_short( idx ), _ptp_role_name( idx ) );
- idx = all_ptp_cfg_info.ptp_cfg_info.settings.nw_prot;
+ idx = ps->nw_prot;
printf( " Network Protocol: %s (%s)\n", nw_prot_short[idx], nw_prot[idx] );
- printf( " Delay Mechanism : %s\n", delay_mech[all_ptp_cfg_info.ptp_cfg_info.settings.delay_mech] );
- printf( " Domain Number : %d\n", all_ptp_cfg_info.ptp_cfg_info.settings.domain_number );
- printf( " V1 HW Compat. : %d\n", ( all_ptp_cfg_info.ptp_cfg_info.settings.flags & PTP_CFG_MSK_V1_HW_COMPAT ) ? 1 : 0 );
+ printf( " Delay Mechanism : %s\n", delay_mech[ps->delay_mech] );
+ printf( " Domain Number : %d\n", ps->domain_number );
+ printf( " V1 HW Compat. : %d\n", ( ps->flags & PTP_CFG_MSK_V1_HW_COMPAT ) ? 1 : 0 );
+
+ printf( " Sync Msg Intv. : % i%s\n", ps->sync_intv, intv_str( ps->sync_intv) );
+ printf( " Ann. Msg Intv. : % i%s\n", ps->ann_intv, intv_str( ps->ann_intv ) );
+ printf( " Dly. Req. Intv. : % i%s\n", ps->delay_req_intv, intv_str( ps->delay_req_intv ) );
if ( unicast_supported )
{
@@ -436,25 +761,31 @@ int show_ptp_cfg( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, const char *info )
{
PTP_UC_MASTER_SETTINGS *p = &all_ptp_cfg_info.all_ptp_uc_master_info_idx[i].info.settings;
- printf( "\nPTP unicast master" );
+ printf( "\nConfigured PTP unicast master" );
if ( p_uc_limits->n_supp_master > 1 )
printf( " %i", i );
+ if ( ps->ptp_role == PTP_ROLE_MULTICAST_SLAVE )
+ printf( " (not used for this role)" );
+
printf( ":\n");
printf( " GM Host: %s\n", p->gm_host );
snprint_octets( ws, sizeof( ws ), p->gm_clock_id.b, sizeof( p->gm_clock_id.b ), MAC_SEP_CHAR, NULL );
- printf( " GM Clock ID: %s\n", ws );
+ printf( " GM Clock ID: %s%s\n", ws,
+ ( memcmp( &p->gm_clock_id, &clock_id_wildcard, sizeof( p->gm_clock_id ) ) == 0 ) ?
+ str_spc_wildcard : str_empty );
- printf( " GM Port ID: %d\n\n", p->gm_port_id );
- printf( " Sync Msg Interval [2^x s]: %i\n", p->sync_intv );
- printf( " Ann. Msg Interval [2^x s]: %i\n", p->ann_intv );
- printf( " DelReq Msg Interval [2^x s]: %i\n", p->delay_req_intv );
- printf( " Message Duration: %i s\n", p->message_duration );
- }
+ printf( " GM Port ID: %d%s\n", p->gm_port_id,
+ ( p->gm_port_id == PTP_PORT_ID_WILDCARD ) ? str_spc_wildcard : str_empty );
+ printf( " Sync Msg Intv. : % i%s\n", p->sync_intv, intv_str( p->sync_intv ) );
+ printf( " Ann. Msg Intv. : % i%s\n", p->ann_intv, intv_str( p->ann_intv ) );
+ printf( " Dly. Req. Intv. : % i%s\n", p->delay_req_intv, intv_str( p->delay_req_intv ) );
+ printf( " Message Duration: %i s\n", p->message_duration );
+ }
}
return MBG_SUCCESS;
@@ -638,7 +969,7 @@ int chk_int16_parm( const char *arg, const char *id, int16_t *p, int16_t range_m
static /*HDR*/
int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
{
- ALL_PTP_CFG_INFO all_ptp_cfg_info;
+ ALL_PTP_CFG_INFO all_ptp_cfg_info = { { { 0 } } };
ALL_PTP_CFG_INFO prv_all_ptp_cfg_info;
PTP_CFG_INFO *p_info;
PTP_CFG_SETTINGS *p_settings;
@@ -652,8 +983,7 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
int idx;
int unicast_supported;
int uc_master_idx = 0;
- int16_t tmp_int16;
-
+ const char *err_info = NULL;
int rc = mbg_get_all_ptp_cfg_info( dh, &all_ptp_cfg_info );
if ( rc < 0 )
@@ -670,7 +1000,7 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
unicast_supported = ( p_info->supp_flags & PTP_CFG_MSK_SUPPORT_PTP_UNICAST ) != 0;
p_uc_limits = &all_ptp_cfg_info.ptp_uc_master_cfg_limits;
- // The pointers below need to be updated wnenever uc_master_idx is changed
+ // The pointers below need to be updated whenever uc_master_idx is changed
p_uc_info = &all_ptp_cfg_info.all_ptp_uc_master_info_idx[uc_master_idx].info;
p_uc_settings = &p_uc_info->settings;
@@ -682,8 +1012,10 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
p_settings->nw_prot = idx;
else
if ( idx < -1 )
+ {
+ err_info = ptp_name_net;
goto fail;
-
+ }
// Delay Mechanism
idx = chk_tbl_parm( arg, ptp_name_del, delay_mech, N_PTP_DELAY_MECH, p_info->supp_delay_mech, "delay mechanism" );
@@ -692,19 +1024,25 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
p_settings->delay_mech = idx;
else
if ( idx < -1 )
+ {
+ err_info = ptp_name_del;
goto fail;
+ }
// Domain Number
idx = chk_parm_name( arg, ptp_name_dom, &cp );
if ( idx < 0 ) // parameter error
+ {
+ err_info = ptp_name_dom;
goto fail;
+ }
if ( cp ) // parameter found
{
idx = atoi( cp );
- //##+++++ must check range!!
+ // TODO Must check range!!
p_settings->domain_number = idx;
}
@@ -713,7 +1051,10 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
idx = chk_parm_name( arg, ptp_name_v1, &cp );
if ( idx < 0 ) // parameter error
+ {
+ err_info = ptp_name_v1;
goto fail;
+ }
if ( cp ) // parameter found
{
@@ -739,7 +1080,7 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
//---- unicast stuff ----
// PTP role
- supp_mask = _get_supp_ptp_role_idx_msk( p_info->supp_flags );
+ supp_mask = get_supp_ptp_role_mask( p_info->supp_flags );
idx = chk_tbl_parm( arg, ptp_name_role, ptp_roles_short, N_PTP_ROLES, supp_mask, "PTP role" );
if ( idx >= 0 ) // valid parameter found
@@ -751,14 +1092,20 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
}
else
if ( idx < -1 ) // parameter error
+ {
+ err_info = ptp_name_role;
goto fail;
+ }
// GM Host
idx = chk_parm_name( arg, ptp_name_gmip, &cp );
if ( idx < 0 ) // parameter error
+ {
+ err_info = ptp_name_gmip;
goto fail;
+ }
if ( cp ) // parameter found
{
@@ -768,7 +1115,7 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
{
// currently IP addresses are accepted only, so check for
// a valid IPv4 address
- if ( str_to_ip4_addr( &ip4addr, cp ) )
+ if ( str_to_ip4_addr( &ip4addr, cp ) > 0 )
{
snprint_ip4_addr( ws, sizeof( ws ), &ip4addr, NULL );
printf( " GM IP Address: %s\n", ws );
@@ -777,7 +1124,10 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
strcpy( p_uc_settings->gm_host, ws );
}
else
+ {
+ err_info = ptp_name_gmip;
goto fail;
+ }
}
}
@@ -786,7 +1136,10 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
idx = chk_parm_name( arg, ptp_name_gmid, &cp );
if ( idx < 0 ) // parameter error
+ {
+ err_info = ptp_name_gmid;
goto fail;
+ }
if ( cp ) // parameter found
{
@@ -795,21 +1148,27 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
else
{
PTP_CLOCK_ID gm_clock_id;
- idx = str_to_octets( gm_clock_id.b, sizeof( gm_clock_id.b ), cp );
+
+ // Check if specified GM ID is wildcard.
+ if ( *cp == '*' ) // TODO check if next char is separator
+ {
+ gm_clock_id = clock_id_wildcard;
+ idx = sizeof( gm_clock_id );
+ }
+ else
+ idx = str_to_octets( gm_clock_id.b, sizeof( gm_clock_id.b ), cp );
if ( idx != sizeof( gm_clock_id ) )
{
printf( "Syntax error in specified GM clock ID\n" );
goto fail;
}
- else
- {
- p_uc_settings->gm_clock_id = gm_clock_id;
- snprint_octets( ws, sizeof( ws ), p_uc_settings->gm_clock_id.b,
- sizeof( p_uc_settings->gm_clock_id.b ), MAC_SEP_CHAR, NULL );
- printf( " setting GM Clock ID: %s\n", ws );
- }
+ p_uc_settings->gm_clock_id = gm_clock_id;
+
+ snprint_octets( ws, sizeof( ws ), p_uc_settings->gm_clock_id.b,
+ sizeof( p_uc_settings->gm_clock_id.b ), MAC_SEP_CHAR, NULL );
+ printf( " setting GM Clock ID: %s\n", ws );
}
}
@@ -818,7 +1177,10 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
idx = chk_parm_name( arg, ptp_name_pid, &cp );
if ( idx < 0 ) // parameter error
+ {
+ err_info = ptp_name_pid;
goto fail;
+ }
if ( cp ) // parameter found
{
@@ -826,75 +1188,87 @@ int set_ptp_cfg( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
err_unicast_nsupp = 1;
else
{
- p_uc_settings->gm_port_id = strtoul( cp, NULL, 0 );
- printf( " setting GM port id: %d\n", p_uc_settings->gm_port_id );
+ // Check if specified Port ID is wildcard.
+ if ( *cp == '*' ) // TODO check if next char is separator
+ p_uc_settings->gm_port_id = PTP_PORT_ID_WILDCARD;
+ else
+ p_uc_settings->gm_port_id = (PTP_PORT_ID) strtoul( cp, NULL, 0 );
+
+ printf( " setting GM port id: %d%s\n", p_uc_settings->gm_port_id,
+ ( p_uc_settings->gm_port_id == PTP_PORT_ID_WILDCARD ) ? str_spc_wildcard : str_empty );
}
}
// Sync Message Rate
- idx = chk_int16_parm( arg, ptp_name_smi, &p_uc_settings->sync_intv,
+ idx = chk_int16_parm( arg, ptp_name_smi,
+ ( p_settings->ptp_role == PTP_ROLE_MULTICAST_SLAVE ) ?
+ &p_settings->sync_intv : &p_uc_settings->sync_intv,
p_uc_limits->sync_intv_min, p_uc_limits->sync_intv_max,
- unicast_supported, "sync intv." );
+ 1, "sync intv." );
if ( idx < 0 )
+ {
+ err_info = ptp_name_smi;
goto fail;
+ }
// Announce Message Rate
- idx = chk_int16_parm( arg, ptp_name_ami, &p_uc_settings->ann_intv,
+ idx = chk_int16_parm( arg, ptp_name_ami,
+ ( p_settings->ptp_role == PTP_ROLE_MULTICAST_SLAVE ) ?
+ &p_settings->ann_intv : &p_uc_settings->ann_intv,
p_uc_limits->ann_intv_min, p_uc_limits->ann_intv_max,
- unicast_supported, "ann. intv." );
+ 1, "ann. intv." );
if ( idx < 0 )
+ {
+ err_info = ptp_name_ami;
goto fail;
+ }
- // Delay Message Rate
- idx = chk_int16_parm( arg, ptp_name_dri, &p_uc_settings->delay_req_intv,
+ // Delay Request Interval Rate
+ idx = chk_int16_parm( arg, ptp_name_dri,
+ ( p_settings->ptp_role == PTP_ROLE_MULTICAST_SLAVE ) ?
+ &p_settings->delay_req_intv : &p_uc_settings->delay_req_intv,
p_uc_limits->delay_req_intv_min, p_uc_limits->delay_req_intv_max,
- unicast_supported, "delay req. intv." );
+ 1, "delay req. intv." );
if ( idx < 0 )
+ {
+ err_info = ptp_name_dri;
goto fail;
+ }
- // Message Duration //##++++ TODO: should this be added to the structure
- tmp_int16 = p_uc_settings->message_duration;
- idx = chk_int16_parm( arg, ptp_name_dur, &tmp_int16,
+
+ // Message Duration
+ idx = chk_int16_parm( arg, ptp_name_dur, (int16_t *) &p_uc_settings->message_duration,
PTP_UC_MSG_DURATION_MIN, PTP_UC_MSG_DURATION_MAX,
unicast_supported, "msg. duration" );
if ( idx < 0 )
+ {
+ err_info = ptp_name_dur;
goto fail;
-
- p_uc_settings->message_duration = tmp_int16;
-
-#if 0 //##++++++++++++
-
- cp = strstr( arg, ptp_name_dur );
-
- if ( cp != NULL )
- {
- l = strlen( ptp_name_dur );
-
- if ( *(cp+l) != ':' )
- goto fail; // parameter syntax error: name not followed by colon
-
- l++;
-
- ptp_unicast_settings.message_duration = atoi( cp+l );
- printf( " setting message duration: %i seconds\n", ptp_unicast_settings.message_duration );
- }
-#endif
+ }
- rc = mbg_set_ptp_cfg_settings( dh, p_settings );
+ if ( memcmp( &all_ptp_cfg_info, &prv_all_ptp_cfg_info, sizeof( all_ptp_cfg_info ) ) != 0 )
+ {
+ rc = mbg_save_all_ptp_cfg_info( dh, &all_ptp_cfg_info );
- if ( mbg_ioctl_err( rc, "mbg_set_ptp_cfg_settings" ) )
- return rc;
+ if ( mbg_ioctl_err( rc, "mbg_save_all_ptp_cfg_info" ) )
+ return rc;
+ }
return MBG_SUCCESS;
fail:
- printf( "Syntax error in argument!\n" );
+ printf( "Invalid parameter in argument" );
+
+ if ( err_info )
+ printf( " %s", err_info );
+
+ printf( "!\n" );
return MBG_ERR_CFG;
@@ -1254,26 +1628,34 @@ int set_date_time( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev,
static /*HDR*/
-void check_setup_receiver_info( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev,
- RECEIVER_INFO *p_ri )
+int check_setup_receiver_info( MBG_DEV_HANDLE dh, RECEIVER_INFO *p_ri )
{
+ int rc = MBG_SUCCESS;
+
// Set up the RECEIVER_INFO structure only if this has not been done
// before. Check the ticks_per_sec field to see if the structure
// has already been set up or not.
- if ( p_ri->ticks_per_sec == 0 )
- mbg_setup_receiver_info( dh, p_dev, p_ri );
+ if ( p_ri->ticks_per_sec == 0 && p_ri->model_code == 0 )
+ {
+ rc = mbg_setup_receiver_info( dh, NULL, p_ri );
+ mbg_ioctl_err( rc, "mbg_setup_receiver_info" );
+ }
+
+ return rc;
} // check_setup_receiver_info
static /*HDR*/
+// returns a negative error code on failure, or the number of supported COM ports on success
int check_get_receiver_port_cfg( MBG_DEV_HANDLE dh, RECEIVER_PORT_CFG *p_rpcfg,
const PCPS_DEV *p_dev, RECEIVER_INFO *p_ri )
{
- int rc = MBG_SUCCESS;
+ int rc = check_setup_receiver_info( dh, p_ri );
- check_setup_receiver_info( dh, p_dev, p_ri );
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
// Set up the RECEIVER_PORT_CFG structure only if this has not been done
// before. Check whether the number of ports is > 0 and the first port's
@@ -1282,10 +1664,13 @@ int check_get_receiver_port_cfg( MBG_DEV_HANDLE dh, RECEIVER_PORT_CFG *p_rpcfg,
( p_rpcfg->pii[0].port_info.port_settings.parm.baud_rate == 0 ) )
{
rc = mbg_get_serial_settings( dh, p_dev, p_rpcfg, p_ri );
-
mbg_ioctl_err( rc, "mbg_get_serial_settings" );
}
+ if ( mbg_rc_is_success( rc ) )
+ rc = p_ri->n_com_ports;
+
+out:
return rc;
} // check_get_receiver_port_cfg
@@ -1442,7 +1827,7 @@ int save_serial_settings( MBG_DEV_HANDLE dh, unsigned int port_num, const char *
ul = strtoul( cp, &p_tail, 10 );
if ( p_tail != cp )
- p_ps->str_type = ul;
+ p_ps->str_type = (uint8_t) ul; // TODO check range ?
cp = p_tail;
@@ -1455,7 +1840,7 @@ int save_serial_settings( MBG_DEV_HANDLE dh, unsigned int port_num, const char *
ul = strtoul( cp, &p_tail, 10 );
if ( p_tail != cp )
- p_ps->mode = ul;
+ p_ps->mode = (uint8_t) ul; // TODO check range ?
done_parm_str:
@@ -1491,6 +1876,479 @@ invalid:
static /*HDR*/
+// returns a negative error code on failure, or the number of supported programmable pulse outputs on success
+int check_get_pout_cfg( MBG_DEV_HANDLE dh, ALL_POUT_INFO_IDX api, RECEIVER_INFO *p_ri )
+{
+ int rc = check_setup_receiver_info( dh, p_ri );
+
+ // Set up the ALL_POUT_INFO_IDX structure only if this has not been done
+ // before. Check whether the number of ports is > 0 and the first port's
+ // baud rate is still 0 to see if the structure has already been set up.
+ if ( ( p_ri->n_prg_out > 0 ) &&
+ ( api[0].pout_info.supp_modes == 0 ) )
+ {
+ rc = mbg_get_gps_all_pout_info( dh, api, p_ri );
+ mbg_ioctl_err( rc, "mbg_get_gps_all_pout_info" );
+ }
+
+ if ( mbg_rc_is_success( rc ) )
+ rc = p_ri->n_prg_out;
+
+ return rc;
+
+} // check_get_pout_cfg
+
+
+
+static /*HDR*/
+int help_pout_arg( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev,
+ const OPT_HANDLER_SPEC *p_opt, CTRL_FLAGS ctrl_flags )
+{
+ const INDENTS *p_ind = &usage_indents;
+ const INDENTS *p_ind_detailed = &usage_indents_detailed;
+ int rc = MBG_SUCCESS;
+ int i;
+
+ usage_line( p_ind, p_opt, NULL, "Show settings of the programmable output(s)" );
+ usage_line( p_ind, p_opt, "MODE:<m>[,LEN:<l>][,INV:<i>][,OIS:<o>][,SHIFT:<s>]", "Configure programmable output <n>" ); // ### TODO
+
+ printf( "\n"
+ " where:\n" );
+
+ printf( " MODE:<m> Specifies the programmable output mode with index <m>, see mbgctrl -?.\n"
+ " Please note that subsequent parameters may only be appropriate for specific modes.\n\n" );
+
+ printf( " LEN:<l> Specifies the pulse lenght for modes that support this.\n"
+ " <l> is an integer value in 10 ms units, i.e. <l> = 20 yields 200 ms.\n\n" );
+
+ printf( " INV:<i> \"Inverted\" flag specifying if the output level is to be inverted,\n"
+ " if the output supports this.\n"
+ " Values for <i>: 1 invert output level, 0 don't invert.\n\n" );
+
+ printf( " OIS:<o> \"Only If Sync\" flag specifying if the output is to be enabled ONLY\n"
+ " while the device is synchronized, if the output supports this.\n"
+ " Values for <o>: 1 enable this feature, 0 disable this feature\n"
+ " NOTE: This overrides the Enable Flags settings (parameter \"EF\").\n"
+ " The output is enabled ONLY when the device state changes to \"synchronized\"\n"
+ " after power-up, and is disabled again when the device enters holdover mode,\n"
+ " i.e. the reference signal is lost.\n\n" );
+
+ printf( " SHIFT:<s> Specifies a phase shift of the output slope, if the output supports this.\n"
+ " <s> is an integer value, in nanoseconds.\n"
+ " The maximum range is %+li to %+li ns,\n"
+ " corresponding to %+li to %+li ms.\n"
+ " The effective resolution depends on the resolution of the device's internal clock,\n"
+ " which may be e.g. 10 or 20 ns, depending on the device type. See mbgctrl -?.\n\n",
+ (long) DEFAULT_POUT_PULSE_SHIFT_MIN, (long) DEFAULT_POUT_PULSE_SHIFT_MAX,
+ (long) DEFAULT_POUT_PULSE_SHIFT_MIN / 1000L, (long) DEFAULT_POUT_PULSE_SHIFT_MAX / 1000L );
+
+
+ if ( dh != MBG_INVALID_DEV_HANDLE )
+ {
+ RECEIVER_INFO ri = { 0 };
+ ALL_POUT_INFO_IDX api = { { 0 } };
+ int n_pout;
+
+ rc = check_get_pout_cfg( dh, api, &ri );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ n_pout = rc;
+
+ for ( i = 0; i < n_pout; i++ )
+ {
+ const POUT_INFO *pi = &api[i].pout_info;
+
+ printf( "%*s", p_ind->indent_2, str_empty );
+ printf( "Programmable output %i:\n", i );
+
+ print_bit_mask_list( "Supported modes", NULL, pi->supp_modes,
+ N_POUT_MODES, pout_mode_names_eng, NULL, 0,
+ ctrl_flags | CTRL_PRINT_IDX, p_ind_detailed );
+
+ // ### TODO evaluate more properties
+ usage_note( p_ind_detailed->indent_2, "Output level can%s be inverted.",
+ ( pi->flags & POUT_NOT_INVERTIBLE ) ? str_spc_not : str_empty );
+
+ if ( pi->flags & POUT_FIXED_PULSE_LEN )
+ usage_note( p_ind_detailed->indent_2, "Pulse length is fixed and can't be changed." );
+
+ if ( pi->flags & POUT_SUPP_PULSE_SHIFT )
+ usage_note( p_ind_detailed->indent_2, "Output supports pulse shift with resolution %u ns.",
+ pi->pulse_shift_res );
+
+ printf( "\n" );
+ }
+ }
+ else
+ {
+#if 0 // ### TODO
+ print_bit_mask_list( "modes", str_supp_by_dev, tsi.supp_scales,
+ N_MBG_TIME_SCALE, time_scale_names, NULL, ctrl_flags | CTRL_PRINT_IDX );
+#endif
+ }
+
+out:
+ return rc;
+
+} // help_pout_arg
+
+
+
+static /*HDR*/
+int eval_pout( MBG_DEV_HANDLE dh, const char *s, int inst_num )
+{
+ RECEIVER_INFO ri = { 0 };
+ ALL_POUT_INFO_IDX api = { { 0 } };
+ ALL_POUT_INFO_IDX prv_api;
+ POUT_INFO *p_pi = &api[inst_num].pout_info; // ### TODO check inst_num range?
+ POUT_SETTINGS *p_ps = &p_pi->pout_settings;
+ const char *err_info = NULL;
+ char *cp;
+ int n_pout;
+ int idx;
+ int i;
+ int rc = check_get_pout_cfg( dh, api, &ri );
+
+ if ( mbg_ioctl_err( rc, "check_get_pout_cfg" ) )
+ return rc;
+
+ n_pout = rc; // Contains now the number of programmable pulse outputs
+
+ // save current settings
+ memcpy( prv_api, api, sizeof( prv_api ) );
+
+ // Mode
+ idx = chk_parm_name( s, pout_name_mode, &cp );
+
+ if ( idx < 0 ) // parameter error
+ {
+ err_info = pout_name_mode;
+ goto fail;
+ }
+
+ if ( cp ) // parameter found
+ {
+ idx = atoi( cp );
+
+ if ( idx < 0 || idx >= N_POUT_MODES )
+ {
+ printf( "Programmable output mode %i out of range (0..%i)\n", idx, N_POUT_MODES - 1 );
+ goto fail;
+ }
+
+ if ( !_is_supported( idx, p_pi->supp_modes ) )
+ {
+ printf( "Programmable output mode %i (%s) not supported for output %i\n",
+ idx, _get_pout_mode_name( idx ), inst_num );
+ goto fail;
+ }
+
+ p_ps->mode = idx;
+ printf( "Programmable output mode for output %i changed to %s (%i)\n",
+ inst_num, _get_pout_mode_name( p_ps->mode ), p_ps->mode );
+ }
+
+
+ // Pulse len
+ idx = chk_parm_name( s, pout_name_len, &cp );
+
+ if ( idx < 0 ) // parameter error
+ {
+ err_info = pout_name_len;
+ goto fail;
+ }
+
+ if ( cp ) // parameter found
+ {
+ idx = atoi( cp );
+
+ if ( !_is_supported( p_ps->mode, POUT_MODES_MODE_PARAM_AS_PULSE_LEN ) )
+ {
+ printf( "Pulse length parameter not supported for mode \"%s\"\n",
+ _get_pout_mode_name( p_ps->mode ) );
+ goto fail;
+ }
+
+ if ( idx < 0 || idx >= MAX_POUT_PULSE_LEN )
+ {
+ printf( "Pulse length %i out of range (1..%i)\n", idx, MAX_POUT_PULSE_LEN );
+ goto fail;
+ }
+
+ if ( p_pi->flags & POUT_FIXED_PULSE_LEN )
+ {
+ if ( idx != p_ps->mode_param )
+ printf( "Warning. pulse length %i (%i ms) is fix and can't be changed!\n",
+ p_ps->mode_param, p_ps->mode_param * 10 );
+ }
+ else
+ {
+ p_ps->mode_param = idx;
+ printf( "Pulse length for programmable output %i changed to %i (%i ms)\n",
+ inst_num, p_ps->mode_param, p_ps->mode_param * 10 );
+ }
+ }
+
+
+ // "Inverted" flag
+ idx = chk_parm_name( s, pout_name_inv, &cp );
+
+ if ( idx < 0 ) // parameter error
+ {
+ err_info = pout_name_inv;
+ goto fail;
+ }
+
+ if ( cp ) // parameter found
+ {
+ idx = atoi( cp );
+
+ if ( idx < 0 || idx > 1 )
+ {
+ printf( "Invalid flag value %i for parameter %s, must be 0 or 1\n", idx, pout_name_inv );
+ goto fail;
+ }
+
+ if ( p_pi->flags & POUT_NOT_INVERTIBLE )
+ {
+ if ( idx )
+ {
+ printf( "Warning: Output level can't be inverted for output %i\n", inst_num );
+ goto fail;
+ }
+ }
+
+ if ( idx )
+ p_ps->flags |= POUT_INVERTED;
+ else
+ p_ps->flags &= ~POUT_INVERTED;
+
+ printf( "Output level for output %i%s inverted\n",
+ inst_num, idx ? str_empty : str_spc_not );
+ }
+
+
+ // "Only If Sync" flag
+ idx = chk_parm_name( s, pout_name_ois, &cp );
+
+ if ( idx < 0 ) // parameter error
+ {
+ err_info = pout_name_ois;
+ goto fail;
+ }
+
+ if ( cp ) // parameter found
+ {
+ idx = atoi( cp );
+
+ if ( idx < 0 || idx > 1 )
+ {
+ printf( "Invalid flag value %i for parameter %s, must be 0 or 1\n", idx, pout_name_ois );
+ goto fail;
+ }
+
+ if ( !( p_pi->flags & POUT_SUPP_IF_SYNC_ONLY ) )
+ {
+ if ( idx )
+ {
+ printf( "Warning: \"Only if sync\" flag not supported for output %i\n", inst_num );
+ goto fail;
+ }
+ }
+
+ if ( idx )
+ p_ps->flags |= POUT_IF_SYNC_ONLY;
+ else
+ p_ps->flags &= ~POUT_IF_SYNC_ONLY;
+
+ printf( "\"Only if sync\" flag%s set for output %i\n",
+ idx ? str_empty : str_spc_not, inst_num );
+ }
+
+
+ // "Pulse Shift" parameter
+ idx = chk_parm_name( s, pout_name_shift, &cp );
+
+ if ( idx < 0 ) // parameter error
+ {
+ err_info = pout_name_shift;
+ goto fail;
+ }
+
+ if ( cp ) // parameter found
+ {
+ long pulse_shift = atol( cp );
+
+ if ( !( p_pi->flags & POUT_SUPP_PULSE_SHIFT ) )
+ {
+ printf( "Warning: pulse shift not supported for output %i\n", inst_num );
+ goto fail;
+ }
+
+ if ( !_is_supported( p_ps->mode, POUT_MODES_DATA_PULSE_SHIFT ) )
+ {
+ printf( "Pulse shift not supported for mode \"%s\"\n",
+ _get_pout_mode_name( p_ps->mode ) );
+ goto fail;
+ }
+
+
+ if ( ( pulse_shift < DEFAULT_POUT_PULSE_SHIFT_MIN ) ||
+ ( pulse_shift > DEFAULT_POUT_PULSE_SHIFT_MAX ) )
+ {
+ printf( "Pulse shift %li ns out of range (%+li..%+li ns)\n", pulse_shift,
+ (long) DEFAULT_POUT_PULSE_SHIFT_MIN, (long) DEFAULT_POUT_PULSE_SHIFT_MAX );
+ goto fail;
+ }
+
+ if ( p_pi->pulse_shift_res )
+ {
+ long rem = pulse_shift % p_pi->pulse_shift_res;
+ long l = pulse_shift - rem;
+
+ #if 0 && defined( DEBUG )
+ printf( "DEBUG: s %li, rem %li, l %li\n", pulse_shift, rem, l );
+ #endif
+
+ if ( l != pulse_shift )
+ {
+ printf( "Warning: pulse shift %+li ns not appropriate for resolution %u ns, truncating to %li ns.\n",
+ pulse_shift, p_pi->pulse_shift_res, l );
+ pulse_shift = l;
+ }
+ }
+
+ p_ps->pout_data.pulse_shift = pulse_shift;
+
+ printf( "Pulse shift for programmable output %i changed to %li ns\n",
+ inst_num, (long) p_ps->pout_data.pulse_shift );
+ }
+
+
+ for ( i = 0; i < n_pout; i++ )
+ {
+ POUT_SETTINGS *p_ps = &api[i].pout_info.pout_settings;
+
+ if ( memcmp( p_ps, &prv_api[i].pout_info.pout_settings, sizeof( *p_ps ) ) )
+ {
+ // settings for this output have changed
+ rc = mbg_set_gps_pout_settings( dh, p_ps, i );
+
+ if ( mbg_rc_is_error( rc ) )
+ return rc;
+ }
+ }
+
+ return MBG_SUCCESS;
+
+fail:
+ printf( "Invalid parameter in argument" );
+
+ if ( err_info )
+ printf( " %s", err_info );
+
+ printf( "!\n" );
+
+ return MBG_ERR_CFG;
+
+} // eval_pout
+
+
+
+static /*HDR*/
+int show_pout( MBG_DEV_HANDLE dh, const OPT_HANDLER_SPEC *p_opt, const PCPS_DEV *p_devx, const char *cmd_info )
+{
+ const INDENTS *p_ind = &show_indents;
+ RECEIVER_INFO ri = { 0 };
+ ALL_POUT_INFO_IDX api = { { 0 } };
+ int i;
+ int n_pout;
+ int rc = check_get_pout_cfg( dh, api, &ri );
+
+ if ( mbg_ioctl_err( rc, "check_get_pout_cfg" ) )
+ return rc;
+
+ n_pout = rc; // Contains now the number of programmable pulse outputs
+
+ print_indent( p_ind->indent_1 );
+ printf( "%s:", cmd_info );
+
+ if ( n_pout )
+ {
+ for ( i = 0; i < n_pout; i++ )
+ {
+ const POUT_INFO *pi = &api[i].pout_info;
+ const POUT_SETTINGS *ps = &pi->pout_settings;
+
+ // TODO: Actually the code below only shows the current mode,
+ // and whether the output signal is inverted, or not.
+ // Full featured code should also display additional parameters
+ // depending the selected mode.
+
+ printf( "\n" );
+ print_indent( p_ind->indent_2 );
+ printf( "Output %i: ", i );
+ printf( "%s", _get_pout_mode_name( ps->mode ) );
+
+ // Print pulse len, if supported by the mode
+ if ( _is_supported( ps->mode, POUT_MODES_MODE_PARAM_AS_PULSE_LEN ) )
+ {
+ // pulse len is 10 ms units, so multiply by 10 to get ms
+ printf( ", len %u ms", (unsigned int) ps->mode_param * 10 );
+
+ if ( pi->flags & POUT_FIXED_PULSE_LEN )
+ printf( " (fix)" );
+ }
+
+ // ### FIXME check more mode_param usage, times etc.
+
+ // If outputs can be inverted then this doesn't depend on the current mode
+ if ( !( pi->flags & POUT_NOT_INVERTIBLE ) )
+ printf( ", %sinverted", ( ps->flags & POUT_INVERTED ) ? str_empty : str_not_spc );
+
+
+
+ if ( _is_supported( ps->mode, POUT_MODES_SUPP_IF_SYNC_ONLY ) )
+ {
+ char ws[80];
+ const char *cp = NULL;
+
+ if ( _is_supported( ps->mode, POUT_MODES_TIMEOUT ) &&
+ ( ( pi->flags & POUT_SUPP_IF_SYNC_ONLY ) == 0 ) &&
+ ( ps->timeout != 0 ) )
+ {
+ snprintf_safe( ws, sizeof( ws ), "after timeout %i min ", ps->timeout );
+ cp = ws;
+ }
+
+ if ( pi->flags & POUT_SUPP_IF_SYNC_ONLY )
+ printf( ", %sdisabled %sif sync. lost",
+ ( ps->flags & POUT_IF_SYNC_ONLY ) ? str_empty : str_not_spc,
+ cp ? cp : str_empty );
+ }
+
+
+
+
+ if ( pi->flags & POUT_SUPP_PULSE_SHIFT )
+ if ( _is_supported( ps->mode, POUT_MODES_DATA_PULSE_SHIFT ) )
+ printf( ", shift %li ns, res. %li ns", (long) ps->pout_data.pulse_shift, (long) pi->pulse_shift_res );
+ }
+ }
+ else
+ printf( str_spc_not_supp );
+
+ printf( "\n" );
+
+ return MBG_SUCCESS;
+
+} // show_pout
+
+
+
+static /*HDR*/
void printf_ef( uint16_t flag, const char *info )
{
printf( "%s:%u", info, ( flag == EF_OFF ) ? 0 : 1 );
@@ -1653,7 +2511,7 @@ int show_ant_cable_len( MBG_DEV_HANDLE dh, const char *info )
static /*HDR*/
int set_ant_cable_len( MBG_DEV_HANDLE dh, const char *s )
{
- ANT_CABLE_LEN len = atol( s );
+ ANT_CABLE_LEN len = (ANT_CABLE_LEN) atol( s ); // TODO check range ?
int rc = mbg_set_gps_ant_cable_len( dh, &len );
if ( mbg_ioctl_err( rc, "mbg_set_gps_ant_cable_len" ) )
@@ -1675,7 +2533,7 @@ int set_event_time( MBG_DEV_HANDLE dh, const char *s )
// set event at current system time + number of seconds
event_time = time( NULL ) + strtol( s, NULL, 10 );
- event_ts.sec = event_time; // Unix UTC seconds
+ event_ts.sec = (uint32_t) event_time; // Unix UTC seconds // TODO: check range / conversion
event_ts.frac = 0; // fraction of second, 0xFFFFFFFF == 0.99.. sec
rc = mbg_set_event_time( dh, &event_ts );
@@ -1683,7 +2541,7 @@ int set_event_time( MBG_DEV_HANDLE dh, const char *s )
if ( mbg_ioctl_err( rc, "mbg_set_event_time" ) )
return rc;
- mbg_snprint_hr_tstamp( ws, sizeof( ws ), &event_ts, 0 ); // raw timestamp?
+ mbg_snprint_hr_tstamp( ws, sizeof( ws ), &event_ts, 0, 0 ); // raw timestamp?
printf( "Event time set to UTC %s\n", ws );
return MBG_SUCCESS;
@@ -1697,12 +2555,18 @@ int get_n_time_scale( MBG_DEV_HANDLE dh, MBG_TIME_SCALE_INFO *p_tsci )
{
MBG_TIME_SCALE_INFO tsci = { { 0 } };
int rc;
- int i;
- rc = mbg_dev_has_time_scale( dh, &i );
+ rc = mbg_chk_dev_has_time_scale( dh );
- if ( ( rc != MBG_SUCCESS ) || ( i == 0 ) )
- goto done; // failed or not supported
+ if ( mbg_rc_is_error( rc ) )
+ {
+ if ( rc == MBG_ERR_NOT_SUPP_BY_DEV )
+ printf( "This device does not support a configurable time scale.\n" );
+ else
+ mbg_ioctl_err( rc, "mbg_chk_dev_has_time_scale" );
+
+ goto done;
+ }
rc = mbg_get_time_scale_info( dh, &tsci );
@@ -1781,17 +2645,14 @@ int set_time_scale( MBG_DEV_HANDLE dh, const char *arg, const PCPS_DEV *p_dev )
static /*HDR*/
-void usage( MBG_DEV_HANDLE dh, PCPS_DEV *p_dev, RECEIVER_INFO *p_ri,
+void usage( MBG_DEV_HANDLE dh, PCPS_DEV *p_dev, RECEIVER_INFO *p_ri,
RECEIVER_PORT_CFG *p_rpcfg )
{
int i;
int n_time_scale;
if ( p_dev )
- {
- check_setup_receiver_info( dh, p_dev, p_ri );
check_get_receiver_port_cfg( dh, p_rpcfg, p_dev, p_ri );
- }
printf( "Usage: %s cmd [dev]\n"
"\n"
@@ -1887,6 +2748,10 @@ void usage( MBG_DEV_HANDLE dh, PCPS_DEV *p_dev, RECEIVER_INFO *p_ri,
printf( "\n" );
+ help_pout_arg( dh, p_dev, &ohs_pout, 0 );
+
+ printf( "\n" );
+
printf( " EF show clock's enable flags\n"
" EF=SERIAL:0,PULSES:1,SYNTH:0 modify clock's enable flags\n"
"\n"
@@ -1937,17 +2802,17 @@ void usage( MBG_DEV_HANDLE dh, PCPS_DEV *p_dev, RECEIVER_INFO *p_ri,
printf( " If the PTP device supports unicast slave mode then the following parameters\n"
" can be specified to configure a unicast master to be queried:\n"
- " PTP=ROLE:<rl>[,GMIP:<ip>][,GMID:<id>][,PID:<po>][,SMI:<sr>][,AMI:<ar>][,DMI:<dr>][,DUR:<du>] set PTP unicast parameters\n"
+ " PTP=ROLE:<rl>[,GMIP:<ip>][,GMID:<id>][,PID:<po>][,SMI:<sr>][,AMI:<ar>][,DRI:<dr>][,DUR:<du>] set PTP unicast parameters\n"
"\n"
" where, e.g.:\n"
" ROLE:MCS specifies \"Multicast Slave\" PTP role\n"
" ROLE:UCS specifies \"Unicast Slave\" PTP role\n"
" GMIP:192.168.1.115 specifies the IP address of the grandmaster\n"
- " GMID:FF:FF:FF:FF:FF:FF:FF:FF specifies the Clock ID of the grandmaster, or '*' as wildcard for all FF\n"
- " PID:1 specifies the target port ID of the grandmaster port to be used, or '*' for wildcard\n"
- " SMI:0 specifies the Sync message interval requested from the grandmaster in 2^x seconds [-6..6]\n"
- " AMI:1 specifies the Announce message interval requested from the grandmaster in 2^x seconds [-6..6]\n"
- " DMI:1 specifies the DelayRequest message interval requested from the grandmaster in 2^x seconds [-6..6]\n"
+ " GMID:FF:FF:FF:FF:FF:FF:FF:FF specifies the Clock ID of the grandmaster, or '*' as wildcard for all 'FF'\n"
+ " PID:1 specifies the target Port ID of the grandmaster port to be used, or '*' for wildcard\n"
+ " SMI:0 specifies the Sync Message Interval requested from the grandmaster in 2^x seconds [-6..6]\n"
+ " AMI:1 specifies the Announce Message Interval requested from the grandmaster in 2^x seconds [-6..6]\n"
+ " DRI:1 specifies the Delay Request Interval requested from the grandmaster in 2^x seconds [-6..6]\n"
" DUR:300 specifies the duration in seconds how long the master shall send messages to the slave until a timeout or renewal occurs\n"
"\n"
);
@@ -1985,7 +2850,7 @@ const char *str_parm_p( const char *s, const char *keyword )
static /*HDR*/
-int check_cmd_line( int argc, char *argv[], MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev,
+int check_cmd_line( int argc, char *argv[], MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev,
RECEIVER_INFO *p_ri, RECEIVER_PORT_CFG *p_rpcfg )
{
const char *sdate = NULL;
@@ -2078,11 +2943,16 @@ int check_cmd_line( int argc, char *argv[], MBG_DEV_HANDLE dh, const PCPS_DEV *p
{
if ( p_dev )
{
- check_setup_receiver_info( dh, p_dev, p_ri );
- if ( p_ri->n_com_ports )
+ int rc = check_get_receiver_port_cfg( dh, p_rpcfg, p_dev, p_ri );
+
+ if ( mbg_rc_is_error( rc ) )
{
- check_get_receiver_port_cfg( dh, p_rpcfg, p_dev, p_ri );
+ // ### TODO print another error?
+ continue;
+ }
+ if ( p_ri->n_com_ports )
+ {
if ( *cp != 0 )
{
printf( "** Invalid parameter: %s\n", argv[i] );
@@ -2109,8 +2979,13 @@ int check_cmd_line( int argc, char *argv[], MBG_DEV_HANDLE dh, const PCPS_DEV *p
char *p_tail;
ulong port_num;
- check_setup_receiver_info( dh, p_dev, p_ri );
- check_get_receiver_port_cfg( dh, p_rpcfg, p_dev, p_ri );
+ rc = check_get_receiver_port_cfg( dh, p_rpcfg, p_dev, p_ri );
+
+ if ( mbg_rc_is_error( rc ) )
+ {
+ // ### TODO print another error?
+ continue;
+ }
port_num = strtoul( cp, &p_tail, 10 );
@@ -2125,7 +3000,7 @@ int check_cmd_line( int argc, char *argv[], MBG_DEV_HANDLE dh, const PCPS_DEV *p
if ( port_num >= (ulong) p_ri->n_com_ports )
{
- printf( "** COM port number %lu exceeds maximum %u\n",
+ printf( "** COM port number %lu exceeds maximum %u\n",
port_num, p_ri->n_com_ports );
must_print_usage = 1;
continue;
@@ -2144,6 +3019,58 @@ int check_cmd_line( int argc, char *argv[], MBG_DEV_HANDLE dh, const PCPS_DEV *p
}
+ cp = str_parm_p( argv[i], "POUT" );
+
+ if ( cp )
+ {
+ if ( p_dev )
+ {
+ ulong n_pout;
+ ulong pout_num;
+ char *p_tail;
+
+ check_setup_receiver_info( dh, p_ri );
+ n_pout = p_ri->n_prg_out;
+
+ if ( n_pout == 0 )
+ {
+ printf( "Programmable outputs not supported!\n" );
+ continue;
+ }
+
+ pout_num = strtoul( cp, &p_tail, 10 );
+
+ if ( p_tail == cp ) // no POUT number specified
+ {
+ show_pout( dh, &ohs_pout, p_dev, "Current programmable outputs settings" );
+ continue;
+ }
+
+ cp = p_tail;
+
+ if ( pout_num >= n_pout )
+ {
+ printf( "** Programmable output number %lu exceeds maximum %lu\n",
+ pout_num, n_pout );
+ must_print_usage = 1;
+ continue;
+ }
+
+ if ( *cp != '=' )
+ {
+ printf( "** Invalid programmable output specification: %s\n", argv[i] );
+ must_print_usage = 1;
+ continue;
+ }
+
+ rc = eval_pout( dh, ++cp, (unsigned) pout_num );
+ printf( "\n" );
+ show_pout( dh, &ohs_pout, p_dev, "Current programmable outputs settings" );
+ }
+ continue;
+ }
+
+
cp = str_parm_p( argv[i], "EF" );
if ( cp )
@@ -2296,10 +3223,7 @@ int check_cmd_line( int argc, char *argv[], MBG_DEV_HANDLE dh, const PCPS_DEV *p
rc = set_ptp_cfg( dh, ++cp, p_dev );
if ( rc < 0 )
- {
- must_print_usage = 1;
continue;
- }
info = "New";
}
@@ -2413,7 +3337,13 @@ int main( int argc, char *argv[] )
check_cmd_line( argc, argv, dh, NULL, &ri, &rpcfg );
if ( dev_name )
- dh = open( dev_name, O_RDWR ); // open specific device
+ {
+ #if defined( MBG_TGT_POSIX ) && !defined( MBG_TGT_QNX_NTO )
+ dh = open( dev_name, O_RDWR );
+ #else
+ dh = mbg_open_device_by_name( dev_name, MBG_MATCH_MODEL );
+ #endif
+ }
else
dh = mbg_open_device( 0 ); // open first device found
diff --git a/mbgfasttstamp/Makefile b/mbgfasttstamp/Makefile
index 0ff4574..6628bd3 100755
--- a/mbgfasttstamp/Makefile
+++ b/mbgfasttstamp/Makefile
@@ -1,13 +1,20 @@
#########################################################################
#
-# $Id: Makefile 1.2.1.3 2011/11/23 17:58:59 martin TEST $
+# $Id: Makefile 1.2.1.7 2016/07/15 14:06:51 martin TEST $
#
# Description:
# Makefile for mbgfasttstamp.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.2.1.7 2016/07/15 14:06:51 martin
+# Added new module timeutil.o.
+# Revision 1.2.1.6 2015/08/31 14:30:51 martin
+# Revision 1.2.1.5 2015/07/14 15:07:20 martin
+# Added object module mbgerror.o.
+# Revision 1.2.1.4 2014/04/28 13:19:51 martin
+# Added module cfg_hlp.o.
# Revision 1.2.1.3 2011/11/23 17:58:59 martin
# Revision 1.2.1.2 2010/08/30 09:05:23 martin
# Revision 1.2.1.1 2010/08/30 08:21:01 martin
@@ -23,7 +30,11 @@ INST_TO_BIN = 1
OBJS = $(TARGET).o
OBJS += mbgdevio.o
+OBJS += timeutil.o
+OBJS += str_util.o
+OBJS += cfg_hlp.o
OBJS += toolutil.o
+OBJS += mbgerror.o
OBJS += gpsutils.o
BASEDIR := ..
diff --git a/mbgfasttstamp/mbgfasttstamp.c b/mbgfasttstamp/mbgfasttstamp.c
index b066f93..daad89b 100755
--- a/mbgfasttstamp/mbgfasttstamp.c
+++ b/mbgfasttstamp/mbgfasttstamp.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgfasttstamp.c 1.6.1.8 2013/04/10 15:40:28 martin TEST $
+ * $Id: mbgfasttstamp.c 1.6.1.14 2017/01/27 12:06:34 martin TEST $
*
* Description:
* Main file for mbgfasttstamp program which demonstrates how to access
@@ -9,6 +9,15 @@
*
* -----------------------------------------------------------------------
* $Log: mbgfasttstamp.c $
+ * Revision 1.6.1.14 2017/01/27 12:06:34 martin
+ * Don't use deprecated API call.
+ * Revision 1.6.1.13 2016/10/20 14:08:03 martin
+ * Parameters -u and -s imply -c.
+ * Revision 1.6.1.12 2015/10/26 13:50:10 martin
+ * Revision 1.6.1.11 2014/10/28 15:38:44Z martin
+ * Revision 1.6.1.10 2013/07/22 16:25:10Z martin
+ * Revision 1.6.1.9 2013/07/11 08:29:29 martin
+ * Account for modified function call parameter list.
* Revision 1.6.1.8 2013/04/10 15:40:28 martin
* Revision 1.6.1.7 2013/01/24 14:39:33Z martin
* Revision 1.6.1.6 2012/06/01 18:46:52 martin
@@ -47,7 +56,6 @@
// include Meinberg headers
#include <mbgdevio.h>
-#include <pcpsutil.h>
#include <toolutil.h> // common utility functions
// include system headers
@@ -174,15 +182,15 @@ fail:
static /*HDR*/
int do_mbgfasttstamp( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
{
- int supported = 0;
- int rc = mbg_dev_has_fast_hr_timestamp( dh, &supported );
+ int rc = mbg_chk_dev_has_fast_hr_timestamp( dh );
- if ( mbg_ioctl_err( rc, "mbg_has_fast_hr_timestamp" ) )
- goto done;
-
- if ( !supported )
+ if ( mbg_rc_is_error( rc ) )
{
- printf( "This device does not support fast (memory mapped) time stamps.\n" );
+ if ( rc == MBG_ERR_NOT_SUPP_BY_DEV )
+ printf( "This device does not support fast (memory mapped) time stamps.\n" );
+ else
+ mbg_ioctl_err( rc, "mbg_chk_dev_has_fast_hr_timestamp" );
+
goto done;
}
@@ -192,8 +200,6 @@ int do_mbgfasttstamp( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
show_fast_hr_timestamp( dh );
done:
- mbg_close_device( &dh );
-
return rc;
} // do_mbgfasttstamp
@@ -214,8 +220,8 @@ void usage( void )
mbg_print_opt_info( "-n num", "run num loops" );
mbg_print_opt_info( "-b", "burst read" );
mbg_print_opt_info( "-r", "read raw time stamps, no cycles" );
- mbg_print_opt_info( "-s num", "sleep num seconds between calls" );
- mbg_print_opt_info( "-u num", "sleep num microseconds between calls" );
+ mbg_print_opt_info( "-s num", "sleep num seconds between calls (implies -c)" );
+ mbg_print_opt_info( "-u num", "sleep num microseconds between calls (implies -c)" );
mbg_print_device_options();
puts( "" );
@@ -253,10 +259,12 @@ int main( int argc, char *argv[] )
case 's':
sleep_secs = atoi( optarg );
+ loops = -1;
break;
case 'u':
sleep_usecs = atoi( optarg );
+ loops = -1;
break;
case 'h':
@@ -293,8 +301,8 @@ int main( int argc, char *argv[] )
// on the command, and for each device
// - tries to open the device
// - shows basic device info
- // - calls the function passed as last parameter
- rc = mbg_check_devices( argc, argv, optind, do_mbgfasttstamp );
+ // - calls the specified callback function
+ rc = mbg_check_devices( argc, argv, optind, do_mbgfasttstamp, 0 );
return abs( rc );
}
diff --git a/mbggpscap/Makefile b/mbggpscap/Makefile
index 390b4cd..f18ee1c 100755
--- a/mbggpscap/Makefile
+++ b/mbggpscap/Makefile
@@ -1,13 +1,20 @@
#########################################################################
#
-# $Id: Makefile 1.7.1.3 2011/09/26 16:01:46 martin TEST $
+# $Id: Makefile 1.7.1.7 2016/07/15 14:06:51 martin TEST $
#
# Description:
# Makefile for mbggpscap.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.7.1.7 2016/07/15 14:06:51 martin
+# Added new module timeutil.o.
+# Revision 1.7.1.6 2015/08/31 14:26:13 martin
+# Revision 1.7.1.5 2015/07/14 15:07:20 martin
+# Added object module mbgerror.o.
+# Revision 1.7.1.4 2014/04/28 13:19:51 martin
+# Added module cfg_hlp.o.
# Revision 1.7.1.3 2011/09/26 16:01:46 martin
# Updated for use with latest base Makefile.
# Revision 1.7.1.2 2010/08/30 09:05:23 martin
@@ -34,8 +41,12 @@ INST_TO_BIN = 1
OBJS = $(TARGET).o
OBJS += mbgdevio.o
-OBJS += gpsutils.o
+OBJS += timeutil.o
+OBJS += str_util.o
OBJS += toolutil.o
+OBJS += mbgerror.o
+OBJS += cfg_hlp.o
+OBJS += gpsutils.o
BASEDIR := ..
include $(BASEDIR)/Makefile
diff --git a/mbggpscap/mbggpscap.c b/mbggpscap/mbggpscap.c
index eaf6744..4a8205d 100755
--- a/mbggpscap/mbggpscap.c
+++ b/mbggpscap/mbggpscap.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbggpscap.c 1.10.1.8 2013/06/25 09:53:47 martin TRASH martin $
+ * $Id: mbggpscap.c 1.10.1.13 2016/12/09 10:16:32 martin TEST $
*
* Description:
* Main file for mbggpscap program which demonstrates how to access
@@ -13,6 +13,15 @@
*
* -----------------------------------------------------------------------
* $Log: mbggpscap.c $
+ * Revision 1.10.1.13 2016/12/09 10:16:32 martin
+ * Enhanced interval checking and error reporting.
+ * New command line option to clear buffer.
+ * Revision 1.10.1.12 2016/11/04 12:29:39 martin
+ * *** empty log message ***
+ * Revision 1.10.1.11 2015/10/26 13:50:42 martin
+ * Revision 1.10.1.10 2013/07/22 16:25:10Z martin
+ * Revision 1.10.1.9 2013/07/11 08:29:29 martin
+ * Account for modified function call parameter list.
* Revision 1.10.1.8 2013/06/25 09:53:47 martin
* Revision 1.10.1.7 2013/04/10 15:40:28 martin
* Revision 1.10.1.6 2011/09/09 08:28:22Z martin
@@ -61,7 +70,6 @@
// include Meinberg headers
#include <mbgdevio.h>
-#include <pcpsutil.h>
#include <toolutil.h> // common utility functions
// include system headers
@@ -85,6 +93,7 @@ static double nom_cap_intv; // nominal capture interval to check [s]
static double max_cap_jitter; // max allowed jitter [s]
static int raw;
static int force_old_api;
+static int clear_buffer;
static int has_been_called;
static int must_check_intv;
@@ -107,6 +116,7 @@ void show_ucap_event( const PCPS_HR_TIME *ucap )
if ( must_check_intv && has_been_called )
{
+ int jitter_exceeded;
double abs_delta;
double d = ucap->tstamp.sec - prv_ucap.tstamp.sec;
d += ( (double) ucap->tstamp.frac - prv_ucap.tstamp.frac ) / PCPS_HRT_BIN_FRAC_SCALE;
@@ -118,11 +128,16 @@ void show_ucap_event( const PCPS_HR_TIME *ucap )
if ( abs_delta < 0.0 )
abs_delta = -abs_delta;
+ jitter_exceeded = 0;
+
if ( abs_delta > max_cap_jitter )
+ {
+ jitter_exceeded = 1;
err_cnt++;
+ }
if ( err_cnt )
- printf( " ** %lu", err_cnt );
+ printf( " %lu%s", err_cnt, jitter_exceeded ? " <<" : "" );
}
// status bit definitions can be found in pcpsdefs.h.
@@ -204,6 +219,9 @@ void check_serial_mode( MBG_DEV_HANDLE dh )
rc = mbg_set_gps_port_parm( dh, &port_parm );
+// ### TODO FIXME The call above requires root permissions, so
+// print a more appropriate message if the cal failed.
+
if ( mbg_ioctl_err( rc, "mbg_set_gps_port_parm" ) )
return;
@@ -217,11 +235,13 @@ static /*HDR*/
int do_mbggpscap( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
{
int rc;
+ int this_clear_buffer = clear_buffer;
must_check_intv = continuous && ( nom_cap_intv != 0 );
has_been_called = 0;
err_cnt = 0;
+
if ( !_pcps_has_ucap( p_dev ) && !_pcps_is_gps( p_dev ) )
{
printf( "This device type does not provide time capture inputs.\n" );
@@ -265,6 +285,13 @@ int do_mbggpscap( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
ucap_entries.used, ucap_entries.max );
}
+ if ( this_clear_buffer )
+ {
+ printf( "Clearing on-board FIFO buffer\n" );
+ mbg_clr_ucap_buff( dh );
+ this_clear_buffer = 0;
+ }
+
// If the program is not to run continuously and no
// capture events are available then we're through.
if ( query_only || ( !continuous && ucap_entries.used == 0 ) )
@@ -276,6 +303,10 @@ int do_mbggpscap( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
"Reading capture events:\n"
);
+ if ( must_check_intv )
+ if ( max_cap_jitter == 0.0 )
+ max_cap_jitter = 0.1e-6;
+
// Now read out all events from the FIFO and wait
// for new events if the FIFO is empty.
for (;;)
@@ -347,6 +378,7 @@ void usage( void )
);
mbg_print_help_options();
mbg_print_opt_info( "-c", "run continuously" );
+ mbg_print_opt_info( "-C", "clear capture buffer" );
mbg_print_opt_info( "-i val", "check interval between captures events [s]" );
mbg_print_opt_info( "-j val", "max allowed jitter of capture interval [s]" );
mbg_print_opt_info( "-q", "query FIFO buffer status only" );
@@ -367,7 +399,7 @@ int main( int argc, char *argv[] )
mbg_print_program_info( pname, MBG_MICRO_VERSION, MBG_FIRST_COPYRIGHT_YEAR, MBG_LAST_COPYRIGHT_YEAR );
// check command line parameters
- while ( ( c = getopt( argc, argv, "ci:j:qroh?" ) ) != -1 )
+ while ( ( c = getopt( argc, argv, "cCi:j:qroh?" ) ) != -1 )
{
switch ( c )
{
@@ -375,6 +407,10 @@ int main( int argc, char *argv[] )
continuous = 1;
break;
+ case 'C':
+ clear_buffer = 1;
+ break;
+
case 'i':
nom_cap_intv = atof( optarg );
break;
@@ -408,12 +444,18 @@ int main( int argc, char *argv[] )
return 1;
}
+ if ( nom_cap_intv != 0.0 )
+ {
+ printf( "Nominal capture interval: %f s\n", nom_cap_intv );
+ printf( "Maximum allowed capture jitter: %f s\n", max_cap_jitter );
+ }
+
// The function below checks which devices have been specified
// on the command, and for each device
// - tries to open the device
// - shows basic device info
- // - calls the function passed as last parameter
- rc = mbg_check_devices( argc, argv, optind, do_mbggpscap );
+ // - calls the specified callback function
+ rc = mbg_check_devices( argc, argv, optind, do_mbggpscap, 0 );
return abs( rc );
}
diff --git a/mbghrtime/Makefile b/mbghrtime/Makefile
index 0c8dc30..7ed855c 100755
--- a/mbghrtime/Makefile
+++ b/mbghrtime/Makefile
@@ -1,13 +1,20 @@
#########################################################################
#
-# $Id: Makefile 1.7.1.3 2011/09/26 16:02:55 martin TEST $
+# $Id: Makefile 1.7.1.7 2016/07/15 14:06:51 martin TEST $
#
# Description:
# Makefile for mbghrtime.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.7.1.7 2016/07/15 14:06:51 martin
+# Added new module timeutil.o.
+# Revision 1.7.1.6 2015/08/31 14:27:38 martin
+# Revision 1.7.1.5 2015/07/14 15:07:20 martin
+# Added object module mbgerror.o.
+# Revision 1.7.1.4 2014/04/28 13:19:51 martin
+# Added module cfg_hlp.o.
# Revision 1.7.1.3 2011/09/26 16:02:55 martin
# Updated for use with latest base Makefile.
# Revision 1.7.1.2 2010/08/30 09:05:23 martin
@@ -34,7 +41,11 @@ INST_TO_BIN = 1
OBJS = $(TARGET).o
OBJS += mbgdevio.o
+OBJS += timeutil.o
+OBJS += str_util.o
OBJS += toolutil.o
+OBJS += mbgerror.o
+OBJS += cfg_hlp.o
OBJS += gpsutils.o
BASEDIR := ..
diff --git a/mbghrtime/mbghrtime.c b/mbghrtime/mbghrtime.c
index 914bbde..7d4e8c8 100755
--- a/mbghrtime/mbghrtime.c
+++ b/mbghrtime/mbghrtime.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbghrtime.c 1.11.1.10 2013/04/10 15:40:29 martin TEST $
+ * $Id: mbghrtime.c 1.11.1.16 2016/10/20 14:08:04 martin TEST $
*
* Description:
* Main file for mbghrtime program which demonstrates how to access
@@ -10,6 +10,15 @@
*
* -----------------------------------------------------------------------
* $Log: mbghrtime.c $
+ * Revision 1.11.1.16 2016/10/20 14:08:04 martin
+ * Parameters -u and -s imply -c.
+ * Revision 1.11.1.15 2016/05/30 15:12:43 martin
+ * *** empty log message ***
+ * Revision 1.11.1.14 2015/10/26 14:17:20 martin
+ * Revision 1.11.1.13 2014/10/28 15:38:44Z martin
+ * Revision 1.11.1.12 2013/07/22 16:25:10Z martin
+ * Revision 1.11.1.11 2013/07/11 08:29:29 martin
+ * Account for modified function call parameter list.
* Revision 1.11.1.10 2013/04/10 15:40:29 martin
* Revision 1.11.1.9 2011/12/19 16:13:46Z martin
* Revision 1.11.1.8 2011/09/29 16:28:34 martin
@@ -61,7 +70,6 @@
// include Meinberg headers
#include <mbgdevio.h>
-#include <pcpsutil.h>
#include <toolutil.h> // common utility functions
// include system headers
@@ -196,15 +204,15 @@ fail:
static /*HDR*/
int do_mbghrtime( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
{
- int supported = 0;
- int rc = mbg_dev_has_hr_time( dh, &supported );
+ int rc = mbg_chk_dev_has_hr_time( dh );
- if ( mbg_ioctl_err( rc, "mbg_dev_has_hr_time" ) )
- goto done;
-
- if ( !supported )
+ if ( mbg_rc_is_error( rc ) )
{
- printf( "High resolution time not supported by this device.\n" );
+ if ( rc == MBG_ERR_NOT_SUPP_BY_DEV ) // ### TODO not_supp
+ printf( "High resolution time not supported by this device.\n" );
+ else
+ mbg_ioctl_err( rc, "mbg_chk_dev_has_hr_time" );
+
goto done;
}
@@ -214,8 +222,6 @@ int do_mbghrtime( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
show_hr_timestamp( dh );
done:
- mbg_close_device( &dh );
-
return rc;
} // do_mbghrtime
@@ -235,8 +241,8 @@ void usage( void )
mbg_print_opt_info( "-n num", "run num loops" );
mbg_print_opt_info( "-b", "burst read" );
mbg_print_opt_info( "-r", "read raw time stamps, no cycles" );
- mbg_print_opt_info( "-s num", "sleep num seconds between calls" );
- mbg_print_opt_info( "-u num", "sleep num microseconds between calls" );
+ mbg_print_opt_info( "-s num", "sleep num seconds between calls (implies -c)" );
+ mbg_print_opt_info( "-u num", "sleep num microseconds between calls (implies -c)" );
mbg_print_opt_info( "-v", "increase verbosity" );
mbg_print_device_options();
puts( "" );
@@ -275,10 +281,12 @@ int main( int argc, char *argv[] )
case 's':
sleep_secs = atoi( optarg );
+ loops = -1;
break;
case 'u':
sleep_usecs = atoi( optarg );
+ loops = -1;
break;
case 'v':
@@ -316,8 +324,8 @@ int main( int argc, char *argv[] )
// on the command, and for each device
// - tries to open the device
// - shows basic device info
- // - calls the function passed as last parameter
- rc = mbg_check_devices( argc, argv, optind, do_mbghrtime );
+ // - calls the specified callback function
+ rc = mbg_check_devices( argc, argv, optind, do_mbghrtime, 0 );
return abs( rc );
}
diff --git a/mbgirigcfg/Makefile b/mbgirigcfg/Makefile
index 7779939..013fb1e 100755
--- a/mbgirigcfg/Makefile
+++ b/mbgirigcfg/Makefile
@@ -1,13 +1,20 @@
#########################################################################
#
-# $Id: Makefile 1.5.1.3 2011/09/26 16:04:01 martin TEST $
+# $Id: Makefile 1.5.1.7 2016/07/15 14:06:52 martin TEST $
#
# Description:
# Makefile for mbgirigcfg.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.5.1.7 2016/07/15 14:06:52 martin
+# Added new module timeutil.o.
+# Revision 1.5.1.6 2015/08/31 14:23:34 martin
+# Revision 1.5.1.5 2015/07/14 15:07:20 martin
+# Added object module mbgerror.o.
+# Revision 1.5.1.4 2014/04/28 13:19:51 martin
+# Added module cfg_hlp.o.
# Revision 1.5.1.3 2011/09/26 16:04:01 martin
# Updated for use with latest base Makefile.
# Revision 1.5.1.2 2010/08/30 09:05:23 martin
@@ -30,7 +37,12 @@ INST_TO_SBIN = 1
OBJS = $(TARGET).o
OBJS += mbgdevio.o
+OBJS += mbgutil.o
+OBJS += timeutil.o
+OBJS += str_util.o
OBJS += toolutil.o
+OBJS += mbgerror.o
+OBJS += cfg_hlp.o
OBJS += gpsutils.o
BASEDIR := ..
diff --git a/mbgirigcfg/mbgirigcfg.c b/mbgirigcfg/mbgirigcfg.c
index f789279..7f1cdd1 100755
--- a/mbgirigcfg/mbgirigcfg.c
+++ b/mbgirigcfg/mbgirigcfg.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgirigcfg.c 1.10.1.14 2012/04/11 16:12:43 martin TEST $
+ * $Id: mbgirigcfg.c 1.10.1.21 2015/10/26 13:52:50 martin TEST $
*
* Description:
* Main file for the mbgirigcfg program which can be used to configure
@@ -10,7 +10,18 @@
*
* -----------------------------------------------------------------------
* $Log: mbgirigcfg.c $
- * Revision 1.10.1.14 2012/04/11 16:12:43 martin
+ * Revision 1.10.1.21 2015/10/26 13:52:50 martin
+ * Revision 1.10.1.20 2015/08/27 16:34:10Z martin
+ * Use safe string functions.
+ * Revision 1.10.1.19 2014/10/14 10:05:24 martin
+ * Revision 1.10.1.18 2014/08/27 10:50:59Z martin
+ * Support specification of minutes for ref offset.
+ * Revision 1.10.1.17 2013/07/22 16:25:11 martin
+ * Revision 1.10.1.16 2013/07/11 08:29:30 martin
+ * Account for modified function call parameter list.
+ * Revision 1.10.1.15 2013/07/10 13:00:51 martin
+ * Removed obsolete include to fix build under Windows.
+ * Revision 1.10.1.14 2012/04/11 16:12:43Z martin
* Added parameter -X which set ref offs to "unconfigured".
* Revision 1.10.1.13 2012/04/10 15:56:40 martin
* Revision 1.10.1.12 2011/07/19 12:59:06 martin
@@ -65,9 +76,9 @@
// include Meinberg headers
#include <mbgdevio.h>
+#include <mbgutil.h>
#include <mbgtime.h>
#include <pcpsmktm.h>
-#include <pcpsutil.h>
#include <pcpslstr.h>
#include <myutil.h>
#include <toolutil.h>
@@ -77,7 +88,6 @@
#include <stdlib.h>
#include <string.h>
#include <time.h>
-#include <unistd.h>
#define MBG_MICRO_VERSION 0
@@ -119,7 +129,28 @@ static const char *icode_rx_descr[N_ICODE_RX] = DEFAULT_ICODE_RX_DESCRIPTIONS_EN
static const char *icode_tx_names[N_ICODE_TX] = DEFAULT_ICODE_TX_NAMES;
static const char *icode_tx_descr[N_ICODE_TX] = DEFAULT_ICODE_TX_DESCRIPTIONS_ENG;
-static int max_ref_offs_h = MBG_REF_OFFS_MAX / MINS_PER_HOUR;
+static char str_ref_offs_min[16]; // need to be snprint_hours_mins'ed with -MBG_REF_OFFS_MAX
+static char str_ref_offs_max[16]; // need to be snprint_hours_mins'ed with +MBG_REF_OFFS_MAX
+
+
+
+static /*HDR*/
+size_t snprint_hours_mins( char *s, size_t max_len, long num_minutes )
+{
+ ldiv_t ldt = ldiv( labs( num_minutes ), MINS_PER_HOUR );
+
+ size_t n = mbg_snprintf( s, max_len, "%c%li",
+ ( num_minutes < 0 ) ? '-' : '+', ldt.quot );
+
+ if ( ldt.rem )
+ n += mbg_snprintf( &s[n], max_len - n, ":%02li", ldt.rem );
+
+ n += mbg_snprintf( &s[n], max_len - n, "h" );
+
+ return n;
+
+} // snprint_hours_mins
+
static /*HDR*/
@@ -182,7 +213,8 @@ static /*HDR*/
void print_cfg_rx( const char *info, const char *msg )
{
int idx = irig_rx_info.settings.icode;
- int ref_offs_h = ref_offs / MINS_PER_HOUR;
+ char ws[16];
+ char *cp = NULL;
printf( "%s %s configuration:\n", info, msg );
@@ -197,10 +229,20 @@ void print_cfg_rx( const char *info, const char *msg )
printf( " " DEFAULT_STR_IRIG_OFFS_EN ": " );
- if ( abs( ref_offs_h ) > max_ref_offs_h )
- printf( "** not configured **\n" );
+ if ( labs( ref_offs ) > MBG_REF_OFFS_MAX )
+ cp = "** not configured **";
else
- printf( "%+i h\n", ref_offs_h );
+ {
+ snprint_hours_mins( ws, sizeof( ws ), ref_offs );
+ cp = ws;
+ }
+
+ printf( "%s", cp );
+
+ if ( ( 1UL << idx ) & MSK_ICODE_RX_HAS_TZI )
+ printf( " (ignored with code %s)", icode_rx_names[idx] );
+
+ printf( "\n" );
if ( opt_info.supp_flags & MBG_OPT_FLAG_STR_UTC )
printf( " " DEFAULT_STR_IRIG_TIMESTR_UTC_EN ": %s\n",
@@ -268,22 +310,54 @@ void set_new_icode_rx( char *s )
static /*HDR*/
void set_new_ref_offs( char *s )
{
- int new_ref_offs_h;
+ long new_ref_offs;
+ char *cp = s;
+ int is_negative = 0;
+
+ // expected format: [-]hh[:mm]
- new_ref_offs_h = atoi( s );
+ // In case of e.g. "-0:30" conversion of the first part "-0" would yield
+ // 0 and thus the sign would get lost, so we check the sign explicitely.
+ if ( *cp == '-' )
+ is_negative = 1;
- if ( abs( new_ref_offs_h ) > max_ref_offs_h )
+ new_ref_offs = strtol( cp, &cp, 10 );
+
+ if ( cp == s ) // no number found at beginning
+ goto invalid;
+
+ new_ref_offs *= MINS_PER_HOUR;
+
+ if ( *cp++ == ':' ) // offset minutes seem to follow
{
- printf( "** New IRIG time offset %ih exceeds range (%+ih..%+ih).\n",
- new_ref_offs_h, -max_ref_offs_h, max_ref_offs_h );
- cfg_err_rx = 1;
+ long tmp = strtol( cp, &cp, 10 );
+
+ // the value behind the colon should always be positive
+ if ( tmp < 0 || tmp >= MINS_PER_HOUR )
+ goto invalid;
+
+ // apply the minutes offset according to the sign
+ new_ref_offs += is_negative ? -tmp : tmp;
}
- else
+
+ if ( labs( new_ref_offs ) > MBG_REF_OFFS_MAX )
{
- ref_offs = new_ref_offs_h * MINS_PER_HOUR;
- changed_cfg_rx = 1;
+ char ws[16];
+ snprint_hours_mins( ws, sizeof( ws ), new_ref_offs );
+ printf( "** New IRIG time offset %s exceeds range (%s..%s).\n",
+ ws, str_ref_offs_min, str_ref_offs_max );
+ goto invalid;
}
+ ref_offs = (MBG_REF_OFFS) new_ref_offs;
+ changed_cfg_rx = 1;
+
+ return;
+
+
+invalid:
+ cfg_err_rx = 1;
+
} // set_new_ref_offs
@@ -552,14 +626,14 @@ void usage( void )
printf( "\n" );
printf(
- " -o offs specifies the IRIG input time offset from UTC, in hours,\n"
- " where \"offs\" can be a value in the range %+i..%+i.\n"
+ " -o offs specifies the IRIG input time offset from UTC, in hours and optional minute,\n"
+ " where \"offs\" can be a value in the range %s .. %s.\n"
" When the device is shipped this parameter is set to \"not configured\"\n"
" to prevent the receiver from synchronizing to an IRIG input signal with\n"
" unknown UTC offset immediately after installation, which could cause\n"
" the system time to be set wrong by the time synchronization software.\n"
"\n",
- -max_ref_offs_h, max_ref_offs_h
+ str_ref_offs_min, str_ref_offs_max
);
printf(
@@ -644,13 +718,17 @@ int do_mbgirigcfg( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
{
printf( "** This device does not provide an IRIG input or output.\n" );
must_print_help_info = 1;
- return rc;
+ goto done;
}
check_cmd_line( glb_argc, glb_argv, p_dev );
if ( cfg_err_rx || cfg_err_tx )
+ {
+ printf( "** Invalid configuration options specified.\n" );
must_print_help_info = 1;
+ goto done;
+ }
if ( changed_cfg_rx || changed_cfg_tx )
{
@@ -690,6 +768,9 @@ int main( int argc, char *argv[] )
mbg_print_program_info( pname, MBG_MICRO_VERSION, MBG_FIRST_COPYRIGHT_YEAR, MBG_LAST_COPYRIGHT_YEAR );
+ snprint_hours_mins( str_ref_offs_min, sizeof( str_ref_offs_min ), -MBG_REF_OFFS_MAX );
+ snprint_hours_mins( str_ref_offs_max, sizeof( str_ref_offs_max ), MBG_REF_OFFS_MAX );
+
check_cmd_line( argc, argv, NULL );
if ( must_print_usage )
@@ -707,8 +788,8 @@ int main( int argc, char *argv[] )
// on the command, and for each device
// - tries to open the device
// - shows basic device info
- // - calls the function passed as last parameter
- rc = mbg_check_devices( glb_argc, glb_argv, optind, do_mbgirigcfg );
+ // - calls the specified callback function
+ rc = mbg_check_devices( glb_argc, glb_argv, optind, do_mbgirigcfg, 0 );
if ( must_print_help_info )
printf( "For help type \"%s -h\"\n\n", pname );
diff --git a/mbglib/bsd/pci_bsd.h b/mbglib/bsd/pci_bsd.h
index aaad78c..7ac79e9 100755
--- a/mbglib/bsd/pci_bsd.h
+++ b/mbglib/bsd/pci_bsd.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pci_bsd.h 1.2 2012/11/07 10:23:46 martin TRASH $
+ * $Id: pci_bsd.h 1.2 2012/11/07 10:23:46 martin REL_M $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
diff --git a/mbglib/bsd/rsrc_bsd.c b/mbglib/bsd/rsrc_bsd.c
index 9859620..a1b14d1 100755
--- a/mbglib/bsd/rsrc_bsd.c
+++ b/mbglib/bsd/rsrc_bsd.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: rsrc_bsd.c 1.1.1.1 2011/02/07 15:28:32 martin TEST martin $
+ * $Id: rsrc_bsd.c 1.1.1.1 2011/02/07 15:28:32 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
diff --git a/mbglib/bsd/rsrc_bsd.h b/mbglib/bsd/rsrc_bsd.h
index 57b0555..80ea291 100755
--- a/mbglib/bsd/rsrc_bsd.h
+++ b/mbglib/bsd/rsrc_bsd.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: rsrc_bsd.h 1.2 2012/11/07 10:24:10 martin TRASH $
+ * $Id: rsrc_bsd.h 1.2 2012/11/07 10:24:10 martin REL_M $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
diff --git a/mbglib/common/cfg_hlp.c b/mbglib/common/cfg_hlp.c
new file mode 100755
index 0000000..b6581ad
--- /dev/null
+++ b/mbglib/common/cfg_hlp.c
@@ -0,0 +1,1747 @@
+
+/**************************************************************************
+ *
+ * $Id: cfg_hlp.c 1.1.1.85 2017/04/11 14:47:08 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Meinberg device configuration helper functions.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: cfg_hlp.c $
+ * Revision 1.1.1.85 2017/04/11 14:47:08 martin
+ * Revision 1.1.1.84 2017/04/06 09:16:16Z thomas-b
+ * mbg_snprint_revision is not preliminary any longer
+ * Revision 1.1.1.83 2017/03/27 10:37:18 thomas-b
+ * Added ALL_PTP_V1_COMMON_DATASETS and the appropriate free function
+ * Revision 1.1.1.82 2017/03/22 09:07:52 thomas-b
+ * Added function get_io_port_type_info_idx
+ * Revision 1.1.1.81 2017/03/02 15:29:27 thomas-b
+ * Adapted free_all_ntp_cfg_info for new ALL_NTP_CFG_INFO structure
+ * Revision 1.1.1.80 2017/02/28 15:24:27 gregoire
+ * peer strucutre in ALL_NTP_CFG_INFO renamed
+ * Revision 1.1.1.79 2017/02/24 09:38:25 philipp
+ * Do not use fixed buffers for monitorung event info and status
+ * Revision 1.1.1.78 2017/02/22 14:28:57 martin
+ * Fixed some warnings from clang compiler.
+ * Revision 1.1.1.77 2017/02/22 11:40:17 martin
+ * Account for preliminary code.
+ * Revision 1.1.1.76 2017/02/21 15:51:40 thomas-b
+ * Added ALL_MONITORING_STATUS and free function and extended ALL_MONITORING_INFO by events
+ * Revision 1.1.1.75 2017/02/16 12:58:01 thomas-b
+ * Added ALL_PTP_V2_COMMON_DATASETS structure and the appropriate free function
+ * Revision 1.1.1.74 2017/02/08 13:16:07 thomas-b
+ * Added ALL_MONITORING_INFO and the appropriate free function
+ * Revision 1.1.1.73 2017/02/07 09:46:51 thomas-b
+ * Added ALL_SNMP_INFO and the appropriate free function
+ * Revision 1.1.1.72 2016/12/19 12:13:55 philipp
+ * Added GPIO associated index helper
+ * Revision 1.1.1.71 2016/11/22 12:40:46 philipp
+ * Added I/O port helper functions
+ * Revision 1.1.1.70 2016/11/08 17:21:19 martin
+ * Doxygen fixes.
+ * Revision 1.1.1.69 2016/11/01 14:51:54 udo
+ * *** empty log message ***
+ * Revision 1.1.1.68 2016/11/01 09:24:01 martin
+ * *** empty log message ***
+ * Revision 1.1.1.67 2016/10/25 07:48:27 martin
+ * Doxygen fixes.
+ * Revision 1.1.1.66 2016/10/21 09:39:25 thomas-b
+ * Added struct ALL_XBP_INFO and appropriate free function
+ * Revision 1.1.1.65 2016/10/14 11:10:02 thomas-b
+ * Added ALL_UCAP_NET_INFO and the appropriate free function
+ * Revision 1.1.1.64 2016/09/28 15:04:02 thomas-b
+ * Added function to check whether NET_CFG_API stage 2 is supported
+ * Revision 1.1.1.63 2016/07/26 08:07:10 philipp
+ * Fixed compiler errors (name clash, syntax error)
+ * Revision 1.1.1.62 2016/07/15 14:09:48 martin
+ * Use functions from new module timeutil.
+ * Revision 1.1.1.61 2016/06/21 13:51:23 philipp
+ * Fixed nasty segfault due to pointer corruption
+ * Revision 1.1.1.60 2016/06/21 12:06:59 thomas-b
+ * Added function calloc_ucap_entry
+ * Revision 1.1.1.59 2016/06/21 10:25:30 philipp
+ * Freeing ucap entry list is now portable
+ * Revision 1.1.1.58 2016/06/21 07:39:21 philipp
+ * Use mbg_klist for ucap events and not an array -> Easier to handle MAX_UCAP_ENTRIES
+ * Revision 1.1.1.57 2016/06/16 07:46:45 philipp
+ * Fixed checking flags for IMS sensor specific features
+ * Revision 1.1.1.56 2016/06/15 14:04:27 thomas-b
+ * Added ALL_UCAP_INFO structure and function free_all_ucap_info
+ * Revision 1.1.1.55 2016/06/03 09:00:13 thomas-b
+ * tm structure does not have gmtoff field under Windows
+ * Revision 1.1.1.54 2016/06/02 10:24:22 philipp
+ * Renaming all revision macros and helper functions
+ * Revision 1.1.1.53 2016/05/27 07:27:43 philipp
+ * Fixed (potential) memleak
+ * Revision 1.1.1.52 2016/05/27 05:48:08 philipp
+ * Refactoring to support XMR_METRICS properly
+ * Revision 1.1.1.51 2016/05/26 11:01:09 thomas-b
+ * Removed info structures from ALL_NTP_STATUS
+ * Moved check functions of specific features to cfg_hlp
+ * Revision 1.1.1.50 2016/05/25 08:43:35 philipp
+ * Redesign of ALL_[xxx]_[XXX] structures and (helper) functions
+ * Revision 1.1.1.49 2016/05/23 09:37:40 philipp
+ * Extended ALL_XMULTI_REF_STATUS by holdover_status
+ * Revision 1.1.1.48 2016/05/23 08:59:03 philipp
+ * New function free_all_gpio_state
+ * Revision 1.1.1.47 2016/05/23 08:24:37 philipp
+ * New function free_all_ims_state
+ * Revision 1.1.1.46 2016/05/11 13:20:55 thomas-b
+ * Added ALL_NET_STATUS_INFO and the appropriate free function
+ * Revision 1.1.1.45 2016/04/26 14:21:58 thomas-b
+ * Renamed ALL_NET_CFG_INFO structure members
+ * Revision 1.1.1.44 2016/04/26 13:45:36 martin
+ * Tried portable printing of int64_t types.
+ * Revision 1.1.1.43 2016/04/26 08:40:17Z philipp
+ * Fixed compiler warning due to invalid format specifier
+ * Revision 1.1.1.42 2016/04/26 08:23:45 thomas-b
+ * Extended ALL_NET_CFG_INFO by DNS configurations
+ * Revision 1.1.1.41 2016/04/26 06:29:27 thomas-b
+ * Added ALL_NET_CFG_INFO for network configuration
+ * Revision 1.1.1.40 2016/04/25 14:55:32 martin
+ * *** empty log message ***
+ * Revision 1.1.1.39 2016/04/25 14:42:18 martin
+ * *** empty log message ***
+ * Revision 1.1.1.38 2016/04/25 11:22:41 martin
+ * Revision 1.1.1.37 2016/04/25 09:01:29Z martin
+ * *** empty log message ***
+ * Revision 1.1.1.36 2016/04/22 07:11:50 philipp
+ * Use pointer to pointer in get_all_* functions
+ * Revision 1.1.1.35 2016/04/20 14:45:46 thomas-b
+ * Renamed ALL_NTP_STATE_INFO to ALL_NTP_STATUS
+ * Revision 1.1.1.34 2016/04/20 13:49:12 thomas-b
+ * Added structure definitions and free functions for NTP
+ * Revision 1.1.1.33 2016/04/20 12:37:53 thomas-b
+ * Moved free functions for ALL_XMULTI_REF_INFO and ALL_XMULTI_REF_STATUS to cfg_hlp
+ * Revision 1.1.1.32 2016/04/08 07:54:17 philipp
+ * Added function mbg_print_ext_rev_info
+ * Revision 1.1.1.31 2016/04/07 08:07:38 philipp
+ * Added function normalize_nano_time_64 (Clemens)
+ * Revision 1.1.1.30 2016/04/04 15:08:45 martin
+ * Replaced chk_model_is_vsg() by xdevfeat::xdevfeat_is_vsg().
+ * Revision 1.1.1.29 2016/03/03 11:16:50 martin
+ * Utility functions to alloc and free memory for hardware ID.
+ * Revision 1.1.1.28 2016/02/17 12:00:06Z gregoire
+ * new function chk_model_is_vsg
+ * Revision 1.1.1.27 2015/11/24 13:12:04Z philipp
+ * Extended / modified TLV functions
+ * Revision 1.1.1.26 2015/11/23 14:15:40 philipp
+ * Moved TLV related initializing functions to here
+ * Revision 1.1.1.25 2015/10/30 15:33:48 martin
+ * Revision 1.1.1.24 2015/10/27 16:17:32Z martin
+ * *** empty log message ***
+ * Revision 1.1.1.23 2015/10/26 16:31:52 martin
+ * *** empty log message ***
+ * Revision 1.1.1.22 2015/10/26 13:36:44 martin
+ * Revision 1.1.1.21 2015/10/15 12:49:09Z marvin
+ * Revision 1.1.1.20 2015/10/12 10:01:59Z martin
+ * *** empty log message ***
+ * Revision 1.1.1.19 2015/10/09 11:09:13 martin
+ * *** empty log message ***
+ * Revision 1.1.1.18 2015/10/08 10:32:16 martin
+ * *** empty log message ***
+ * Revision 1.1.1.17 2015/10/08 09:30:34 martin
+ * *** empty log message ***
+ * Revision 1.1.1.16 2015/10/07 16:03:19 martin
+ * *** empty log message ***
+ * Revision 1.1.1.15 2015/10/07 09:59:00 martin
+ * More common GNSS support.
+ * Revision 1.1.1.14 2015/10/05 13:29:45 martin
+ * Revision 1.1.1.13 2015/10/01 10:58:35Z thomas-b
+ * fixed call of mbgmktm with correct month and day values in nano_time_64_to_tm_gps
+ * Revision 1.1.1.12 2015/09/15 09:11:13 martin
+ * Moved some functions into a _PRELIMINARY_CODE section.
+ * Revision 1.1.1.11 2015/09/14 08:56:05 thomas-b
+ * Sustract 1900 from year when calling mbg_mktime
+ * Revision 1.1.1.10 2015/09/14 07:34:08 thomas-b
+ * Added missing includes of time.h and mbgmktm.h
+ * Revision 1.1.1.9 2015/09/11 12:09:04 thomas-b
+ * Added nano_time_64_to_tm_gps and tm_gps_to_nano_time_64 functions
+ * Revision 1.1.1.8 2015/08/31 14:55:11 martin
+ * Moved string trim functions to str_util module.
+ * Revision 1.1.1.7 2015/08/31 13:41:56 martin
+ * Revision 1.1.1.6 2014/10/29 16:25:31 martin
+ * Moved some functions and structures to more convenient files.
+ * Revision 1.1.1.5 2014/10/14 10:20:18 martin
+ * Revision 1.1.1.4 2014/10/14 10:05:10 martin
+ * Revision 1.1.1.3 2014/09/26 11:43:24Z martin
+ * Revision 1.1.1.2 2014/07/22 13:05:34 martin
+ * Revision 1.1.1.1 2014/04/28 12:29:45Z martin
+ * Revision 1.1 2014/04/25 09:14:49 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#define _CFG_HLP
+ #include <cfg_hlp.h>
+#undef _CFG_HLP
+
+#include <mbgerror.h>
+#include <timeutil.h>
+#include <str_util.h>
+#include <myutil.h>
+#include <mbgtime.h>
+
+#if defined( _PRELIMINARY_CODE )
+ #include <mbgmktm.h>
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <time.h>
+
+
+#if !defined( MBG_TGT_MISSING_64_BIT_TYPES )
+
+/*HDR*/
+/**
+ * @brief Normalize a ::NANO_TIME_64 struct
+ *
+ * After normalization, the following can be assumed:<br>
+ * - nano_secs is in the range [-10^9 + 1, 10^9 - 1]<br>
+ * - if secs is not 0, secs and nano_secs have the same sign
+ *
+ * @param[in,out] nt The NANO_TIME_64 to be normalized
+ */
+void normalize_nano_time_64( NANO_TIME_64 *nt )
+{
+ int64_t additional_secs;
+
+ // Step 1: Make sure nano seconds are in the interval [-10^9 + 1, 10^9 - 1]
+ additional_secs = nt->nano_secs / NSECS_PER_SEC;
+ nt->nano_secs -= additional_secs * NSECS_PER_SEC;
+ nt->secs += additional_secs;
+
+ // Step 2: Make sure seconds and nanoseconds have same sign if seconds is not 0
+ if ( nt->secs > 0 && nt->nano_secs < 0 )
+ {
+ nt->secs -= 1;
+ nt->nano_secs += NSECS_PER_SEC;
+ }
+ else if ( nt->secs < 0 && nt->nano_secs > 0 )
+ {
+ nt->secs += 1;
+ nt->nano_secs -= NSECS_PER_SEC;
+ }
+
+} // normalize_nano_time_64
+
+#endif // !defined( MBG_TGT_MISSING_64_BIT_TYPES )
+
+
+
+#if !defined( MBG_TGT_MISSING_64_BIT_TYPES )
+
+/*HDR*/
+/**
+ * @brief Print a normalized ::NANO_TIME_64 into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] nt The ::NANO_TIME_64 to be printed
+ */
+size_t snprint_nano_time_64( char *s, size_t max_len, const NANO_TIME_64 *nt )
+{
+ size_t n = snprintf_safe( s, max_len, "%c%" PRId64 ".%09" PRId64,
+ _nano_time_negative( nt ) ? '-' : '+',
+ _abs64( nt->secs ),
+ _abs64( nt->nano_secs ) );
+ return n;
+
+} // snprint_nano_time_64
+
+#endif // !defined( MBG_TGT_MISSING_64_BIT_TYPES )
+
+
+
+/*HDR*/
+/**
+ * @brief Print nano time into string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] nt The ::NANO_TIME to be printed
+ */
+size_t snprint_nano_time( char *s, size_t max_len, const NANO_TIME *nt )
+{
+ size_t n = snprintf_safe( s, max_len, "%c%li.%09li",
+ _nano_time_negative( nt ) ? '-' : '+',
+ labs( (long) nt->secs ),
+ labs( (long) nt->nano_secs ) );
+ return n;
+
+} // snprint_nano_time
+
+
+
+#if defined( _PRELIMINARY_CODE )
+
+//### TODO: eventually move these functions to a different module
+
+#if !defined( MBG_TGT_MISSING_64_BIT_TYPES )
+
+/*HDR*/
+/**
+ * @brief Convert ::NANO_TIME_64 to ::TM_GPS
+ *
+ * @param[out] tm_gps The ::TM_GPS to be filled
+ * @param[in] nt The ::NANO_TIME_64 to be converted
+ *
+ * @return 1 on success, 0 on error
+ *
+ * @see ::tm_gps_to_nano_time_64
+ */
+int nano_time_64_to_tm_gps( TM_GPS *tm_gps, const NANO_TIME_64 *nt )
+{
+ struct tm tm = { 0 };
+ time_t t = cvt_to_time_t( nt->secs );
+ int rc = mbg_gmtime( &tm, &t );
+
+ if ( mbg_rc_is_success( rc ) )
+ {
+ tm_gps->year = tm.tm_year + 1900;
+ tm_gps->month = tm.tm_mon + 1;
+ tm_gps->mday = tm.tm_mday;
+ tm_gps->yday = tm.tm_yday;
+ tm_gps->wday = tm.tm_wday;
+ tm_gps->hour = tm.tm_hour;
+ tm_gps->min = tm.tm_min;
+ tm_gps->sec = tm.tm_sec;
+ tm_gps->frac = 0; //### TODO convert fractions
+#if defined( MBG_TGT_POSIX )
+ tm_gps->offs_from_utc = tm.tm_gmtoff; //### TODO Is tm.tm_gmtoff even valid?
+#endif
+ return 1; //### TODO return MBG_SUCCESS
+ }
+
+ return 0; //### TODO return rc
+
+} // nano_time_64_to_tm_gps
+
+
+
+/*HDR*/
+/**
+ * @brief Convert ::TM_GPS to ::NANO_TIME_64
+ *
+ * @param[out] nt The ::NANO_TIME_64 to be filled
+ * @param[in] tm The ::TM_GPS to be converted
+ *
+ * @return 1 on success, 0 on error
+ *
+ * @see ::nano_time_64_to_tm_gps
+ */
+int tm_gps_to_nano_time_64( NANO_TIME_64 *nt, const TM_GPS *tm )
+{
+ time_t t = mbg_mktime( tm->year - 1900, tm->month - 1, tm->mday - 1, tm->hour, tm->min, tm->sec );
+
+ if ( t != (time_t) -1 )
+ {
+ nt->secs = (uint64_t) t;
+ nt->nano_secs = 0; //### TODO: convert fractions
+ return 1;
+ }
+
+ return 0;
+
+} // tm_gps_to_nano_time_64
+
+#endif // !defined( MBG_TGT_MISSING_64_BIT_TYPES )
+
+#endif // defined( _PRELIMINARY_CODE )
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a software revision name should be displayed
+ *
+ * The software revision name is usually empty, except if the
+ * firmware is a customized version, in which case the field
+ * contains an identifier string.
+ *
+ * There are some standard firmware versions where this string
+ * is not empty but padded with spaces, etc., so we try to
+ * clean this up and display the string properly, if appropriate.
+ *
+ * @param[in,out] p The ::SW_REV name to check
+ * @param[in] verbose The app's verbosity level
+ *
+ * @return != 0 if SW name should be displayed
+ */
+int chk_sw_rev_name( SW_REV *p, int verbose )
+{
+ if ( verbose > 1 ) // more than just verbose
+ return 1; // just return raw string
+
+ trim_whitespace( p->name );
+
+ // Some firmware versions have "CC_STANDARD" in their standard version,
+ // which doesn't provide any valuable information.
+ // We discard this by default.
+ if ( strstr( p->name, "CC_STANDARD" ) )
+ p->name[0] = 0;
+
+ if ( verbose )
+ return 1; // calling app should display string, even if empty
+
+ // calling app should display string only if not empty
+ return strlen( p->name ) != 0;
+
+} // chk_sw_rev_name
+
+
+
+/*HDR*/
+int get_str_idx( const char *search,
+ const char *str_table[],
+ int n_entries )
+{
+ int i;
+
+ for ( i = 0; i < n_entries; i++ )
+ if ( strcmp( search, str_table[i] ) == 0 )
+ return i;
+
+ return -1;
+
+} // get_str_idx
+
+
+
+/*HDR*/
+int get_baud_rate_idx( BAUD_RATE baud_rate )
+{
+ int i;
+
+ for ( i = 0; i < N_MBG_BAUD_RATES; i++ )
+ if ( baud_rate == mbg_baud_rate[i] )
+ return i;
+
+ return -1;
+
+} // get_baud_rate_idx
+
+
+
+/*HDR*/
+int get_framing_idx( const char *framing )
+{
+ return get_str_idx( framing, mbg_framing_str, N_MBG_FRAMINGS );
+
+} // get_framing_idx
+
+
+
+/*HDR*/
+void port_settings_from_port_parm_mode(
+ PORT_SETTINGS *p_ps,
+ uint8_t pp_mode,
+ int str_type_cap
+ )
+{
+ if ( pp_mode >= STR_UCAP )
+ {
+ p_ps->str_type = str_type_cap;
+ p_ps->mode = ( pp_mode == STR_UCAP ) ? STR_AUTO : STR_ON_REQ;
+ }
+ else
+ {
+ p_ps->str_type = 0;
+ p_ps->mode = pp_mode;
+ }
+
+} // port_settings_from_port_parm_mode
+
+
+
+/*HDR*/
+void port_parm_mode_from_port_settings(
+ uint8_t *pp_mode,
+ const PORT_SETTINGS *p_ps,
+ int str_type_cap
+ )
+{
+ if ( p_ps->str_type == str_type_cap )
+ *pp_mode = ( p_ps->mode == STR_ON_REQ ) ? STR_UCAP_REQ : STR_UCAP;
+ else
+ *pp_mode = p_ps->mode;
+
+} // port_parm_mode_from_port_settings
+
+
+
+/*HDR*/
+void port_settings_from_port_parm(
+ PORT_SETTINGS *p_ps,
+ int port_num,
+ const PORT_PARM *p_pp,
+ int cap_str_idx
+)
+{
+ p_ps->parm = p_pp->com[port_num];
+
+ port_settings_from_port_parm_mode( p_ps, p_pp->mode[port_num],
+ cap_str_idx );
+
+} // port_info_from_port_parm
+
+
+
+/*HDR*/
+void port_parm_from_port_settings(
+ PORT_PARM *p_pp,
+ int port_num,
+ const PORT_SETTINGS *p_ps,
+ int cap_str_idx
+)
+{
+ p_pp->com[port_num] = p_ps->parm;
+
+ port_parm_mode_from_port_settings( &p_pp->mode[port_num],
+ p_ps, cap_str_idx );
+
+} // port_parm_from_port_settings
+
+
+
+/*HDR*/
+uint32_t check_valid_port_info( const PORT_INFO *p_pi,
+ const STR_TYPE_INFO_IDX str_type_info_idx[],
+ int n_str_type )
+{
+ const PORT_SETTINGS *p_ps = &p_pi->port_settings;
+ int idx;
+ uint32_t flags = 0;
+
+
+ if ( p_pi->supp_baud_rates & ~_mask( N_MBG_BAUD_RATES ) )
+ flags |= MBG_PS_MSK_BAUD_RATE_OVR_SW; // dev. supports more baud rates than driver
+
+ idx = get_baud_rate_idx( p_ps->parm.baud_rate );
+
+ if ( !_inrange( idx, 0, N_MBG_BAUD_RATES ) ||
+ !_is_supported( idx, p_pi->supp_baud_rates ) )
+ flags |= MBG_PS_MSK_BAUD_RATE;
+
+
+ if ( p_pi->supp_framings & ~_mask( N_MBG_FRAMINGS ) )
+ flags |= MBG_PS_MSK_FRAMING_OVR_SW; // dev. supports more framings than driver
+
+ idx = get_framing_idx( p_ps->parm.framing );
+
+ if ( !_inrange( idx, 0, N_MBG_FRAMINGS ) ||
+ !_is_supported( idx, p_pi->supp_framings ) )
+ flags |= MBG_PS_MSK_FRAMING;
+
+
+ if ( p_ps->parm.handshake >= N_COM_HS )
+ flags |= MBG_PS_MSK_HS_OVR_SW; // handshake index exceeds max.
+
+ if ( p_ps->parm.handshake != HS_NONE ) // currently no device supports any handshake
+ flags |= MBG_PS_MSK_HS; // handshake mode not supp. by dev.
+
+
+ if ( p_pi->supp_str_types & ~_mask( n_str_type ) )
+ flags |= MBG_PS_MSK_STR_TYPE_OVR_SW; // firmware error: more string types supported than reported
+
+ idx = p_ps->str_type;
+
+ if ( idx >= n_str_type )
+ flags |= MBG_PS_MSK_STR_TYPE_OVR_DEV; // string type index exceeds max.
+ else
+ {
+ if ( !_is_supported( idx, p_pi->supp_str_types ) )
+ flags |= MBG_PS_MSK_STR_TYPE; // string type not supported by this port
+ else
+ {
+ // Use the str_type index to get the supported output mode mask
+ // from the string type info table. This is required to check
+ // whether the selected mode is supported by the selected
+ // string type.
+ ulong supp_modes = str_type_info_idx[idx].str_type_info.supp_modes;
+
+ if ( supp_modes & ~_mask( N_STR_MODE ) )
+ flags |= MBG_PS_MSK_STR_MODE_OVR_SW; // dev. supports more string modes than driver
+
+ idx = p_ps->mode;
+
+ if ( idx >= N_STR_MODE ) // mode is always >= 0
+ flags |= MBG_PS_MSK_STR_MODE_OVR_SW; // string mode index exceeds max.
+ else
+ if ( !_is_supported( idx, supp_modes ) )
+ flags |= MBG_PS_MSK_STR_MODE; // string mode not supp. by this string type and port
+ }
+ }
+
+
+ if ( p_ps->flags != 0 ) /* currently always 0 */
+ flags |= MBG_PS_MSK_FLAGS_OVR_SW | MBG_PS_MSK_FLAGS;
+
+
+ return flags;
+
+} // check_valid_port_info
+
+
+
+/*HDR*/
+int valid_port_info( const PORT_INFO *p_pi,
+ const STR_TYPE_INFO_IDX str_type_info_idx[],
+ int n_str_type )
+{
+ return check_valid_port_info( p_pi, str_type_info_idx, n_str_type ) == 0;
+
+} // valid_port_info
+
+
+
+/*HDR*/
+int setup_port_info_from_port_settings( PORT_INFO_IDX pii[], const PORT_PARM *p_pp,
+ const RECEIVER_INFO *p_ri )
+{
+ int i;
+
+ for ( i = 0; i < p_ri->n_com_ports; i++ )
+ {
+ PORT_INFO_IDX *p_pii = &pii[i];
+ PORT_INFO *p_pi = &p_pii->port_info;
+
+ p_pii->idx = i;
+ port_settings_from_port_parm( &p_pi->port_settings, i, p_pp, 1 );
+
+ p_pi->supp_baud_rates = DEFAULT_GPS_BAUD_RATES_C166;
+ p_pi->supp_framings = DEFAULT_GPS_FRAMINGS_C166;
+ p_pi->supp_str_types = DEFAULT_SUPP_STR_TYPES_GPS;
+ }
+
+ return MBG_SUCCESS;
+
+} // setup_port_info_from_port_settings
+
+
+
+/*HDR*/
+int setup_default_str_type_info_idx( STR_TYPE_INFO_IDX stii[], const RECEIVER_INFO *p_ri )
+{
+ int i;
+
+ for ( i = 0; i < p_ri->n_str_type; i++ )
+ {
+ STR_TYPE_INFO_IDX *stip = &stii[i];
+ stip->idx = i;
+ stip->str_type_info = default_str_type_info[i];
+ }
+
+ return MBG_SUCCESS;
+
+} // setup_default_str_type_info_idx
+
+
+
+/*HDR*/
+int chk_set_n_gnss_supp( ALL_GNSS_INFO *p_agi )
+{
+ p_agi->n_gnss_supp = num_bits_set( p_agi->gnss_mode_info.supp_gnss_types );
+
+ if ( p_agi->n_gnss_supp > N_GNSS_TYPES )
+ return MBG_ERR_N_GNSS_EXCEEDS_SUPP;
+
+ return MBG_SUCCESS;
+
+} // chk_set_n_gnss_supp
+
+
+
+/*HDR*/
+/**
+ * @brief
+ *
+ * ### Setup GNSS info from stat_info so we can use the same printing routine
+ */
+void setup_gps_only_sat_info_idx_from_statinfo( ALL_GNSS_INFO *p_agi )
+{
+ STAT_INFO *p_si = &p_agi->stat_info;
+ GNSS_SAT_INFO_IDX *p_gsii = &p_agi->gnss_sat_info_idx[GNSS_TYPE_GPS];
+ GNSS_SAT_INFO *p_gsi = &p_gsii->gnss_sat_info;
+
+ memset( p_gsii, 0, sizeof( *p_gsii ) );
+ p_gsii->idx = GNSS_TYPE_GPS;
+
+ p_gsi->gnss_type = GNSS_TYPE_GPS;
+ p_gsi->svs_in_view = p_si->svs_in_view;
+ p_gsi->good_svs = p_si->good_svs;
+
+} // setup_gps_only_sat_info_idx_from_statinfo
+
+
+
+/*HDR*/
+/**
+ * @brief
+ *
+ * Setup GNSS info from stat_info so we can use the same printing routine
+ */
+int setup_gps_only_gnss_info_from_statinfo( ALL_GNSS_INFO *p_agi )
+{
+ MBG_GNSS_MODE_INFO *p_gmi = &p_agi->gnss_mode_info;
+
+ memset( p_gmi, 0, sizeof( *p_gmi ) );
+
+ p_gmi->supp_gnss_types = MBG_GNSS_TYPE_MSK_GPS;
+ p_gmi->settings.gnss_set = p_gmi->supp_gnss_types;
+
+ memset( p_agi->gnss_sat_info_idx, 0, sizeof( p_agi->gnss_sat_info_idx ) );
+
+ setup_gps_only_sat_info_idx_from_statinfo( p_agi );
+
+ return chk_set_n_gnss_supp( p_agi );
+
+} // setup_gps_only_gnss_info_from_statinfo
+
+
+
+/*HDR*/
+void chk_free_dev_hw_id( DEVICE_INFO *p )
+{
+ if ( p->hw_id )
+ {
+ free( p->hw_id );
+ p->hw_id = NULL;
+ }
+
+} // chk_free_dev_hw_id
+
+
+
+/*HDR*/
+int alloc_dev_hw_id( DEVICE_INFO *p, size_t len )
+{
+ if ( p->hw_id )
+ return MBG_ERR_ALREADY_ALLOC;
+
+
+ p->hw_id = (char *) malloc( len );
+
+ if ( p->hw_id == NULL )
+ return MBG_ERR_NO_MEM;
+
+ return MBG_SUCCESS;
+
+} // alloc_dev_hw_id
+
+
+
+/*HDR*/
+const char *get_fw_id_from_hw_id( const char *hw_id )
+{
+ int i;
+
+ for ( i = 0; i < N_SUPP_DEV_TOTAL; i++ )
+ {
+ DEVICE_INFO *p = &device_list[i];
+
+ if ( strlen( p->fw_id ) && p->hw_id ) //### TODO check if this still works as expected
+ {
+ if ( strcmp( hw_id, p->hw_id ) == 0 )
+ {
+ if ( strlen( p->fw_id ) > 0 )
+ return p->fw_id;
+
+ #if defined( DEBUG )
+ fprintf( stderr, "Length of fw_id is 0 in %s for device %i (%s)\n",
+ __func__, i, p->hw_id );
+ #endif
+ }
+ }
+ }
+
+ return NULL;
+
+} // get_fw_id_from_hw_id
+
+
+
+/*HDR*/
+const char *get_hw_id_from_fw_id( const char *fw_id )
+{
+ int i;
+
+ for ( i = 0; i < N_SUPP_DEV_TOTAL; i++ )
+ {
+ DEVICE_INFO *p = &device_list[i];
+
+ if ( strlen( p->fw_id ) && p->hw_id ) //### TODO check if this still works as expected
+ {
+ if ( strcmp( fw_id, p->fw_id ) == 0 )
+ {
+ if ( strlen( p->hw_id ) > 0 )
+ return p->hw_id;
+
+ #if defined( DEBUG )
+ fprintf( stderr, "Length of hw_id is 0 in %s for device %i (%s)\n",
+ __func__, i, p->fw_id );
+ #endif
+ }
+ }
+ }
+
+ return NULL;
+
+} // get_hw_id_from_fw_id
+
+
+
+/*HDR*/
+/**
+ * @brief Returns the currently used ::MBG_IO_PORT_TYPE_INFO_IDX for the appropriate ::MBG_IO_PORT_INFO_IDX
+ *
+ * @param[in] all_io_port_info Pointer to the ::ALL_IO_PORT_INFO, containing the current configuration
+ * @param[in] io_port_info_idx Pointer to the ::MBG_IO_PORT_INFO_IDX, for which the ::MBG_IO_PORT_TYPE_INFO_IDX shall be found
+ *
+ * @return Pointer to the found ::MBG_IO_PORT_TYPE_INFO_IDX or NULL
+ *
+ */
+MBG_IO_PORT_TYPE_INFO_IDX *get_io_port_type_info_idx(ALL_IO_PORT_INFO *all_io_port_info, MBG_IO_PORT_INFO_IDX *io_port_info_idx)
+{
+ uint8_t i;
+
+ if(!all_io_port_info || !io_port_info_idx)
+ return NULL;
+
+ for(i = 0; i < io_port_info_idx->info.num_types; ++i)
+ {
+ if(all_io_port_info->pt_infos[io_port_info_idx->idx][i].info.port_type == io_port_info_idx->info.settings.type)
+ {
+ if(all_io_port_info->pt_infos[io_port_info_idx->idx][i].info.port_type == MBG_IO_PORT_TYPE_GPIO)
+ {
+ if(all_io_port_info->pt_infos[io_port_info_idx->idx][i].info.data.gpio_limits.type == io_port_info_idx->info.settings.data.gpio_settings.type)
+ return &all_io_port_info->pt_infos[io_port_info_idx->idx][i];
+ }
+ else return &all_io_port_info->pt_infos[io_port_info_idx->idx][i];
+ }
+ }
+
+ return NULL;
+
+}
+
+
+
+/*HDR*/
+/**
+ * @brief Initializes a ::MBG_TLV_ANNOUNCE structure
+ *
+ * @param[out] tlv Pointer to a ::MBG_TLV_ANNOUNCE structure
+ * @param[in] uid Unique sender ID used as identifier with all
+ * subsequent messages related to this transaction.
+ * @param[in] tlv_feat_type One of the ::MBG_TLV_FEAT_TYPES
+ * @param[in] total_bytes Total number of bytes of all upcoming TLVs
+ */
+void mbg_tlv_announce_init( MBG_TLV_ANNOUNCE *tlv, MBG_TLV_UID uid,
+ MBG_TLV_TYPE tlv_feat_type, uint32_t total_bytes )
+{
+ memset( tlv, 0, sizeof( *tlv ) );
+ tlv->data.uid = uid;
+ tlv->data.type = tlv_feat_type;
+ tlv->data.total_bytes = total_bytes;
+ tlv->data.reserved_1 = 0;
+ tlv->reserved_1 = 0;
+ tlv->reserved_2 = 0;
+
+} // mbg_tlv_announce_init
+
+
+
+/*HDR*/
+/**
+ * @brief Initializes a ::MBG_TLV
+ *
+ * @param[out] tlv Pointer to a valid ::MBG_TLV structure
+ * @param[in] uid Unique sender ID used as identifier for each further
+ * TLV message related to this type.
+ * @param[in] tlv_type Type identifier, see ::MBG_TLV_TYPES
+ * @param[in] total_bytes Total number of bytes belonging to this
+ * TLV transaction (which is very likely split into several TLVs)
+ */
+void mbg_tlv_init( MBG_TLV *tlv, MBG_TLV_UID uid,
+ MBG_TLV_TYPE tlv_type, uint32_t total_bytes )
+{
+ memset( tlv, 0, sizeof( *tlv ) );
+ tlv->hdr.uid = uid;
+ tlv->hdr.tlv_type = tlv_type;
+ tlv->hdr.cur_bytes = 0;
+ tlv->hdr.trans_bytes = 0;
+ tlv->hdr.total_bytes = total_bytes;
+ tlv->hdr.reserved_1 = 0;
+ tlv->hdr.reserved_2 = 0;
+ tlv->hdr.reserved_3 = 0;
+
+} // mbg_tlv_init
+
+
+
+/*HDR*/
+/**
+ * @brief Initializes ::MBG_TLV_RCV_STATE structure
+ *
+ * @param[in,out] state Pointer to ::MBG_TLV_RCV_STATE structure
+ * @param[in] uid Unique sender ID used as identifier for each further
+ * TLV message related to this type.
+ * @param[in] total_bytes Total number of bytes belonging to this
+ * TLV transaction (which is very likely split into several TLVS)
+ */
+void mbg_tlv_rcv_state_init( MBG_TLV_RCV_STATE *state, MBG_TLV_UID uid, uint32_t total_bytes )
+{
+ state->data.uid = uid;
+ state->data.type = 0;
+ state->data.total_bytes = total_bytes;
+ state->data.reserved_1 = 0;
+ state->read_bytes = 0;
+ state->reserved_1 = 0;
+
+} // mbg_tlv_state_init
+
+
+
+/*HDR*/
+size_t mbg_snprint_revision( char *buf, size_t buflen,
+ const char *prefix, const char *suffix,
+ uint32_t rev)
+{
+ size_t bytes = 0;
+ uint32_t major, minor, patch;
+
+ if ( prefix )
+ bytes += snprintf_safe( &buf[bytes], buflen, "%s", prefix );
+
+ _mbg_decode_revision( rev, major, minor, patch );
+ bytes += snprintf_safe( &buf[bytes], buflen - bytes, "%u.%u.%u",
+ major, minor, patch);
+
+ if ( suffix )
+ bytes += snprintf_safe( &buf[bytes], buflen - bytes, "%s", suffix );
+
+ return bytes;
+
+} // mbg_snprint_revision
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_xbp_supp_nodes( const ALL_XBP_INFO *info )
+{
+ if ( info )
+ {
+ if ( ( info->limits.features & XBP_FEAT_MASK_NODES ) == XBP_FEAT_MASK_NODES )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+ }
+
+ return MBG_ERR_INV_PARM;
+
+} // chk_dev_xbp_supp_nodes
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_net_cfg_supp_stage_2( const ALL_NET_CFG_INFO *info )
+{
+ if ( info->glb_cfg_info.feat_flags & MBG_NET_GLB_SUPP_STAGE_2_MASK )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_net_cfg_supp_stage_2
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_ntp_supp_client( const ALL_NTP_CFG_INFO *info )
+{
+ if ( ( ( info->glb_info.supp_ntp_roles & NTP_MSK_ROLE_CLIENT ) == NTP_MSK_ROLE_CLIENT ) ||
+ ( ( info->glb_info.supp_ntp_roles & NTP_MSK_ROLE_CLIENT_SERVER ) == NTP_MSK_ROLE_CLIENT_SERVER ) )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_ntp_supp_client
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_ntp_supp_server( const ALL_NTP_CFG_INFO *info )
+{
+ if ( ( ( info->glb_info.supp_ntp_roles & NTP_MSK_ROLE_SERVER ) == NTP_MSK_ROLE_SERVER ) ||
+ ( ( info->glb_info.supp_ntp_roles & NTP_MSK_ROLE_CLIENT_SERVER ) == NTP_MSK_ROLE_CLIENT_SERVER ) )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_ntp_supp_server
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_mrf_none( const ALL_XMULTI_REF_INFO *info )
+{
+ if ( ( info->instances.flags & XMRIF_MSK_MRF_NONE_SUPP ) == XMRIF_MSK_MRF_NONE_SUPP )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_xmulti_ref_supp_mrf_none
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_ext_src_info( const ALL_XMULTI_REF_INFO *info )
+{
+ if ( ( info->instances.flags & XMRIF_MSK_EXT_SRC_INFO_SUPP ) == XMRIF_MSK_EXT_SRC_INFO_SUPP )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_xmulti_ref_supp_ext_src_info
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_holdover_status( const ALL_XMULTI_REF_INFO *info )
+{
+ if ( ( info->instances.flags & XMRIF_MSK_HOLDOVER_STATUS_SUPP ) == XMRIF_MSK_HOLDOVER_STATUS_SUPP )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_xmulti_ref_supp_holdover_status
+
+
+/*HDR*/
+/*
+ * Type is NOT an index of ::XMULTI_REF_INSTANCES::n_xmr_settings,
+ * but of ::MULTI_REF_TYPES.
+ * Depends on chk_dev_supp_xmulti_ref_ext_src_info.
+ * @see chk_dev_supp_xmulti_ref_ext_src_info
+ */
+_NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_ext_source_stats( const ALL_XMULTI_REF_INFO *info, int type )
+{
+ if (
+ ( type < N_MULTI_REF ) &&
+ (( info->ext_src_infos[type].info.feat_flags & XMR_EXT_SRC_FEAT_FLAG_MSK_STATS ) == XMR_EXT_SRC_FEAT_FLAG_MSK_STATS )
+ ) return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_xmulti_ref_supp_ext_source_stats
+
+
+/*HDR*/
+/*
+ * Type is NOT an index of ::XMULTI_REF_INSTANCES::n_xmr_settings,
+ * but of ::MULTI_REF_TYPES.
+ * Depends on chk_dev_supp_xmulti_ref_ext_src_info.
+ * @see chk_dev_supp_xmulti_ref_ext_src_info
+ */
+_NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_ext_source_metrics( const ALL_XMULTI_REF_INFO *info, int type )
+{
+ if (
+ ( type < N_MULTI_REF ) &&
+ (( info->ext_src_infos[type].info.feat_flags & XMR_EXT_SRC_FEAT_FLAG_MSK_METRICS ) == XMR_EXT_SRC_FEAT_FLAG_MSK_METRICS )
+ ) return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_xmulti_ref_supp_ext_source_metrics
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_ims_has_fdm( const ALL_IMS_INFO *info )
+{
+ if ( ( info->state.flags & MBG_IMS_STATE_FLAG_MSK_HAS_FDM ) == MBG_IMS_STATE_FLAG_MSK_HAS_FDM )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_ims_has_fdm
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_ims_is_volt_out_enabled( const ALL_IMS_STATE *ims_state, unsigned idx )
+{
+ const MBG_IMS_SENSOR_STATE *sstate = &ims_state->sensor_state_idx[idx].state;
+
+ if (
+ ( sstate->type == MBG_IMS_SENSOR_VOLTAGE ) &&
+ ( ( sstate->flags & MBG_IMS_SENSOR_VOLTAGE_OUT_ENB ) == MBG_IMS_SENSOR_VOLTAGE_OUT_ENB )
+ ) return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_ims_is_volt_out_enabled
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_ims_is_volt_out_overload( const ALL_IMS_STATE *ims_state, unsigned idx )
+{
+ const MBG_IMS_SENSOR_STATE *sstate = &ims_state->sensor_state_idx[idx].state;
+
+ if (
+ ( sstate->type == MBG_IMS_SENSOR_VOLTAGE ) &&
+ ( ( sstate->flags & MBG_IMS_SENSOR_VOLTAGE_OUT_OVR ) == MBG_IMS_SENSOR_VOLTAGE_OUT_OVR )
+ ) return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_ims_is_volt_out_overload
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_ims_is_pll_locked( const ALL_IMS_STATE *ims_state, unsigned idx )
+{
+ const MBG_IMS_SENSOR_STATE *sstate = &ims_state->sensor_state_idx[idx].state;
+
+ if (
+ ( sstate->type == MBG_IMS_SENSOR_PLL ) &&
+ ( ( sstate->flags & MBG_IMS_SENSOR_PLL_LOCKED ) == MBG_IMS_SENSOR_PLL_LOCKED )
+ ) return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_ims_is_pll_locked
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_gpio_supp_ass_idx( const ALL_GPIO_INFO *gpio_info, unsigned idx )
+{
+ const MBG_GPIO_LIMITS *limits = &gpio_info->infos[idx].info.limits;
+
+ if ( ( limits->supp_flags & MSK_MBG_GPIO_DEPENDS_ON_ASS_IO_IDX ) == MSK_MBG_GPIO_DEPENDS_ON_ASS_IO_IDX )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_gpio_supp_ass_idx
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _MBG_API chk_dev_gpio_dep_on_ass_idx( const ALL_GPIO_INFO *gpio_info, unsigned idx )
+{
+ const MBG_GPIO_SETTINGS *settings = &gpio_info->infos[idx].info.settings;
+
+ if ( ( settings->flags & MSK_MBG_GPIO_DEPENDS_ON_ASS_IO_IDX ) == MSK_MBG_GPIO_DEPENDS_ON_ASS_IO_IDX )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_gpio_dep_on_ass_idx
+
+
+/*HDR*/
+/**
+ * @brief Checks whether GPIO supports status function
+ *
+ * @param[out] info Pointer to a ::ALL_GPIO_INFO structure to be filled up
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_gpio
+ * @see ::mbg_chk_dev_supp_gpio
+ * @see ::free_all_gpio_info
+ */
+_NO_MBG_API_ATTR int _MBG_API chk_dev_gpio_has_status( const ALL_GPIO_INFO *info )
+{
+ if ( ( info->cfg_limits.flags & MBG_GPIO_CFG_LIMIT_FLAG_MASK_STATUS_SUPP ) == MBG_GPIO_CFG_LIMIT_FLAG_MASK_STATUS_SUPP )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_dev_gpio_has_status
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_XBP_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_XBP_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_xbp_info
+ */
+void free_all_xbp_info ( ALL_XBP_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->node_limits )
+ free( p->node_limits );
+
+ if ( p->node_infos )
+ free( p->node_infos );
+
+ free( p );
+ }
+
+} // free_all_xbp_info
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_NET_CFG_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_NET_CFG_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_net_cfg_info
+ */
+void free_all_net_cfg_info ( ALL_NET_CFG_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->link_infos )
+ free( p->link_infos );
+
+ if ( p->addr_infos )
+ free( p->addr_infos );
+
+ if ( p->dns_srvrs )
+ free( p->dns_srvrs );
+
+ if ( p->dns_srch_doms )
+ free( p->dns_srch_doms );
+
+ if ( p->route_infos )
+ free( p->route_infos );
+
+ free( p );
+ }
+
+} // free_all_net_cfg_info
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_NET_STATUS_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_NET_STATUS_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_net_status_info
+ */
+void free_all_net_status_info ( ALL_NET_STATUS_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->link_infos )
+ free( p->link_infos );
+
+ if ( p->addr_infos )
+ free( p->addr_infos );
+
+ if ( p->dns_srvrs )
+ free( p->dns_srvrs );
+
+ if ( p->dns_srch_doms )
+ free( p->dns_srch_doms );
+
+ if ( p->route_infos )
+ free( p->route_infos );
+
+ free( p );
+ }
+
+} // free_all_net_status_info
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_SNMP_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_SNMP_INFO structure, which will be freed
+ *
+ */
+void free_all_snmp_info ( ALL_SNMP_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->v12_infos )
+ free( p->v12_infos );
+
+ if ( p->v12_trap_infos )
+ free( p->v12_trap_infos );
+
+ if ( p->v3_infos )
+ free( p->v3_infos );
+
+ if ( p->v3_trap_infos )
+ free( p->v3_trap_infos );
+
+ free( p );
+ }
+
+} // free_all_snmp_info
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_MONITORING_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_MONITORING_INFO structure, which will be freed
+ *
+ */
+void free_all_monitoring_info ( ALL_MONITORING_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->all_snmp_info )
+ free_all_snmp_info( p->all_snmp_info );
+
+ if ( p->event_infos )
+ free( p->event_infos );
+
+ free ( p );
+ }
+}
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_MONITORING_STATUS structure
+ *
+ * @param[in] p Pointer to the ::ALL_MONITORING_STATUS structure, which will be freed
+ *
+ */
+void free_all_monitoring_status ( ALL_MONITORING_STATUS *p )
+{
+ if ( p )
+ {
+ if ( p->event_stati )
+ free( p->event_stati );
+
+ free ( p );
+ }
+}
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_XMULTI_REF_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_XMULTI_REF_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_xmulti_ref_info
+ * @see ::mbg_get_all_xmulti_ref_info
+ */
+void free_all_xmulti_ref_info( ALL_XMULTI_REF_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->infos )
+ free( p->infos );
+
+ if ( p->ext_src_infos )
+ free( p->ext_src_infos );
+
+ free ( p );
+ }
+
+} // free_all_xmulti_ref_info
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_XMULTI_REF_STATUS structure
+ *
+ * @param[in] p Pointer to the ::ALL_XMULTI_REF_STATUS structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_xmulti_ref_status
+ * @see ::mbg_get_all_xmulti_ref_status
+ */
+void free_all_xmulti_ref_status( ALL_XMULTI_REF_STATUS *p )
+{
+ if ( p )
+ {
+ if ( p->status )
+ free( p->status );
+
+ if ( p->holdover_status )
+ free( p->holdover_status );
+
+ if ( p->stats_idx )
+ free( p->stats_idx );
+
+ if ( p->metrics_idx )
+ free( p->metrics_idx );
+
+ free( p );
+ }
+
+} // free_all_xmulti_ref_status
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_PTP_V1_COMMON_DATASETS structure allocated by ::mbgextio_get_all_ptp_v1_common_datasets
+ *
+ * @param[in] p Pointer to the ::ALL_PTP_V1_COMMON_DATASETS structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ptp_v1_common_datasets
+ */
+void free_all_ptp_v1_common_datasets( ALL_PTP_V1_COMMON_DATASETS *p )
+{
+ if ( p )
+ {
+ if ( p->port_datasets )
+ free( p->port_datasets );
+
+ free( p );
+ }
+
+} // free_all_ptp_v1_common_datasets
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_PTP_V2_COMMON_DATASETS structure allocated by ::mbgextio_get_all_ptp_v2_common_datasets
+ *
+ * @param[in] p Pointer to the ::ALL_PTP_V2_COMMON_DATASETS structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ptp_v2_common_datasets
+ */
+void free_all_ptp_v2_common_datasets( ALL_PTP_V2_COMMON_DATASETS *p )
+{
+ if ( p )
+ {
+ if ( p->port_datasets )
+ free( p->port_datasets );
+
+ free( p );
+ }
+
+} // free_all_ptp_v2_common_datasets
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_NTP_CFG_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_NTP_CFG_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ntp_cfg_info
+ */
+void free_all_ntp_cfg_info( ALL_NTP_CFG_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->symm_key_limits )
+ free( p->symm_key_limits );
+
+ if ( p->symm_key_info_idx )
+ free( p->symm_key_info_idx );
+
+ if ( p->trusted_key_info_idx )
+ free( p->trusted_key_info_idx );
+
+ if ( p->clnt_info )
+ free( p->clnt_info );
+
+ if ( p->peer_settings_idx )
+ free( p->peer_settings_idx );
+
+ if ( p->srv_info )
+ free( p->srv_info );
+
+ if ( p->refclk_info_idx )
+ free( p->refclk_info_idx );
+
+ if ( p->misc_limits )
+ free( p->misc_limits );
+
+ if ( p->orphan_mode_info )
+ free( p->orphan_mode_info );
+
+ free( p );
+ }
+
+} // free_all_ntp_cfg_info
+
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_NTP_STATUS structure
+ *
+ * @param[in] p Pointer to the ::ALL_NTP_STATUS structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ntp_status
+ */
+void free_all_ntp_status( ALL_NTP_STATUS *p )
+{
+ if ( p )
+ {
+ if ( p->peer_states )
+ free( p->peer_states );
+
+ free( p );
+ }
+
+} // free_all_ntp_status
+
+
+
+/*HDR*/
+/**
+ * @brief Frees memory allocated by ::mbgextio_get_all_ims_info
+ *
+ * @param[in] p Pointer to the ::ALL_IMS_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_dev_has_ims
+ * @see ::mbgextio_dev_ims_has_fdm
+ * @see ::mbgextio_get_all_ims_info
+ * @see ::mbgextio_get_all_ims_state
+ */
+void free_all_ims_info( ALL_IMS_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->fdm_info )
+ free( p->fdm_info );
+
+ if ( p->fdm_limits )
+ free( p->fdm_limits );
+
+ if ( p->fdm_outinfo_idx )
+ free( p->fdm_outinfo_idx );
+
+ free( p );
+ }
+
+} // free_all_ims_info
+
+
+
+/*HDR*/
+/**
+ * @brief Frees memory allocated by ::mbgextio_get_all_ims_state
+ *
+ * @param[in] p Pointer to the ::ALL_IMS_STATE structure, which will be freed
+ *
+ * @see ::mbgextio_dev_has_ims
+ * @see ::mbgextio_dev_ims_has_fdm
+ * @see ::mbgextio_get_all_ims_info
+ * @see ::mbgextio_get_all_ims_state
+ */
+void free_all_ims_state( ALL_IMS_STATE *p )
+{
+ if ( p )
+ {
+ if ( p->sensor_state_idx )
+ free( p->sensor_state_idx );
+
+ if ( p->fdm_state )
+ free( p->fdm_state );
+
+ if ( p->fdm_output_state_idx )
+ free( p->fdm_output_state_idx );
+
+ free( p );
+ }
+
+} // free_all_ims_state
+
+
+
+/*HDR*/
+/**
+ * @brief Frees memory allocated by ::mbgextio_get_all_gpio_info
+ *
+ * @param[in] p Pointer to the ::ALL_GPIO_INFO structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_gpio
+ * @see ::mbgextio_get_all_gpio_info
+ */
+void free_all_gpio_info( ALL_GPIO_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->infos )
+ free( p->infos );
+
+ free( p );
+ }
+
+} // free_all_gpio_info
+
+
+
+/*HDR*/
+/**
+ * @brief Frees memory allocated by ::mbgextio_get_all_io_port_info
+ *
+ * @param[in] p Pointer to the ::ALL_IO_PORT_INFO structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_io_ports
+ * @see ::mbgextio_get_all_io_port_info
+ * @see ::mbgextio_get_all_io_port_status
+ * @see ::free_all_io_port_status
+ */
+void free_all_io_port_info( ALL_IO_PORT_INFO *p )
+{
+ uint8_t i;
+
+ if ( p )
+ {
+ if ( p->pt_infos )
+ {
+ for ( i = 0; i < p->limits.num_ports; ++i )
+ {
+ if ( p->pt_infos[i] )
+ free( p->pt_infos[i] );
+ }
+
+ free ( p->pt_infos );
+ }
+
+ if ( p->p_infos )
+ free( p->p_infos );
+
+ free( p );
+ }
+
+} // free_all_io_port_info
+
+
+
+/*HDR*/
+/**
+ * @brief Frees memory allocated by ::mbgextio_get_all_io_port_status
+ *
+ * @param[in] p Pointer to the ::ALL_IO_PORT_STATUS structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_io_ports
+ * @see ::mbgextio_get_all_io_port_info
+ * @see ::mbgextio_get_all_io_port_status
+ * @see ::free_all_io_port_info
+ */
+void free_all_io_port_status( ALL_IO_PORT_STATUS *p )
+{
+ if ( p )
+ {
+ if ( p->status )
+ free ( p->status );
+
+ free( p );
+ }
+
+} // free_all_io_port_status
+
+
+
+/*HDR*/
+/**
+ * @brief Frees memory allocated by ::mbgextio_get_all_gpio_state
+ *
+ * @param[in] p Pointer to the ::ALL_GPIO_STATE structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_gpio
+ * @see ::mbgextio_get_all_gpio_state
+ */
+void free_all_gpio_state( ALL_GPIO_STATE *p )
+{
+ if ( p )
+ {
+ if ( p->states )
+ free( p->states );
+
+ free( p );
+ }
+
+} // free_all_gpio_state
+
+
+
+/*HDR*/
+/**
+ * Allocates memory for a new ::UCAP_ENTRY structure
+ *
+ * @return The new allocated ::UCAP_ENTRY or NULL if the calloc call was not successful
+ */
+UCAP_ENTRY* calloc_ucap_entry( void )
+{
+ UCAP_ENTRY *entry = (UCAP_ENTRY *) calloc( 1, sizeof( *entry ) );
+ if ( entry )
+ {
+ mbg_klist_init(&entry->head);
+ }
+ return entry;
+
+} // calloc_ucap_entry
+
+
+/*HDR*/
+/**
+ * @brief Frees memory allocated by ::mbgextio_get_all_ucap_info
+ *
+ * @param[in] p Pointer to the ::ALL_UCAP_INFO structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_ucap
+ * @see ::mbg_chk_dev_has_ucap
+ * @see ::mbgextio_get_all_ucap_info
+ * @see ::mbg_get_all_ucap_info
+ */
+void free_all_ucap_info( ALL_UCAP_INFO *p )
+{
+ if ( p )
+ {
+ UCAP_ENTRY *entry;
+
+ while ( !mbg_klist_is_empty( &p->list ) )
+ {
+ entry = mbg_klist_first_entry( &p->list, UCAP_ENTRY, head );
+ mbg_klist_delete_item( &entry->head );
+ free( entry );
+ }
+
+ free( p );
+ }
+
+} // free_all_ucap_info
+
+
+/*HDR*/
+/**
+ * @brief Frees ::ALL_UCAP_NET_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_UCAP_NET_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ucap_net_info
+ */
+void free_all_ucap_net_info( ALL_UCAP_NET_INFO *p )
+{
+ if ( p )
+ {
+ if ( p->recv_infos )
+ free( p->recv_infos );
+
+ free( p );
+ }
+
+} // free_all_ucap_net_info
+
+
diff --git a/mbglib/common/cfg_hlp.h b/mbglib/common/cfg_hlp.h
index b7c4033..1ea7397 100755
--- a/mbglib/common/cfg_hlp.h
+++ b/mbglib/common/cfg_hlp.h
@@ -1,15 +1,213 @@
/**************************************************************************
*
- * $Id: cfg_hlp.h 1.2 2012/10/02 18:16:26 martin REL_M $
+ * $Id: cfg_hlp.h 1.3.1.101 2017/04/25 15:41:20 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
* Description:
* Definitions and prototypes for configuration programs.
*
+ * WARNING: Changing the constants defined here affects the size of
+ * the related structures and arrays, and thus would break compatibility
+ * if used in DLLs / shared object libraries.
+ *
+ * Care must be taken that the number of objects supported by
+ * any particular device (which can be only determined at runtime)
+ * does not exceed the max. number of objects specified here
+ * for the configuration programs.
+ *
* -----------------------------------------------------------------------
* $Log: cfg_hlp.h $
+ * Revision 1.3.1.101 2017/04/25 15:41:20 martin
+ * Fixed build under FreeBSD.
+ * Revision 1.3.1.100 2017/03/29 12:33:26 philipp
+ * Extended event info and event status index structures by data pointer
+ * Revision 1.3.1.99 2017/03/27 10:37:18 thomas-b
+ * Added ALL_PTP_V1_COMMON_DATASETS and the appropriate free function
+ * Revision 1.3.1.98 2017/03/22 09:07:53 thomas-b
+ * Added function get_io_port_type_info_idx
+ * Revision 1.3.1.97 2017/03/17 12:01:02 martin
+ * Moved definitions of PCPS_HRT_FRAC_CONVERSION_TYPE,
+ * PCPS_HRT_BIN_FRAC_SCALE, and PCPS_HRT_FRAC_SCALE_FMT
+ * here.
+ * Revision 1.3.1.96 2017/03/17 11:45:17 martin
+ * Moved binary fraction conversion functions here.
+ * Revision 1.3.1.95 2017/03/02 14:03:00 gregoire
+ * ALL_NTP_CFG_INFO reworked
+ * Revision 1.3.1.94 2017/03/02 08:34:08 gregoire
+ * ALL_NTP_CFG_INFO: NTP_REFCLK_CFG_INFO_IDX added
+ * Revision 1.3.1.93 2017/02/28 15:25:17 gregoire
+ * ALL_NTP_CFG_INFO extended
+ * Revision 1.3.1.92 2017/02/24 09:38:25 philipp
+ * Do not use fixed buffers for monitorung event info and status
+ * Revision 1.3.1.91 2017/02/22 11:40:17 martin
+ * Account for preliminary code.
+ * Revision 1.3.1.90 2017/02/21 15:51:40 thomas-b
+ * Added ALL_MONITORING_STATUS and free function and extended ALL_MONITORING_INFO by events
+ * Revision 1.3.1.89 2017/02/16 12:58:01 thomas-b
+ * Added ALL_PTP_V2_COMMON_DATASETS structure and the appropriate free function
+ * Revision 1.3.1.88 2017/02/08 13:16:08 thomas-b
+ * Added ALL_MONITORING_INFO and the appropriate free function
+ * Revision 1.3.1.87 2017/02/07 09:46:51 thomas-b
+ * Added ALL_SNMP_INFO and the appropriate free function
+ * Revision 1.3.1.86 2016/12/19 12:13:55 philipp
+ * Added GPIO associated index helper
+ * Revision 1.3.1.85 2016/12/13 13:46:22 martin
+ * Increased MAX_PARM_PORT and MAX_PARM_POUT to 10.
+ * Revision 1.3.1.84 2016/11/22 12:40:46Z philipp
+ * Added I/O port helper functions
+ * Revision 1.3.1.83 2016/11/08 17:21:35 martin
+ * Updated function prototypes.
+ * Revision 1.3.1.82 2016/11/01 09:24:02 martin
+ * *** empty log message ***
+ * Revision 1.3.1.81 2016/10/25 07:48:27 martin
+ * Doxygen fixes.
+ * Revision 1.3.1.80 2016/10/21 09:39:26 thomas-b
+ * Added struct ALL_XBP_INFO and appropriate free function
+ * Revision 1.3.1.79 2016/10/14 11:10:03 thomas-b
+ * Added ALL_UCAP_NET_INFO and the appropriate free function
+ * Revision 1.3.1.78 2016/09/28 15:04:03 thomas-b
+ * Added function to check whether NET_CFG_API stage 2 is supported
+ * Revision 1.3.1.77 2016/08/11 13:25:06 martin
+ * Use mbgklist.h instead of mbg_klist.h.
+ * Revision 1.3.1.76 2016/08/11 08:36:56Z martin
+ * Exclude function prototypes from build for kernel space.
+ * Revision 1.3.1.75 2016/08/10 12:25:02Z martin
+ * Support FreeBSD.
+ * Revision 1.3.1.74 2016/08/09 07:09:28 martin
+ * Support QNX Neutrino.
+ * Revision 1.3.1.73 2016/06/21 12:06:59 thomas-b
+ * Added function calloc_ucap_entry
+ * Revision 1.3.1.72 2016/06/21 07:39:21 philipp
+ * Use mbg_klist for ucap events and not an array -> Easier to handle MAX_UCAP_ENTRIES
+ * Revision 1.3.1.71 2016/06/16 07:46:45 philipp
+ * Fixed checking flags for IMS sensor specific features
+ * Revision 1.3.1.70 2016/06/15 14:04:27 thomas-b
+ * Added ALL_UCAP_INFO structure and function free_all_ucap_info
+ * Revision 1.3.1.69 2016/06/02 10:24:22 philipp
+ * Renaming all revision macros and helper functions
+ * Revision 1.3.1.68 2016/05/31 11:29:15 philipp
+ * Extended ALL_XMULTI_REF_STATUS by flags if at least one ref type supports stats and/or metrics
+ * Revision 1.3.1.67 2016/05/27 05:48:08 philipp
+ * Refactoring to support XMR_METRICS properly
+ * Revision 1.3.1.66 2016/05/26 11:01:03 thomas-b
+ * Removed info structures from ALL_NTP_STATUS
+ * Moved check functions of specific features to cfg_hlp
+ * Revision 1.3.1.65 2016/05/25 08:43:36 philipp
+ * Redesign of ALL_[xxx]_[XXX] structures and (helper) functions
+ * Revision 1.3.1.64 2016/05/23 09:37:40 philipp
+ * Extended ALL_XMULTI_REF_STATUS by holdover_status
+ * Revision 1.3.1.63 2016/05/23 08:59:03 philipp
+ * New function free_all_gpio_state
+ * Revision 1.3.1.62 2016/05/23 08:24:38 philipp
+ * New function free_all_ims_state
+ * Revision 1.3.1.61 2016/05/11 13:20:59 thomas-b
+ * Added ALL_NET_STATUS_INFO and the appropriate free function
+ * Revision 1.3.1.60 2016/04/26 14:21:58 thomas-b
+ * Renamed ALL_NET_CFG_INFO structure members
+ * Revision 1.3.1.59 2016/04/26 08:23:45 thomas-b
+ * Extended ALL_NET_CFG_INFO by DNS configurations
+ * Revision 1.3.1.58 2016/04/26 06:29:30 thomas-b
+ * Added ALL_NET_CFG_INFO for network configuration
+ * Revision 1.3.1.57 2016/04/25 11:22:31 martin
+ * Revision 1.3.1.56 2016/04/25 10:43:38Z martin
+ * *** empty log message ***
+ * Revision 1.3.1.55 2016/04/22 07:11:50 philipp
+ * Use pointer to pointer in get_all_* functions
+ * Revision 1.3.1.54 2016/04/20 14:45:46 thomas-b
+ * Renamed ALL_NTP_STATE_INFO to ALL_NTP_STATUS
+ * Revision 1.3.1.53 2016/04/20 13:49:13 thomas-b
+ * Added structure definitions and free functions for NTP
+ * Revision 1.3.1.52 2016/04/20 12:37:53 thomas-b
+ * Moved free functions for ALL_XMULTI_REF_INFO and ALL_XMULTI_REF_STATUS to cfg_hlp
+ * Revision 1.3.1.51 2016/04/12 13:28:39 philipp
+ * New helper functions to get all feature related structures at once
+ * Revision 1.3.1.50 2016/04/12 08:25:10 thomas-b
+ * Added ALL_XMULTI_REF_STATUS structure
+ * Revision 1.3.1.49 2016/04/11 13:56:24 thomas-b
+ * Added ALL_XMULTI_REF_INFO structure
+ * Revision 1.3.1.48 2016/04/08 07:54:26 philipp
+ * Added function prototype mbg_print_ext_rev_info
+ * Revision 1.3.1.47 2016/04/04 15:08:45 martin
+ * Replaced chk_model_is_vsg() by xdevfeat::xdevfeat_is_vsg().
+ * Revision 1.3.1.46 2016/03/03 11:20:30 martin
+ * Updated function prototypes.
+ * Revision 1.3.1.45 2016/02/17 12:00:07Z gregoire
+ * new function chk_model_is_vsg
+ * Revision 1.3.1.44 2016/02/10 15:45:32Z martin
+ * *** empty log message ***
+ * Revision 1.3.1.43 2015/11/24 13:12:04 philipp
+ * Extended / modified TLV functions
+ * Revision 1.3.1.42 2015/11/23 14:15:40 philipp
+ * Moved TLV related initializing functions to here
+ * Revision 1.3.1.41 2015/11/20 14:51:10 martin
+ * Revision 1.3.1.40 2015/11/02 11:00:48Z martin
+ * *** empty log message ***
+ * Revision 1.3.1.39 2015/11/02 09:20:02 martin
+ * *** empty log message ***
+ * Revision 1.3.1.38 2015/10/27 16:21:31 martin
+ * Older defines N_SUPP_DEV, PCPS_MAX_DDEVS, and MBG_MAX_DEVICES
+ * have been obsoleted by new defines N_SUPP_DEV_BUS, N_SUPP_DEV_EXT,
+ * and N_SUPP_DEV_TOTAL.
+ * Revision 1.3.1.37 2015/10/26 16:31:53 martin
+ * *** empty log message ***
+ * Revision 1.3.1.36 2015/10/26 14:18:34 martin
+ * Revision 1.3.1.35 2015/10/15 12:49:10Z marvin
+ * Revision 1.3.1.34 2015/10/12 10:01:59Z martin
+ * *** empty log message ***
+ * Revision 1.3.1.33 2015/10/08 13:27:37 martin
+ * *** empty log message ***
+ * Revision 1.3.1.32 2015/10/08 10:32:16 martin
+ * *** empty log message ***
+ * Revision 1.3.1.31 2015/10/08 09:30:34 martin
+ * *** empty log message ***
+ * Revision 1.3.1.30 2015/10/07 10:12:08 martin
+ * *** empty log message ***
+ * Revision 1.3.1.29 2015/10/07 10:08:34 martin
+ * *** empty log message ***
+ * Revision 1.3.1.28 2015/10/07 09:59:00 martin
+ * More common GNSS support.
+ * Revision 1.3.1.27 2015/09/15 09:10:40 martin
+ * Updated function prototypes.
+ * Revision 1.3.1.26 2015/09/11 12:09:09 thomas-b
+ * Added nano_time_64_to_tm_gps and tm_gps_to_nano_time_64 functions
+ * Revision 1.3.1.25 2015/08/31 14:55:11 martin
+ * Moved string trim functions to str_util module.
+ * Revision 1.3.1.24 2015/08/31 14:49:25 martin
+ * Revision 1.3.1.23 2015/08/31 09:58:08 martin
+ * Revision 1.3.1.22 2015/08/27 16:30:10Z martin
+ * Revision 1.3.1.21 2015/08/26 07:31:51 martin
+ * Revision 1.3.1.20 2015/08/21 14:22:59 martin
+ * Revision 1.3.1.19 2014/10/29 16:25:31 martin
+ * Moved some functions and structures to more convenient files.
+ * Revision 1.3.1.18 2014/10/29 16:00:37 martin
+ * Revision 1.3.1.17 2014/10/29 14:21:55 martin
+ * Revision 1.3.1.16 2014/09/26 11:43:24 martin
+ * Revision 1.3.1.15 2014/07/22 13:05:35 martin
+ * Revision 1.3.1.14 2014/07/14 15:42:45Z martin
+ * Revision 1.3.1.13 2014/06/25 15:15:20 martin
+ * Revision 1.3.1.12 2014/06/25 08:51:36Z martin
+ * Support GPIO status.
+ * Revision 1.3.1.11 2014/05/22 16:15:16Z martin
+ * Revision 1.3.1.10 2014/05/14 12:43:53 martin
+ * Revision 1.3.1.9 2014/05/13 08:23:24 martin
+ * Revision 1.3.1.8 2014/05/13 08:19:34Z martin
+ * Revision 1.3.1.7 2014/04/28 12:33:09 martin
+ * Revision 1.3.1.6 2014/04/28 12:04:32 martin
+ * Revision 1.3.1.5 2014/04/25 09:16:38 martin
+ * Updated function prototypes.
+ * Revision 1.3.1.4 2013/12/18 14:51:37 martin
+ * Moved inline function num_bits_set() here.
+ * Revision 1.3.1.3 2013/11/13 10:00:09 martin
+ * Revision 1.3.1.2 2013/11/12 12:12:40 marvin
+ * Changed calls for NTP info and settings.
+ * Revision 1.3.1.1 2013/09/25 10:14:38Z martin
+ * Started to support NTP configuration.
+ * Revision 1.3 2013/09/25 10:02:15 martin
+ * Added ALL_PTP_CFG_INFO, ALL_GNSS_SAT_INFO_IDX and
+ * related definitions.
+ * Added doxygen comments.
* Revision 1.2 2012/10/02 18:16:26 martin
* Modified some typedefs to be more compliant with the underlying types.
* Revision 1.1 2011/09/21 15:59:59 martin
@@ -24,7 +222,24 @@
/* Other headers to be included */
#include <gpsdefs.h>
+#include <mbgklist.h>
+
+#if !defined( MBG_TGT_KERNEL )
+ #include <stdlib.h>
+ #include <string.h>
+#endif
+#if defined( _PRELIMINARY_CODE )
+ #if defined( MBG_TGT_POSIX )
+ #include <sys/stat.h>
+ #include <time.h>
+ #endif // MBG_TGT_POSIX
+
+ #if defined( MBG_TGT_LINUX )
+ #include <sys/sysinfo.h>
+ #endif // MBG_TGT_LINUX
+
+#endif // _PRELIMINARY_CODE
#ifdef _CFG_HLP
#define _ext
@@ -41,69 +256,868 @@ extern "C" {
#endif
-/*
- * The definitions and types below are used to collect
- * all configuration parameters of a clock's serial ports
- * that can be handled by this library:
- */
+#if 1 // ### TODO cleanup
+#define N_SUPP_DEV_BUS 16
+#define N_SUPP_DEV_EXT 1
-/*
- * The maximum number of clocks' serial ports and string types
- * that can be handled by the configuration programs.
- * WARNING: Changing these constants affects the size of the
- * structures ALL_PORT_INFO ALL_STR_TYPE_INFO
- */
-#define MAX_PARM_PORT 4
+#define N_SUPP_DEV_TOTAL ( N_SUPP_DEV_BUS + N_SUPP_DEV_EXT )
+
+typedef struct _DEVICE_INFO
+{
+ char *hw_id;
+ char fw_id[100];
+
+} DEVICE_INFO;
+
+_ext DEVICE_INFO device_list[N_SUPP_DEV_TOTAL];
+
+#endif
+
+
+
+/// @brief The max number of serial ports supported by configuration programs
+#define MAX_PARM_PORT 10
+
+/// @brief The max number of serial string types supported by configuration programs
#define MAX_PARM_STR_TYPE 20
+/// @brief The max number of programmable pulse outputs supported by configuration programs
+#define MAX_PARM_POUT 10
+
+/// @brief The max number of GNSS settings supported by configuration programs
+#define MAX_PARM_GNSS_SAT N_GNSS_TYPES
+
+/// @brief The max number of PTP unicast masters supported by configuration programs
+#define MAX_PARM_PTP_UC_MASTER 3
+
+/// @brief The max number of external NTP server associations to be handled by configuration programs
+#define MAX_PARM_EXT_NTP_SRVR 20
+
+/// @brief The max number of GPIO ports supported by configuration programs
+#define MAX_PARM_GPIO 10
+
+/// @brief The max number of XMR sources supported by configuration programs
+#define MAX_PARM_XMR 10
+
+/// @brief The max number of external NTP servers supported by configuration programs
+#define MAX_EXT_NTP_SERVERS 20
+
+/// @brief The max. number of time monitoring modules supported by configuration programs
+/// Each module may support a different number of targets to be monitored.
+/// @see ### TODO
+#define MAX_MBG_TIME_MON_MODULES 10
+
+/// @brief The max. number of time monitoring targets supported by configuration programs
+/// This is the sum of all targets from all monitoring modules.
+/// @see ### TODO
+#define MAX_MBG_TIME_MON_TARGETS 100
+
+
+
+/// @brief An array of configuration settings for all serial ports
typedef PORT_INFO_IDX ALL_PORT_INFO_IDX[MAX_PARM_PORT];
+
+/// @brief An array of configuration settings for all serial string types
typedef STR_TYPE_INFO_IDX ALL_STR_TYPE_INFO_IDX[MAX_PARM_STR_TYPE];
+/**
+ * @brief All configuration parameters for all serial ports
+ *
+ * Used to collect all configuration parameters of a clock's serial ports
+ * that can be handled by a configuration program.
+ *
+ * @see ::RECEIVER_INFO::n_com_ports
+ * @see ::RECEIVER_INFO::n_str_type
+ */
typedef struct
{
- ALL_PORT_INFO_IDX pii;
- ALL_STR_TYPE_INFO_IDX stii;
- PORT_PARM tmp_pp;
+ ALL_PORT_INFO_IDX pii; ///< all serial port configuration settings
+ ALL_STR_TYPE_INFO_IDX stii; ///< all supported serial string types
+ PORT_PARM tmp_pp; ///< used internally only, for compatibility
} RECEIVER_PORT_CFG;
-/*
- * The definitions and types below are used to collect
- * all configuration parameters of a clock's programmable
- * pulse outputs that can be handled by this library:
+
+/**
+ * @brief All XBP information of a XBP supporting device
+ *
+ * This structure represents a list of connected devices
+ *
+ * @see ::GPS_HAS_XBP
*/
+typedef struct
+{
+ XBP_LIMITS limits;
+ XBP_NODE_LIMITS* node_limits;
+ XBP_NODE_INFO_IDX* node_infos;
+} ALL_XBP_INFO;
-#define MAX_PARM_POUT 4
-#if 1 //##+++++++++++++++++++++++
+/**
+ * @brief An array of configuration settings for all programmable pulse outputs
+ *
+ * Used to collect all configuration parameters of a clock's programmable pulse outputs
+ * that can be handled by a configuration program.
+ *
+ * @see ::RECEIVER_INFO::n_prg_out
+ */
typedef POUT_INFO_IDX ALL_POUT_INFO_IDX[MAX_PARM_POUT];
-#else
+
+/**
+ * @brief All network configuration parameters
+ *
+ * Used to collect all configuration parameters for networking
+ *
+ * @see ::GPS_HAS_NET_CFG
+ * @see ::GPS_HAS_LAN_IP4
+ */
typedef struct
{
- POUT_INFO_IDX pii[MAX_PARM_POUT];
-} POUT_CFG;
+ MBG_NET_GLB_CFG_INFO glb_cfg_info;
+ MBG_NET_INTF_LINK_INFO_IDX *link_infos;
+ MBG_NET_INTF_ADDR_INFO_IDX *addr_infos;
+ MBG_IP_ADDR_IDX *dns_srvrs;
+ MBG_NET_NAME_IDX *dns_srch_doms;
+ MBG_NET_INTF_ROUTE_INFO_IDX *route_infos;
+} ALL_NET_CFG_INFO;
-#endif
+typedef ALL_NET_CFG_INFO ALL_NET_STATUS_INFO;
-/*
- * The definitions and types below are used to collect
- * all configuration parameters of PTP device's unicast
- * master specification:
+
+/**
+ * @brief All SNMP configuration information
+ *
+ * Used to collect all configuration parameters for monitoring via SNMP
+ * Can be used, if ::MBG_MONITORING_TYPE_MSK_SNMP is set in ::MBG_MONITORING_LIMITS::supp_types
+ *
+ * @see ::MBG_XFEATURE_MONITORING
*/
+typedef struct
+{
+ MBG_SNMP_GLB_INFO glb_info;
+ MBG_SNMP_V12_INFO_IDX *v12_infos;
+ MBG_SNMP_V12_TRAP_INFO_IDX *v12_trap_infos;
+ MBG_SNMP_V3_INFO_IDX *v3_infos;
+ MBG_SNMP_V3_TRAP_INFO_IDX *v3_trap_infos;
+
+} ALL_SNMP_INFO;
+
+
+/**
+ * @brief All monitoring information
+ *
+ * Used to collect all configuration parameters for monitoring of a device
+ * Depending on the ::MBG_MONITORING_LIMITS::supp_types,
+ * the approriate configurations can be found in the sub structures
+ *
+ * @see ::MBG_XFEATURE_MONITORING
+ */
+typedef struct
+{
+ MBG_EVENT_INFO_IDX info;
+ void *priv_data;
+
+} MBG_EVENT_INFO_IDX_DATA;
+
+typedef struct
+{
+ MBG_MONITORING_LIMITS limits;
+ ALL_SNMP_INFO *all_snmp_info;
+ MBG_EVENT_INFO_IDX_DATA *event_infos;
+
+} ALL_MONITORING_INFO;
+
+
+
+/**
+ * @brief All monitoring status
+ *
+ * Used to collect all status information for monitoring of a device
+ * Depending on the ::MBG_MONITORING_LIMITS::supp_events, the
+ * appropriate event status for each event can be found in ::event_stati.
+ */
+typedef struct
+{
+ MBG_EVENT_STATUS_IDX status;
+ void *priv_data;
+
+} MBG_EVENT_STATUS_IDX_DATA;
+
+typedef struct
+{
+ MBG_MONITORING_STATUS status;
+ MBG_EVENT_STATUS_IDX_DATA *event_stati;
+
+} ALL_MONITORING_STATUS;
-#define MAX_PARM_PTP_UC_MASTER 3
+/// @brief Configuration settings for all unicast master specifications
typedef PTP_UC_MASTER_INFO_IDX ALL_PTP_UC_MASTER_INFO_IDX[MAX_PARM_PTP_UC_MASTER];
+/**
+ * @brief All PTP configuration parameters
+ *
+ * Used to collect all configuration parameters for a PTP daemon
+ * that can be handled by a configuration program.
+ *
+ * @see ::GPS_HAS_PTP
+ * @see ::PTP_UC_MASTER_CFG_LIMITS::n_supp_master
+ */
+typedef struct
+{
+ PTP_CFG_INFO ptp_cfg_info;
+ PTP_UC_MASTER_CFG_LIMITS ptp_uc_master_cfg_limits;
+ ALL_PTP_UC_MASTER_INFO_IDX all_ptp_uc_master_info_idx;
+
+} ALL_PTP_CFG_INFO;
+
+
+
+/**
+ * @brief All PTPv1 common datasets for a PTP device
+ *
+ * Contains one of each common datasets plus one port dataset
+ * for each port of a device. The number of port datasets is
+ * defined in ::default_dataset::number_ports.
+ *
+ * @see ::MBG_PTP_V1_DEFAULT_DATASET
+ * @see ::MBG_PTP_V1_CURRENT_DATASET
+ * @see ::MBG_PTP_V1_PARENT_DATASET
+ * @see ::MBG_PTP_V1_TIME_PROPERTIES_DATASET
+ * @see ::MBG_PTP_V1_PORT_DATASET_IDX
+ */
+typedef struct
+{
+ MBG_PTP_V1_DEFAULT_DATASET default_dataset;
+ MBG_PTP_V1_CURRENT_DATASET current_dataset;
+ MBG_PTP_V1_PARENT_DATASET parent_dataset;
+ MBG_PTP_V1_TIME_PROPERTIES_DATASET time_properties_dataset;
+ MBG_PTP_V1_PORT_DATASET_IDX *port_datasets;
+
+} ALL_PTP_V1_COMMON_DATASETS;
+
+
+
+/**
+ * @brief All PTPv2 common datasets for a PTP device
+ *
+ * Contains one of each common datasets plus one port dataset
+ * for each port of a device. The number of port datasets is
+ * defined in ::default_dataset::number_ports.
+ *
+ * @see ::MBG_PTP_V2_DEFAULT_DATASET
+ * @see ::MBG_PTP_V2_CURRENT_DATASET
+ * @see ::MBG_PTP_V2_PARENT_DATASET
+ * @see ::MBG_PTP_V2_TIME_PROPERTIES_DATASET
+ * @see ::MBG_PTP_V2_PORT_DATASET_IDX
+ */
+typedef struct
+{
+ MBG_PTP_V2_DEFAULT_DATASET default_dataset;
+ MBG_PTP_V2_CURRENT_DATASET current_dataset;
+ MBG_PTP_V2_PARENT_DATASET parent_dataset;
+ MBG_PTP_V2_TIME_PROPERTIES_DATASET time_properties_dataset;
+ MBG_PTP_V2_PORT_DATASET_IDX *port_datasets;
+
+} ALL_PTP_V2_COMMON_DATASETS;
+
+
+
+/**
+ * @brief An array of configuration settings for all programmable pulse outputs
+ *
+ * Used to collect all configuration parameters of a clock's programmable pulse outputs
+ * that can be handled by a configuration program.
+ */
+typedef GNSS_SAT_INFO_IDX ALL_GNSS_SAT_INFO_IDX[MAX_PARM_GNSS_SAT];
+
+
+
+/**
+ * @brief An array of configuration settings for all programmable pulse outputs ####
+ *
+ * Used to collect all configuration parameters of a clock's programmable pulse outputs
+ * that can be handled by a configuration program. #####
+ */
+typedef struct
+{
+ STAT_INFO stat_info;
+ int n_gnss_supp;
+ MBG_GNSS_MODE_INFO gnss_mode_info;
+ ALL_GNSS_SAT_INFO_IDX gnss_sat_info_idx;
+
+} ALL_GNSS_INFO;
+
+
+
+/// @brief Configuration settings for all NTP server associatioions
+typedef NTP_PEER_SETTINGS ALL_NTP_PEER_SETTINGS[MAX_EXT_NTP_SERVERS];
+
+/**
+ * @brief All NTP configuration parameters
+ *
+ * Used to collect all configuration parameters for an NTP daemon
+ * that can be handled by a configuration program.
+ *
+ * @see ::GPS_HAS_NTP
+ */
+typedef struct
+{
+ ALL_NTP_PEER_SETTINGS all_ntp_peer_settings;
+
+} NTP_CLIENT_CFG_PEER_SETTINGS;
+
+
+typedef struct
+{
+ NTP_GLB_INFO glb_info;
+ NTP_SYMM_KEY_LIMITS *symm_key_limits;
+ NTP_SYMM_KEY_INFO_IDX *symm_key_info_idx;
+ NTP_TRUSTED_KEY_INFO_IDX *trusted_key_info_idx;
+
+ NTP_CLNT_MODE_INFO *clnt_info;
+ NTP_PEER_SETTINGS_IDX *peer_settings_idx;
+
+ NTP_SRV_MODE_INFO *srv_info;
+ NTP_REFCLK_CFG_INFO_IDX *refclk_info_idx;
+ NTP_MISC_LIMITS *misc_limits;
+ NTP_MISC_ORPHAN_MODE_INFO *orphan_mode_info;
+
+} ALL_NTP_CFG_INFO;
+
+
+typedef struct
+{
+ NTP_SYS_STATE sys_state;
+ NTP_PEER_STATE_IDX *peer_states;
+} ALL_NTP_STATUS;
+
+
+
+/// @brief Configuration settings for all GPIO ports
+typedef MBG_GPIO_INFO_IDX ALL_GPIO_INFO_IDX[MAX_PARM_GPIO];
+
+/// @brief Status information on all GPIO ports
+typedef MBG_GPIO_STATUS_IDX ALL_GPIO_STATUS_IDX[MAX_PARM_GPIO];
+
+
+
+
+/// @brief Status of all XMR inputs
+typedef XMULTI_REF_STATUS_IDX ALL_XMULTI_REF_STATUS_IDX[MAX_PARM_XMR];
+
+/// @brief Configuration settings for all XMR inputs
+typedef XMULTI_REF_INFO_IDX ALL_XMULTI_REF_INFO_IDX[MAX_PARM_XMR];
+
+
+
+typedef struct
+{
+ XMULTI_REF_INSTANCES instances;
+ XMULTI_REF_INFO_IDX *infos;
+ XMR_EXT_SRC_INFO_IDX *ext_src_infos;
+} ALL_XMULTI_REF_INFO;
+
+
+typedef struct
+{
+ XMULTI_REF_STATUS_IDX *status;
+ XMR_HOLDOVER_STATUS *holdover_status;
+ XMR_STATS_IDX *stats_idx;
+ XMR_METRICS_IDX *metrics_idx;
+ /* ALL_XMULTI_REF_STATUS related flag if at least one ref type supports stats */
+ unsigned char has_stats;
+ /* ALL_XMULTI_REF_STATUS related flag if at least one ref type supports metrics */
+ unsigned char has_metrics;
+} ALL_XMULTI_REF_STATUS;
+
+
+
+typedef struct
+{
+ MBG_IMS_STATE state;
+ MBG_IMS_FDM_INFO *fdm_info;
+ MBG_IMS_FDM_LIMITS *fdm_limits;
+ MBG_IMS_FDM_OUTPUT_INFO_IDX *fdm_outinfo_idx;
+} ALL_IMS_INFO;
+
+
+typedef struct
+{
+ MBG_IMS_SENSOR_STATE_IDX *sensor_state_idx;
+ MBG_IMS_FDM_STATE *fdm_state;
+ MBG_IMS_FDM_OUTPUT_STATE_IDX *fdm_output_state_idx;
+} ALL_IMS_STATE;
+
+
+
+typedef struct
+{
+ MBG_GPIO_CFG_LIMITS cfg_limits;
+ MBG_GPIO_INFO_IDX *infos;
+} ALL_GPIO_INFO;
+
+
+typedef struct
+{
+ MBG_GPIO_STATUS_IDX *states;
+} ALL_GPIO_STATE;
+
+
+typedef struct
+{
+ MBG_IO_PORT_LIMITS limits;
+ MBG_IO_PORT_INFO_IDX *p_infos;
+ MBG_IO_PORT_TYPE_INFO_IDX **pt_infos;
+} ALL_IO_PORT_INFO;
+
+
+typedef struct
+{
+ MBG_IO_PORT_STATUS_IDX *status;
+} ALL_IO_PORT_STATUS;
+
+
+#ifndef MAX_UCAP_ENTRIES
+/*
+ * According to Andre's GPS firmware this is the maximum
+ * number of user captures that are preserved.
+ */
+#define MAX_UCAP_ENTRIES 585
+#endif
+
+typedef struct
+{
+ struct mbg_klist_head head;
+ TTM ttm;
+} UCAP_ENTRY;
+
+typedef struct
+{
+ uint32_t num_ucaps; /// User capture counter, see ::MAX_UCAP_ENTRIES
+ struct mbg_klist_head list;
+} ALL_UCAP_INFO;
+
+// User Captures via Network configuration, see ::MBG_XFEATURE_UCAP_NET
+typedef struct
+{
+ MBG_UCAP_NET_GLB_INFO glb_info;
+ MBG_UCAP_NET_RECV_INFO_IDX *recv_infos;
+} ALL_UCAP_NET_INFO;
+
+
+
+/**
+ * @brief A mode specifying how to interpret a ::PCPS_SIG_VAL
+ *
+ * Used with ::PCPS_TIME_EXT::comp_sig_mode. Depending on this mode
+ * a signal value can be interpreted e.g. as signal strength (with
+ * long wave or IRIG time code receivers), or as indicator whether an
+ * antenna is connected (satellite receivers), or a network link is
+ * available (PTP slaves) or not, and an appropriate status message
+ * can be displayed.
+ *
+ * @see @ref PCPS_SIG_VAL_DEFS
+ */
+enum COMP_SIG_MODES
+{
+ COMP_SIG_MODE_NONE, ///< signal value not used
+ COMP_SIG_MODE_SIGNAL, ///< input signal strength
+ COMP_SIG_MODE_ANT_CONN, ///< antenna connection state
+ COMP_SIG_MODE_PORT_LINK, ///< port link state
+ N_CONN_SIG_MODES
+};
+
+
+/**
+ * @brief Flag bits indicating if some extended status is available
+ *
+ * @see ::PCPS_TIME_EXT_FLAGS
+ */
+enum PCPS_TIME_EXT_FLAG_BITS
+{
+ PCPS_TIME_EXT_FLAG_BIT_UTC_VALID, ///< ::PCPS_TIME_EXT::utc_offs field is valid
+ N_PCPS_TIME_EXT_FLAG_BITS
+};
+
+
+/**
+ * @brief Flag masks used with ::PCPS_TIME_EXT::flags
+ *
+ * @see ::PCPS_TIME_EXT_FLAG_BITS
+ */
+enum PCPS_TIME_EXT_FLAGS
+{
+ PCPS_TIME_EXT_FLAG_UTC_VALID = ( 1UL << PCPS_TIME_EXT_FLAG_BIT_UTC_VALID ) ///< see ::PCPS_TIME_EXT_FLAG_BIT_UTC_VALID
+};
+
+
+
+_ext BAUD_RATE mbg_baud_rate[N_MBG_BAUD_RATES]
+#ifdef _DO_INIT
+ = MBG_BAUD_RATES
+#endif
+;
+
+_ext const char *mbg_baud_str[N_MBG_BAUD_RATES]
+#ifdef _DO_INIT
+ = MBG_BAUD_STRS
+#endif
+;
+
+_ext const char *mbg_framing_str[N_MBG_FRAMINGS]
+#ifdef _DO_INIT
+ = MBG_FRAMING_STRS
+#endif
+;
+
+_ext const char *str_unknown
+#ifdef _DO_INIT
+ = "unknown"
+#endif
+;
+
+
+_ext const char *str_undefined
+#ifdef _DO_INIT
+ = "(undefined)"
+#endif
+;
+
+
+_ext const char *str_not_spc
+#ifdef _DO_INIT
+ = "not "
+#endif
+;
+
+
+
+//### TODO
+#define DEFAULT_MAX_STR_TYPE 2 // DEFAULT_N_STR_TYPE_GPS ?
+
+_ext STR_TYPE_INFO default_str_type_info[DEFAULT_MAX_STR_TYPE]
+#ifdef _DO_INIT
+ = {
+ { DEFAULT_STR_MODES, "Default Time String", "Time", 0 },
+ { DEFAULT_STR_MODES_UCAP, "Capture String", "Cap", 0 }
+ }
+#endif
+;
+
+
+
+_ext const char *mbg_gpio_type_names[N_MBG_GPIO_TYPES]
+#ifdef _DO_INIT
+ = DEFAULT_GPIO_TYPES_SHORT_STRS
+#endif
+;
+
+#define _get_gpio_type_name( _i ) \
+ ( ( (_i) < N_MBG_GPIO_TYPES ) ? mbg_gpio_type_names[_i] : str_unknown )
+
+
+
+_ext const char *mbg_gpio_port_state_names[N_MBG_GPIO_PORT_STATES]
+#ifdef _DO_INIT
+ = DEFAULT_GPIO_PORT_STATE_NAMES
+#endif
+;
+
+#define _get_gpio_port_state_name( _i ) \
+ ( ( (_i) < N_MBG_GPIO_PORT_STATES ) ? mbg_gpio_port_state_names[_i] : str_unknown )
+
+
+
+_ext const char *mbg_gpio_signal_shape_names[N_MBG_GPIO_SIGNAL_SHAPES]
+#ifdef _DO_INIT
+ = DEFAULT_GPIO_SIGNAL_SHAPE_NAMES
+#endif
+;
+#define _get_gpio_signal_shape_name( _i ) \
+ ( ( (_i) < N_MBG_GPIO_SIGNAL_SHAPES ) ? mbg_gpio_signal_shape_names[_i] : str_unknown )
+
+_ext const char *mbg_gpio_fixed_freq_strs[N_MBG_GPIO_FIXED_FREQ]
+#ifdef _DO_INIT
+ = MBG_GPIO_FIXED_FREQ_STRS
+#endif
+;
+
+#define _get_gpio_fixed_freq_str( _i ) \
+ ( ( (_i) < N_MBG_GPIO_FIXED_FREQ ) ? mbg_gpio_fixed_freq_strs[_i] : str_unknown )
+
+
+
+_ext const char *xmr_holdover_status_mode_names[N_XMR_HOLDOVER_STATUS_MODES]
+#ifdef _DO_INIT
+ = XMR_HOLDOVER_STATUS_MODE_NAMES
+#endif
+;
+
+#define _get_xmr_holdover_status_mode_name( _i ) \
+ ( ( (_i) < N_XMR_HOLDOVER_STATUS_MODES ) ? xmr_holdover_status_mode_names[_i] : str_unknown )
+
+
+
+/**
+ * @brief Count the number of bits which are not 0
+ *
+ * @param[in] val Value to be tested
+ *
+ * @return The number of non-zero bits in val
+ */
+static __mbg_inline
+int num_bits_set( long val )
+{
+ int bits_set = 0;
+ size_t i;
+
+ for ( i = 0; i < ( 8 * sizeof( val ) ); i++ )
+ {
+ if ( val & 1 )
+ bits_set++;
+
+ val >>= 1;
+ }
+
+ return bits_set;
+
+} // num_bits_set
+
+
+
+/**
+ * @brief Check if a device ID refers to a serial port
+ *
+ * @param[in] dev_id A string with the device name or port name
+ *
+ * @see ::DEFAULT_SERIAL_DEVICE_NAME
+ *
+ * @return true if the device id contains the name of a serial port, else false
+ */
+static __mbg_inline
+bool device_id_is_serial( const char *dev_id )
+{
+ #if defined( MBG_TGT_WIN32 )
+ //##++++ There may be also serial ports under Windows
+ // which don't have "COM" in their name.
+ return strstr( dev_id, "COM" ) != NULL;
+ #elif defined( MBG_TGT_LINUX )
+ return strstr( dev_id, "/dev/ttyS" ) != NULL // standard serial device
+ || strstr( dev_id, "/dev/ttyUSB" ) != NULL; // serial-to-USB adapter
+ #elif defined( MBG_TGT_FREEBSD )
+ return strstr( dev_id, "/dev/ttyu" ) != NULL // dial-in device (standard), FreeBSD 10 and newer
+ || strstr( dev_id, "/dev/cuau" ) != NULL // dial out device, FreeBSD 10 and newer
+ || strstr( dev_id, "/dev/ttyd" ) != NULL // dial-in device (standard), before FreeBSD 10
+ || strstr( dev_id, "/dev/cuad" ) != NULL; // dial-out device, before FreeBSD 10
+ #elif defined( MBG_TGT_QNX_NTO )
+ return strstr( dev_id, "/dev/ser" ) != NULL;
+ #elif defined( MBG_TGT_DOS )
+ return strstr( dev_id, "COM" ) != NULL;
+ #else
+ #error device_id_is_serial() needs to be implemented for this platform
+ #endif
+
+} // device_id_is_serial
+
+
+
+/**
+ * @brief Check if a device ID refers to a LAN connection
+ *
+ * @param[in] dev_id A string with the device ID
+ *
+ * @return true if the device id specifies a LAN connection, else false
+ */
+static __mbg_inline
+bool device_id_is_lan( const char *dev_id )
+{
+ return strstr( dev_id, "LAN" ) != NULL;
+
+} // device_id_is_lan
+
+
+
+#if defined( _PRELIMINARY_CODE )
+
+static __mbg_inline
+MBG_TLV_UID mbg_tlv_create_id( void )
+{
+#if defined( MBG_TGT_LINUX ) ///### FIXME for FreeBSD and Windows
+ struct sysinfo info;
+
+ // Linux specific, implement Windows equivalent
+ sysinfo( &info );
+ return ( (MBG_TLV_UID) ( ( time( NULL ) >> 16 ) | ( info.uptime << 16 ) ) );
+#else
+ return 0;
+#endif
+} // mbg_tlv_create_id
+
+#endif // defined( _PRELIMINARY_CODE )
+
+
+
+// Depending on the target environment define a data type
+// which can be used to convert binary fractions without
+// range overflow.
+#if defined( MBG_TGT_MISSING_64_BIT_TYPES )
+ #define PCPS_HRT_FRAC_CONVERSION_TYPE double
+#else
+ #define PCPS_HRT_FRAC_CONVERSION_TYPE int64_t
+#endif
+
+/**
+ * @brief Constant used to convert ::PCPS_TIME_STAMP::frac values
+ *
+ * Max value of ::PCPS_TIME_STAMP::frac + 1, used for scaling
+ */
+#define PCPS_HRT_BIN_FRAC_SCALE ( (PCPS_HRT_FRAC_CONVERSION_TYPE) 4294967296.0 ) // == 0x100000000
+
+
+#ifndef PCPS_HRT_FRAC_SCALE
+ /**
+ * @brief Scale to be used to print ::PCPS_TIME_STAMP::frac values
+ *
+ * The function ::frac_sec_from_bin can be used for the conversion.
+ *
+ * @see ::PCPS_HRT_FRAC_SCALE_FMT
+ */
+ #define PCPS_HRT_FRAC_SCALE 10000000UL
+#endif
+
+#ifndef PCPS_HRT_FRAC_SCALE_FMT
+ /**
+ * @brief Format specifier used to print ::PCPS_TIME_STAMP::frac values
+ *
+ * Used to print values scaled with ::frac_sec_from_bin called
+ * with ::PCPS_HRT_FRAC_SCALE.
+ *
+ * @see ::PCPS_HRT_FRAC_SCALE
+ */
+ #define PCPS_HRT_FRAC_SCALE_FMT "%07lu"
+#endif
+
+
+static __mbg_inline
+uint32_t bin_frac_16_to_dec_frac( uint16_t bin, uint32_t scale )
+{
+ return (uint32_t) ( (PCPS_HRT_FRAC_CONVERSION_TYPE) bin * scale
+ / 0x10000UL );
+
+} // bin_frac_16_to_dec_frac
+
+
+static __mbg_inline
+uint32_t bin_frac_32_to_dec_frac( uint32_t bin, uint32_t scale )
+{
+ return (uint32_t) ( (PCPS_HRT_FRAC_CONVERSION_TYPE) bin * scale
+ / PCPS_HRT_BIN_FRAC_SCALE );
+
+} // bin_frac_32_to_dec_frac
+
+
+#if !defined( MBG_TGT_MISSING_64_BIT_TYPES )
+
+// On targets which don't provide 64 bit data types
+// PCPS_HRT_FRAC_CONVERSION_TYPE is defined as double,
+// in which case the ">> 1" operation in the 2 functions
+// below yields an "invalid use of floating point" error.
+// This could probably be fixed by a different way of
+// casting, at least for a partial expression.
+
+static __mbg_inline
+uint16_t dec_frac_to_bin_frac_16( uint32_t dec, uint32_t scale )
+{
+ return (uint16_t) ( ( ( (PCPS_HRT_FRAC_CONVERSION_TYPE) dec * 0x20000 / scale ) + 1 ) >> 1 );
+
+} // dec_frac_to_bin_frac_16
+
+
+static __mbg_inline
+uint32_t dec_frac_to_bin_frac_32( uint32_t dec, uint32_t scale )
+{
+ return (uint32_t) ( ( ( (PCPS_HRT_FRAC_CONVERSION_TYPE) dec * PCPS_HRT_BIN_FRAC_SCALE * 2 / scale ) + 1 ) >> 1 );
+
+} // dec_frac_to_bin_frac_32
+
+#endif
+
+
+#define bin_frac_32_to_msec( _bin ) bin_frac_32_to_dec_frac( (_bin), 1000 )
+#define bin_frac_32_to_usec( _bin ) bin_frac_32_to_dec_frac( (_bin), 1000000 )
+#define bin_frac_32_to_nsec( _bin ) bin_frac_32_to_dec_frac( (_bin), 1000000000 )
+#define bin_frac_16_to_msec( _bin ) bin_frac_16_to_dec_frac( (_bin), 1000 )
+#define bin_frac_16_to_usec( _bin ) bin_frac_16_to_dec_frac( (_bin), 1000000 )
+#define bin_frac_16_to_nsec( _bin ) bin_frac_16_to_dec_frac( (_bin), 1000000000 )
+
+
+#define msec_to_bin_frac_32( _msec ) dec_frac_to_bin_frac_32( (_msec), 1000 )
+#define usec_to_bin_frac_32( _usec ) dec_frac_to_bin_frac_32( (_usec), 1000000 )
+#define nsec_to_bin_frac_32( _nsec ) dec_frac_to_bin_frac_32( (_nsec), 1000000000 )
+#define msec_to_bin_frac_16( _msec ) dec_frac_to_bin_frac_16( (_msec), 1000 )
+#define usec_to_bin_frac_16( _usec ) dec_frac_to_bin_frac_16( (_usec), 1000000 )
+#define nsec_to_bin_frac_16( _nsec ) dec_frac_to_bin_frac_16( (_nsec), 1000000000 )
+
+
+
+/**
+ * @brief Convert a fraction of a second from binary
+ *
+ * Convert a fraction of a second from binary format (as returned
+ * as part of the ::PCPS_HR_TIME structure) to a decimal fraction,
+ * using a specified scale factor.
+ *
+ * @param[in] b The binary fraction
+ * @param[in] scale The scale factor
+ *
+ * @return The calculated number
+ *
+ * @see ::PCPS_HRT_FRAC_SCALE
+ * @see ::PCPS_HRT_FRAC_SCALE_FMT
+ */
+static __mbg_inline
+uint32_t frac_sec_from_bin( uint32_t b, uint32_t scale )
+{
+ return bin_frac_32_to_dec_frac( b, scale );
+
+} // frac_sec_from_bin
+
+
+
+/**
+ * @brief Convert a fraction of a second to double
+ *
+ * Convert a fraction of a second from binary format (as returned
+ * as part of the ::PCPS_HR_TIME structure) to a double with the
+ * units of seconds, e.g. 0xFFFFFFFF yields 0.9999999999....
+ *
+ * @param[in] b The binary fraction
+ *
+ * @return The calculated fraction
+ *
+ * @see ::PCPS_HRT_FRAC_SCALE
+ */
+static __mbg_inline
+double dfrac_sec_from_bin( uint32_t b )
+{
+ return (double) b / (double) PCPS_HRT_BIN_FRAC_SCALE;
+
+} // dfrac_sec_from_bin
+
+
+
+#if !defined( MBG_TGT_KERNEL )
+
/* function prototypes: */
/* ----- function prototypes begin ----- */
@@ -111,9 +1125,413 @@ typedef PTP_UC_MASTER_INFO_IDX ALL_PTP_UC_MASTER_INFO_IDX[MAX_PARM_PTP_UC_MASTER
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
+ /**
+ * @brief Normalize a ::NANO_TIME_64 struct
+ *
+ * After normalization, the following can be assumed:<br>
+ * - nano_secs is in the range [-10^9 + 1, 10^9 - 1]<br>
+ * - if secs is not 0, secs and nano_secs have the same sign
+ *
+ * @param[in,out] nt The NANO_TIME_64 to be normalized
+ */
+ void normalize_nano_time_64( NANO_TIME_64 *nt ) ;
+
+ /**
+ * @brief Print a normalized ::NANO_TIME_64 into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] nt The ::NANO_TIME_64 to be printed
+ */
+ size_t snprint_nano_time_64( char *s, size_t max_len, const NANO_TIME_64 *nt ) ;
+
+ /**
+ * @brief Print nano time into string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] nt The ::NANO_TIME to be printed
+ */
+ size_t snprint_nano_time( char *s, size_t max_len, const NANO_TIME *nt ) ;
+
+ /**
+ * @brief Convert ::NANO_TIME_64 to ::TM_GPS
+ *
+ * @param[out] tm_gps The ::TM_GPS to be filled
+ * @param[in] nt The ::NANO_TIME_64 to be converted
+ *
+ * @return 1 on success, 0 on error
+ *
+ * @see ::tm_gps_to_nano_time_64
+ */
+ int nano_time_64_to_tm_gps( TM_GPS *tm_gps, const NANO_TIME_64 *nt ) ;
+
+ /**
+ * @brief Convert ::TM_GPS to ::NANO_TIME_64
+ *
+ * @param[out] nt The ::NANO_TIME_64 to be filled
+ * @param[in] tm The ::TM_GPS to be converted
+ *
+ * @return 1 on success, 0 on error
+ *
+ * @see ::nano_time_64_to_tm_gps
+ */
+ int tm_gps_to_nano_time_64( NANO_TIME_64 *nt, const TM_GPS *tm ) ;
+
+ /**
+ * @brief Check if a software revision name should be displayed
+ *
+ * The software revision name is usually empty, except if the
+ * firmware is a customized version, in which case the field
+ * contains an identifier string.
+ *
+ * There are some standard firmware versions where this string
+ * is not empty but padded with spaces, etc., so we try to
+ * clean this up and display the string properly, if appropriate.
+ *
+ * @param[in,out] p The ::SW_REV name to check
+ * @param[in] verbose The app's verbosity level
+ *
+ * @return != 0 if SW name should be displayed
+ */
+ int chk_sw_rev_name( SW_REV *p, int verbose ) ;
+
+ int get_str_idx( const char *search, const char *str_table[], int n_entries ) ;
+ int get_baud_rate_idx( BAUD_RATE baud_rate ) ;
+ int get_framing_idx( const char *framing ) ;
+ void port_settings_from_port_parm_mode( PORT_SETTINGS *p_ps, uint8_t pp_mode, int str_type_cap ) ;
+ void port_parm_mode_from_port_settings( uint8_t *pp_mode, const PORT_SETTINGS *p_ps, int str_type_cap ) ;
+ void port_settings_from_port_parm( PORT_SETTINGS *p_ps, int port_num, const PORT_PARM *p_pp, int cap_str_idx ) ;
+ void port_parm_from_port_settings( PORT_PARM *p_pp, int port_num, const PORT_SETTINGS *p_ps, int cap_str_idx ) ;
+ uint32_t check_valid_port_info( const PORT_INFO *p_pi, const STR_TYPE_INFO_IDX str_type_info_idx[], int n_str_type ) ;
+ int valid_port_info( const PORT_INFO *p_pi, const STR_TYPE_INFO_IDX str_type_info_idx[], int n_str_type ) ;
+ int setup_port_info_from_port_settings( PORT_INFO_IDX pii[], const PORT_PARM *p_pp, const RECEIVER_INFO *p_ri ) ;
+ int setup_default_str_type_info_idx( STR_TYPE_INFO_IDX stii[], const RECEIVER_INFO *p_ri ) ;
+ int chk_set_n_gnss_supp( ALL_GNSS_INFO *p_agi ) ;
+ /**
+ * @brief
+ *
+ * ### Setup GNSS info from stat_info so we can use the same printing routine
+ */
+ void setup_gps_only_sat_info_idx_from_statinfo( ALL_GNSS_INFO *p_agi ) ;
+
+ /**
+ * @brief
+ *
+ * Setup GNSS info from stat_info so we can use the same printing routine
+ */
+ int setup_gps_only_gnss_info_from_statinfo( ALL_GNSS_INFO *p_agi ) ;
+
+ void chk_free_dev_hw_id( DEVICE_INFO *p ) ;
+ int alloc_dev_hw_id( DEVICE_INFO *p, size_t len ) ;
+ const char *get_fw_id_from_hw_id( const char *hw_id ) ;
+ const char *get_hw_id_from_fw_id( const char *fw_id ) ;
+ /**
+ * @brief Returns the currently used ::MBG_IO_PORT_TYPE_INFO_IDX for the appropriate ::MBG_IO_PORT_INFO_IDX
+ *
+ * @param[in] all_io_port_info Pointer to the ::ALL_IO_PORT_INFO, containing the current configuration
+ * @param[in] io_port_info_idx Pointer to the ::MBG_IO_PORT_INFO_IDX, for which the ::MBG_IO_PORT_TYPE_INFO_IDX shall be found
+ *
+ * @return Pointer to the found ::MBG_IO_PORT_TYPE_INFO_IDX or NULL
+ *
+ */
+ MBG_IO_PORT_TYPE_INFO_IDX *get_io_port_type_info_idx(ALL_IO_PORT_INFO *all_io_port_info, MBG_IO_PORT_INFO_IDX *io_port_info_idx) ;
+
+ /**
+ * @brief Initializes a ::MBG_TLV_ANNOUNCE structure
+ *
+ * @param[out] tlv Pointer to a ::MBG_TLV_ANNOUNCE structure
+ * @param[in] uid Unique sender ID used as identifier with all
+ * subsequent messages related to this transaction.
+ * @param[in] tlv_feat_type One of the ::MBG_TLV_FEAT_TYPES
+ * @param[in] total_bytes Total number of bytes of all upcoming TLVs
+ */
+ void mbg_tlv_announce_init( MBG_TLV_ANNOUNCE *tlv, MBG_TLV_UID uid, MBG_TLV_TYPE tlv_feat_type, uint32_t total_bytes ) ;
+
+ /**
+ * @brief Initializes a ::MBG_TLV
+ *
+ * @param[out] tlv Pointer to a valid ::MBG_TLV structure
+ * @param[in] uid Unique sender ID used as identifier for each further
+ * TLV message related to this type.
+ * @param[in] tlv_type Type identifier, see ::MBG_TLV_TYPES
+ * @param[in] total_bytes Total number of bytes belonging to this
+ * TLV transaction (which is very likely split into several TLVs)
+ */
+ void mbg_tlv_init( MBG_TLV *tlv, MBG_TLV_UID uid, MBG_TLV_TYPE tlv_type, uint32_t total_bytes ) ;
+
+ /**
+ * @brief Initializes ::MBG_TLV_RCV_STATE structure
+ *
+ * @param[in,out] state Pointer to ::MBG_TLV_RCV_STATE structure
+ * @param[in] uid Unique sender ID used as identifier for each further
+ * TLV message related to this type.
+ * @param[in] total_bytes Total number of bytes belonging to this
+ * TLV transaction (which is very likely split into several TLVS)
+ */
+ void mbg_tlv_rcv_state_init( MBG_TLV_RCV_STATE *state, MBG_TLV_UID uid, uint32_t total_bytes ) ;
+
+ size_t mbg_snprint_revision( char *buf, size_t buflen, const char *prefix, const char *suffix, uint32_t rev) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_xbp_supp_nodes( const ALL_XBP_INFO *info ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_net_cfg_supp_stage_2( const ALL_NET_CFG_INFO *info ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_ntp_supp_client( const ALL_NTP_CFG_INFO *info ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_ntp_supp_server( const ALL_NTP_CFG_INFO *info ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_mrf_none( const ALL_XMULTI_REF_INFO *info ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_ext_src_info( const ALL_XMULTI_REF_INFO *info ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_holdover_status( const ALL_XMULTI_REF_INFO *info ) ;
+ /*
+ * Type is NOT an index of ::XMULTI_REF_INSTANCES::n_xmr_settings,
+ * but of ::MULTI_REF_TYPES.
+ * Depends on chk_dev_supp_xmulti_ref_ext_src_info.
+ * @see chk_dev_supp_xmulti_ref_ext_src_info
+ */
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_ext_source_stats( const ALL_XMULTI_REF_INFO *info, int type ) ;
+
+ /*
+ * Type is NOT an index of ::XMULTI_REF_INSTANCES::n_xmr_settings,
+ * but of ::MULTI_REF_TYPES.
+ * Depends on chk_dev_supp_xmulti_ref_ext_src_info.
+ * @see chk_dev_supp_xmulti_ref_ext_src_info
+ */
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_xmulti_ref_supp_ext_source_metrics( const ALL_XMULTI_REF_INFO *info, int type ) ;
+
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_ims_has_fdm( const ALL_IMS_INFO *info ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_ims_is_volt_out_enabled( const ALL_IMS_STATE *ims_state, unsigned idx ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_ims_is_volt_out_overload( const ALL_IMS_STATE *ims_state, unsigned idx ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_ims_is_pll_locked( const ALL_IMS_STATE *ims_state, unsigned idx ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_gpio_supp_ass_idx( const ALL_GPIO_INFO *gpio_info, unsigned idx ) ;
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_gpio_dep_on_ass_idx( const ALL_GPIO_INFO *gpio_info, unsigned idx ) ;
+ /**
+ * @brief Checks whether GPIO supports status function
+ *
+ * @param[out] info Pointer to a ::ALL_GPIO_INFO structure to be filled up
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_gpio
+ * @see ::mbg_chk_dev_supp_gpio
+ * @see ::free_all_gpio_info
+ */
+ _NO_MBG_API_ATTR int _MBG_API chk_dev_gpio_has_status( const ALL_GPIO_INFO *info ) ;
+
+ /**
+ * @brief Frees ::ALL_XBP_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_XBP_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_xbp_info
+ */
+ void free_all_xbp_info ( ALL_XBP_INFO *p ) ;
+
+ /**
+ * @brief Frees ::ALL_NET_CFG_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_NET_CFG_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_net_cfg_info
+ */
+ void free_all_net_cfg_info ( ALL_NET_CFG_INFO *p ) ;
+
+ /**
+ * @brief Frees ::ALL_NET_STATUS_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_NET_STATUS_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_net_status_info
+ */
+ void free_all_net_status_info ( ALL_NET_STATUS_INFO *p ) ;
+
+ /**
+ * @brief Frees ::ALL_SNMP_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_SNMP_INFO structure, which will be freed
+ *
+ */
+ void free_all_snmp_info ( ALL_SNMP_INFO *p ) ;
+
+ /**
+ * @brief Frees ::ALL_MONITORING_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_MONITORING_INFO structure, which will be freed
+ *
+ */
+ void free_all_monitoring_info ( ALL_MONITORING_INFO *p ) ;
+
+ /**
+ * @brief Frees ::ALL_MONITORING_STATUS structure
+ *
+ * @param[in] p Pointer to the ::ALL_MONITORING_STATUS structure, which will be freed
+ *
+ */
+ void free_all_monitoring_status ( ALL_MONITORING_STATUS *p ) ;
+
+ /**
+ * @brief Frees ::ALL_XMULTI_REF_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_XMULTI_REF_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_xmulti_ref_info
+ * @see ::mbg_get_all_xmulti_ref_info
+ */
+ void free_all_xmulti_ref_info( ALL_XMULTI_REF_INFO *p ) ;
+
+ /**
+ * @brief Frees ::ALL_XMULTI_REF_STATUS structure
+ *
+ * @param[in] p Pointer to the ::ALL_XMULTI_REF_STATUS structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_xmulti_ref_status
+ * @see ::mbg_get_all_xmulti_ref_status
+ */
+ void free_all_xmulti_ref_status( ALL_XMULTI_REF_STATUS *p ) ;
+
+ /**
+ * @brief Frees ::ALL_PTP_V1_COMMON_DATASETS structure allocated by ::mbgextio_get_all_ptp_v1_common_datasets
+ *
+ * @param[in] p Pointer to the ::ALL_PTP_V1_COMMON_DATASETS structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ptp_v1_common_datasets
+ */
+ void free_all_ptp_v1_common_datasets( ALL_PTP_V1_COMMON_DATASETS *p ) ;
+
+ /**
+ * @brief Frees ::ALL_PTP_V2_COMMON_DATASETS structure allocated by ::mbgextio_get_all_ptp_v2_common_datasets
+ *
+ * @param[in] p Pointer to the ::ALL_PTP_V2_COMMON_DATASETS structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ptp_v2_common_datasets
+ */
+ void free_all_ptp_v2_common_datasets( ALL_PTP_V2_COMMON_DATASETS *p ) ;
+
+ /**
+ * @brief Frees ::ALL_NTP_CFG_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_NTP_CFG_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ntp_cfg_info
+ */
+ void free_all_ntp_cfg_info( ALL_NTP_CFG_INFO *p ) ;
+
+ /**
+ * @brief Frees ::ALL_NTP_STATUS structure
+ *
+ * @param[in] p Pointer to the ::ALL_NTP_STATUS structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ntp_status
+ */
+ void free_all_ntp_status( ALL_NTP_STATUS *p ) ;
+
+ /**
+ * @brief Frees memory allocated by ::mbgextio_get_all_ims_info
+ *
+ * @param[in] p Pointer to the ::ALL_IMS_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_dev_has_ims
+ * @see ::mbgextio_dev_ims_has_fdm
+ * @see ::mbgextio_get_all_ims_info
+ * @see ::mbgextio_get_all_ims_state
+ */
+ void free_all_ims_info( ALL_IMS_INFO *p ) ;
+
+ /**
+ * @brief Frees memory allocated by ::mbgextio_get_all_ims_state
+ *
+ * @param[in] p Pointer to the ::ALL_IMS_STATE structure, which will be freed
+ *
+ * @see ::mbgextio_dev_has_ims
+ * @see ::mbgextio_dev_ims_has_fdm
+ * @see ::mbgextio_get_all_ims_info
+ * @see ::mbgextio_get_all_ims_state
+ */
+ void free_all_ims_state( ALL_IMS_STATE *p ) ;
+
+ /**
+ * @brief Frees memory allocated by ::mbgextio_get_all_gpio_info
+ *
+ * @param[in] p Pointer to the ::ALL_GPIO_INFO structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_gpio
+ * @see ::mbgextio_get_all_gpio_info
+ */
+ void free_all_gpio_info( ALL_GPIO_INFO *p ) ;
+
+ /**
+ * @brief Frees memory allocated by ::mbgextio_get_all_io_port_info
+ *
+ * @param[in] p Pointer to the ::ALL_IO_PORT_INFO structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_io_ports
+ * @see ::mbgextio_get_all_io_port_info
+ * @see ::mbgextio_get_all_io_port_status
+ * @see ::free_all_io_port_status
+ */
+ void free_all_io_port_info( ALL_IO_PORT_INFO *p ) ;
+
+ /**
+ * @brief Frees memory allocated by ::mbgextio_get_all_io_port_status
+ *
+ * @param[in] p Pointer to the ::ALL_IO_PORT_STATUS structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_io_ports
+ * @see ::mbgextio_get_all_io_port_info
+ * @see ::mbgextio_get_all_io_port_status
+ * @see ::free_all_io_port_info
+ */
+ void free_all_io_port_status( ALL_IO_PORT_STATUS *p ) ;
+
+ /**
+ * @brief Frees memory allocated by ::mbgextio_get_all_gpio_state
+ *
+ * @param[in] p Pointer to the ::ALL_GPIO_STATE structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_gpio
+ * @see ::mbgextio_get_all_gpio_state
+ */
+ void free_all_gpio_state( ALL_GPIO_STATE *p ) ;
+
+ /**
+ * Allocates memory for a new ::UCAP_ENTRY structure
+ *
+ * @return The new allocated ::UCAP_ENTRY or null if the calloc call was not successful
+ */
+ UCAP_ENTRY* calloc_ucap_entry(void) ;
+
+ /**
+ * @brief Frees memory allocated by ::mbgextio_get_all_ucap_info
+ *
+ * @param[in] p Pointer to the ::ALL_UCAP_INFO structure, which will be freed
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgextio_dev_has_ucap
+ * @see ::mbg_chk_dev_has_ucap
+ * @see ::mbgextio_get_all_ucap_info
+ * @see ::mbg_get_all_ucap_info
+ */
+ void free_all_ucap_info( ALL_UCAP_INFO *p ) ;
+
+ /**
+ * @brief Frees ::ALL_UCAP_NET_INFO structure
+ *
+ * @param[in] p Pointer to the ::ALL_UCAP_NET_INFO structure, which will be freed
+ *
+ * @see ::mbgextio_get_all_ucap_net_info
+ */
+ void free_all_ucap_net_info( ALL_UCAP_NET_INFO *p ) ;
+
/* ----- function prototypes end ----- */
+#endif // !defined( MBG_TGT_KERNEL )
+
#ifdef __cplusplus
}
#endif
diff --git a/mbglib/common/charcode.h b/mbglib/common/charcode.h
new file mode 100755
index 0000000..192a0f4
--- /dev/null
+++ b/mbglib/common/charcode.h
@@ -0,0 +1,275 @@
+
+/**************************************************************************
+ *
+ * $Id: charcode.h 1.4 2016/08/10 12:25:41 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Definitions and prototypes for pcpslstr.c.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: charcode.h $
+ * Revision 1.4 2016/08/10 12:25:41 martin
+ * Check for MBG_TGT_POSIX instead of MBG_TGT_UNIX.
+ * Revision 1.3 2015/11/11 14:55:59 martin
+ * Support Unicode and UTF-8 encodings.
+ * Revision 1.2 2014/04/24 14:13:17 martin
+ * Added new codes and conversion table initializers.
+ * Revision 1.1 2012/11/20 13:41:24 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#ifndef _CHARCODE_H
+#define _CHARCODE_H
+
+
+/* Other headers to be included */
+
+#include <mbg_tgt.h>
+
+#if MBG_TGT_HAS_WCHAR_T
+ #include <wchar.h>
+#endif
+
+#ifdef _CHARCODE
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+#if defined( MBG_TGT_LINUX )
+
+ #define MBG_UML_UTF8
+
+#elif defined( MBG_TGT_WIN32 ) \
+ || defined( MBG_TGT_POSIX ) \
+ || defined( MBG_TGT_QNX )
+
+ #define MBG_UML_ANSI
+
+#else
+
+ #define MBG_UML_DOS
+
+#endif
+
+
+
+// upper case 'A' umlaut
+#define ANSI_UC_A_UML '\xC4' // uppercase ANSI char
+#define ANSI_US_A_UML "\xC4" // uppercase ANSI string literal
+
+#define DOS_UC_A_UML '\x8E' // uppercase DOS char
+#define DOS_US_A_UML "\x8E" // uppercase DOS string literal
+
+#define UNICODE_US_A_UML "\u00C4" // uppercase Unicode string literal
+
+#define UTF8_US_A_UML "\xc3\x84" // uppercase UTF-8 string literal
+
+
+
+// upper case 'O' umlaut
+#define ANSI_UC_O_UML '\xD6' // uppercase ANSI char
+#define ANSI_US_O_UML "\xD6" // uppercase ANSI string literal
+
+#define DOS_UC_O_UML '\x99' // uppercase DOS char
+#define DOS_US_O_UML "\x99" // uppercase DOS string literal
+
+#define UNICODE_US_O_UML "\u00D6" // uppercase Unicode string literal
+
+#define UTF8_US_O_UML "\xc3\x96" // uppercase UTF-8 string literal
+
+
+
+// upper case 'U' umlaut
+#define ANSI_UC_U_UML '\xDC' // uppercase ANSI char
+#define ANSI_US_U_UML "\xDC" // uppercase ANSI string literal
+
+#define DOS_UC_U_UML '\x9A' // uppercase DOS char
+#define DOS_US_U_UML "\x9A" // uppercase DOS string literal
+
+#define UNICODE_US_U_UML "\u00DC" // uppercase Unicode string literal
+
+#define UTF8_US_U_UML "\xc3\x9c" // uppercase UTF-8 string literal
+
+
+
+// lower case 'a' umlaut
+#define ANSI_LC_A_UML '\xE4' // lowercase ANSI char
+#define ANSI_LS_A_UML "\xE4" // lowercase ANSI string literal
+
+#define DOS_LC_A_UML '\x84' // lowercase DOS char
+#define DOS_LS_A_UML "\x84" // lowercase DOS string literal
+
+#define UNICODE_LS_A_UML "\u00E4" // lowercase Unicode string literal
+
+#define UTF8_LS_A_UML "\xc3\xa4" // lowercase UTF-8 string literal
+
+
+
+// lower case 'o' umlaut
+#define ANSI_LC_O_UML '\xF6' // lowercase ANSI char
+#define ANSI_LS_O_UML "\xF6" // lowercase ANSI string literal
+
+#define DOS_LC_O_UML '\x94' // lowercase DOS char
+#define DOS_LS_O_UML "\x94" // lowercase DOS string literal
+
+#define UNICODE_LS_O_UML "\u00F6" // lowercase Unicode string literal
+
+#define UTF8_LS_O_UML "\xc3\xb6" // lowercase UTF-8 string literal
+
+
+
+// lower case 'u' umlaut
+#define ANSI_LC_U_UML '\xFC' // lowercase ANSI char
+#define ANSI_LS_U_UML "\xFC" // lowercase ANSI string literal
+
+#define DOS_LC_U_UML '\x81' // lowercase DOS char
+#define DOS_LS_U_UML "\x81" // lowercase DOS string literal
+
+#define UNICODE_LS_U_UML "\u00FC" // lowercase Unicode string literal
+
+#define UTF8_LS_U_UML "\xc3\xbc" // lowercase UTF-8 string literal
+
+
+
+// 'sz' umlaut
+#define ANSI_LC_SZ_UML '\xDF' // ANSI char
+#define ANSI_LS_SZ_UML "\xDF" // ANSI string literal
+
+#define DOS_LC_SZ_UML '\xE1' // DOS char
+#define DOS_LS_SZ_UML "\xE1" // DOS string literal
+
+#define UNICODE_LS_SZ_UML "\u00DF" // Unicode string literal
+
+#define UTF8_LS_SZ_UML "\xc3\x9f" // UTF-8 string literal
+
+
+
+// degree character
+#define ANSI_C_DEGREE '\xB0' // ANSI char
+#define ANSI_S_DEGREE "\xB0" // ANSI string literal
+
+#define DOS_C_DEGREE '\xF8' // DOS char
+#define DOS_S_DEGREE "\xF8" // DOS string literal
+
+#define UNICODE_S_DEGREE "\u00E0" // Unicode string liter
+
+#define UTF8_S_DEGREE "\xc2\xb0" // UTF-8 string literal
+
+
+
+// greek mu character (micro sign)
+#define ANSI_C_MU '\xB5' // ANSI char
+#define ANSI_S_MU "\xB5" // ANSI string literal
+
+#define DOS_C_MU '\xE6' // DOS char
+#define DOS_S_MU "\xE6" // DOS string literal
+
+#define UNICODE_S_MU "\u00B5" // Unicode string liter
+
+#define UTF8_S_MU "\xc2\xb5" // UTF-8 string literal
+
+
+
+#if defined( MBG_UML_UTF8 )
+
+ #define UCAE UTF8_US_A_UML
+ #define UCOE UTF8_US_O_UML
+ #define UCUE UTF8_US_U_UML
+
+ #define LCAE UTF8_LS_A_UML
+ #define LCOE UTF8_LS_O_UML
+ #define LCUE UTF8_LS_U_UML
+
+ #define LCSZ UTF8_LS_SZ_UML
+ #define DEG UTF8_S_DEGREE
+ #define MU UTF8_S_MU
+
+#elif defined( MBG_UML_ANSI )
+
+ #define UCAE ANSI_US_A_UML
+ #define UCOE ANSI_US_O_UML
+ #define UCUE ANSI_US_U_UML
+
+ #define LCAE ANSI_LS_A_UML
+ #define LCOE ANSI_LS_O_UML
+ #define LCUE ANSI_LS_U_UML
+
+ #define LCSZ ANSI_LS_SZ_UML
+ #define DEG ANSI_S_DEGREE
+ #define MU ANSI_S_MU
+
+#elif defined( MBG_UML_DOS )
+
+ #define UCAE DOS_US_A_UML
+ #define UCOE DOS_US_O_UML
+ #define UCUE DOS_US_U_UML
+
+ #define LCAE DOS_LS_A_UML
+ #define LCOE DOS_LS_O_UML
+ #define LCUE DOS_LS_U_UML
+
+ #define LCSZ DOS_LS_SZ_UML
+ #define DEG DOS_S_DEGREE
+ #define MU DOS_S_MU
+
+#else
+
+ #error Need to define default encoding for umlauts.
+
+#endif
+
+
+
+// A string initializer which can be used to set up a string
+// to check if all umlauts are displayed correctly.
+#define UMLAUTS_STRING UCAE UCOE UCUE LCAE LCOE LCUE LCSZ DEG MU
+
+
+#define ANSI_UMLAUTS \
+{ \
+ ANSI_UC_A_UML, ANSI_UC_O_UML, ANSI_UC_U_UML, \
+ ANSI_LC_A_UML, ANSI_LC_O_UML, ANSI_LC_U_UML, \
+ ANSI_LC_SZ_UML, ANSI_C_DEGREE, ANSI_C_MU, 0 \
+}
+
+
+#define DOS_UMLAUTS \
+{ \
+ DOS_UC_A_UML, DOS_UC_O_UML, DOS_UC_U_UML, \
+ DOS_LC_A_UML, DOS_LC_O_UML, DOS_LC_U_UML, \
+ DOS_LC_SZ_UML, DOS_C_DEGREE, DOS_S_MU, 0 \
+}
+
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+/* (no header definitions found) */
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+/* End of header body */
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _CHARCODE_H */
diff --git a/mbglib/common/chk_time_info.c b/mbglib/common/chk_time_info.c
index 78f6ff6..67d7106 100755
--- a/mbglib/common/chk_time_info.c
+++ b/mbglib/common/chk_time_info.c
@@ -1,15 +1,26 @@
/**************************************************************************
*
- * $Id: chk_time_info.c 1.2 2013/03/04 16:01:01 martin REL_M $
+ * $Id: chk_time_info.c 1.3.1.1.1.3 2015/09/03 11:19:15 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
* Description:
- * NTP shared memory support functions.
+ * System time checking support functions.
*
* -----------------------------------------------------------------------
* $Log: chk_time_info.c $
+ * Revision 1.3.1.1.1.3 2015/09/03 11:19:15 martin
+ * Made mbg_snprint_hr_tstamp() more versatile
+ * by passing a new optional UTC offset parameter.
+ * Revision 1.3.1.1.1.2 2015/08/27 16:29:44 martin
+ * Use safe string functions from str_util.c.
+ * Revision 1.3.1.1.1.1 2014/11/10 10:35:57 martin
+ * Temporarily use a different definition of NANO_TIME_64.
+ * Revision 1.3.1.1 2013/11/08 14:56:36 martin
+ * Preliminary changes.
+ * Revision 1.3 2013/07/30 12:55:33 martin
+ * Updated file description.
* Revision 1.2 2013/03/04 16:01:01 martin
* Use common function setup_hr_time_cycles_from_timestamp_cycles().
* Made snprint_chk_time_info() more flexible.
@@ -23,6 +34,8 @@
#undef _CHK_TIME_INFO
#include <toolutil.h>
+#include <str_util.h>
+
#include <stdio.h>
@@ -81,7 +94,7 @@ int mbg_chk_time_info( MBG_DEV_HANDLE dh, MBG_CHK_TIME_INFO *p, FILTER *p_filter
p_sys_tic = &p->hrti.sys_time_cycles;
p->d_ref = (double) p_ref_ts->sec + ( (double) p_ref_ts->frac ) / (double) PCPS_HRT_BIN_FRAC_SCALE;
- p->d_sys = (double) p_sys_tic->sys_time.sec + (double) p_sys_tic->sys_time.nsec / 1e9;
+ p->d_sys = (double) p_sys_tic->sys_time.secs + (double) p_sys_tic->sys_time.nano_secs / 1e9;
p->ltcy_cyc = mbg_delta_pc_cycles( p_ref_cyc, &p_sys_tic->cyc_after );
p->exec_cyc = mbg_delta_pc_cycles( &p_sys_tic->cyc_after, &p_sys_tic->cyc_before );
@@ -115,40 +128,40 @@ int mbg_chk_time_info( MBG_DEV_HANDLE dh, MBG_CHK_TIME_INFO *p, FILTER *p_filter
/*HDR*/
-int snprint_chk_time_info( char *s, size_t max_len, const MBG_CHK_TIME_INFO *p, const PCPS_DEV *p_dev,
- int frac_digits, int print_raw )
+size_t snprint_chk_time_info( char *s, size_t max_len, const MBG_CHK_TIME_INFO *p, const PCPS_DEV *p_dev,
+ int frac_digits, int print_raw )
{
size_t n = 0;
if ( p_dev )
- n += snprintf( &s[n], max_len - n, "%-9s: ", _pcps_type_name( p_dev ) );
-
- n += mbg_snprint_hr_tstamp( &s[n], max_len - n, &p->hrti.ref_hr_time_cycles.t.tstamp, 0 ); // raw timestamp?
+ n += snprintf_safe( &s[n], max_len - n, "%-9s: ", _pcps_type_name( p_dev ) );
- n += snprintf( &s[n], max_len - n, ": %.*f-%.*f: ",
- frac_digits, p->d_ref,
- frac_digits, p->d_sys );
+ n += mbg_snprint_hr_tstamp( &s[n], max_len - n, &p->hrti.ref_hr_time_cycles.t.tstamp, 0, 0 ); // raw timestamp?
- if ( print_raw )
- n += snprintf( &s[n], max_len - n, "%+.*f->",
- frac_digits, p->d_ref - p->d_sys );
+ n += snprintf_safe( &s[n], max_len - n, " %.*f %.*f ",
+ frac_digits, p->d_ref,
+ frac_digits, p->d_sys );
- n += snprintf( &s[n], max_len - n, "%+.*f, ltcy: ",
- frac_digits, p->d_ref_comp - p->d_sys );
+ n += snprintf_safe( &s[n], max_len - n, "%+.*f, ltcy: ",
+ frac_digits, p->d_ref_comp - p->d_sys );
if ( cyc_freq ) // print latency and execution time in microseconds
{
- n += snprintf( &s[n], max_len - n, "%.2f us, exec: %.2f us, limit: %.2f us",
- p->ltcy_sec * 1e6, p->exec_sec * 1e6, p->exec_sec_limit * 1e6 );
+ n += snprintf_safe( &s[n], max_len - n, "%.2f us, exec: %.2f us, limit: %.2f us",
+ p->ltcy_sec * 1e6, p->exec_sec * 1e6, p->exec_sec_limit * 1e6 );
}
else // print latency and execution time in cycles only
{
- n += snprintf( &s[n], max_len - n, "%lli cyc, exec: %lli cyc, limit: %lli cyc",
- (long long) p->ltcy_cyc, (long long) p->exec_cyc,
- (long long) p->exec_cyc_limit );
+ n += snprintf_safe( &s[n], max_len - n, "%lli cyc, exec: %lli cyc, limit: %lli cyc",
+ (long long) p->ltcy_cyc, (long long) p->exec_cyc,
+ (long long) p->exec_cyc_limit );
}
+ if ( print_raw )
+ n += snprintf_safe( &s[n], max_len - n, ", raw: %+.*f",
+ frac_digits, p->d_ref - p->d_sys );
+
return n;
} // snprint_chk_time_info
diff --git a/mbglib/common/chk_time_info.h b/mbglib/common/chk_time_info.h
index 260691e..c1fc4b7 100755
--- a/mbglib/common/chk_time_info.h
+++ b/mbglib/common/chk_time_info.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: chk_time_info.h 1.2 2013/03/04 16:02:31 martin REL_M $
+ * $Id: chk_time_info.h 1.2.1.1 2015/08/27 16:29:54 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,7 @@
*
* -----------------------------------------------------------------------
* $Log: chk_time_info.h $
+ * Revision 1.2.1.1 2015/08/27 16:29:54 martin
* Revision 1.2 2013/03/04 16:02:31 martin
* Updated function prototypes.
* Revision 1.1 2012/05/29 09:52:27 martin
@@ -88,7 +89,7 @@ typedef struct
/* by MAKEHDR, do not remove the comments. */
int mbg_chk_time_info( MBG_DEV_HANDLE dh, MBG_CHK_TIME_INFO *p, FILTER *p_filter, int fast_ts_only ) ;
- int snprint_chk_time_info( char *s, size_t max_len, const MBG_CHK_TIME_INFO *p, const PCPS_DEV *p_dev, int frac_digits, int print_raw ) ;
+ size_t snprint_chk_time_info( char *s, size_t max_len, const MBG_CHK_TIME_INFO *p, const PCPS_DEV *p_dev, int frac_digits, int print_raw ) ;
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/cmp_time_util.c b/mbglib/common/cmp_time_util.c
new file mode 100755
index 0000000..de4c142
--- /dev/null
+++ b/mbglib/common/cmp_time_util.c
@@ -0,0 +1,287 @@
+
+/**************************************************************************
+ *
+ * $Id: cmp_time_util.c 1.1.1.3 2014/05/26 16:01:48 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Shared time campare utility functions.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: cmp_time_util.c $
+ * Revision 1.1.1.3 2014/05/26 16:01:48 martin
+ * Revision 1.1.1.2 2013/08/01 16:51:39 martin
+ * Revision 1.1.1.1 2013/08/01 15:17:30 marvin
+ * Revision 1.1 2013/07/25 10:42:59Z martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#define _CMP_TIME_UTIL
+ #include <cmp_time_util.h>
+#undef _CMP_TIME_UTIL
+
+#include <mbgdevio.h>
+#include <mbgutil.h>
+#include <pcpsutil.h>
+#include <stdio.h>
+
+
+//##++++++
+extern MBG_PC_CYCLES_FREQUENCY cyc_freq;
+
+
+/*HDR*/
+int chk_feat_supp( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, MBG_CHK_SUPP_FNC *chk_supp_fnc,
+ MBG_ERR_MSG_FNC err_msg_fnc, const char *not_supp_msg )
+{
+ int ret_val = MBG_SUCCESS; // assume option is supported
+
+ // If a check function has been specified we must call it to check
+ // if this parameter/command is supported by this particular device.
+ if ( chk_supp_fnc && ( dh != MBG_INVALID_DEV_HANDLE ) )
+ {
+ int is_supported;
+ int rc = chk_supp_fnc( dh, &is_supported );
+
+ if ( rc != MBG_SUCCESS )
+ {
+ if ( err_msg_fnc )
+ err_msg_fnc( p_dev, "Failed to check if supported" ); //##++++ TODO:proper error msg
+
+ ret_val = rc;
+ goto out;
+ }
+
+ if ( !is_supported )
+ {
+ ret_val = MBG_ERR_NOT_SUPP_BY_DEV;
+
+ if ( err_msg_fnc && not_supp_msg )
+ err_msg_fnc( p_dev, not_supp_msg );
+
+ goto out;
+ }
+ }
+
+out:
+ return ret_val;
+
+} // chk_feat_supp
+
+
+
+/*HDR*/
+int chk_fast_tstamp_supp( MBG_DEV_HANDLE dh1, const PCPS_DEV *p_dev_1,
+ MBG_DEV_HANDLE dh2, const PCPS_DEV *p_dev_2,
+ MBG_ERR_MSG_FNC err_msg_fnc )
+{
+ int rc;
+ const char n_supp_msg[] = "fast (memory mapped) time stamps";
+
+ rc = chk_feat_supp( dh1, p_dev_1, mbg_dev_has_fast_hr_timestamp,
+ err_msg_fnc, n_supp_msg );
+
+ if ( rc == MBG_SUCCESS )
+ rc = chk_feat_supp( dh2, p_dev_2, mbg_dev_has_fast_hr_timestamp,
+ err_msg_fnc, n_supp_msg );
+ return rc;
+
+} // chk_fast_tstamp_supp
+
+
+
+/*HDR*/
+int get_htc_timestamps( MBG_DEV_HANDLE dh1, PCPS_HR_TIME_CYCLES *p_htc1,
+ MBG_DEV_HANDLE dh2, PCPS_HR_TIME_CYCLES *p_htc2,
+ int read_fast )
+{
+ int rc;
+
+ if ( read_fast )
+ {
+ PCPS_TIME_STAMP_CYCLES ts_c1;
+ PCPS_TIME_STAMP_CYCLES ts_c2;
+
+ rc = mbg_get_fast_hr_timestamp_cycles( dh1, &ts_c1 );
+
+ if ( mbg_ioctl_err( rc, "mbg_get_fast_hr_timestamp_cycles 1" ) )
+ goto done;
+
+ rc = mbg_get_fast_hr_timestamp_cycles( dh2, &ts_c2 );
+
+ if ( mbg_ioctl_err( rc, "mbg_get_fast_hr_timestamp_cycles 2" ) )
+ goto done;
+
+ setup_hr_time_cycles_from_timestamp_cycles( p_htc1, &ts_c1 );
+ setup_hr_time_cycles_from_timestamp_cycles( p_htc2, &ts_c2 );
+ }
+ else
+ {
+ rc = mbg_get_hr_time_cycles( dh1, p_htc1 );
+
+ if ( mbg_ioctl_err( rc, "mbg_get_hr_time_cycles 1" ) )
+ goto done;
+
+ rc = mbg_get_hr_time_cycles( dh2, p_htc2 );
+
+ if ( mbg_ioctl_err( rc, "mbg_get_hr_time_cycles 2" ) )
+ goto done;
+ }
+
+done:
+ return rc;
+
+} // get_htc_timestamps
+
+
+
+/*HDR*/
+double get_htc_delta( const PCPS_HR_TIME_CYCLES *p_htc,
+ const PCPS_HR_TIME_CYCLES *p_htc_ref,
+ double *p_delta_ts, double *p_delta_cyc )
+{
+ double delta_ts;
+ double delta_cyc;
+
+ delta_ts = (double) p_htc->t.tstamp.sec + dfrac_sec_from_bin( p_htc->t.tstamp.frac )
+ - (double) p_htc_ref->t.tstamp.sec - dfrac_sec_from_bin( p_htc_ref->t.tstamp.frac );
+
+ #if defined( MBG_TGT_WIN32 )
+ {
+ __int64 dt_t = p_htc->cycles - p_htc_ref->cycles;
+ delta_cyc = (double) dt_t / (__int64) cyc_freq;
+ }
+ #else
+ delta_cyc = ( (double) ( p_htc->cycles - p_htc_ref->cycles ) ) / cyc_freq;
+ #endif
+
+ if ( p_delta_ts )
+ *p_delta_ts = delta_ts;
+
+ if ( p_delta_cyc )
+ *p_delta_cyc = delta_cyc;
+
+ return delta_ts - delta_cyc;
+
+} // get_htc_delta
+
+
+
+/*HDR*/
+int mbg_snprint_hr_tstamp_ext( char *s, int max_len,
+ const PCPS_TIME_STAMP *p_ts, int print_raw )
+{
+ int n = mbg_snprint_hr_tstamp( s, max_len, p_ts, 0 );
+
+ if ( print_raw )
+ n += snprintf( &s[n], max_len - n, " (0x%08lX.%08lX)",
+ (ulong) p_ts->sec,
+ (ulong) p_ts->frac );
+
+ return n;
+
+} // mbg_snprint_hr_tstamp_ext
+
+
+
+#if defined( MBG_WX )
+
+/*HDR*/
+int mbg_snprint_hr_tstamp( char *s, int len_s, const PCPS_TIME_STAMP *p, int show_raw )
+{
+ int n = 0;
+
+ // We'll use the standard C library functions to convert the seconds
+ // to broken-down calendar date and time.
+ time_t t = p->sec;
+
+ // Our time stamp may be UTC, or have been converted to local time.
+ // Anyway, since we don't want to account for the system's time zone
+ // settings, we always use the gmtime() function for conversion:
+ struct tm *tmp = gmtime( &t );
+
+ if ( show_raw )
+ n += snprintf( s + n, len_s - n, "raw: 0x%08lX.%08lX, ",
+ (ulong) p->sec,
+ (ulong) p->frac );
+
+ n += snprintf( s + n, len_s - n, "%04i-%02i-%02i %02i:%02i:%02i." PCPS_HRT_FRAC_SCALE_FMT,
+ tmp->tm_year + 1900,
+ tmp->tm_mon + 1,
+ tmp->tm_mday,
+ tmp->tm_hour,
+ tmp->tm_min,
+ tmp->tm_sec,
+ (ulong) frac_sec_from_bin( p->frac, PCPS_HRT_FRAC_SCALE )
+ );
+
+ return n;
+
+} // mbg_snprint_hr_tstamp
+
+#endif
+
+
+
+/*HDR*/
+int mbg_snprint_hr_time_loc( char *s, int len_s, const PCPS_HR_TIME *p )
+{
+ int n = 0;
+
+ // We'll use the standard C library functions to convert the seconds
+ // to broken-down calendar date and time.
+ time_t t = p->tstamp.sec + p->utc_offs;
+
+ // Our time stamp may be UTC, or have been converted to local time.
+ // Anyway, since we don't want to account for the system's time zone
+ // settings, we always use the gmtime() function for conversion:
+ struct tm *tmp = gmtime( &t );
+
+ n += snprintf( s + n, len_s - n, "%04i-%02i-%02i %02i:%02i:%02i." PCPS_HRT_FRAC_SCALE_FMT,
+ tmp->tm_year + 1900,
+ tmp->tm_mon + 1,
+ tmp->tm_mday,
+ tmp->tm_hour,
+ tmp->tm_min,
+ tmp->tm_sec,
+ (ulong) frac_sec_from_bin( p->tstamp.frac, PCPS_HRT_FRAC_SCALE )
+ );
+
+ n += snprintf( s + n, len_s - n, " UTC" );
+
+ if ( !(p->status & PCPS_UTC ) )
+ n += mbg_str_pcps_hr_time_offs( s + n, len_s - n, p, "" );
+
+#if 0
+ if(p->utc_offs != 0)
+ n += mbg_snprintf( n, len_s - n, "(%+02luh",
+ ( pt->utc_offs < 0 ) ? '-' : '+',
+ ldt.quot, ldt.rem );
+#endif
+
+ return n;
+
+} // mbg_snprint_hr_time_loc
+
+
+
+#if defined( MBG_WX )
+
+/*HDR*/
+int mbg_ioctl_err( int rc, const char *descr )
+{
+ if ( rc < 0 )
+ {
+ fprintf( stderr, "** IOCTL error %i: ", rc );
+ perror( descr );
+ return -1;
+ }
+
+ return 0;
+
+} // mbg_ioctl_err
+
+#endif
+
diff --git a/mbglib/common/cmp_time_util.h b/mbglib/common/cmp_time_util.h
new file mode 100755
index 0000000..88dcd73
--- /dev/null
+++ b/mbglib/common/cmp_time_util.h
@@ -0,0 +1,87 @@
+
+/**************************************************************************
+ *
+ * $Id: cmp_time_util.h 1.1.2.1 2015/07/09 08:16:46 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Definitions and prototypes for cmp_time_util.c.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: cmp_time_util.h $
+ * Revision 1.1.2.1 2015/07/09 08:16:46 martin
+ * Tmp. backward compatibility patch for mbgtools-lx-dev-2014-12-02.
+ * Revision 1.1 2013/07/25 10:42:59 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#ifndef _CMP_TIME_UTIL_H
+#define _CMP_TIME_UTIL_H
+
+
+/* Other headers to be included */
+
+#include <mbgdevio.h>
+#include <toolutil.h>
+
+
+#ifdef _CMP_TIME_UTIL
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#if 0 && defined( _USE_PACK ) // use default alignment
+ #pragma pack( 1 ) // set byte alignment
+ #define _USING_BYTE_ALIGNMENT
+#endif
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+typedef int (*MBG_ERR_MSG_FNC)( const PCPS_DEV *p_dev, const char *s );
+
+typedef int _MBG_API MBG_CHK_SUPP_FNC( MBG_DEV_HANDLE dh, int *p );
+
+
+
+/* function prototypes: */
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+ int chk_feat_supp( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, MBG_CHK_SUPP_FNC *chk_supp_fnc, MBG_ERR_MSG_FNC err_msg_fnc, const char *not_supp_msg ) ;
+ int chk_fast_tstamp_supp( MBG_DEV_HANDLE dh1, const PCPS_DEV *p_dev_1, MBG_DEV_HANDLE dh2, const PCPS_DEV *p_dev_2, MBG_ERR_MSG_FNC err_msg_fnc ) ;
+ int get_htc_timestamps( MBG_DEV_HANDLE dh1, PCPS_HR_TIME_CYCLES *p_htc1, MBG_DEV_HANDLE dh2, PCPS_HR_TIME_CYCLES *p_htc2, int read_fast ) ;
+ double get_htc_delta( const PCPS_HR_TIME_CYCLES *p_htc, const PCPS_HR_TIME_CYCLES *p_htc_ref, double *p_delta_ts, double *p_delta_cyc ) ;
+ int mbg_snprint_hr_tstamp_ext( char *s, int max_len, const PCPS_TIME_STAMP *p_ts, int print_raw ) ;
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+
+#if defined( _USING_BYTE_ALIGNMENT )
+ #pragma pack() // set default alignment
+ #undef _USING_BYTE_ALIGNMENT
+#endif
+
+/* End of header body */
+
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _CMP_TIME_UTIL_H */
+
diff --git a/mbglib/common/ctrydttm.c b/mbglib/common/ctrydttm.c
index 4d35644..d8ada7c 100755
--- a/mbglib/common/ctrydttm.c
+++ b/mbglib/common/ctrydttm.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: ctrydttm.c 1.5 2008/11/24 16:15:46 martin REL_M $
+ * $Id: ctrydttm.c 1.7 2015/11/09 11:22:12 martin REL_M $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -11,11 +11,16 @@
*
* -----------------------------------------------------------------------
* $Log: ctrydttm.c $
- * Revision 1.5 2008/11/24 16:15:46 martin
+ * Revision 1.7 2015/11/09 11:22:12 martin
+ * Modified snprint_ctry_dt_short() and fixed snprint_ctry_dt().
+ * Revision 1.6 2015/08/31 10:00:46 martin
+ * Use safe string functions from str_util.c.
+ * This required renaming of functions and changing parameters.
+ * Revision 1.5 2008/11/24 16:15:46Z martin
* Don't use sprintf() without format string.
* Revision 1.4 2000/11/27 10:06:27 MARTIN
* Renamed local variable wday_str to lstrs_wday.
- * If macro USER_LSTR_WDAY is defined, lstrs_wday can be declared
+ * If macro USER_LSTR_WDAY is defined, lstrs_wday can be declared
* externally to override the defaults.
* Revision 1.3 2000/09/14 15:13:25 MARTIN
* Renamed sprint_short_ctry_dt() to sprint_ctry_dt_short() to match
@@ -30,6 +35,7 @@
#undef _CTRYDTTM
#include <ctry.h>
+#include <str_util.h>
#include <stdio.h>
@@ -53,45 +59,44 @@ extern LANGUAGE language;
/*HDR*/
-ushort sprint_02u( char *s, uchar uc )
+size_t snprint_02u( char *s, size_t max_len, uchar uc )
{
- return( sprintf( s, "%02u", uc ) );
+ return snprintf_safe( s, max_len, "%02u", uc );
-} // sprint_02u
+} // snprint_02u
/*HDR*/
-ushort sprint_04u( char *s, ushort us )
+size_t snprint_04u( char *s, size_t max_len, ushort us )
{
- return( sprintf( s, "%04u", us ) );
+ return snprintf_safe( s, max_len, "%04u", us );
-} // sprint_04u
+} // snprint_04u
/*HDR*/
-ushort sprint_ctry_wday( char *s, uchar wday, ushort language )
+size_t snprint_ctry_wday( char *s, size_t max_len, uchar wday, ushort language )
{
if ( language >= N_LNG )
language = LNG_ENGLISH;
- return( sprintf( s, "%s", ( wday < DAYS_PER_WEEK ) ?
- lstrs_wday[language][wday] : "--" ) );
+ return snprintf_safe( s, max_len, "%s", ( wday < DAYS_PER_WEEK ) ?
+ lstrs_wday[language][wday] : "--" );
-} // sprint_ctry_wday
+} // snprint_ctry_wday
/*HDR*/
-ushort sprint_ctry_dt_short( char *s, uchar mday, uchar month )
+size_t snprint_ctry_dt_short( char *s, size_t max_len, uchar mday, uchar month )
{
uchar tmp_1;
uchar tmp_2;
ushort n = 0;
-
- switch( ctry.dt_fmt )
+ switch ( ctry.dt_fmt )
{
case DT_FMT_YYYYMMDD:
case DT_FMT_MMDDYYYY:
@@ -106,79 +111,77 @@ ushort sprint_ctry_dt_short( char *s, uchar mday, uchar month )
} // switch
- n = sprint_02u( s, tmp_1 );
- s[n++] = ctry.dt_sep;
- n += sprint_02u( &s[n], tmp_2 );
- s[n++] = ctry.dt_sep;
- s[n] = 0;
+ n = snprint_02u( s, max_len, tmp_1 );
+ n += sn_cpy_char_safe( &s[n], max_len - n, ctry.dt_sep );
+ n += snprint_02u( &s[n], max_len - n, tmp_2 );
- return( n );
+ return n;
-} // sprint_ctry_dt_short
+} // snprint_ctry_dt_short
/*HDR*/
-ushort sprint_ctry_dt( char *s, uchar mday, uchar month, ushort year )
+size_t snprint_ctry_dt( char *s, size_t max_len, uchar mday, uchar month, ushort year )
{
- ushort n = 0;
-
+ size_t n = 0;
if ( ctry.dt_fmt == DT_FMT_YYYYMMDD )
{
- n = sprint_04u( s, year );
- s[n++] = ctry.dt_sep;
+ n += snprint_04u( &s[n], max_len - n, year );
+ n += sn_cpy_char_safe( &s[n], max_len - n, ctry.dt_sep );
}
- n += sprint_ctry_dt_short( &s[n], mday, month );
+ n += snprint_ctry_dt_short( &s[n], max_len - n, mday, month );
- if ( ctry.dt_fmt == DT_FMT_YYYYMMDD )
- s[--n] = 0;
- else
- n += sprint_04u( &s[n], year );
+ if ( ctry.dt_fmt != DT_FMT_YYYYMMDD )
+ {
+ n += sn_cpy_char_safe( &s[n], max_len - n, ctry.dt_sep );
+ n += snprint_04u( &s[n], max_len - n, year );
+ }
- return( n );
+ return n;
-} // sprint_ctry_dt
+} // snprint_ctry_dt
/*HDR*/
-ushort sprint_ctry_tm_short( char *s, uchar hour, uchar minute )
+size_t snprint_ctry_tm_short( char *s, size_t max_len, uchar hour, uchar minute )
{
- ushort n = sprint_02u( s, hour );
- s[n++] = ctry.tm_sep;
- n += sprint_02u( &s[n], minute );
+ size_t n = snprint_02u( s, max_len, hour );
+ n += sn_cpy_char_safe( &s[n], max_len - n, ctry.tm_sep );
+ n += snprint_02u( &s[n], max_len - n, minute );
- return( n );
+ return n;
-} // sprint_ctry_tm_short
+} // snprint_ctry_tm_short
/*HDR*/
-ushort sprint_ctry_tm( char *s, uchar hour, uchar minute, uchar second )
+size_t snprint_ctry_tm( char *s, size_t max_len, uchar hour, uchar minute, uchar second )
{
- ushort n = sprint_ctry_tm_short( s, hour, minute );
- s[n++] = ctry.tm_sep;
- n += sprint_02u( &s[n], second );
+ size_t n = snprint_ctry_tm_short( s, max_len, hour, minute );
+ n += sn_cpy_char_safe( &s[n], max_len - n, ctry.tm_sep );
+ n += snprint_02u( &s[n], max_len - n, second );
- return( n );
+ return n;
-} // sprint_ctry_tm
+} // snprint_ctry_tm
/*HDR*/
-ushort sprint_ctry_tm_long( char *s, uchar hour, uchar minute, uchar second,
- long frac, ushort frac_digits )
+size_t snprint_ctry_tm_long( char *s, size_t max_len, uchar hour, uchar minute,
+ uchar second, long frac, ushort frac_digits )
{
- ushort n = sprint_ctry_tm( s, hour, minute, second );
- s[n++] = '.';
- n += sprintf( &s[n], "%0*lu", frac_digits, frac );
+ size_t n = snprint_ctry_tm( s, max_len, hour, minute, second );
+ n += sn_cpy_char_safe( &s[n], max_len - n, '.' );
+ n += snprintf_safe( &s[n], max_len - n, "%0*lu", frac_digits, frac );
- return( n );
+ return n;
-} // sprint_ctry_tm_long
+} // snprint_ctry_tm_long
diff --git a/mbglib/common/ctrydttm.h b/mbglib/common/ctrydttm.h
index ce613d7..0d2807e 100755
--- a/mbglib/common/ctrydttm.h
+++ b/mbglib/common/ctrydttm.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: ctrydttm.h 1.3 2000/09/14 15:13:45 MARTIN REL_M $
+ * $Id: ctrydttm.h 1.5 2015/08/31 10:00:46 martin REL_M $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,10 @@
*
* -----------------------------------------------------------------------
* $Log: ctrydttm.h $
+ * Revision 1.5 2015/08/31 10:00:46 martin
+ * Fixed DOS build.
+ * Revision 1.4 2015/08/27 16:28:25Z martin
+ * Updated function prototypes.
* Revision 1.3 2000/09/14 15:13:45 MARTIN
* Updated function prototypes.
* Revision 1.2 2000/07/21 11:50:43 MARTIN
@@ -25,6 +29,8 @@
#include <ctry.h>
+#include <stdlib.h>
+
#ifdef __cplusplus
extern "C" {
@@ -49,14 +55,14 @@ extern "C" {
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
- ushort sprint_02u( char *s, uchar uc ) ;
- ushort sprint_04u( char *s, ushort us ) ;
- ushort sprint_ctry_wday( char *s, uchar wday, ushort language ) ;
- ushort sprint_ctry_dt_short( char *s, uchar mday, uchar month ) ;
- ushort sprint_ctry_dt( char *s, uchar mday, uchar month, ushort year ) ;
- ushort sprint_ctry_tm_short( char *s, uchar hour, uchar minute ) ;
- ushort sprint_ctry_tm( char *s, uchar hour, uchar minute, uchar second ) ;
- ushort sprint_ctry_tm_long( char *s, uchar hour, uchar minute, uchar second, long frac, ushort frac_digits ) ;
+ size_t snprint_02u( char *s, size_t max_len, uchar uc ) ;
+ size_t snprint_04u( char *s, size_t max_len, ushort us ) ;
+ size_t snprint_ctry_wday( char *s, size_t max_len, uchar wday, ushort language ) ;
+ size_t snprint_ctry_dt_short( char *s, size_t max_len, uchar mday, uchar month ) ;
+ size_t snprint_ctry_dt( char *s, size_t max_len, uchar mday, uchar month, ushort year ) ;
+ size_t snprint_ctry_tm_short( char *s, size_t max_len, uchar hour, uchar minute ) ;
+ size_t snprint_ctry_tm( char *s, size_t max_len, uchar hour, uchar minute, uchar second ) ;
+ size_t snprint_ctry_tm_long( char *s, size_t max_len, uchar hour, uchar minute, uchar second, long frac, ushort frac_digits ) ;
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/deviohlp.c b/mbglib/common/deviohlp.c
index 6261ca8..991a1a2 100755
--- a/mbglib/common/deviohlp.c
+++ b/mbglib/common/deviohlp.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: deviohlp.c 1.2 2012/10/15 13:48:35 martin REL_M $
+ * $Id: deviohlp.c 1.2.1.47 2016/11/08 17:21:49 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -18,7 +18,89 @@
*
* -----------------------------------------------------------------------
* $Log: deviohlp.c $
- * Revision 1.2 2012/10/15 13:48:35 martin
+ * Revision 1.2.1.47 2016/11/08 17:21:49 martin
+ * Doxygen fixes.
+ * Revision 1.2.1.46 2016/09/08 10:36:20 martin
+ * Removed obsolete parameter from an API call.
+ * Revision 1.2.1.45 2016/08/25 13:52:06Z thomas-b
+ * Adapted net_cfg functions to the structure changes
+ * Revision 1.2.1.44 2016/08/09 07:09:41 martin
+ * *** empty log message ***
+ * Revision 1.2.1.43 2016/07/22 09:58:45 martin
+ * Excluded some test code from build.
+ * Revision 1.2.1.42 2016/06/21 14:13:26 thomas-b
+ * Fixed bug when checking if ttm is available
+ * Revision 1.2.1.41 2016/06/21 12:07:35 thomas-b
+ * Adapted mbg_get_all_ucap_info to the new ALL_UCAP_INFO structure
+ * Revision 1.2.1.40 2016/06/15 14:04:06 thomas-b
+ * Added function mbg_get_all_ucap_info
+ * Revision 1.2.1.39 2016/06/01 11:35:29 martin
+ * Removed some code which is now in mbgdevio.c,h.
+ * Revision 1.2.1.38 2016/06/01 10:07:44 daniel
+ * *** empty log message ***
+ * Revision 1.2.1.37 2016/05/26 11:00:10 thomas-b
+ * Added parameter ALL_NTP_CFG_INFO to mbgextio_get_all_ntp_status
+ * Use calloc instead of realloc due to performance improvement
+ * Revision 1.2.1.36 2016/05/11 14:37:20 thomas-b
+ * Added functions to read/write ALL_NET_CFG_INFO and ALL_NET_STATUS_INFO
+ * Revision 1.2.1.35 2016/04/26 09:11:11 martin
+ * Made pcps_time_is_valid an inline function.
+ * Revision 1.2.1.34 2016/04/25 14:47:56Z martin
+ * *** empty log message ***
+ * Revision 1.2.1.33 2016/04/20 12:37:54 thomas-b
+ * Moved free functions for ALL_XMULTI_REF_INFO and ALL_XMULTI_REF_STATUS to cfg_hlp
+ * Revision 1.2.1.32 2016/04/18 14:45:29 thomas-b
+ * Added functions to get and save xmr info and status
+ * Revision 1.2.1.31 2016/04/04 12:29:30 thomas-b
+ * Reworked chk_bus_flags and PCI/PCI-E functions
+ * Revision 1.2.1.30 2016/03/30 07:56:55 thomas-b
+ * Fixed chk_bus_flags and mbg_chk_dev_is_pci
+ * Revision 1.2.1.29 2016/03/24 14:08:46 martin
+ * *** empty log message ***
+ * Revision 1.2.1.28 2016/03/22 10:53:29 martin
+ * *** empty log message ***
+ * Revision 1.2.1.27 2016/03/10 10:11:58 thomas-b
+ * Added functions, which check to which bus a device is connected
+ * Revision 1.2.1.26 2015/11/20 15:18:09 martin
+ * Revision 1.2.1.25 2015/11/02 11:00:48Z martin
+ * *** empty log message ***
+ * Revision 1.2.1.24 2015/10/28 16:06:40 martin
+ * Revision 1.2.1.23 2015/10/26 14:13:22Z martin
+ * Revision 1.2.1.22 2015/10/26 14:15:22Z martin
+ * Revision 1.2.1.21 2015/10/21 11:31:17Z martin
+ * *** empty log message ***
+ * Revision 1.2.1.20 2015/10/21 11:29:16 martin
+ * *** empty log message ***
+ * Revision 1.2.1.19 2015/10/21 11:21:51 martin
+ * *** empty log message ***
+ * Revision 1.2.1.18 2015/10/20 15:19:24 martin
+ * *** empty log message ***
+ * Revision 1.2.1.17 2015/10/19 16:42:15 martin
+ * *** empty log message ***
+ * Revision 1.2.1.16 2015/10/12 10:12:31 martin
+ * *** empty log message ***
+ * Revision 1.2.1.15 2015/10/08 13:27:37 martin
+ * *** empty log message ***
+ * Revision 1.2.1.14 2015/10/07 16:03:20 martin
+ * *** empty log message ***
+ * Revision 1.2.1.13 2015/10/07 10:54:19 martin
+ * Modified GNSS support.
+ * Revision 1.2.1.12 2015/09/17 10:05:17 martin
+ * Revision 1.2.1.11 2015/09/15 09:11:50Z martin
+ * *** empty log message ***
+ * Revision 1.2.1.10 2014/11/19 16:02:52 martin
+ * Revision 1.2.1.9 2014/10/29 16:25:31 martin
+ * Moved some functions and structures to more convenient files.
+ * Revision 1.2.1.8 2014/10/27 10:43:18 martin
+ * Revision 1.2.1.7 2014/07/14 15:42:45 martin
+ * Revision 1.2.1.6 2014/06/30 15:43:44 martin
+ * Revision 1.2.1.5 2014/04/28 12:21:26 martin
+ * Revision 1.2.1.4 2014/04/28 10:32:40 martin
+ * Revision 1.2.1.3 2014/04/28 09:49:15 martin
+ * Revision 1.2.1.2 2013/12/17 15:05:31 martin
+ * Revision 1.2.1.1 2013/12/16 13:53:27Z martin
+ * GNSS support
+ * Revision 1.2 2012/10/15 13:48:35Z martin
* Added functions mbg_get_all_ptp_cfg_info(), mbg_save_all_ptp_cfg_info().
* Revision 1.1.1.9 2012/07/18 11:00:46 martin
* Revision 1.1.1.8 2012/07/12 09:07:36Z martin
@@ -30,7 +112,7 @@
* Revision 1.1.1.4 2011/09/21 14:45:24 martin
* Moved mbgextio support functions to new module extiohlp.c.
* Revision 1.1.1.3 2011/09/20 15:36:02 marvin
- * new functions:
+ * new functions:
* mbg_get_serial_settings
* mbg_set_serial_settings
* include mbgextio.h
@@ -45,104 +127,283 @@
#include <deviohlp.h>
#undef _DEVIOHLP
-#include <parmpcps.h>
-#include <parmgps.h>
+#include <str_util.h>
+#include <lan_util.h>
+#include <stdio.h>
+
+
+#define DEFAULT_BAUD_RATES_DCF \
+( \
+ MBG_PORT_HAS_300 | \
+ MBG_PORT_HAS_600 | \
+ MBG_PORT_HAS_1200 | \
+ MBG_PORT_HAS_2400 | \
+ MBG_PORT_HAS_4800 | \
+ MBG_PORT_HAS_9600 \
+)
+
+#define DEFAULT_BAUD_RATES_DCF_HS \
+( \
+ MBG_PORT_HAS_300 | \
+ MBG_PORT_HAS_600 | \
+ MBG_PORT_HAS_1200 | \
+ MBG_PORT_HAS_2400 | \
+ MBG_PORT_HAS_4800 | \
+ MBG_PORT_HAS_9600 | \
+ MBG_PORT_HAS_19200 | \
+ MBG_PORT_HAS_38400 \
+)
+
+
+#define DEFAULT_FRAMINGS_DCF \
+( \
+ MBG_PORT_HAS_7E2 | \
+ MBG_PORT_HAS_8N1 | \
+ MBG_PORT_HAS_8N2 | \
+ MBG_PORT_HAS_8E1 \
+)
+
+
+/*HDR*/
+int chk_feat_supp( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, MBG_CHK_SUPP_FNC *chk_supp_fnc,
+ MBG_ERR_MSG_FNC err_msg_fnc, const char *not_supp_msg )
+{
+ const char *cp = NULL;
+ int rc = MBG_SUCCESS; // assume option is supported
+
+ if ( chk_supp_fnc == NULL ) // no check function specified
+ goto out;
+
+
+ // A check function has been specified, so we must call it to check if
+ // the specific parameter/command is supported by this particular device.
+
+ if ( dh == MBG_INVALID_DEV_HANDLE )
+ {
+ cp = "Tried checking feature support with invalid device handle.";
+ rc = MBG_ERR_INV_HANDLE;
+ goto out;
+ }
+
+ rc = chk_supp_fnc( dh );
+
+ if ( mbg_rc_is_success( rc ) )
+ goto out; // return with success
+
+
+ if ( rc == MBG_ERR_NOT_SUPP_BY_DEV )
+ {
+ cp = not_supp_msg;
+ goto fail;
+ }
+
+
+ cp = "Failed to check if supported"; //##++++ TODO:proper error msg
+
+fail:
+ if ( err_msg_fnc && cp )
+ err_msg_fnc( p_dev, cp );
+
+out:
+ return rc;
+
+} // chk_feat_supp
/*HDR*/
/**
- Read all serial port settings and supported configuration parameters.
+ * @brief Read or setup all GNSS status information
+ *
+ * This function should be called preferably to get a summary of
+ * the GNSS status from GNSS receivers (GPS, GLONASS, ...).
+ *
+ * The function ::mbg_get_device_info must have been called before, and
+ * the returned ::PCPS_DEV structure has to be passed to this function.
+ *
+ * If the device supports this then the low level GNSS API functions
+ * are called directly to collect the status information. If the device
+ * doesn't support the GNSS API but is a pure GPS receiver then the GPS
+ * API functions are called and the GNSS data structures are filled up
+ * accordingly, so the calling application can always evaluate the
+ * GNSS data structures in ::ALL_GNSS_INFO.
+ *
+ * If neither GPS nor another GNSS system is supported then this function
+ * returns the ::MBG_ERR_NOT_SUPP_BY_DEV error.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p_agi Pointer to a ::ALL_GNSS_INFO to be filled
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_stat_info
+ * @see ::mbg_get_gps_gnss_mode_info
+ * @see ::mbg_get_gps_all_gnss_sat_info
+ */
+int mbg_chk_get_all_gnss_info( MBG_DEV_HANDLE dh, ALL_GNSS_INFO *p_agi )
+{
+ int rc = MBG_ERR_UNSPEC;
- The functions mbg_get_device_info() and mbg_setup_receiver_info()
- must have been called before, and the returned ::PCPS_DEV and
- ::RECEIVER_INFO structures must be passed to this function.
+ memset( p_agi, 0, sizeof( *p_agi ) );
+
+ // First we check if the device is a GPS receiver,
+ // which includes GNSS receivers.
+ rc = mbg_chk_dev_is_gps( dh );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+
+ // Read the STAT_INFO structure which is supported by all GPS
+ // and GNSS receivers.
+ rc = mbg_get_gps_stat_info( dh, &p_agi->stat_info );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+
+ // Check if the device is a GNSS receiver, i.e. can track satellites
+ // from different systems (GPS, GLONASS, Beidou, ...).
+ rc = mbg_chk_dev_is_gnss( dh );
+
+ if ( mbg_rc_is_success( rc ) )
+ {
+ // The device is a GNSS receiver, i.e. it can track satellites
+ // from different systems (GPS, GLONASS, Beidou, ...).
+ // Read some specific GNSS information.
+ rc = mbg_get_gps_gnss_mode_info( dh, &p_agi->gnss_mode_info );
- The complementary function mbg_save_serial_settings() should be used
- to write the modified serial port configuration back to the board.
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
- @param dh Valid handle to a Meinberg device.
- @param *pdev Pointer to a ::PCPS_DEV structure.
- @param *pcfg Pointer to a ::RECEIVER_PORT_CFG structure to be filled up.
- @param *p_ri Pointer to a ::RECEIVER_INFO structure.
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ rc = chk_set_n_gnss_supp( p_agi );
- @see mbg_get_device_info()
- @see mbg_setup_receiver_info()
- @see mbg_save_serial_settings()
-*/
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+
+ // If the the device supports the current API we can simply
+ // retrieve status information for each individual GNSS system.
+ rc = mbg_get_gps_all_gnss_sat_info( dh, p_agi->gnss_sat_info_idx, &p_agi->gnss_mode_info );
+ goto out;
+ }
+
+
+ // If we get here then the device is a pure GPS receiver
+ // which neither supports additional GNSS systems nor the
+ // associated data structures, so we set up all GNSS
+ // data structures for GPS only.
+ rc = setup_gps_only_gnss_info_from_statinfo( p_agi );
+
+out:
+ return rc;
+
+} // mbg_chk_get_all_gnss_info
+
+
+
+#if !MBGDEVIO_SIMPLE
+
+/*HDR*/
+/**
+ * @brief Read all serial port settings and supported configuration parameters
+ *
+ * The functions ::mbg_get_device_info and ::mbg_setup_receiver_info
+ * must have been called before, and the returned ::PCPS_DEV and
+ * ::RECEIVER_INFO structures have to be passed to this function.
+ *
+ * The complementary function ::mbg_save_serial_settings should be used
+ * to write the modified serial port configuration back to the board.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] *p_dev Pointer to a valid ::PCPS_DEV structure
+ * @param[out] *p_rpcfg Pointer to a ::RECEIVER_PORT_CFG structure to be filled up
+ * @param[in] *p_ri Pointer to a valid ::RECEIVER_INFO structure
+ *
+ * @return ::MBG_SUCCESS or error code returned by device I/O control function
+ *
+ * @see ::mbg_get_device_info
+ * @see ::mbg_setup_receiver_info
+ * @see ::mbg_save_serial_settings
+ */
int mbg_get_serial_settings( MBG_DEV_HANDLE dh,
- const PCPS_DEV *pdev,
- RECEIVER_PORT_CFG *pcfg,
+ const PCPS_DEV *p_dev,
+ RECEIVER_PORT_CFG *p_rpcfg,
const RECEIVER_INFO *p_ri )
{
int rc;
- int i;
- memset( pcfg, 0, sizeof( *pcfg ) );
+ memset( p_rpcfg, 0, sizeof( *p_rpcfg ) );
- if ( _pcps_has_receiver_info( pdev ) )
+ if ( _pcps_has_receiver_info( p_dev ) )
{
- rc = mbg_get_gps_all_port_info( dh, pcfg->pii, p_ri );
- if ( rc != MBG_SUCCESS )
- goto error;
+ // The device provides a RECEIVER_INFO, so we can simply read all
+ // serial port configuration and supported string types directly.
- rc = mbg_get_gps_all_str_type_info( dh, pcfg->stii, p_ri );
- if ( rc != MBG_SUCCESS )
- goto error;
+ rc = mbg_get_gps_all_port_info( dh, p_rpcfg->pii, p_ri );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ rc = mbg_get_gps_all_str_type_info( dh, p_rpcfg->stii, p_ri );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
}
else
{
- if ( _pcps_is_gps( pdev ) )
+ // The device doesn't support a RECEIVER_INFO, so this is
+ // an old GPS or non-GPS device.
+
+ if ( _pcps_is_gps( p_dev ) )
{
- rc = mbg_get_gps_port_parm( dh, &pcfg->tmp_pp );
- if ( rc != MBG_SUCCESS )
- goto error;
+ // Read the serial port configuration from an old GPS device using
+ // a legacy API call and set up current structures accordingly.
- for ( i = 0; i < p_ri->n_com_ports; i++ )
- {
- PORT_INFO_IDX *p_pii = &pcfg->pii[i];
- PORT_INFO *p_pi = &p_pii->port_info;
+ rc = mbg_get_gps_port_parm( dh, &p_rpcfg->tmp_pp );
- p_pii->idx = i;
- port_settings_from_port_parm( &p_pi->port_settings,
- i, &pcfg->tmp_pp, 1 );
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
- p_pi->supp_baud_rates = DEFAULT_GPS_BAUD_RATES_C166;
- p_pi->supp_framings = DEFAULT_GPS_FRAMINGS_C166;
- p_pi->supp_str_types = DEFAULT_SUPP_STR_TYPES_GPS;
- }
+ rc = setup_port_info_from_port_settings( p_rpcfg->pii, &p_rpcfg->tmp_pp, p_ri );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ // Also set up default string type information.
+ rc = setup_default_str_type_info_idx( p_rpcfg->stii, p_ri );
}
else
- if ( _pcps_has_serial ( pdev ) ) // Not all non-GPS clocks have a serial port!
+ {
+ // Not all legacy non-GPS clocks have a serial port.
+ if ( _pcps_has_serial( p_dev ) )
{
+ // Read the serial port configuration from an old non-GPS device using
+ // a legacy API call and set up current structures accordingly.
+
PCPS_SERIAL ser_code;
rc = mbg_get_serial( dh, &ser_code );
- if ( rc != MBG_SUCCESS )
- goto error;
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
- port_info_from_pcps_serial( pcfg->pii, ser_code,
- _pcps_has_serial_hs( pdev ) ?
+ port_info_from_pcps_serial( p_rpcfg->pii, ser_code,
+ _pcps_has_serial_hs( p_dev ) ?
DEFAULT_BAUD_RATES_DCF_HS :
DEFAULT_BAUD_RATES_DCF
);
+ // Also set up default string type information.
+ rc = setup_default_str_type_info_idx( p_rpcfg->stii, p_ri );
}
-
- for ( i = 0; i < p_ri->n_str_type; i++ )
- {
- STR_TYPE_INFO_IDX *stip = &pcfg->stii[i];
- stip->idx = i;
- stip->str_type_info = default_str_type_info[i];
}
- }
- return MBG_SUCCESS;
+ }
+ rc = MBG_SUCCESS;
-error:
+out:
return rc;
} // mbg_get_serial_settings
@@ -151,53 +412,53 @@ error:
/*HDR*/
/**
- Write the configuration settings for a single serial port to the board.
-
- Modifications to the serial port configuration should be made only
- after mbg_get_serial_settings() had been called to read all serial port
- settings and supported configuration parameters.
- This function has finally to be called once for every serial port
- the configuration of which has been modified.
-
- As also required by mbg_get_serial_settings(), the functions
- mbg_get_device_info() and mbg_setup_receiver_info() must have been
- called before, and the returned ::PCPS_DEV and ::RECEIVER_INFO structures
- must be passed to this function.
-
- @param dh Valid handle to a Meinberg device
- @param *pdev Pointer to a ::PCPS_DEV structure
- @param *pcfg Pointer to a ::RECEIVER_PORT_CFG structure
- @param port_num Index of the ::serial port to be saved
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_serial_settings()
- @see mbg_get_device_info()
- @see mbg_setup_receiver_info()
-*/
-int mbg_save_serial_settings( MBG_DEV_HANDLE dh, const PCPS_DEV *pdev,
- RECEIVER_PORT_CFG *pcfg, int port_num )
+ * @brief Write the configuration settings for a single serial port to a device
+ *
+ * Modifications to the serial port configuration should be made only
+ * after ::mbg_get_serial_settings had been called to read all serial port
+ * settings and supported configuration parameters.
+ * This function has finally to be called once for every serial port
+ * the configuration of which has been modified.
+ *
+ * As also required by ::mbg_get_serial_settings, the functions
+ * ::mbg_get_device_info and ::mbg_setup_receiver_info must have been
+ * called before, and the returned ::PCPS_DEV and ::RECEIVER_INFO structures
+ * vave to be passed to this function.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] *p_dev Pointer to a valid ::PCPS_DEV structure
+ * @param[in] *p_rpcfg Pointer to a valid ::RECEIVER_PORT_CFG structure
+ * @param[in] port_num Index of the serial port to be saved
+ *
+ * @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ *
+ * @see ::mbg_get_serial_settings
+ * @see ::mbg_get_device_info
+ * @see ::mbg_setup_receiver_info
+ */
+int mbg_save_serial_settings( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev,
+ RECEIVER_PORT_CFG *p_rpcfg, int port_num )
{
int rc;
- if ( _pcps_has_receiver_info( pdev ) )
+ if ( _pcps_has_receiver_info( p_dev ) )
{
- rc = mbg_set_gps_port_settings( dh, &pcfg->pii[port_num].port_info.port_settings, port_num );
+ rc = mbg_set_gps_port_settings( dh, &p_rpcfg->pii[port_num].port_info.port_settings, port_num );
}
else
{
- if ( _pcps_is_gps( pdev ) )
+ if ( _pcps_is_gps( p_dev ) )
{
- port_parm_from_port_settings( &pcfg->tmp_pp, port_num,
- &pcfg->pii[port_num].port_info.port_settings, 1 );
+ port_parm_from_port_settings( &p_rpcfg->tmp_pp, port_num,
+ &p_rpcfg->pii[port_num].port_info.port_settings, 1 );
- rc = mbg_set_gps_port_parm( dh, &pcfg->tmp_pp );
+ rc = mbg_set_gps_port_parm( dh, &p_rpcfg->tmp_pp );
}
else
{
PCPS_SERIAL ser_code;
- pcps_serial_from_port_info( &ser_code, pcfg->pii );
+ pcps_serial_from_port_info( &ser_code, p_rpcfg->pii );
rc = mbg_set_serial( dh, &ser_code );
}
@@ -211,23 +472,477 @@ int mbg_save_serial_settings( MBG_DEV_HANDLE dh, const PCPS_DEV *pdev,
/*HDR*/
/**
- Read all PTP settings and supported configuration parameters.
+ * @brief Read all network configuration into an ::ALL_NET_CFG_INFO structure
+ *
+ * Reads the network configuration of a device via the LAN_IP4 API and
+ * translates the structures into NET_CFG structures.
+ *
+ * As soon as available, this function should make use of the NET_CFG API.
+ *
+ * A ::ALL_NET_CFG_INFO and the appropriate number of ::MBG_NET_INTF_LINK_INFO_IDX,
+ * ::MBG_NET_INTF_ADDR_INFO_IDX, ::MBG_IP_ADDR_IDX, ::MBG_NET_NAME_IDX and
+ * ::MBG_NET_INTF_ROUTE_INFO_IDX will be allocated and need to be freed later
+ * by calling ::free_all_net_cfg_info
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a pointer of ::ALL_NET_CFG_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_settings
+ * @see ::free_all_net_cfg_info
+ */
+int mbg_get_all_net_cfg_info( MBG_DEV_HANDLE dh, ALL_NET_CFG_INFO **p )
+{
+ ALL_NET_CFG_INFO *net_cfg_info = *p;
+ int rc;
+
+ if ( net_cfg_info == NULL )
+ {
+ net_cfg_info = ( ALL_NET_CFG_INFO * )calloc( 1, sizeof( *net_cfg_info ) );
+ if ( net_cfg_info == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ // TODO Use NET_CFG API as soon as its available for PCI/PCIe devices
+ rc = mbg_chk_dev_has_lan_intf( dh );
+
+ if ( mbg_rc_is_success( rc ) )
+ {
+ LAN_IF_INFO lan_if_info;
+ IP4_SETTINGS ip4_settings;
+
+ if ( net_cfg_info->glb_cfg_info.n_supp_intf_link != 0 )
+ goto out;
+
+ rc = mbg_get_lan_if_info( dh, &lan_if_info );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ if ( net_cfg_info->link_infos == NULL )
+ {
+ net_cfg_info->link_infos = ( MBG_NET_INTF_LINK_INFO_IDX * )calloc( 1, sizeof( *net_cfg_info->link_infos ) );
+ if ( net_cfg_info->link_infos == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ net_cfg_info->glb_cfg_info.glb_settings.num_intf_link = 1;
+
+ memset( &net_cfg_info->link_infos[0], 0, sizeof( net_cfg_info->link_infos[0] ) );
+
+ net_cfg_info->link_infos[0].info.supp_states = MBG_NET_INTF_LINK_STATE_MASK_UP;
+ net_cfg_info->link_infos[0].info.supp_types = MBG_NET_INTF_LINK_TYPE_MASK_PHYS | MBG_NET_INTF_LINK_TYPE_MASK_VLAN;
+ net_cfg_info->link_infos[0].info.supp_speed_modes = MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_HALF | MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_FULL | MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_HALF | MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_FULL;
+ net_cfg_info->link_infos[0].info.supp_port_types = MBG_NET_INTF_LINK_PORT_TYPE_MASK_TP;
+
+ snprintf_safe( net_cfg_info->link_infos[0].info.link_settings.name, sizeof( net_cfg_info->link_infos[0].info.link_settings.name ), "lan0" );
+ net_cfg_info->link_infos[0].info.link_settings.mac_addr = lan_if_info.mac_addr;
+ net_cfg_info->link_infos[0].info.link_settings.if_index = 0;
+ net_cfg_info->link_infos[0].info.link_settings.type = MBG_NET_INTF_LINK_TYPE_PHYS;
+ net_cfg_info->link_infos[0].info.link_settings.port_type = MBG_NET_INTF_LINK_PORT_TYPE_TP;
+
+ if ( net_cfg_info->glb_cfg_info.n_supp_intf_addr != 0 )
+ goto out;
+
+ rc = mbg_get_ip4_settings( dh, &ip4_settings );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ if( ip4_settings.flags & IP4_MSK_LINK )
+ {
+ net_cfg_info->link_infos->info.link_settings.states |= MBG_NET_INTF_LINK_STATE_MASK_UP;
+ net_cfg_info->link_infos->info.link_settings.states |= MBG_NET_INTF_LINK_STATE_MASK_LOWER_UP;
+ }
+
+ if ( net_cfg_info->addr_infos == NULL )
+ {
+ net_cfg_info->addr_infos = ( MBG_NET_INTF_ADDR_INFO_IDX * )calloc( 1, sizeof( *net_cfg_info->addr_infos ) );
+ if ( net_cfg_info->addr_infos == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ net_cfg_info->glb_cfg_info.glb_settings.num_intf_addr = 1;
+
+ memset( &net_cfg_info->addr_infos[0], 0, sizeof( net_cfg_info->addr_infos[0] ) );
+
+ net_cfg_info->addr_infos[0].info.supp_flags = MBG_NET_INTF_ADDR_MASK_DHCP4;
+
+ snprintf_safe( net_cfg_info->addr_infos[0].info.addr_settings.label, sizeof( net_cfg_info->addr_infos[0].info.addr_settings.label ), "lan0:0" );
+
+ if ( ip4_settings.flags & IP4_MSK_VLAN )
+ {
+ net_cfg_info->link_infos = ( MBG_NET_INTF_LINK_INFO_IDX * )realloc( net_cfg_info->link_infos, 2 * sizeof( *net_cfg_info->link_infos ) );
+ if ( net_cfg_info->link_infos == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+
+ net_cfg_info->glb_cfg_info.glb_settings.num_intf_link = 2;
+
+ memset(&net_cfg_info->link_infos[1], 0, sizeof(net_cfg_info->link_infos[1]));
+
+ net_cfg_info->link_infos[1].idx = 1;
+ net_cfg_info->link_infos[1].info.supp_states = MBG_NET_INTF_LINK_STATE_MASK_UP;
+ net_cfg_info->link_infos[1].info.supp_types = MBG_NET_INTF_LINK_TYPE_MASK_VLAN;
+ net_cfg_info->link_infos[1].info.supp_speed_modes = MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_HALF | MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_FULL | MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_HALF | MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_FULL;
+ net_cfg_info->link_infos[1].info.supp_port_types = MBG_NET_INTF_LINK_PORT_TYPE_MASK_TP;
+
+ snprintf_safe( net_cfg_info->link_infos[1].info.link_settings.name, sizeof( net_cfg_info->link_infos[1].info.link_settings.name ), "vlan0" );
+ net_cfg_info->link_infos[1].info.link_settings.mac_addr = net_cfg_info->link_infos[0].info.link_settings.mac_addr;
+ net_cfg_info->link_infos[1].info.link_settings.if_index = 1;
+ net_cfg_info->link_infos[1].info.link_settings.ass_if_index = 0;
+ net_cfg_info->link_infos[1].info.link_settings.states = net_cfg_info->link_infos[0].info.link_settings.states;
+ net_cfg_info->link_infos[1].info.link_settings.type = MBG_NET_INTF_LINK_TYPE_VLAN;
+ net_cfg_info->link_infos[1].info.link_settings.vlan_cfg = ip4_settings.vlan_cfg;
+
+ net_cfg_info->addr_infos[0].info.addr_settings.ass_if_index = 1;
+ }
+
+ if ( ip4_settings.flags & IP4_MSK_DHCP )
+ net_cfg_info->addr_infos[0].info.addr_settings.flags |= MBG_NET_INTF_ADDR_MASK_DHCP4;
+
+ net_cfg_info->addr_infos[0].info.addr_settings.ip.type = MBG_IP_ADDR_TYPE_IP4;
+ net_cfg_info->addr_infos[0].info.addr_settings.ip.u_addr.ip4_addr = ip4_settings.ip_addr;
+
+ net_cfg_info->addr_infos[0].info.addr_settings.broadcast.type = MBG_IP_ADDR_TYPE_IP4;
+ net_cfg_info->addr_infos[0].info.addr_settings.broadcast.u_addr.ip4_addr = ip4_settings.broad_addr;
+
+ net_cfg_info->addr_infos[0].info.addr_settings.prefix_bits = get_ip4_net_mask_bits(&ip4_settings.netmask);
+
+ if ( net_cfg_info->glb_cfg_info.n_supp_intf_route == 0 )
+ {
+ if ( net_cfg_info->route_infos == NULL )
+ {
+ net_cfg_info->route_infos = ( MBG_NET_INTF_ROUTE_INFO_IDX * )calloc( 1, sizeof( *net_cfg_info->route_infos ) );
+ if ( net_cfg_info->route_infos == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ net_cfg_info->glb_cfg_info.glb_settings.num_intf_route = 1;
+
+ memset( &net_cfg_info->route_infos[0], 0, sizeof( net_cfg_info->route_infos[0] ) );
+
+ net_cfg_info->route_infos[0].info.route_settings.type = MBG_NET_INTF_ROUTE_TYPE_DEFAULT_GATEWAY;
+ net_cfg_info->route_infos[0].info.route_settings.gateway.type = MBG_IP_ADDR_TYPE_IP4;
+ net_cfg_info->route_infos[0].info.route_settings.gateway.u_addr.ip4_addr = ip4_settings.gateway;
+ if ( ip4_settings.gateway != 0 )
+ {
+ if(net_cfg_info->glb_cfg_info.glb_settings.num_intf_link == 2)
+ net_cfg_info->route_infos[0].info.route_settings.ass_if_index = 1;
+ }
+ else net_cfg_info->route_infos[0].info.route_settings.ass_if_index = (uint32_t)-1;
+
+ }
+
+ }
+
+out:
+ if ( mbg_rc_is_error( rc ) )
+ {
+ free_all_net_cfg_info( net_cfg_info );
+ net_cfg_info = NULL;
+ }
+
+ *p = net_cfg_info;
+
+ return rc;
+
+} // mbg_get_all_net_cfg_info
+
+
+
+/*HDR*/
+/**
+ * @brief Write all network settings to a device
+ *
+ * The complementary function ::mbg_get_all_net_cfg_info should
+ * have been used to read the original network settings and
+ * supported configuration parameters.
+ *
+ * The appropriate settings are translated into LAN_IP4 structures
+ * and send to the device using the appropriate API functions.
+ *
+ * As soon as available, this function should make use of the NET_CFG API.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] p Pointer to a pointer of ::ALL_NET_CFG_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_lan_intf
+ * @see ::mbg_set_ip4_settings
+ */
+int mbg_save_all_net_cfg_info( MBG_DEV_HANDLE dh, ALL_NET_CFG_INFO *p )
+{
+ // TODO: Use NET_CFG API as soon as its available for PCI/PCIe devices
+ int rc = mbg_chk_dev_has_lan_intf( dh );
+
+ if ( mbg_rc_is_success( rc ) )
+ {
+ IP4_SETTINGS ip4_settings;
+ memset( &ip4_settings, 0, sizeof( ip4_settings ) );
+
+ if ( p->addr_infos[0].info.addr_settings.ip.type == MBG_IP_ADDR_TYPE_IP4 )
+ ip4_settings.ip_addr = p->addr_infos[0].info.addr_settings.ip.u_addr.ip4_addr;
+
+ ip4_settings.netmask = ip4_net_mask_from_cidr( p->addr_infos[0].info.addr_settings.prefix_bits );
+ ip4_settings.broad_addr = ip4_broad_addr_from_addr( &ip4_settings.ip_addr, &ip4_settings.netmask );
+
+ if ( p->route_infos[0].info.route_settings.gateway.type == MBG_IP_ADDR_TYPE_IP4 )
+ ip4_settings.gateway = p->route_infos[0].info.route_settings.gateway.u_addr.ip4_addr;
+
+ if ( ( p->glb_cfg_info.glb_settings.num_intf_link > 1 ) && ( p->addr_infos[0].info.addr_settings.ass_if_index == 1 ) )
+ {
+ ip4_settings.flags |= IP4_MSK_VLAN;
+ ip4_settings.vlan_cfg = p->link_infos[1].info.link_settings.vlan_cfg;
+ }
+
+ if ( ( p->addr_infos[0].info.addr_settings.flags & MBG_NET_INTF_ADDR_MASK_DHCP4 ) == MBG_NET_INTF_ADDR_MASK_DHCP4 )
+ ip4_settings.flags |= IP4_MSK_DHCP;
+
+ rc = mbg_set_ip4_settings( dh, &ip4_settings );
+ }
+
+ return rc;
+
+} // mbg_save_all_net_cfg_info
+
+
+
+/*HDR*/
+/**
+ * @brief Read current network status into an ::ALL_NET_STATUS_INFO structure
+ *
+ * Reads the network status of a device via the LAN_IP4 API and
+ * translates the structures into NET_CFG structures.
+ *
+ * As soon as available, this function should make use of the NET_CFG API.
+ *
+ * A ::ALL_NET_STATUS_INFO and the appropriate number of ::MBG_NET_INTF_LINK_INFO_IDX,
+ * ::MBG_NET_INTF_ADDR_INFO_IDX, ::MBG_IP_ADDR_IDX, ::MBG_NET_NAME_IDX and
+ * ::MBG_NET_INTF_ROUTE_INFO_IDX will be allocated and need to be freed later
+ * by calling ::free_all_net_status_info
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a pointer of ::ALL_NET_STATUS_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_state
+ * @see ::free_all_net_status_info
+ */
+int mbg_get_all_net_status_info( MBG_DEV_HANDLE dh, ALL_NET_STATUS_INFO **p )
+{
+ ALL_NET_STATUS_INFO *net_status_info = *p;
+ int rc;
+
+ if ( net_status_info == NULL )
+ {
+ net_status_info = ( ALL_NET_STATUS_INFO * )calloc( 1, sizeof( *net_status_info ) );
+ if ( net_status_info == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ // TODO Use NET_CFG API as soon as its available for PCI/PCIe devices
+ rc = mbg_chk_dev_has_lan_intf( dh );
+
+ if ( mbg_rc_is_success( rc ) )
+ {
+ LAN_IF_INFO lan_if_info;
+ IP4_SETTINGS ip4_state;
+
+ if ( net_status_info->glb_cfg_info.n_supp_intf_link != 0 )
+ goto out;
+
+ rc = mbg_get_lan_if_info( dh, &lan_if_info );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ if ( net_status_info->link_infos == NULL )
+ {
+ net_status_info->link_infos = ( MBG_NET_INTF_LINK_INFO_IDX * )calloc( 1, sizeof( *net_status_info->link_infos ) );
+ if ( net_status_info->link_infos == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ net_status_info->glb_cfg_info.glb_settings.num_intf_addr = 1;
+
+ memset( &net_status_info->link_infos[0], 0, sizeof( net_status_info->link_infos[0] ) );
+
+ net_status_info->link_infos[0].info.supp_states = MBG_NET_INTF_LINK_STATE_MASK_UP;
+ net_status_info->link_infos[0].info.supp_types = MBG_NET_INTF_LINK_TYPE_MASK_PHYS | MBG_NET_INTF_LINK_TYPE_MASK_VLAN;
+ net_status_info->link_infos[0].info.supp_speed_modes = MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_HALF | MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_FULL | MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_HALF | MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_FULL;
+ net_status_info->link_infos[0].info.supp_port_types = MBG_NET_INTF_LINK_PORT_TYPE_MASK_TP;
+
+ snprintf_safe( net_status_info->link_infos[0].info.link_settings.name, sizeof( net_status_info->link_infos[0].info.link_settings.name ), "lan0" );
+ net_status_info->link_infos[0].info.link_settings.mac_addr = lan_if_info.mac_addr;
+ net_status_info->link_infos[0].info.link_settings.if_index = 0;
+ net_status_info->link_infos[0].info.link_settings.type = MBG_NET_INTF_LINK_TYPE_PHYS;
+ net_status_info->link_infos[0].info.link_settings.port_type = MBG_NET_INTF_LINK_PORT_TYPE_TP;
+
+ if ( net_status_info->glb_cfg_info.n_supp_intf_addr != 0 )
+ goto out;
+
+ rc = mbg_get_ip4_state( dh, &ip4_state );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ if( ip4_state.flags & IP4_MSK_LINK )
+ {
+ net_status_info->link_infos[0].info.link_settings.states |= MBG_NET_INTF_LINK_STATE_MASK_UP;
+ net_status_info->link_infos[0].info.link_settings.states |= MBG_NET_INTF_LINK_STATE_MASK_LOWER_UP;
+ }
+
+ if ( net_status_info->addr_infos == NULL )
+ {
+ net_status_info->addr_infos = ( MBG_NET_INTF_ADDR_INFO_IDX * )realloc( net_status_info->addr_infos, sizeof( *net_status_info->addr_infos ) );
+ if ( net_status_info->addr_infos == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ net_status_info->glb_cfg_info.glb_settings.num_intf_addr = 1;
+
+ memset( &net_status_info->addr_infos[0], 0, sizeof( net_status_info->addr_infos[0] ) );
+
+ net_status_info->addr_infos[0].info.supp_flags = MBG_NET_INTF_ADDR_MASK_DHCP4;
- The complementary function mbg_save_all_ptp_cfg_info() should
- be used to write the modified configuration back to the device.
+ snprintf_safe( net_status_info->addr_infos[0].info.addr_settings.label, sizeof( net_status_info->addr_infos[0].info.addr_settings.label ), "lan0:0" );
- @param dh Valid handle to a Meinberg device.
- @param *p Pointer to a ::ALL_PTP_CFG_INFO structure.
+ if ( ip4_state.flags & IP4_MSK_VLAN )
+ {
+ net_status_info->link_infos = ( MBG_NET_INTF_LINK_INFO_IDX * )realloc( net_status_info->link_infos, 2 * sizeof( *net_status_info->link_infos ) );
+ if ( net_status_info->link_infos == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+
+ net_status_info->glb_cfg_info.glb_settings.num_intf_link = 2;
+
+ memset(&net_status_info->link_infos[1], 0, sizeof(net_status_info->link_infos[1]));
+
+ net_status_info->link_infos[1].idx = 1;
+ net_status_info->link_infos[1].info.supp_states = MBG_NET_INTF_LINK_STATE_MASK_UP;
+ net_status_info->link_infos[1].info.supp_types = MBG_NET_INTF_LINK_TYPE_MASK_VLAN;
+ net_status_info->link_infos[1].info.supp_speed_modes = MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_HALF | MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_FULL | MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_HALF | MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_FULL;
+ net_status_info->link_infos[1].info.supp_port_types = MBG_NET_INTF_LINK_PORT_TYPE_MASK_TP;
+
+ snprintf_safe( net_status_info->link_infos[1].info.link_settings.name, sizeof( net_status_info->link_infos[1].info.link_settings.name ), "vlan0" );
+ net_status_info->link_infos[1].info.link_settings.mac_addr = net_status_info->link_infos[0].info.link_settings.mac_addr;
+ net_status_info->link_infos[1].info.link_settings.if_index = 1;
+ net_status_info->link_infos[1].info.link_settings.ass_if_index = 0;
+ net_status_info->link_infos[1].info.link_settings.states = net_status_info->link_infos[0].info.link_settings.states;
+ net_status_info->link_infos[1].info.link_settings.type = MBG_NET_INTF_LINK_TYPE_VLAN;
+ net_status_info->link_infos[1].info.link_settings.vlan_cfg = ip4_state.vlan_cfg;
+
+ net_status_info->addr_infos[0].info.addr_settings.ass_if_index = 1;
+ }
+
+ if ( ip4_state.flags & IP4_MSK_DHCP )
+ net_status_info->addr_infos[0].info.addr_settings.flags |= MBG_NET_INTF_ADDR_MASK_DHCP4;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ net_status_info->addr_infos[0].info.addr_settings.ip.type = MBG_IP_ADDR_TYPE_IP4;
+ net_status_info->addr_infos[0].info.addr_settings.ip.u_addr.ip4_addr = ip4_state.ip_addr;
- @see mbg_save_all_ptp_cfg_info()
- @see mbg_get_ptp_cfg_info()
- @see mbg_get_ptp_uc_master_cfg_limits()
- @see mbg_get_all_ptp_uc_master_info()
- @see mbg_dev_has_ptp()
- @see mbg_dev_has_ptp_unicast()
-*/
+ net_status_info->addr_infos[0].info.addr_settings.broadcast.type = MBG_IP_ADDR_TYPE_IP4;
+ net_status_info->addr_infos[0].info.addr_settings.broadcast.u_addr.ip4_addr = ip4_state.broad_addr;
+
+ net_status_info->addr_infos[0].info.addr_settings.prefix_bits = get_ip4_net_mask_bits(&ip4_state.netmask);
+
+ if ( net_status_info->glb_cfg_info.n_supp_intf_route == 0 )
+ {
+ if ( net_status_info->route_infos == NULL )
+ {
+ net_status_info->route_infos = ( MBG_NET_INTF_ROUTE_INFO_IDX * )calloc( 1, sizeof( *net_status_info->route_infos ) );
+ if ( net_status_info->route_infos == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ net_status_info->glb_cfg_info.glb_settings.num_intf_route = 1;
+
+ memset( &net_status_info->route_infos[0], 0, sizeof( net_status_info->route_infos[0] ) );
+
+ net_status_info->route_infos[0].info.route_settings.type = MBG_NET_INTF_ROUTE_TYPE_DEFAULT_GATEWAY;
+ net_status_info->route_infos[0].info.route_settings.gateway.type = MBG_IP_ADDR_TYPE_IP4;
+ net_status_info->route_infos[0].info.route_settings.gateway.u_addr.ip4_addr = ip4_state.gateway;
+ if ( ip4_state.gateway != 0 )
+ {
+ if(net_status_info->glb_cfg_info.glb_settings.num_intf_link == 2)
+ net_status_info->route_infos[0].info.route_settings.ass_if_index = 1;
+ }
+ else net_status_info->route_infos[0].info.route_settings.ass_if_index = (uint32_t)-1;
+
+ }
+
+ }
+
+out:
+ if ( mbg_rc_is_error( rc ) )
+ {
+ free_all_net_status_info( net_status_info );
+ net_status_info = NULL;
+ }
+
+ *p = net_status_info;
+
+ return rc;
+
+} // mbg_get_all_net_status_info
+
+
+
+/*HDR*/
+/**
+ * @brief Read all PTP settings and supported configuration parameters
+ *
+ * The complementary function ::mbg_save_all_ptp_cfg_info should
+ * be used to write the modified configuration back to the device.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] *p Pointer to a ::ALL_PTP_CFG_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ *
+ * @see ::mbg_save_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_cfg_info
+ * @see ::mbg_get_ptp_uc_master_cfg_limits
+ * @see ::mbg_get_all_ptp_uc_master_info
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_dev_has_ptp_unicast
+ */
int mbg_get_all_ptp_cfg_info( MBG_DEV_HANDLE dh, ALL_PTP_CFG_INFO *p )
{
int rc = MBG_SUCCESS;
@@ -267,24 +982,23 @@ int mbg_get_all_ptp_cfg_info( MBG_DEV_HANDLE dh, ALL_PTP_CFG_INFO *p )
/*HDR*/
/**
- Write all PTP settings and supported configuration parameters
- to a device.
-
- The complementary function mbg_get_all_ptp_cfg_info() should
- have been used to read the original PTP settings and supported
- configuration parameters.
-
- @param dh Valid handle to a Meinberg device.
- @param *p Pointer to a ::ALL_PTP_CFG_INFO structure.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_all_ptp_cfg_info()
- @see mbg_set_ptp_cfg_settings()
- @see mbg_set_ptp_uc_master_settings_idx()
- @see mbg_dev_has_ptp()
- @see mbg_dev_has_ptp_unicast()
-*/
+ * @brief Write all PTP settings to a device
+ *
+ * The complementary function ::mbg_get_all_ptp_cfg_info should
+ * have been used to read the original PTP settings and supported
+ * configuration parameters.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] *p Pointer to a valid ::ALL_PTP_CFG_INFO structure
+ *
+ * @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ *
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_set_ptp_cfg_settings
+ * @see ::mbg_set_ptp_uc_master_settings_idx
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_dev_has_ptp_unicast
+ */
int mbg_save_all_ptp_cfg_info( MBG_DEV_HANDLE dh, const ALL_PTP_CFG_INFO *p )
{
int rc = MBG_SUCCESS;
@@ -319,4 +1033,778 @@ int mbg_save_all_ptp_cfg_info( MBG_DEV_HANDLE dh, const ALL_PTP_CFG_INFO *p )
} // mbg_save_all_ptp_cfg_info
+#endif // !MBGDEVIO_SIMPLE
+
+
+/*HDR*/
+/**
+ * @brief Read all XMR info into a newly or re-allocated ::ALL_XMULTI_REF_INFO
+ *
+ * @note ::mbg_chk_dev_supp_xmr should be called before using this function
+ *
+ * A ::ALL_XMULTI_REF_INFO and a number of ::XMULTI_REF_INSTANCES::n_xmr_settings
+ * of ::XMULTI_REF_INFO_IDX and ::XMR_EXT_SRC_INFO_IDX will be allocated and needs
+ * to be freed by calling ::free_all_xmulti_ref_info
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a pointer of ::ALL_XMULTI_REF_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::free_all_xmulti_ref_info
+ */
+int mbg_get_all_xmulti_ref_info( MBG_DEV_HANDLE dh, ALL_XMULTI_REF_INFO **p )
+{
+ ALL_XMULTI_REF_INFO *xmr_info = *p;
+ int rc;
+
+ if ( xmr_info == NULL )
+ {
+ xmr_info = ( ALL_XMULTI_REF_INFO * )calloc( 1, sizeof( *xmr_info ) );
+ if ( xmr_info == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ // First, get the XMULTI_REF_INSTANCES to check how many sources are supported
+ rc = mbg_get_xmr_instances( dh, &xmr_info->instances );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ if ( xmr_info->infos == NULL )
+ {
+ xmr_info->infos = ( XMULTI_REF_INFO_IDX * )calloc( xmr_info->instances.n_xmr_settings, sizeof( *xmr_info->infos ) );
+ if ( xmr_info->infos == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ rc = mbg_get_gps_all_xmr_info( dh, xmr_info->infos, &xmr_info->instances );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ if ( mbg_rc_is_success( chk_dev_xmulti_ref_supp_ext_src_info( xmr_info ) ) )
+ {
+ // TODO!!!
+ // XMR_EXT_SRC_INFO_IDX can not be read out from bus devices, yet
+ // Therefore, remove the feature bit from this card
+ // Has to be changed as soon as low level functions are ready
+ // TODO!!!
+ xmr_info->instances.flags &= ~XMRIF_MSK_EXT_SRC_INFO_SUPP;
+ }
+
+out:
+ if ( mbg_rc_is_error( rc ) )
+ {
+ free_all_xmulti_ref_info( xmr_info );
+ xmr_info = NULL;
+ }
+
+ *p = xmr_info;
+
+ return rc;
+
+} // mbg_get_all_xmulti_ref_info
+
+
+/*HDR*/
+/**
+ * @brief Set all extended multi ref settings to a device
+ *
+ * The complementary function ::mbg_get_all_xmulti_ref_info should
+ * have been used to read the original extended multi ref info.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a ::ALL_XMULTI_REF_INFO structure with all settings
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_set_gps_xmr_settings_idx
+ */
+_NO_MBG_API_ATTR int _MBG_API mbg_save_all_xmulti_ref_info( MBG_DEV_HANDLE dh, ALL_XMULTI_REF_INFO *p )
+{
+ int rc = MBG_SUCCESS, i;
+ XMULTI_REF_SETTINGS_IDX settings;
+
+ for (i = 0; ( i < p->instances.n_xmr_settings ) && mbg_rc_is_success( rc ); i++ )
+ {
+ settings.idx = i;
+ memcpy( &settings.settings, &p->infos[i].info.settings, sizeof( settings.settings ) );
+ rc = mbg_set_gps_xmr_settings_idx( dh, &settings );
+ }
+
+ // if all settings have been successully set, send dummy structure with index -1 to apply settings
+ if( mbg_rc_is_success( rc ) )
+ {
+ memset( &settings, 0, sizeof( settings ) );
+ settings.idx = -1;
+ settings.settings.id.type = MULTI_REF_NONE;
+ rc = mbg_set_gps_xmr_settings_idx( dh, &settings );
+ }
+
+ return rc;
+
+} // mbg_save_all_xmulti_ref_info
+
+
+/*HDR*/
+/**
+ * @brief Read all XMR status info into a newly or re-allocated ::ALL_XMULTI_REF_STATUS
+ *
+ * @note ::mbg_chk_dev_supp_xmr should be called before using this function
+ *
+ * A ::ALL_XMULTI_REF_STATUS and a number of ::XMULTI_REF_INSTANCES::n_xmr_settings
+ * of ::XMULTI_REF_STATUS_IDX will be allocated and needs to be freed by calling
+ * ::free_all_xmulti_ref_status
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] info Pointer to the appropriate info structure
+ * @param[out] p Pointer to a pointer of ::ALL_XMULTI_REF_STATUS
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::free_all_xmulti_ref_status
+ */
+int mbg_get_all_xmulti_ref_status( MBG_DEV_HANDLE dh, const ALL_XMULTI_REF_INFO *info, ALL_XMULTI_REF_STATUS **p )
+{
+ ALL_XMULTI_REF_STATUS *xmr_status = *p;
+ int rc;
+
+ if ( info == NULL )
+ return MBG_ERR_INV_PARM;
+
+ if ( xmr_status == NULL )
+ {
+ xmr_status = ( ALL_XMULTI_REF_STATUS * )calloc( 1, sizeof( *xmr_status ) );
+ if ( xmr_status == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ if ( xmr_status->status == NULL )
+ {
+ xmr_status->status = ( XMULTI_REF_STATUS_IDX* )calloc( info->instances.n_xmr_settings, sizeof( *xmr_status->status ) );
+
+ if ( xmr_status->status == NULL )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto out;
+ }
+ }
+
+ rc = mbg_get_gps_all_xmr_status( dh, xmr_status->status, &info->instances );
+
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+
+ if ( mbg_rc_is_success( chk_dev_xmulti_ref_supp_ext_src_info( info ) ) )
+ {
+ // TODO
+ // XMR_EXT_SRC_INFO_IDX can not be read out from bus devices, yet
+ }
+
+out:
+ if ( mbg_rc_is_error( rc ) )
+ {
+ free_all_xmulti_ref_status( xmr_status );
+ xmr_status = NULL;
+ }
+
+ *p = xmr_status;
+
+ return rc;
+
+} // mbg_get_all_xmulti_ref_status
+
+
+
+/*HDR*/
+/**
+ * @brief Read all user capture information and store it into a newly allocated or reused ::ALL_UCAP_INFO
+ *
+ * @note ::mbg_chk_dev_has_ucap should be called to check if this API is supported.
+ *
+ * The appropriate number of ::TTM structures will be allocated and needs to be freed
+ * by calling ::free_all_ucap_info. Existing user captures will not be removed, so the
+ * number of user captures can never decrease.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a pointer to ::ALL_UCAP_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ucap
+ * @see ::free_all_ucap_info
+ */
+int mbg_get_all_ucap_info( MBG_DEV_HANDLE dh, ALL_UCAP_INFO **p )
+{
+ int rc;
+ ALL_UCAP_INFO *ucap_info = *p;
+ UCAP_ENTRY *new_entry, *old_entry;
+
+ // if this function is called for the first time, allocate a new ::ALL_UCAP_INFO structure
+ if ( ucap_info == NULL )
+ {
+ ucap_info = ( ALL_UCAP_INFO* )calloc( 1, sizeof( *ucap_info ) );
+ if ( ucap_info == NULL )
+ {
+ *p = NULL;
+ return MBG_ERR_NO_MEM;
+ }
+ mbg_klist_init(&ucap_info->list);
+ }
+
+ do
+ {
+ new_entry = calloc_ucap_entry();
+ if ( !new_entry )
+ {
+ rc = MBG_ERR_NO_MEM;
+ goto err_out;
+ }
+
+ rc = mbg_get_gps_ucap( dh, &new_entry->ttm );
+ if ( mbg_rc_is_error( rc ) )
+ goto err_out;
+
+ if ( ( (uint8_t)new_entry->ttm.tm.sec == (uint8_t) 0xFF ) )
+ {
+ free ( new_entry );
+ new_entry = NULL;
+ break;
+ }
+
+ if ( ucap_info->num_ucaps < MAX_UCAP_ENTRIES )
+ {
+ mbg_klist_append_item(&ucap_info->list, &new_entry->head);
+ ++ucap_info->num_ucaps;
+ }
+ else
+ {
+ old_entry = mbg_klist_first_entry(&ucap_info->list, UCAP_ENTRY, head);
+ mbg_klist_delete_item(&old_entry->head);
+ free(old_entry);
+ mbg_klist_append_item(&ucap_info->list, &new_entry->head);
+ }
+
+ } while (1);
+
+ rc = MBG_SUCCESS;
+
+ goto success_out;
+
+err_out:
+ free_all_ucap_info( ucap_info );
+ ucap_info = NULL;
+ if ( new_entry )
+ free( new_entry );
+
+success_out:
+ *p = ucap_info;
+
+ return rc;
+
+} // mbg_get_all_ucap_info
+
+
+
+#if 0 && defined( DEBUG ) // ### TODO
+
+/*HDR*/
+void test_gpio( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, int verbose )
+{
+ int b;
+ int rc;
+ unsigned int i;
+ MBG_GPIO_CFG_LIMITS gpio_cfg_limits = { 0 };
+ ALL_GPIO_INFO_IDX all_gpio_info_idx = { { 0 } };
+ ALL_GPIO_STATUS_IDX all_gpio_status_idx = { { 0 } };
+
+ rc = mbg_chk_dev_supp_gpio( dh );
+
+ printf( "\nGPIO chk supp: %i\n", rc );
+
+ rc = mbg_dev_has_gpio( dh, &b );
+
+ if ( rc != MBG_SUCCESS || !b )
+ {
+ printf( "GPIO not supported, rc: %i, b: %i\n", rc, b );
+ return;
+ }
+
+ printf( "GPIO supported, rc: %i, b: %i\n", rc, b );
+
+ printf( "\nChecking GPIO:\n" );
+
+ rc = mbg_get_gpio_cfg_limits( dh, &gpio_cfg_limits );
+
+ if ( rc != MBG_SUCCESS )
+ {
+ printf( "Failed to read GPIO limits, rc: %i\n", rc );
+ return;
+ }
+
+ printf( "Number of GPIO ports: %i\n", gpio_cfg_limits.num_io );
+
+ rc = mbg_get_gps_all_gpio_info( dh, all_gpio_info_idx, &gpio_cfg_limits );
+
+ if ( rc != MBG_SUCCESS )
+ printf( "Failed to read all GPIO info, rc: %i\n", rc );
+
+ if ( !( gpio_cfg_limits.flags & MBG_GPIO_CFG_LIMIT_FLAG_MASK_STATUS_SUPP ) )
+ printf( "GPIO status not supported (flag not set).\n" );
+ else
+ {
+ rc = mbg_get_gps_all_gpio_status( dh, all_gpio_status_idx, &gpio_cfg_limits );
+
+ if ( rc != MBG_SUCCESS )
+ printf( "Failed to read all GPIO status, rc: %i\n", rc );
+ }
+
+
+ for ( i = 0; i < gpio_cfg_limits.num_io; i++ )
+ {
+ MBG_GPIO_INFO *p_i = &all_gpio_info_idx[i].info;
+ MBG_GPIO_STATUS *p_st = &all_gpio_status_idx[i].status;
+ int gpio_type = p_i->settings.type;
+
+ printf( "GPIO %i: type 0x%02X (%s)", i,
+ gpio_type, _get_gpio_type_name( gpio_type ) );
+
+ switch ( gpio_type )
+ {
+ case MBG_GPIO_TYPE_FREQ_IN: // variable frequency input, freq == 0 if input not used
+ {
+ MBG_GPIO_FREQ_IN_SETTINGS *p = &p_i->settings.u.freq_in;
+#if 0
+ MBG_GPIO_FREQ freq; ///< frequency in range ::MBG_GPIO_FREQ_IN_SUPP::freq_min..::MBG_GPIO_FREQ_IN_SUPP::freq_max, or 0 if input is not used
+ uint32_t csc_limit; ///< max. cycle slip [1/1000 cycle units], see ::MBG_GPIO_FREQ_IN_SUPP::csc_limit_max
+ uint32_t shape; ///< selected signal shape, see ::MBG_GPIO_SIGNAL_SHAPES
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< reserved, currently always 0
+#endif
+
+ } break;
+
+ case MBG_GPIO_TYPE_FREQ_OUT: // variable frequency output
+ {
+ MBG_GPIO_FREQ_OUT_SETTINGS *p = &p_i->settings.u.freq_out;
+
+ printf( " %lu.%lu Hz %s, phase %li.%03li deg",
+ (ulong) p->freq.hz, (ulong) p->freq.frac,
+ _get_gpio_signal_shape_name( p->shape ),
+ (long) p->milli_phase / 1000,
+ labs( (long) p->milli_phase % 1000 ) );
+
+ } break;
+
+ case MBG_GPIO_TYPE_FIXED_FREQ_OUT: // fixed frequency output
+ {
+ MBG_GPIO_FIXED_FREQ_OUT_SETTINGS *p = &p_i->settings.u.ff_out;
+
+#if 0
+typedef struct
+{
+ uint32_t freq_idx; ///< fixed frequency index, see ::MBG_GPIO_FIXED_FREQS
+ uint32_t shape; ///< selected signal shape, see ::MBG_GPIO_SIGNAL_SHAPES
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< reserved, currently always 0
+
+} MBG_GPIO_FIXED_FREQ_OUT_SETTINGS;
+#endif
+
+ printf( " %s %s", _get_gpio_fixed_freq_str( p->freq_idx ),
+ _get_gpio_signal_shape_name( p->shape ) );
+
+ } break;
+
+ case MBG_GPIO_TYPE_BITS_IN: // framed data stream input
+ break;
+
+ case MBG_GPIO_TYPE_BITS_OUT: // framed data stream output
+ break;
+ }
+
+ printf( ", status 0x%02X (%s)",
+ p_st->port_state, _get_gpio_port_state_name( p_st->port_state ) );
+
+ printf( "\n" );
+ }
+
+#if 0
+ rc = mbg_set_gps_gpio_settings_idx( dh, MBG_GPIO_SETTINGS_IDX *p )
+#endif
+
+} // test_gpio
+
+
+
+/*HDR*/
+void test_xmr( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, int verbose )
+{
+ static const char *multi_ref_names[N_MULTI_REF] = DEFAULT_MULTI_REF_NAMES;
+
+ XMULTI_REF_INSTANCES xmr_instances = { 0 };
+ ALL_XMULTI_REF_INFO_IDX all_xmulti_ref_info_idx = { { 0 } };
+ ALL_XMULTI_REF_STATUS_IDX all_xmulti_ref_status_idx = { { 0 } };
+ XMR_HOLDOVER_STATUS xmr_holdover_status;
+
+ int b;
+ int rc;
+ int i;
+
+ rc = mbg_chk_dev_supp_xmr( dh );
+
+ printf( "\nXMR chk supp: %i\n", rc );
+
+ rc = mbg_dev_has_xmr( dh, &b );
+
+ if ( rc != MBG_SUCCESS || !b )
+ {
+ printf( "XMR not supported, rc: %i, b: %i\n", rc, b );
+ return;
+ }
+
+ printf( "XMR supported, rc: %i, b: %i\n", rc, b );
+
+ printf( "\nChecking XMR:\n" );
+
+ rc = mbg_get_xmr_instances( dh, &xmr_instances );
+
+ if ( rc != MBG_SUCCESS )
+ {
+ printf( "*** Failed to read XMR instances, rc: %i\n", rc );
+ return;
+ }
+
+ printf( "Slot %u, supp. XMR instances/priority levels: %u, flags: 0x%08lX\n",
+ xmr_instances.slot_id, xmr_instances.n_xmr_settings,
+ (ulong) xmr_instances.flags );
+
+ if ( verbose )
+ {
+// XMRIF_MSK_MRF_NONE_SUPP = ( 1UL << XMRIF_BIT_MRF_NONE_SUPP ), ///< see ::XMRIF_BIT_MRF_NONE_SUPP
+//##++++++++++++++++++++ XMRIF_MSK_HOLDOVER_STATUS_SUPP = ( 1UL << XMRIF_BIT_HOLDOVER_STATUS_SUPP ) ///< see ::XMRIF_BIT_HOLDOVER_STATUS_SUPP
+ }
+
+
+ for ( i = 0; i < MAX_N_MULTI_REF_TYPES; i++ )
+ {
+ int n_inst = xmr_instances.n_inst[i];
+
+ if ( i < N_MULTI_REF ) // a known signal type
+ {
+ if ( verbose )
+ {
+ if ( n_inst )
+ printf( "%u %s input%s supported\n", n_inst,
+ multi_ref_names[i], ( n_inst == 1 ) ? "" : "s" );
+ else
+ if ( verbose > 1 )
+ printf( "No %s input supported\n", multi_ref_names[i] );
+ }
+
+ continue;
+ }
+
+ // If execution gets here then the signal type is unknown.
+ // Print a warning if the device supports instances of this signal type.
+ if ( n_inst )
+ printf( "*** Warning: %u instances of unknown signal type idx %u supported!\n",
+ n_inst, i );
+ }
+
+ rc = mbg_get_gps_all_xmr_info( dh, all_xmulti_ref_info_idx, &xmr_instances );
+
+ if ( rc != MBG_SUCCESS )
+ printf( "*** Failed to read all XMR info, rc: %i\n", rc );
+
+ rc = mbg_get_gps_all_xmr_status( dh, all_xmulti_ref_status_idx, &xmr_instances );
+
+ if ( rc != MBG_SUCCESS )
+ printf( "*** Failed to read all XMR status, rc: %i\n", rc );
+
+ for ( i = 0; i < xmr_instances.n_xmr_settings; i++ )
+ {
+ XMULTI_REF_INFO *p = &all_xmulti_ref_info_idx[i].info;
+
+ printf( "XMR %i: %li\n", i,
+ (long) p->settings.bias.secs );
+
+#if 0
+ XMULTI_REF_SETTINGS_IDX xmrsi;
+ xmrsi.settings = p->settings;
+ xmrsi.settings.precision.nano_secs = i + 40;
+ xmrsi.settings.bias.secs = 0xA55ACDEF;
+ xmrsi.settings.bias.nano_secs = 0x12345678;
+ xmrsi.idx = i;
+
+ rc = mbg_set_gps_xmr_settings_idx( dh, &xmrsi );
+
+ if ( rc != MBG_SUCCESS )
+ printf( "Failed to write XMR settings %i, rc: %i\n", i, rc );
+#endif
+ }
+
+ if ( !( xmr_instances.flags & XMRIF_MSK_HOLDOVER_STATUS_SUPP ) )
+ printf( "*** Warning: XMR holdover status not supported!\n" );
+ else
+ {
+ rc = mbg_get_xmr_holdover_status( dh, &xmr_holdover_status, &xmr_instances );
+
+ if ( rc != MBG_SUCCESS )
+ printf( "*** Failed to read XMR holdover status, rc: %i\n", rc );
+ else
+ {
+ printf( "XMR mode: %s, %s%s, %s%s, %s%s\n",
+ _get_xmr_holdover_status_mode_name( xmr_holdover_status.mode ),
+ ( xmr_holdover_status.flags & XMR_HLDOVR_MSK_IN_HOLDOVER ) ? "" : str_not_spc, "in holdover",
+ ( xmr_holdover_status.flags & XMR_HLDOVR_MSK_TRANSITION_ENBD ) ? "" : str_not_spc, "transition enabled",
+ ( xmr_holdover_status.flags & XMR_HLDOVR_MSK_IN_TRANSITION ) ? "" : str_not_spc, "in transition"
+ );
+
+//##+++++ print_xmr_prio( xmr_holdover_status.curr_prio, "Current",
+#if 0
+typedef struct
+{
+ uint8_t mode; ///< XMR/holdover mode, see ::XMR_HOLDOVER_STATUS_MODES
+ int8_t curr_prio; ///< current priority level, 0..::XMULTI_REF_INSTANCES::n_xmr_settings, or ::XMR_PRIO_LVL_UNSPEC
+ int8_t nxt_prio; ///< next priority level after holdover, 0..::XMULTI_REF_INSTANCES::n_xmr_settings, or ::XMR_PRIO_LVL_UNSPEC
+ uint8_t remote_watchdog; ///< counts down in ::XMR_HLDOVR_PRE_AUTONOMOUS mode
+ uint32_t reserved; ///< reserved, don't use, currently 0
+ XMR_HOLDOVER_INTV elapsed; ///< elapsed time in holdover mode, only valid if ::XMR_HLDOVR_MSK_IN_HOLDOVER is set
+ XMR_HOLDOVER_INTV interval; ///< current holdover interval, only valid if ::XMR_HLDOVR_MSK_IN_HOLDOVER is set
+ uint32_t flags; ///< holdover status flags, see ::XMR_HOLDOVER_STATUS_FLAG_MASKS
+
+} XMR_HOLDOVER_STATUS;
+#endif
+
+ }
+ }
+
+} // test_xmr
+
+#endif // defined DEBUG
+
+
+
+static const int pcps_to_mbg_framing_tbl[N_PCPS_FR_DCF] =
+{
+ MBG_FRAMING_8N1,
+ MBG_FRAMING_7E2,
+ MBG_FRAMING_8N2,
+ MBG_FRAMING_8E1
+};
+
+
+
+/*HDR*/
+void port_info_from_pcps_serial(
+ PORT_INFO_IDX *p_pii,
+ PCPS_SERIAL pcps_serial,
+ uint32_t supp_baud_rates
+)
+{
+ PCPS_SER_PACK ser_pack;
+ PORT_INFO *p_pi;
+ PORT_SETTINGS *p_ps;
+
+ ser_pack.pack = pcps_serial;
+ pcps_unpack_serial( &ser_pack );
+
+ p_pi = &p_pii[0].port_info;
+ p_ps = &p_pi->port_settings;
+
+ p_ps->parm.baud_rate = mbg_baud_rate[ser_pack.baud];
+
+ strncpy_safe( p_ps->parm.framing, //### TODO
+ mbg_framing_str[pcps_to_mbg_framing_tbl[ser_pack.frame]],
+ sizeof( p_ps->parm.framing ) );
+
+ p_ps->parm.handshake = HS_NONE;
+
+ p_ps->str_type = 0;
+ p_ps->mode = ser_pack.mode;
+
+ p_pi->supp_baud_rates = supp_baud_rates;
+ p_pi->supp_framings = DEFAULT_FRAMINGS_DCF;
+ p_pi->supp_str_types = DEFAULT_SUPP_STR_TYPES_DCF;
+
+} // port_info_from_pcps_serial
+
+
+/*HDR*/
+void pcps_serial_from_port_info(
+ PCPS_SERIAL *p,
+ const PORT_INFO_IDX *p_pii
+)
+{
+ PCPS_SER_PACK ser_pack;
+ const PORT_INFO *p_pi = &p_pii[0].port_info;
+ const PORT_SETTINGS *p_ps = &p_pi->port_settings;
+ int framing_idx = get_framing_idx( p_ps->parm.framing );
+ int i;
+
+
+ ser_pack.baud = get_baud_rate_idx( p_ps->parm.baud_rate );
+
+ // Translate the common framing index to the corresponding
+ // number used with the old PCPS_SERIAL parameter.
+ // This should always return a valid result since the
+ // framing index is expected to be selected from
+ // supported framings.
+ for ( i = 0; i < N_PCPS_FR_DCF; i++ )
+ if ( pcps_to_mbg_framing_tbl[i] == framing_idx )
+ break;
+
+ ser_pack.frame = i;
+
+ ser_pack.mode = p_ps->mode;
+
+ pcps_pack_serial( &ser_pack );
+
+ *p = ser_pack.pack;
+
+} // pcps_serial_from_port_info
+
+
+
+/*--------------------------------------------------------------
+ * Name: pcps_unpack_serial()
+ *
+ * Purpose: Unpack a structure with serial port parameters
+ *
+ * Input/Output: p address of a structure holding both the
+ * packed and unpacked information
+ *
+ * Ret value: --
+ *-------------------------------------------------------------*/
+
+/*HDR*/
+void pcps_unpack_serial( PCPS_SER_PACK *p )
+{
+ uint8_t pack = p->pack;
+
+ p->baud = (uint8_t) ( pack & BITMASK( PCPS_BD_BITS ) );
+ p->frame = (uint8_t) ( ( pack >> PCPS_FR_SHIFT ) & BITMASK( PCPS_FR_BITS ) );
+ p->mode = (uint8_t) ( ( pack >> PCPS_MOD_SHIFT ) & BITMASK( PCPS_MOD_BITS ) );
+
+} // pcps_unpack_serial
+
+
+
+/*--------------------------------------------------------------
+ * Name: pcps_pack_serial()
+ *
+ * Purpose: Pack a structure with serial port parameters
+ *
+ * Input/Output: p address of a structure holding both the
+ * packed and unpacked information
+ *
+ * Ret value: --
+ *-------------------------------------------------------------*/
+
+/*HDR*/
+void pcps_pack_serial( PCPS_SER_PACK *p )
+{
+ p->pack = (uint8_t) ( ( p->baud & BITMASK( PCPS_BD_BITS ) )
+ | ( ( p->frame & BITMASK( PCPS_FR_BITS ) ) << PCPS_FR_SHIFT )
+ | ( ( p->mode & BITMASK( PCPS_MOD_BITS ) ) << PCPS_MOD_SHIFT ) );
+
+} /* pcps_pack_serial */
+
+
+
+/*--------------------------------------------------------------
+ * Name: pcps_str_to_port()
+ *
+ * Purpose: Try to convert a string to a valid port
+ * address.
+ *
+ * Input: s the string
+ *
+ * Output: --
+ *
+ * Ret value: a valid port number or 0
+ *+-------------------------------------------------------------*/
+
+/*HDR*/
+void pcps_setup_isa_ports( char *s,
+ int *port_vals,
+ int n_vals )
+{
+ ushort i;
+
+
+ for ( i = 0; i < n_vals; i++ )
+ {
+ if ( *s == 0 )
+ break;
+
+ *port_vals++ = (uint16_t) strtoul( s, &s, 16 );
+
+ if ( *s == ',' )
+ s++;
+ }
+
+} // pcps_setup_isa_ports
+
+
+
+/*HDR*/
+const char *setup_device_type_name( char *s, size_t max_len, MBG_DEV_HANDLE dh,
+ const RECEIVER_INFO *p_ri )
+{
+ size_t n = sn_cpy_str_safe( s, max_len, p_ri->model_name );
+
+ if ( mbg_rc_is_success( mbg_chk_dev_has_asic_version( dh ) ) )
+ {
+ PCI_ASIC_VERSION asic_version;
+
+ if ( mbg_rc_is_success( mbg_get_asic_version( dh, &asic_version ) ) )
+ n += snprintf_safe( &s[n], max_len - n, " (PCI ASIC v%i.%02i)",
+ _convert_asic_version_number( asic_version ) >> 8,
+ _convert_asic_version_number( asic_version ) & 0xFF );
+ }
+
+ return s;
+
+} // setup_device_type_name
+
+
+
+/*HDR*/
+const char *setup_asic_features( char *s, size_t max_len, MBG_DEV_HANDLE dh )
+{
+ size_t n = 0;
+
+ if ( mbg_rc_is_success( mbg_chk_dev_has_asic_features( dh ) ) )
+ {
+ PCI_ASIC_FEATURES asic_features;
+
+ if ( mbg_rc_is_success( mbg_get_asic_features( dh, &asic_features ) ) )
+ {
+ if ( asic_features & PCI_ASIC_HAS_MM_IO )
+ n += sn_cpy_str_safe( &s[n], max_len - n, "Memory Mapped I/O" );
+
+ //### if ( asic_features & PCI_ASIC_HAS_PGMB_IRQ )
+ // (implement this as loop)
+ }
+ }
+
+ if ( n == 0 ) // nothing else printed
+ sn_cpy_str_safe( s, max_len, str_not_avail );
+
+ return s;
+
+} // setup_asic_features
+
diff --git a/mbglib/common/deviohlp.h b/mbglib/common/deviohlp.h
index a622c07..95b9aa8 100755
--- a/mbglib/common/deviohlp.h
+++ b/mbglib/common/deviohlp.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: deviohlp.h 1.2 2012/10/15 13:51:18 martin REL_M $
+ * $Id: deviohlp.h 1.3.1.29 2016/11/08 17:21:56 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,7 +10,62 @@
*
* -----------------------------------------------------------------------
* $Log: deviohlp.h $
- * Revision 1.2 2012/10/15 13:51:18 martin
+ * Revision 1.3.1.29 2016/11/08 17:21:56 martin
+ * Updated function prototypes.
+ * Revision 1.3.1.28 2016/09/08 10:36:37 martin
+ * Removed obsolete parameter from an API call.
+ * Revision 1.3.1.27 2016/06/15 14:04:06Z thomas-b
+ * Added function mbg_get_all_ucap_info
+ * Revision 1.3.1.26 2016/06/01 11:35:30 martin
+ * Removed some code which is now in mbgdevio.c,h.
+ * Revision 1.3.1.25 2016/05/26 11:00:10 thomas-b
+ * Added parameter ALL_NTP_CFG_INFO to mbgextio_get_all_ntp_status
+ * Use calloc instead of realloc due to performance improvement
+ * Revision 1.3.1.24 2016/05/11 14:37:21 thomas-b
+ * Added functions to read/write ALL_NET_CFG_INFO and ALL_NET_STATUS_INFO
+ * Revision 1.3.1.23 2016/04/26 09:12:24 martin
+ * Made pcps_time_is_valid an inline function.
+ * Revision 1.3.1.22 2016/04/25 14:47:56Z martin
+ * *** empty log message ***
+ * Revision 1.3.1.21 2016/04/20 12:37:54 thomas-b
+ * Moved free functions for ALL_XMULTI_REF_INFO and ALL_XMULTI_REF_STATUS to cfg_hlp
+ * Revision 1.3.1.20 2016/04/18 14:45:30 thomas-b
+ * Added functions to get and save xmr info and status
+ * Revision 1.3.1.19 2016/03/24 14:08:46 martin
+ * *** empty log message ***
+ * Revision 1.3.1.18 2016/03/22 10:53:29 martin
+ * *** empty log message ***
+ * Revision 1.3.1.17 2016/03/10 10:11:58 thomas-b
+ * Added functions, which check to which bus a device is connected
+ * Revision 1.3.1.16 2015/11/20 15:18:27 martin
+ * Revision 1.3.1.15 2015/10/26 16:32:09Z martin
+ * *** empty log message ***
+ * Revision 1.3.1.14 2015/10/26 14:15:27 martin
+ * Revision 1.3.1.13 2015/10/21 11:31:17Z martin
+ * *** empty log message ***
+ * Revision 1.3.1.12 2015/10/21 11:29:16 martin
+ * *** empty log message ***
+ * Revision 1.3.1.11 2015/10/21 11:21:51 martin
+ * *** empty log message ***
+ * Revision 1.3.1.10 2015/10/19 16:42:16 martin
+ * *** empty log message ***
+ * Revision 1.3.1.9 2015/10/07 16:03:21 martin
+ * *** empty log message ***
+ * Revision 1.3.1.8 2015/10/07 10:54:19 martin
+ * Modified GNSS support.
+ * Revision 1.3.1.7 2014/10/29 16:25:32 martin
+ * Moved some functions and structures to more convenient files.
+ * Revision 1.3.1.6 2014/07/14 15:42:45 martin
+ * Revision 1.3.1.5 2014/06/30 15:43:44 martin
+ * Revision 1.3.1.4 2014/04/28 12:21:27 martin
+ * Revision 1.3.1.3 2014/04/28 10:32:40 martin
+ * Revision 1.3.1.2 2013/12/17 15:05:32 martin
+ * Revision 1.3.1.1 2013/12/16 13:53:45Z martin
+ * Updated function prototypes.
+ * Revision 1.3 2013/09/26 08:25:18Z martin
+ * Moved ALL_PTP_CFG_INFO definition to cfg_hlp.h.
+ * Updated doxygen comments.
+ * Revision 1.2 2012/10/15 13:51:18Z martin
* Include cfg_hlp.h.
* Added structure ALL_PTP_CFG_INFO.
* Updated function prototypes.
@@ -44,114 +99,354 @@ extern "C" {
#endif
+/**
+ * @brief A helper structure used with configuration of old DCF77 clocks
+ *
+ * @deprecated This structure has been used with some very
+ * old DCF77 clocks to configure the serial interface.
+ * It has been deprecated by ::PORT_SETTINGS and ::PORT_INFO.
+ */
typedef struct
{
- PTP_CFG_INFO ptp_cfg_info;
- PTP_UC_MASTER_CFG_LIMITS ptp_uc_master_cfg_limits;
- ALL_PTP_UC_MASTER_INFO_IDX all_ptp_uc_master_info_idx;
+ PCPS_SERIAL pack; ///< This packed byte is read from or written to the board
-} ALL_PTP_CFG_INFO;
+ uint8_t baud; ///< The unpacked baud rate code, see ::PCPS_BD_CODES
+ uint8_t frame; ///< The unpacked framing code, see ::PCPS_FR_CODES
+ uint8_t mode; ///< The unpacked mode code, see ::PCPS_MOD_CODES
+} PCPS_SER_PACK;
-/* function prototypes: */
-/* ----- function prototypes begin ----- */
+typedef int (*MBG_ERR_MSG_FNC)( const PCPS_DEV *p_dev, const char *s );
-/* This section was generated automatically */
-/* by MAKEHDR, do not remove the comments. */
- /**
- Read all serial port settings and supported configuration parameters.
+/**
+ * @brief An extended time and status structure
+ *
+ * This structure provides monitoring and configuration tools
+ * with a unified structure containing the current time and
+ * extended status. The structure needs to be set up depending
+ * on the capabilities of a particular device and the API calls
+ * which could be used to retrieve the information.
+ */
+typedef struct
+{
+ PCPS_TIME t; ///< current date, time, and limited status
+ uint8_t comp_sig_mode; ///< 0..::N_CONN_SIG_MODES-1, see ::COMP_SIG_MODES
+ int16_t comp_sig_val; ///< compensated signal value, see @ref PCPS_SIG_VAL_DEFS
+ int32_t utc_offs; ///< %UTC offset, always expanded to [seconds]
+ PCPS_TIME_STATUS_X status_x; ///< extended status, see @see @ref PCPS_TIME_STATUS_FLAGS
+ uint16_t year; ///< full year number
+ uint32_t flags; ///< see ::PCPS_TIME_EXT_FLAGS
- The functions mbg_get_device_info() and mbg_setup_receiver_info()
- must have been called before, and the returned ::PCPS_DEV and
- ::RECEIVER_INFO structures must be passed to this function.
+} PCPS_TIME_EXT;
- The complementary function mbg_save_serial_settings() should be used
- to write the modified serial port configuration back to the board.
- @param dh Valid handle to a Meinberg device.
- @param *pdev Pointer to a ::PCPS_DEV structure.
- @param *pcfg Pointer to a ::RECEIVER_PORT_CFG structure to be filled up.
- @param *p_ri Pointer to a ::RECEIVER_INFO structure.
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+/**
+ * @brief Check if a ::PCPS_TIME structure contains valid date and time
+ *
+ * @param[in] p The structure to be checked
+ *
+ * @return != 0 if date and time valid, else 0
+ */
+static __mbg_inline
+int pcps_time_is_valid( const PCPS_TIME *p )
+{
+ return ( p->sec100 <= 99 )
+ && ( p->sec <= 60 ) // allow for leap second
+ && ( p->min <= 59 )
+ && ( p->hour <= 23 )
+ && ( p->mday >= 1 ) && ( p->mday <= 31 )
+ && ( p->wday >= 1 ) && ( p->wday <= 7 )
+ && ( p->month >= 1 ) && ( p->month <= 12 )
+ && ( p->year <= 99 );
- @see mbg_get_device_info()
- @see mbg_setup_receiver_info()
- @see mbg_save_serial_settings()
-*/
- int mbg_get_serial_settings( MBG_DEV_HANDLE dh, const PCPS_DEV *pdev, RECEIVER_PORT_CFG *pcfg, const RECEIVER_INFO *p_ri ) ;
+} // pcps_time_is_valid
- /**
- Write the configuration settings for a single serial port to the board.
- Modifications to the serial port configuration should be made only
- after mbg_get_serial_settings() had been called to read all serial port
- settings and supported configuration parameters.
- This function has finally to be called once for every serial port
- the configuration of which has been modified.
- As also required by mbg_get_serial_settings(), the functions
- mbg_get_device_info() and mbg_setup_receiver_info() must have been
- called before, and the returned ::PCPS_DEV and ::RECEIVER_INFO structures
- must be passed to this function.
+/* function prototypes: */
- @param dh Valid handle to a Meinberg device
- @param *pdev Pointer to a ::PCPS_DEV structure
- @param *pcfg Pointer to a ::RECEIVER_PORT_CFG structure
- @param port_num Index of the ::serial port to be saved
+/* ----- function prototypes begin ----- */
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
- @see mbg_get_serial_settings()
- @see mbg_get_device_info()
- @see mbg_setup_receiver_info()
-*/
- int mbg_save_serial_settings( MBG_DEV_HANDLE dh, const PCPS_DEV *pdev, RECEIVER_PORT_CFG *pcfg, int port_num ) ;
+ int chk_feat_supp( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, MBG_CHK_SUPP_FNC *chk_supp_fnc, MBG_ERR_MSG_FNC err_msg_fnc, const char *not_supp_msg ) ;
+ /**
+ * @brief Read or setup all GNSS status information
+ *
+ * This function should be called preferably to get a summary of
+ * the GNSS status from GNSS receivers (GPS, GLONASS, ...).
+ *
+ * The function ::mbg_get_device_info must have been called before, and
+ * the returned ::PCPS_DEV structure has to be passed to this function.
+ *
+ * If the device supports this then the low level GNSS API functions
+ * are called directly to collect the status information. If the device
+ * doesn't support the GNSS API but is a pure GPS receiver then the GPS
+ * API functions are called and the GNSS data structures are filled up
+ * accordingly, so the calling application can always evaluate the
+ * GNSS data structures in ::ALL_GNSS_INFO.
+ *
+ * If neither GPS nor another GNSS system is supported then this function
+ * returns the ::MBG_ERR_NOT_SUPP_BY_DEV error.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p_agi Pointer to a ::ALL_GNSS_INFO to be filled
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_stat_info
+ * @see ::mbg_get_gps_gnss_mode_info
+ * @see ::mbg_get_gps_all_gnss_sat_info
+ */
+ int mbg_chk_get_all_gnss_info( MBG_DEV_HANDLE dh, ALL_GNSS_INFO *p_agi ) ;
/**
- Read all PTP settings and supported configuration parameters.
+ * @brief Read all serial port settings and supported configuration parameters
+ *
+ * The functions ::mbg_get_device_info and ::mbg_setup_receiver_info
+ * must have been called before, and the returned ::PCPS_DEV and
+ * ::RECEIVER_INFO structures have to be passed to this function.
+ *
+ * The complementary function ::mbg_save_serial_settings should be used
+ * to write the modified serial port configuration back to the board.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] *p_dev Pointer to a valid ::PCPS_DEV structure
+ * @param[out] *p_rpcfg Pointer to a ::RECEIVER_PORT_CFG structure to be filled up
+ * @param[in] *p_ri Pointer to a valid ::RECEIVER_INFO structure
+ *
+ * @return ::MBG_SUCCESS or error code returned by device I/O control function
+ *
+ * @see ::mbg_get_device_info
+ * @see ::mbg_setup_receiver_info
+ * @see ::mbg_save_serial_settings
+ */
+ int mbg_get_serial_settings( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, RECEIVER_PORT_CFG *p_rpcfg, const RECEIVER_INFO *p_ri ) ;
- The complementary function mbg_save_all_ptp_cfg_info() should
- be used to write the modified configuration back to the device.
+ /**
+ * @brief Write the configuration settings for a single serial port to a device
+ *
+ * Modifications to the serial port configuration should be made only
+ * after ::mbg_get_serial_settings had been called to read all serial port
+ * settings and supported configuration parameters.
+ * This function has finally to be called once for every serial port
+ * the configuration of which has been modified.
+ *
+ * As also required by ::mbg_get_serial_settings, the functions
+ * ::mbg_get_device_info and ::mbg_setup_receiver_info must have been
+ * called before, and the returned ::PCPS_DEV and ::RECEIVER_INFO structures
+ * vave to be passed to this function.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] *p_dev Pointer to a valid ::PCPS_DEV structure
+ * @param[in] *p_rpcfg Pointer to a valid ::RECEIVER_PORT_CFG structure
+ * @param[in] port_num Index of the serial port to be saved
+ *
+ * @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ *
+ * @see ::mbg_get_serial_settings
+ * @see ::mbg_get_device_info
+ * @see ::mbg_setup_receiver_info
+ */
+ int mbg_save_serial_settings( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, RECEIVER_PORT_CFG *p_rpcfg, int port_num ) ;
- @param dh Valid handle to a Meinberg device.
- @param *p Pointer to a ::ALL_PTP_CFG_INFO structure.
+ /**
+ * @brief Read all network configuration into an ::ALL_NET_CFG_INFO structure
+ *
+ * Reads the network configuration of a device via the LAN_IP4 API and
+ * translates the structures into NET_CFG structures.
+ *
+ * As soon as available, this function should make use of the NET_CFG API.
+ *
+ * A ::ALL_NET_CFG_INFO and the appropriate number of ::MBG_NET_INTF_LINK_INFO_IDX,
+ * ::MBG_NET_INTF_ADDR_INFO_IDX, ::MBG_IP_ADDR_IDX, ::MBG_NET_NAME_IDX and
+ * ::MBG_NET_INTF_ROUTE_INFO_IDX will be allocated and need to be freed later
+ * by calling ::free_all_net_cfg_info
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a pointer of ::ALL_NET_CFG_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_settings
+ * @see ::free_all_net_cfg_info
+ */
+ int mbg_get_all_net_cfg_info( MBG_DEV_HANDLE dh, ALL_NET_CFG_INFO **p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Write all network settings to a device
+ *
+ * The complementary function ::mbg_get_all_net_cfg_info should
+ * have been used to read the original network settings and
+ * supported configuration parameters.
+ *
+ * The appropriate settings are translated into LAN_IP4 structures
+ * and send to the device using the appropriate API functions.
+ *
+ * As soon as available, this function should make use of the NET_CFG API.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] p Pointer to a pointer of ::ALL_NET_CFG_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_lan_intf
+ * @see ::mbg_set_ip4_settings
+ */
+ int mbg_save_all_net_cfg_info( MBG_DEV_HANDLE dh, ALL_NET_CFG_INFO *p ) ;
- @see mbg_save_all_ptp_cfg_info()
- @see mbg_get_ptp_cfg_info()
- @see mbg_get_ptp_uc_master_cfg_limits()
- @see mbg_get_all_ptp_uc_master_info()
- @see mbg_dev_has_ptp()
- @see mbg_dev_has_ptp_unicast()
-*/
- int mbg_get_all_ptp_cfg_info( MBG_DEV_HANDLE dh, ALL_PTP_CFG_INFO *p ) ;
+ /**
+ * @brief Read current network status into an ::ALL_NET_STATUS_INFO structure
+ *
+ * Reads the network status of a device via the LAN_IP4 API and
+ * translates the structures into NET_CFG structures.
+ *
+ * As soon as available, this function should make use of the NET_CFG API.
+ *
+ * A ::ALL_NET_STATUS_INFO and the appropriate number of ::MBG_NET_INTF_LINK_INFO_IDX,
+ * ::MBG_NET_INTF_ADDR_INFO_IDX, ::MBG_IP_ADDR_IDX, ::MBG_NET_NAME_IDX and
+ * ::MBG_NET_INTF_ROUTE_INFO_IDX will be allocated and need to be freed later
+ * by calling ::free_all_net_status_info
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a pointer of ::ALL_NET_STATUS_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_state
+ * @see ::free_all_net_status_info
+ */
+ int mbg_get_all_net_status_info( MBG_DEV_HANDLE dh, ALL_NET_STATUS_INFO **p ) ;
/**
- Write all PTP settings and supported configuration parameters
- to a device.
+ * @brief Read all PTP settings and supported configuration parameters
+ *
+ * The complementary function ::mbg_save_all_ptp_cfg_info should
+ * be used to write the modified configuration back to the device.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] *p Pointer to a ::ALL_PTP_CFG_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ *
+ * @see ::mbg_save_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_cfg_info
+ * @see ::mbg_get_ptp_uc_master_cfg_limits
+ * @see ::mbg_get_all_ptp_uc_master_info
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_dev_has_ptp_unicast
+ */
+ int mbg_get_all_ptp_cfg_info( MBG_DEV_HANDLE dh, ALL_PTP_CFG_INFO *p ) ;
- The complementary function mbg_get_all_ptp_cfg_info() should
- have been used to read the original PTP settings and supported
- configuration parameters.
+ /**
+ * @brief Write all PTP settings to a device
+ *
+ * The complementary function ::mbg_get_all_ptp_cfg_info should
+ * have been used to read the original PTP settings and supported
+ * configuration parameters.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] *p Pointer to a valid ::ALL_PTP_CFG_INFO structure
+ *
+ * @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ *
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_set_ptp_cfg_settings
+ * @see ::mbg_set_ptp_uc_master_settings_idx
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_dev_has_ptp_unicast
+ */
+ int mbg_save_all_ptp_cfg_info( MBG_DEV_HANDLE dh, const ALL_PTP_CFG_INFO *p ) ;
- @param dh Valid handle to a Meinberg device.
- @param *p Pointer to a ::ALL_PTP_CFG_INFO structure.
+ /**
+ * @brief Read all XMR info into a newly or re-allocated ::ALL_XMULTI_REF_INFO
+ *
+ * @note ::mbg_chk_dev_supp_xmr should be called before using this function
+ *
+ * A ::ALL_XMULTI_REF_INFO and a number of ::XMULTI_REF_INSTANCES::n_xmr_settings
+ * of ::XMULTI_REF_INFO_IDX and ::XMR_EXT_SRC_INFO_IDX will be allocated and needs
+ * to be freed by calling ::free_all_xmulti_ref_info
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a pointer of ::ALL_XMULTI_REF_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::free_all_xmulti_ref_info
+ */
+ int mbg_get_all_xmulti_ref_info( MBG_DEV_HANDLE dh, ALL_XMULTI_REF_INFO **p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Set all extended multi ref settings to a device
+ *
+ * The complementary function ::mbg_get_all_xmulti_ref_info should
+ * have been used to read the original extended multi ref info.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a ::ALL_XMULTI_REF_INFO structure with all settings
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_set_gps_xmr_settings_idx
+ */
+ _NO_MBG_API_ATTR int _MBG_API mbg_save_all_xmulti_ref_info( MBG_DEV_HANDLE dh, ALL_XMULTI_REF_INFO *p ) ;
- @see mbg_get_all_ptp_cfg_info()
- @see mbg_set_ptp_cfg_settings()
- @see mbg_set_ptp_uc_master_settings_idx()
- @see mbg_dev_has_ptp()
- @see mbg_dev_has_ptp_unicast()
-*/
- int mbg_save_all_ptp_cfg_info( MBG_DEV_HANDLE dh, const ALL_PTP_CFG_INFO *p ) ;
+ /**
+ * @brief Read all XMR status info into a newly or re-allocated ::ALL_XMULTI_REF_STATUS
+ *
+ * @note ::mbg_chk_dev_supp_xmr should be called before using this function
+ *
+ * A ::ALL_XMULTI_REF_STATUS and a number of ::XMULTI_REF_INSTANCES::n_xmr_settings
+ * of ::XMULTI_REF_STATUS_IDX will be allocated and needs to be freed by calling
+ * ::free_all_xmulti_ref_status
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[in] info Pointer to the appropriate info structure
+ * @param[out] p Pointer to a pointer of ::ALL_XMULTI_REF_STATUS
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::free_all_xmulti_ref_status
+ */
+ int mbg_get_all_xmulti_ref_status( MBG_DEV_HANDLE dh, const ALL_XMULTI_REF_INFO *info, ALL_XMULTI_REF_STATUS **p ) ;
+ /**
+ * @brief Read all user capture information and store it into a newly allocated or reused ::ALL_UCAP_INFO
+ *
+ * @note ::mbg_chk_dev_has_ucap should be called to check if this API is supported.
+ *
+ * The appropriate number of ::TTM structures will be allocated and needs to be freed
+ * by calling ::free_all_ucap_info. Existing user captures will not be removed, so the
+ * number of user captures can never decrease.
+ *
+ * @param[in] dh Valid handle to a Meinberg device
+ * @param[out] p Pointer to a pointer to ::ALL_UCAP_INFO
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ucap
+ * @see ::free_all_ucap_info
+ */
+ int mbg_get_all_ucap_info( MBG_DEV_HANDLE dh, ALL_UCAP_INFO **p ) ;
+
+ void test_gpio( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, int verbose ) ;
+ void test_xmr( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, int verbose ) ;
+ void port_info_from_pcps_serial( PORT_INFO_IDX *p_pii, PCPS_SERIAL pcps_serial, uint32_t supp_baud_rates ) ;
+ void pcps_serial_from_port_info( PCPS_SERIAL *p, const PORT_INFO_IDX *p_pii ) ;
+ void pcps_unpack_serial( PCPS_SER_PACK *p ) ;
+ void pcps_pack_serial( PCPS_SER_PACK *p ) ;
+ void pcps_setup_isa_ports( char *s, int *port_vals, int n_vals ) ;
+ const char *setup_device_type_name( char *s, size_t max_len, MBG_DEV_HANDLE dh, const RECEIVER_INFO *p_ri ) ;
+ const char *setup_asic_features( char *s, size_t max_len, MBG_DEV_HANDLE dh ) ;
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/gpsdefs.h b/mbglib/common/gpsdefs.h
index 5266ee0..b5f9de7 100755
--- a/mbglib/common/gpsdefs.h
+++ b/mbglib/common/gpsdefs.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: gpsdefs.h 1.113.1.11 2013/06/26 15:49:24 martin TRASH $
+ * $Id: gpsdefs.h 1.124.1.311 2017/04/25 11:36:24 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -13,29 +13,732 @@
*
* -----------------------------------------------------------------------
* $Log: gpsdefs.h $
- * Revision 1.113.1.11 2013/06/26 15:49:24 martin
+ * Revision 1.124.1.311 2017/04/25 11:36:24 martin
+ * Renamed GRC181PEX to GNS181PEX.
+ * Revision 1.124.1.310 2017/04/11 10:30:14 philipp
+ * Added USB lock swap macros
+ * Revision 1.124.1.309 2017/04/11 06:42:41 philipp
+ * Renamed MBG_USB_INTR structures to MBG_USB_LOCK
+ * Revision 1.124.1.308 2017/04/11 06:22:29 philipp
+ * Put MBG_USB_INTR_SETTINGS into MBG_USB_INTR_INFO
+ * Revision 1.124.1.307 2017/04/11 05:29:56 philipp
+ * Added commands, structures and defines for feature USB interrupt
+ * Revision 1.124.1.306 2017/04/04 10:57:27 paul.kretz
+ * Added FDM180M and associated definitions
+ * Revision 1.124.1.305 2017/04/04 09:06:40Z philipp
+ * Added general monitoring and event transactions
+ * Revision 1.124.1.304 2017/04/04 06:20:49 andre.hartmann
+ * xfeature for xhe unit added
+ * Revision 1.124.1.303 2017/03/28 09:38:45Z paul.kretz
+ * added support for MircoSync power supply module
+ * Revision 1.124.1.302 2017/03/27 10:38:13Z thomas-b
+ * Renamed PTPv1 common datasets, added swab macros, feature flag and comments
+ * Revision 1.124.1.301 2017/03/24 10:18:56 paul.kretz
+ * removed ENABLE_FLAGS in BUILTIN_FEAT_VSG180
+ * Revision 1.124.1.300 2017/03/23 08:55:57Z thomas-b
+ * Fixed wrong documentation for MBG_IO_PORT_STATUS_BUFFER
+ * Revision 1.124.1.299 2017/03/22 09:46:28 thomas-b
+ * Added transaction for IO ports
+ * Revision 1.124.1.298 2017/03/22 08:54:45 thomas-b
+ * Fixed string initializer for POUT IO port type
+ * Revision 1.124.1.297 2017/03/22 08:28:21 philipp
+ * Added MBG_IO_PORT_OP_MODE_NONE to enum MBG_IO_PORT_OP_MODE_BITS
+ * Revision 1.124.1.296 2017/03/21 13:32:55 thomas-b
+ * Added relation string variable to MBG_IO_PORT_INFO structure
+ * Revision 1.124.1.295 2017/03/21 08:46:46 thomas-b
+ * Added support for physical and logical IO port groups
+ * Revision 1.124.1.294 2017/03/20 17:10:23 martin
+ * Fixed and added lots of swab..() macros.
+ * Revision 1.124.1.293 2017/03/20 10:10:02 martin
+ * Fixed build without _PRELIMINARY_CODE.
+ * Revision 1.124.1.292 2017/03/17 11:59:47 thomas-b
+ * Added directio in/out and io port positions
+ * Revision 1.124.1.291 2017/03/16 07:47:51 thomas-b
+ * Added several missing IO port conn types
+ * Added new IO port type prog. pulse and appropriate structures
+ * Revision 1.124.1.290 2017/03/15 09:08:12 philipp
+ * Added I/O port types
+ * Revision 1.124.1.289 2017/03/15 09:00:49 gregoire
+ * str initializer for NTP_SYMM_KEY_HASHES added
+ * Revision 1.124.1.288 2017/03/15 06:46:24 thomas-b
+ * Shortened string defines for IO port OP modes
+ * Revision 1.124.1.287 2017/03/14 13:44:41 philipp
+ * Added size initializer for new I/O port type ethernet
+ * Revision 1.124.1.286 2017/03/14 08:55:17 thomas-b
+ * Added IO port type for network
+ * Reworked event info structure
+ * Revision 1.124.1.285 2017/03/13 11:42:13 gregoire.diehl
+ * New PTP preset DOCSIS 3.1 added
+ * Revision 1.124.1.284 2017/03/10 10:36:41Z paul.kretz
+ * extended MBG_GPIO_VIDEO_TC_MODES enum
+ * Revision 1.124.1.283 2017/03/10 09:03:22Z philipp
+ * Added event_cfg_counter to MBG_MONITORING_STATUS
+ * Revision 1.124.1.282 2017/03/10 07:23:52 thomas-b
+ * Added define for invalid event sub_idx
+ * Revision 1.124.1.281 2017/03/08 12:44:25 thomas-b
+ * Added mask MBG_TRANSACTION_MSK_SET
+ * Revision 1.124.1.280 2017/03/08 12:35:44 thomas-b
+ * Added macros for transaction type set
+ * Revision 1.124.1.279 2017/03/08 11:42:41 paul.kretz
+ * bugfix in MBG_GPIO_VIDEO_TC_MODE_MASKS
+ * Revision 1.124.1.278 2017/03/07 13:56:35Z paul.kretz
+ * extended GPIO structs for time code support
+ * Revision 1.124.1.277 2017/03/07 13:46:12Z thomas-b
+ * Removed builtin feature for ignore lock
+ * Revision 1.124.1.276 2017/03/07 09:08:43 thomas-b
+ * *** empty log message ***
+ * Revision 1.124.1.275 2017/03/07 08:11:01 thomas-b
+ * Added global feature flag for bonding
+ * Revision 1.124.1.274 2017/03/03 07:26:53 thomas-b
+ * Renamed NTP transaction
+ * Revision 1.124.1.273 2017/03/03 06:42:39 thomas-b
+ * Relocated NTP_GLB_INFO, fixed several swab macros of new NTP structures
+ * Revision 1.124.1.272 2017/03/02 14:02:25 gregoire
+ * NTP related structures reworked
+ * MBG_TRANSACTION_TYPE_MONITORING_NTP added
+ * Revision 1.124.1.271 2017/03/01 10:44:26 philipp
+ * Use _PRELIMINARY_CODE macro instead of debug macro
+ * Revision 1.124.1.270 2017/02/28 15:31:08 gregoire
+ * NTP_GLB_INFO: field max_trusted_keys added
+ * NTP_CLNT_MODE_SETTINGS: field num_peers added
+ * NTP_SRV_MODE_SETTINGS: field num_refclks added
+ * NTP_SRV_MODE_INFO: field max_refclks added
+ * Revision 1.124.1.269 2017/02/27 09:20:34 thomas-b
+ * Fixed typo in GNSS_SV_STAT_QUALITY_INDS
+ * Revision 1.124.1.268 2017/02/27 07:44:30 thomas-b
+ * Changed builtin features for GNS181_UC from preset GPS to preset GNSS
+ * Revision 1.124.1.267 2017/02/24 11:00:55 philipp
+ * Moved event type from settings to info
+ * Revision 1.124.1.266 2017/02/24 09:38:25 philipp
+ * Do not use fixed buffers for monitorung event info and status
+ * Revision 1.124.1.265 2017/02/22 12:21:45 thomas-b
+ * Added string initializers for event types and severities
+ * Revision 1.124.1.264 2017/02/22 07:53:35 thomas-b
+ * Added swab macros for monitoring event and status structures
+ * Revision 1.124.1.263 2017/02/21 15:53:47 philipp
+ * Added monitoring event and status structures and defines
+ * Revision 1.124.1.262 2017/02/16 13:00:57 thomas-b
+ * Added MBG_PTP_V2_PORT_DATASET_IDX structure and removed MBG_PTP_V2_COMMON_DATASETS
+ * Revision 1.124.1.261 2017/02/16 09:01:31 martin
+ * New field MBG_GNSS_MODE_INFO::n_sv_status.
+ * Revision 1.124.1.260 2017/02/16 08:13:00 thomas-b
+ * Added structures and supp. flag for PTPv2 common datasets defined in IEEE1588-2008, chapter 8.2
+ * Revision 1.124.1.259 2017/02/15 16:14:47 martin
+ * New GNSS type QZSS.
+ * Renamed GNSS_SV_INFO to GNSS_SV_STATUS.
+ * New flag MBG_GNSS_FLAG_MSK_HAS_SV_STATUS.
+ * Revision 1.124.1.258 2017/02/13 08:32:12 philipp
+ * Fixed GNSS swap macro redefinitions
+ * Revision 1.124.1.257 2017/02/13 08:26:53 philipp
+ * Fixed some typos in SNMP structures
+ * Revision 1.124.1.256 2017/02/10 15:21:11 martin
+ * Added swab macros for new structures.
+ * Revision 1.124.1.255 2017/02/10 14:26:22 martin
+ * New extended feature MBG_XFEATURE_GNSS_SV_INFO
+ * and associated structures.
+ * Revision 1.124.1.254 2017/02/08 13:33:42 philipp
+ * Removed redundant information MBG_SNMP_V12_TRAP_SETTINGS
+ * Revision 1.124.1.253 2017/02/08 12:49:30 thomas-b
+ * Changed all int8_t to char in SNMP structs, fixed typo and added some documentation
+ * Revision 1.124.1.252 2017/02/08 07:04:53 philipp
+ * Added swaP macros for SNMP monitoring structures
+ * Revision 1.124.1.251 2017/02/07 11:46:19 philipp
+ * Fixed duplicate members
+ * Revision 1.124.1.250 2017/02/07 11:39:42 philipp
+ * Added destination port for SNMP trap receivers
+ * Revision 1.124.1.249 2017/02/07 11:34:46 daniel
+ * *** empty log message ***
+ * Revision 1.124.1.248 2017/02/07 10:15:19 daniel
+ * Removed unneccessary xfeature LICENSE_LIMITS
+ * Revision 1.124.1.247 2017/02/06 13:10:25 philipp
+ * Added SNMP monitoring structures and defines
+ * Revision 1.124.1.246 2017/02/06 10:47:49 philipp
+ * Added monitoring XFeature skeleton
+ * Revision 1.124.1.245 2017/02/06 08:57:58 daniel
+ * Added XFEATURE for License Limits
+ * Revision 1.124.1.244 2017/02/01 09:45:25 daniel
+ * Added new TLV License types for PTPv1 and Time Monitor
+ * Revision 1.124.1.243 2017/02/01 09:35:38 martin
+ * Defined DEFAULT_POUT_PULSE_SHIFT_MIN and
+ * DEFAULT_POUT_PULSE_SHIFT_MAX.
+ * Revision 1.124.1.242 2017/01/27 10:24:11 philipp
+ * Fixed missing while in macro
+ * Revision 1.124.1.241 2017/01/27 09:13:15 martin
+ * Fixed macro syntax.
+ * Revision 1.124.1.240 2017/01/26 15:24:36 martin
+ * Support new model RSC180RDU.
+ * Revision 1.124.1.239 2017/01/26 15:13:57 martin
+ * Fixed some macros.
+ * Revision 1.124.1.238 2017/01/25 14:34:12 martin
+ * Added definition POUT_MODES_SUPP_TIMEBASE_UTC.
+ * Updated comments for POUT_SETTINGS_FLAG_BITS.
+ * Revision 1.124.1.237 2017/01/25 13:10:38 martin
+ * Added POUT bit masks definitions indicating which parameter fields
+ * are relevant for which POUT modes.
+ * Fixed macros _mbg_swab_pout_settings_on_get() and
+ * _mbg_swab_pout_settings_on_set().
+ * Updated comments, and fixed some typos in comments.
+ * Revision 1.124.1.236 2017/01/24 14:15:44 daniel
+ * Started to define structures for PTPv1 datasets
+ * Revision 1.124.1.235 2017/01/10 16:17:11 daniel
+ * Added PTPv1 roles
+ * Revision 1.124.1.234 2017/01/06 15:53:20 martin
+ * More POUT pulse shift support.
+ * Revision 1.124.1.233 2017/01/05 14:16:35 martin
+ * Added missing definitions for PSX_4GE.
+ * Revision 1.124.1.232 2017/01/02 10:43:39 andre.hartmann
+ * Added model code for PSX_4GE board.
+ * Revision 1.124.1.231 2016/12/22 11:21:32Z philipp
+ * Added NTP and PTP hardware timestamping flags to MBG_NET_INTF_LINK_OPTS
+ * Revision 1.124.1.230 2016/12/22 10:19:21 martin
+ * Doxygen fix.
+ * Revision 1.124.1.229 2016/12/21 09:15:23 martin
+ * Added GPS_MODEL_HAS_SV_INFO to the BUILTIN_FEAT_GPS mask.
+ * Support new model GNS180_UC.
+ * Revision 1.124.1.228 2016/12/08 11:44:17 paul.kretz
+ * Updated masks for SCU_STAT_INFO
+ * Revision 1.124.1.227 2016/12/07 14:44:44Z paul.kretz
+ * Added new masks for SCU_STAT_INFO to support up to 4 power supplies
+ * Revision 1.124.1.226 2016/12/07 09:34:40Z martin
+ * Removed trailing spaces.
+ * Revision 1.124.1.225 2016/12/06 14:50:15 andre.hartmann
+ * Added model code for GPS165
+ * Revision 1.124.1.224 2016/12/06 09:15:58Z thomas-b
+ * Added builtin feature HAS_SV_INFO for all GPS (only) receivers
+ * Revision 1.124.1.223 2016/12/01 11:20:08 philipp
+ * Fixed MBG_IO_PORT_INFO_MIN_SIZE
+ * Revision 1.124.1.222 2016/11/30 11:25:07 thomas-b
+ * Added builtin feature for SCU_STAT and added it to RSC180 and MDU180
+ * Revision 1.124.1.221 2016/11/29 14:07:00 philipp
+ * Added MBG_IO_PORT_INFO_IDX_SIZES
+ * Revision 1.124.1.220 2016/11/25 11:32:15 philipp
+ * Finalized I/O port structures, enums, defines
+ * Revision 1.124.1.219 2016/11/24 07:06:34 philipp
+ * Honour big endian system when swapping bytes
+ * Revision 1.124.1.218 2016/11/23 12:41:12 philipp
+ * Fixed GPIO swap macro typos
+ * Revision 1.124.1.217 2016/11/23 09:36:30 paul.kretz
+ * added swab macros for GPIO's
+ * extended MBG_IO_PORT structs
+ * removed unused preprocessor symbol in FPGA_INFO struct
+ * Revision 1.124.1.216 2016/11/22 10:33:16Z philipp
+ * Implemented I/O ports
+ * Revision 1.124.1.215 2016/11/21 12:22:44 thomas-b
+ * Added enable flags as builtin feature for FDM180
+ * Revision 1.124.1.214 2016/11/16 11:00:36 thomas-b
+ * Added core module type and revision to MBG_EXT_SYS_INFO
+ * Revision 1.124.1.213 2016/11/10 14:08:17 thomas-b
+ * Changed string name for GPS_MODEL_NAME_UNKNOWN
+ * Revision 1.124.1.212 2016/11/08 17:22:11 martin
+ * Doxygen fixes.
+ * Revision 1.124.1.211 2016/11/04 11:48:35 paul.kretz
+ * Support MDU312.
+ * Revision 1.124.1.210 2016/11/04 07:21:26Z thomas-b
+ * Added flag, mask, and idx for GPIO, which indicates that a GPIO configuration depends on another GPIO
+ * Revision 1.124.1.209 2016/11/02 11:54:57 paul.kretz
+ * added new xfeature MBG_XFEATURE_REQ_TTM
+ * Revision 1.124.1.208 2016/11/01 09:27:49Z thomas-b
+ * Added builtin feature for TZDL to FDM180
+ * Revision 1.124.1.207 2016/11/01 09:24:12 martin
+ * *** empty log message ***
+ * Revision 1.124.1.206 2016/10/25 13:24:37 martin
+ * *** empty log message ***
+ * Revision 1.124.1.205 2016/10/25 08:56:40 martin
+ * Renamed MSK_ICODE_RX_HAS_SHORT_YEAR to MSK_ICODE_RX_HAS_SHORT_YEAR_AFTER_P5.
+ * New MSK_ICODE_RX_HAS_ANY_SHORT_YEAR which includes
+ * all codes providing a year number, either after P5 or after P6.
+ * Doxygen fixes.
+ * Changes to builtin feature definitions.
+ * Revision 1.124.1.204 2016/10/24 08:12:04 martin
+ * Support MDU180.
+ * Revision 1.124.1.203 2016/10/20 10:43:20 thomas-b
+ * Added builtin feature GPS_MODEL_IS_BUS_LVL_DEV
+ * Revision 1.124.1.202 2016/10/19 10:19:59 thomas-b
+ * Added define for default user capture network UDP port
+ * Revision 1.124.1.201 2016/10/19 09:07:28 thomas-b
+ * Added supported flags for MBG_UCAP_NET_GLB_INFO
+ * Revision 1.124.1.200 2016/10/13 07:30:10 paul.kretz
+ * Extended sysinfo proc and fpga types by SAM3s, STM32F4, Cyclone4GX15 and Cyclone4CE22
+ * Revision 1.124.1.199 2016/10/10 10:36:35Z thomas-b
+ * Added transfer protocol for ucap network receivers and added destination port
+ * Revision 1.124.1.198 2016/10/10 10:17:37 thomas-b
+ * Removed _PRELIMINARY_CODE_AUDIO restrictions
+ * Added new extended feature and structure definitions for ucap via network
+ * Revision 1.124.1.197 2016/10/07 11:24:50 thomas-b
+ * Fixed swab makro for addr settings
+ * Revision 1.124.1.196 2016/10/05 08:26:36 andre.hartmann
+ * Revision 1.124.1.195 2016/09/29 11:56:43Z philipp
+ * Added documentation for MBG_TRANSACTION_TYPE_NETWORK
+ * Revision 1.124.1.194 2016/09/29 10:43:41 thomas-b
+ * Added define for MBG_ARPHRD_ETHER
+ * Revision 1.124.1.193 2016/09/29 06:13:07 philipp
+ * Added support for beginning / ending typed transactions
+ * Revision 1.124.1.192 2016/09/28 13:35:00 philipp
+ * Renamed flag field
+ * Revision 1.124.1.191 2016/09/28 13:29:22 thomas-b
+ * Added feature flags for MBG_NET_GLB_CFG_INFO
+ * Revision 1.124.1.190 2016/09/26 13:04:54 udo
+ * added missing comma in MBG_TLV_FEAT_TYPE_NAMES
+ * Revision 1.124.1.189 2016/09/26 10:08:14 udo
+ * added TLV Feature MBG_TLV_FEAT_TYPE_FILE_REQUEST to request a generic file from HPS
+ * Revision 1.124.1.188 2016/09/23 08:29:09 martin
+ * Fixed missing comma in string table initializer.
+ * Revision 1.124.1.187 2016/09/22 12:12:29 philipp
+ * Split ::MBG_NET_INTF_LINK_OPTS::MBG_NET_INTF_LINK_OPT_CAN_SYNCE up into SyncE In and SyncE Out option
+ * Revision 1.124.1.186 2016/09/15 14:54:30 martin
+ * Support GRC181PEX.
+ * Revision 1.124.1.185 2016/09/12 09:16:49 martin
+ * Fixed cascaded comment characters.
+ * Revision 1.124.1.184 2016/09/08 10:25:03 martin
+ * Fixed build for 16 bit targets.
+ * Revision 1.124.1.183 2016/09/05 13:23:04 paul.kretz
+ * Added ENABLE_FLAGS to BUILTIN_FEAT_VSG180
+ * Revision 1.124.1.182 2016/08/25 14:37:16Z paul.kretz
+ * added new gpio video type PAL_M
+ * Revision 1.124.1.181 2016/08/23 15:47:04Z martin
+ * Moved macros _setup_default_receiver_info_dcf() and
+ * _setup_default_receiver_info_gps() here.
+ * Revision 1.124.1.180 2016/08/16 13:01:13 martin
+ * Syntax fix.
+ * Revision 1.124.1.179 2016/08/12 11:05:14 paul.kretz
+ * Added digital audio output as new gpio type which is only included
+ * if symbol _PRELIMINARY_CODE_AUDIO is defined.
+ * Revision 1.124.1.178 2016/08/11 11:34:06Z martin
+ * Modified MBG_REF_OFFS_NOT_CFGD to avoid compiler warning.
+ * Revision 1.124.1.177 2016/08/11 11:30:16 martin
+ * Moved time monitoring stuff to new file time_mon.h.
+ * Revision 1.124.1.176 2016/08/11 10:28:09 udo
+ * prepare extended data set for time monitor
+ * Revision 1.124.1.175 2016/08/10 05:17:08 udo
+ * added domain number to Time Monitor Target Settings
+ * Revision 1.124.1.174 2016/08/09 14:48:06 martin
+ * Revision 1.124.1.173 2016/08/03 08:05:11Z thomas-b
+ * Finished new network structures, definitions and relations
+ * Revision 1.124.1.172 2016/07/29 09:36:21 paul.kretz
+ * Added definitions for N2X180.
+ * Revision 1.124.1.171 2016/07/15 14:08:09Z martin
+ * Fixed a typo.
+ * Revision 1.124.1.170 2016/07/07 14:17:02 martin
+ * Cleaned up POUT API.
+ * Doxygen fixes.
+ * Revision 1.124.1.169 2016/07/07 09:57:10 andre.hartmann
+ * added mbg_clk_res_info
+ * Revision 1.124.1.168 2016/06/28 15:42:16Z martin
+ * *** empty log message ***
+ * Revision 1.124.1.167 2016/06/28 15:04:40 martin
+ * Added definitions for GRC181.
+ * Added missing definitions for GPS180CSM.
+ * Revision 1.124.1.166 2016/06/23 09:23:24 thomas-b
+ * Added num_dns_srvr and num_dns_srch_dom to MBG_NET_GLB_CFG_SETTINGS
+ * Revision 1.124.1.165 2016/06/22 06:58:37 udo
+ * added new parameters to MBG_TIME_MON_TARGET_STATUS
+ * Revision 1.124.1.164 2016/06/21 06:34:54 andre
+ * QL alarms now separated for TDEV and MTIE
+ * comment for QL hysteresis added
+ * Revision 1.124.1.163 2016/06/10 07:59:09Z philipp
+ * Extended sysinfo proc and fpga types by SAM3u and Cyclone5
+ * Revision 1.124.1.162 2016/06/09 09:17:08 thomas-b
+ * Added builtin features TIME and TZDL for TCR cards
+ * Revision 1.124.1.161 2016/06/06 08:59:45 andre
+ * Revision 1.124.1.160 2016/06/02 13:36:11Z philipp
+ * Extended MBG_EXT_SYS_INFO proc and fpga types
+ * Revision 1.124.1.159 2016/06/02 10:57:51 philipp
+ * Added string initializers for MBG_EXT_SYS_INFO's proc and FPGA types
+ * Revision 1.124.1.158 2016/06/02 10:24:22 philipp
+ * Renaming all revision macros and helper functions
+ * Revision 1.124.1.157 2016/06/02 10:15:35 philipp
+ * Renaming all MBG_EXT_REV_INFO related stuff to MBG_EXT_SYS_INFO.
+ * Revision 1.124.1.156 2016/06/01 10:49:49 andre
+ * Revision 1.124.1.155 2016/06/01 09:51:26Z philipp
+ * Added structures and definitions for new type MBG_LICENSE to be queried via TLV_API.
+ * Revision 1.124.1.154 2016/06/01 06:59:00 andre
+ * Revision 1.124.1.153 2016/05/31 14:32:27Z andre
+ * Revision 1.124.1.152 2016/05/31 14:32:02Z andre
+ * Revision 1.124.1.151 2016/05/30 08:14:09Z thomas-b
+ * Added builtin feature GPS_MODEL_HAS_TIME to GPS receivers and N2x
+ * Revision 1.124.1.150 2016/05/27 06:32:12 philipp
+ * Changed XMR_HOLDOVER_STATUS_MODE_NAMES
+ * Revision 1.124.1.149 2016/05/26 08:01:16 andre
+ * Revision 1.124.1.148 2016/05/24 14:43:10Z andre
+ * Revision 1.124.1.147 2016/05/24 13:32:24Z philipp
+ * Added PTP Statistics
+ * Revision 1.124.1.146 2016/05/20 08:58:52 thomas-b
+ * New BUILTIN_FEATURE GPS_HAS_TZCODE for older PZF cards
+ * Revision 1.124.1.145 2016/05/20 06:41:42 thomas-b
+ * Added TZDL and ENABLE_FLAGS to BUILTIN_FEAT_N2X
+ * Revision 1.124.1.144 2016/05/19 13:12:32 paul
+ * renamed two video HD formats:
+ * 1080i29.97Hz to 1080i59.94Hz and 1080i25Hz to 1080i50Hz
+ * Revision 1.124.1.143 2016/05/11 13:20:20Z thomas-b
+ * Changed several fields and flags in NET_CFG structures
+ * Revision 1.124.1.142 2016/05/09 08:06:53 philipp
+ * New array string initializers for LED modes and colors
+ * Revision 1.124.1.141 2016/05/04 09:57:27 thomas-b
+ * Comment changed
+ * Revision 1.124.1.140 2016/04/26 09:17:41 thomas-b
+ * Changed structure MBG_NET_GLB_CFG_SETTINGS
+ * Revision 1.124.1.139 2016/04/26 08:51:47 philipp
+ * New multi reference input type SyncE
+ * Revision 1.124.1.138 2016/04/26 08:18:58 thomas-b
+ * Added typedefs for interface route structures if _PRELIMINARY_CODE is not defined
+ * Revision 1.124.1.137 2016/04/26 07:39:45 thomas-b
+ * Changed names and descriptions in net_cfg structures
+ * Relocated preliminary code areas in net_cfg and ntp definitions
+ * Revision 1.124.1.136 2016/04/26 06:05:44 philipp
+ * Removed space to fix compiler error on ARM GCC 4.9.3
+ * Revision 1.124.1.135 2016/04/25 15:13:58 martin
+ * *** empty log message ***
+ * Revision 1.124.1.134 2016/04/25 14:34:46 martin
+ * *** empty log message ***
+ * Revision 1.124.1.133 2016/04/25 10:23:22Z martin
+ * TLV code isn't preliminary anymore.
+ * Enums with more than 16 entries are not supported by 16 bit compilers.
+ * Revision 1.124.1.132 2016/04/22 08:36:27 philipp
+ * Added String initializers for GPIO bit out flags
+ * Revision 1.124.1.131 2016/04/21 10:53:29 philipp
+ * Added GPIO bits format strings.
+ * Added T1 SSM quality levels.
+ * Revision 1.124.1.130 2016/04/20 14:43:29 udo
+ * use NANO_TIME instead of double
+ * Revision 1.124.1.129 2016/04/20 13:16:58 thomas-b
+ * Added typedefs for NTP_SRV_MODE_INFO and NTP_SRV_MODE_SETTINGS
+ * Revision 1.124.1.128 2016/04/20 09:26:05 philipp
+ * Moved all HPS-PTP related structures to gpspriv.h and removed related extended feature bit from gpsdefs.h.
+ * Also removed functions from mbgextio and xdevfeat since HPS-PTP handling needs a redesign concerning structures.
+ * Thus, handle everything explicitly for now!
+ * -> Redesing this A.S.A.P.!!!
+ * Revision 1.124.1.127 2016/04/18 12:37:02 thomas-b
+ * New network structures and definitions for bonding and routing
+ * Revision 1.124.1.126 2016/04/15 13:14:08 daniel
+ * Added PTP profile ITU-T. G. 8275.2
+ * Revision 1.124.1.125 2016/04/15 09:22:16 udo
+ * fixed alignment problem in PTP_DEV_CFG_GLB
+ * Revision 1.124.1.124 2016/04/15 08:17:28 philipp
+ * New feature MBG_XFEATURE_EXT_PTP
+ * Revision 1.124.1.123 2016/04/15 07:31:46 andre
+ * Revision 1.124.1.122 2016/04/08 10:18:02Z daniel
+ * Fixed MBG_ENCODE_EXT_REV macro
+ * Revision 1.124.1.121 2016/04/08 10:16:29 martin
+ * *** empty log message ***
+ * Revision 1.124.1.120 2016/04/07 13:20:23 philipp
+ * Extended NTP definitions and added new structure MBG_EXT_REV_INFO including enums, masks, etc..
+ * Revision 1.124.1.119 2016/04/05 13:29:25 daniel
+ * Adjust ptp cfg and state structures to take care of unified data type sizes and alignment
+ * Revision 1.124.1.118 2016/04/04 14:46:13 martin
+ * Added TLV feature type names.
+ * Revision 1.124.1.117 2016/03/24 14:08:47 martin
+ * *** empty log message ***
+ * Revision 1.124.1.116 2016/03/24 09:14:52 martin
+ * New extended feature MBG_XFEATURE_PWR_CTL_API.
+ * Revision 1.124.1.115 2016/03/18 11:21:52 martin
+ * *** empty log message ***
+ * Revision 1.124.1.114 2016/03/18 10:32:25 martin
+ * *** empty log message ***
+ * Revision 1.124.1.113 2016/03/17 09:21:01 martin
+ * *** empty log message ***
+ * Revision 1.124.1.112 2016/03/16 15:13:37 martin
+ * *** empty log message ***
+ * Revision 1.124.1.111 2016/03/16 08:29:13 martin
+ * Removed ..._MODEL_HAS_GNSS_MODE definitions, use ..._MODEL_IS_GNSS
+ * instead.
+ * Revision 1.124.1.110 2016/03/15 14:55:04 martin
+ * Modified LNE and LED API.
+ * Revision 1.124.1.109 2016/03/14 11:54:06 martin
+ * Fixed duplicate macro name.
+ * Revision 1.124.1.108 2016/03/11 15:12:08 martin
+ * Started to refactor LED and LNE API.
+ * Revision 1.124.1.107 2016/03/11 11:25:26 martin
+ * Made XMR_STATS::step_det_val a reserved, unused field.
+ * Cleanup.
+ * Revision 1.124.1.106 2016/03/11 10:09:44 andre
+ * Revision 1.124.1.105 2016/03/02 15:03:42Z daniel
+ * Updates for new PTP Utility profile and PTP statistics
+ * Revision 1.124.1.104 2016/02/29 15:51:31 andre
+ * added estimated holdover var to XMR_HOLDOVER_STATUS
+ * Revision 1.124.1.103 2016/02/25 08:47:32Z paul
+ * Added definitions for GTS180.
+ * Revision 1.124.1.102 2016/02/24 09:23:55Z gregoire
+ * change PTP_ANN_RCPT_TIMEOUT_MAX from 255 to 8
+ * Revision 1.124.1.101 2016/02/19 12:11:21Z udo
+ * added MBG_LNE_INFO_EXT
+ * Revision 1.124.1.100 2016/02/18 14:56:37 daniel
+ * Added TLV FEAT_TYPE LICENSE UPGRADE
+ * Revision 1.124.1.99 2016/02/18 11:27:27 udo
+ * added MBG_LNE_LED_STATUS
+ * Revision 1.124.1.98 2016/02/16 08:38:50 gregoire
+ * added new initializer to MBG_XFEATURE_NAMES
+ * Revision 1.124.1.97 2016/02/11 12:02:39Z daniel
+ * Added two TLV_FEAT_TYPES
+ * Revision 1.124.1.96 2016/02/10 15:52:36 thomas-b
+ * Added enum MBG_IMS_FDM_FLAGS and appropriate masks enum
+ * Revision 1.124.1.95 2016/02/03 13:27:44 martin
+ * Added definitions for LNE180SFP.
+ * Revision 1.124.1.94 2016/02/03 09:41:32 martin
+ * Fixed build without _PRELIMINARY_CODE.
+ * Revision 1.124.1.93 2016/02/02 15:53:46Z martin
+ * Added definitions for CSM100.
+ * Revision 1.124.1.92 2016/01/29 09:06:32 udo
+ * Added time-protocol type to Time Monitor Target settings.
+ * Revision 1.124.1.91 2016/01/22 11:34:39 gregoire
+ * Added string initializers for XMR_STATS_FLAGS_BITS.
+ * Revision 1.124.1.90 2016/01/22 08:16:07Z gregoire
+ * Renamed DEFAULT_MULTI_REF_NAMES_SHORT strings.
+ * Revision 1.124.1.89 2016/01/21 08:59:03Z andre
+ * Added auto_bis field in XMR_STATS.
+ * Revision 1.124.1.88 2016/01/19 14:11:47Z udo
+ * Modified time monitor structures.
+ * Revision 1.124.1.87 2016/01/18 08:37:03 udo
+ * Added support for PTP Time Monitoring on TSU/HPS100.
+ * Revision 1.124.1.86 2016/01/15 11:30:14 martin
+ * New field 'timestamp' in XMR_STATS.
+ * Revision 1.124.1.85 2016/01/15 08:52:51 martin
+ * Some flag masks for XMR_STATS.
+ * Revision 1.124.1.84 2016/01/13 15:26:00 martin
+ * Removed obsolete code added in the previous version.
+ * Revision 1.124.1.83 2016/01/13 15:09:17 martin
+ * Support XMR_STATS.
+ * Revision 1.124.1.82 2015/12/14 13:03:09 lars
+ * Fixes / changes in IRIG TX / RX masks.
+ * Revision 1.124.1.81 2015/12/14 11:09:01Z lars
+ * *** preliminary ***
+ * Revision 1.124.1.80 2015/12/09 17:34:56Z martin
+ * *** empty log message ***
+ * Revision 1.124.1.79 2015/12/09 10:21:18 martin
+ * *** empty log message ***
+ * Revision 1.124.1.78 2015/12/09 08:28:36 martin
+ * New legacy model codes.
+ * Changed/Added some IRIG enums.
+ * Revision 1.124.1.77 2015/12/07 14:43:04 martin
+ * Doxygen fixes.
+ * Revision 1.124.1.76 2015/12/04 14:20:18 paul
+ * Fixed a typo in comment of video string initialzier.
+ * Added support for configurable epochs for video outputs.
+ * Revision 1.124.1.75 2015/12/02 16:51:19Z martin
+ * *** empty log message ***
+ * Revision 1.124.1.74 2015/12/02 16:35:32 martin
+ * *** empty log message ***
+ * Revision 1.124.1.73 2015/12/01 11:34:33 martin
+ * *** empty log message ***
+ * Revision 1.124.1.72 2015/11/30 16:51:12 martin
+ * *** empty log message ***
+ * Revision 1.124.1.71 2015/11/30 16:22:30 martin
+ * *** empty log message ***
+ * Revision 1.124.1.70 2015/11/30 09:02:47 philipp
+ * Added TLV feature MBG_TLV_CTX_FLAG_FW_ROLLBACK.
+ * Revision 1.124.1.69 2015/11/30 08:16:57 philipp
+ * Added MBG_TLV_INFO feature macros.
+ * Revision 1.124.1.68 2015/11/26 17:01:08 martin
+ * *** empty log message ***
+ * Revision 1.124.1.67 2015/11/26 08:32:54 martin
+ * *** empty log message ***
+ * Revision 1.124.1.66 2015/11/25 16:55:08 martin
+ * Started to implement extended features.
+ * Revision 1.124.1.65 2015/11/24 13:10:54 philipp
+ * TLV additions / partly redesign and feature inline functions.
+ * Revision 1.124.1.64 2015/11/23 10:23:47 philipp
+ * Added Doxygen documentation for TLV structures, flags and masks.
+ * Revision 1.124.1.63 2015/11/23 10:11:28 martin
+ * *** empty log message ***
+ * Revision 1.124.1.62 2015/11/23 08:27:32 gregoire
+ * Added initializers for MBG_IMS_FDM_LINE_FREQS.
+ * Revision 1.124.1.61 2015/11/20 09:16:39Z philipp
+ * Fixed macro _mbg_swab_tlv_announce.
+ * Revision 1.124.1.60 2015/11/20 08:14:29 philipp
+ * Added id member to struct MBG_TLV_ANNOUNCE.
+ * Revision 1.124.1.59 2015/11/20 07:26:29 philipp
+ * Moved TLV structures here.
+ * Revision 1.124.1.58 2015/11/18 13:51:50 philipp
+ * Added leapfile to NTP miscellaneous structures.
+ * Revision 1.124.1.57 2015/11/18 13:39:22 philipp
+ * Added NTP miscellaneous structures.
+ * Revision 1.124.1.56 2015/11/06 12:42:08 philipp
+ * Added NTP statistics structures.
+ * Revision 1.124.1.55 2015/11/06 11:25:22 philipp
+ * Removed member symlink in NTP_REFCLK_CFG_SPEC since it is implementation defined.
+ * Revision 1.124.1.54 2015/11/06 11:16:35 philipp
+ * Added NTP symmetric key structures.
+ * Revision 1.124.1.53 2015/11/06 09:17:40 philipp
+ * Added byte swap macros to NTP restriction and NTP refclock configuration structures.
+ * Revision 1.124.1.52 2015/11/05 12:20:12 martin
+ * New define MBG_MAX_HOSTNAME_LEN.
+ * Preliminary fix for TZDL initializers.
+ * Updated some comments.
+ * Revision 1.124.1.51 2015/11/05 09:07:56 philipp
+ * Added structures for NTP restriction and refclock configuration (preliminary code).
+ * Revision 1.124.1.50 2015/10/28 12:09:26 martin
+ * GPIO types for SCG not preliminary anymore.
+ * Added definitions for LUE180.
+ * Revision 1.124.1.49 2015/10/26 11:55:19 daniel
+ * Merged aligned PTP SMPTE and TELECOM PHASE profile structures from previous branch here.
+ * Revision 1.124.1.48 2015/10/26 11:24:04 daniel
+ * Support for PTP Preset 802.1AS
+ * Revision 1.124.1.47 2015/10/26 10:56:42 paul
+ * added a new flag for GPIO studio clock out
+ * Revision 1.124.1.46 2015/10/26 09:47:53Z paul
+ * added a missing GPIO studio clock scale string initializer
+ * Revision 1.124.1.45 2015/10/23 11:00:27Z paul
+ * Revision 1.124.1.44 2015/10/22 14:35:51Z paul
+ * fixed a typo
+ * Revision 1.124.1.43 2015/10/22 14:17:34Z martin
+ * *** empty log message ***
+ * Revision 1.124.1.42 2015/10/22 14:15:02 paul
+ * some changes in GPIO structs
+ * Revision 1.124.1.41 2015/10/21 14:36:32Z paul
+ * renamed stud_clk_out in studio_clk_out and vid_sync_out in video_sync_out
+ * Revision 1.124.1.40 2015/10/20 13:38:57Z paul
+ * renamed HD format in GPIO video type
+ * Revision 1.124.1.39 2015/10/20 12:11:36Z paul
+ * Revision 1.124.1.38 2015/10/20 10:58:01Z martin
+ * *** empty log message ***
+ * Revision 1.124.1.37 2015/10/20 10:43:39 paul
+ * Revision 1.124.1.36 2015/10/20 10:15:57Z paul
+ * added preliminary studio clock structs and defines
+ * Revision 1.124.1.35 2015/10/19 10:48:00Z gregoire
+ * Revision 1.124.1.34 2015/10/19 10:08:47Z gregoire
+ * Revision 1.124.1.33 2015/10/16 11:03:06Z martin
+ * *** empty log message ***
+ * Revision 1.124.1.32 2015/10/15 14:17:22 martin
+ * *** empty log message ***
+ * Revision 1.124.1.31 2015/10/15 08:40:37 paul
+ * added two new HD video formats
+ * Revision 1.124.1.30 2015/10/15 07:38:14Z gregoire
+ * AES67 Media Profile added
+ * Revision 1.124.1.29 2015/10/13 08:44:08Z gregoire
+ * smpte_jam_event added to PTP_DEV_CFG_GLB
+ * Revision 1.124.1.28 2015/10/12 10:01:59Z martin
+ * *** empty log message ***
+ * Revision 1.124.1.27 2015/10/09 11:09:13 martin
+ * *** empty log message ***
+ * Revision 1.124.1.26 2015/10/09 09:03:50 gregoire
+ * Revision 1.124.1.25 2015/10/09 07:18:49Z gregoire
+ * Builtin feature BUILTIN_FEAT_GNSS set for GRC models.
+ * Revision 1.124.1.24 2015/10/08 13:27:37Z martin
+ * *** empty log message ***
+ * Revision 1.124.1.23 2015/10/06 10:33:39 paul
+ * Changed GPIO names.
+ * Added two defines for GPIO_TYPE_VIDEO_SYNC.
+ * Revision 1.124.1.22 2015/10/06 07:55:11Z paul
+ * Changed names of GPIO types and structs.
+ * Revision 1.124.1.21 2015/10/02 13:07:11Z martin
+ * Doxygen fixes.
+ * Revision 1.124.1.20 2015/10/02 10:33:00 martin
+ * *** empty log message ***
+ * Revision 1.124.1.19 2015/10/01 10:51:32 martin
+ * *** empty log message ***
+ * Revision 1.124.1.18 2015/09/30 08:03:45 paul
+ * Bug fix in some GPIO structs.
+ * Added comments.
+ * Revision 1.124.1.17 2015/09/29 09:55:22Z paul
+ * added video output and sync output as two new GPIO types
+ * Revision 1.124.1.16 2015/09/28 09:34:56Z thomas-b
+ * Renamed td_max_limit in MBG_IMS_FDM_LIMITS to td_pos_limit
+ * Revision 1.124.1.15 2015/09/18 13:58:44 martin
+ * *** empty log message ***
+ * Revision 1.124.1.14 2015/09/17 14:56:57 thomas-b
+ * Renamed several variables in MBG_FDM_SETTINGS and MBG_FDM_LIMITS
+ * Revision 1.124.1.13 2015/09/15 13:15:01 martin
+ * Moved definitions for NANO_TIME and NANO_TIME_64 to words.h.
+ * Revision 1.124.1.12 2015/09/15 11:08:22 martin
+ * Support new model TCR180.
+ * Added missing comma in DEFAULT_GPS_MODEL_NAMES.
+ * Revision 1.124.1.11 2015/09/07 09:19:21 martin
+ * Revision 1.124.1.10 2015/09/04 09:19:17 daniel
+ * Moved 2 additional TSU strcutures to PREMINARY_CODE block
+ * Revision 1.124.1.9 2015/09/03 09:17:41 martin
+ * Doxygen fixes.
+ * Revision 1.124.1.8 2015/09/02 16:42:17 martin
+ * Preliminary code which is only included if a preprocessor symbol
+ * _PRELIMINARY_CODE is defined in the project Makefile.
+ * Revision 1.124.1.7 2015/08/25 10:30:13 daniel
+ * Revision 1.124.1.6 2015/08/25 10:02:37 daniel
+ * Revision 1.124.1.5 2015/08/25 09:16:39 daniel
+ * Changed reserved member in PTP_STATE to include tsu_secs
+ * Revision 1.124.1.4 2015/08/10 07:37:09 daniel
+ * Added sync_e byte swab macros
+ * Revision 1.124.1.3 2015/08/07 10:51:10 daniel
+ * Fixed typo in CTC100 declaration
+ * Revision 1.124.1.2 2015/08/07 10:49:40 daniel
+ * RE-added temp. PTP structures PTP_DEV_CFG_GLB and PTP_DEV_CFG_NET
+ * Added new model CTC100
+ * Revision 1.124.1.1 2015/07/29 07:40:55 daniel
+ * Revision 1.124 2015/07/14 14:22:46 martin
+ * Doxygen fix.
+ * Revision 1.123 2015/07/06 13:00:10 martin
+ * Added definitions for VSG180, MSF180, WWVB180, and CPC180.
+ * Added definitions for PZF180.
+ * Definitions for SDI and MDU300 added by stephan.
+ * Definitions for HPS100 added by daniel.
+ * FDM180 and associated definitions added by paul.
+ * Started to support eXtended Binary Protocol (XBP).
+ * Merged daniel and gregoire's changes from the 1.120.2.x branch.
+ * Defines for IPv6 multicast scopes added by gregoire.
+ * XMR_EXT_SRC_INFO and associated XMR_SETTINGS_FLAG_MSKS flags
+ * defined by andre.
+ * Support XMULTI_REF_INFO::n_prio field again.
+ * Fixed _mbg_swab_gpio_cfg_limits() macro.
+ * Added MBG_NET_LINK_OPT_MASK_CAN_SYNCE to MBG_NET_LINK_OPT_MASKS.
+ * New PTP_ROLE_MASKS PTP_ROLE_NTP_SERVER and PTP_ROLE_NTP_CLIENT.
+ * Some PTP profile extensions added by daniel.
+ * Added missing defines for SPT.
+ * Added definitions for REL1000.
+ * Moved structure NANO_TIME_64 here.
+ * Revision 1.122 2014/07/29 08:57:44Z martin
+ * Updated doxygen comments.
+ * Revision 1.121 2014/07/17 09:41:50 martin
+ * Introduced XMR_HOLDOVER_STATUS, MBG_GPIO_STATUS,
+ * and associated definitions.
+ * Huge update and cleanup on doxygen comments.
+ * Revision 1.120 2014/05/27 08:34:40 martin
+ * Fixed braces in some _mbg_rcvr_is_..() macros.
+ * Definitions used with extended network cfg, VST, and SHS.
+ * Introduced XMR_HOLDOVER_STATUS.
+ * Introduced programmable output mode POUT_GPIO.
+ * Introduced oscillator type OCXO_SQ.
+ * Defined some new baud rates.
+ * Defines for IEEE C37.118.1-2011 CTQ.
+ * Support for new model SCG by paul.
+ * Support new model PPG180.
+ * New SCU control masks.
+ * New GNSS flag MBG_GNSS_FLAG_SAT_INFO_IDX_SUPP_SER.
+ * DEFAULT_MULTI_REF_NAMES_SHORT added by udo.
+ * Definitions used for NTP configuration by thomas-b and marvin.
+ * MBG_NET_ADDR structures changed to MBG_IP_ADDR, and
+ * associated symbols defined by marvin.
+ * Huge rework of comments in doxygen format.
+ * Revision 1.119 2013/12/05 10:13:13 daniel
+ * Support new PTP_CFG_FLAGS for 1-step-L2 and 1-step-P2P support
+ * Revision 1.118 2013/11/19 13:38:35 martin
+ * Added LAN_IF_TYPE_RSC.
+ * Revision 1.117 2013/11/18 14:13:39 martin
+ * Support model LNE_GB.
+ * Revision 1.116 2013/11/11 09:46:11 martin
+ * New PTP configuration flags PTP_CFG_SUPP_MCAST_SLAVE_FLAG and
+ * PTP_CFG_CAN_BE_MULTICAST_SLAVE, plus associated bit masks.
+ * New XMR_INST_FLAGS and XMR_INST_FLAG_MASKS defined by andre.
+ * Fixes for big-endian targets.
+ * Updated doxygen comments.
+ * Revision 1.115 2013/10/02 15:19:28 martin
+ * Changed PTP_CFG_SETTINGS::vlan_cfg back to a reserved field,
+ * and removed associated flag and flag mask.
+ * Revision 1.114 2013/09/25 11:02:10 martin
+ * Support models MRI, BPE, GLN180PEX, N2X, RSC180.
+ * Added feature bit GPS_FEAT_NTP.
+ * Enhanced VLAN configuration structures.
* Started to support IPv6.
- * Revision 1.113.1.10 2013/06/26 08:17:18 martin
- * Revision 1.113.1.9 2013/06/25 10:13:59 martin
- * Temp. workaround for DOS.
- * Revision 1.113.1.8 2013/06/21 13:59:51Z martin
- * Revision 1.113.1.7 2013/06/21 13:51:35 martin
- * Renamed and reversed meaning of management msg control flag.
- * Started to support PTP presets properly.
- * Not yet finished.
- * Revision 1.113.1.6 2013/06/18 12:24:52 martin
- * Support GLN180PEX.
- * Fixed some typos.
- * Revision 1.113.1.5 2013/06/18 11:01:50 udo
- * Revision 1.113.1.4 2013/06/18 08:57:36 daniel
- * Added new PTP roles and CFG flags for Hybrid mode, simultanous UC/MC mode,
- * 1-step and selectable management
- * Revision 1.113.1.3 2013/06/17 13:12:26 daniel
- * Added model codes and names for MRI and BPE
- * Revision 1.113.1.2 2013/04/25 14:43:10 Gregoire
- * DEFAULT_HQ_SHRT_FMT_NAMES added
- * Revision 1.113.1.1 2013/04/11 14:21:05Z Gregoire
- * string initializers for supported havequick formats added
+ * Renamed PTP_CFG_SETTINGS field "profile" to "selected_presets".
+ * Renamed PTP_CFG_INFO field "supp_profiles" to "supp_opt_ext".
+ * New PTP role PTP_ROLE_BOTH_MASTER.
+ * New PTP flag PTP_FLAG_ONE_STEP.
+ * Added some new PTP_CFG_FLAGS flags.
+ * Added PTP_OPT_EXTS and associated definitions.
+ * Added PTP_PRESETS and associated definitions.
+ * Added "tzdl" field to PTP_POWER_PROFILE_CFG.
+ * Made reserved PTP_CFG_SETTINGS field to "opt_ext" field.
+ * Made reserved PTP_CFG_SETTINGS field to "vlan_cfg" field.
+ * Made reserved PTP_STATE field to "parent_clock_class" and "parent_clock_accuracy".
+ * Definitions for MULTI_REF_EXT_OSC added by Andre.
+ * String initializers for supported HaveQuick formats added by Gregoire.
+ * Lots of doxygen changes.
* Revision 1.113 2013/04/04 09:02:01Z martin
* Added definitions to support HaveQuick.
* Fixed a typo.
@@ -163,7 +866,7 @@
* Added support for new model GLN170.
* Revision 1.87 2010/03/10 11:29:37Z martin
* Added definitions for GPS180.
- * Added multiref source 1 PPS plus associated string.
+ * Added multi ref source 1 PPS plus associated string.
* Revision 1.86 2010/02/17 14:16:42 martin
* Added definitions for PZF600 and TCR600.
* Revision 1.85 2010/02/15 11:34:36 martin
@@ -233,7 +936,7 @@
* Added definitions for PTP270PEX and FRC511PEX.
* Revision 1.67 2008/07/17 08:54:52Z martin
* Added macros to convert the endianess of structures.
- * Added multiref fixed frequency source.
+ * Added multi ref fixed frequency source.
* Revision 1.66 2008/05/19 14:49:07 daniel
* Renamed s_addr to start_addr in FPGA_INFO.
* Revision 1.65 2008/05/19 09:00:01Z martin
@@ -255,7 +958,7 @@
* Added definitions to support GPS170PEX.
* Revision 1.60 2007/09/13 12:37:35Z martin
* Modified and added initializers for TZDL.
- * Added multiref source PTP over E1.
+ * Added multi ref source PTP over E1.
* Added codes for MSF511 and GRC170 devices.
* Modified XMULTI_REF_SETTINGS and XMULTI_REF_STATUS structures.
* Avoid inclusion of other Meinberg headers in non-Meinberg projects.
@@ -453,6 +1156,7 @@
#endif
+
/* Start of header body */
#if defined( _USE_PACK )
@@ -461,12 +1165,36 @@
#endif
+
/* "magic" number */
#define MEINBERG_MAGIC 0x6AAC
-#define MIN_SVNO 1 /* min. SV number */
-#define MAX_SVNO 32 /* max. SV number */
-#define N_SVNO ( MAX_SVNO - MIN_SVNO + 1) /* number of possibly active SVs */
+/**
+ * @brief GNSS satellite numbers
+ *
+ * @todo: Check if MAX_SVNO_GLN is 94 instead of 95, and thus
+ * N_SVNO_GLN is 30 instead of 31, as reported by Wikipedia.
+ */
+enum GNSS_SVNOS
+{
+ MIN_SVNO_GPS = 1, ///< min. GPS satellite PRN number
+ MAX_SVNO_GPS = 32, ///< max. GPS satellite PRN number
+ N_SVNO_GPS = 32, ///< max. number of active GPS satellites
+
+ MIN_SVNO_WAAS = 33, ///< min. WAAS satellite number
+ MAX_SVNO_WAAS = 64, ///< max. WAAS satellite number
+ N_SVNO_WAAS = 32, ///< max. number of active WAAS satellites
+
+ MIN_SVNO_GLONASS = 65, ///< min. Glonass satellite number (64 + sat slot ID)
+ MAX_SVNO_GLONASS = 95, ///< max. Glonass satellite number (64 + sat slot ID)
+ N_SVNO_GLONASS = 31 ///< max. number of active Glonass satellites
+};
+
+// for compatibility with GPS-only software:
+#define MIN_SVNO MIN_SVNO_GPS ///< min. SV number
+#define MAX_SVNO MAX_SVNO_GPS ///< max. SV number
+#define N_SVNO N_SVNO_GPS ///< number of possibly active SVs
+
#define GPS_ID_STR_LEN 16
@@ -482,17 +1210,17 @@
/*
* The actual ticks per seconds may vary for different
* GPS receiver models. If this is the case, the receiver
- * model support the RECEIVER_INFO structure which contains
+ * model support the ::RECEIVER_INFO structure which contains
* the actual value.
*/
- #define GPS_TICKS_PER_SEC DEFAULT_GPS_TICKS_PER_SEC ///< @see DEFAULT_GPS_TICKS_PER_SEC
+ #define GPS_TICKS_PER_SEC DEFAULT_GPS_TICKS_PER_SEC ///< see ::DEFAULT_GPS_TICKS_PER_SEC
#endif
typedef uint16_t SVNO; ///< the number of an SV (Space Vehicle, i.e. satellite)
-typedef uint16_t HEALTH; ///< an SV's health code
-typedef uint16_t CFG; ///< an SV's configuration code
+typedef uint16_t HEALTH; ///< an SV's 6 bit health code
+typedef uint16_t CFG; ///< an SV's 4 bit configuration code
typedef uint16_t IOD; ///< Issue-Of-Data code
@@ -501,17 +1229,17 @@ typedef uint16_t IOD; ///< Issue-Of-Data code
#ifndef _CSUM_DEFINED
typedef uint16_t CSUM; ///< checksum used by some structures stored in non-volatile memory
#define _CSUM_DEFINED
-
- #define _mbg_swab_csum( _p ) _mbg_swab16( _p )
#endif
+#define _mbg_swab_csum( _p ) _mbg_swab16( _p )
+
+
/**
* @brief The type of a GPS command code
*
- * These command codes can be passed via
- * @ref group_gps_cmds_serial "serial port" (see @file gpsserio.h), or
- * @ref group_gps_cmds_bus "system bus" (see @file pcpsdefs.h).
+ * @see ::GPS_CMD_CODES
+ * @see ::PC_GPS_CMD_CODES
*/
typedef uint16_t GPS_CMD;
@@ -523,23 +1251,27 @@ typedef uint16_t GPS_CMD;
*
* Contains a software revision code, plus an optional
* identifier for a customized version.
+ *
+ * @see @ref group_ext_sys_info
*/
typedef struct
{
uint16_t code; ///< Version number, e.g. 0x0120 means v1.20
- char name[GPS_ID_STR_SIZE]; ///< Optional string identifying a customized version
+ char name[GPS_ID_STR_SIZE]; ///< Optional string identifying a customized firmware version, should be empty in standard versions
uint8_t reserved; ///< Reserved field to yield even structure size
+
} SW_REV;
#define _mbg_swab_sw_rev( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->code ); \
-}
+} while ( 0 )
/**
- * @defgroup group_bvar_stat BVAR_STAT status of buffered GPS data
+ * @defgroup group_bvar_stat Status of buffered (non-volatile) data
*
* Status word, associated bit numbers and bit masks indicating
* whether certain data from the GPS satellites are
@@ -551,11 +1283,14 @@ typedef struct
* @{ */
/**
- * @brief Status flags of battery buffered data received
- * from GPS satellites.
+ * @brief Status flags of battery buffered data
+ *
+ * Related to data received from the satellites, or data derived thereof.
*
* All '0' means OK, single bits set to '1' indicate
* the associated type of GPS data is not available.
+ *
+ * @see ::BVAR_FLAGS
*/
typedef uint16_t BVAR_STAT;
@@ -563,16 +1298,20 @@ typedef uint16_t BVAR_STAT;
/**
- * @brief Enumeration of bits used with BVAR_STAT
+ * @brief Enumeration of flag bits used to define ::BVAR_FLAGS
*
* For each bit which is set this means the associated data set in
- * non-volatile memory is not available or incomplete.
+ * non-volatile memory is not available, or incomplete.
* Most data sets will just be re-collected from the data streams sent
* by the satellites. However, the receiver position has usually been
* computed earlier during normal operation, and will be re-computed
* when a sufficient number of satellites can be received.
+ *
+ * @see ::BVAR_STAT
+ * @see ::BVAR_FLAGS
+ * @see ::BVAR_FLAG_NAMES
*/
-enum BVAR_BITS
+enum BVAR_FLAG_BITS
{
BVAR_BIT_CFGH_INVALID, ///< Satellite configuration and health parameters incomplete
BVAR_BIT_ALM_NOT_COMPLETE, ///< Almanac parameters incomplete
@@ -582,15 +1321,45 @@ enum BVAR_BITS
N_BVAR_BIT ///< number of defined ::BVAR_STAT bits
};
-#define BVAR_CFGH_INVALID ( 1UL << BVAR_BIT_CFGH_INVALID ) ///< Configuration and health data (::CFGH) not valid
-#define BVAR_ALM_NOT_COMPLETE ( 1UL << BVAR_BIT_ALM_NOT_COMPLETE ) ///< Almanach data (::ALM) not complete
-#define BVAR_UTC_INVALID ( 1UL << BVAR_BIT_UTC_INVALID ) ///< ::UTC data not valid
-#define BVAR_IONO_INVALID ( 1UL << BVAR_BIT_IONO_INVALID ) ///< Ionospheric correction data (::IONO) not valid
-#define BVAR_RCVR_POS_INVALID ( 1UL << BVAR_BIT_RCVR_POS_INVALID ) ///< Receiver position (::POS) not valid
+
+/**
+ * @brief Bit masks associated with ::BVAR_FLAG_BITS
+ *
+ * Used with ::BVAR_STAT.
+ *
+ * @see ::BVAR_STAT
+ * @see ::BVAR_FLAG_BITS
+ * @see ::BVAR_FLAG_NAMES
+ */
+enum BVAR_FLAGS
+{
+ BVAR_CFGH_INVALID = ( 1UL << BVAR_BIT_CFGH_INVALID ), ///< see ::BVAR_BIT_CFGH_INVALID
+ BVAR_ALM_NOT_COMPLETE = ( 1UL << BVAR_BIT_ALM_NOT_COMPLETE ), ///< see ::BVAR_BIT_ALM_NOT_COMPLETE
+ BVAR_UTC_INVALID = ( 1UL << BVAR_BIT_UTC_INVALID ), ///< see ::BVAR_BIT_UTC_INVALID
+ BVAR_IONO_INVALID = ( 1UL << BVAR_BIT_IONO_INVALID ), ///< see ::BVAR_BIT_IONO_INVALID
+ BVAR_RCVR_POS_INVALID = ( 1UL << BVAR_BIT_RCVR_POS_INVALID ), ///< see ::BVAR_BIT_RCVR_POS_INVALID
+};
#define BVAR_MASK ( ( 1UL << N_BVAR_BIT ) - 1 ) ///< Bit mask for all defined bits
-/** @} group_bvar_stat */
+
+/**
+ * @brief String initializer for ::BVAR_STAT flag names
+ *
+ * @see ::BVAR_STAT
+ * @see ::BVAR_FLAG_BITS
+ * @see ::BVAR_FLAGS
+ */
+#define BVAR_FLAG_NAMES \
+{ \
+ "Sat. config and health", \
+ "Almanac", \
+ "UTC offset", \
+ "Ionospheric correction", \
+ "Receiver position" \
+}
+
+/** @} defgroup group_bvar_stat */
@@ -603,19 +1372,21 @@ typedef struct
{
uint16_t khz_val; ///< the base frequency in [kHz]
int16_t range; ///< an optional base 10 exponent
+
} FIXED_FREQ_INFO;
#define _mbg_swab_fixed_freq_info( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->khz_val ); \
_mbg_swab16( &(_p)->range ); \
-}
+} while ( 0 )
/**
* @brief A data type to specify feature flags within ::RECEIVER_INFO
*/
-typedef uint32_t RI_FEATURES; ///< @see GPS_FEATURE_MASKS
+typedef uint32_t RI_FEATURES; ///< see @ref GPS_FEATURE_MASKS
@@ -630,21 +1401,23 @@ typedef struct
SW_REV sw_rev; ///< software revision and ID
char model_name[GPS_ID_STR_SIZE]; ///< ASCIIZ, name of receiver model
char sernum[GPS_ID_STR_SIZE]; ///< ASCIIZ, serial number
- char epld_name[GPS_EPLD_STR_SIZE]; ///< ASCIIZ, file name of EPLD image
+ char epld_name[GPS_EPLD_STR_SIZE]; ///< ASCIIZ, file name of EPLD image (optional)
uint8_t n_channels; ///< number of satellites which can be tracked simultaneously
uint32_t ticks_per_sec; ///< resolution of fractions of seconds, see ::GPS_TICKS_PER_SEC
- RI_FEATURES features; ///< optional features, see ::GPS_FEATURE_MASKS
- FIXED_FREQ_INFO fixed_freq; ///< optional non-standard fixed frequency
+ RI_FEATURES features; ///< optional features, see @ref GPS_FEATURE_MASKS
+ FIXED_FREQ_INFO fixed_freq; ///< optional non-standard fixed frequency, may be 0 if not supported
uint8_t osc_type; ///< type of installed oscillator, see ::GPS_OSC_TYPES
uint8_t osc_flags; ///< oscillator flags, actually not used and always 0
uint8_t n_ucaps; ///< number of user time capture inputs
uint8_t n_com_ports; ///< number of on-board serial ports
uint8_t n_str_type; ///< max num of string types supported by any port
uint8_t n_prg_out; ///< number of programmable pulse outputs
- uint16_t flags; ///< additional information, see ::RECEIVER_INFO_FLAG_BITS
+ uint16_t flags; ///< additional information, see ::RECEIVER_INFO_FLAG_MASKS
+
} RECEIVER_INFO;
#define _mbg_swab_receiver_info( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->model_code ); \
_mbg_swab_sw_rev( &(_p)->sw_rev ); \
@@ -652,11 +1425,14 @@ typedef struct
_mbg_swab32( &(_p)->features ); \
_mbg_swab_fixed_freq_info( &(_p)->fixed_freq ); \
_mbg_swab16( &(_p)->flags ); \
-}
+} while ( 0 )
/**
- * @brief Known device ID codes for RECEIVER_INFO::model_code
+ * @brief Known device ID codes for ::RECEIVER_INFO::model_code
+ *
+ * @see @ref GPS_MODEL_NAMES
+ * @see ::DEFAULT_GPS_MODEL_NAMES
*/
enum GPS_MODEL_CODES
{
@@ -711,21 +1487,67 @@ enum GPS_MODEL_CODES
GPS_MODEL_MRI,
GPS_MODEL_BPE,
GPS_MODEL_GLN180PEX,
+ GPS_MODEL_N2X,
+ GPS_MODEL_RSC180,
+ GPS_MODEL_LNE_GB,
+ GPS_MODEL_PPG180,
+ GPS_MODEL_SCG,
+ GPS_MODEL_MDU300,
+ GPS_MODEL_SDI,
+ GPS_MODEL_FDM180,
+ GPS_MODEL_SPT,
+ GPS_MODEL_PZF180,
+ GPS_MODEL_REL1000,
+ GPS_MODEL_HPS100,
+ GPS_MODEL_VSG180,
+ GPS_MODEL_MSF180,
+ GPS_MODEL_WWVB180,
+ GPS_MODEL_CPC180,
+ GPS_MODEL_CTC100,
+ GPS_MODEL_TCR180,
+ GPS_MODEL_LUE180,
+ GPS_MODEL_CPC_01,
+ GPS_MODEL_TSU_01,
+ GPS_MODEL_CMC_01,
+ GPS_MODEL_SCU_01,
+ GPS_MODEL_FCU_01,
+ GPS_MODEL_CSM100,
+ GPS_MODEL_LNE180SFP,
+ GPS_MODEL_GTS180,
+ GPS_MODEL_GPS180CSM,
+ GPS_MODEL_GRC181,
+ GPS_MODEL_N2X180,
+ GPS_MODEL_GNS181PEX,
+ GPS_MODEL_MDU180,
+ GPS_MODEL_MDU312,
+ GPS_MODEL_GPS165,
+ GPS_MODEL_GNS181_UC,
+ GPS_MODEL_PSX_4GE,
+ GPS_MODEL_RSC180RDU,
+ GPS_MODEL_USYNCPWR,
+ GPS_MODEL_FDM180M,
N_GPS_MODEL
/* If new model codes are added then care must be taken
- * to update the associated string initializers below
- * accordingly, and to check whether the classification macros
- * also cover the new model names. */
+ * to update the associated string initializers GPS_MODEL_NAMES
+ * and GPS_MODEL_NAME_TABLE accordingly, and to check whether
+ * the classification macros also cover the new model names.
+ */
};
+/**
+ * @brief Model name strings used with Meinberg devices
+ *
+ * String initializers for each of the device models
+ * enumerated in ::GPS_MODEL_CODES.
+ *
+ * @see ::GPS_MODEL_CODES
+ * @see ::DEFAULT_GPS_MODEL_NAMES
+ *
+ * @anchor GPS_MODEL_NAMES @{ */
-/*
- * String initializers for each of the GPS
- * receiver models enum'ed above:
- */
-#define GPS_MODEL_NAME_UNKNOWN "(unknown)"
+#define GPS_MODEL_NAME_UNKNOWN "Unknown"
#define GPS_MODEL_NAME_GPS166 "GPS166"
#define GPS_MODEL_NAME_GPS167 "GPS167"
#define GPS_MODEL_NAME_GPS167SV "GPS167SV"
@@ -776,12 +1598,61 @@ enum GPS_MODEL_CODES
#define GPS_MODEL_NAME_MRI "MRI"
#define GPS_MODEL_NAME_BPE "BPE"
#define GPS_MODEL_NAME_GLN180PEX "GLN180PEX"
-
-/*
- * The definition below can be used to initialize
- * an array of N_GPS_MODEL type name strings.
- * Including the trailing 0, each name must not
- * exceed GPS_ID_STR_SIZE chars.
+#define GPS_MODEL_NAME_N2X "N2X"
+#define GPS_MODEL_NAME_RSC180 "RSC180"
+#define GPS_MODEL_NAME_LNE_GB "LNE_GB"
+#define GPS_MODEL_NAME_PPG180 "PPG180"
+#define GPS_MODEL_NAME_SCG "SCG"
+#define GPS_MODEL_NAME_MDU300 "MDU300"
+#define GPS_MODEL_NAME_SDI "SDI"
+#define GPS_MODEL_NAME_FDM180 "FDM180"
+#define GPS_MODEL_NAME_SPT "SPT"
+#define GPS_MODEL_NAME_PZF180 "PZF180"
+#define GPS_MODEL_NAME_REL1000 "REL1000"
+#define GPS_MODEL_NAME_HPS100 "HPS100"
+#define GPS_MODEL_NAME_VSG180 "VSG180"
+#define GPS_MODEL_NAME_MSF180 "MSF180"
+#define GPS_MODEL_NAME_WWVB180 "WWVB180"
+#define GPS_MODEL_NAME_CPC180 "CPC180"
+#define GPS_MODEL_NAME_CTC100 "CTC100"
+#define GPS_MODEL_NAME_TCR180 "TCR180"
+#define GPS_MODEL_NAME_LUE180 "LUE180"
+#define GPS_MODEL_NAME_CPC_01 "CPC_01"
+#define GPS_MODEL_NAME_TSU_01 "TSU_01"
+#define GPS_MODEL_NAME_CMC_01 "CMC_01"
+#define GPS_MODEL_NAME_SCU_01 "SCU_01"
+#define GPS_MODEL_NAME_FCU_01 "FCU_01"
+#define GPS_MODEL_NAME_CSM100 "CSM100"
+#define GPS_MODEL_NAME_LNE180SFP "LNE180SFP"
+#define GPS_MODEL_NAME_GTS180 "GTS180"
+#define GPS_MODEL_NAME_GPS180CSM "GPS180CSM"
+#define GPS_MODEL_NAME_GRC181 "GRC181"
+#define GPS_MODEL_NAME_N2X180 "N2X180"
+#define GPS_MODEL_NAME_GNS181PEX "GNS181PEX"
+#define GPS_MODEL_NAME_MDU180 "MDU180"
+#define GPS_MODEL_NAME_MDU312 "MDU312"
+#define GPS_MODEL_NAME_GPS165 "GPS165"
+#define GPS_MODEL_NAME_GNS181_UC "GNS181_UC"
+#define GPS_MODEL_NAME_PSX_4GE "PSX_4GE"
+#define GPS_MODEL_NAME_RSC180RDU "RSC180RDU"
+#define GPS_MODEL_NAME_USYNCPWR "MICROSYNC-PWR"
+#define GPS_MODEL_NAME_FDM180M "FDM180M"
+
+/** @} anchor GPS_MODEL_NAMES */
+
+
+
+/**
+ * @brief An initializer for a table of device names
+ *
+ * Can be used to initialize an array of ::N_GPS_MODEL
+ * type name strings.
+ *
+ * @note Including the trailing 0, each name must not
+ * exceed ::GPS_ID_STR_SIZE chars.
+ *
+ * @see ::GPS_MODEL_CODES
+ * @see @ref GPS_MODEL_NAMES
*/
#define DEFAULT_GPS_MODEL_NAMES \
{ \
@@ -835,10 +1706,739 @@ enum GPS_MODEL_CODES
GPS_MODEL_NAME_DCF600RS, \
GPS_MODEL_NAME_MRI, \
GPS_MODEL_NAME_BPE, \
- GPS_MODEL_NAME_GLN180PEX \
+ GPS_MODEL_NAME_GLN180PEX, \
+ GPS_MODEL_NAME_N2X, \
+ GPS_MODEL_NAME_RSC180, \
+ GPS_MODEL_NAME_LNE_GB, \
+ GPS_MODEL_NAME_PPG180, \
+ GPS_MODEL_NAME_SCG, \
+ GPS_MODEL_NAME_MDU300, \
+ GPS_MODEL_NAME_SDI, \
+ GPS_MODEL_NAME_FDM180, \
+ GPS_MODEL_NAME_SPT, \
+ GPS_MODEL_NAME_PZF180, \
+ GPS_MODEL_NAME_REL1000, \
+ GPS_MODEL_NAME_HPS100, \
+ GPS_MODEL_NAME_VSG180, \
+ GPS_MODEL_NAME_MSF180, \
+ GPS_MODEL_NAME_WWVB180, \
+ GPS_MODEL_NAME_CPC180, \
+ GPS_MODEL_NAME_CTC100, \
+ GPS_MODEL_NAME_TCR180, \
+ GPS_MODEL_NAME_LUE180, \
+ GPS_MODEL_NAME_CPC_01, \
+ GPS_MODEL_NAME_TSU_01, \
+ GPS_MODEL_NAME_CMC_01, \
+ GPS_MODEL_NAME_SCU_01, \
+ GPS_MODEL_NAME_FCU_01, \
+ GPS_MODEL_NAME_CSM100, \
+ GPS_MODEL_NAME_LNE180SFP, \
+ GPS_MODEL_NAME_GTS180, \
+ GPS_MODEL_NAME_GPS180CSM, \
+ GPS_MODEL_NAME_GRC181, \
+ GPS_MODEL_NAME_N2X180, \
+ GPS_MODEL_NAME_GNS181PEX, \
+ GPS_MODEL_NAME_MDU180, \
+ GPS_MODEL_NAME_MDU312, \
+ GPS_MODEL_NAME_GPS165, \
+ GPS_MODEL_NAME_GNS181_UC, \
+ GPS_MODEL_NAME_PSX_4GE, \
+ GPS_MODEL_NAME_RSC180RDU, \
+ GPS_MODEL_NAME_USYNCPWR, \
+ GPS_MODEL_NAME_FDM180M \
}
+
+/**
+ * @brief Definitions used to classify devices and built-in features
+ *
+ * @see ::GPS_MODEL_CODES
+ * @see ::GPS_BUILTIN_FEATURE_BITS
+ * @see @ref GPS_BUILTIN_FEATURE_MASKS
+ *
+ * @anchor GPS_BUILTIN_FEATURE_DEFS @{ */
+
+
+/**
+ * @brief Enumeration of classifiers and built-in features
+ *
+ * @see ::GPS_MODEL_CODES
+ * @see @ref GPS_BUILTIN_FEATURE_MASKS
+ */
+enum GPS_BUILTIN_FEATURE_BITS
+{
+ GPS_BIT_MODEL_IS_GPS,
+ GPS_BIT_MODEL_IS_GNSS,
+ GPS_BIT_MODEL_IS_TCR,
+ GPS_BIT_MODEL_IS_DCF_AM,
+ GPS_BIT_MODEL_IS_DCF_PZF,
+ GPS_BIT_MODEL_IS_MSF,
+ GPS_BIT_MODEL_IS_JJY,
+ GPS_BIT_MODEL_IS_WWVB,
+
+ GPS_BIT_MODEL_IS_BUS_LVL_DEV,
+ GPS_BIT_MODEL_HAS_BVAR_STAT,
+ GPS_BIT_MODEL_HAS_POS_XYZ,
+ GPS_BIT_MODEL_HAS_POS_LLA,
+ GPS_BIT_MODEL_HAS_TIME_TTM,
+ GPS_BIT_MODEL_HAS_TZDL,
+ GPS_BIT_MODEL_HAS_TZCODE,
+ GPS_BIT_MODEL_HAS_ANT_INFO,
+
+ GPS_BIT_MODEL_HAS_ENABLE_FLAGS,
+ GPS_BIT_MODEL_HAS_STAT_INFO,
+ GPS_BIT_MODEL_HAS_ANT_CABLE_LEN,
+ GPS_BIT_MODEL_HAS_SCU_STAT,
+ GPS_BIT_MODEL_HAS_SV_INFO,
+
+ GPS_BIT_MODEL_HAS_XMR_HOLDOVER_INTV,
+
+#if 0 //### TODO This has to be discussed
+ GPS_BIT_MODEL_IS_LNO,
+ GPS_BIT_MODEL_IS_SCU,
+#endif
+
+ N_GPS_BUILTIN_FEATURE_BITS
+};
+
+
+
+/**
+ * @brief Bit masks associated with classifiers and built-in features
+ *
+ * @see ::GPS_MODEL_CODES
+ * @see ::GPS_BUILTIN_FEATURE_BITS
+ *
+ * @anchor GPS_BUILTIN_FEATURE_MASKS @{ */
+
+#define GPS_MODEL_IS_GPS ( 1UL << GPS_BIT_MODEL_IS_GPS ) ///< see ::GPS_BIT_MODEL_IS_GPS
+#define GPS_MODEL_IS_GNSS ( 1UL << GPS_BIT_MODEL_IS_GNSS ) ///< see ::GPS_BIT_MODEL_IS_GNSS
+#define GPS_MODEL_IS_TCR ( 1UL << GPS_BIT_MODEL_IS_TCR ) ///< see ::GPS_BIT_MODEL_IS_TCR
+#define GPS_MODEL_IS_DCF_AM ( 1UL << GPS_BIT_MODEL_IS_DCF_AM ) ///< see ::GPS_BIT_MODEL_IS_DCF_AM
+#define GPS_MODEL_IS_DCF_PZF ( 1UL << GPS_BIT_MODEL_IS_DCF_PZF ) ///< see ::GPS_BIT_MODEL_IS_DCF_PZF
+#define GPS_MODEL_IS_MSF ( 1UL << GPS_BIT_MODEL_IS_MSF ) ///< see ::GPS_BIT_MODEL_IS_MSF
+#define GPS_MODEL_IS_JJY ( 1UL << GPS_BIT_MODEL_IS_JJY ) ///< see ::GPS_BIT_MODEL_IS_JJY
+#define GPS_MODEL_IS_WWVB ( 1UL << GPS_BIT_MODEL_IS_WWVB ) ///< see ::GPS_BIT_MODEL_IS_WWVB
+
+#define GPS_MODEL_IS_BUS_LVL_DEV ( 1UL << GPS_BIT_MODEL_IS_BUS_LVL_DEV ) ///< see ::GPS_BIT_MODEL_IS_BUS_LVL_DEV
+#define GPS_MODEL_HAS_BVAR_STAT ( 1UL << GPS_BIT_MODEL_HAS_BVAR_STAT ) ///< see ::GPS_BIT_MODEL_HAS_BVAR_STAT
+#define GPS_MODEL_HAS_POS_XYZ ( 1UL << GPS_BIT_MODEL_HAS_POS_XYZ ) ///< see ::GPS_BIT_MODEL_HAS_POS_XYZ
+#define GPS_MODEL_HAS_POS_LLA ( 1UL << GPS_BIT_MODEL_HAS_POS_LLA ) ///< see ::GPS_BIT_MODEL_HAS_POS_LLA
+#define GPS_MODEL_HAS_TIME_TTM ( 1UL << GPS_BIT_MODEL_HAS_TIME_TTM ) ///< see ::GPS_BIT_MODEL_HAS_TIME_TTM
+#define GPS_MODEL_HAS_TZDL ( 1UL << GPS_BIT_MODEL_HAS_TZDL ) ///< see ::GPS_BIT_MODEL_HAS_TZDL
+#define GPS_MODEL_HAS_TZCODE ( 1UL << GPS_BIT_MODEL_HAS_TZCODE ) ///< see ::GPS_BIT_MODEL_HAS_TZCODE
+#define GPS_MODEL_HAS_ANT_INFO ( 1UL << GPS_BIT_MODEL_HAS_ANT_INFO ) ///< see ::GPS_BIT_MODEL_HAS_ANT_INFO
+
+#define GPS_MODEL_HAS_ENABLE_FLAGS ( 1UL << GPS_BIT_MODEL_HAS_ENABLE_FLAGS ) ///< see ::GPS_BIT_MODEL_HAS_ENABLE_FLAGS
+#define GPS_MODEL_HAS_STAT_INFO ( 1UL << GPS_BIT_MODEL_HAS_STAT_INFO ) ///< see ::GPS_BIT_MODEL_HAS_STAT_INFO
+#define GPS_MODEL_HAS_ANT_CABLE_LEN ( 1UL << GPS_BIT_MODEL_HAS_ANT_CABLE_LEN ) ///< see ::GPS_BIT_MODEL_HAS_ANT_CABLE_LEN
+#define GPS_MODEL_HAS_SCU_STAT ( 1UL << GPS_BIT_MODEL_HAS_SCU_STAT ) ///< see ::GPS_BIT_MODEL_HAS_SCU_STAT
+#define GPS_MODEL_HAS_SV_INFO ( 1UL << GPS_BIT_MODEL_HAS_SV_INFO ) ///< see ::GPS_BIT_MODEL_HAS_SV_INFO
+
+#if 0 // ### TODO This has to be discussed
+ #define GPS_MODEL_IS_LNO ( 1UL << GPS_BIT_MODEL_IS_LNO ) ///< see ::GPS_BIT_MODEL_IS_LNO
+ #define GPS_MODEL_IS_SCU ( 1UL << GPS_BIT_MODEL_IS_SCU ) ///< see ::GPS_BIT_MODEL_IS_SCU
+#endif
+
+// ### TODO do we need the next one?
+#define GPS_MODEL_HAS_XMR_HOLDOVER_INTV ( 1UL << GPS_BIT_MODEL_HAS_XMR_HOLDOVER_INTV ) ///< see ::GPS_BIT_MODEL_HAS_XMR_HOLDOVER_INTV
+
+//### TODO: should we use an extra flag?
+#define GPS_MODEL_HAS_POS ( GPS_MODEL_HAS_POS_XYZ | GPS_MODEL_HAS_POS_LLA )
+
+/** @} anchor GPS_BUILTIN_FEATURE_MASKS */
+
+
+#if 0 //##++ more potential builtin features and classifiers
+
+ GPS_MODEL_HAS_CFGH | \
+ GPS_MODEL_HAS_ALM | \
+ GPS_MODEL_HAS_EPH | \
+ GPS_MODEL_HAS_UTC | \
+ GPS_MODEL_HAS_IONO \
+
+#define GPS_MODEL_HAS_AUTO_ON // --
+#define GPS_MODEL_HAS_AUTO_OFF // --
+#define GPS_MODEL_HAS_SW_REV // deprecated, use only if ri not supported
+#define GPS_MODEL_HAS_BVAR_STAT // req
+#define GPS_MODEL_HAS_POS_XYZ // GPS_MODEL_IS_GPS, GPS_MODEL_HAS_POS, GPS_MODEL_HAS_POS_XYZ ?
+#define GPS_MODEL_HAS_POS_LLA // GPS_MODEL_IS_GPS, GPS_MODEL_HAS_POS, GPS_MODEL_HAS_POS_LLA ?
+#define GPS_MODEL_HAS_TZDL // req
+#define GPS_MODEL_HAS_PORT_PARM // deprecated, use only if ri not supported
+#define GPS_MODEL_HAS_SYNTH // ri GPS_HAS_SYNTH
+#define GPS_MODEL_HAS_ANT_INFO // GPS_MODEL_IS_GPS, also GNSS, or req?
+#define GPS_MODEL_HAS_UCAP // ri n_ucap
+#define GPS_MODEL_HAS_ENABLE_FLAGS // req
+#define GPS_MODEL_HAS_STAT_INFO // req
+#define GPS_MODEL_HAS_SWITCH_PARMS // deprecated, use ...
+#define GPS_MODEL_HAS_STRING_PARMS // deprecated, use ...
+#define GPS_MODEL_HAS_ANT_CABLE_LEN // GPS_MODEL_IS_GPS, also GNSS, or req?
+#define GPS_MODEL_HAS_SYNC_OUTAGE_DELAY // custom
+#define GPS_MODEL_HAS_PULSE_INFO // custom
+#define GPS_MODEL_HAS_OPT_FEATURES // deprecated, use ri
+#define GPS_MODEL_HAS_IRIG_TX_SETTINGS // ri GPS_HAS_IRIG_TX
+#define GPS_MODEL_HAS_RECEIVER_INFO // --
+#define GPS_MODEL_HAS_STR_TYPE_INFO_IDX // ri n_str_type
+#define GPS_MODEL_HAS_PORT_INFO_IDX // ri n_com
+#define GPS_MODEL_HAS_PORT_SETTINGS_IDX // ri n_com
+#define GPS_MODEL_HAS_POUT_INFO_IDX // ri n_pout
+#define GPS_MODEL_HAS_POUT_SETTINGS_IDX // ri n_pout
+#define GPS_MODEL_HAS_IRIG_TX_INFO // ri GPS_HAS_IRIG_TX
+#define GPS_MODEL_HAS_MULTI_REF_SETTINGS // ri GPS_HAS_MULTI_REF
+#define GPS_MODEL_HAS_MULTI_REF_INFO // ri GPS_HAS_MULTI_REF
+#define GPS_MODEL_HAS_ROM_CSUM // ?
+#define GPS_MODEL_HAS_MULTI_REF_STATUS // ri ...
+#define GPS_MODEL_HAS_RCV_TIMEOUT // ri ...
+#define GPS_MODEL_HAS_IRIG_RX_SETTINGS // ri ...
+#define GPS_MODEL_HAS_IRIG_RX_INFO // ri ...
+#define GPS_MODEL_HAS_REF_OFFS // ri ...
+#define GPS_MODEL_HAS_DEBUG_STATUS //
+#define GPS_MODEL_HAS_XMR_SETTINGS_IDX //
+#define GPS_MODEL_HAS_XMR_INFO_IDX //
+#define GPS_MODEL_HAS_XMR_STATUS_IDX //
+#define GPS_MODEL_HAS_OPT_SETTINGS //
+#define GPS_MODEL_HAS_OPT_INFO //
+#define GPS_MODEL_HAS_CLR_UCAP_BUFF //
+#define GPS_MODEL_HAS_TIME_SCALE //
+#define GPS_MODEL_HAS_NAV_ENG_SETTINGS //
+#define GPS_MODEL_HAS_RAW_IRIG_DATA //
+#define GPS_MODEL_HAS_GPIO_CFG_LIMITS //
+#define GPS_MODEL_HAS_GPIO_INFO_IDX //
+#define GPS_MODEL_HAS_GPIO_SETTINGS_IDX //
+#define GPS_MODEL_HAS_XMR_INSTANCES //
+#define GPS_MODEL_HAS_CLR_EVT_LOG //
+#define GPS_MODEL_HAS_NUM_EVT_LOG_ENTRIES //
+#define GPS_MODEL_HAS_FIRST_EVT_LOG_ENTRY //
+#define GPS_MODEL_HAS_NEXT_EVT_LOG_ENTRY //
+#define GPS_MODEL_HAS_LNO_STATUS //
+#define GPS_MODEL_HAS_IMS_STATE //
+#define GPS_MODEL_HAS_IMS_SENSOR_STATE_IDX //
+#define GPS_MODEL_HAS_XMR_HOLDOVER_INTV //
+#define GPS_MODEL_HAS_HAVEQUICK_RX_SETTINGS //
+#define GPS_MODEL_HAS_HAVEQUICK_RX_INFO //
+#define GPS_MODEL_HAS_HAVEQUICK_TX_SETTINGS //
+#define GPS_MODEL_HAS_HAVEQUICK_TX_INFO //
+#define GPS_MODEL_HAS_PTP_CFG //
+#define GPS_MODEL_HAS_PTP_STATE //
+#define GPS_MODEL_HAS_PTP_UC_MASTER_CFG_LIMITS //
+#define GPS_MODEL_HAS_PTP_UC_MASTER_CFG //
+#define GPS_MODEL_HAS_NTP_GLB_CFG //
+#define GPS_MODEL_HAS_NTP_CLNT_MODE_CFG //
+#define GPS_MODEL_HAS_NTP_SRV_MODE_CFG //
+#define GPS_MODEL_HAS_NTP_PEER_SETTINGS_IDX //
+#define GPS_MODEL_HAS_NTP_SYS_STATE //
+#define GPS_MODEL_HAS_NTP_PEER_STATE_IDX //
+#define GPS_MODEL_HAS_SHS //
+#define GPS_MODEL_HAS_SHS_STATUS //
+#define GPS_MODEL_HAS_NET_GLB_CFG //
+#define GPS_MODEL_HAS_NET_DNS_SRVR //
+#define GPS_MODEL_HAS_NET_DNS_SRCH_DOM //
+#define GPS_MODEL_HAS_NET_STAT_DNS_SRVR //
+#define GPS_MODEL_HAS_NET_STAT_DNS_SRCH_DOM //
+#define GPS_MODEL_HAS_GNSS_SAT_INFO_IDX //
+
+#define GPS_MODEL_HAS_CFGH //
+#define GPS_MODEL_HAS_ALM //
+#define GPS_MODEL_HAS_EPH //
+#define GPS_MODEL_HAS_UTC //
+#define GPS_MODEL_HAS_IONO //
+#define GPS_MODEL_HAS_ASCII_MSG //
+
+#define GPS_MODEL_HAS_GLNS_ALM //
+#define GPS_MODEL_HAS_GNSS_SAT_INFO //
+//#define GPS_MODEL_HAS_GNSS_MODE //
+
+#define GPS_MODEL_HAS_IP4_SETTINGS //
+#define GPS_MODEL_HAS_LAN_IF_INFO //
+#define GPS_MODEL_HAS_IP4_STATE //
+
+#define GPS_MODEL_HAS_CRYPTED_PACKET //
+#define GPS_MODEL_HAS_CRYPTED_RAW_PACKET //
+
+#define GPS_MODEL_HAS_SECU_INFO //
+#define GPS_MODEL_HAS_SECU_SETTINGS //
+#define GPS_MODEL_HAS_SECU_PUBLIC_KEY //
+
+#endif //##++ more potential builtin features and classifiers
+
+
+
+/**
+ * @brief Common builtin features of all GPS receivers
+ *
+ * @see ::BUILTIN_FEAT_GPS_BUS_LVL
+ * @see ::BUILTIN_FEAT_GNSS
+ */
+#define BUILTIN_FEAT_GPS \
+( \
+ GPS_MODEL_IS_GPS | \
+ GPS_MODEL_HAS_BVAR_STAT | \
+ GPS_MODEL_HAS_POS_XYZ | \
+ GPS_MODEL_HAS_POS_LLA | \
+ GPS_MODEL_HAS_TIME_TTM | \
+ GPS_MODEL_HAS_TZDL | \
+ GPS_MODEL_HAS_ANT_INFO | \
+ GPS_MODEL_HAS_ENABLE_FLAGS | \
+ GPS_MODEL_HAS_STAT_INFO | \
+ GPS_MODEL_HAS_ANT_CABLE_LEN | \
+ GPS_MODEL_HAS_SV_INFO \
+)
+
+
+/**
+ * @brief Common builtin features of all GNSS receivers
+ *
+ * GNSS includes GPS but optionally other satellite systems,
+ * and the associated API.
+ *
+ * @see ::BUILTIN_FEAT_GNSS_BUS_LVL
+ * @see ::BUILTIN_FEAT_GPS
+ */
+#define BUILTIN_FEAT_GNSS \
+( \
+ BUILTIN_FEAT_GPS | \
+ GPS_MODEL_IS_GNSS \
+)
+
+
+
+/**
+ * @brief Common builtin features of all simple TCR devices
+ */
+#define BUILTIN_FEAT_TCR_1 \
+( \
+ GPS_MODEL_IS_TCR \
+)
+
+
+/**
+ * @brief Common builtin features of all enhanced TCR devices
+ */
+#define BUILTIN_FEAT_TCR_2 \
+( \
+ GPS_MODEL_IS_TCR | \
+ GPS_MODEL_HAS_TIME_TTM | \
+ GPS_MODEL_HAS_TZDL | \
+ GPS_MODEL_HAS_ANT_INFO | \
+ GPS_MODEL_HAS_ENABLE_FLAGS \
+)
+
+
+
+/**
+ * @brief Common builtin features of all simple DCF77 AM receivers
+ */
+#define BUILTIN_FEAT_DCF_1 \
+( \
+ GPS_MODEL_IS_DCF_AM | \
+ GPS_MODEL_HAS_TZCODE \
+)
+
+
+/**
+ * @brief Common builtin features of all enhanced DCF77 AM receivers
+ */
+#define BUILTIN_FEAT_DCF_2 \
+( \
+ GPS_MODEL_IS_DCF_AM | \
+ GPS_MODEL_HAS_TIME_TTM | \
+ GPS_MODEL_HAS_TZDL | \
+ GPS_MODEL_HAS_ANT_INFO | \
+ GPS_MODEL_HAS_ENABLE_FLAGS \
+)
+
+
+/**
+ * @brief Common builtin features of all simple DCF77 PZF receivers
+ */
+#define BUILTIN_FEAT_DCF_PZF_1 \
+( \
+ GPS_MODEL_IS_DCF_PZF | \
+ GPS_MODEL_HAS_TZCODE \
+)
+
+
+/**
+ * @brief Common builtin features of all enhanced DCF77 PZF receivers
+ */
+#define BUILTIN_FEAT_DCF_PZF_2 \
+( \
+ GPS_MODEL_IS_DCF_PZF | \
+ GPS_MODEL_HAS_TIME_TTM | \
+ GPS_MODEL_HAS_TZDL | \
+ GPS_MODEL_HAS_ANT_INFO | \
+ GPS_MODEL_HAS_ENABLE_FLAGS \
+)
+
+
+
+/**
+ * @brief Common builtin features of all simple MSF receivers
+ */
+#define BUILTIN_FEAT_MSF_1 \
+( \
+ GPS_MODEL_IS_MSF | \
+ GPS_MODEL_HAS_TZCODE \
+)
+
+
+/**
+ * @brief Common builtin features of all enhanced MSF receivers
+ */
+#define BUILTIN_FEAT_MSF_2 \
+( \
+ GPS_MODEL_IS_MSF | \
+ GPS_MODEL_HAS_TIME_TTM | \
+ GPS_MODEL_HAS_TZDL | \
+ GPS_MODEL_HAS_ANT_INFO | \
+ GPS_MODEL_HAS_ENABLE_FLAGS \
+)
+
+
+
+/**
+ * @brief Common builtin features of all simple WWVB receivers
+ */
+#define BUILTIN_FEAT_WVB_1 \
+( \
+ GPS_MODEL_IS_WWVB | \
+ GPS_MODEL_HAS_TZCODE \
+)
+
+
+/**
+ * @brief Common builtin features of all enhanced WWVB receivers
+ */
+#define BUILTIN_FEAT_WVB_2 \
+( \
+ GPS_MODEL_IS_WWVB | \
+ GPS_MODEL_HAS_TZDL \
+)
+
+
+
+/**
+ * @brief Common builtin features of all simple JJY receivers
+ */
+#define BUILTIN_FEAT_JJY_1 \
+( \
+ GPS_MODEL_IS_JJY | \
+ GPS_MODEL_HAS_TZCODE \
+)
+
+
+
+/**
+ * @brief Common builtin features of all N2X devices
+ */
+#define BUILTIN_FEAT_COMM_N2X \
+( \
+ GPS_MODEL_HAS_TIME_TTM | \
+ GPS_MODEL_HAS_TZDL | \
+ GPS_MODEL_HAS_ENABLE_FLAGS \
+)
+
+
+
+/**
+ * @brief Common builtin features of all bus-level GPS receivers
+ */
+#define BUILTIN_FEAT_GPS_BUS_LVL ( BUILTIN_FEAT_GPS | GPS_MODEL_IS_BUS_LVL_DEV )
+
+
+/**
+ * @brief Common builtin features of all bus-level GNSS receivers
+ */
+#define BUILTIN_FEAT_GNSS_BUS_LVL ( BUILTIN_FEAT_GNSS | GPS_MODEL_IS_BUS_LVL_DEV )
+
+
+/**
+ * @brief Common builtin features of all simple, bus-level TCR devices
+ */
+#define BUILTIN_FEAT_TCR_1_BUS_LVL ( BUILTIN_FEAT_TCR_1 | GPS_MODEL_IS_BUS_LVL_DEV )
+
+/**
+ * @brief Common builtin features of all enhanced, bus-level TCR devices
+ */
+#define BUILTIN_FEAT_TCR_2_BUS_LVL ( BUILTIN_FEAT_TCR_2 | GPS_MODEL_IS_BUS_LVL_DEV )
+
+
+/**
+ * @brief Common builtin features of all simple, bus-level DCF77 AM receivers
+ */
+#define BUILTIN_FEAT_DCF_1_BUS_LVL ( BUILTIN_FEAT_DCF_1 | GPS_MODEL_IS_BUS_LVL_DEV )
+
+/**
+ * @brief Common builtin features of all enhanced, bus-level DCF77 AM receivers
+ */
+#define BUILTIN_FEAT_DCF_2_BUS_LVL ( BUILTIN_FEAT_DCF_2 | GPS_MODEL_IS_BUS_LVL_DEV )
+
+/**
+ * @brief Common builtin features of all enhanced, bus-level DCF77 PZF receivers
+ */
+#define BUILTIN_FEAT_DCF_PZF_2_BUS_LVL ( BUILTIN_FEAT_DCF_PZF_2 | GPS_MODEL_IS_BUS_LVL_DEV )
+
+
+
+/**
+ * @brief Definitions of builtin features per device type
+ *
+ * @see ::GPS_MODEL_CODES
+ * @see @ref GPS_MODEL_BUILTIN_FEATURES
+ *
+ * @anchor GPS_MODEL_BUILTIN_FEATURE_MASKS @{ */
+
+#define BUILTIN_FEAT_GPS166 ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GPS167 ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GPS167SV ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GPS167PC ( BUILTIN_FEAT_GPS_BUS_LVL )
+#define BUILTIN_FEAT_GPS167PCI ( BUILTIN_FEAT_GPS_BUS_LVL )
+#define BUILTIN_FEAT_GPS163 ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GPS168PCI ( BUILTIN_FEAT_GPS_BUS_LVL )
+#define BUILTIN_FEAT_GPS161 ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GPS169PCI ( BUILTIN_FEAT_GPS_BUS_LVL )
+#define BUILTIN_FEAT_TCR167PCI ( BUILTIN_FEAT_TCR_2_BUS_LVL )
+#define BUILTIN_FEAT_GPS164 ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GPS170PCI ( BUILTIN_FEAT_GPS_BUS_LVL )
+#define BUILTIN_FEAT_PZF511 ( BUILTIN_FEAT_DCF_PZF_1 )
+#define BUILTIN_FEAT_GPS170 ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_TCR511 ( BUILTIN_FEAT_TCR_1_BUS_LVL | GPS_MODEL_HAS_TIME_TTM ) //### TODO Or full TCR_2?
+#define BUILTIN_FEAT_AM511 ( BUILTIN_FEAT_DCF_1 )
+#define BUILTIN_FEAT_MSF511 ( BUILTIN_FEAT_MSF_1 )
+#define BUILTIN_FEAT_GRC170 ( BUILTIN_FEAT_GNSS )
+#define BUILTIN_FEAT_GPS170PEX ( BUILTIN_FEAT_GPS_BUS_LVL )
+#define BUILTIN_FEAT_GPS162 ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_PTP270PEX ( GPS_MODEL_IS_BUS_LVL_DEV )
+#define BUILTIN_FEAT_FRC511PEX ( GPS_MODEL_IS_BUS_LVL_DEV )
+#define BUILTIN_FEAT_GEN170 ( 0 )
+#define BUILTIN_FEAT_TCR170PEX ( BUILTIN_FEAT_TCR_2_BUS_LVL )
+#define BUILTIN_FEAT_WWVB511 ( BUILTIN_FEAT_WVB_1 )
+#define BUILTIN_FEAT_MGR170 ( 0 )
+#define BUILTIN_FEAT_JJY511 ( BUILTIN_FEAT_JJY_1 )
+#define BUILTIN_FEAT_PZF600 ( BUILTIN_FEAT_DCF_PZF_1 ) //### TODO Or full PZF_2?
+#define BUILTIN_FEAT_TCR600 ( BUILTIN_FEAT_TCR_1 | GPS_MODEL_HAS_TIME_TTM ) //### TODO Or full TCR_2?
+#define BUILTIN_FEAT_GPS180 ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GLN170 ( BUILTIN_FEAT_GNSS)
+#define BUILTIN_FEAT_GPS180PEX ( BUILTIN_FEAT_GPS_BUS_LVL )
+#define BUILTIN_FEAT_TCR180PEX ( BUILTIN_FEAT_TCR_2_BUS_LVL )
+#define BUILTIN_FEAT_PZF180PEX ( BUILTIN_FEAT_DCF_PZF_2_BUS_LVL )
+#define BUILTIN_FEAT_MGR180 ( 0 )
+#define BUILTIN_FEAT_MSF600 ( BUILTIN_FEAT_MSF_1 ) //### TODO Or full MSF_2?
+#define BUILTIN_FEAT_WWVB600 ( BUILTIN_FEAT_WVB_1 ) //### TODO Or full WVB_2?
+#define BUILTIN_FEAT_JJY600 ( BUILTIN_FEAT_JJY_1 ) //### TODO Or full JJY_2?
+#define BUILTIN_FEAT_GPS180HS ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GPS180AMC ( BUILTIN_FEAT_GPS_BUS_LVL )
+#define BUILTIN_FEAT_ESI180 ( 0 )
+#define BUILTIN_FEAT_CPE180 ( 0 )
+#define BUILTIN_FEAT_LNO180 ( 0 )
+#define BUILTIN_FEAT_GRC180 ( BUILTIN_FEAT_GNSS )
+#define BUILTIN_FEAT_LIU ( 0 )
+#define BUILTIN_FEAT_DCF600HS ( BUILTIN_FEAT_DCF_2 ) //### TODO
+#define BUILTIN_FEAT_DCF600RS ( BUILTIN_FEAT_DCF_2 ) //### TODO
+#define BUILTIN_FEAT_MRI ( 0 )
+#define BUILTIN_FEAT_BPE ( 0 )
+#define BUILTIN_FEAT_GLN180PEX ( BUILTIN_FEAT_GNSS_BUS_LVL )
+#define BUILTIN_FEAT_N2X ( BUILTIN_FEAT_COMM_N2X )
+#define BUILTIN_FEAT_RSC180 ( GPS_MODEL_HAS_SCU_STAT )
+#define BUILTIN_FEAT_LNE_GB ( 0 )
+#define BUILTIN_FEAT_PPG180 ( 0 )
+#define BUILTIN_FEAT_SCG ( 0 )
+#define BUILTIN_FEAT_MDU300 ( 0 )
+#define BUILTIN_FEAT_SDI ( 0 )
+#define BUILTIN_FEAT_FDM180 ( GPS_MODEL_HAS_TZDL | GPS_MODEL_HAS_ENABLE_FLAGS )
+#define BUILTIN_FEAT_SPT ( 0 )
+#define BUILTIN_FEAT_PZF180 ( BUILTIN_FEAT_DCF_PZF_2 )
+#define BUILTIN_FEAT_REL1000 ( 0 )
+#define BUILTIN_FEAT_HPS100 ( 0 )
+#define BUILTIN_FEAT_VSG180 ( 0 )
+#define BUILTIN_FEAT_MSF180 ( BUILTIN_FEAT_MSF_2 )
+#define BUILTIN_FEAT_WWVB180 ( BUILTIN_FEAT_WVB_2 )
+#define BUILTIN_FEAT_CPC180 ( 0 )
+#define BUILTIN_FEAT_CTC100 ( 0 )
+#define BUILTIN_FEAT_TCR180 ( BUILTIN_FEAT_TCR_2 )
+#define BUILTIN_FEAT_LUE180 ( 0 )
+#define BUILTIN_FEAT_CPC_01 ( 0 )
+#define BUILTIN_FEAT_TSU_01 ( 0 )
+#define BUILTIN_FEAT_CMC_01 ( 0 )
+#define BUILTIN_FEAT_SCU_01 ( 0 )
+#define BUILTIN_FEAT_FCU_01 ( 0 )
+#define BUILTIN_FEAT_CSM100 ( 0 )
+#define BUILTIN_FEAT_LNE180SFP ( 0 )
+#define BUILTIN_FEAT_GTS180 ( 0 )
+#define BUILTIN_FEAT_GPS180CSM ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GRC181 ( BUILTIN_FEAT_GNSS )
+#define BUILTIN_FEAT_N2X180 ( BUILTIN_FEAT_COMM_N2X )
+#define BUILTIN_FEAT_GNS181PEX ( BUILTIN_FEAT_GNSS_BUS_LVL )
+#define BUILTIN_FEAT_MDU180 ( GPS_MODEL_HAS_SCU_STAT )
+#define BUILTIN_FEAT_MDU312 ( 0 )
+#define BUILTIN_FEAT_GPS165 ( BUILTIN_FEAT_GPS )
+#define BUILTIN_FEAT_GNS181_UC ( BUILTIN_FEAT_GNSS )
+#define BUILTIN_FEAT_PSX_4GE ( 0 )
+#define BUILTIN_FEAT_RSC180RDU ( GPS_MODEL_HAS_SCU_STAT )
+#define BUILTIN_FEAT_USYNCPWR ( 0 )
+#define BUILTIN_FEAT_FDM180M ( GPS_MODEL_HAS_TZDL | GPS_MODEL_HAS_ENABLE_FLAGS )
+
+/** @} anchor GPS_MODEL_BUILTIN_FEATURE_MASKS */
+
+
+
+/**
+ * @brief Initializer for a table of built-in features per device
+ *
+ * Last entry is all zero to indicated end of table.
+ *
+ * @see ::GPS_MODEL_CODES
+ * @see @ref GPS_MODEL_BUILTIN_FEATURE_MASKS
+ */
+#define GPS_MODEL_BUILTIN_FEATURES \
+{ \
+ { GPS_MODEL_GPS166, BUILTIN_FEAT_GPS166 }, \
+ { GPS_MODEL_GPS167, BUILTIN_FEAT_GPS167 }, \
+ { GPS_MODEL_GPS167SV, BUILTIN_FEAT_GPS167SV }, \
+ { GPS_MODEL_GPS167PC, BUILTIN_FEAT_GPS167PC }, \
+ { GPS_MODEL_GPS167PCI, BUILTIN_FEAT_GPS167PCI }, \
+ { GPS_MODEL_GPS163, BUILTIN_FEAT_GPS163 }, \
+ { GPS_MODEL_GPS168PCI, BUILTIN_FEAT_GPS168PCI }, \
+ { GPS_MODEL_GPS161, BUILTIN_FEAT_GPS161 }, \
+ { GPS_MODEL_GPS169PCI, BUILTIN_FEAT_GPS169PCI }, \
+ { GPS_MODEL_TCR167PCI, BUILTIN_FEAT_TCR167PCI }, \
+ { GPS_MODEL_GPS164, BUILTIN_FEAT_GPS164 }, \
+ { GPS_MODEL_GPS170PCI, BUILTIN_FEAT_GPS170PCI }, \
+ { GPS_MODEL_PZF511, BUILTIN_FEAT_PZF511 }, \
+ { GPS_MODEL_GPS170, BUILTIN_FEAT_GPS170 }, \
+ { GPS_MODEL_TCR511, BUILTIN_FEAT_TCR511 }, \
+ { GPS_MODEL_AM511, BUILTIN_FEAT_AM511 }, \
+ { GPS_MODEL_MSF511, BUILTIN_FEAT_MSF511 }, \
+ { GPS_MODEL_GRC170, BUILTIN_FEAT_GRC170 }, \
+ { GPS_MODEL_GPS170PEX, BUILTIN_FEAT_GPS170PEX }, \
+ { GPS_MODEL_GPS162, BUILTIN_FEAT_GPS162 }, \
+ { GPS_MODEL_PTP270PEX, BUILTIN_FEAT_PTP270PEX }, \
+ { GPS_MODEL_FRC511PEX, BUILTIN_FEAT_FRC511PEX }, \
+ { GPS_MODEL_GEN170, BUILTIN_FEAT_GEN170 }, \
+ { GPS_MODEL_TCR170PEX, BUILTIN_FEAT_TCR170PEX }, \
+ { GPS_MODEL_WWVB511, BUILTIN_FEAT_WWVB511 }, \
+ { GPS_MODEL_MGR170, BUILTIN_FEAT_MGR170 }, \
+ { GPS_MODEL_JJY511, BUILTIN_FEAT_JJY511 }, \
+ { GPS_MODEL_PZF600, BUILTIN_FEAT_PZF600 }, \
+ { GPS_MODEL_TCR600, BUILTIN_FEAT_TCR600 }, \
+ { GPS_MODEL_GPS180, BUILTIN_FEAT_GPS180 }, \
+ { GPS_MODEL_GLN170, BUILTIN_FEAT_GLN170 }, \
+ { GPS_MODEL_GPS180PEX, BUILTIN_FEAT_GPS180PEX }, \
+ { GPS_MODEL_TCR180PEX, BUILTIN_FEAT_TCR180PEX }, \
+ { GPS_MODEL_PZF180PEX, BUILTIN_FEAT_PZF180PEX }, \
+ { GPS_MODEL_MGR180, BUILTIN_FEAT_MGR180 }, \
+ { GPS_MODEL_MSF600, BUILTIN_FEAT_MSF600 }, \
+ { GPS_MODEL_WWVB600, BUILTIN_FEAT_WWVB600 }, \
+ { GPS_MODEL_JJY600, BUILTIN_FEAT_JJY600 }, \
+ { GPS_MODEL_GPS180HS, BUILTIN_FEAT_GPS180HS }, \
+ { GPS_MODEL_GPS180AMC, BUILTIN_FEAT_GPS180AMC }, \
+ { GPS_MODEL_ESI180, BUILTIN_FEAT_ESI180 }, \
+ { GPS_MODEL_CPE180, BUILTIN_FEAT_CPE180 }, \
+ { GPS_MODEL_LNO180, BUILTIN_FEAT_LNO180 }, \
+ { GPS_MODEL_GRC180, BUILTIN_FEAT_GRC180 }, \
+ { GPS_MODEL_LIU, BUILTIN_FEAT_LIU }, \
+ { GPS_MODEL_DCF600HS, BUILTIN_FEAT_DCF600HS }, \
+ { GPS_MODEL_DCF600RS, BUILTIN_FEAT_DCF600RS }, \
+ { GPS_MODEL_MRI, BUILTIN_FEAT_MRI }, \
+ { GPS_MODEL_BPE, BUILTIN_FEAT_BPE }, \
+ { GPS_MODEL_GLN180PEX, BUILTIN_FEAT_GLN180PEX }, \
+ { GPS_MODEL_N2X, BUILTIN_FEAT_N2X }, \
+ { GPS_MODEL_RSC180, BUILTIN_FEAT_RSC180 }, \
+ { GPS_MODEL_LNE_GB, BUILTIN_FEAT_LNE_GB }, \
+ { GPS_MODEL_PPG180, BUILTIN_FEAT_PPG180 }, \
+ { GPS_MODEL_SCG, BUILTIN_FEAT_SCG }, \
+ { GPS_MODEL_MDU300, BUILTIN_FEAT_MDU300 }, \
+ { GPS_MODEL_SDI, BUILTIN_FEAT_SDI }, \
+ { GPS_MODEL_FDM180, BUILTIN_FEAT_FDM180 }, \
+ { GPS_MODEL_SPT, BUILTIN_FEAT_SPT }, \
+ { GPS_MODEL_PZF180, BUILTIN_FEAT_PZF180 }, \
+ { GPS_MODEL_REL1000, BUILTIN_FEAT_REL1000 }, \
+ { GPS_MODEL_HPS100, BUILTIN_FEAT_HPS100 }, \
+ { GPS_MODEL_VSG180, BUILTIN_FEAT_VSG180 }, \
+ { GPS_MODEL_MSF180, BUILTIN_FEAT_MSF180 }, \
+ { GPS_MODEL_WWVB180, BUILTIN_FEAT_WWVB180 }, \
+ { GPS_MODEL_CPC180, BUILTIN_FEAT_CPC180 }, \
+ { GPS_MODEL_CTC100, BUILTIN_FEAT_CTC100 }, \
+ { GPS_MODEL_TCR180, BUILTIN_FEAT_TCR180 }, \
+ { GPS_MODEL_LUE180, BUILTIN_FEAT_LUE180 }, \
+ { GPS_MODEL_CPC_01, BUILTIN_FEAT_CPC_01 }, \
+ { GPS_MODEL_TSU_01, BUILTIN_FEAT_TSU_01 }, \
+ { GPS_MODEL_CMC_01, BUILTIN_FEAT_CMC_01 }, \
+ { GPS_MODEL_SCU_01, BUILTIN_FEAT_SCU_01 }, \
+ { GPS_MODEL_FCU_01, BUILTIN_FEAT_FCU_01 }, \
+ { GPS_MODEL_CSM100, BUILTIN_FEAT_CSM100 }, \
+ { GPS_MODEL_LNE180SFP, BUILTIN_FEAT_LNE180SFP }, \
+ { GPS_MODEL_GTS180, BUILTIN_FEAT_GTS180 }, \
+ { GPS_MODEL_GPS180CSM, BUILTIN_FEAT_GPS180CSM }, \
+ { GPS_MODEL_GRC181, BUILTIN_FEAT_GRC181 }, \
+ { GPS_MODEL_N2X180, BUILTIN_FEAT_N2X180 }, \
+ { GPS_MODEL_GNS181PEX, BUILTIN_FEAT_GNS181PEX }, \
+ { GPS_MODEL_MDU180, BUILTIN_FEAT_MDU180 }, \
+ { GPS_MODEL_MDU312, BUILTIN_FEAT_MDU312 }, \
+ { GPS_MODEL_GPS165, BUILTIN_FEAT_GPS165 }, \
+ { GPS_MODEL_GNS181_UC, BUILTIN_FEAT_GNS181_UC }, \
+ { GPS_MODEL_PSX_4GE, BUILTIN_FEAT_PSX_4GE }, \
+ { GPS_MODEL_RSC180RDU, BUILTIN_FEAT_RSC180RDU }, \
+ { GPS_MODEL_USYNCPWR, BUILTIN_FEAT_USYNCPWR }, \
+ { GPS_MODEL_FDM180M, BUILTIN_FEAT_FDM180M }, \
+ { 0, 0 } \
+}
+
+/** @} anchor GPS_BUILTIN_FEATURE_DEFS */
+
+
+
+/**
+ * @brief Initialize a ::RECEIVER_INFO structure for legacy DCF77 receivers
+ *
+ * Legacy DCF77 receivers may not provide a ::RECEIVER_INFO structure,
+ * but have well-known properties which can be used to set up a
+ * default ::RECEIVER_INFO.
+ *
+ * @param[in,out] _p Pointer to a ::RECEIVER_INFO STRUCTURE to be set up
+ * @param[in] _pdev Pointer to a ::PCPS_DEV structure read before
+ *
+ * @see ::_setup_default_receiver_info_gps
+ */
+#define _setup_default_receiver_info_dcf( _p, _pdev ) \
+do \
+{ \
+ memset( (_p), 0, sizeof( *(_p) ) ); \
+ \
+ (_p)->ticks_per_sec = DEFAULT_GPS_TICKS_PER_SEC; \
+ (_p)->n_ucaps = 0; \
+ (_p)->n_com_ports = _pcps_has_serial( _pdev ) ? 1 : 0; \
+ (_p)->n_str_type = ( (_p)->n_com_ports != 0 ) ? \
+ DEFAULT_N_STR_TYPE_DCF : 0; \
+} while ( 0 )
+
+
+
+/**
+ * @brief Initialize a ::RECEIVER_INFO structure for legacy GPS receivers
+ *
+ * Legacy GPS receivers may not provide a ::RECEIVER_INFO structure,
+ * but have well-known properties which can be used to set up a
+ * default ::RECEIVER_INFO.
+ *
+ * @param[in,out] _p Pointer to a ::RECEIVER_INFO STRUCTURE to be set up
+ *
+ * @see ::_setup_default_receiver_info_dcf
+ */
+#define _setup_default_receiver_info_gps( _p ) \
+do \
+{ \
+ memset( (_p), 0, sizeof( *(_p) ) ); \
+ \
+ (_p)->ticks_per_sec = DEFAULT_GPS_TICKS_PER_SEC; \
+ (_p)->n_ucaps = 2; \
+ (_p)->n_com_ports = DEFAULT_N_COM; \
+ (_p)->n_str_type = DEFAULT_N_STR_TYPE_GPS; \
+} while ( 0 )
+
+
+
/*
* The macros below can be used to classify a receiver,
* e.g. depending on the time source and/or depending on
@@ -847,11 +2447,11 @@ enum GPS_MODEL_CODES
#define _mbg_rcvr_is_plug_in( _p_ri ) \
( strstr( (_p_ri)->model_name, "PC" ) || \
- ( strstr( (_p_ri)->model_name, "PEX" ) )
+ strstr( (_p_ri)->model_name, "PEX" ) )
#define _mbg_rcvr_is_gps( _p_ri ) \
( strstr( (_p_ri)->model_name, "GPS" ) || \
- ( strstr( (_p_ri)->model_name, "MGR" ) )
+ strstr( (_p_ri)->model_name, "MGR" ) )
#define _mbg_rcvr_is_mobile_gps( _p_ri ) \
( strstr( (_p_ri)->model_name, "MGR" ) )
@@ -901,7 +2501,7 @@ enum GPS_MODEL_CODES
#define _mbg_rcvr_is_glonass( _p_ri ) \
( strstr( (_p_ri)->model_name, "GRC" ) || \
- ( strstr( (_p_ri)->model_name, "GLN" ) )
+ strstr( (_p_ri)->model_name, "GLN" ) )
#define _mbg_rcvr_is_glonass_plug_in( _p_ri ) \
( _mbg_rcvr_is_glonass( _p_ri ) && \
@@ -915,11 +2515,15 @@ enum GPS_MODEL_CODES
_mbg_rcvr_is_plug_in( _p_ri ) )
+
/**
- * @brief Oscillator classification codes used with RECEIVER_INFO::osc_type
+ * @brief Known oscillator types used with ::RECEIVER_INFO::osc_type
*
- * New codes will just be appended to the enumeration, so the sequence
- * of codes does NOT reflect the order of quality.
+ * The sequence of codes does NOT reflect the order of quality.
+ * New oscillator type codes will just be appended to the enumeration.
+ *
+ * @see ::DEFAULT_GPS_OSC_NAMES
+ * @see ::DEFAULT_GPS_OSC_QUALITY_IDX
*/
enum GPS_OSC_TYPES
{
@@ -933,14 +2537,19 @@ enum GPS_OSC_TYPES
GPS_OSC_RUBIDIUM,
GPS_OSC_TCXO_MQ,
GPS_OSC_OCXO_DHQ,
+ GPS_OSC_OCXO_SQ,
N_GPS_OSC
};
-/*
- * The sequence and number of oscillator names
- * listed below must correspond to the enumeration
- * above:
+/**
+ * @brief Oscillator type name string initializer
+ *
+ * The sequence and number of oscillator names has to
+ * correspond to the enumeration in ::GPS_OSC_TYPES
+ *
+ * @see ::GPS_OSC_TYPES
+ * @see ::DEFAULT_GPS_OSC_QUALITY_IDX
*/
#define DEFAULT_GPS_OSC_NAMES \
{ \
@@ -953,15 +2562,21 @@ enum GPS_OSC_TYPES
"OCXO XHQ", \
"RUBIDIUM", \
"TCXO MQ", \
- "OCXO DHQ" \
+ "OCXO DHQ", \
+ "OCXO SQ" \
}
-/*
- * The initializer below can be used to initialize
- * an array (e.g. "int osc_quality_idx[N_GPS_OSC]")
- * which allows to display the oscillator types
- * ordered by quality:
+/**
+ * @brief Oscillator quality index
+ *
+ * Can be used to initialize a index array
+ * (e.g. "int osc_quality_idx[N_GPS_OSC];")
+ * allowing to display the oscillator types
+ * ordered by quality
+ *
+ * @see ::GPS_OSC_TYPES
+ * @see ::DEFAULT_GPS_OSC_NAMES
*/
#define DEFAULT_GPS_OSC_QUALITY_IDX \
{ \
@@ -970,6 +2585,7 @@ enum GPS_OSC_TYPES
GPS_OSC_TCXO_MQ, \
GPS_OSC_TCXO_HQ, \
GPS_OSC_OCXO_LQ, \
+ GPS_OSC_OCXO_SQ, \
GPS_OSC_OCXO_MQ, \
GPS_OSC_OCXO_HQ, \
GPS_OSC_OCXO_DHQ, \
@@ -980,9 +2596,20 @@ enum GPS_OSC_TYPES
/**
- * @brief Enumeration of device features flags reported in RECEIVER_INFO::features
+ * @brief Enumeration of device features flags reported in ::RI_FEATURES
*
- * Each flags indicates if a device supports the associated feature.
+ * Used with ::RECEIVER_INFO::features. Each flags indicates if a device
+ * supports the associated feature, but due to the limited bit size of
+ * the ::RI_FEATURES type the number of these features is limited to 32.
+ *
+ * To extend the number of possible features the ::MBG_XFEATURE_BITS, the
+ * ::MBG_XFEATURE_BUFFER structure and associated definitions have been
+ * introduced, which are supported by devices which have ::GPS_HAS_XFEATURE
+ * set in ::RI_FEATURES.
+ *
+ * @see ::RI_FEATURES
+ * @see ::MBG_XFEATURE_BITS
+ * @see ::MBG_XFEATURE_BUFFER
*/
enum GPS_FEATURE_BITS
{
@@ -992,42 +2619,46 @@ enum GPS_FEATURE_BITS
GPS_FEAT_DCFMARKS, ///< has DCF77 compatible time mark output
GPS_FEAT_IRIG_TX, ///< has on-board IRIG output
GPS_FEAT_IRIG_RX, ///< has on-board IRIG input
- GPS_FEAT_LAN_IP4, ///< has LAN IPv4 interface
- GPS_FEAT_MULTI_REF, ///< has multiple input sources with priorities
+ GPS_FEAT_LAN_IP4, ///< has simple LAN IPv4 interface, superseded by ::GPS_FEAT_NET_CFG
+ GPS_FEAT_MULTI_REF, ///< has multiple input sources with priorities, superseded by ::GPS_FEAT_XMULTI_REF
GPS_FEAT_RCV_TIMEOUT, ///< timeout after GPS reception has stopped
- GPS_FEAT_IGNORE_LOCK, ///< supports "ignore lock", MBG_OPT_BIT_EMU_SYNC can be set alternatively
+ GPS_FEAT_IGNORE_LOCK, ///< supports "ignore lock", ::MBG_OPT_BIT_EMU_SYNC can be set alternatively
GPS_FEAT_5_MHZ, ///< output 5 MHz rather than 100 kHz
- GPS_FEAT_XMULTI_REF, ///< has extended multiple input source configuration
- GPS_FEAT_OPT_SETTINGS, ///< supports MBG_OPT_SETTINGS
+ GPS_FEAT_XMULTI_REF, ///< has extended multiple input source configuration, supersedes ::GPS_FEAT_MULTI_REF
+ GPS_FEAT_OPT_SETTINGS, ///< supports ::MBG_OPT_SETTINGS
GPS_FEAT_TIME_SCALE, ///< supports configurable time scale (%UTC, TAI, GPS, ...)
- GPS_FEAT_IRIG_CTRL_BITS, ///< supports IRIG control bits
+ GPS_FEAT_IRIG_CTRL_BITS, ///< supports IRIG control bits (::MBG_IRIG_CTRL_BITS)
GPS_FEAT_PTP, ///< has PTP support
GPS_FEAT_NAV_ENGINE_SETTINGS, ///< supports navigation engine configuration
- GPS_FEAT_RAW_IRIG_DATA, ///< supports reading raw IRIG input data
- GPS_FEAT_RAW_IRIG_TIME, ///< supports reading decoded IRIG time
+ GPS_FEAT_RAW_IRIG_DATA, ///< supports reading raw IRIG input data (::MBG_RAW_IRIG_DATA)
+ GPS_FEAT_RAW_IRIG_TIME, ///< supports reading decoded IRIG time (::PCPS_IRIG_TIME)
GPS_FEAT_PTP_UNICAST, ///< has PTP Unicast support
- GPS_FEAT_GPIO, ///< has general purpose in/outputs
- GPS_FEAT_XMRS_MULT_INSTC, ///< multiple XMRS instances of the same ref type supported, see ::XMRSF_BIT_MULT_INSTC_SUPP
+ GPS_FEAT_GPIO, ///< has general purpose inputs/outputs
+ GPS_FEAT_XMRS_MULT_INSTC, ///< multiple XMRS instances of the same ref type supported (::XMULTI_REF_INSTANCES)
GPS_FEAT_10MHZ_DISBD, ///< 10 MHz output is always disabled
GPS_FEAT_EVT_LOG, ///< Event logging supported
- GPS_FEAT_IMS, ///< Support IMS data structures
- GPS_FEAT_HAVEQUICK, ///< Support HaveQuick structures
-
- N_GPS_FEATURE ///< the number of valid features
- /*
- * If new features are added then care must be taken to update the associated
- * definitions below accordingly, e.g. string initializers and bit masks.
- */
+ GPS_FEAT_IMS, ///< supports IMS data structures
+ GPS_FEAT_HAVEQUICK, ///< supports HaveQuick structures
+ GPS_FEAT_NTP, ///< supports NTP structures
+ GPS_FEAT_NET_CFG, ///< supports extended network interface configuration, supersedes ::GPS_FEAT_LAN_IP4
+ GPS_FEAT_VST, ///< supports VST (Versatile Storage) API and structures
+ GPS_FEAT_SHS, ///< supports SHS (Secure Hybrid System) API and structures
+ GPS_FEAT_XBP, ///< supports XBP (eXtended Binary Protocol) API and structures, see @ref group_xbp
+ GPS_FEAT_XFEATURE, ///< support eXtended features, see @ref group_xfeature
+ N_GPS_FEATURE ///< the number of known ::GPS_FEATURE_BITS, should now be at its limit, i.e. 32.
+
+ // WARNING: There are no more unassigned feature bits available here.
+ // New features have to be defined using the ::MBG_XFEATURE_BITS
};
/**
* @brief Names of device features
*
- * @see GPS_FEATURE_BITS
+ * @see ::GPS_FEATURE_BITS
*/
#define DEFAULT_GPS_FEATURE_NAMES \
{ \
@@ -1056,15 +2687,23 @@ enum GPS_FEATURE_BITS
"10 MHz Output Disabled", \
"Event Logging", \
"IMS data", \
- "HaveQuick" \
+ "HaveQuick", \
+ "NTP", \
+ "Ext. Network Config", \
+ "Versatile Storage", \
+ "SHS", \
+ "Extended Binary Protocol", \
+ "Extended Features" \
}
/**
- * @brief Bit masks used with RECEIVER_INFO::features
- * @name GPS_FEATURE_MASKS
- * @see GPS_FEATURE_BITS
- */
+ * @brief Bit masks used with ::RECEIVER_INFO::features
+ *
+ * @see ::GPS_FEATURE_BITS
+ *
+ * @anchor GPS_FEATURE_MASKS @{ */
+
#define GPS_HAS_PPS ( 1UL << GPS_FEAT_PPS ) ///< see ::GPS_FEAT_PPS
#define GPS_HAS_PPM ( 1UL << GPS_FEAT_PPM ) ///< see ::GPS_FEAT_PPM
#define GPS_HAS_SYNTH ( 1UL << GPS_FEAT_SYNTH ) ///< see ::GPS_FEAT_SYNTH
@@ -1094,10 +2733,146 @@ enum GPS_FEATURE_BITS
#define GPS_HAS_IMS ( 1UL << GPS_FEAT_IMS ) ///< see ::GPS_FEAT_IMS
#define GPS_HAS_HAVEQUICK ( 1UL << GPS_FEAT_HAVEQUICK ) ///< see ::GPS_FEAT_HAVEQUICK
+#define GPS_HAS_NTP ( 1UL << GPS_FEAT_NTP ) ///< see ::GPS_FEAT_NTP
+#define GPS_HAS_NET_CFG ( 1UL << GPS_FEAT_NET_CFG ) ///< see ::GPS_FEAT_NET_CFG
+#define GPS_HAS_VST ( 1UL << GPS_FEAT_VST ) ///< see ::GPS_FEAT_VST
+#define GPS_HAS_SHS ( 1UL << GPS_FEAT_SHS ) ///< see ::GPS_FEAT_SHS
+#define GPS_HAS_XBP ( 1UL << GPS_FEAT_XBP ) ///< see ::GPS_FEAT_XBP
+#define GPS_HAS_XFEATURE ( 1UL << GPS_FEAT_XFEATURE ) ///< see ::GPS_FEAT_XFEATURE
// the next ones are special since they just shadow another flag:
-#define GPS_HAS_REF_OFFS GPS_HAS_IRIG_RX ///< always supported with IRIG inputs, see ::GPS_HAS_IRIG_RX
-#define GPS_HAS_DEBUG_INFO GPS_HAS_IRIG_RX ///< always supported with IRIG inputs, see ::GPS_HAS_IRIG_RX
+#define GPS_HAS_REF_OFFS GPS_HAS_IRIG_RX ///< always supported with IRIG inputs, see ::GPS_HAS_IRIG_RX
+#define GPS_HAS_DEBUG_STATUS GPS_HAS_IRIG_RX ///< always supported with IRIG inputs, see ::GPS_HAS_IRIG_RX
+
+/** @} anchor GPS_FEATURE_MASKS */
+
+
+/**
+ * @defgroup group_xfeature Extended feature definitions
+ *
+ * @note These structures and definitions are only supported by a device
+ * if ::GPS_HAS_XFEATURE is set in ::RECEIVER_INFO::features.
+ *
+ * @{ */
+
+
+/**
+ * @brief The maximum number of feature bits supported by the MBG_XFEATURE API.
+ *
+ * Warning: Changing this number breaks API compatibility!
+ *
+ * @see ::MBG_XFEATURE_BITS
+ */
+#define MAX_XFEATURE_BITS 1024
+
+
+
+/**
+ * @brief Enumeration of defined extended features.
+ *
+ * @see ::MBG_XFEATURE_NAMES
+ * @see ::MBG_XFEATURE_BUFFER
+ */
+enum MBG_XFEATURE_BITS
+{
+ MBG_XFEATURE_TLV_API, ///< Supports generic TLV API, see @ref group_tlv_api
+ MBG_XFEATURE_SAVE_CFG, ///< Supports the ::GPS_SAVE_CFG command
+ MBG_XFEATURE_LED_API, ///< Supports programmable LED API, see @ref group_led_api
+ MBG_XFEATURE_LNE_API, ///< Supports specific LNE API, see @ref group_lne_api
+ MBG_XFEATURE_PWR_CTL_API, ///< Supports power control, see @ref group_pwr_ctl_api
+ MBG_XFEATURE_EXT_SYS_INFO, ///< Supports extended revision information, see @ref group_ext_sys_info
+ MBG_XFEATURE_TRANSACTIONS, ///< Supports the ::GPS_BEGIN_TRANSACTION and ::GPS_END_TRANSACTION commands, see also ::MBG_TRANSACTION_TYPES
+ MBG_XFEATURE_REBOOT, ///< Supports the ::GPS_REBOOT command
+ MBG_XFEATURE_CLK_RES_INFO, ///< Supports the ::GPS_CLK_RES_INFO command, see @ref group_clk_res_info
+ MBG_XFEATURE_UCAP_NET, ///< Supports the ::GPS_UCAP_NET_GLB_INFO and ::GPS_UCAP_NET_RECV_INFO_IDX commands, see @ref group_ucap_net
+ MBG_XFEATURE_REQ_TTM, ///< Supports TTM requests via GPS_TIME command
+ MBG_XFEATURE_IO_PORTS, ///< Supports I/O port structures, see @ref group_io_ports
+ MBG_XFEATURE_MONITORING, ///< Supports monitoring / notifications, see @ref group_monitoring
+ MBG_XFEATURE_XHE, ///< Supports XHE external rubidium unit I/O commands
+ MBG_XFEATURE_USB_LOCK, ///< Supports USB interrupt structures, see @ref group_usb_lock
+ N_MBG_XFEATURE ///< Number of defined extended features
+ // NOTE If new features are appended here then an appropriate feature
+ // name string has to be appended to ::MBG_XFEATURE_NAMES, and care must
+ // be taken that ::N_MBG_XFEATURE doesn't exceed ::MAX_XFEATURE_BITS.
+};
+
+
+
+/**
+ * @brief Names of extended device features
+ *
+ * Can be used to initialize a string array of ::N_MBG_XFEATURE entries,
+ * so the number of strings must correspond to ::N_MBG_XFEATURE.
+ *
+ * @see ::MBG_XFEATURE_BITS
+ */
+#define MBG_XFEATURE_NAMES \
+{ \
+ "Generic TLV API", \
+ "Save Config On Card", \
+ "Programmable LED API", \
+ "LNE API", \
+ "Power Control API", \
+ "Extended Revision Info", \
+ "Transaction commands", \
+ "Reboot command", \
+ "Clock Resolution Info", \
+ "Extended User Captures", \
+ "Request TTM", \
+ "I/O Ports", \
+ "Monitoring", \
+ "XHE unit", \
+ "USB lock" \
+}
+
+
+
+/**
+ * @brief Array size required to store all extended features
+ *
+ * The number of bytes required to store up to ::MAX_XFEATURE_BITS
+ * feature bits in a byte array.
+ */
+#define MAX_XFEATURE_BYTES ( MAX_XFEATURE_BITS / 8 )
+
+
+
+/**
+ * @brief A structure used to store extended device features.
+ *
+ * Up to ::MAX_XFEATURE_BITS totally can be stored, but only
+ * ::N_MBG_XFEATURE extended features are currently defined.
+ * The ::_set_xfeature_bit macro should be used by the firmware
+ * to set a feature bit in the buffer, and the ::check_xfeature
+ * function should be used to implement API calls which test if an
+ * extended feature is supported.
+ *
+ * @see ::_set_xfeature_bit
+ * @see ::check_xfeature
+ */
+typedef struct
+{
+ uint8_t b[MAX_XFEATURE_BYTES];
+
+} MBG_XFEATURE_BUFFER;
+
+
+
+/**
+ * @brief Set an extended feature bit in a ::MBG_XFEATURE_BUFFER
+ *
+ * Should be used by the firmware only to set one of the ::MBG_XFEATURE_BITS
+ * in an ::MBG_XFEATURE_BUFFER after power-up.
+ *
+ * @param[in] _xf_bit One of the ::MBG_XFEATURE_BITS
+ * @param[in] _xf_buffp Pointer to an ::MBG_XFEATURE_BUFFER
+ */
+#define _set_xfeature_bit( _xf_bit, _xf_buffp ) \
+ _set_array_bit( _xf_bit, (_xf_buffp)->b, MAX_XFEATURE_BYTES )
+
+
+/** @} defgroup group_xfeature */
+
/*
@@ -1114,7 +2889,7 @@ enum GPS_FEATURE_BITS
/**
- * @brief Bits to be used with RECEIVER_INFO::flags
+ * @brief Bits used to define ::RECEIVER_INFO_FLAG_MASKS
*/
enum RECEIVER_INFO_FLAG_BITS
{
@@ -1124,14 +2899,21 @@ enum RECEIVER_INFO_FLAG_BITS
N_RECEIVER_INFO_FLAG_BITS ///< number of known bits
};
-#define GPS_OSC_CFG_SUPP ( 1UL << GPS_BIT_OSC_CFG_SUPP )
-#define GPS_IRIG_FO_IN ( 1UL << GPS_BIT_IRIG_FO_IN )
-#define GPS_HAS_FPGA ( 1UL << GPS_BIT_HAS_FPGA )
+
+/**
+ * @brief Bit masks to be used with ::RECEIVER_INFO::flags
+ */
+enum RECEIVER_INFO_FLAG_MASKS
+{
+ GPS_OSC_CFG_SUPP = ( 1UL << GPS_BIT_OSC_CFG_SUPP ), ///< see ::GPS_BIT_OSC_CFG_SUPP
+ GPS_IRIG_FO_IN = ( 1UL << GPS_BIT_IRIG_FO_IN ), ///< see ::GPS_BIT_IRIG_FO_IN
+ GPS_HAS_FPGA = ( 1UL << GPS_BIT_HAS_FPGA ) ///< see ::GPS_BIT_HAS_FPGA
+};
/*
- * If the GPS_HAS_FPGA flag is set in RECEIVER_INFO::flags then the card
+ * If the ::GPS_HAS_FPGA flag is set in ::RECEIVER_INFO::flags then the card
* provides an FPGA and the following information about the FPGA is available:
*/
#define FPGA_NAME_LEN 31 // max name length
@@ -1145,11 +2927,7 @@ typedef union
{
CSUM csum;
uint32_t fsize;
- #if _IS_MBG_FIRMWARE
- uint32_t start_addr;
- #else
- uint8_t *start_addr;
- #endif
+ uint32_t start_addr;
char name[FPGA_NAME_SIZE];
} hdr;
@@ -1167,6 +2945,7 @@ typedef struct
{
CSUM csum;
uint16_t fpga_start_seg; // Number of the 4k block where an FPGA image is located
+
} FPGA_START_INFO;
#define DEFAULT_FPGA_START_SEG 0x60
@@ -1192,23 +2971,25 @@ typedef struct
* the receiver's internal time.
*
* %UTC time differs from GPS time since a number of leap seconds have
- * been inserted in the %UTC time scale after the GPS epoche. The number
+ * been inserted in the %UTC time scale after the GPS epoch. The number
* of leap seconds is disseminated by the satellites using the ::UTC
* parameter set, which also provides info on pending leap seconds.
*/
typedef struct
{
- uint16_t wn; ///< the week number since GPS has been installed
+ uint16_t wn; ///< the week number since the GPS system has been put into operation
uint32_t sec; ///< the second of that week
- uint32_t tick; ///< fractions of a second; scale: 1/::RECEIVER_INFO::ticks_per_sec
+ uint32_t tick; ///< fractions of a second, 1/::RECEIVER_INFO::ticks_per_sec units
+
} T_GPS;
#define _mbg_swab_t_gps( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->wn ); \
_mbg_swab32( &(_p)->sec ); \
_mbg_swab32( &(_p)->tick ); \
-}
+} while ( 0 )
/**
@@ -1229,31 +3010,35 @@ typedef struct
int16_t year; ///< year number, 0..9999
int8_t month; ///< month, 1..12
int8_t mday; ///< day of month, 1..31
- int16_t yday; ///< day of year, 1..366
+ int16_t yday; ///< day of year, 1..365, or 366 in case of leap year
int8_t wday; ///< day of week, 0..6 == Sun..Sat
int8_t hour; ///< hours, 0..23
int8_t min; ///< minutes, 0..59
- int8_t sec; ///< seconds, 0..59
- int32_t frac; ///< fractions of a second; scale: 1/::RECEIVER_INFO::ticks_per_sec
- int32_t offs_from_utc; ///< local time's offset from %UTC
- uint16_t status; ///< status flags, see ::TM_GPS_STATUS_BITS
+ int8_t sec; ///< seconds, 0..59, or 60 in case of inserted leap second
+ int32_t frac; ///< fractions of a second, 1/::RECEIVER_INFO::ticks_per_sec units
+ int32_t offs_from_utc; ///< local time offset from %UTC [sec]
+ uint16_t status; ///< status flags, see ::TM_GPS_STATUS_BIT_MASKS
+
} TM_GPS;
#define _mbg_swab_tm_gps( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->year ); \
_mbg_swab16( &(_p)->yday ); \
_mbg_swab32( &(_p)->frac ); \
_mbg_swab32( &(_p)->offs_from_utc ); \
_mbg_swab16( &(_p)->status ); \
-}
+} while ( 0 )
/**
- * @brief Status flags used with TM_GPS::status
+ * @brief Status flag bits used to define ::TM_GPS_STATUS_BIT_MASKS
*
* These bits report info on the time conversion from GPS time to %UTC
* and/or local time as well as device status info.
+ *
+ * @see ::TM_GPS_STATUS_BIT_MASKS
*/
enum TM_GPS_STATUS_BITS
{
@@ -1269,31 +3054,43 @@ enum TM_GPS_STATUS_BITS
TM_BIT_EXT_SYNC, ///< synchronized externally
TM_BIT_HOLDOVER, ///< in holdover mode after previous synchronization
TM_BIT_ANT_SHORT, ///< antenna cable short circuited
- TM_BIT_NO_WARM, ///< OCXO has not warmed up
+ TM_BIT_NO_WARM, ///< oscillator control loop not settled
TM_BIT_ANT_DISCONN, ///< antenna currently disconnected
- TM_BIT_SYN_FLAG, ///< TIME_SYN output is low
+ TM_BIT_SYN_FLAG, ///< clock not synchronized, reflects the state of the "time sync error" output pin
TM_BIT_NO_SYNC, ///< time sync actually not verified
TM_BIT_NO_POS ///< position actually not verified, LOCK LED off
};
-// bit masks corresponding to the flag bits above
-#define TM_UTC ( 1UL << TM_BIT_UTC )
-#define TM_LOCAL ( 1UL << TM_BIT_LOCAL )
-#define TM_DL_ANN ( 1UL << TM_BIT_DL_ANN )
-#define TM_DL_ENB ( 1UL << TM_BIT_DL_ENB )
-#define TM_LS_ANN ( 1UL << TM_BIT_LS_ANN )
-#define TM_LS_ENB ( 1UL << TM_BIT_LS_ENB )
-#define TM_LS_ANN_NEG ( 1UL << TM_BIT_LS_ANN_NEG )
-#define TM_INVT ( 1UL << TM_BIT_INVT )
-#define TM_EXT_SYNC ( 1UL << TM_BIT_EXT_SYNC )
-#define TM_HOLDOVER ( 1UL << TM_BIT_HOLDOVER )
-#define TM_ANT_SHORT ( 1UL << TM_BIT_ANT_SHORT )
-#define TM_NO_WARM ( 1UL << TM_BIT_NO_WARM )
-#define TM_ANT_DISCONN ( 1UL << TM_BIT_ANT_DISCONN )
-#define TM_SYN_FLAG ( 1UL << TM_BIT_SYN_FLAG )
-#define TM_NO_SYNC ( 1UL << TM_BIT_NO_SYNC )
-#define TM_NO_POS ( 1UL << TM_BIT_NO_POS )
+/**
+ * @brief Status flag masks used with ::TM_GPS::status
+ *
+ * These bits report info on the time conversion from GPS time to %UTC
+ * and/or local time as well as device status info.
+ *
+ * @see ::TM_GPS_STATUS_BITS
+ */
+enum TM_GPS_STATUS_BIT_MASKS
+{
+ TM_UTC = ( 1UL << TM_BIT_UTC ), ///< see ::TM_BIT_UTC
+ TM_LOCAL = ( 1UL << TM_BIT_LOCAL ), ///< see ::TM_BIT_LOCAL
+ TM_DL_ANN = ( 1UL << TM_BIT_DL_ANN ), ///< see ::TM_BIT_DL_ANN
+ TM_DL_ENB = ( 1UL << TM_BIT_DL_ENB ), ///< see ::TM_BIT_DL_ENB
+ TM_LS_ANN = ( 1UL << TM_BIT_LS_ANN ), ///< see ::TM_BIT_LS_ANN
+ TM_LS_ENB = ( 1UL << TM_BIT_LS_ENB ), ///< see ::TM_BIT_LS_ENB
+ TM_LS_ANN_NEG = ( 1UL << TM_BIT_LS_ANN_NEG ), ///< see ::TM_BIT_LS_ANN_NEG
+ TM_INVT = ( 1UL << TM_BIT_INVT ), ///< see ::TM_BIT_INVT
+
+ TM_EXT_SYNC = ( 1UL << TM_BIT_EXT_SYNC ), ///< see ::TM_BIT_EXT_SYNC
+ TM_HOLDOVER = ( 1UL << TM_BIT_HOLDOVER ), ///< see ::TM_BIT_HOLDOVER
+ TM_ANT_SHORT = ( 1UL << TM_BIT_ANT_SHORT ), ///< see ::TM_BIT_ANT_SHORT
+ TM_NO_WARM = ( 1UL << TM_BIT_NO_WARM ), ///< see ::TM_BIT_NO_WARM
+ TM_ANT_DISCONN = ( 1UL << TM_BIT_ANT_DISCONN ), ///< see ::TM_BIT_ANT_DISCONN
+ TM_SYN_FLAG = ( 1UL << TM_BIT_SYN_FLAG ), ///< see ::TM_BIT_SYN_FLAG
+ TM_NO_SYNC = ( 1UL << TM_BIT_NO_SYNC ), ///< see ::TM_BIT_NO_SYNC
+ TM_NO_POS = ( 1UL << TM_BIT_NO_POS ) ///< see ::TM_BIT_NO_POS
+};
+
/**
@@ -1302,7 +3099,7 @@ enum TM_GPS_STATUS_BITS
typedef uint32_t TM_STATUS_EXT;
/**
- * @brief Enumeration of extended status bits used with TM_STATUS_EXT
+ * @brief Enumeration of extended status bits used with ::TM_STATUS_EXT
*
* @note The lower 16 bits correspond to ::TM_GPS_STATUS_BITS
*/
@@ -1313,7 +3110,7 @@ enum TM_GPS_STATUS_BITS_EX
// the remaining bits are reserved
};
-// The following bits are only used with the TM_STATUS_X type:
+// The following bits are only used with the ::TM_STATUS_X type:
#define TM_SCALE_GPS ( 1UL << TM_BIT_SCALE_GPS )
#define TM_SCALE_TAI ( 1UL << TM_BIT_SCALE_TAI )
@@ -1333,44 +3130,19 @@ typedef struct
int16_t channel; ///< -1: the current on-board time; >= 0 the capture channel number
T_GPS t; ///< time in GPS scale and format
TM_GPS tm; ///< time converted to %UTC and/or local time according to ::TZDL settings
+
} TTM;
#define _mbg_swab_ttm( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->channel ); \
_mbg_swab_t_gps( &(_p)->t ); \
_mbg_swab_tm_gps( &(_p)->tm ); \
-}
-
-
-
-/**
- * @brief A timestamp with nanosecond resolution
- */
-typedef struct
-{
- int32_t nano_secs; ///< [nanoseconds]
- int32_t secs; ///< [seconds]
-} NANO_TIME;
-
-#define _mbg_swab_nano_time( _p ) \
-{ \
- _mbg_swab32( &(_p)->nano_secs ); \
- _mbg_swab32( &(_p)->secs ); \
-}
+} while ( 0 )
-// The macro below checks if a NANO_TIME value is negative.
-#define _nano_time_negative( _nt ) \
- ( ( (_nt)->secs < 0 ) || ( (_nt)->nano_secs < 0 ) )
-
-/* Two types of variables used to store a position. Type XYZ is */
-/* used with a position in earth centered, earth fixed (ECEF) */
-/* coordinates whereas type LLA holds such a position converted */
-/* to geographic coordinates as defined by WGS84 (World Geodetic */
-/* System from 1984). */
-
#ifndef _XYZ_DEFINED
/**
* @brief Sequence and number of components of a cartesian position
@@ -1378,7 +3150,9 @@ typedef struct
enum XYZ_FIELDS { XP, YP, ZP, N_XYZ }; // x, y, z
/**
- * @brief An array holding a cartesian position
+ * @brief A position in cartesian coordinates
+ *
+ * Usually earth centered, earth fixed (ECEF) coordinates.
*/
typedef double XYZ[N_XYZ]; ///< values are in [m], see ::XYZ_FIELDS
@@ -1395,7 +3169,12 @@ typedef struct
enum LLA_FIELDS { LAT, LON, ALT, N_LLA }; /* latitude, longitude, altitude */
/**
- * @brief An array holding a geographic position
+ * @brief A geographic position based on latitude, longitude, and altitude
+ *
+ * The geographic position associated to specific cartesian coordinates
+ * depends on the characteristics of the ellipsoid used for the computation,
+ * the so-called geographic datum. GPS uses the WGS84 (World Geodetic System
+ * from 1984) ellipsoid by default.
*/
typedef double LLA[N_LLA]; ///< lon, lat in [rad], alt in [m], see ::LLA_FIELDS
@@ -1406,35 +3185,35 @@ typedef struct
/**
- @defgroup group_synth Synthesizer parameters
-
- Synthesizer frequency is expressed as a
- four digit decimal number (freq) to be multiplied by 0.1 Hz and an
- base 10 exponent (range). If the effective frequency is less than
- 10 kHz its phase is synchronized corresponding to the variable phase.
- Phase may be in a range from -360 deg to +360 deg with a resolution
- of 0.1 deg, so the resulting numbers to be stored are in a range of
- -3600 to +3600.
-
- Example:<br>
- Assume the value of freq is 2345 (decimal) and the value of phase is 900.
- If range == 0 the effective frequency is 234.5 Hz with a phase of +90 deg.
- If range == 1 the synthesizer will generate a 2345 Hz output frequency
- and so on.
-
- Limitations:<br>
- If freq == 0 the synthesizer is disabled. If range == 0 the least
- significant digit of freq is limited to 0, 3, 5 or 6. The resulting
- frequency is shown in the examples below:
- - freq == 1230 --> 123.0 Hz
- - freq == 1233 --> 123 1/3 Hz (real 1/3 Hz, NOT 123.3 Hz)
- - freq == 1235 --> 123.5 Hz
- - freq == 1236 --> 123 2/3 Hz (real 2/3 Hz, NOT 123.6 Hz)
-
- If range == MAX_RANGE the value of freq must not exceed 1000, so the
- output frequency is limited to 10 MHz.
- @{
-*/
+ * @defgroup group_synth Synthesizer parameters
+ *
+ * Synthesizer frequency is expressed as a
+ * four digit decimal number (freq) to be multiplied by 0.1 Hz and an
+ * base 10 exponent (range). If the effective frequency is less than
+ * 10 kHz its phase is synchronized corresponding to the variable phase.
+ * Phase may be in a range from -360 deg to +360 deg with a resolution
+ * of 0.1 deg, so the resulting numbers to be stored are in a range of
+ * -3600 to +3600.
+ *
+ * Example:<br>
+ * Assume the value of freq is 2345 (decimal) and the value of phase is 900.
+ * If range == 0 the effective frequency is 234.5 Hz with a phase of +90 deg.
+ * If range == 1 the synthesizer will generate a 2345 Hz output frequency
+ * and so on.
+ *
+ * Limitations:<br>
+ * If freq == 0 the synthesizer is disabled. If range == 0 the least
+ * significant digit of freq is limited to 0, 3, 5 or 6. The resulting
+ * frequency is shown in the examples below:
+ * - freq == 1230 --> 123.0 Hz
+ * - freq == 1233 --> 123 1/3 Hz (real 1/3 Hz, NOT 123.3 Hz)
+ * - freq == 1235 --> 123.5 Hz
+ * - freq == 1236 --> 123 2/3 Hz (real 2/3 Hz, NOT 123.6 Hz)
+ *
+ * If range == ::MAX_SYNTH_RANGE the value of freq must not exceed 1000, so
+ * the output frequency is limited to 10 MHz (see ::MAX_SYNTH_FREQ_VAL).
+ *
+ * @{ */
#define N_SYNTH_FREQ_DIGIT 4 ///< number of digits to edit
#define MAX_SYNTH_FREQ 1000 ///< if range == ::MAX_SYNTH_RANGE
@@ -1443,12 +3222,13 @@ typedef struct
#define MAX_SYNTH_RANGE 5
#define N_SYNTH_RANGE ( MAX_SYNTH_RANGE - MIN_SYNTH_RANGE + 1 )
-#define N_SYNTH_PHASE_DIGIT 4
-#define MAX_SYNTH_PHASE 3600
+#define N_SYNTH_PHASE_DIGIT 4
+#define MAX_SYNTH_PHASE 3600
#define MAX_SYNTH_FREQ_EDIT 9999 ///< max sequence of digits when editing
+
/**
* @brief The maximum frequency that can be configured for the synthesizer
*/
@@ -1471,7 +3251,7 @@ typedef struct
* @brief Synthesizer frequency units
*
* An initializer for commonly displayed synthesizer frequency units
- * (N_SYNTH_RANGE strings)
+ * (::N_SYNTH_RANGE strings)
*/
#define DEFAULT_FREQ_RANGES \
{ \
@@ -1490,17 +3270,19 @@ typedef struct
*/
typedef struct
{
- int16_t freq; ///< four digits used; scale: 0.1; e.g. 1234 -> 123.4 Hz
+ int16_t freq; ///< four digits used; scale: 0.1 Hz; e.g. 1234 -> 123.4 Hz
int16_t range; ///< scale factor for freq; 0..::MAX_SYNTH_RANGE
int16_t phase; ///< -::MAX_SYNTH_PHASE..+::MAX_SYNTH_PHASE; >0 -> pulses later
+
} SYNTH;
#define _mbg_swab_synth( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->freq ); \
_mbg_swab16( &(_p)->range ); \
_mbg_swab16( &(_p)->phase ); \
-}
+} while ( 0 )
/**
@@ -1524,42 +3306,51 @@ typedef struct
{
uint8_t state; ///< state code as enumerated in ::SYNTH_STATES
uint8_t flags; ///< reserved, currently always 0
+
} SYNTH_STATE;
#define _mbg_swab_synth_state( _p ) _nop_macro_fnc()
#define SYNTH_FLAG_PHASE_IGNORED 0x01
-/** @} group_synth */
+/** @} defgroup group_synth */
+
+
/**
- * @defgroup group_tzdl Time zone/daylight saving parameters
- *
- * Example: <br>
- * For automatic daylight saving enable/disable in Central Europe,
- * the variables are to be set as shown below: <br>
- * - offs = 3600L one hour from %UTC
- * - offs_dl = 3600L one additional hour if daylight saving enabled
- * - tm_on = first Sunday from March 25, 02:00:00h ( year |= DL_AUTO_FLAG )
- * - tm_off = first Sunday from October 25, 03:00:00h ( year |= DL_AUTO_FLAG )
- * - name[0] == "CET " name if daylight saving not enabled
- * - name[1] == "CEST " name if daylight saving is enabled
- * @{
- */
+ * @defgroup group_tzdl Time zone / daylight saving parameters
+ *
+ * Example: <br>
+ * For automatic daylight saving enable/disable in Central Europe,
+ * the variables are to be set as shown below: <br>
+ * - offs = 3600L one hour from %UTC
+ * - offs_dl = 3600L one additional hour if daylight saving enabled
+ * - tm_on = first Sunday from March 25, 02:00:00h ( year |= ::DL_AUTO_FLAG )
+ * - tm_off = first Sunday from October 25, 03:00:00h ( year |= ::DL_AUTO_FLAG )
+ * - name[0] == "CET " name if daylight saving not enabled
+ * - name[1] == "CEST " name if daylight saving is enabled
+ *
+ * @{ */
/**
* @brief The name of a time zone
*
- * @note Up to 5 printable characters plus trailing zero
+ * @note Up to 5 printable characters, plus trailing zero
*/
typedef char TZ_NAME[6];
/**
* @brief Time zone / daylight saving parameters
*
- * This structure is used to specify how a device is to convert
- * on-board %UTC to local time, including computation of beginning
- * and end of daylight saving time (DST), if required.
+ * This structure is used to specify how a device converts on-board %UTC
+ * to local time, including computation of beginning and end of daylight
+ * saving time (DST), if required.
+ *
+ * @note The ::TZDL structure contains members of type ::TM_GPS to specify
+ * the times for beginning and end of DST. However, the ::TM_GPS::frac,
+ * ::TM_GPS::offs_from_utc, and ::TM_GPS::status fields of these ::TZDL::tm_on
+ * and ::TZDL::tm_off members are ignored for the conversion to local time,
+ * and thus should be 0.
*/
typedef struct
{
@@ -1568,21 +3359,23 @@ typedef struct
TM_GPS tm_on; ///< date/time when daylight saving starts
TM_GPS tm_off; ///< date/time when daylight saving ends
TZ_NAME name[2]; ///< names without and with daylight saving enabled
+
} TZDL;
#define _mbg_swab_tzdl( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->offs ); \
_mbg_swab32( &(_p)->offs_dl ); \
_mbg_swab_tm_gps( &(_p)->tm_on ); \
_mbg_swab_tm_gps( &(_p)->tm_off ); \
-}
+} while ( 0 )
/**
* @brief A flag indicating automatic computation of DST
*
- * If this flag is or'ed to the year numbers in TZDL::tm_on and TZDL::tm_off
+ * If this flag is or'ed to the year numbers in ::TZDL::tm_on and ::TZDL::tm_off
* then daylight saving is computed automatically year by year.
*/
#define DL_AUTO_FLAG 0x8000
@@ -1591,13 +3384,13 @@ typedef struct
// Below there are some initializers for commonly used TZDL configurations:
-#define DEFAULT_TZDL_AUTO_YEAR ( 2007 | DL_AUTO_FLAG )
+#define DEFAULT_TZDL_AUTO_YEAR ( (int16_t) ( 2007L | DL_AUTO_FLAG ) )
-#define DEFAULt_TZDL_OFFS_DL 3600L /**< usually DST is +1 hour */
+#define DEFAULt_TZDL_OFFS_DL 3600L ///< usually DST is +1 hour
/**
- * An initializer for TZDL::tm_on and TZDL::tm_off for time zones
+ * An initializer for ::TZDL::tm_on and ::TZDL::tm_off for time zones
* which do not observe DST.
*/
#define DEFAULT_TZDL_TM_ON_OFF_NO_DST \
@@ -1612,22 +3405,22 @@ typedef struct
#define DEFAULT_TZDL_UTC \
{ \
- 0L, /**< offs */ \
- 0L, /**< offs_dl */ \
- DEFAULT_TZDL_TM_ON_OFF_NO_DST, /**< tm_on */ \
- DEFAULT_TZDL_TM_ON_OFF_NO_DST, /**< tm_off */ \
- DEFAULT_TZDL_NAMES_UTC /**< name[] */ \
+ 0L, /* offs */ \
+ 0L, /* offs_dl */ \
+ DEFAULT_TZDL_TM_ON_OFF_NO_DST, /* tm_on */ \
+ DEFAULT_TZDL_TM_ON_OFF_NO_DST, /* tm_off */ \
+ DEFAULT_TZDL_NAMES_UTC /* name */ \
}
/**
- * @brief An initializer for TZDL::tm_on according to the rules for Central Europe
+ * @brief An initializer for ::TZDL::tm_on according to the rules for Central Europe
*/
#define DEFAULT_TZDL_TM_ON_CET_CEST \
{ DEFAULT_TZDL_AUTO_YEAR, 3, 25, 0, 0, 2, 0, 0, 0L, 0L, 0 }
/**
- * @brief An initializer for TZDL::tm_off according to the rules for Central Europe
+ * @brief An initializer for ::TZDL::tm_off according to the rules for Central Europe
*/
#define DEFAULT_TZDL_TM_OFF_CET_CEST \
{ DEFAULT_TZDL_AUTO_YEAR, 10, 25, 0, 0, 3, 0, 0, 0L, 0L, 0 }
@@ -1645,20 +3438,20 @@ typedef struct
#define DEFAULT_TZDL_CET_CEST_EN \
{ \
- DEFAULT_TZDL_OFFS_CET, /**< offs */ \
- DEFAULt_TZDL_OFFS_DL, /**< offs_dl */ \
- DEFAULT_TZDL_TM_ON_CET_CEST, /**< tm_on */ \
- DEFAULT_TZDL_TM_OFF_CET_CEST, /**< tm_off */ \
- DEFAULT_TZDL_NAMES_CET_CEST_EN /**< name[] */ \
+ DEFAULT_TZDL_OFFS_CET, /* offs */ \
+ DEFAULt_TZDL_OFFS_DL, /* offs_dl */ \
+ DEFAULT_TZDL_TM_ON_CET_CEST, /* tm_on */ \
+ DEFAULT_TZDL_TM_OFF_CET_CEST, /* tm_off */ \
+ DEFAULT_TZDL_NAMES_CET_CEST_EN /* name */ \
}
#define DEFAULT_TZDL_CET_CEST_DE \
{ \
- DEFAULT_TZDL_OFFS_CET, /**< offs */ \
- DEFAULt_TZDL_OFFS_DL, /**< offs_dl */ \
- DEFAULT_TZDL_TM_ON_CET_CEST, /**< tm_on */ \
- DEFAULT_TZDL_TM_OFF_CET_CEST, /**< tm_off */ \
- DEFAULT_TZDL_NAMES_CET_CEST_DE /**< name[] */ \
+ DEFAULT_TZDL_OFFS_CET, /* offs */ \
+ DEFAULt_TZDL_OFFS_DL, /* offs_dl */ \
+ DEFAULT_TZDL_TM_ON_CET_CEST, /* tm_on */ \
+ DEFAULT_TZDL_TM_OFF_CET_CEST, /* tm_off */ \
+ DEFAULT_TZDL_NAMES_CET_CEST_DE /* name */ \
}
@@ -1688,7 +3481,7 @@ typedef struct
DEFAULt_TZDL_OFFS_DL, /* offs_dl */ \
DEFAULT_TZDL_TM_ON_EET_EEST, /* tm_on */ \
DEFAULT_TZDL_TM_OFF_EET_EEST, /* tm_off */ \
- DEFAULT_TZDL_NAMES_EET_EEST_EN /* name[] */ \
+ DEFAULT_TZDL_NAMES_EET_EEST_EN /* name */ \
}
#define DEFAULT_TZDL_EET_EEST_DE \
@@ -1697,24 +3490,25 @@ typedef struct
DEFAULt_TZDL_OFFS_DL, /* offs_dl */ \
DEFAULT_TZDL_TM_ON_EET_EEST, /* tm_on */ \
DEFAULT_TZDL_TM_OFF_EET_EEST, /* tm_off */ \
- DEFAULT_TZDL_NAMES_EET_EEST_DE /* name[] */ \
+ DEFAULT_TZDL_NAMES_EET_EEST_DE /* name */ \
}
-/** @} group_tzdl */
+/** @} defgroup group_tzdl */
/**
- * @brief Antenna status information
+ * @brief Antenna status and error at reconnect information
*
* The structure below reflects the status of the antenna,
* the times of last disconnect/reconnect, and the board's
- * clock offset after the disconnection interval.
+ * clock offset when it has synchronized again after the
+ * disconnection interval.
*
- * @note ANT_INFO::status changes back to ::ANT_RECONN only
+ * @note ::ANT_INFO::status changes back to ::ANT_RECONN only
* after the antenna has been reconnected <b>and</b> the
* receiver has re-synchronized to the satellite signal.
- * In this case ANT_INFO::delta_t reports the time offset
+ * In this case ::ANT_INFO::delta_t reports the time offset
* before resynchronization, i.e. how much the internal
* time has drifted while the antenna was disconnected.
*/
@@ -1723,20 +3517,22 @@ typedef struct
int16_t status; ///< current status of antenna, see ::ANT_STATUS_CODES
TM_GPS tm_disconn; ///< time of antenna disconnect
TM_GPS tm_reconn; ///< time of antenna reconnect
- int32_t delta_t; ///< clock offs at reconn. time in 1/::RECEIVER_INFO::ticks_per_sec
+ int32_t delta_t; ///< clock offs at reconn. time in 1/::RECEIVER_INFO::ticks_per_sec units
+
} ANT_INFO;
#define _mbg_swab_ant_info( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->status ); \
_mbg_swab_tm_gps( &(_p)->tm_disconn ); \
_mbg_swab_tm_gps( &(_p)->tm_reconn ); \
_mbg_swab32( &(_p)->delta_t ); \
-}
+} while ( 0 )
/**
- * @brief Status code used with ANT_INFO::status
+ * @brief Status code used with ::ANT_INFO::status
*/
enum ANT_STATUS_CODES
{
@@ -1747,23 +3543,15 @@ enum ANT_STATUS_CODES
};
-/* Defines used with ENABLE_FLAGS */
-
-#define EF_OFF 0x00 /**< outputs off until sync'd */
-
-#define EF_SERIAL_BOTH 0x03 /**< both serial ports on */
-#define EF_PULSES_BOTH 0x03 /**< both pulses P_SEC and P_MIN on */
-#define EF_FREQ_ALL 0x07 /**< all fixed freq. outputs on */
-#define EF_SYNTH 0x01 /**< synth. on */
/**
* @brief A structure controlling when output signals are enabled
*
* The structure holds some flags which let the corresponding outputs
* be disabled after power-up until the receiver has synchronized
- * (flag == ::EF_OFF, the default) or force the outputs to be enabled
+ * (flags == ::EF_OFF, the default) or force the outputs to be enabled
* immediately after power-up. The fixed frequency output is hard-wired
- * to be enabled immediately after power-up, so ENABLE_FLAGS::freq must
+ * to be enabled immediately after power-up, so ::ENABLE_FLAGS::freq must
* always be set to ::EF_FREQ_ALL.
*/
typedef struct
@@ -1772,18 +3560,33 @@ typedef struct
uint16_t pulses; ///< ::EF_OFF or ::EF_PULSES_BOTH
uint16_t freq; ///< always ::EF_FREQ_ALL
uint16_t synth; ///< ::EF_OFF or ::EF_SYNTH
+
} ENABLE_FLAGS;
#define _mbg_swab_enable_flags( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->serial ); \
_mbg_swab16( &(_p)->pulses ); \
_mbg_swab16( &(_p)->freq ); \
_mbg_swab16( &(_p)->synth ); \
-}
+} while ( 0 )
+
+
+/**
+ * @brief Codes used with ::ENABLE_FLAGS
+ **/
+enum ENABLE_FLAGS_CODES
+{
+ EF_OFF = 0x00, ///< associated outputs off until synchronized
+
+ EF_SERIAL_BOTH = 0x03, ///< both serial ports on, use with ::ENABLE_FLAGS::serial
+ EF_PULSES_BOTH = 0x03, ///< both pulses P_SEC and P_MIN on, use with ::ENABLE_FLAGS::pulses
+ EF_FREQ_ALL = 0x07, ///< all fixed freq. outputs on, use with ::ENABLE_FLAGS::freq
+ EF_SYNTH = 0x01 ///< synthesizer on, use with ::ENABLE_FLAGS::synth
+};
-/* A struct used to hold the settings of a serial port: */
#ifndef _COM_HS_DEFINED
/**
@@ -1795,22 +3598,26 @@ typedef struct
#ifndef _COM_PARM_DEFINED
/**
- * @brief A data type to configure a baud rate
+ * @brief A data type to configure a serial port's baud rate
+ *
+ * @see ::MBG_BAUD_RATES
*/
typedef int32_t BAUD_RATE;
/**
* @brief Indices used to identify a parameter in the framing string
+ *
+ * @see ::MBG_FRAMING_STRS
*/
- enum { F_DBITS, F_PRTY, F_STBITS };
+ enum MBG_FRAMING_STR_IDXS { F_DBITS, F_PRTY, F_STBITS };
/**
* @brief A structure to store the configuration of a serial port
*/
typedef struct
{
- BAUD_RATE baud_rate; ///< transmission speed, e.g. 19200L
- char framing[4]; ///< ASCIIZ framing string, e.g. "8N1" or "7E2"
+ BAUD_RATE baud_rate; ///< transmission speed, e.g. 19200L, see ::MBG_BAUD_RATES
+ char framing[4]; ///< ASCIIZ framing string, e.g. "8N1" or "7E2", see ::MBG_FRAMING_STRS
int16_t handshake; ///< handshake mode, yet only ::HS_NONE supported
} COM_PARM;
@@ -1821,16 +3628,20 @@ typedef struct
#define _mbg_swab_baud_rate( _p ) _mbg_swab32( _p )
#define _mbg_swab_com_parm( _p ) \
+do \
{ \
_mbg_swab_baud_rate( &(_p)->baud_rate ); \
_mbg_swab16( &(_p)->handshake ); \
-}
+} while ( 0 )
/**
- * @brief Indices of any supported serial port baud rates
+ * @brief Enumeration of serial port baud rates
*
* @note Most clock models and/or serial ports don't support all defined baud rates.
+ *
+ * @see ::MBG_BAUD_RATES
+ * @see ::MBG_BAUD_RATE_MASKS
*/
enum MBG_BAUD_RATE_CODES
{
@@ -1842,12 +3653,23 @@ enum MBG_BAUD_RATE_CODES
MBG_BAUD_RATE_9600,
MBG_BAUD_RATE_19200,
MBG_BAUD_RATE_38400,
- N_MBG_BAUD_RATES /**< the number of supported baud rates */
+ MBG_BAUD_RATE_57600,
+ MBG_BAUD_RATE_115200,
+ MBG_BAUD_RATE_230400,
+ MBG_BAUD_RATE_460800,
+ MBG_BAUD_RATE_921600,
+ N_MBG_BAUD_RATES ///< the number of known baud rates
};
-/*
- * An initializer for a table of baud rate values.
- * The values must correspond to the enumeration above.
+/**
+ * @brief An initializer for a table of baud rate values
+ *
+ * These values can be used with ::COM_PARM::baud_rate, if the device
+ * supports the particular baud rate.
+ *
+ * The values must correspond to the enumeration ::MBG_BAUD_RATE_CODES
+ *
+ * @see ::MBG_BAUD_RATE_CODES
*/
#define MBG_BAUD_RATES \
{ \
@@ -1858,12 +3680,20 @@ enum MBG_BAUD_RATE_CODES
4800L, \
9600L, \
19200L, \
- 38400L \
+ 38400L, \
+ 57600L, \
+ 115200L, \
+ 230400L, \
+ 460800L, \
+ 921600L \
}
-/*
- * An initializer for a table of baud rate strings.
- * The values must correspond to the enumeration above.
+/**
+ * @brief An initializer for a table of baud rate strings
+ *
+ * The values must correspond to the enumeration ::MBG_BAUD_RATE_CODES
+ *
+ * @see ::MBG_BAUD_RATE_CODES
*/
#define MBG_BAUD_STRS \
{ \
@@ -1874,30 +3704,47 @@ enum MBG_BAUD_RATE_CODES
"4800", \
"9600", \
"19200", \
- "38400" \
+ "38400", \
+ "57600", \
+ "115200", \
+ "230400", \
+ "460800", \
+ "921600" \
}
-/*
- * The bit masks below can be used to determine which baud rates
- * are supported by a serial port. This may vary between
- * different ports of the same device since different
- * types of UART are used which must not necessarily support
- * each baud rate:
+/**
+ * @brief Bit masks associated with baud rates enumerated in ::MBG_BAUD_RATE_CODES
+ *
+ * These bit masks are used e.g. with ::PORT_INFO::supp_baud_rates to
+ * determine which baud rates are supported by a particular serial port.
+ *
+ * @see ::MBG_BAUD_RATE_CODES
+ * @see ::MBG_FRAMING_MASKS
*/
-#define MBG_PORT_HAS_300 ( 1UL << MBG_BAUD_RATE_300 )
-#define MBG_PORT_HAS_600 ( 1UL << MBG_BAUD_RATE_600 )
-#define MBG_PORT_HAS_1200 ( 1UL << MBG_BAUD_RATE_1200 )
-#define MBG_PORT_HAS_2400 ( 1UL << MBG_BAUD_RATE_2400 )
-#define MBG_PORT_HAS_4800 ( 1UL << MBG_BAUD_RATE_4800 )
-#define MBG_PORT_HAS_9600 ( 1UL << MBG_BAUD_RATE_9600 )
-#define MBG_PORT_HAS_19200 ( 1UL << MBG_BAUD_RATE_19200 )
-#define MBG_PORT_HAS_38400 ( 1UL << MBG_BAUD_RATE_38400 )
+enum MBG_BAUD_RATE_MASKS
+{
+ MBG_PORT_HAS_300 = ( 1UL << MBG_BAUD_RATE_300 ), ///< see ::MBG_BAUD_RATE_300
+ MBG_PORT_HAS_600 = ( 1UL << MBG_BAUD_RATE_600 ), ///< see ::MBG_BAUD_RATE_600
+ MBG_PORT_HAS_1200 = ( 1UL << MBG_BAUD_RATE_1200 ), ///< see ::MBG_BAUD_RATE_1200
+ MBG_PORT_HAS_2400 = ( 1UL << MBG_BAUD_RATE_2400 ), ///< see ::MBG_BAUD_RATE_2400
+ MBG_PORT_HAS_4800 = ( 1UL << MBG_BAUD_RATE_4800 ), ///< see ::MBG_BAUD_RATE_4800
+ MBG_PORT_HAS_9600 = ( 1UL << MBG_BAUD_RATE_9600 ), ///< see ::MBG_BAUD_RATE_9600
+ MBG_PORT_HAS_19200 = ( 1UL << MBG_BAUD_RATE_19200 ), ///< see ::MBG_BAUD_RATE_19200
+ MBG_PORT_HAS_38400 = ( 1UL << MBG_BAUD_RATE_38400 ), ///< see ::MBG_BAUD_RATE_38400
+ MBG_PORT_HAS_57600 = ( 1UL << MBG_BAUD_RATE_57600 ), ///< see ::MBG_BAUD_RATE_57600
+ MBG_PORT_HAS_115200 = ( 1UL << MBG_BAUD_RATE_115200 ), ///< see ::MBG_BAUD_RATE_115200
+ MBG_PORT_HAS_230400 = ( 1UL << MBG_BAUD_RATE_230400 ), ///< see ::MBG_BAUD_RATE_230400
+ MBG_PORT_HAS_460800 = ( 1UL << MBG_BAUD_RATE_460800 ), ///< see ::MBG_BAUD_RATE_460800
+ MBG_PORT_HAS_921600 = ( 1UL << MBG_BAUD_RATE_921600 ) ///< see ::MBG_BAUD_RATE_921600
+};
/**
- * @brief Indices of any supported serial port framings.
+ * @brief Enumeration of all known serial port framings
*
* @note Most clock models and/or serial ports don't support all defined framing types.
+ *
+ * @see ::MBG_FRAMING_STRS
*/
enum MBG_FRAMING_CODES
{
@@ -1910,13 +3757,21 @@ enum MBG_FRAMING_CODES
MBG_FRAMING_7O1,
MBG_FRAMING_7O2,
MBG_FRAMING_8O1,
- MBG_FRAMING_8E2, /**< @note: Most serial ports don't support this! */
- N_MBG_FRAMINGS /**< the number of supported framings */
+ MBG_FRAMING_8E2, ///< Note: most serial ports don't support this!
+ N_MBG_FRAMINGS ///< the number of known framings
};
-/*
- * An initializer for a table of framing strings.
- * The values must correspond to the enumeration above.
+/**
+ * @brief An initializer for a table of known framing strings
+ *
+ * These values can be used with ::COM_PARM::framing, if the device
+ * supports the particular framing.
+ *
+ * The values must correspond to the enumeration ::MBG_FRAMING_CODES
+ *
+ * @see ::MBG_FRAMING_CODES
+ * @see ::MBG_FRAMING_MASKS
+ * @see ::MBG_FRAMING_STR_IDXS
*/
#define MBG_FRAMING_STRS \
{ \
@@ -1932,29 +3787,76 @@ enum MBG_FRAMING_CODES
"8E2" \
}
-/*
- * The bit masks below can be used to determine which framings
- * are supported by a serial port. This may vary between
- * different ports of the same device since different
- * types of UART are used which must not necessarily support
- * each framing type:
+/**
+ * @brief Bit masks associated with framings enumerated in ::MBG_FRAMING_CODES
+ *
+ * These bit masks are used e.g. with ::PORT_INFO::supp_framings to
+ * determine which framings are supported by a particular serial port.
+ *
+ * @see ::MBG_FRAMING_CODES
+ * @see ::MBG_FRAMING_STRS
*/
-#define MBG_PORT_HAS_7N2 ( 1UL << MBG_FRAMING_7N2 )
-#define MBG_PORT_HAS_7E1 ( 1UL << MBG_FRAMING_7E1 )
-#define MBG_PORT_HAS_7E2 ( 1UL << MBG_FRAMING_7E2 )
-#define MBG_PORT_HAS_8N1 ( 1UL << MBG_FRAMING_8N1 )
-#define MBG_PORT_HAS_8N2 ( 1UL << MBG_FRAMING_8N2 )
-#define MBG_PORT_HAS_8E1 ( 1UL << MBG_FRAMING_8E1 )
-#define MBG_PORT_HAS_7O1 ( 1UL << MBG_FRAMING_7O1 )
-#define MBG_PORT_HAS_7O2 ( 1UL << MBG_FRAMING_7O2 )
-#define MBG_PORT_HAS_8O1 ( 1UL << MBG_FRAMING_8O1 )
-#define MBG_PORT_HAS_8E2 ( 1UL << MBG_FRAMING_8E2 )
+enum MBG_FRAMING_MASKS
+{
+ MBG_PORT_HAS_7N2 = ( 1UL << MBG_FRAMING_7N2 ), ///< see ::MBG_FRAMING_7N2
+ MBG_PORT_HAS_7E1 = ( 1UL << MBG_FRAMING_7E1 ), ///< see ::MBG_FRAMING_7E1
+ MBG_PORT_HAS_7E2 = ( 1UL << MBG_FRAMING_7E2 ), ///< see ::MBG_FRAMING_7E2
+ MBG_PORT_HAS_8N1 = ( 1UL << MBG_FRAMING_8N1 ), ///< see ::MBG_FRAMING_8N1
+ MBG_PORT_HAS_8N2 = ( 1UL << MBG_FRAMING_8N2 ), ///< see ::MBG_FRAMING_8N2
+ MBG_PORT_HAS_8E1 = ( 1UL << MBG_FRAMING_8E1 ), ///< see ::MBG_FRAMING_8E1
+ MBG_PORT_HAS_7O1 = ( 1UL << MBG_FRAMING_7O1 ), ///< see ::MBG_FRAMING_7O1
+ MBG_PORT_HAS_7O2 = ( 1UL << MBG_FRAMING_7O2 ), ///< see ::MBG_FRAMING_7O2
+ MBG_PORT_HAS_8O1 = ( 1UL << MBG_FRAMING_8O1 ), ///< see ::MBG_FRAMING_8O1
+ MBG_PORT_HAS_8E2 = ( 1UL << MBG_FRAMING_8E2 ) ///< see ::MBG_FRAMING_8E2
+};
+
+
+
+/**
+ * @brief Definitions used with the Meinberg binary protocol
+ *
+ * @anchor GPS_BIN_PROT_DEFS @{ */
+
+/**
+ * @brief Framing used with the binary protocol
+ *
+ * Different data length, or parity settings would corrupt
+ * the binary data.
+ */
+#define MBG_DEFAULT_FRAMING "8N1"
+/**
+ * @brief The standard baud rate used for the binary protocol
+ *
+ * This is supported by most devices. Some new devices may also
+ * support ::MBG_DEFAULT_BAUDRATE_HS
+ */
+#define MBG_DEFAULT_BAUDRATE 19200L
+
+/**
+ * @brief The high speed baud rate used for the binary protocol
+ *
+ * This is not supported by older devices which work
+ * with ::MBG_DEFAULT_BAUDRATE only.
+ */
+#define MBG_DEFAULT_BAUDRATE_HS 115200L
+
+
+/**
+ * @brief Strings used to force connection settings for the binary protocol
+ *
+ * If a device supports this and receives one of these ASCII strings
+ * then it temporarily switches the serial port to some well-known
+ * baud rate and framing appropriate for the binary protocol.
+ *
+ * @anchor GPS_BIN_PROT_CMD_STRS @{ */
-// Default port settings to be used
-// with the binary protocol
-#define MBG_DEFAULT_BAUDRATE 19200L
-#define MBG_DEFAULT_FRAMING "8N1"
+#define MBG_FORCE_CONN_CMD_STR "\nDFC\n" ///< switch to ::MBG_DEFAULT_BAUDRATE
+#define MBG_FORCE_CONN_HS_CMD_STR "\nDFCHS\n" ///< switch to ::MBG_DEFAULT_BAUDRATE_HS
+
+/** @} anchor GPS_BIN_PROT_CMD_STRS */
+
+/** @} anchor GPS_BIN_PROT_DEFS */
@@ -2022,21 +3924,23 @@ typedef struct
COM_PARM parm; ///< transmission speed, framing, etc.
uint8_t mode; ///< string mode, see ::STR_MODES
uint8_t str_type; ///< index of the supported time string formats, see ::STR_TYPE_INFO_IDX
- uint32_t flags; ///< @see COM_CFG_STATUS_BITS
+ uint32_t flags; ///< reserved, don't use, currently 0
+
} PORT_SETTINGS;
#define _mbg_swab_port_settings( _p ) \
+do \
{ \
_mbg_swab_com_parm( &(_p)->parm ); \
_mbg_swab32( &(_p)->flags ); \
-}
+} while ( 0 )
/**
- * @brief Flag bits used to marks individual ::PORT_SETTINGS fields
+ * @brief Flag bits used to mark individual ::PORT_SETTINGS fields
*
* These definitions can be used to mark specific fields of a
- * PORT_SETTINGS structure, e.g. which fields have changed when
+ * ::PORT_SETTINGS structure, e.g. which fields have changed when
* editing, or which fields have settings which are not valid.
*/
enum MBG_COM_CFG_STATUS_BITS
@@ -2060,22 +3964,33 @@ enum MBG_COM_CFG_STATUS_BITS
N_MBG_PS_BIT
};
-#define MBG_PS_MSK_BAUD_RATE_OVR_SW ( 1UL << MBG_PS_BIT_BAUD_RATE_OVR_SW )
-#define MBG_PS_MSK_BAUD_RATE_OVR_DEV ( 1UL << MBG_PS_BIT_BAUD_RATE_OVR_DEV )
-#define MBG_PS_MSK_BAUD_RATE ( 1UL << MBG_PS_BIT_BAUD_RATE )
-#define MBG_PS_MSK_FRAMING_OVR_SW ( 1UL << MBG_PS_BIT_FRAMING_OVR_SW )
-#define MBG_PS_MSK_FRAMING_OVR_DEV ( 1UL << MBG_PS_BIT_FRAMING_OVR_DEV )
-#define MBG_PS_MSK_FRAMING ( 1UL << MBG_PS_BIT_FRAMING )
-#define MBG_PS_MSK_HS_OVR_SW ( 1UL << MBG_PS_BIT_HS_OVR_SW )
-#define MBG_PS_MSK_HS ( 1UL << MBG_PS_BIT_HS )
-#define MBG_PS_MSK_STR_TYPE_OVR_SW ( 1UL << MBG_PS_BIT_STR_TYPE_OVR_SW )
-#define MBG_PS_MSK_STR_TYPE_OVR_DEV ( 1UL << MBG_PS_BIT_STR_TYPE_OVR_DEV )
-#define MBG_PS_MSK_STR_TYPE ( 1UL << MBG_PS_BIT_STR_TYPE )
-#define MBG_PS_MSK_STR_MODE_OVR_SW ( 1UL << MBG_PS_BIT_STR_MODE_OVR_SW )
-#define MBG_PS_MSK_STR_MODE_OVR_DEV ( 1UL << MBG_PS_BIT_STR_MODE_OVR_DEV )
-#define MBG_PS_MSK_STR_MODE ( 1UL << MBG_PS_BIT_STR_MODE )
-#define MBG_PS_MSK_FLAGS_OVR_SW ( 1UL << MBG_PS_BIT_FLAGS_OVR_SW )
-#define MBG_PS_MSK_FLAGS ( 1UL << MBG_PS_BIT_FLAGS )
+/**
+ * @brief Flag bit masks associated with ::MBG_COM_CFG_STATUS_BITS
+ *
+ * These definitions can be used to mark specific fields of a
+ * ::PORT_SETTINGS structure, e.g. which fields have changed when
+ * editing, or which fields have settings which are not valid.
+ *
+ * @anchor MBG_COM_CFG_STATUS_MASKS @{ */
+
+#define MBG_PS_MSK_BAUD_RATE_OVR_SW ( 1UL << MBG_PS_BIT_BAUD_RATE_OVR_SW ) ///< see ::MBG_PS_BIT_BAUD_RATE_OVR_SW
+#define MBG_PS_MSK_BAUD_RATE_OVR_DEV ( 1UL << MBG_PS_BIT_BAUD_RATE_OVR_DEV ) ///< see ::MBG_PS_BIT_BAUD_RATE_OVR_DEV
+#define MBG_PS_MSK_BAUD_RATE ( 1UL << MBG_PS_BIT_BAUD_RATE ) ///< see ::MBG_PS_BIT_BAUD_RATE
+#define MBG_PS_MSK_FRAMING_OVR_SW ( 1UL << MBG_PS_BIT_FRAMING_OVR_SW ) ///< see ::MBG_PS_BIT_FRAMING_OVR_SW
+#define MBG_PS_MSK_FRAMING_OVR_DEV ( 1UL << MBG_PS_BIT_FRAMING_OVR_DEV ) ///< see ::MBG_PS_BIT_FRAMING_OVR_DEV
+#define MBG_PS_MSK_FRAMING ( 1UL << MBG_PS_BIT_FRAMING ) ///< see ::MBG_PS_BIT_FRAMING
+#define MBG_PS_MSK_HS_OVR_SW ( 1UL << MBG_PS_BIT_HS_OVR_SW ) ///< see ::MBG_PS_BIT_HS_OVR_SW
+#define MBG_PS_MSK_HS ( 1UL << MBG_PS_BIT_HS ) ///< see ::MBG_PS_BIT_HS
+#define MBG_PS_MSK_STR_TYPE_OVR_SW ( 1UL << MBG_PS_BIT_STR_TYPE_OVR_SW ) ///< see ::MBG_PS_BIT_STR_TYPE_OVR_SW
+#define MBG_PS_MSK_STR_TYPE_OVR_DEV ( 1UL << MBG_PS_BIT_STR_TYPE_OVR_DEV ) ///< see ::MBG_PS_BIT_STR_TYPE_OVR_DEV
+#define MBG_PS_MSK_STR_TYPE ( 1UL << MBG_PS_BIT_STR_TYPE ) ///< see ::MBG_PS_BIT_STR_TYPE
+#define MBG_PS_MSK_STR_MODE_OVR_SW ( 1UL << MBG_PS_BIT_STR_MODE_OVR_SW ) ///< see ::MBG_PS_BIT_STR_MODE_OVR_SW
+#define MBG_PS_MSK_STR_MODE_OVR_DEV ( 1UL << MBG_PS_BIT_STR_MODE_OVR_DEV ) ///< see ::MBG_PS_BIT_STR_MODE_OVR_DEV
+#define MBG_PS_MSK_STR_MODE ( 1UL << MBG_PS_BIT_STR_MODE ) ///< see ::MBG_PS_BIT_STR_MODE
+#define MBG_PS_MSK_FLAGS_OVR_SW ( 1UL << MBG_PS_BIT_FLAGS_OVR_SW ) ///< see ::MBG_PS_BIT_FLAGS_OVR_SW
+#define MBG_PS_MSK_FLAGS ( 1UL << MBG_PS_BIT_FLAGS ) ///< see ::MBG_PS_BIT_FLAGS
+
+/** @} anchor MBG_COM_CFG_STATUS_MASKS */
@@ -2084,24 +3999,26 @@ enum MBG_COM_CFG_STATUS_BITS
*
* This structure should be sent to a device to configure
* a specific serial port. The number of supported ports
- * is RECEIVER_INFO::n_com_port.
+ * is ::RECEIVER_INFO::n_com_ports.
*
* @note The ::PORT_INFO_IDX structure should be read from
* a device to retrieve the current settings and capabilities.
*
- * @see STR_TYPE_INFO
+ * @see ::STR_TYPE_INFO
*/
typedef struct
{
- uint16_t idx; ///< port index, 0..RECEIVER_INFO::n_com_port - 1
+ uint16_t idx; ///< port index, 0..::RECEIVER_INFO::n_com_ports-1
PORT_SETTINGS port_settings;
+
} PORT_SETTINGS_IDX;
#define _mbg_swab_port_settings_idx( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->idx ); \
_mbg_swab_port_settings( &(_p)->port_settings ); \
-}
+} while ( 0 )
/**
@@ -2111,19 +4028,21 @@ typedef struct
* the current settings of a serial port plus its capabilities,
* e.g. supported baud rates, supported string formats, etc.
*
- * @see STR_TYPE_INFO
+ * @see ::STR_TYPE_INFO
*/
typedef struct
{
PORT_SETTINGS port_settings; ///< current configuration of the port
- uint32_t supp_baud_rates; ///< bit mask of baud rates supp. by this port, see ::MBG_BAUD_RATE_CODES
- uint32_t supp_framings; ///< bit mask of framings supp. by this port, see ::MBG_FRAMING_CODES
+ uint32_t supp_baud_rates; ///< bit mask of baud rates supp. by this port, see ::MBG_BAUD_RATE_MASKS
+ uint32_t supp_framings; ///< bit mask of framings supp. by this port, see ::MBG_FRAMING_MASKS
uint32_t supp_str_types; ///< bit mask of string types supp. by this port, i.e. bit 0 set if str_type[0] is supp.
uint32_t reserved; ///< reserved for future use, currently always 0
- uint32_t flags; ///< @see COM_CFG_STATUS_BITS
+ uint32_t flags; ///< see ::PORT_INFO_FLAGS
+
} PORT_INFO;
#define _mbg_swab_port_info( _p ) \
+do \
{ \
_mbg_swab_port_settings( &(_p)->port_settings ); \
_mbg_swab32( &(_p)->supp_baud_rates ); \
@@ -2131,20 +4050,32 @@ typedef struct
_mbg_swab32( &(_p)->supp_str_types ); \
_mbg_swab32( &(_p)->reserved ); \
_mbg_swab32( &(_p)->flags ); \
-}
+} while ( 0 )
/**
- * @brief Flags used with PORT_SETTINGS::flags and PORT_INFO::flags
+ * @brief Flags bits used to define ::PORT_INFO_FLAGS
+ *
+ * @see ::PORT_INFO_FLAGS
*/
-enum COM_CFG_STATUS_BITS
+enum PORT_INFO_FLAG_BITS
{
- PORT_FLAG_BIT_PORT_INVISIBLE, ///< port is used internally and should not be displayed by config apps
- N_PORT_FLAGS ///< the number of defined bits
+ PORT_INFO_FLAG_BIT_PORT_INVISIBLE, ///< port is used internally and should not be displayed by config apps
+ PORT_INFO_FLAG_BIT_BIN_PROT_HS, ///< port supports binary protocol at high speed, see ::MBG_DEFAULT_BAUDRATE_HS
+ N_PORT_INFO_FLAG_BITS ///< the number of defined bits
};
-#define PORT_FLAG_PORT_INVISIBLE ( 1UL << PORT_FLAG_BIT_PORT_INVISIBLE )
+/**
+ * @brief Bit masks used with ::PORT_INFO::flags
+ *
+ * @see ::PORT_INFO_FLAG_BITS
+ */
+enum PORT_INFO_FLAGS
+{
+ PORT_INFO_FLAG_PORT_INVISIBLE = ( 1UL << PORT_INFO_FLAG_BIT_PORT_INVISIBLE ), ///< see ::PORT_INFO_FLAG_BIT_PORT_INVISIBLE
+ PORT_INFO_FLAG_BIN_PROT_HS = ( 1UL << PORT_INFO_FLAG_BIT_BIN_PROT_HS ) ///< see ::PORT_INFO_FLAG_BIT_BIN_PROT_HS
+};
/**
@@ -2153,22 +4084,24 @@ enum COM_CFG_STATUS_BITS
* This structure should be read from the device to retrieve the
* current settings of a specific serial port plus its capabilities,
* e.g. supported baud rates, supported string formats, etc.
- * The number of supported ports is RECEIVER_INFO::n_com_port.
+ * The number of supported ports is ::RECEIVER_INFO::n_com_ports.
*
* @note The ::PORT_SETTINGS_IDX structure should be send back to
* the device to configure the specified serial port.
*/
typedef struct
{
- uint16_t idx; ///< port index, 0..RECEIVER_INFO::n_com_port - 1
+ uint16_t idx; ///< port index, 0..::RECEIVER_INFO::n_com_ports-1
PORT_INFO port_info;
+
} PORT_INFO_IDX;
#define _mbg_swab_port_info_idx( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->idx ); \
_mbg_swab_port_info( &(_p)->port_info ); \
-}
+} while ( 0 )
/**
@@ -2180,22 +4113,24 @@ typedef struct
* The number of string types, and which string types are supported
* depends on the device type and firmware version.
*
- * @note The structure ::STR_TYPE_INFO_IDX should be read repeatedly
+ * @note Multiple structures ::STR_TYPE_INFO_IDX should be read
* to retrieve all supported string types.
*/
typedef struct
{
- uint32_t supp_modes; ///< bit mask of modes supp. for this string type
+ uint32_t supp_modes; ///< bit mask of modes supp. for this string type, see ::STR_MODE_MASKS
char long_name[23]; ///< long name of the string format
char short_name[11]; ///< short name of the string format
uint16_t flags; ///< reserved, currently always 0
+
} STR_TYPE_INFO;
#define _mbg_swab_str_type_info( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->supp_modes ); \
_mbg_swab16( &(_p)->flags ); \
-}
+} while ( 0 )
@@ -2205,33 +4140,38 @@ typedef struct
* This structure should be read from a device to retrieve information
* on a specific supported time string type from an array of supported
* string types. The number of supported string types is returned
- * in RECEIVER_INFO::n_str_type.
+ * in ::RECEIVER_INFO::n_str_type.
*
- * A selected index number can be saved in PORT_SETTINGS::str_type to
+ * A selected index number can be saved in ::PORT_SETTINGS::str_type to
* configure the selected string type for the specific serial port.
*/
typedef struct
{
- uint16_t idx; ///< string type index, 0..RECEIVER_INFO::n_str_type - 1
+ uint16_t idx; ///< string type index, 0..::RECEIVER_INFO::n_str_type-1
STR_TYPE_INFO str_type_info;
+
} STR_TYPE_INFO_IDX;
#define _mbg_swab_str_type_info_idx( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->idx ); \
_mbg_swab_str_type_info( &(_p)->str_type_info ); \
-}
+} while ( 0 )
/**
- * @brief Modes supported for time string transmission
+ * @brief Enumeration of modes supported for time string transmission
*
* This determines e.g. at which point in time a string starts
* to be transmitted via the serial port.
+ * Used with ::PORT_SETTINGS::mode.
+ *
+ * @see ::STR_MODE_MASKS
*/
enum STR_MODES
{
- STR_ON_REQ, ///< transmission on request by received '?' only
+ STR_ON_REQ, ///< transmission on request by received '?' character only
STR_PER_SEC, ///< transmission automatically if second changes
STR_PER_MIN, ///< transmission automatically if minute changes
STR_AUTO, ///< transmission automatically if required, e.g. on capture event
@@ -2240,6 +4180,29 @@ enum STR_MODES
};
+/**
+ * @brief Bit masks associated with ::STR_MODES
+ *
+ * Used with ::STR_TYPE_INFO::supp_modes to indicate which
+ * transmission modes are supported by the particular string type.
+ *
+ * @see ::STR_MODES
+ */
+enum STR_MODE_MASKS
+{
+ MSK_STR_ON_REQ = ( 1UL << STR_ON_REQ ), ///< see ::STR_ON_REQ
+ MSK_STR_PER_SEC = ( 1UL << STR_PER_SEC ), ///< see ::STR_PER_SEC
+ MSK_STR_PER_MIN = ( 1UL << STR_PER_MIN ), ///< see ::STR_PER_MIN
+ MSK_STR_AUTO = ( 1UL << STR_AUTO ), ///< see ::STR_AUTO
+ MSK_STR_ON_REQ_SEC = ( 1UL << STR_ON_REQ_SEC ) ///< see ::STR_ON_REQ_SEC
+};
+
+
+/**
+ * @brief Initializer for short name strings associated with ::STR_MODES
+ *
+ * @see ::STR_MODES
+ */
#define DEFAULT_SHORT_MODE_NAMES \
{ \
"'?'", \
@@ -2250,9 +4213,12 @@ enum STR_MODES
}
-/*
- * Default initializers for English mode string names. Initializers
- * for multi-language strings can be found in pcpslstr.h.
+/**
+ * @brief Default initializers for English mode name strings
+ *
+ * Initializers for multi-language strings can be found in pcpslstr.h.
+ *
+ * @see ::STR_MODES
*/
#define ENG_MODE_NAME_STR_ON_REQ "on request '?' only"
#define ENG_MODE_NAME_STR_PER_SEC "per second"
@@ -2260,6 +4226,14 @@ enum STR_MODES
#define ENG_MODE_NAME_STR_AUTO "automatically"
#define ENG_MODE_NAME_STR_ON_REQ_SEC "sec after request"
+
+/**
+ * @brief Initializer for an English mode name string table
+ *
+ * Initializers for multi-language strings can be found in pcpslstr.h.
+ *
+ * @see ::STR_MODES
+ */
#define DEFAULT_ENG_MODE_NAMES \
{ \
ENG_MODE_NAME_STR_ON_REQ, \
@@ -2269,17 +4243,6 @@ enum STR_MODES
ENG_MODE_NAME_STR_ON_REQ_SEC \
}
-/*
- * The definitions below are used to set up bit masks
- * which restrict the modes which can be used with
- * a given string type:
- */
-#define MSK_STR_ON_REQ ( 1UL << STR_ON_REQ )
-#define MSK_STR_PER_SEC ( 1UL << STR_PER_SEC )
-#define MSK_STR_PER_MIN ( 1UL << STR_PER_MIN )
-#define MSK_STR_AUTO ( 1UL << STR_AUTO )
-#define MSK_STR_ON_REQ_SEC ( 1UL << STR_ON_REQ_SEC )
-
/*
* The modes below are supported by most string types:
@@ -2304,8 +4267,56 @@ enum STR_MODES
/**
+ * @brief The number of string types supported by legacy DCF77 receivers
+ *
+ * For receivers supporting a ::RECEIVER_INFO this should be determined
+ * from ::RECEIVER_INFO::n_str_type.
+ *
+ * @see ::DEFAULT_SUPP_STR_TYPES_DCF
+ */
+#define DEFAULT_N_STR_TYPE_DCF 1
+
+/**
+ * @brief Bit mask of string types supported by legacy DCF77 receivers
+ *
+ * For receivers supporting a ::RECEIVER_INFO this should be determined
+ * from ::PORT_INFO::supp_str_types.
+ *
+ * @see ::DEFAULT_N_STR_TYPE_DCF
+ */
+#define DEFAULT_SUPP_STR_TYPES_DCF \
+ ( ( 1UL << DEFAULT_N_STR_TYPE_DCF ) - 1 )
+
+
+
+/**
+ * @brief The number of string types supported by legacy GPS receivers
+ *
+ * For receivers supporting a ::RECEIVER_INFO this should be determined
+ * from ::RECEIVER_INFO::n_str_type.
+ *
+ * @see ::DEFAULT_SUPP_STR_TYPES_GPS
+ */
+#define DEFAULT_N_STR_TYPE_GPS 2
+
+/**
+ * @brief Bit mask of string types supported by legacy GPS receivers
+ *
+ * For receivers supporting a ::RECEIVER_INFO this should be determined
+ * from ::PORT_INFO::supp_str_types.
+ *
+ * @see ::DEFAULT_N_STR_TYPE_GPS
+ */
+#define DEFAULT_SUPP_STR_TYPES_GPS \
+ ( ( 1UL << DEFAULT_N_STR_TYPE_GPS ) - 1 )
+
+
+
+/*
* The number of serial ports which are at least available
- * even with very old GPS receiver models
+ * even with very old GPS receiver models. For devices providing
+ * a ::RECEIVER_INFO structure the number of provided COM ports
+ * is available in ::RECEIVER_INFO::n_com_ports.
*/
#define DEFAULT_N_COM 2
@@ -2318,18 +4329,20 @@ enum STR_MODES
#endif
/**
- * @brief A The structure used to store the configuration of both serial ports
+ * @brief A The structure used to store the configuration of two serial ports
*
* @deprecated This structure is deprecated, ::PORT_SETTINGS and related structures
* should be used instead, if supported by the device.
*/
typedef struct
{
- COM_PARM com[DEFAULT_N_COM]; /**< COM0 and COM1 settings */
- uint8_t mode[DEFAULT_N_COM]; /**< COM0 and COM1 output mode */
+ COM_PARM com[DEFAULT_N_COM]; ///< COM0 and COM1 settings
+ uint8_t mode[DEFAULT_N_COM]; ///< COM0 and COM1 output mode
+
} PORT_PARM;
#define _mbg_swab_port_parm( _p ) \
+do \
{ \
int i; \
for ( i = 0; i < DEFAULT_N_COM; i++ ) \
@@ -2337,13 +4350,17 @@ typedef struct
_mbg_swab_com_parm( &(_p)->com[i] ); \
/* no need to swap mode byte */ \
} \
-}
+} while ( 0 )
-/*
- * The codes below were used with the obsolete
- * PORT_PARM.mode above. They are defined for
- * compatibility with older devices only:
+/**
+ * @brief Deprecated codes for mode of operation
+ *
+ * @deprecated These codes have been used with the
+ * deprecated ::PORT_PARM::mode. They are only still
+ * defined for compatibility with older devices.
+ *
+ * @see ::STR_MODES
*/
enum
{
@@ -2359,76 +4376,133 @@ enum
/**
- @defgroup group_icode IRIG codes
-
- The following definitions are used to configure an optional
- on-board IRIG input or output. Which frame types are supported
- by a device depends on the device type, and may eventually
- depend on the device's firmware version.
-
- All IRIG frames transport the day-of-year number plus the time-of-day,
- and include a control field segment which can transport user defined
- information.
-
- Some newer IRIG frames are compatible with older frame types but support
- well defined extensions like the year number, local time offset, DST status,
- etc., in the control fields:
-
- - Supported IRIG signal code types:
- - \b A002: 1000 bps, DCLS, time-of-year
- - \b A003: 1000 bps, DCLS, time-of-year, SBS
- - \b A132: 1000 bps, 10 kHz carrier, time-of-year
- - \b A133: 1000 bps, 10 kHz carrier, time-of-year, SBS
- - \b B002: 100 bps, DCLS, time-of-year
- - \b B003: 100 bps, DCLS, time-of-year, SBS
- - \b B122: 100 bps, 1 kHz carrier, time-of-year
- - \b B123: 100 bps, 1 kHz carrier, time-of-year, SBS
- - \b B006: 100 bps, DCLS, complete date
- - \b B007: 100 bps, DCLS, complete date, SBS
- - \b B126: 100 bps, 1 kHz carrier, complete date
- - \b B127: 100 bps, 1 kHz carrier, complete date, SBS
- - \b B220/1344: 100 bps, DCLS, manchester encoded, IEEE1344 extensions
- - \b B222: 100 bps, DCLS, manchester encoded, time-of-year
- - \b B223: 100 bps, DCLS, manchester encoded, time-of-year, SBS
- - \b G002: 10 kbps, DCLS, time-of-year
- - \b G142: 10 kbps, 100 kHz carrier, time-of-year
- - \b G006: 10 kbps, DCLS, complete date
- - \b G146: 10 kbps, 100 kHz carrier, complete date
- - \b AFNOR: 100 bps, 1 kHz carrier, SBS, complete date
- - <b> AFNOR DC:</b> 100 bps, DCLS, SBS, complete date
- - \b IEEE1344: 100 bps, 1 kHz carrier, time-of-year, SBS, IEEE1344 extensions (B120)
- - <b> IEEE1344 DC:</b> 100 bps, DCLS, time-of-year, SBS, IEEE1344 extensions (B000)
- - \b C37.118: like IEEE1344, but %UTC offset with reversed sign
- - \b C37.118 DC: like IEEE1344 DC, but %UTC offset with reversed sign
-
- - time-of-year: day-of-year, hours, minutes, seconds
- - complete date: time-of-year plus year number
- - SBS: straight binary seconds, second-of-day
-
- AFNOR codes are based on the french standard AFNOR NF S87-500
-
- IEEE1344 codes are defined in IEEE standard 1344-1995. The code frame is compatible
- with B002/B122 but provides some well defined extensions in the control field which
- include a quality indicator (time figure of merit, TFOM), year number, DST and leap
- second status, and local time offset from %UTC.
-
- C37.118 codes are defined in IEEE standard C37.118-2005 which includes a revised version
- of the IEEE 1344 standard from 1995. These codes provide the same extensions as IEEE 1344
- but unfortunately define the %UTC offset with reversed sign.
-
- @note There are 3rd party IRIG devices out there which apply the %UTC offset as specified
- in C37.118, but claim to be compatible with IEEE 1344. So if local time is transmitted
- by the IRIG signal then care must be taken that the %UTC offset is evaluated by the IRIG
- receiver in the same way as computed by the IRIG generator. Otherwise the %UTC
- time computed by the receiver may be <b>wrong</b>.
- @{
- */
+ * @defgroup group_icode IRIG time codes
+ *
+ * The following definitions are used to configure an optional
+ * on-board IRIG input or output. Which frame types are supported
+ * by a device depends on the device type, and may eventually
+ * depend on the device's firmware version.
+ *
+ * All IRIG frames transport the day-of-year number plus the time-of-day,
+ * and include a control field segment which can transport user defined
+ * information.
+ *
+ * Some newer IRIG frames are compatible with older frame types but support
+ * well defined extensions like the year number, local time offset, DST status,
+ * etc., in the control fields:
+ *
+ * The following specification can be found in IRIG Standard 200-04 (September 2004):
+ *
+ * Format A: 1k pps
+ * Format B: 100 pps
+ * Format D: 1 ppm
+ * Format E: 10 pps
+ * Format G: 10k pps
+ * Format H: 1 pps
+ *
+ * 1st digit: Modulation Frequency
+ * 0 Pulse width code
+ * 1 Sine wave, amplitude modulated
+ * 2 Manchester modulated
+ *
+ * 2nd digit: Frequency / Resolution
+ * 0: No carrier / index count interval
+ * 1: 100 Hz / 10 ms
+ * 2: 1 kHz / 1 ms
+ * 3: 10 kHz / 0.1 ms
+ * 4: 100 kHz / 10 ms
+ * 5: 1 MHz / 1 ms
+ *
+ * 3rd digit: Coded expressions
+ * 0: DOY+TOD, CF, SBS
+ * 1: DOY+TOD, CF
+ * 2: DOY+TOD
+ * 3: DOY+TOD, SBS
+ * 4: DOY+TOD, Year, CF, SBS
+ * 5: DOY+TOD, Year, CF
+ * 6: DOY+TOD, Year
+ * 7: DOY+TOD, Year, SBS
+ *
+ *
+ * Table of Permissible Code Formats
+ *
+ * Letter 1st digit 2nd digit 3rd digit
+ * ----------------------------------------------
+ * A 0,1,2 0,3,4,5 0,1,2,3,4,5,6,7
+ * B 0,1,2 0,2,3,4,5 0,1,2,3,4,5,6,7
+ * D 0,1 0,1,2 1,2
+ * E 0,1 0,1,2 1,2,5,6
+ * G 0,1,2 0,4,5 1,2,5,6
+ * H 0,1 0,1,2 1,2
+ *
+ * - Known IRIG signal code types:
+ * - \b A002: 1000 bps, DCLS, time-of-year
+ * - \b A003: 1000 bps, DCLS, time-of-year, SBS
+ * - \b A132: 1000 bps, 10 kHz carrier, time-of-year
+ * - \b A133: 1000 bps, 10 kHz carrier, time-of-year, SBS
+ * - \b B002: 100 bps, DCLS, time-of-year
+ * - \b B003: 100 bps, DCLS, time-of-year, SBS
+ * - \b B122: 100 bps, 1 kHz carrier, time-of-year
+ * - \b B123: 100 bps, 1 kHz carrier, time-of-year, SBS
+ * - \b B006: 100 bps, DCLS, complete date
+ * - \b B007: 100 bps, DCLS, complete date, SBS
+ * - \b B126: 100 bps, 1 kHz carrier, complete date
+ * - \b B127: 100 bps, 1 kHz carrier, complete date, SBS
+ * - \b B220/1344: 100 bps, DCLS, manchester encoded, IEEE1344 extensions
+ * - \b B222: 100 bps, DCLS, manchester encoded, time-of-year
+ * - \b B223: 100 bps, DCLS, manchester encoded, time-of-year, SBS
+ * - \b G002: 10 kbps, DCLS, time-of-year
+ * - \b G142: 10 kbps, 100 kHz carrier, time-of-year
+ * - \b G006: 10 kbps, DCLS, complete date
+ * - \b G146: 10 kbps, 100 kHz carrier, complete date
+ * - \b AFNOR: 100 bps, 1 kHz carrier, SBS, complete date
+ * - \b AFNOR DC: 100 bps, DCLS, SBS, complete date
+ * - \b IEEE1344: 100 bps, 1 kHz carrier, time-of-year, SBS, IEEE 1344 extensions (B120)
+ * - \b IEEE1344 DC: 100 bps, DCLS, time-of-year, SBS, IEEE 1344 extensions (B000)
+ * - \b C37.118: like IEEE 1344, but %UTC offset applied with reversed sign
+ * - \b C37.118 DC: like IEEE 1344 DC, but %UTC offset applied with reversed sign
+ *
+ * - time-of-year: day-of-year, hours, minutes, seconds
+ * - complete date: time-of-year plus year number
+ * - SBS: straight binary seconds, second-of-day
+ *
+ * AFNOR codes are based on the french standard AFNOR NF S87-500
+ *
+ * IEEE 1344 codes are defined in IEEE standard 1344-1995. The code frame is compatible
+ * with B002/B122 but provides some well defined extensions in the control field which
+ * include a quality indicator (time figure of merit, TFOM), year number, DST and leap
+ * second status, and local time offset from %UTC.
+ *
+ * IEEE C37.118 codes are defined in IEEE standard C37.118-2005 which includes a revised version
+ * of the IEEE 1344 standard from 1995. These codes provide the same extensions as IEEE 1344
+ * but unfortunately determine that the %UTC offset has to be applied with reversed sign.
+ *
+ * For example, if a -6 hours UTC offset is transmitted in the time code:<br>
+ * IEEE 1344: (IRIG time 14:43:27 h) - (offs -6 h) = (UTC 20:43:27)<br>
+ * IEEE C37.118: (IRIG time 14:43:27 h) + (offs -6 h) = (UTC 08:43:27)<br>
+ *
+ * @see @ref MSK_ICODE_RX_UTC_OFFS_ADD and @ref MSK_ICODE_RX_UTC_OFFS_SUB
+ *
+ * @note There are 3rd party IRIG devices out there which apply the %UTC offset as specified
+ * in IEEE C37.118-2005, but claim to be compatible with IEEE 1344. So if local time is transmitted
+ * by the timecode then care must be taken that the %UTC offset is evaluated by the timecode
+ * receiver in the same way as computed by the timecode generator. Otherwise the %UTC
+ * time computed by the receiver may be <b>wrong</b>.
+ *
+ * @{ */
/**
* @brief Known IRIG TX code formats
*
- * Definitions used with IRIG transmitters which usually output both
- * the unmodulated and the modulated IRIG signals at the same time.
+ * Used with ::IRIG_SETTINGS::icode for IRIG transmitters.
+ * For IRIG receivers see ::ICODE_RX_CODES.
+ *
+ * Meinberg timecode transmitters always generate the unmodulated (DCLS)
+ * and usually the modulated timecode signals internally at the same time,
+ * so the code definitions always refer to both.
+ *
+ * @note Not all device may provide both the modulated and unmodulated
+ * signal externally.
*/
enum ICODE_TX_CODES
{
@@ -2449,89 +4523,111 @@ enum ICODE_TX_CODES
ICODE_TX_TXC101,
ICODE_TX_E002_E112,
ICODE_TX_NASA36,
+ ICODE_TX_A006_A136,
+ ICODE_TX_A007_A137,
N_ICODE_TX ///< number of known codes
};
/**
- * Initializers for format name strings.
+ * @brief Initializers for TX timecode format name strings
+ *
+ * @see ::ICODE_TX_CODES
*/
-#define DEFAULT_ICODE_TX_NAMES \
-{ \
- "B002+B122", \
- "B003+B123", \
- "A002+A132", \
- "A003+A133", \
- "AFNOR NF S87-500", \
- "IEEE1344", \
- "B220(1344) DCLS", \
- "B222 DCLS", \
- "B223 DCLS", \
- "B006+B126", \
- "B007+B127", \
- "G002+G142", \
- "G006+G146", \
- "C37.118", \
- "TXC-101 DTR-6", \
- "E002+E112", \
- "NASA 36" \
-}
-
-/**
- * Initializers for short name strings which must not
- * be longer than 10 printable characters.
+#define DEFAULT_ICODE_TX_NAMES \
+{ \
+ /* B002_B122 */ "B002+B122", \
+ /* B003_B123 */ "B003+B123", \
+ /* A002_A132 */ "A002+A132", \
+ /* A003_A133 */ "A003+A133", \
+ /* AFNOR */ "AFNOR NF S87-500", \
+ /* IEEE1344 */ "IEEE 1344", \
+ /* B2201344 */ "B220(1344) DCLS", \
+ /* B222 */ "B222 DCLS", \
+ /* B223 */ "B223 DCLS", \
+ /* B006_B126 */ "B006+B126", \
+ /* B007_B127 */ "B007+B127", \
+ /* G002_G142 */ "G002+G142", \
+ /* G006_G146 */ "G006+G146", \
+ /* C37118 */ "IEEE C37.118", \
+ /* TXC101 */ "TXC-101 DTR-6", \
+ /* E002_E112 */ "E002+E112", \
+ /* NASA36 */ "NASA 36", \
+ /* A006_A136 */ "A006+A136", \
+ /* A007_A137 */ "A007+A137" \
+}
+
+/**
+ * @brief Initializers for short TX timecode format name strings
+ *
+ * @note Must not be longer than 10 printable characters
+ *
+ * @see ::ICODE_TX_CODES
*/
#define DEFAULT_ICODE_TX_NAMES_SHORT \
{ \
- "B002+B122", \
- "B003+B123", \
- "A002+A132", \
- "A003+A133", \
- "AFNOR NF-S", \
- "IEEE1344", \
- "B220/1344", \
- "B222 DC", \
- "B223 DC", \
- "B006+B126", \
- "B007+B127", \
- "G002+G142", \
- "G006+G146", \
- "C37.118", \
- "TXC-101", \
- "E002+E112", \
- "NASA 36" \
-}
-
-
-/**
- * Initializers for English format description strings.
- */
-#define DEFAULT_ICODE_TX_DESCRIPTIONS_ENG \
-{ \
- "100 bps, DCLS or 1 kHz carrier", \
- "100 bps, DCLS or 1 kHz carrier, SBS", \
- "1000 bps, DCLS or 10 kHz carrier", \
- "1000 bps, DCLS or 10 kHz carrier, SBS", \
- "100 bps, DCLS or 1 kHz carrier, SBS, complete date", \
- "100 bps, DCLS or 1 kHz carrier, SBS, complete date, time zone info", \
- "100 bps, Manchester enc., DCLS only, SBS, complete date, time zone info", \
- "100 bps, Manchester enc., DCLS only", \
- "100 bps, Manchester enc., DCLS only, SBS", \
- "100 bps, DCLS or 1 kHz carrier, complete date", \
- "100 bps, DCLS or 1 kHz carrier, complete date, SBS", \
- "10 kbps, DCLS or 100 kHz carrier", \
- "10 kbps, DCLS or 100 kHz carrier, complete date", \
- "like IEEE1344, but UTC offset with reversed sign", \
- "code from TV time sync device TXC-101 DTR-6", \
- "10 bps, DCLS or 100 Hz carrier", \
- "100 bps, DCLS or 1 kHz carrier" \
+ /* B002_B122 */ "B002+B122", \
+ /* B003_B123 */ "B003+B123", \
+ /* A002_A132 */ "A002+A132", \
+ /* A003_A133 */ "A003+A133", \
+ /* AFNOR */ "AFNOR NF S", \
+ /* IEEE1344 */ "IEEE 1344", \
+ /* B2201344 */ "B220/1344", \
+ /* B222 */ "B222 DC", \
+ /* B223 */ "B223 DC", \
+ /* B006_B126 */ "B006+B126", \
+ /* B007_B127 */ "B007+B127", \
+ /* G002_G142 */ "G002+G142", \
+ /* G006_G146 */ "G006+G146", \
+ /* C37118 */ "C37.118", \
+ /* TXC101 */ "TXC-101", \
+ /* E002_E112 */ "E002+E112", \
+ /* NASA36 */ "NASA 36", \
+ /* A006_A136 */ "A006+A136", \
+ /* A007_A137 */ "A007+A137" \
}
-/*
- * The definitions below are used to set up bit masks
- * which restrict the IRIG formats which are supported
- * by a given IRIG transmitter device:
- */
+
+/**
+ * @brief Initializers for English TX format description strings
+ *
+ * @see ::ICODE_TX_CODES
+ */
+#define DEFAULT_ICODE_TX_DESCRIPTIONS_ENG \
+{ \
+ /* B002_B122 */ "100 bps, DCLS or 1 kHz carrier", \
+ /* B003_B123 */ "100 bps, DCLS or 1 kHz carrier, SBS", \
+ /* A002_A132 */ "1000 bps, DCLS or 10 kHz carrier", \
+ /* A003_A133 */ "1000 bps, DCLS or 10 kHz carrier, SBS", \
+ /* AFNOR */ "100 bps, DCLS or 1 kHz carrier, complete date, SBS", \
+ /* IEEE1344 */ "100 bps, DCLS or 1 kHz carrier, 2 digit year number, SBS, UTC offset, DST and Leap sec status", \
+ /* B2201344 */ "100 bps, Manchester enc., DCLS only, 2 digit year number, SBS, UTC offset, DST and Leap sec status", \
+ /* B222 */ "100 bps, Manchester enc., DCLS only", \
+ /* B223 */ "100 bps, Manchester enc., DCLS only, SBS", \
+ /* B006_B126 */ "100 bps, DCLS or 1 kHz carrier, 2 digit year number", \
+ /* B007_B127 */ "100 bps, DCLS or 1 kHz carrier, 2 digit year number, SBS", \
+ /* G002_G142 */ "10 kbps, DCLS or 100 kHz carrier", \
+ /* G006_G146 */ "10 kbps, DCLS or 100 kHz carrier, 2 digit year number", \
+ /* C37118 */ "100 bps, DCLS or 1 kHz carrier, 2 digit year number, SBS, UTC offs. reverse to 1344, DST/Leap sec status", \
+ /* TXC101 */ "code from TV time sync device TXC-101 DTR-6", \
+ /* E002_E112 */ "10 bps, DCLS or 100 Hz carrier", \
+ /* NASA36 */ "100 bps, DCLS or 1 kHz carrier", \
+ /* A006_A136 */ "1000 bps, DCLS or 10 kHz carrier, 2 digit year number", \
+ /* A007_A137 */ "1000 bps, DCLS or 10 kHz carrier, 2 digit year number, SBS" \
+}
+
+
+/**
+ * @brief Bit masks used with ::IRIG_INFO::supp_codes for TX
+ *
+ * These bit masks are used with timecode receivers only
+ *
+ * @see @ref ICODE_TX_CODES
+ * @see @ref ICODE_RX_CODES
+ * @see @ref ICODE_RX_MASKS
+ *
+ * @anchor ICODE_TX_MASKS @{ */
+
#define MSK_ICODE_TX_B002_B122 ( 1UL << ICODE_TX_B002_B122 )
#define MSK_ICODE_TX_B003_B123 ( 1UL << ICODE_TX_B003_B123 )
#define MSK_ICODE_TX_A002_A132 ( 1UL << ICODE_TX_A002_A132 )
@@ -2549,19 +4645,24 @@ enum ICODE_TX_CODES
#define MSK_ICODE_TX_TXC101 ( 1UL << ICODE_TX_TXC101 )
#define MSK_ICODE_TX_E002_E112 ( 1UL << ICODE_TX_E002_E112 )
#define MSK_ICODE_TX_NASA36 ( 1UL << ICODE_TX_NASA36 )
+#define MSK_ICODE_TX_A006_A136 ( 1UL << ICODE_TX_A006_A136 )
+#define MSK_ICODE_TX_A007_A137 ( 1UL << ICODE_TX_A007_A137 )
+
+/** @} anchor ICODE_TX_MASKS */
+
/**
- * A mask of IRIG formats with manchester encoded DC output:
+ * @brief A mask of IRIG TX formats with manchester encoded DC output
*/
#define MSK_ICODE_TX_DC_MANCH \
( \
- MSK_ICODE_TX_B2201344 | \
- MSK_ICODE_TX_B222 | \
+ MSK_ICODE_TX_B2201344 | \
+ MSK_ICODE_TX_B222 | \
MSK_ICODE_TX_B223 \
)
/**
- * A mask of IRIG formats with 100 Hz carrier:
+ * @brief A mask of IRIG TX formats with 100 Hz carrier
*/
#define MSK_ICODE_TX_100HZ \
( \
@@ -2569,7 +4670,7 @@ enum ICODE_TX_CODES
)
/**
- * A mask of IRIG formats with 1 kHz carrier:
+ * @brief A mask of IRIG TX formats with 1 kHz carrier
*/
#define MSK_ICODE_TX_1KHZ \
( \
@@ -2587,25 +4688,27 @@ enum ICODE_TX_CODES
)
/**
- * A mask of IRIG formats with 10 kHz carrier:
+ * @brief A mask of IRIG TX formats with 10 kHz carrier
*/
#define MSK_ICODE_TX_10KHZ \
( \
MSK_ICODE_TX_A002_A132 | \
- MSK_ICODE_TX_A003_A133 \
+ MSK_ICODE_TX_A003_A133 | \
+ MSK_ICODE_TX_A006_A136 | \
+ MSK_ICODE_TX_A007_A137 \
)
/**
- * A mask of IRIG formats with 100 kHz carrier:
+ * @brief A mask of IRIG TX formats with 100 kHz carrier
*/
#define MSK_ICODE_TX_100KHZ \
( \
- MSK_ICODE_TX_G002_G142 | \
+ MSK_ICODE_TX_G002_G142 | \
MSK_ICODE_TX_G006_G146 \
)
/**
- * A mask of IRIG formats with 10 bps data rate:
+ * @brief A mask of IRIG TX formats with 10 bps data rate
*/
#define MSK_ICODE_TX_10BPS \
( \
@@ -2613,58 +4716,164 @@ enum ICODE_TX_CODES
)
/**
- * A mask of IRIG formats with 100 bps data rate:
+ * @brief A mask of IRIG TX formats with 100 bps data rate
*/
#define MSK_ICODE_TX_100BPS \
( \
- MSK_ICODE_TX_B002_B122 | \
- MSK_ICODE_TX_B003_B123 | \
- MSK_ICODE_TX_AFNOR | \
- MSK_ICODE_TX_IEEE1344 | \
- MSK_ICODE_TX_B006_B126 | \
- MSK_ICODE_TX_B007_B127 | \
+ MSK_ICODE_TX_B002_B122 | \
+ MSK_ICODE_TX_B003_B123 | \
+ MSK_ICODE_TX_AFNOR | \
+ MSK_ICODE_TX_IEEE1344 | \
+ MSK_ICODE_TX_B006_B126 | \
+ MSK_ICODE_TX_B007_B127 | \
MSK_ICODE_TX_C37118 \
)
/**
- * A mask of IRIG formats with 1000 bps data rate:
+ * @brief A mask of IRIG TX formats with 1000 bps data rate
*/
#define MSK_ICODE_TX_1000BPS \
( \
- MSK_ICODE_TX_A002_A132 | \
- MSK_ICODE_TX_A003_A133 \
+ MSK_ICODE_TX_A002_A132 | \
+ MSK_ICODE_TX_A003_A133 | \
+ MSK_ICODE_TX_A006_A136 | \
+ MSK_ICODE_TX_A007_A137 \
)
/**
- * A mask of IRIG formats with 10 kbps data rate:
+ * @brief A mask of IRIG TX formats with 10 kbps data rate
*/
#define MSK_ICODE_TX_10000BPS \
( \
- MSK_ICODE_TX_G002_G142 | \
+ MSK_ICODE_TX_G002_G142 | \
MSK_ICODE_TX_G006_G146 \
)
/**
- * A mask of IRIG formats which support TFOM:
+ * @brief A mask of IRIG TX formats supporting 10ths of seconds
+ */
+#define MSK_ICODE_TX_HAS_SEC10THS \
+( \
+ MSK_ICODE_TX_A002_A132 | \
+ MSK_ICODE_TX_A003_A133 | \
+ MSK_ICODE_TX_G002_G142 | \
+ MSK_ICODE_TX_G006_G146 | \
+ MSK_ICODE_TX_A006_A136 | \
+ MSK_ICODE_TX_A007_A137 \
+)
+
+/**
+ * @brief A mask of IRIG TX formats supporting 100ths of seconds
+ */
+#define MSK_ICODE_TX_HAS_SEC100THS \
+( \
+ MSK_ICODE_TX_G002_G142 | \
+ MSK_ICODE_TX_G006_G146 \
+)
+
+/**
+ * @brief A mask of IRIG TX formats supporting a 2 digit year number
+ */
+#define MSK_ICODE_TX_HAS_SHORT_YEAR \
+( \
+ MSK_ICODE_TX_AFNOR | \
+ MSK_ICODE_TX_IEEE1344 | \
+ MSK_ICODE_TX_B2201344 | \
+ MSK_ICODE_TX_B006_B126 | \
+ MSK_ICODE_TX_B007_B127 | \
+ MSK_ICODE_TX_G006_G146 | \
+ MSK_ICODE_TX_C37118 | \
+ MSK_ICODE_TX_A006_A136 | \
+ MSK_ICODE_TX_A007_A137 \
+)
+
+/**
+ * @brief A mask of IRIG TX formats supporting a 2 digit year number
+ *
+ * This is after the P6 identifier.
+ */
+ #define MSK_ICODE_TX_HAS_SHORT_YEAR_AFTER_P6 \
+( \
+ MSK_ICODE_TX_G006_G146 \
+)
+
+/**
+ * @brief A mask of IRIG TX formats supporting TFOM
*/
#define MSK_ICODE_TX_HAS_TFOM \
( \
- MSK_ICODE_TX_IEEE1344 | \
+ MSK_ICODE_TX_IEEE1344 | \
MSK_ICODE_TX_C37118 \
)
/**
- * A mask of IRIG formats which support time zone information:
+ * @brief A mask of IRIG TX formats supporting CTQ continuous time quality
+ *
+ * This has been introduced in IEEE C37.118.1-2011
+ */
+#define MSK_ICODE_TX_HAS_CTQ \
+( \
+ MSK_ICODE_TX_IEEE1344 | \
+ MSK_ICODE_TX_C37118 \
+)
+
+/**
+ * @brief A mask of IRIG TX formats supporting time zone information
*/
#define MSK_ICODE_TX_HAS_TZI \
( \
- MSK_ICODE_TX_IEEE1344 | \
+ MSK_ICODE_TX_IEEE1344 | \
MSK_ICODE_TX_C37118 \
)
/**
- * The default mask of IRIG formats supported by
- * IRIG transmitters:
+ * @brief IRIG TX formats where UTC offset must be subtracted to yield UTC
+ *
+ * A mask of IRIG formats where the decoded UTC offset must be
+ * subtracted from the time decoded from the IRIG signal to yield UTC, e.g.:<br>
+ * (IRIG time 14:43:27 h) - (offs -6 h) = (UTC 20:43:27)
+ */
+#define MSK_ICODE_TX_UTC_OFFS_SUB \
+( \
+ MSK_ICODE_TX_IEEE1344 \
+)
+
+/**
+ * @brief IRIG TX formats where UTC offset must be added to yield UTC
+ *
+ * A mask of IRIG formats where the decoded UTC offset must be
+ * added to the time decoded from the IRIG signal to yield UTC, e.g.:<br>
+ * (IRIG time 14:43:27 h) + (offs -6 h) = (UTC 08:43:27)
+ */
+#define MSK_ICODE_TX_UTC_OFFS_ADD \
+( \
+ MSK_ICODE_TX_C37118 \
+)
+
+/**
+ * @brief A mask of IRIG TX formats supporting a day of week number
+ */
+#define MSK_ICODE_TX_HAS_AFNOR_WDAY \
+( \
+ MSK_ICODE_TX_AFNOR | \
+ MSK_ICODE_TX_AFNOR_DC \
+)
+
+/**
+ * @brief A mask of IRIG TX formats supporting a date (day-of-month, month)
+ */
+#define MSK_ICODE_TX_HAS_AFNOR_DATE \
+( \
+ MSK_ICODE_TX_AFNOR | \
+ MSK_ICODE_TX_AFNOR_DC \
+)
+
+
+/**
+ * @brief The default mask of IRIG TX formats supported by IRIG transmitters
+ *
+ * @note The formats which are actually supported should be retrieved
+ * from the device
*/
#if !defined( SUPP_MSK_ICODE_TX )
#define SUPP_MSK_ICODE_TX \
@@ -2682,9 +4891,14 @@ enum ICODE_TX_CODES
/**
* @brief Known IRIG RX code formats
*
- * Definitions used with IRIG receivers which decode
- * two similar IRIG codes (with or without SBS)
- * at the same time.
+ * Used with ::IRIG_SETTINGS::icode for IRIG receivers.
+ * For IRIG transmitters see ::ICODE_TX_CODES.
+ *
+ * The SBS value is redundant and can easily by computed
+ * from the time-of-day, so Meinberg time code receivers
+ * usually don't evaluate the SBS field anyway, and thus
+ * it makes no difference if a code with or withour SBS
+ * is supplied.
*/
enum ICODE_RX_CODES
{
@@ -2698,8 +4912,8 @@ enum ICODE_RX_CODES
ICODE_RX_IEEE1344_DC, ///< DCLS
ICODE_RX_B126_B127, ///< modulated
ICODE_RX_B006_B007, ///< DCLS
- ICODE_RX_G142_G146, ///< modulated
- ICODE_RX_G002_G006, ///< DCLS
+ ICODE_RX_G142, ///< modulated (G143 is undefined, SBS not supported with Gxxx)
+ ICODE_RX_G002, ///< DCLS (G003 is undefined, SBS not supported with Gxxx)
ICODE_RX_C37118, ///< modulated
ICODE_RX_C37118_DC, ///< DCLS
ICODE_RX_TXC101, ///< modulated
@@ -2708,95 +4922,126 @@ enum ICODE_RX_CODES
ICODE_RX_E002, ///< DCLS
ICODE_RX_NASA36, ///< modulated
ICODE_RX_NASA36_DC, ///< DCLS
+ ICODE_RX_A136_A137, ///< modulated
+ ICODE_RX_A006_A007, ///< DCLS
+ ICODE_RX_G146, ///< modulated (G147 is undefined, SBS not supported with Gxxx)
+ ICODE_RX_G006, ///< DCLS (G007 is undefined, SBS not supported with Gxxx)
N_ICODE_RX ///< the number of known codes
};
/**
- * Initializers for format name strings.
+ * @brief Initializers for RX timecode format name strings
+ *
+ * @see ::ICODE_RX_CODES
*/
#define DEFAULT_ICODE_RX_NAMES \
{ \
- "B122/B123", \
- "A132/A133", \
- "B002/B003 (DCLS)", \
- "A002/A003 (DCLS)", \
- "AFNOR NF S87-500", \
- "AFNOR NF S87-500 (DCLS)", \
- "IEEE1344", \
- "IEEE1344 (DCLS)", \
- "B126/B127", \
- "B006/B007 (DCLS)", \
- "G142/G146", \
- "G002/G006 (DCLS)", \
- "C37.118", \
- "C37.118 (DCLS)", \
- "TXC-101 DTR-6", \
- "TXC-101 DTR-6 (DCLS)", \
- "E112", \
- "E002 (DCLS)", \
- "NASA-36", \
- "NASA-36 (DCLS)" \
-}
-
-/**
- * Initializers for short name strings which must not
- * be longer than 11 printable characters.
- */
-#define DEFAULT_ICODE_RX_NAMES_SHORT \
-{ \
- "B122/B123", \
- "A132/A133", \
- "B002/B003", \
- "A002/A003", \
- "AFNOR NF-S", \
- "AFNOR DC", \
- "IEEE1344", \
- "IEEE1344 DC", \
- "B126/B127", \
- "B006/B007", \
- "G142/G146", \
- "G002/G006", \
- "C37.118", \
- "C37.118 DC", \
- "TXC-101", \
- "TXC-101 DC", \
- "E112", \
- "E002 DC", \
- "NASA-36", \
- "NASA-36 DC" \
-}
-
-
-/**
- * Initializers for English format description strings.
- */
-#define DEFAULT_ICODE_RX_DESCRIPTIONS_ENG \
-{ \
- "100 bps, 1 kHz carrier, SBS optionally", \
- "1000 bps, 10 kHz carrier, SBS optionally", \
- "100 bps, DCLS, SBS optionally", \
- "1000 bps, DCLS, SBS optionally", \
- "100 bps, 1 kHz carrier, SBS, complete date", \
- "100 bps, DCLS, SBS, complete date", \
- "100 bps, 1 kHz carrier, SBS, time zone info", \
- "100 bps, DCLS, SBS, time zone info", \
- "100 bps, 1 kHz carrier, complete date, SBS optionally", \
- "100 bps, DCLS, complete date, SBS optionally", \
- "10 kbps, 100 kHz carrier, complete date optionally", \
- "10 kbps, DCLS, complete date optionally", \
- "like IEEE1344, but UTC offset with reversed sign", \
- "like IEEE1344 DC, but UTC offset with reversed sign", \
- "code from TV time sync device TXC-101 DTR-6", \
- "DC code from TV time sync device TXC-101 DTR-6", \
- "10 bps, 100 Hz carrier", \
- "10 bps, DCLS", \
- "100 bps, 1 kHz carrier", \
- "100 bps, DCLS" \
+ /* B122_B123 */ "B122/B123", \
+ /* A132_A133 */ "A132/A133", \
+ /* B002_B003 */ "B002/B003 (DCLS)", \
+ /* A002_A003 */ "A002/A003 (DCLS)", \
+ /* AFNOR */ "AFNOR NF S87-500", \
+ /* AFNOR_DC */ "AFNOR NF S87-500 (DCLS)", \
+ /* IEEE1344 */ "IEEE1344", \
+ /* IEEE1344_DC */ "IEEE1344 (DCLS)", \
+ /* B126_B127 */ "B126/B127", \
+ /* B006_B007 */ "B006/B007 (DCLS)", \
+ /* G142 */ "G142", \
+ /* G002 */ "G002 (DCLS)", \
+ /* C37118 */ "C37.118", \
+ /* C37118_DC */ "C37.118 (DCLS)", \
+ /* TXC101 */ "TXC-101 DTR-6", \
+ /* TXC101_DC */ "TXC-101 DTR-6 (DCLS)", \
+ /* E112 */ "E112", \
+ /* E002 */ "E002 (DCLS)", \
+ /* NASA36 */ "NASA-36", \
+ /* NASA36_DC */ "NASA-36 (DCLS)", \
+ /* A136_A137 */ "A136/A137", \
+ /* A006_A007 */ "A006/A007 (DCLS)", \
+ /* G146 */ "G146", \
+ /* G006 */ "G006 (DCLS)" \
}
-/*
- * Bit masks corresponding to the enumeration above:
+/**
+ * @brief Initializers for short RX timecode format name strings
+ *
+ * @note Must not be longer than 11 printable characters
+ *
+ * @see ::ICODE_RX_CODES
*/
+#define DEFAULT_ICODE_RX_NAMES_SHORT \
+{ \
+ /* B122_B123 */ "B122/B123", \
+ /* A132_A133 */ "A132/A133", \
+ /* B002_B003 */ "B002/B003", \
+ /* A002_A003 */ "A002/A003", \
+ /* AFNOR */ "AFNOR NF S", \
+ /* AFNOR_DC */ "AFNOR DC", \
+ /* IEEE1344 */ "IEEE1344", \
+ /* IEEE1344_DC */ "IEEE1344 DC", \
+ /* B126_B127 */ "B126/B127", \
+ /* B006_B007 */ "B006/B007", \
+ /* G142 */ "G142", \
+ /* G002 */ "G002 DC", \
+ /* C37118 */ "C37.118", \
+ /* C37118_DC */ "C37.118 DC", \
+ /* TXC101 */ "TXC-101", \
+ /* TXC101_DC */ "TXC-101 DC", \
+ /* E112 */ "E112", \
+ /* E002 */ "E002 DC", \
+ /* NASA36 */ "NASA-36", \
+ /* NASA36_DC */ "NASA-36 DC", \
+ /* A136_A137 */ "A136/A137", \
+ /* A006_A007 */ "A006/A007", \
+ /* G146 */ "G146", \
+ /* G006 */ "G006 DC" \
+}
+
+
+/**
+ * @brief Initializers for English RX format description strings
+ *
+ * @see ::ICODE_RX_CODES
+ */
+#define DEFAULT_ICODE_RX_DESCRIPTIONS_ENG \
+{ \
+ /* B122_B123 */ "100 bps, 1 kHz carrier, SBS optionally", \
+ /* A132_A133 */ "1000 bps, 10 kHz carrier, SBS optionally", \
+ /* B002_B003 */ "100 bps, DCLS, SBS optionally", \
+ /* A002_A003 */ "1000 bps, DCLS, SBS optionally", \
+ /* AFNOR */ "100 bps, 1 kHz carrier, complete date, SBS", \
+ /* AFNOR_DC */ "100 bps, DCLS, complete date, SBS", \
+ /* IEEE1344 */ "100 bps, 1 kHz carrier, SBS, time zone info", \
+ /* IEEE1344_DC */ "100 bps, DCLS, SBS, time zone info", \
+ /* B126_B127 */ "100 bps, 1 kHz carrier, 2 digit year number, SBS optionally", \
+ /* B006_B007 */ "100 bps, DCLS, 2 digit year number, SBS optionally", \
+ /* G142 */ "10 kbps, 100 kHz carrier", \
+ /* G002 */ "10 kbps, DCLS", \
+ /* C37118 */ "like IEEE1344, but UTC offset with reversed sign", \
+ /* C37118_DC */ "like IEEE1344 DC, but UTC offset with reversed sign", \
+ /* TXC101 */ "code from TV time sync device TXC-101 DTR-6", \
+ /* TXC101_DC */ "DC code from TV time sync device TXC-101 DTR-6", \
+ /* E112 */ "10 bps, 100 Hz carrier", \
+ /* E002 */ "10 bps, DCLS", \
+ /* NASA36 */ "100 bps, 1 kHz carrier", \
+ /* NASA36_DC */ "100 bps, DCLS", \
+ /* A136_A137 */ "1000 bps, 10 kHz carrier, 2 digit year number, SBS optionally", \
+ /* A006_A007 */ "1000 bps, DCLS, 2 digit year number, SBS optionally", \
+ /* G146 */ "10 kbps, 100 kHz carrier, 2 digit year number", \
+ /* G006 */ "10 kbps, DCLS, 2 digit year number" \
+}
+
+/**
+ * @brief Bit masks used with ::IRIG_INFO::supp_codes for RX
+ *
+ * These bit masks are used with timecode receivers only
+ *
+ * @see @ref ICODE_RX_CODES
+ * @see @ref ICODE_TX_CODES
+ * @see @ref ICODE_TX_MASKS
+ *
+ * @anchor ICODE_RX_MASKS @{ */
+
#define MSK_ICODE_RX_B122_B123 ( 1UL << ICODE_RX_B122_B123 )
#define MSK_ICODE_RX_A132_A133 ( 1UL << ICODE_RX_A132_A133 )
#define MSK_ICODE_RX_B002_B003 ( 1UL << ICODE_RX_B002_B003 )
@@ -2807,8 +5052,8 @@ enum ICODE_RX_CODES
#define MSK_ICODE_RX_IEEE1344_DC ( 1UL << ICODE_RX_IEEE1344_DC )
#define MSK_ICODE_RX_B126_B127 ( 1UL << ICODE_RX_B126_B127 )
#define MSK_ICODE_RX_B006_B007 ( 1UL << ICODE_RX_B006_B007 )
-#define MSK_ICODE_RX_G142_G146 ( 1UL << ICODE_RX_G142_G146 )
-#define MSK_ICODE_RX_G002_G006 ( 1UL << ICODE_RX_G002_G006 )
+#define MSK_ICODE_RX_G142 ( 1UL << ICODE_RX_G142 )
+#define MSK_ICODE_RX_G002 ( 1UL << ICODE_RX_G002 )
#define MSK_ICODE_RX_C37118 ( 1UL << ICODE_RX_C37118 )
#define MSK_ICODE_RX_C37118_DC ( 1UL << ICODE_RX_C37118_DC )
#define MSK_ICODE_RX_TXC101 ( 1UL << ICODE_RX_TXC101 )
@@ -2817,9 +5062,16 @@ enum ICODE_RX_CODES
#define MSK_ICODE_RX_E002 ( 1UL << ICODE_RX_E002 )
#define MSK_ICODE_RX_NASA36 ( 1UL << ICODE_RX_NASA36 )
#define MSK_ICODE_RX_NASA36_DC ( 1UL << ICODE_RX_NASA36_DC )
+#define MSK_ICODE_RX_A136_A137 ( 1UL << ICODE_RX_A136_A137 )
+#define MSK_ICODE_RX_A006_A007 ( 1UL << ICODE_RX_A006_A007 )
+#define MSK_ICODE_RX_G146 ( 1UL << ICODE_RX_G146 )
+#define MSK_ICODE_RX_G006 ( 1UL << ICODE_RX_G006 )
+
+/** @} anchor ICODE_RX_MASKS */
+
/**
- * A mask of IRIG DCLS formats:
+ * @brief A mask of IRIG RX DCLS formats
*/
#define MSK_ICODE_RX_DC \
( \
@@ -2828,24 +5080,25 @@ enum ICODE_RX_CODES
MSK_ICODE_RX_AFNOR_DC | \
MSK_ICODE_RX_IEEE1344_DC | \
MSK_ICODE_RX_B006_B007 | \
- MSK_ICODE_RX_G002_G006 | \
+ MSK_ICODE_RX_G002 | \
MSK_ICODE_RX_C37118_DC | \
MSK_ICODE_RX_TXC101_DC | \
MSK_ICODE_RX_E002 | \
- MSK_ICODE_RX_NASA36_DC \
+ MSK_ICODE_RX_NASA36_DC | \
+ MSK_ICODE_RX_A006_A007 | \
+ MSK_ICODE_RX_G006 \
)
/**
- * A mask of IRIG formats with 100 Hz carrier:
+ * @brief A mask of IRIG RX formats with 100 Hz carrier
*/
#define MSK_ICODE_RX_100HZ \
( \
- MSK_ICODE_RX_E112 | \
- MSK_ICODE_RX_E002 \
+ MSK_ICODE_RX_E112 \
)
/**
- * A mask of IRIG formats with 1 kHz carrier:
+ * @brief A mask of IRIG RX formats with 1 kHz carrier
*/
#define MSK_ICODE_RX_1KHZ \
( \
@@ -2859,23 +5112,25 @@ enum ICODE_RX_CODES
)
/**
- * A mask of IRIG formats with 10 kHz carrier:
+ * @brief A mask of IRIG RX formats with 10 kHz carrier
*/
#define MSK_ICODE_RX_10KHZ \
( \
- MSK_ICODE_RX_A132_A133 \
+ MSK_ICODE_RX_A132_A133 | \
+ MSK_ICODE_RX_A136_A137 \
)
/**
- * A mask of IRIG formats with 100 kHz carrier:
+ * @brief A mask of IRIG RX formats with 100 kHz carrier
*/
#define MSK_ICODE_RX_100KHZ \
( \
- MSK_ICODE_RX_G142_G146 \
+ MSK_ICODE_RX_G142 | \
+ MSK_ICODE_RX_G146 \
)
/**
- * A mask of IRIG formats with 10 bps data rate:
+ * @brief A mask of IRIG RX formats with 10 bps data rate
*/
#define MSK_ICODE_RX_10BPS \
( \
@@ -2884,7 +5139,7 @@ enum ICODE_RX_CODES
)
/**
- * A mask of IRIG formats with 100 bps data rate:
+ * @brief A mask of IRIG RX formats with 100 bps data rate
*/
#define MSK_ICODE_RX_100BPS \
( \
@@ -2905,25 +5160,110 @@ enum ICODE_RX_CODES
)
/**
- * A mask of IRIG formats with 1000 bps data rate:
+ * @brief A mask of IRIG RX formats with 1000 bps data rate
*/
#define MSK_ICODE_RX_1000BPS \
( \
- MSK_ICODE_RX_A132_A133 | \
- MSK_ICODE_RX_A002_A003 \
+ MSK_ICODE_RX_A132_A133 | \
+ MSK_ICODE_RX_A002_A003 | \
+ MSK_ICODE_RX_A136_A137 | \
+ MSK_ICODE_RX_A006_A007 \
)
/**
- * A mask of IRIG formats with 10 kbps data rate:
+ * @brief A mask of IRIG RX formats with 10 kbps data rate
*/
#define MSK_ICODE_RX_10000BPS \
( \
- MSK_ICODE_RX_G142_G146 | \
- MSK_ICODE_RX_G002_G006 \
+ MSK_ICODE_RX_G142 | \
+ MSK_ICODE_RX_G002 | \
+ MSK_ICODE_RX_G146 | \
+ MSK_ICODE_RX_G006 \
+)
+
+/**
+ * @brief A mask of IRIG RX formats supporting 10ths of seconds
+ */
+#define MSK_ICODE_RX_HAS_SEC10THS \
+( \
+ MSK_ICODE_RX_A132_A133 | \
+ MSK_ICODE_RX_A002_A003 | \
+ MSK_ICODE_RX_G142 | \
+ MSK_ICODE_RX_G002 | \
+ MSK_ICODE_RX_A136_A137 | \
+ MSK_ICODE_RX_A006_A007 | \
+ MSK_ICODE_RX_G146 | \
+ MSK_ICODE_RX_G006 \
)
/**
- * A mask of IRIG formats which support TFOM:
+ * @brief A mask of IRIG RX formats which support 100ths of seconds
+ */
+#define MSK_ICODE_RX_HAS_SEC100THS \
+( \
+ MSK_ICODE_RX_G142 | \
+ MSK_ICODE_RX_G002 | \
+ MSK_ICODE_RX_G146 | \
+ MSK_ICODE_RX_G006 \
+)
+
+/**
+ * @brief A mask of IRIG RX formats supporting a 2 digit year number after P5
+ *
+ * Note: This macro specifies ONLY the codes where the year number
+ * is transmitted after position identifier P5.
+ *
+ * @see ::MSK_ICODE_RX_HAS_SHORT_YEAR_AFTER_P6
+ * @see ::MSK_ICODE_RX_HAS_ANY_SHORT_YEAR
+ */
+#define MSK_ICODE_RX_HAS_SHORT_YEAR_AFTER_P5 \
+( \
+ MSK_ICODE_RX_AFNOR | \
+ MSK_ICODE_RX_AFNOR_DC | \
+ MSK_ICODE_RX_IEEE1344 | \
+ MSK_ICODE_RX_IEEE1344_DC | \
+ MSK_ICODE_RX_B126_B127 | \
+ MSK_ICODE_RX_B006_B007 | \
+ MSK_ICODE_RX_C37118 | \
+ MSK_ICODE_RX_C37118_DC | \
+ MSK_ICODE_RX_A136_A137 | \
+ MSK_ICODE_RX_A006_A007 \
+)
+
+/**
+ * @brief A mask of IRIG RX formats supporting a 2 digit year number after P6
+ *
+ * Note: This macro specifies ONLY the codes where the year number
+ * is transmitted after position identifier P6.
+ *
+ * @see ::MSK_ICODE_RX_HAS_SHORT_YEAR_AFTER_P5
+ * @see ::MSK_ICODE_RX_HAS_ANY_SHORT_YEAR
+ */
+#define MSK_ICODE_RX_HAS_SHORT_YEAR_AFTER_P6 \
+( \
+ MSK_ICODE_RX_G146 | \
+ MSK_ICODE_RX_G006 \
+)
+
+/**
+ * @brief A mask of IRIG RX formats providing any 2 digit year number
+ *
+ * Note: Different sets of code frames may provide a year number
+ * in different locations of the transmitted code.
+ *
+ * @see ::MSK_ICODE_RX_HAS_SHORT_YEAR_AFTER_P5
+ * @see ::MSK_ICODE_RX_HAS_SHORT_YEAR_AFTER_P6
+ */
+#define MSK_ICODE_RX_HAS_ANY_SHORT_YEAR \
+( \
+ MSK_ICODE_RX_HAS_SHORT_YEAR_AFTER_P5 | \
+ MSK_ICODE_RX_HAS_SHORT_YEAR_AFTER_P6 \
+)
+
+
+
+/**
+ * @brief A mask of IRIG RX formats supporting TFOM time quality indicator
*/
#define MSK_ICODE_RX_HAS_TFOM \
( \
@@ -2934,7 +5274,20 @@ enum ICODE_RX_CODES
)
/**
- * A mask of IRIG formats which support time zone information:
+ * @brief A mask of IRIG RX formats supporting CTQ continuous time quality
+ *
+ * This has been introduced in IEEE C37.118.1-2011
+ */
+#define MSK_ICODE_RX_HAS_CTQ \
+( \
+ MSK_ICODE_RX_IEEE1344 | \
+ MSK_ICODE_RX_IEEE1344_DC | \
+ MSK_ICODE_RX_C37118 | \
+ MSK_ICODE_RX_C37118_DC \
+)
+
+/**
+ * @brief A mask of IRIG RX formats supporting time zone information
*/
#define MSK_ICODE_RX_HAS_TZI \
( \
@@ -2945,8 +5298,55 @@ enum ICODE_RX_CODES
)
/**
- * The default mask of IRIG formats supported by
- * IRIG receivers:
+ * @brief IRIG RX formats where UTC offset must be subtracted to yield UTC
+ *
+ * A mask of IRIG formats where the decoded UTC offset must be
+ * subtracted from the time decoded from the IRIG signal to yield UTC, e.g.:<br>
+ * (IRIG time 14:43:27 h) - (offs -6 h) = (UTC 20:43:27)
+ */
+#define MSK_ICODE_RX_UTC_OFFS_SUB \
+( \
+ MSK_ICODE_RX_IEEE1344 | \
+ MSK_ICODE_RX_IEEE1344_DC \
+)
+
+/**
+ * @brief IRIG RX formats where UTC offset must be added to yield UTC
+ *
+ * A mask of IRIG formats where the decoded UTC offset must be
+ * added to the time decoded from the IRIG signal to yield UTC, e.g.:<br>
+ * (IRIG time 14:43:27 h) + (offs -6 h) = (UTC 08:43:27)
+ */
+#define MSK_ICODE_RX_UTC_OFFS_ADD \
+( \
+ MSK_ICODE_RX_C37118 | \
+ MSK_ICODE_RX_C37118_DC \
+)
+
+/**
+ * @brief A mask of IRIG RX formats supporting a day of week number
+ */
+#define MSK_ICODE_RX_HAS_AFNOR_WDAY \
+( \
+ MSK_ICODE_RX_AFNOR | \
+ MSK_ICODE_RX_AFNOR_DC \
+)
+
+/**
+ * @brief A mask of IRIG RX formats supporting a date (day-of-month, month)
+ */
+#define MSK_ICODE_RX_HAS_AFNOR_DATE \
+( \
+ MSK_ICODE_RX_AFNOR | \
+ MSK_ICODE_RX_AFNOR_DC \
+)
+
+
+/**
+ * @brief The default mask of IRIG RX formats supported by IRIG receivers
+ *
+ * @note The formats which are actually supported should be retrieved
+ * from the device
*/
#if !defined( SUPP_MSK_ICODE_RX )
#define SUPP_MSK_ICODE_RX \
@@ -2960,50 +5360,62 @@ enum ICODE_RX_CODES
)
#endif
-/** @} group_icode */
+/** @} defgroup group_icode */
/**
* @brief Configuration settings of an IRIG input or output
*
- * @see group_icode
+ * @see @ref group_icode
*/
typedef struct
{
- uint16_t icode; ///< IRIG signal code, see ::ICODE_RX_CODES
- uint16_t flags; ///< see ::IFLAGS_BITS
+ uint16_t icode; ///< IRIG signal code, see ::ICODE_RX_CODES and ::ICODE_TX_CODES
+ uint16_t flags; ///< see ::IFLAGS_BIT_MASKS
+
} IRIG_SETTINGS;
#define _mbg_swab_irig_settings( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->icode ); \
_mbg_swab16( &(_p)->flags ); \
-}
+} while ( 0 )
/**
- * @brief Bits used with IRIG_SETTINGS::flags
+ * @brief Flag bits used to define ::IFLAGS_BIT_MASKS
*
- * @note The presence or absence of the ::IFLAGS_BIT_DISABLE_TFOM flag for the IRIG RX
- * settings of some PCI cards may not be evaluated correctly by some firmware
- * versions for those cards, even if an IRIG code has been configured which supports
- * this flag. See the comments near the declaration of the _pcps_incoming_tfom_ignored()
- * macro in pcpsdev.h for details.
+ * @see ::IFLAGS_BIT_MASKS
*/
enum IFLAGS_BITS
{
IFLAGS_BIT_DISABLE_TFOM, ///< for RX ignore, for TX don't generate TFOM flag
- IFLAGS_BIT_TX_GEN_LOCAL_TIME, ///< TX output local time, not %UTC
+ IFLAGS_BIT_TX_GEN_LOCAL_TIME, ///< TX output local time instead of %UTC
N_IFLAGS_BITS ///< number of known bits
};
-#define IFLAGS_DISABLE_TFOM ( 1UL << IFLAGS_BIT_DISABLE_TFOM )
-#define IFLAGS_TX_GEN_LOCAL_TIME ( 1UL << IFLAGS_BIT_TX_GEN_LOCAL_TIME )
-#define IFLAGS_MASK ( ( 1UL << N_IFLAGS_BITS ) - 1 ) ///< mask of all known flags
+/**
+ * @brief Bit masks used with ::IRIG_SETTINGS::flags
+ *
+ * @note The presence or absence of the ::IFLAGS_DISABLE_TFOM flag for the IRIG RX
+ * settings of some PCI cards may not be evaluated correctly by some firmware
+ * versions for those cards, even if an IRIG code has been configured which supports
+ * this flag. See the comments near the declaration of the ::_pcps_incoming_tfom_ignored
+ * macro in pcpsdev.h for details.
+ *
+ * @see ::IFLAGS_BITS
+ */
+enum IFLAGS_BIT_MASKS
+{
+ IFLAGS_DISABLE_TFOM = ( 1UL << IFLAGS_BIT_DISABLE_TFOM ), ///< see ::IFLAGS_BIT_DISABLE_TFOM
+ IFLAGS_TX_GEN_LOCAL_TIME = ( 1UL << IFLAGS_BIT_TX_GEN_LOCAL_TIME ), ///< see ::IFLAGS_BIT_TX_GEN_LOCAL_TIME
+ IFLAGS_MASK = ( ( 1UL << N_IFLAGS_BITS ) - 1 ) ///< mask of all known flags
+};
/**
@@ -3015,14 +5427,16 @@ enum IFLAGS_BITS
typedef struct
{
IRIG_SETTINGS settings; ///< current settings
- uint32_t supp_codes; ///< bit mask of supported codes
+ uint32_t supp_codes; ///< see @ref ICODE_TX_MASKS and @ref ICODE_RX_MASKS
+
} IRIG_INFO;
#define _mbg_swab_irig_info( _p ) \
+do \
{ \
_mbg_swab_irig_settings( &(_p)->settings ); \
_mbg_swab32( &(_p)->supp_codes ); \
-}
+} while ( 0 )
/**
@@ -3032,6 +5446,7 @@ typedef struct
* which is supported by some IRIG receivers. Delay compensation
* depends on the basic frame type, so there are different records
* required for the different frame type groups.
+ *
* @{ */
/**
@@ -3057,14 +5472,15 @@ typedef struct
} IRIG_RX_COMP;
#define _mbg_swab_irig_rx_comp( _p ) \
+do \
{ \
int i; \
for ( i = 0; i < N_IRIG_RX_COMP_VAL; i++ ) \
_mbg_swab16( &(_p)->c[i] ); \
-}
+} while ( 0 )
-/** The absolute value of the maximum compensation value accepted by a device */
+/** The absolute value of the maximum compensation value accepted by a device */
#define IRIG_RX_COMP_MAX 999 // [100 ns units], i.e. valid range is +/-99.9 us
@@ -3074,19 +5490,21 @@ typedef struct
*/
typedef struct
{
- uint16_t type; ///< record type @see CAL_REC_TYPES
+ uint16_t type; ///< record type, see ::CAL_REC_TYPES
uint16_t idx; ///< index if several records of same type are supported, see ::IRIG_RX_COMP_GROUPS
+
} CAL_REC_HDR;
#define _mbg_swab_cal_rec_hdr( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->type ); \
_mbg_swab16( &(_p)->idx ); \
-}
+} while ( 0 )
/**
- * @brief Types to be used with CAL_REC_HDR::type
+ * @brief Types to be used with ::CAL_REC_HDR::type
*/
enum CAL_REC_TYPES
{
@@ -3097,7 +5515,7 @@ enum CAL_REC_TYPES
/**
- * @brief Types to be used with CAL_REC_HDR::idx
+ * @brief Types to be used with ::CAL_REC_HDR::idx
*
* IRIG frame type groups to be distinguished for delay compensation.
*/
@@ -3133,27 +5551,30 @@ enum IRIG_RX_COMP_GROUPS
*/
typedef struct
{
- CAL_REC_HDR hdr;
+ CAL_REC_HDR hdr; ///< data header
IRIG_RX_COMP comp_data; ///< IRIG receiver delay compensation
} CAL_REC_IRIG_RX_COMP;
#define _mbg_swab_cal_rec_irig_rx_comp( _p ) \
+do \
{ \
_mbg_swab_cal_rec_hdr( &(_p)->hdr ); \
_mbg_swab_irig_rx_comp( &(_p)->comp_data ); \
-}
+} while ( 0 )
-/** @} group_irig_comp */
+/** @} defgroup group_irig_comp */
/**
* @brief A data type used to read the board's debug status
*
- * @note This also include IRIG decoder status.
+ * @note This also includes IRIG decoder status.
+ *
+ * @see @ref MBG_DEBUG_STATUS_BIT_MASKS
*/
-typedef uint32_t MBG_DEBUG_STATUS; ///< @see MBG_DEBUG_STATUS_BITS
+typedef uint32_t MBG_DEBUG_STATUS;
#define _mbg_swab_debug_status( _p ) \
_mbg_swab32( _p )
@@ -3161,29 +5582,33 @@ typedef uint32_t MBG_DEBUG_STATUS; ///< @see MBG_DEBUG_STATUS_BITS
/**
- * @brief Enumeration of bits used with ::MBG_DEBUG_STATUS
+ * @brief Enumeration of flag bits used for debug status
+ *
+ * @see @ref MBG_DEBUG_STATUS_BIT_MASKS
*/
enum MBG_DEBUG_STATUS_BITS
{
- MBG_IRIG_BIT_WARMED_UP, /**< Osc has warmed up */
- MBG_IRIG_BIT_PPS_ACTIVE, /**< PPS output is active */
- MBG_IRIG_BIT_INV_CONFIG, /**< Invalid config, e.g. data csum error */
- MBG_IRIG_BIT_MSG_DECODED, /**< IRIG msg could be decoded */
- MBG_IRIG_BIT_MSG_INCONSISTENT, /**< IRIG msg contains inconsistent data */
- MBG_IRIG_BIT_LOOP_LOCKED, /**< Decoder control loop is locked */
- MBG_IRIG_BIT_JITTER_TOO_LARGE, /**< Phase jitter too large */
- MBG_IRIG_BIT_INV_REF_OFFS, /**< %UTC ref offset not configured */
-
- MBG_SYS_BIT_INV_TIME, /**< Internal time not valid/set */
- MBG_SYS_BIT_TIME_SET_VIA_API, /**< On board time set externally */
- MBG_SYS_BIT_INV_RTC, /**< On board RTC invalid */
- MBG_SYS_BIT_CPU_PLL_FAILED, /**< The CPU's PLL watchdog */
-
- N_MBG_DEBUG_BIT
+ MBG_IRIG_BIT_WARMED_UP, ///< Osc has warmed up
+ MBG_IRIG_BIT_PPS_ACTIVE, ///< PPS output is active
+ MBG_IRIG_BIT_INV_CONFIG, ///< Invalid config, e.g. data csum error
+ MBG_IRIG_BIT_MSG_DECODED, ///< IRIG msg could be decoded
+ MBG_IRIG_BIT_MSG_INCONSISTENT, ///< IRIG msg contains inconsistent data
+ MBG_IRIG_BIT_LOOP_LOCKED, ///< Decoder control loop is locked
+ MBG_IRIG_BIT_JITTER_TOO_LARGE, ///< Phase jitter too large
+ MBG_IRIG_BIT_INV_REF_OFFS, ///< %UTC ref offset not configured
+
+ MBG_SYS_BIT_INV_TIME, ///< Internal time not valid/set
+ MBG_SYS_BIT_TIME_SET_VIA_API, ///< On board time set externally
+ MBG_SYS_BIT_INV_RTC, ///< On board RTC invalid
+ MBG_SYS_BIT_CPU_PLL_FAILED, ///< The CPU's PLL watchdog
+
+ N_MBG_DEBUG_BIT ///< The number of known bits
};
/**
* @brief Initializers for debug status bit strings
+ *
+ * @see ::MBG_DEBUG_STATUS_BITS
*/
#define MBG_DEBUG_STATUS_STRS \
{ \
@@ -3203,6 +5628,12 @@ enum MBG_DEBUG_STATUS_BITS
}
+/**
+ * @brief Bit masks used with ::MBG_DEBUG_STATUS
+ *
+ * @see ::MBG_DEBUG_STATUS_BITS
+ *
+ * @anchor MBG_DEBUG_STATUS_BIT_MASKS @{ */
#define MBG_IRIG_MSK_WARMED_UP ( 1UL << MBG_IRIG_BIT_WARMED_UP )
#define MBG_IRIG_MSK_PPS_ACTIVE ( 1UL << MBG_IRIG_BIT_PPS_ACTIVE )
@@ -3218,6 +5649,7 @@ enum MBG_DEBUG_STATUS_BITS
#define MBG_SYS_MSK_INV_RTC ( 1UL << MBG_SYS_BIT_INV_RTC )
#define MBG_SYS_MSK_CPU_PLL_FAILED ( 1UL << MBG_SYS_BIT_CPU_PLL_FAILED )
+/** @} anchor MBG_DEBUG_STATUS_BIT_MASKS */
/**
@@ -3227,10 +5659,15 @@ enum MBG_DEBUG_STATUS_BITS
* For some types of signal (e.g. most IRIG frame formats) this can't be
* determined automatically.
*
+ * Valid range: -::MBG_REF_OFFS_MAX..::MBG_REF_OFFS_MAX, or ::MBG_REF_OFFS_NOT_CFGD
+ *
* @note There's a special flag ::MBG_REF_OFFS_NOT_CFGD indicating that
- * this parameter is unconfigured
+ * this parameter is unconfigured, in which case a Meinberg time code
+ * receiver refuses to synchronize to the time code signal unless a time
+ * code frame has been configured which provides the UTC offset (namely
+ * IEEE 1344 or IEEE C37.118).
*/
-typedef int16_t MBG_REF_OFFS; ///< -::MBG_REF_OFFS_MAX..::MBG_REF_OFFS_MAX, or ::MBG_REF_OFFS_NOT_CFGD
+typedef int16_t MBG_REF_OFFS;
#define _mbg_swab_mbg_ref_offs( _p ) _mbg_swab16( (_p) )
@@ -3247,7 +5684,8 @@ typedef int16_t MBG_REF_OFFS; ///< -::MBG_REF_OFFS_MAX..::MBG_REF_OFFS_MAX, or
* (time offset from %UTC) has not yet been configured. This is usually
* the case for IRIG receiver devices right after they have been shipped.
*/
-#define MBG_REF_OFFS_NOT_CFGD 0x8000
+#define MBG_REF_OFFS_NOT_CFGD ( (MBG_REF_OFFS) 0x8000 )
+
/**
@@ -3257,13 +5695,15 @@ typedef int16_t MBG_REF_OFFS; ///< -::MBG_REF_OFFS_MAX..::MBG_REF_OFFS_MAX, or
*/
typedef struct
{
- uint32_t flags; ///< @see MBG_OPT_BITS
+ uint32_t flags; ///< @see ::MBG_OPT_FLAGS
+
} MBG_OPT_SETTINGS;
#define _mbg_swab_mbg_opt_settings( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->flags ); \
-}
+} while ( 0 )
/**
@@ -3274,48 +5714,68 @@ typedef struct
*/
typedef struct
{
- MBG_OPT_SETTINGS settings;
- uint32_t supp_flags; ///< bit mask of supported flags, see ::MBG_OPT_BITS
+ MBG_OPT_SETTINGS settings; ///< current settings
+ uint32_t supp_flags; ///< bit mask of supported flags, see ::MBG_OPT_FLAGS
+
} MBG_OPT_INFO;
#define _mbg_swab_mbg_opt_info( _p ) \
+do \
{ \
_mbg_swab_mbg_opt_settings( &(_p)->settings ); \
_mbg_swab32( &(_p)->supp_flags ); \
-}
+} while ( 0 )
+/**
+ * @brief Enumeration of flag bits used to define ::MBG_OPT_FLAGS
+ */
enum MBG_OPT_BITS
{
- MBG_OPT_BIT_STR_UTC, /**< serial string contains %UTC time */
- MBG_OPT_BIT_EMU_SYNC, /**< emulate/pretend to be synchronized, alternatively
- ::GPS_FEAT_IGNORE_LOCK may be supported */
+ MBG_OPT_BIT_STR_UTC, ///< serial time string contains %UTC time
+ MBG_OPT_BIT_EMU_SYNC, ///< always pretend to be synchronized, alternatively ::GPS_FEAT_IGNORE_LOCK may be supported
N_MBG_OPT_BIT
};
-/*
- * Bit masks corresponding to the enumeration above:
+
+/**
+ * @brief Bit masks according to ::MBG_OPT_BITS
+ *
+ * Used with ::MBG_OPT_SETTINGS::flags and ::MBG_OPT_INFO::supp_flags.
*/
-#define MBG_OPT_FLAG_STR_UTC ( 1UL << MBG_OPT_BIT_STR_UTC )
-#define MBG_OPT_FLAG_EMU_SYNC ( 1UL << MBG_OPT_BIT_EMU_SYNC )
+enum MBG_OPT_FLAGS
+{
+ MBG_OPT_FLAG_STR_UTC = ( 1UL << MBG_OPT_BIT_STR_UTC ), ///< see ::MBG_OPT_BIT_STR_UTC
+ MBG_OPT_FLAG_EMU_SYNC = ( 1UL << MBG_OPT_BIT_EMU_SYNC ) ///< see ::MBG_OPT_BIT_EMU_SYNC
+};
/**
* @brief Bit coded return type for ::PCPS_GET_IRIG_CTRL_BITS
*
- * This type returns the control bits an IRIG receiver has decoded
- * from an incoming time code signal.
+ * The control bits a time code receiver has decoded from
+ * the incoming time code signal.
+ *
+ * @note ::MBG_RAW_IRIG_DATA is more versatile and should
+ * be used preferably, if supported.
+ *
+ * @see ::MBG_RAW_IRIG_DATA
*/
typedef uint32_t MBG_IRIG_CTRL_BITS;
#define _mbg_swab_irig_ctrl_bits( _p ) _mbg_swab32( _p )
-// The following macro extracts the 4 bit TFOM code from the
-// IRIG control bits read from a card. This only works if the received
-// IRIG code is a code which supports TFOM, this is currently
-// only IEEE1344.
+/**
+ * @brief Extract the TFOM code from ::MBG_IRIG_CTRL_BITS
+ *
+ * The resulting code is only valid if the configured IRIG code frame format
+ * supports this. See @ref MSK_ICODE_TX_HAS_TFOM and @ref MSK_ICODE_RX_HAS_TFOM
+ *
+ * As specified in the IEEE 1344 standard as "Time Quality", the TFOM code is
+ * the range 0x0 (locked, maximum accuracy) to 0xF (failed, data unreliable).
+ */
#define _pcps_tfom_from_irig_ctrl_bits( _p ) \
( ( ( *(_p) ) >> 24 ) & 0x0F )
@@ -3336,13 +5796,21 @@ typedef uint32_t MBG_IRIG_CTRL_BITS;
typedef struct
{
uint8_t data_bytes[RAW_IRIG_SIZE];
+
} MBG_RAW_IRIG_DATA;
-// The following macro extracts the 4 bit TFOM code from the raw
-// data bits read from a card. This only works if the received
-// IRIG code is a code which supports TFOM, this is currently
-// only IEEE1344.
-#define _pcps_tfom_from_raw_irig_data( _p ) \
+#define _mbg_swab_mbg_raw_irig_data( _p ) _nop_macro_fnc()
+
+/**
+ * @brief Extract the TFOM code from ::MBG_RAW_IRIG_DATA
+ *
+ * The resulting code is only valid if the configured IRIG code frame format
+ * supports this. See @ref MSK_ICODE_TX_HAS_TFOM and @ref MSK_ICODE_RX_HAS_TFOM
+ *
+ * As specified in the IEEE 1344 standard as "Time Quality", the TFOM code is
+ * the range 0x0 (locked, maximum accuracy) to 0xF (failed, data unreliable).
+ */
+#define _pcps_tfom_from_raw_irig_data( _p ) \
( ( ( (_p)->data_bytes[9] >> 2 ) & 0x08 ) \
| ( ( (_p)->data_bytes[9] >> 4 ) & 0x04 ) \
| ( ( (_p)->data_bytes[9] >> 6 ) & 0x02 ) \
@@ -3351,35 +5819,43 @@ typedef struct
/**
- @defgroup group_time_scale Time Scale Configuration
-
- The structures and defines can be used to configure the GPS receiver's
- basic time scale. By default this is %UTC which can optionally
- be converted to some local time. However, some applications
- prefer TAI or pure GPS time. This can be configured using the
- structures below if the GPS_HAS_TIME_SCALE flag is set in
- RECEIVER_INFO::features.
- @{
-*/
+ * @defgroup group_time_scale Time Scale Configuration
+ *
+ * Used to configure the GPS receiver's basic time scale.
+ * By default this is %UTC which can optionally be converted
+ * to some local time. However, some applications prefer
+ * TAI or pure GPS time. This can be configured using the
+ * structures below if the ::GPS_HAS_TIME_SCALE flag is set
+ * in ::RECEIVER_INFO::features.
+ *
+ * @{ */
/**
* @brief Known time scales
*
- * @note See also the extended status bits ::TM_SCALE_GPS
- * and ::TM_SCALE_TAI indicating the active time scale setting
+ * @see ::MBG_TIME_SCALE_MASKS
+ * @see ::TM_SCALE_GPS
+ * @see ::TM_SCALE_TAI
*/
enum MBG_TIME_SCALES
{
MBG_TIME_SCALE_DEFAULT, ///< %UTC or local time according to ::UTC parameters and ::TZDL configuration
MBG_TIME_SCALE_GPS, ///< GPS time as sent by the satellites, monotonical
- MBG_TIME_SCALE_TAI, ///< TAI, i.e. GPS time plus constant offset (::GPS_TAI_OFFSET)
+ MBG_TIME_SCALE_TAI, ///< TAI, i.e. GPS time plus constant offset (see ::GPS_TAI_OFFSET)
N_MBG_TIME_SCALE
};
-#define MBG_TIME_SCALE_MSK_DEFAULT ( 1UL << MBG_TIME_SCALE_DEFAULT )
-#define MBG_TIME_SCALE_MSK_GPS ( 1UL << MBG_TIME_SCALE_GPS )
-#define MBG_TIME_SCALE_MSK_TAI ( 1UL << MBG_TIME_SCALE_TAI )
-
+/**
+ * @brief Bit masks for known time scales
+ *
+ * @see ::MBG_TIME_SCALES
+ */
+enum MBG_TIME_SCALE_MASKS
+{
+ MBG_TIME_SCALE_MSK_DEFAULT = ( 1UL << MBG_TIME_SCALE_DEFAULT ), ///< see ::MBG_TIME_SCALE_DEFAULT
+ MBG_TIME_SCALE_MSK_GPS = ( 1UL << MBG_TIME_SCALE_GPS ), ///< see ::MBG_TIME_SCALE_GPS
+ MBG_TIME_SCALE_MSK_TAI = ( 1UL << MBG_TIME_SCALE_TAI ) ///< see ::MBG_TIME_SCALE_TAI
+};
#define MBG_TIME_SCALE_STRS \
{ \
@@ -3401,8 +5877,9 @@ enum MBG_TIME_SCALES
*/
typedef struct
{
- uint8_t scale; ///< current time scale code from enum MBG_TIME_SCALES
- uint8_t flags; ///< reserved, currently always 0
+ uint8_t scale; ///< current time scale code, see ::MBG_TIME_SCALES
+ uint8_t flags; ///< reserved, don't use, currently always 0
+
} MBG_TIME_SCALE_SETTINGS;
#define _mbg_swab_mbg_time_scale_settings( _p ) \
@@ -3415,26 +5892,33 @@ typedef struct
typedef struct
{
MBG_TIME_SCALE_SETTINGS settings; ///< current settings
- MBG_TIME_SCALE_SETTINGS max_settings; ///< numb. of scales, all supported flags
- uint32_t supp_scales; ///< bit masks of supported scales
+ MBG_TIME_SCALE_SETTINGS max_settings; ///< number of scales, all supported flags
+ uint32_t supp_scales; ///< bit masks of supported scales, see ::MBG_TIME_SCALE_MASKS
+
} MBG_TIME_SCALE_INFO;
#define _mbg_swab_mbg_time_scale_info( _p ) \
+do \
{ \
_mbg_swab_mbg_time_scale_settings( &(_p)->settings ); \
_mbg_swab_mbg_time_scale_settings( &(_p)->max_settings ); \
_mbg_swab32( &(_p)->supp_scales ); \
-}
+} while ( 0 )
-/** @} group_time_scale */
+/** @} defgroup group_time_scale */
-/*
- * The structures below are required to setup the programmable
+
+/**
+ * @defgroup group_pout_api Programmable Output API
+ *
+ * These structures below are used to configure the programmable
* pulse outputs which are provided by some GPS receivers.
* The number of programmable pulse outputs supported by a GPS
- * receiver is reported in the RECEIVER_INFO::n_str_type field.
- */
+ * receiver is reported in the RECEIVER_INFO::n_prg_out field.
+ *
+ * @{ */
+
/**
* @brief A calendar date including full year number
@@ -3444,12 +5928,14 @@ typedef struct
uint8_t mday; ///< 1..28,29,30,31
uint8_t month; ///< 1..12
uint16_t year; ///< including century
+
} MBG_DATE;
#define _mbg_swab_mbg_date( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->year ); \
-}
+} while ( 0 )
/**
@@ -3460,7 +5946,8 @@ typedef struct
uint8_t hour; ///< 0..23
uint8_t min; ///< 0..59
uint8_t sec; ///< 0..59,60
- uint8_t sec100; ///< reserved, currently always 0
+ uint8_t sec100; ///< 100ths of seconds
+
} MBG_TIME;
#define _mbg_swab_mbg_time( _p ) \
@@ -3476,29 +5963,38 @@ typedef struct
MBG_TIME t; ///< time to switch
uint8_t wday; ///< reserved, currently always 0
uint8_t flags; ///< reserved, currently 0
+
} MBG_DATE_TIME;
#define _mbg_swab_mbg_date_time( _p ) \
+do \
{ \
_mbg_swab_mbg_date( &(_p)->d ); \
_mbg_swab_mbg_time( &(_p)->t ); \
-}
+} while ( 0 )
/**
* @brief A structure to define on/off cycle times
+ *
+ * @note The ::MBG_TIME::sec100 field in ::POUT_TIME:on and
+ * ::POUT_TIME:off is not evaluated by the firmware and thus
+ * should always be set to 0.
*/
typedef struct
{
MBG_DATE_TIME on; ///< date and time to switch on
MBG_DATE_TIME off; ///< date and time to switch off
+
} POUT_TIME;
#define _mbg_swab_pout_time( _p ) \
+do \
{ \
_mbg_swab_mbg_date_time( &(_p)->on ); \
_mbg_swab_mbg_date_time( &(_p)->off ); \
-}
+} while ( 0 )
+
/**
@@ -3509,73 +6005,120 @@ typedef struct
#define N_POUT_TIMES 3
/**
+ * @brief A Generic data field for programmable output settings
+ */
+typedef union
+{
+ /// Switching times. See ::POUT_MODES_DATA_TM, ::POUT_MODES_DATA_TM_0
+ POUT_TIME tm[N_POUT_TIMES];
+
+ uint8_t b[N_POUT_TIMES * sizeof( POUT_TIME )];
+
+ /// Only if ::POUT_SUPP_PULSE_SHIFT is set, this field can be used to
+ /// configure the time interval in [ns] by which output pulse slopes are
+ /// to be shifted. The configured pulse shift must be in the range
+ /// ::DEFAULT_POUT_PULSE_SHIFT_MIN through ::DEFAULT_POUT_PULSE_SHIFT_MAX.
+ /// The resolution / steps at which the pulse shift interval can be configured
+ /// is returned in ::POUT_INFO::pulse_shift_res.
+ /// @see ::POUT_MODES_DATA_PULSE_SHIFT
+ int32_t pulse_shift;
+
+} POUT_DATA;
+
+#define DEFAULT_POUT_PULSE_SHIFT_MIN -500000000L ///< Default minimum value for ::POUT_DATA::pulse_shift, in [ns]
+#define DEFAULT_POUT_PULSE_SHIFT_MAX 499000000L ///< Default maximum value for ::POUT_DATA::pulse_shift, in [ns]
+
+
+/**
+ * @brief Convert ::POUT_DATA endianess depending on the mode
+ *
+ * Assuming the mode is passed to the macro with correct endianess.
+ */
+#define _mbg_swab_pout_data( _p, _mode ) \
+do \
+{ \
+ uint32_t mode_mask = 1UL << _mode; \
+ \
+ if ( mode_mask & POUT_MODES_DATA_TM ) \
+ { \
+ int i; \
+ \
+ for ( i = 0; i < N_POUT_TIMES; i++ ) \
+ _mbg_swab_pout_time( &(_p)->tm[i] ); \
+ } \
+ else \
+ { \
+ if ( mode_mask & POUT_MODES_DATA_TM_0 ) \
+ _mbg_swab_pout_time( &(_p)->tm[0] ); \
+ else \
+ if ( mode_mask & POUT_MODES_DATA_PULSE_SHIFT ) \
+ _mbg_swab32( &(_p)->pulse_shift ); \
+ } \
+ \
+} while ( 0 )
+
+
+
+/**
* @brief Configuration settings for a single programmable pulse output
*/
typedef struct
{
- uint16_t mode; ///< mode of operation, see ::POUT_MODES
- uint16_t pulse_len; ///< 10 msec units, or COM port number
- uint16_t timeout; ///< [min], for DCF77 emulation mode only
- uint16_t flags; ///< @see POUT_SETTINGS_FLAG_BITS
- POUT_TIME tm[N_POUT_TIMES]; ///< switching times, or other data, see ::POUT_DATA
+ uint16_t mode; ///< Mode of operation, see ::POUT_MODES
+ uint16_t mode_param; ///< Optional parameter depending on the mode, see @ref POUT_MODES_PARAM_MASKS
+
+ /// Timeout [min] which can be specified for some modes, see ::POUT_MODES_TIMEOUT, ::MAX_POUT_DCF_TIMOUT.
+ ///
+ /// If the clock looses synchronization then the output
+ /// - is disabled **immediately** if ::POUT_IF_SYNC_ONLY is set in ::POUT_SETTINGS::flags
+ /// - is disabled after ::POUT_SETTINGS::timeout, if timeout is not 0 (see ::MAX_POUT_DCF_TIMOUT)
+ /// - stays enabled if timeout is 0 **and** ::POUT_IF_SYNC_ONLY is **not** set
+ uint16_t timeout;
+
+ uint16_t flags; ///< @see ::POUT_SETTINGS_FLAGS
+ POUT_DATA pout_data; ///< Additional configuration data, see ::POUT_DATA
+
} POUT_SETTINGS;
/**
- * @brief A Generic data field for programmable output settings
- *
- * If the mode is set to ::POUT_TIME_SLOTS then POUT_SETTINGS::tm must be
- * interpreted as ::POUT_DATA, i.e. just an array of bytes. We can not change
- * the type of the tm field to a union for compatibility reasons ... :(
+ * @brief Convert ::POUT_SETTINGS endianess after reading from a device
*/
-typedef union
-{
- uint8_t b[N_POUT_TIMES * sizeof( POUT_TIME )];
-} POUT_DATA;
+#define _mbg_swab_pout_settings_on_get( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->mode ); \
+ _mbg_swab16( &(_p)->mode_param ); \
+ _mbg_swab16( &(_p)->timeout ); \
+ _mbg_swab16( &(_p)->flags ); \
+ _mbg_swab_pout_data( &(_p)->pout_data, (_p)->mode ); \
+} while ( 0 )
-// When reading data from a device we first need to correct the endianess
-// of the mode first, and correct the endianess of the tm field only
-// if the tm field is not interpreted as POUT_DATA.
-#define _mbg_swab_pout_settings_on_get( _p ) \
-{ \
- _mbg_swab16( &(_p)->mode ); \
- _mbg_swab16( &(_p)->pulse_len ); \
- _mbg_swab16( &(_p)->timeout ); \
- _mbg_swab16( &(_p)->flags ); \
- \
- if ( (_p)->mode != POUT_TIME_SLOTS ) \
- { \
- int i; \
- \
- for ( i = 0; i < N_POUT_TIMES; i++ ) \
- _mbg_swab_pout_time( &(_p)->tm[i] ); \
- } \
-}
-
-// When writing data to a device we first need to check the mode,
-// and correct the endianess of the tm field only if the tm field
-// is not interpreted as POUT_DATA. Finally we can also correct
-// the endianess of the mode field.
-#define _mbg_swab_pout_settings_on_set( _p ) \
-{ \
- if ( (_p)->mode != POUT_TIME_SLOTS ) \
- { \
- int i; \
- \
- for ( i = 0; i < N_POUT_TIMES; i++ ) \
- _mbg_swab_pout_time( &(_p)->tm[i] ); \
- } \
- \
- _mbg_swab16( &(_p)->mode ); \
- _mbg_swab16( &(_p)->pulse_len ); \
- _mbg_swab16( &(_p)->timeout ); \
- _mbg_swab16( &(_p)->flags ); \
-}
+/**
+ * @brief Convert ::POUT_SETTINGS endianess before writing to a device
+ */
+#define _mbg_swab_pout_settings_on_set( _p ) \
+do \
+{ \
+ _mbg_swab_pout_data( &(_p)->pout_data, (_p)->mode ); \
+ _mbg_swab16( &(_p)->mode ); \
+ _mbg_swab16( &(_p)->mode_param ); \
+ _mbg_swab16( &(_p)->timeout ); \
+ _mbg_swab16( &(_p)->flags ); \
+} while ( 0 )
-// In POUT_TIME_SLOTS mode the number of time slots per minute is stored
-// in the pulse_len field. Valid numbers all numbers n in the range 1..60
-// for which the remainder of 60 / n is 0.
+/**
+ * @brief Definitions used with ::POUT_TIME_SLOTS mode
+ *
+ * If ::POUT_SETTINGS::mode is set to ::POUT_TIME_SLOTS then the number
+ * of time slots per minute is stored in ::POUT_SETTINGS::mode_param.
+ * Valid numbers are all numbers n in the range ::MIN_TIME_SLOTS_PER_MINUTE
+ * to ::MAX_TIME_SLOTS_PER_MINUTE for which the remainder of 60 / n is 0.
+ * @see ::POUT_MODES_MODE_PARAM_AS_SLOTS_PER_MIN
+ *
+ * @anchor POUT_TIME_SLOTS_MODE_DEFS @{ */
+
#define MIN_TIME_SLOTS_PER_MINUTE 1
#define MAX_TIME_SLOTS_PER_MINUTE 60
#define TIME_SLOT_REGISTER_IN_SEC 60
@@ -3592,45 +6135,311 @@ typedef union
( ( 60 % (_n) ) == 0 ) \
)
+/** @} anchor POUT_TIME_SLOTS_MODE_DEFS */
+
+
#define MAX_POUT_PULSE_LEN 1000 ///< 10 secs, in 10 msec units
#define MAX_POUT_DCF_TIMOUT ( 48 * 60 ) ///< 48 hours, in minutes
+
/**
- * @brief Operation modes for a programmable pulse output
+ * @brief Enumeration of known operation modes for programmable pulse outputs
+ *
+ * These codes are used with ::POUT_SETTINGS::mode. One or more of
+ * the remaining fields in ::POUT_SETTINGS are evaluated depending
+ * on the selected mode. Unused fields should be set to 0.
*
- * These codes are used with POUT_SETTINGS::mode.
+ * Unless ::POUT_NOT_INVERTIBLE is set in ::POUT_INFO::flags
+ * the output signal level can be inverted if ::POUT_INVERTED
+ * is set in ::POUT_SETTINGS::flags.
*
* @note Not every programmable pulse output supports all modes.
+ *
+ * @see @ref POUT_MODE_MASKS
+ * @see @ref POUT_MODES_PARAM_MASKS
+ * @see @ref ENG_POUT_NAMES
+ * @see @ref ENG_POUT_HINTS
*/
enum POUT_MODES
{
- POUT_IDLE, ///< always off, or on if ::POUT_INVERTED flag is set
- POUT_TIMER, ///< switch on/off at configured times
- POUT_SINGLE_SHOT, ///< pulse at time POUT_SETTINGS::tm[0].on
- POUT_CYCLIC_PULSE, ///< pulse every POUT_SETTINGS::tm[0].on.t interval
- POUT_PER_SEC, ///< pulse if second changes
- POUT_PER_MIN, ///< pulse if minute changes
- POUT_PER_HOUR, ///< pulse if hour changes
- POUT_DCF77, ///< emulate DCF77 signal
- POUT_POS_OK, ///< on if pos. OK (nav_solved)
- POUT_TIME_SYNC, ///< on if time sync (time_syn)
- POUT_ALL_SYNC, ///< on if pos. OK and time sync
- POUT_TIMECODE, ///< IRIG/AFNOR DCLS output
- POUT_TIMESTR, ///< COM port number in pulse_len field
- POUT_10MHZ, ///< 10 MHz fixed frequency
- POUT_DCF77_M59, ///< DCF77-like signal with 500 ms pulse in 59th second
- POUT_SYNTH, ///< programmable synthesizer frequency
- POUT_TIME_SLOTS, ///< programmable time slots during each minute
+ /// Output is normally always 'off', or always 'on', if flag ::POUT_INVERTED is set.
+ POUT_IDLE,
+
+ /// Switch 'on' or 'off' at the times specified in ::POUT_DATA::tm.
+ POUT_TIMER,
+
+ /// Generate a pulse at the time specified in ::POUT_SETTINGS::POUT_DATA::tm[0]::on.
+ /// Pulse length according to ::POUT_SETTINGS::mode_param, in [10 ms] units.
+ /// See ::MAX_POUT_PULSE_LEN.
+ POUT_SINGLE_SHOT,
+
+ /// Generate a cyclic pulse at the interval specified in ::POUT_SETTINGS::POUT_DATA::tm[0]:on::t.
+ /// Pulse length according to ::POUT_SETTINGS::mode_param, in [10 ms] units.
+ /// See ::MAX_POUT_PULSE_LEN.
+ POUT_CYCLIC_PULSE,
+
+ /// Generate a pulse whenever the second changes.
+ /// Pulse length according to ::POUT_SETTINGS::mode_param, in [10 ms] units.
+ /// See ::MAX_POUT_PULSE_LEN.
+ POUT_PER_SEC,
+
+ /// Generate a pulse whenever the minute changes.
+ /// Pulse length according to ::POUT_SETTINGS::mode_param, in [10 ms] units.
+ /// See ::MAX_POUT_PULSE_LEN.
+ POUT_PER_MIN,
+
+ /// Generate a pulse whenever the hour changes.
+ /// Pulse length according to ::POUT_SETTINGS::mode_param, in [10 ms] units.
+ /// See ::MAX_POUT_PULSE_LEN.
+ POUT_PER_HOUR,
+
+ /// Generate DCF77-compatible second marks.
+ /// See ::POUT_DCF77_M59, ::POUT_SETTINGS::timeout and ::MAX_POUT_DCF_TIMOUT.
+ POUT_DCF77,
+
+ /// Output switched on if receiver position verified (condition nav_solved).
+ POUT_POS_OK,
+
+ /// Output switched on if time synchronized (condition time_syn).
+ POUT_TIME_SYNC,
+
+ /// Output switched on if both position verified and time synchronized.
+ POUT_ALL_SYNC,
+
+ /// IRIG/AFNOR DCLS time code signal mapped to this output.
+ POUT_TIMECODE,
+
+ /// Serial time string of one one of the serial ports mapped to this output.
+ /// ::POUT_SETTINGS::mode_param contains the number of the COM port.
+ /// See ::MAX_POUT_TIMESTR_PORTS.
+ POUT_TIMESTR,
+
+ /// 10 MHz fixed frequency output.
+ POUT_10MHZ,
+
+ /// DCF77-like signal with extra 500 ms pulse in the 59th second
+ /// (the original DCF77 signal has no such pulse). See ::POUT_DCF77,
+ /// ::POUT_SETTINGS::timeout and ::MAX_POUT_DCF_TIMOUT.
+ POUT_DCF77_M59,
+
+ /// Output signal generated by the programmable frequency synthesizer.
+ POUT_SYNTH,
+
+ /// Programmable time slots during each minute.
+ /// ::POUT_SETTINGS::mode_param specifies the time slots per minute.
+ /// Uses ::POUT_DATA. ::TODO
+ POUT_TIME_SLOTS,
+
+ /// A GPIO input or output signal is reflected at this pulse output.
+ /// ::POUT_SETTINGS::mode_param specifies the GPIO number which must
+ /// be in the range 0..::MBG_GPIO_CFG_LIMITS::num_io.
+ POUT_GPIO,
+
+ /// A 1PPS signal with a fixed 20us pulse length
+ POUT_PTTI_PPS,
+
+ /// A HaveQuick signal as configured in ::HAVEQUICK_SETTINGS::format
+ POUT_HAVEQUICK,
+
+ // New modes have to be added here at the end of the enumeration, and the
+ // POUT_MODE_MASKS, the POUT_MODES_PARAM_MASKS as well as string initializers
+ // (also in pcpslstr.h) have to be updated accordingly.
N_POUT_MODES ///< the number of known modes
};
-/*
- * Default initializers for English pulse mode names. Initializers
- * for multi-language strings can be found in pcpslstr.h.
+/**
+ * @brief Bit masks associated with ::POUT_MODES
+ *
+ * Used with ::POUT_INFO::supp_modes to specify which ::POUT_MODES
+ * are supported for a particular programmable output.
+ *
+ * @see ::POUT_MODES
+ *
+ * @anchor POUT_MODE_MASKS @{ */
+
+#define MSK_POUT_IDLE ( 1UL << POUT_IDLE ) ///< see ::POUT_IDLE
+#define MSK_POUT_TIMER ( 1UL << POUT_TIMER ) ///< see ::POUT_TIMER
+#define MSK_POUT_SINGLE_SHOT ( 1UL << POUT_SINGLE_SHOT ) ///< see ::POUT_SINGLE_SHOT
+#define MSK_POUT_CYCLIC_PULSE ( 1UL << POUT_CYCLIC_PULSE ) ///< see ::POUT_CYCLIC_PULSE
+#define MSK_POUT_PER_SEC ( 1UL << POUT_PER_SEC ) ///< see ::POUT_PER_SEC
+#define MSK_POUT_PER_MIN ( 1UL << POUT_PER_MIN ) ///< see ::POUT_PER_MIN
+#define MSK_POUT_PER_HOUR ( 1UL << POUT_PER_HOUR ) ///< see ::POUT_PER_HOUR
+#define MSK_POUT_DCF77 ( 1UL << POUT_DCF77 ) ///< see ::POUT_DCF77
+#define MSK_POUT_POS_OK ( 1UL << POUT_POS_OK ) ///< see ::POUT_POS_OK
+#define MSK_POUT_TIME_SYNC ( 1UL << POUT_TIME_SYNC ) ///< see ::POUT_TIME_SYNC
+#define MSK_POUT_ALL_SYNC ( 1UL << POUT_ALL_SYNC ) ///< see ::POUT_ALL_SYNC
+#define MSK_POUT_TIMECODE ( 1UL << POUT_TIMECODE ) ///< see ::POUT_TIMECODE
+#define MSK_POUT_TIMESTR ( 1UL << POUT_TIMESTR ) ///< see ::POUT_TIMESTR
+#define MSK_POUT_10MHZ ( 1UL << POUT_10MHZ ) ///< see ::POUT_10MHZ
+#define MSK_POUT_DCF77_M59 ( 1UL << POUT_DCF77_M59 ) ///< see ::POUT_DCF77_M59
+#define MSK_POUT_SYNTH ( 1UL << POUT_SYNTH ) ///< see ::POUT_SYNTH
+#define MSK_POUT_TIME_SLOTS ( 1UL << POUT_TIME_SLOTS ) ///< see ::POUT_TIME_SLOTS
+#define MSK_POUT_GPIO ( 1UL << POUT_GPIO ) ///< see ::POUT_GPIO
+#define MSK_POUT_PTTI_PPS ( 1UL << POUT_PTTI_PPS ) ///< see ::POUT_PTTI_PPS
+#define MSK_POUT_HAVEQUICK ( 1UL << POUT_HAVEQUICK ) ///< see ::POUT_HAVEQUICK
+
+/** @} anchor POUT_MODE_MASKS */
+
+
+
+/**
+ * @brief Bit masks indicating which parameters relevant for which ::POUT_MODES
+ *
+ * @see ::POUT_MODES
+ * @see @ref POUT_MODE_MASKS
+ *
+ * @anchor POUT_MODES_PARAM_MASKS @{ */
+
+
+/**
+ * @brief POUT modes which use the full ::POUT_DATA::tm array as parameter
+ */
+#define POUT_MODES_DATA_TM \
+( \
+ MSK_POUT_TIMER \
+)
+
+
+/**
+ * @brief POUT modes which use only ::POUT_DATA::tm[0] as parameter
*/
+#define POUT_MODES_DATA_TM_0 \
+( \
+ MSK_POUT_SINGLE_SHOT | \
+ MSK_POUT_CYCLIC_PULSE \
+)
+
+
+/**
+ * @brief POUT modes which use ::POUT_SETTINGS::mode_param as pulse length
+ *
+ * @see ::MAX_POUT_PULSE_LEN
+ */
+#define POUT_MODES_MODE_PARAM_AS_PULSE_LEN \
+( \
+ MSK_POUT_SINGLE_SHOT | \
+ MSK_POUT_CYCLIC_PULSE | \
+ MSK_POUT_PER_SEC | \
+ MSK_POUT_PER_MIN | \
+ MSK_POUT_PER_HOUR \
+)
+
+
+/**
+ * @brief POUT modes which use ::POUT_SETTINGS::mode_param as COM port index number
+ */
+#define POUT_MODES_MODE_PARAM_AS_COM_IDX \
+( \
+ MSK_POUT_TIMESTR \
+)
+
+
+/**
+ * @brief POUT modes which use ::POUT_SETTINGS::mode_param as time slots per minute
+ *
+ * @see @ref POUT_TIME_SLOTS_MODE_DEFS
+ */
+#define POUT_MODES_MODE_PARAM_AS_SLOTS_PER_MIN \
+( \
+ MSK_POUT_TIME_SLOTS \
+)
+
+
+/**
+ * @brief POUT modes which use ::POUT_SETTINGS::mode_param as GPIO index number
+ */
+#define POUT_MODES_MODE_PARAM_AS_GPIO_IDX \
+( \
+ MSK_POUT_GPIO \
+)
+
+
+/**
+ * @brief POUT modes which use ::POUT_SETTINGS::timeout
+ */
+#define POUT_MODES_TIMEOUT \
+( \
+ MSK_POUT_DCF77 | \
+ MSK_POUT_DCF77_M59 \
+)
+
+
+/**
+ * @brief POUT modes which which support ::POUT_TIMEBASE_UTC
+ */
+#define POUT_MODES_SUPP_TIMEBASE_UTC \
+( \
+ MSK_POUT_DCF77 | \
+ MSK_POUT_DCF77_M59 \
+)
+
+
+/**
+ * @brief POUT modes which use ::POUT_DATA::pulse_shift
+ *
+ * @note: Supported only if ::POUT_SUPP_PULSE_SHIFT is set
+ */
+#define POUT_MODES_DATA_PULSE_SHIFT \
+( \
+ MSK_POUT_PER_SEC | \
+ MSK_POUT_PER_MIN | \
+ MSK_POUT_PER_HOUR \
+)
+
+
+/**
+ * @brief POUT modes which support ::POUT_SUPP_IF_SYNC_ONLY
+ *
+ * Even if ::POUT_SUPP_IF_SYNC_ONLY is set in ::POUT_INFO::flags
+ * the associated flag ::POUT_IF_SYNC_ONLY in ::POUT_SETTINGS::flags
+ * may be evaluated depending on the mode.
+ *
+ * Modes ::POUT_POS_OK, ::POUT_TIME_SYNC, and ::MSK_POUT_ALL_SYNC
+ * are explicitly excluded.
+ *
+ * For modes ::MSK_POUT_DCF77 and ::MSK_POUT_DCF77_M59 see also
+ * ::POUT_SETTINGS::timeout.
+ */
+#define POUT_MODES_SUPP_IF_SYNC_ONLY \
+( \
+ MSK_POUT_IDLE | \
+ MSK_POUT_TIMER | \
+ MSK_POUT_SINGLE_SHOT | \
+ MSK_POUT_CYCLIC_PULSE | \
+ MSK_POUT_PER_SEC | \
+ MSK_POUT_PER_MIN | \
+ MSK_POUT_PER_HOUR | \
+ MSK_POUT_DCF77 | \
+ MSK_POUT_TIMECODE | \
+ MSK_POUT_TIMESTR | \
+ MSK_POUT_10MHZ | \
+ MSK_POUT_DCF77_M59 | \
+ MSK_POUT_SYNTH | \
+ MSK_POUT_TIME_SLOTS | \
+ MSK_POUT_GPIO | \
+ MSK_POUT_PTTI_PPS | \
+ MSK_POUT_HAVEQUICK \
+)
+
+
+/** @} anchor POUT_MODES_PARAM_MASKS */
+
+
+
+/**
+ * @brief Name strings associated with ::POUT_MODES
+ *
+ * Default initializers for English programmable output mode names.
+ * Initializers for multi-language strings can be found in pcpslstr.h.
+ *
+ * @see ::POUT_MODES
+ * @see ::DEFAULT_ENG_POUT_NAMES
+ *
+ * @anchor ENG_POUT_NAMES @{ */
+
#define ENG_POUT_NAME_IDLE "Idle"
#define ENG_POUT_NAME_TIMER "Timer"
#define ENG_POUT_NAME_SINGLE_SHOT "Single Shot"
@@ -3643,12 +6452,24 @@ enum POUT_MODES
#define ENG_POUT_NAME_TIME_SYNC "Time Sync"
#define ENG_POUT_NAME_ALL_SYNC "All Sync"
#define ENG_POUT_NAME_TIMECODE "DCLS Time Code"
-#define ENG_POUT_NAME_TIMESTR "COM Time String"
+#define ENG_POUT_NAME_TIMESTR "Serial Time String"
#define ENG_POUT_NAME_10MHZ "10 MHz Frequency"
#define ENG_POUT_NAME_DCF77_M59 "DCF77-like M59"
#define ENG_POUT_NAME_SYNTH "Synthesizer Frequency"
#define ENG_POUT_NAME_TIME_SLOTS "Time Slots per Minute"
+#define ENG_POUT_NAME_GPIO "GPIO Signal"
+#define ENG_POUT_PTTI_PPS "PTTI 1PPS"
+#define ENG_POUT_HAVEQUICK "HaveQuick"
+
+/** @} anchor ENG_POUT_NAMES */
+
+
+/**
+ * @brief An initializer for a table of English POUT name strings
+ *
+ * @see @ref ENG_POUT_NAMES
+ */
#define DEFAULT_ENG_POUT_NAMES \
{ \
ENG_POUT_NAME_IDLE, \
@@ -3667,10 +6488,24 @@ enum POUT_MODES
ENG_POUT_NAME_10MHZ, \
ENG_POUT_NAME_DCF77_M59, \
ENG_POUT_NAME_SYNTH, \
- ENG_POUT_NAME_TIME_SLOTS \
+ ENG_POUT_NAME_TIME_SLOTS, \
+ ENG_POUT_NAME_GPIO, \
+ ENG_POUT_PTTI_PPS, \
+ ENG_POUT_HAVEQUICK \
}
+/**
+ * @brief Hint strings associated with ::POUT_MODES
+ *
+ * Default initializers for English programmable output mode hints.
+ * Initializers for multi-language strings can be found in pcpslstr.h.
+ *
+ * @see ::POUT_MODES
+ * @see ::DEFAULT_ENG_POUT_HINTS
+ *
+ * @anchor ENG_POUT_HINTS @{ */
+
#define ENG_POUT_HINT_IDLE "Constant output level"
#define ENG_POUT_HINT_TIMER "Switch based on configured on/off times"
#define ENG_POUT_HINT_SINGLE_SHOT "Generate a single pulse of determined length"
@@ -3688,7 +6523,18 @@ enum POUT_MODES
#define ENG_POUT_HINT_DCF77_M59 "DCF77 time marks with 500 ms pulse in 59th second"
#define ENG_POUT_HINT_SYNTH "Frequency generated by programmable synthesizer"
#define ENG_POUT_HINT_TIME_SLOTS "Output enabled during specified time slots per minute"
+#define ENG_POUT_HINT_GPIO "Duplicated signal of the specified GPIO input or output"
+#define ENG_POUT_HINT_PTTI_PPS "Generate 20us Pulse at beginning of the second"
+#define ENG_POUT_HINT_HAVEQUICK "Duplicated HaveQuick Signal"
+/** @} anchor ENG_POUT_HINTS */
+
+
+/**
+ * @brief An initializer for a table of English POUT hint strings
+ *
+ * @see @ref ENG_POUT_HINTS
+ */
#define DEFAULT_ENG_POUT_HINTS \
{ \
ENG_POUT_HINT_IDLE, \
@@ -3707,48 +6553,58 @@ enum POUT_MODES
ENG_POUT_HINT_10MHZ, \
ENG_POUT_HINT_DCF77_M59, \
ENG_POUT_HINT_SYNTH, \
- ENG_POUT_HINT_TIME_SLOTS \
+ ENG_POUT_HINT_TIME_SLOTS, \
+ ENG_POUT_HINT_GPIO, \
+ ENG_POUT_HINT_PTTI_PPS, \
+ ENG_POUT_HINT_HAVEQUICK \
}
-/*
- * The definitions below are used to set up bit masks
- * which restrict the modes which can be used with
- * a given programmable output:
- */
-#define MSK_POUT_IDLE ( 1UL << POUT_IDLE )
-#define MSK_POUT_TIMER ( 1UL << POUT_TIMER )
-#define MSK_POUT_SINGLE_SHOT ( 1UL << POUT_SINGLE_SHOT )
-#define MSK_POUT_CYCLIC_PULSE ( 1UL << POUT_CYCLIC_PULSE )
-#define MSK_POUT_PER_SEC ( 1UL << POUT_PER_SEC )
-#define MSK_POUT_PER_MIN ( 1UL << POUT_PER_MIN )
-#define MSK_POUT_PER_HOUR ( 1UL << POUT_PER_HOUR )
-#define MSK_POUT_DCF77 ( 1UL << POUT_DCF77 )
-#define MSK_POUT_POS_OK ( 1UL << POUT_POS_OK )
-#define MSK_POUT_TIME_SYNC ( 1UL << POUT_TIME_SYNC )
-#define MSK_POUT_ALL_SYNC ( 1UL << POUT_ALL_SYNC )
-#define MSK_POUT_TIMECODE ( 1UL << POUT_TIMECODE )
-#define MSK_POUT_TIMESTR ( 1UL << POUT_TIMESTR )
-#define MSK_POUT_10MHZ ( 1UL << POUT_10MHZ )
-#define MSK_POUT_DCF77_M59 ( 1UL << POUT_DCF77_M59 )
-#define MSK_POUT_SYNTH ( 1UL << POUT_SYNTH )
-#define MSK_POUT_TIME_SLOTS ( 1UL << POUT_TIME_SLOTS )
-
-
-/**
- * @brief Bits used with POUT_SETTINGS::flags
+
+/**
+ * @brief Flag bits used to define ::POUT_SETTINGS_FLAGS
+ *
+ * @see ::POUT_SETTINGS_FLAGS
*/
enum POUT_SETTINGS_FLAG_BITS
{
- POUT_BIT_INVERTED, ///< output level has to be inverted
- POUT_BIT_IF_SYNC_ONLY, ///< disable output in holdover mode
- POUT_BIT_TIMEBASE_UTC, ///< use %UTC, only applicable for DCF77 output
+ /// Output level is to be inverted. Can only be used
+ /// if ::POUT_NOT_INVERTIBLE is **not** set, but is
+ /// supported by all ::POUT_MODES.
+ POUT_BIT_INVERTED,
+
+ /// Enable output **only** while synchronized. This even overrides
+ /// the settings in ::ENABLE_FLAGS::pulses, so if this flag is set
+ /// the output is only enabled if the clock is synchronized, and is
+ /// disabled when synchronization is lost, i.e. the device enters
+ /// holdover mode.
+ /// This flag can only be used with outputs that have ::POUT_SUPP_IF_SYNC_ONLY
+ /// set, and is only supported for the ::POUT_MODES specified in
+ /// ::POUT_MODES_SUPP_IF_SYNC_ONLY.
+ POUT_BIT_IF_SYNC_ONLY,
+
+ /// Output %UTC time instead of local time for DCF77 emulation.
+ /// This flag can only be used with outputs that have ::POUT_SUPP_DCF77_UTC
+ /// set, and is only supported for the ::POUT_MODES specified in
+ /// ::POUT_MODES_SUPP_TIMEBASE_UTC (e.g. ::POUT_DCF77 or ::POUT_DCF77_M59).
+ POUT_BIT_TIMEBASE_UTC,
+
N_POUT_SETTINGS_FLAG_BITS ///< Number of known flag bits
};
-#define POUT_INVERTED ( 1UL << POUT_BIT_INVERTED )
-#define POUT_IF_SYNC_ONLY ( 1UL << POUT_BIT_IF_SYNC_ONLY )
-#define POUT_TIMEBASE_UTC ( 1UL << POUT_BIT_TIMEBASE_UTC )
+
+/**
+ * @brief Flag bit masks used with ::POUT_SETTINGS::flags
+ *
+ * @see ::POUT_SETTINGS_FLAG_BITS
+ */
+enum POUT_SETTINGS_FLAGS
+{
+ POUT_INVERTED = ( 1UL << POUT_BIT_INVERTED ), ///< see ::POUT_BIT_INVERTED, ::POUT_NOT_INVERTIBLE
+ POUT_IF_SYNC_ONLY = ( 1UL << POUT_BIT_IF_SYNC_ONLY ), ///< see ::POUT_BIT_IF_SYNC_ONLY, ::POUT_SUPP_IF_SYNC_ONLY
+ POUT_TIMEBASE_UTC = ( 1UL << POUT_BIT_TIMEBASE_UTC ) ///< see ::POUT_BIT_TIMEBASE_UTC, ::POUT_SUPP_DCF77_UTC
+};
+
/**
@@ -3763,21 +6619,24 @@ enum POUT_SETTINGS_FLAG_BITS
*/
typedef struct
{
- uint16_t idx; ///< 0..RECEIVER_INFO::n_prg_out - 1
+ uint16_t idx; ///< 0..::RECEIVER_INFO::n_prg_out-1
POUT_SETTINGS pout_settings;
+
} POUT_SETTINGS_IDX;
#define _mbg_swab_pout_settings_idx_on_set( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->idx ); \
_mbg_swab_pout_settings_on_set( &(_p)->pout_settings ); \
-}
+} while ( 0 )
#define _mbg_swab_pout_settings_idx_on_get( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->idx ); \
_mbg_swab_pout_settings_on_get( &(_p)->pout_settings ); \
-}
+} while ( 0 )
/**
@@ -3793,48 +6652,64 @@ typedef struct
typedef struct
{
POUT_SETTINGS pout_settings;
- uint32_t supp_modes; ///< bit mask of modes supp. by this output, see ::POUT_MODES
- uint8_t timestr_ports; ///< bit mask of COM ports supported for mode ::POUT_TIMESTR, see ::MAX_POUT_TIMESTR_PORTS
- uint8_t reserved_0; ///< reserved for future use, currently 0
- uint16_t reserved_1; ///< reserved for future use, currently 0
- uint32_t flags; ///< @see POUT_INFO_FLAG_BITS
+ uint32_t supp_modes; ///< bit mask of modes supp. by this output, see @ref POUT_MODE_MASKS
+ uint8_t timestr_ports; ///< bit mask of COM ports supported for mode ::POUT_TIMESTR, see ::MAX_POUT_TIMESTR_PORTS
+ uint8_t pulse_shift_res; ///< pulse shift resolution, in [ns], only if ::POUT_SUPP_PULSE_SHIFT, see ::POUT_DATA::pulse_shift
+ uint16_t reserved_1; ///< reserved for future use, currently unused and always 0
+ uint32_t flags; ///< @see ::POUT_INFO_FLAG_MASKS
+
} POUT_INFO;
#define _mbg_swab_pout_info_on_get( _p ) \
+do \
{ \
_mbg_swab_pout_settings_on_get( &(_p)->pout_settings ); \
_mbg_swab32( &(_p)->supp_modes ); \
+ _mbg_swab8( &(_p)->timestr_ports ); \
+ _mbg_swab8( &(_p)->pulse_shift_res ); \
_mbg_swab16( &(_p)->reserved_1 ); \
_mbg_swab32( &(_p)->flags ); \
-}
+} while ( 0 )
-/**
- * The max number of COM ports that can be handled by POUT_INFO::timestr_ports
- */
-#define MAX_POUT_TIMESTR_PORTS 8
+#define MAX_POUT_TIMESTR_PORTS 8 ///< The max number of COM ports that can be handled by ::POUT_INFO::timestr_ports
+
/**
- * @brief Bits used with POUT_INFO::flags
+ * @brief Flag bits used to define ::POUT_INFO_FLAG_MASKS
+ *
+ * @see ::POUT_INFO_FLAG_MASKS
*/
enum POUT_INFO_FLAG_BITS
{
- POUT_BIT_SUPP_IF_SYNC_ONLY, ///< supports disabling outputs in holdover mode
- POUT_BIT_SUPP_DCF77_UTC, ///< supports %UTC output in DCF77 mode
- POUT_BIT_FIXED_PULSE_LEN, ///< pulse length is fixed to the value reported in settings
- POUT_BIT_NOT_INVERTIBLE, ///< output level can not be inverted
+ POUT_BIT_SUPP_IF_SYNC_ONLY, ///< ::POUT_IF_SYNC_ONLY is supported for this output
+ POUT_BIT_SUPP_DCF77_UTC, ///< ::POUT_SUPP_DCF77_UTC is supported for this output
+ POUT_BIT_FIXED_PULSE_LEN, ///< pulse length is limited to the value ::POUT_SETTINGS::mode_param
+ POUT_BIT_NOT_INVERTIBLE, ///< output level can't be inverted, thus ::POUT_INVERTED is not supported for this output
+ POUT_BIT_SUPP_PULSE_SHIFT, ///< output slopes can be shifted, see ::POUT_DATA::pulse_shift
N_POUT_INFO_FLAG_BITS ///< number of known flag bits
};
-#define POUT_SUPP_IF_SYNC_ONLY ( 1UL << POUT_BIT_SUPP_IF_SYNC_ONLY )
-#define POUT_SUPP_DCF77_UTC ( 1UL << POUT_BIT_SUPP_DCF77_UTC )
-#define POUT_FIXED_PULSE_LEN ( 1UL << POUT_BIT_FIXED_PULSE_LEN )
-#define POUT_NOT_INVERTIBLE ( 1UL << POUT_BIT_NOT_INVERTIBLE )
+
+/**
+ * @brief Flag bit masks used with ::POUT_INFO::flags
+ *
+ * @see ::POUT_INFO_FLAG_BITS
+ */
+enum POUT_INFO_FLAG_MASKS
+{
+ POUT_SUPP_IF_SYNC_ONLY = ( 1UL << POUT_BIT_SUPP_IF_SYNC_ONLY ), ///< see ::POUT_BIT_SUPP_IF_SYNC_ONLY, ::POUT_IF_SYNC_ONLY
+ POUT_SUPP_DCF77_UTC = ( 1UL << POUT_BIT_SUPP_DCF77_UTC ), ///< see ::POUT_BIT_SUPP_DCF77_UTC, ::POUT_SUPP_DCF77_UTC
+ POUT_FIXED_PULSE_LEN = ( 1UL << POUT_BIT_FIXED_PULSE_LEN ), ///< see ::POUT_BIT_FIXED_PULSE_LEN
+ POUT_NOT_INVERTIBLE = ( 1UL << POUT_BIT_NOT_INVERTIBLE ), ///< see ::POUT_BIT_NOT_INVERTIBLE, ::POUT_INVERTED
+ POUT_SUPP_PULSE_SHIFT = ( 1UL << POUT_BIT_SUPP_PULSE_SHIFT ) ///< see ::POUT_BIT_SUPP_PULSE_SHIFT, ::POUT_DATA::pulse_shift
+};
+
/**
- * @brief Current settings and general capabilities of a specific serial port
+ * @brief Current settings and general capabilities of a specific programmable pulse output
*
* This structure should be read from the device to retrieve the
* current settings of a specific programmable output plus its capabilities,
@@ -3846,56 +6721,109 @@ enum POUT_INFO_FLAG_BITS
*/
typedef struct
{
- uint16_t idx; ///< 0..RECEIVER_INFO::n_prg_out - 1
+ uint16_t idx; ///< 0..::RECEIVER_INFO::n_prg_out-1
POUT_INFO pout_info;
+
} POUT_INFO_IDX;
#define _mbg_swab_pout_info_idx_on_get( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->idx ); \
_mbg_swab_pout_info_on_get( &(_p)->pout_info ); \
-}
+} while ( 0 )
+/** @} defgroup group_pout_api */
-/*
- * The codes below are used with devices which support multiple
- * ref time sources at the same time. The priorities of the
- * supported ref time sources is configurable.
- */
/**
- * @brief All possibly supported ref time sources
+ * @defgroup group_multi_ref_all Support for multiple reference time sources
+ *
+ * Some devices can evaluate and synchronize to several different types
+ * of input signal, and eventually even several signals of the same type,
+ * e.g. several 1 PPS input signals.
+ *
+ * There are two different ways to configure multi ref devices.
+ *
+ * Newer devices which have the ::GPS_HAS_XMULTI_REF flag set in
+ * ::RECEIVER_INFO::features support the newer XMULTI_REF_... structures
+ * which provide a more flexible API, see @ref group_multi_ref_ext
+ *
+ * Older devices may have the ::GPS_FEAT_MULTI_REF flag set in which
+ * case an older API is supported, see @ref group_multi_ref_old
+ *
+ * Symbols defined in @ref group_multi_ref_common can be used
+ * with both APIs.
+ *
+ * @see @ref group_multi_ref_common
+ * @see @ref group_multi_ref_old
+ * @see @ref group_multi_ref_ext
+ * @{ */
+
+/**
+ * @defgroup group_multi_ref_common Common multi ref definitions
+ *
+ * Common definitions used with both the old and the extended
+ * multi ref API.
+ *
+ * @{ */
+
+/**
+ * @brief Enumeration of all known types of reference time source
*
- * @see MULTI_REF_TYPE_MASKS
+ * All known types of input signal which may possibly be supported
+ * by devices which support several different input signals, i.e.
+ * have the ::GPS_HAS_MULTI_REF or ::GPS_HAS_XMULTI_REF bit set
+ * in ::RECEIVER_INFO::features. Not all devices support each known
+ * type of input signal.
+ *
+ * @see @ref group_multi_ref_all
+ * @see ::DEFAULT_MULTI_REF_NAMES
+ * @see ::DEFAULT_MULTI_REF_NAMES_SHORT
+ * @see @ref MULTI_REF_TYPE_MASKS
*/
enum MULTI_REF_TYPES
{
- MULTI_REF_NONE = -1, ///< nothing, undefined
- MULTI_REF_GPS = 0, ///< standard GPS
- MULTI_REF_10MHZ, ///< 10 MHz input frequency
- MULTI_REF_PPS, ///< 1 PPS input signal
- MULTI_REF_10MHZ_PPS, ///< combined 10 MHz plus PPS
- MULTI_REF_IRIG, ///< IRIG input
- MULTI_REF_NTP, ///< Network Time Protocol (NTP)
- MULTI_REF_PTP, ///< Precision Time Protocol (PTP, IEEE1588)
- MULTI_REF_PTP_E1, ///< PTP over E1
- MULTI_REF_FREQ, ///< fixed frequency
- MULTI_REF_PPS_STRING, ///< PPS in addition to string
- MULTI_REF_GPIO, ///< variable input signal via GPIO
- MULTI_REF_INTERNAL, ///< reserved, used internally by firmware only
- MULTI_REF_PZF, ///< DCF77 PZF providing much more accuracy than a standard LWR
- MULTI_REF_LWR, ///< long wave receiver. e.g. DCF77 AM, WWVB, MSF, JJY
- MULTI_REF_GRC, ///< Glonass / GPS receiver
- MULTI_REF_HAVEQUICK, ///< HaveQuick input
- N_MULTI_REF ///< the number of defined sources, can not exceed bit number of uint32_t - 1
+ /// This ref type must not be used as index, but marks particular
+ /// ::XMULTI_REF_SETTINGS structures as "unused". It is only
+ /// supported if bit ::XMRIF_BIT_MRF_NONE_SUPP is set.
+ MULTI_REF_NONE = -1,
+
+ MULTI_REF_GPS = 0, ///< standard GPS
+ MULTI_REF_10MHZ, ///< 10 MHz input frequency
+ MULTI_REF_PPS, ///< 1 PPS input signal
+ MULTI_REF_10MHZ_PPS, ///< combined 10 MHz plus PPS
+ MULTI_REF_IRIG, ///< IRIG input
+ MULTI_REF_NTP, ///< Network Time Protocol (NTP)
+ MULTI_REF_PTP, ///< Precision Time Protocol (PTP/IEEE1588)
+ MULTI_REF_PTP_E1, ///< PTP over E1
+ MULTI_REF_FREQ, ///< fixed frequency
+ MULTI_REF_PPS_STRING, ///< 1 PPS in addition to time string
+ MULTI_REF_GPIO, ///< variable input signal via GPIO
+ MULTI_REF_INTERNAL, ///< reserved, used internally by firmware only
+ MULTI_REF_PZF, ///< DCF77 PZF providing much more accuracy than a standard LWR
+ MULTI_REF_LWR, ///< long wave receiver. e.g. DCF77 AM, WWVB, MSF, JJY
+ MULTI_REF_GRC, ///< Glonass / GPS receiver
+ MULTI_REF_HAVEQUICK, ///< HaveQuick input
+ MULTI_REF_EXT_OSC, ///< external oscillator disciplined and looped back via 1 PPS I/O
+ MULTI_REF_SYNCE, ///< Synchronous Ethernet, needs (external) ethernet interface
+ N_MULTI_REF ///< the number of defined sources, must not exceed ::MAX_N_MULTI_REF_TYPES
};
+/**
+ * @brief Theoretical maximum number of multi ref input signal types
+ *
+ * Actually only ::N_MULTI_REF types have been defined, but ::N_MULTI_REF
+ * must not exceed the number of bits which can be hold by a uint32_t type.
+ */
+#define MAX_N_MULTI_REF_TYPES 32
+
/**
- * @brief Names of supported ref time sources
+ * @brief Names of known ref time sources
*
- * @see MULTI_REF_TYPES
+ * @see ::MULTI_REF_TYPES
*/
#define DEFAULT_MULTI_REF_NAMES \
{ \
@@ -3914,49 +6842,93 @@ enum MULTI_REF_TYPES
"DCF77 PZF Receiver", \
"Long Wave Receiver", \
"GLONASS/GPS Receiver", \
- "HaveQuick Input" \
+ "HaveQuick Input", \
+ "ext. Osc.", \
+ "Synchronous Ethernet" \
+}
+
+/**
+ * @brief Short names of supported ref time sources
+ *
+ * Used e.g. to configure a particular input signal type
+ *
+ * @see ::MULTI_REF_TYPES
+ */
+#define DEFAULT_MULTI_REF_NAMES_SHORT \
+{ \
+ "GPS", \
+ "FRQ", \
+ "PPS", \
+ "10MHZ+PPS", \
+ "TCR", \
+ "NTP", \
+ "PTP", \
+ "PTP_E1", \
+ "FIXED_FREQ", \
+ "STRING+PPS", \
+ "GPIO", \
+ "(reserved)", \
+ "PZF", \
+ "LWR", \
+ "GGR", \
+ "HQI", \
+ "EXT", \
+ "SYNCE" \
}
/**
- * @brief Bit masks according to enumerated ref time sources
+ * @brief Bit masks associated with multi ref types
*
- * @see MULTI_REF_TYPES
- */
-enum MULTI_REF_TYPE_MASKS
-{
- HAS_MULTI_REF_GPS = ( 1UL << MULTI_REF_GPS ), ///< see ::MULTI_REF_GPS
- HAS_MULTI_REF_10MHZ = ( 1UL << MULTI_REF_10MHZ ), ///< see ::MULTI_REF_10MHZ
- HAS_MULTI_REF_PPS = ( 1UL << MULTI_REF_PPS ), ///< see ::MULTI_REF_PPS
- HAS_MULTI_REF_10MHZ_PPS = ( 1UL << MULTI_REF_10MHZ_PPS ), ///< see ::MULTI_REF_10MHZ_PPS
- HAS_MULTI_REF_IRIG = ( 1UL << MULTI_REF_IRIG ), ///< see ::MULTI_REF_IRIG
- HAS_MULTI_REF_NTP = ( 1UL << MULTI_REF_NTP ), ///< see ::MULTI_REF_NTP
- HAS_MULTI_REF_PTP = ( 1UL << MULTI_REF_PTP ), ///< see ::MULTI_REF_PTP
- HAS_MULTI_REF_PTP_E1 = ( 1UL << MULTI_REF_PTP_E1 ), ///< see ::MULTI_REF_PTP_E1
+ * Used to indicate which multi ref types are supported, e.g.
+ * in ::XMULTI_REF_INFO::supp_ref or ::MULTI_REF_INFO::supp_ref.
+ *
+ * @see ::MULTI_REF_TYPES
+ *
+ * @anchor MULTI_REF_TYPE_MASKS @{ */
- HAS_MULTI_REF_FREQ = ( 1UL << MULTI_REF_FREQ ), ///< see ::MULTI_REF_FREQ
- HAS_MULTI_REF_PPS_STRING = ( 1UL << MULTI_REF_PPS_STRING ), ///< see ::MULTI_REF_PPS_STRING
- HAS_MULTI_REF_GPIO = ( 1UL << MULTI_REF_GPIO ), ///< see ::MULTI_REF_GPIO
- HAS_MULTI_REF_INTERNAL = ( 1UL << MULTI_REF_INTERNAL ), ///< see ::MULTI_REF_INTERNAL
- HAS_MULTI_REF_PZF = ( 1UL << MULTI_REF_PZF ), ///< see ::MULTI_REF_PZF
- HAS_MULTI_REF_LWR = ( 1UL << MULTI_REF_LWR ), ///< see ::MULTI_REF_LWR
- HAS_MULTI_REF_GRC = ( 1UL << MULTI_REF_GRC ), ///< see ::MULTI_REF_GRC
- HAS_MULTI_REF_HAVEQUICK = ( 1UL << MULTI_REF_HAVEQUICK ) ///< see ::MULTI_REF_HAVEQUICK
-};
+#define HAS_MULTI_REF_GPS ( 1UL << MULTI_REF_GPS ) ///< see ::MULTI_REF_GPS
+#define HAS_MULTI_REF_10MHZ ( 1UL << MULTI_REF_10MHZ ) ///< see ::MULTI_REF_10MHZ
+#define HAS_MULTI_REF_PPS ( 1UL << MULTI_REF_PPS ) ///< see ::MULTI_REF_PPS
+#define HAS_MULTI_REF_10MHZ_PPS ( 1UL << MULTI_REF_10MHZ_PPS ) ///< see ::MULTI_REF_10MHZ_PPS
+#define HAS_MULTI_REF_IRIG ( 1UL << MULTI_REF_IRIG ) ///< see ::MULTI_REF_IRIG
+#define HAS_MULTI_REF_NTP ( 1UL << MULTI_REF_NTP ) ///< see ::MULTI_REF_NTP
+#define HAS_MULTI_REF_PTP ( 1UL << MULTI_REF_PTP ) ///< see ::MULTI_REF_PTP
+#define HAS_MULTI_REF_PTP_E1 ( 1UL << MULTI_REF_PTP_E1 ) ///< see ::MULTI_REF_PTP_E1
+#define HAS_MULTI_REF_FREQ ( 1UL << MULTI_REF_FREQ ) ///< see ::MULTI_REF_FREQ
+#define HAS_MULTI_REF_PPS_STRING ( 1UL << MULTI_REF_PPS_STRING ) ///< see ::MULTI_REF_PPS_STRING
+#define HAS_MULTI_REF_GPIO ( 1UL << MULTI_REF_GPIO ) ///< see ::MULTI_REF_GPIO
+#define HAS_MULTI_REF_INTERNAL ( 1UL << MULTI_REF_INTERNAL ) ///< see ::MULTI_REF_INTERNAL
+#define HAS_MULTI_REF_PZF ( 1UL << MULTI_REF_PZF ) ///< see ::MULTI_REF_PZF
+#define HAS_MULTI_REF_LWR ( 1UL << MULTI_REF_LWR ) ///< see ::MULTI_REF_LWR
+#define HAS_MULTI_REF_GRC ( 1UL << MULTI_REF_GRC ) ///< see ::MULTI_REF_GRC
+#define HAS_MULTI_REF_HAVEQUICK ( 1UL << MULTI_REF_HAVEQUICK ) ///< see ::MULTI_REF_HAVEQUICK
-/*
- * There are 2 different ways to configure multi ref support
- * provided by some devices.
+#define HAS_MULTI_REF_EXT_OSC ( 1UL << MULTI_REF_EXT_OSC ) ///< see ::MULTI_REF_EXT_OSC
+#define HAS_MULTI_REF_SYNCE ( 1UL << MULTI_REF_SYNCE ) ///< see ::MULTI_REF_SYNCE
+
+/** @} anchor MULTI_REF_TYPE_MASKS */
+
+/** @} defgroup group_multi_ref_common */
+
+
+
+/**
+ * @defgroup group_multi_ref_old Definitions used with the old multi ref API
+ *
+ * This API has been deprecated by a newer one which should be used preferably.
*
- * Newer devices which have the GPS_FEAT_XMULTI_REF flag set
- * in RECEIVER_INFO::features support the newer XMULTI_REF_...
- * structures which provide a more flexible interface.
+ * @see @ref group_multi_ref_ext
*
- * Older devices which have the GPS_FEAT_MULTI_REF flag set
- * support these MULTI_REF_... structures below where
- * the number of supported input sources and priorities
- * is limited to N_MULTI_REF_PRIO.
+ * @{ */
+
+/**
+ * @brief Maximum number of input sources
+ *
+ * The number of supported input sources and priorities is
+ * limited to this value if the old API is used, i.e. if only
+ * the ::GPS_FEAT_MULTI_REF flag is set.
*/
#define N_MULTI_REF_PRIO 4
@@ -3967,12 +6939,13 @@ enum MULTI_REF_TYPE_MASKS
* The number stored in prio[0] of the array indicates the ref time
* source with highest priority. If that source fails, the device
* falls back to the source indicated by prio[1]. Each field of
- * the prio[] array must be set to one of the values 0..N_MULTI_REF-1,
- * or to -1 (0xFF) if the value is not assigned.
+ * the prio[] array has to be set to one of the values 0..::N_MULTI_REF-1,
+ * or to ::MULTI_REF_NONE if no time source is specified.
*/
typedef struct
{
uint8_t prio[N_MULTI_REF_PRIO];
+
} MULTI_REF_SETTINGS;
@@ -3984,20 +6957,25 @@ typedef struct
typedef struct
{
MULTI_REF_SETTINGS settings; ///< current settings
- uint32_t supp_ref; ///< bit mask of supported sources, see ::MULTI_REF_TYPE_MASKS
- uint16_t n_levels; ///< supp. levels, 0..N_MULTI_REF_PRIO-1
+ uint32_t supp_ref; ///< bit mask of supported sources, see @ref MULTI_REF_TYPE_MASKS
+ uint16_t n_levels; ///< supported priority levels, 0..::N_MULTI_REF_PRIO-1
uint16_t flags; ///< reserved, currently always 0
+
} MULTI_REF_INFO;
/**
* @brief A data type used to query MULTI_REF status information
+ *
+ * @see ::MULTI_REF_STATUS_BIT_MASKS
*/
-typedef uint16_t MULTI_REF_STATUS; ///< @see MULTI_REF_STATUS_BITS
+typedef uint16_t MULTI_REF_STATUS;
/**
- * @brief Bits and associated masks used with ::MULTI_REF_STATUS
+ * @brief Enumeration of multi ref status bits
+ *
+ * @see ::MULTI_REF_STATUS_BIT_MASKS
*/
enum MULTI_REF_STATUS_BITS
{
@@ -4005,53 +6983,106 @@ enum MULTI_REF_STATUS_BITS
WRN_COLD_BOOT, ///< GPS is in cold boot mode
WRN_WARM_BOOT, ///< GPS is in warm boot mode
WRN_ANT_DISCONN, ///< antenna is disconnected
- WRN_10MHZ_UNLOCK, ///< impossible to lock to external 10MHz reference
- WRN_1PPS_UNLOCK, ///< impossible to lock to external 1PPS reference
+ WRN_10MHZ_UNLOCK, ///< impossible to lock to external 10 MHz reference
+ WRN_1PPS_UNLOCK, ///< impossible to lock to external 1 PPS reference
WRN_GPS_UNLOCK, ///< impossible to lock to GPS
- WRN_10MHZ_MISSING, ///< external 10MHz signal not available
- WRN_1PPS_MISSING, ///< external 1PPS signal not available
+ WRN_10MHZ_MISSING, ///< external 10 MHz signal not available
+ WRN_1PPS_MISSING, ///< external 1 PPS signal not available
N_MULTI_REF_STATUS_BITS ///< the number of known bits
};
-#define MSK_WRN_COLD_BOOT ( 1UL << WRN_COLD_BOOT )
-#define MSK_WRN_WARM_BOOT ( 1UL << WRN_WARM_BOOT )
-#define MSK_WRN_ANT_DISCONN ( 1UL << WRN_ANT_DISCONN )
-#define MSK_WRN_10MHZ_UNLOCK ( 1UL << WRN_10MHZ_UNLOCK )
-#define MSK_WRN_1PPS_UNLOCK ( 1UL << WRN_1PPS_UNLOCK )
-#define MSK_WRN_GPS_UNLOCK ( 1UL << WRN_GPS_UNLOCK )
-#define MSK_WRN_10MHZ_MISSING ( 1UL << WRN_10MHZ_MISSING )
-#define MSK_WRN_1PPS_MISSING ( 1UL << WRN_1PPS_MISSING )
-#define MSK_WRN_MODULE_MODE ( 1UL << WRN_MODULE_MODE )
+
+/**
+ * @brief Bit masks associated with ::MULTI_REF_STATUS_BITS
+ *
+ * Used with ::MULTI_REF_STATUS.
+ *
+ * @see ::MULTI_REF_STATUS_BITS
+ */
+enum MULTI_REF_STATUS_BIT_MASKS
+{
+ MSK_WRN_COLD_BOOT = ( 1UL << WRN_COLD_BOOT ), ///< see ::WRN_COLD_BOOT
+ MSK_WRN_WARM_BOOT = ( 1UL << WRN_WARM_BOOT ), ///< see ::WRN_WARM_BOOT
+ MSK_WRN_ANT_DISCONN = ( 1UL << WRN_ANT_DISCONN ), ///< see ::WRN_ANT_DISCONN
+ MSK_WRN_10MHZ_UNLOCK = ( 1UL << WRN_10MHZ_UNLOCK ), ///< see ::WRN_10MHZ_UNLOCK
+ MSK_WRN_1PPS_UNLOCK = ( 1UL << WRN_1PPS_UNLOCK ), ///< see ::WRN_1PPS_UNLOCK
+ MSK_WRN_GPS_UNLOCK = ( 1UL << WRN_GPS_UNLOCK ), ///< see ::WRN_GPS_UNLOCK
+ MSK_WRN_10MHZ_MISSING = ( 1UL << WRN_10MHZ_MISSING ), ///< see ::WRN_10MHZ_MISSING
+ MSK_WRN_1PPS_MISSING = ( 1UL << WRN_1PPS_MISSING ), ///< see ::WRN_1PPS_MISSING
+ MSK_WRN_MODULE_MODE = ( 1UL << WRN_MODULE_MODE ) ///< see ::WRN_MODULE_MODE
+};
+
+/** @} defgroup group_multi_ref_old */
/**
- * @defgroup group_xmr_cfg Extended multiref configuration stuff
+ * @defgroup group_multi_ref_ext Extended multi ref definitions
+ *
+ * If the ::GPS_HAS_XMULTI_REF feature is set in ::RECEIVER_INFO::features then
+ * the XMULTI_REF (extended multi ref, XMR) feature and API are supported and
+ * have to be used in favor of the older multi ref API (see @ref group_multi_ref_old).
+ *
+ * Devices supporting the XMULTI_REF feature provide a number of
+ * priority levels addressed by the priority index, starting at 0
+ * for highest priority. A single reference time source from the set
+ * of supported sources can be assigned to each priority level.
+ *
+ * These structures are used to configure the individual time source for each
+ * priority level, and retrieve the status of the time source at each priority level.
+ *
+ * If ::GPS_HAS_XMRS_MULT_INSTC is also set in ::RECEIVER_INFO::features then
+ * ::XMULTI_REF_INSTANCES can be used to find out which types of input source
+ * are supported (::XMULTI_REF_INSTANCES::n_inst array entries != 0), and
+ * how many priority levels are supported to which an input source can be
+ * assigned (::XMULTI_REF_INSTANCES::n_xmr_settings).
+ *
+ * If ::XMRIF_MSK_HOLDOVER_STATUS_SUPP is set in ::XMULTI_REF_INSTANCES::flags
+ * then ::XMR_HOLDOVER_STATUS can be used to monitor the switching between
+ * different time sources when they become available or unavailable.
+ *
+ * If an XMR time source at a high priority level becomes unavailable the
+ * XMR control function tries to find and switch to a different time source
+ * at a lower level of the priority list, which is still available.
+ *
+ * On the other hand, if a time source at a higher priority level becomes
+ * available again, the XMR control function switches over to the time source
+ * at the higher priority even if the current time source is still available.
*
- * If the RECEIVER_INFO::features flag GPS_FEAT_XMULTI_REF is set
- * then the following XMULTI_REF_... data structures must be used
- * instead of the older MULTI_REF_... structures.
+ * If the accuracy of the time source at the next priority level is better than
+ * the accuracy of the time source at the current priority level then switching
+ * can be done immediately. However, if the next time source is worse than
+ * the current one it makes more sense to switch only after a certain holdover
+ * interval.
*
- * Those devices support a number of priority levels addressed by
- * the priority index, starting at 0 for highest priority. A single
- * reference time source from the set of supported sources can be
- * assigned to each priority level.
+ * The holdover interval is computed so that the time error due to the expected
+ * drift of the previously disciplined time base grows until it reaches the
+ * accuracy level of the next available reference time source.
*
- * These structures are used to configure the individual
- * time source for each priority level, and retrieve the status
- * of the time source at each priority level.
+ * Only if the time source at the current priority level is still unavailable
+ * when the holdover interval expires the reference time source is switched
+ * to the time source at the next available priority level.
*
* @{ */
+
/**
* @brief Identifier for a reference source
*/
typedef struct
{
- uint8_t type; ///< @see MULTI_REF_TYPES
+ uint8_t type; ///< see ::MULTI_REF_TYPES, and note for ::XMRIF_BIT_MRF_NONE_SUPP
uint8_t instance; ///< instance number, if multiple instances are supported, else 0
+
} XMULTI_REF_ID;
+#define _mbg_swab_xmulti_ref_id( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->type ); \
+ _mbg_swab8( &(_p)->instance ); \
+} while ( 0 )
+
/**
@@ -4059,52 +7090,129 @@ typedef struct
*/
typedef struct
{
- XMULTI_REF_ID id; ///< time source identifier
- uint16_t flags; ///< reserved, currently always 0
- NANO_TIME bias; ///< time bias, e.g. path delay
- NANO_TIME precision; ///< precision of the time source
- uint32_t fine_limit; ///< smooth control if below this limit
+ XMULTI_REF_ID id; ///< reference time source identifier
+ uint16_t flags; ///< see ::XMR_SETTINGS_FLAG_MSKS and ::XMR_EXT_SRC_INFO::supp_flags
+ NANO_TIME bias; ///< time bias, e.g. path delay @todo specify sign vs. earlier/later
+ NANO_TIME precision; ///< precision of the time source
+ uint32_t reserved; ///< reserved, currently always 0
+
} XMULTI_REF_SETTINGS;
+#define _mbg_swab_xmulti_ref_settings( _p ) \
+do \
+{ \
+ _mbg_swab_xmulti_ref_id( &(_p)->id ); \
+ _mbg_swab16( &(_p)->flags ); \
+ _mbg_swab_nano_time( &(_p)->bias ); \
+ _mbg_swab_nano_time( &(_p)->precision ); \
+ _mbg_swab32( &(_p)->reserved ); \
+} while ( 0 )
+
/**
- * @brief Reference source configuration settings for a specific priority level
+ * @brief Reference source configuration for a specific priority level
*
- * @note After configuring, a structure with idx == 0xFFFF (-1) must be sent
- * to let the changes become effective.
+ * @note After all other ::XMULTI_REF_SETTINGS_IDX configuration structures
+ * have been sent to a device, an additional structure with idx == -1 (0xFFFF)
+ * has to be sent to let the new settings come into effect.
*/
typedef struct
{
- uint16_t idx; ///< the priority level index, highest == 0
- XMULTI_REF_SETTINGS settings; ///< the settings configured for this level
+ uint16_t idx; ///< the priority level index (highest == 0), 0..::XMULTI_REF_INSTANCES::n_xmr_settings-1
+ XMULTI_REF_SETTINGS settings; ///< the settings configured for this level
+
} XMULTI_REF_SETTINGS_IDX;
+#define _mbg_swab_xmulti_ref_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_xmulti_ref_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Bit masks used to define ::XMR_SETTINGS_FLAG_MSKS
+ */
+enum XMR_SETTINGS_FLAG_BITS
+{
+ XMRSF_BIT_AUTO_BIAS_MASTER, ///< src is allowed to operate as zero asymmetry master
+ XMRSF_BIT_AUTO_BIAS_SLAVE, ///< accept static bias correction from zero asymmetry master
+ XMRSF_BIT_ASYMMETRY_STEP_DETECTION, ///< static bias auto correction in case of step
+ N_XMRSF_BITS ///< number of known flag bits
+};
+
+
+/**
+ * @brief Bit masks used with ::XMULTI_REF_SETTINGS::flags and ::XMR_EXT_SRC_INFO::supp_flags
+ */
+enum XMR_SETTINGS_FLAG_MSKS
+{
+ XMRSF_MSK_AUTO_BIAS_MASTER = ( 1UL << XMRSF_BIT_AUTO_BIAS_MASTER ), ///< see ::XMRSF_BIT_AUTO_BIAS_MASTER
+ XMRSF_MSK_AUTO_BIAS_SLAVE = ( 1UL << XMRSF_BIT_AUTO_BIAS_SLAVE ), ///< see ::XMRSF_BIT_AUTO_BIAS_SLAVE
+ XMRSF_MSK_ASYMMETRY_STEP_DETECTION = ( 1UL << XMRSF_BIT_ASYMMETRY_STEP_DETECTION ) ///< see ::XMRSF_BIT_ASYMMETRY_STEP_DETECTION
+};
+
/**
- * @brief Reference source configuration settings and capabilities
+ * @brief Reference source capabilities and current configuration
*/
typedef struct
{
- XMULTI_REF_SETTINGS settings; ///< current settings
- uint32_t supp_ref; ///< bit mask of supported sources, see ::MULTI_REF_TYPES
- uint8_t n_supp_ref; ///< number of supported ref time sources
- uint8_t n_prio; ///< number of supported priority levels
- uint16_t flags; ///< currently always 0
+ XMULTI_REF_SETTINGS settings; ///< current settings
+
+ /**
+ * @deprecated Deprecated by ::XMULTI_REF_INSTANCES::n_inst.
+ * If ::GPS_HAS_XMRS_MULT_INSTC is *not* set then this field provides
+ * a bit mask of supported sources (see @ref MULTI_REF_TYPE_MASKS),
+ * and only a single instance of each source signal type is supported.
+ */
+ uint32_t supp_ref;
+
+ /**
+ * @deprecated Deprecated by ::XMULTI_REF_INSTANCES::n_xmr_settings.
+ * If ::GPS_HAS_XMRS_MULT_INSTC is *not* set then this field
+ * reports the number of priority levels supported by the device.
+ */
+ uint8_t n_supp_ref;
+
+ uint8_t n_prio; ///< reserved, don't use, currently always 0 //##++++ TODO: check which devices support/use this field
+ uint16_t flags; ///< reserved, don't use, currently always 0
+
} XMULTI_REF_INFO;
+#define _mbg_swab_xmulti_ref_info( _p ) \
+do \
+{ \
+ _mbg_swab_xmulti_ref_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->supp_ref ); \
+ _mbg_swab8( &(_p)->n_supp_ref ); \
+ _mbg_swab8( &(_p)->n_prio ); \
+ _mbg_swab16( &(_p)->flags ); \
+} while ( 0 )
+
/**
- * @brief Reference source configuration settings and capabilities for a specific priority level
+ * @brief Reference source capabilities and current configuration for a specific priority level
*/
typedef struct
{
- uint16_t idx; ///< the priority level index, highest == 0
- XMULTI_REF_INFO info; ///< ref source cfg and capabilities
+ uint16_t idx; ///< the priority level index (highest == 0), 0..::XMULTI_REF_INSTANCES::n_xmr_settings-1
+ XMULTI_REF_INFO info; ///< ref source configuration and capabilities
+
} XMULTI_REF_INFO_IDX;
+#define _mbg_swab_xmulti_ref_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_xmulti_ref_info( &(_p)->info ); \
+} while ( 0 )
+
/**
@@ -4112,14 +7220,26 @@ typedef struct
*/
typedef struct
{
- XMULTI_REF_ID id; ///< time source identifier, see ::MULTI_REF_TYPES
- uint16_t status; ///< status bits, see ::XMR_REF_STATUS_BITS
- NANO_TIME offset; ///< time offset from main time base
- uint16_t flags; ///< flags, see ::XMR_REF_FLAG_BITS
- uint8_t ssm; ///< synchronization status message (if supported by src.)
- uint8_t soc; ///< signal outage counter (updated on loss of signal)
+ XMULTI_REF_ID id; ///< time source identifier
+ uint16_t status; ///< status bits, see @ref XMR_REF_STATUS_BIT_MASKS
+ NANO_TIME offset; ///< time offset from main time base @todo specify sign vs. earlier/later
+ uint16_t flags; ///< flags, see ::XMR_QL // TODO ###
+ uint8_t ssm; ///< synchronization status message, if supported by signal source
+ uint8_t soc; ///< signal outage counter, incremented on loss of signal
+
} XMULTI_REF_STATUS;
+#define _mbg_swab_xmulti_ref_status( _p ) \
+do \
+{ \
+ _mbg_swab_xmulti_ref_id( &(_p)->id ); \
+ _mbg_swab16( &(_p)->status ); \
+ _mbg_swab_nano_time( &(_p)->offset ); \
+ _mbg_swab16( &(_p)->flags ); \
+ _mbg_swab8( &(_p)->ssm ); \
+ _mbg_swab8( &(_p)->soc ); \
+} while ( 0 )
+
/**
@@ -4127,46 +7247,109 @@ typedef struct
*/
typedef struct
{
- uint16_t idx; /**< the priority level index, highest == 0 */
- XMULTI_REF_STATUS status; /**< status information */
+ uint16_t idx; ///< the priority level index (highest == 0), 0..::XMULTI_REF_INSTANCES::n_xmr_settings-1
+ XMULTI_REF_STATUS status; ///< status information
} XMULTI_REF_STATUS_IDX;
+#define _mbg_swab_xmulti_ref_status_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_xmulti_ref_status( &(_p)->status ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief ::TODO
+ *
+ * Used with the ::... field of ::XMULTI_REF_STATUS::flags
+ *
+ * @see ::XMULTI_REF_STATUS::flags
+ * @see ::XMR_QL_MASK
+ * @see ::_GET_XMR_QL
+ * @see ::_PUT_XMR_QL
+ */
+enum XMR_QL
+{
+ XMR_QL_UNKNOWN,
+ XMR_QL_GREEN,
+ XMR_QL_YELLOW,
+ XMR_QL_RED,
+ N_XMR_QL
+};
+
+#define XMR_QL_TDEV_MASK ( 0x03 << 0 )
+#define XMR_QL_MTIE_MASK ( 0x03 << 2 )
+
+#define _GET_XMR_QL_TDEV( _x ) ( ( ( _x ) & XMR_QL_TDEV_MASK ) >> 0 )
+#define _PUT_XMR_QL_TDEV( _x, _ql ) \
+do { \
+ ( _x ) = ( ( _x ) & ~XMR_QL_TDEV_MASK ) | ( ( ( _ql ) << 0 ) & XMR_QL_TDEV_MASK ); \
+} while ( 0 )
+
+
+#define _GET_XMR_QL_MTIE( _x ) ( ( ( _x ) & XMR_QL_MTIE_MASK ) >> 2 )
+#define _PUT_XMR_QL_MTIE( _x, _ql ) \
+do { \
+ ( _x ) = ( ( _x ) & ~XMR_QL_MTIE_MASK ) | ( ( ( _ql ) << 2 ) & XMR_QL_MTIE_MASK ); \
+} while ( 0 )
+
/**
- * @brief Bits and bit masks used with XMULTI_REF_STATUS::status
+ * @brief XMULTI_REF status bits
*/
enum XMR_REF_STATUS_BITS
{
- XMRS_BIT_NOT_SUPP, ///< ref type cfg'd for this level is not supported
- XMRS_BIT_NO_CONN, ///< input signal is disconnected
- XMRS_BIT_NO_SIGNAL, ///< no input signal
- XMRS_BIT_IS_MASTER, ///< reference is master source
- XMRS_BIT_IS_LOCKED, ///< locked to input signal
- XMRS_BIT_IS_ACCURATE, ///< oscillator control has reached full accuracy
- XMRS_BIT_NOT_SETTLED, ///< reference time signal not settled
- XMRS_BIT_NOT_PHASE_LOCKED, ///< oscillator not phase locked to PPS
- XMRS_BIT_NUM_SRC_EXC, ///< number of available sources exceeds what can be handled
- XMRS_BIT_IS_EXTERNAL, ///< this ref source is on extension card
- XMRS_BIT_LOW_JITTER, ///< this ref source has low jitter
- N_XMRS_BITS ///< number of know status bits
-};
-
-#define XMRS_MSK_NOT_SUPP ( 1UL << XMRS_BIT_NOT_SUPP )
-#define XMRS_MSK_NO_CONN ( 1UL << XMRS_BIT_NO_CONN )
-#define XMRS_MSK_NO_SIGNAL ( 1UL << XMRS_BIT_NO_SIGNAL )
-#define XMRS_MSK_IS_MASTER ( 1UL << XMRS_BIT_IS_MASTER )
-#define XMRS_MSK_IS_LOCKED ( 1UL << XMRS_BIT_IS_LOCKED )
-#define XMRS_MSK_IS_ACCURATE ( 1UL << XMRS_BIT_IS_ACCURATE )
-#define XMRS_MSK_NOT_SETTLED ( 1UL << XMRS_BIT_NOT_SETTLED )
-#define XMRS_MSK_NOT_PHASE_LOCKED ( 1UL << XMRS_BIT_NOT_PHASE_LOCKED )
-#define XMRS_MSK_NUM_SRC_EXC ( 1UL << XMRS_BIT_NUM_SRC_EXC )
-#define XMRS_MSK_IS_EXTERNAL ( 1UL << XMRS_BIT_IS_EXTERNAL )
-#define XMRS_MSK_LOW_JITTER ( 1UL << XMRS_BIT_LOW_JITTER )
+ XMRS_BIT_NOT_SUPP, ///< ref type cfg'd for this level is not supported
+ XMRS_BIT_NO_CONN, ///< input signal is disconnected
+ XMRS_BIT_NO_SIGNAL, ///< no input signal
+ XMRS_BIT_IS_MASTER, ///< reference is master source
+ XMRS_BIT_IS_LOCKED, ///< locked to input signal
+ XMRS_BIT_IS_ACCURATE, ///< oscillator control has reached full accuracy
+ XMRS_BIT_NOT_SETTLED, ///< reference time signal not settled
+ XMRS_BIT_NOT_PHASE_LOCKED, ///< oscillator not phase locked to PPS
+ XMRS_BIT_NUM_SRC_EXC, ///< number of available sources exceeds what can be handled
+ XMRS_BIT_IS_EXTERNAL, ///< this ref source is on extension card
+ XMRS_BIT_LOW_JITTER, ///< this ref source has low jitter
+ XMRS_BIT_ITU_LIMIT_VIOLATED, ///< ITU limits violated (valid if device has ::XMR_METRICS)
+ N_XMRS_BITS ///< number of know status bits
+};
-/*
- * Initializers for XMRS status bit strings.
+
+
+/**
+ * @brief Bit masks associated with ::XMR_REF_STATUS_BITS
+ *
+ * Used with ::XMULTI_REF_STATUS::status.
+ *
+ * @see ::XMR_REF_STATUS_BITS
+ *
+ * @anchor XMR_REF_STATUS_BIT_MASKS @{ */
+
+#define XMRS_MSK_NOT_SUPP ( 1UL << XMRS_BIT_NOT_SUPP ) ///< see ::XMRS_BIT_NOT_SUPP
+#define XMRS_MSK_NO_CONN ( 1UL << XMRS_BIT_NO_CONN ) ///< see ::XMRS_BIT_NO_CONN
+#define XMRS_MSK_NO_SIGNAL ( 1UL << XMRS_BIT_NO_SIGNAL ) ///< see ::XMRS_BIT_NO_SIGNAL
+#define XMRS_MSK_IS_MASTER ( 1UL << XMRS_BIT_IS_MASTER ) ///< see ::XMRS_BIT_IS_MASTER
+#define XMRS_MSK_IS_LOCKED ( 1UL << XMRS_BIT_IS_LOCKED ) ///< see ::XMRS_BIT_IS_LOCKED
+#define XMRS_MSK_IS_ACCURATE ( 1UL << XMRS_BIT_IS_ACCURATE ) ///< see ::XMRS_BIT_IS_ACCURATE
+#define XMRS_MSK_NOT_SETTLED ( 1UL << XMRS_BIT_NOT_SETTLED ) ///< see ::XMRS_BIT_NOT_SETTLED
+#define XMRS_MSK_NOT_PHASE_LOCKED ( 1UL << XMRS_BIT_NOT_PHASE_LOCKED ) ///< see ::XMRS_BIT_NOT_PHASE_LOCKED
+#define XMRS_MSK_NUM_SRC_EXC ( 1UL << XMRS_BIT_NUM_SRC_EXC ) ///< see ::XMRS_BIT_NUM_SRC_EXC
+#define XMRS_MSK_IS_EXTERNAL ( 1UL << XMRS_BIT_IS_EXTERNAL ) ///< see ::XMRS_BIT_IS_EXTERNAL
+#define XMRS_MSK_LOW_JITTER ( 1UL << XMRS_BIT_LOW_JITTER ) ///< see ::XMRS_BIT_LOW_JITTER
+#define XMRS_MSK_ITU_LIMIT_VIOLATED ( 1UL << XMRS_BIT_ITU_LIMIT_VIOLATED ) ///< see ::XMRS_BIT_ITU_LIMIT_VIOLATED
+
+/** @} anchor XMR_REF_STATUS_BIT_MASKS */
+
+
+
+/**
+ * @brief XMRS status bit name strings
+ *
+ * @see ::XMR_REF_STATUS_BITS
*/
#define MBG_XMRS_STATUS_STRS \
{ \
@@ -4180,30 +7363,14 @@ enum XMR_REF_STATUS_BITS
"Phase not locked", \
"Number sources exceeds limit", \
"Is external", \
- "Low jitter" \
+ "Low jitter", \
+ "ITU Limit violated" \
}
-/**
- * @brief Bits and masks used with XMULTI_REF_STATUS::flags
- *
- * @note This API is only supported if bit ::GPS_FEAT_XMRS_MULT_INSTC
- * is set in RECEIVER_INFO::features.
- */
-enum XMR_REF_FLAG_BITS
-{
- XMRSF_BIT_MULT_INSTC_SUPP, ///< multiple instances of the same ref type supported
- XMRSF_BIT_IS_EXTERNAL, ///< this ref source is on extension card
- N_XMRS_FLAGS
-};
-
-#define XMRSF_MSK_MULT_INSTC_SUPP ( 1UL << XMRSF_BIT_MULT_INSTC_SUPP )
-#define XMRSF_MSK_IS_EXTERNAL ( 1UL << XMRSF_BIT_IS_EXTERNAL )
-
-
/*
- * An initializer for a XMULTI_REF_STATUS variable
+ * An initializer for a ::XMULTI_REF_STATUS variable
* with status invalid / not used
*/
#define XMULTI_REF_STATUS_INVALID \
@@ -4215,41 +7382,570 @@ enum XMR_REF_FLAG_BITS
}
+
/**
- * @brief The number of supported instances of each ref source type
+ * @brief General info on supported XMR sources and instances
*
- * @note This structure is only supported if bit ::GPS_FEAT_XMRS_MULT_INSTC
- * is set in RECEIVER_INFO::features.
+ * @note This structure is only supported if ::GPS_HAS_XMRS_MULT_INSTC
+ * is set in ::RECEIVER_INFO::features.
+ *
+ * The field ::XMULTI_REF_INSTANCES::n_xmr_settings reports the maximum number
+ * of entries that can be held by the input source table provided by this device.
+ * The input source table entry with the lowest index has the highest priority,
+ * and values 0..::XMULTI_REF_INSTANCES::n_xmr_settings-1 can be used as index
+ * when reading ::XMULTI_REF_INFO_IDX or ::XMULTI_REF_STATUS_IDX from the device,
+ * or when writing ::XMULTI_REF_SETTINGS_IDX to the device to configure
+ * the priority/order of input sources.
+ *
+ * An input source table entry is empty if ::XMULTI_REF_ID::type is set to
+ * ::MULTI_REF_NONE in ::XMULTI_REF_SETTINGS::id, and accordingly
+ * in ::XMULTI_REF_STATUS::id.
+ *
+ * The array ::XMULTI_REF_INSTANCES::n_inst reports how many instances are supported
+ * for every known reference type. For example, if 2 PPS input signals were supported
+ * then ::XMULTI_REF_INSTANCES::n_inst[::MULTI_REF_PPS] was set to 2. Even though
+ * this array can hold up to ::MAX_N_MULTI_REF_TYPES entries, the number entries
+ * which are actually used is ::N_MULTI_REF, according to the number of known
+ * reference signal types, which is less or equal than ::MAX_N_MULTI_REF_TYPES.
*/
typedef struct
{
- uint32_t flags; ///< reserved, currently always 0
- uint16_t n_xmr_settings; ///< number of configurable multi ref settings
- uint8_t slot_id; ///< current slot ID of board (0..15)
- uint8_t reserved; ///< reserved, currently always 0
- uint8_t n_inst[32]; ///< ::N_MULTI_REF entries used, but can not exceed bit number of uint32_t - 1
+ uint32_t flags; ///< see ::XMR_INST_FLAG_BIT_MASKS
+ uint16_t n_xmr_settings; ///< number of ::XMULTI_REF_INFO_IDX or ::XMULTI_REF_STATUS_IDX which can be retrieved
+ uint8_t slot_id; ///< ID of the slot in which this device is installed, 0 or up to 15, if multiple slots not supported
+ uint8_t reserved; ///< reserved, don't use, currently always 0
+ uint8_t n_inst[MAX_N_MULTI_REF_TYPES]; ///< the number of supported instances of each input signal type
+
} XMULTI_REF_INSTANCES;
+#define _mbg_swab_xmulti_ref_instances( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab16( &(_p)->n_xmr_settings ); \
+} while ( 0 )
+
+
/**
- * @brief Holdover interval while switching XMR sources
+ * @brief Enumeration of flag bits used with XMULTI_REF instances
*
- * @note This parameter can be sent to a device to specify a holdover
- * interval during which the sync state shall be kept when switching
- * to a different time source.
+ * @see ::XMR_INST_FLAG_BIT_MASKS
*/
-typedef uint32_t XMR_HOLDOVER_INTV; ///< [s] */
+enum XMR_INST_FLAGS
+{
+ /// This flag indicates that configuration programs may set
+ /// ::XMULTI_REF_ID::type to ::MULTI_REF_NONE in ::XMULTI_REF_SETTINGS::id
+ /// for unused priority levels, and that this will be reflected in
+ /// ::XMULTI_REF_STATUS::id accordingly. With some older firmware versions
+ /// this was not supported.
+ XMRIF_BIT_MRF_NONE_SUPP,
+ XMRIF_BIT_HOLDOVER_STATUS_SUPP, ///< ::XMR_HOLDOVER_STATUS and associated types supported
-/** @} group_xmr_cfg */
+ XMRIF_BIT_EXT_SRC_INFO_SUPP, ///< ::XMR_EXT_SRC_INFO structure supported
+ N_XMRIF_BITS ///< number of known flag bits
+};
+
+
+/**
+ * @brief Bit masks associated with ::XMR_INST_FLAGS
+ *
+ * Used with ::XMULTI_REF_INSTANCES::flags.
+ *
+ * @see ::XMR_INST_FLAGS
+ */
+enum XMR_INST_FLAG_BIT_MASKS
+{
+ XMRIF_MSK_MRF_NONE_SUPP = ( 1UL << XMRIF_BIT_MRF_NONE_SUPP ), ///< see ::XMRIF_BIT_MRF_NONE_SUPP
+ XMRIF_MSK_HOLDOVER_STATUS_SUPP = ( 1UL << XMRIF_BIT_HOLDOVER_STATUS_SUPP ), ///< see ::XMRIF_BIT_HOLDOVER_STATUS_SUPP
+ XMRIF_MSK_EXT_SRC_INFO_SUPP = ( 1UL << XMRIF_BIT_EXT_SRC_INFO_SUPP ) ///< see ::XMRIF_BIT_EXT_SRC_INFO_SUPP
+};
+
+
+
+/**
+ * @brief XMR holdover interval, or elapsed holdover time, in [s]
+ */
+typedef uint32_t XMR_HOLDOVER_INTV;
+
+#define _mbg_swab_xmr_holdover_intv( _p ) \
+ _mbg_swab32( _p )
+
+
+
+/**
+ * @brief A code used to indicate that a input source table index is unspecified
+ */
+#define XMR_PRIO_LVL_UNSPEC -1
+
+
+
+/**
+ * @brief XMR holdover status
+ *
+ * Only supported if ::XMRIF_MSK_HOLDOVER_STATUS_SUPP is set in ::XMULTI_REF_INSTANCES::flags
+ *
+ * Reports the current holdover status including the elapsed holdover time
+ * and the currently active holdover interval, as well as the indices of the
+ * current and next XMR time source.
+ *
+ * The flag ::XMR_HLDOVR_MSK_IN_HOLDOVER is set if holdover mode is currently active.
+ *
+ * The fields ::XMR_HOLDOVER_STATUS::curr_prio and ::XMR_HOLDOVER_STATUS::nxt_prio
+ * specify the current or next priority level which can be in the range
+ * 0..::XMULTI_REF_INSTANCES::n_xmr_settings-1, or ::XMR_PRIO_LVL_UNSPEC if the
+ * index is undefined, e.g. because no input source is available to which can
+ * be switched after the holdover interval.
+ *
+ * The ::XMR_HOLDOVER_STATUS::mode field indicates the current XMR/holdover mode
+ * which is usually ::XMR_HLDOVR_AUTONOMOUS. However, in certain applications
+ * XMR switching is controlled remotely, in which case ::XMR_HOLDOVER_STATUS::mode
+ * is set to ::XMR_HLDOVR_REMOTE.
+ *
+ * If the device is in remote mode and needs to switch XMR sources then mode changes
+ * to ::XMR_HLDOVR_PRE_AUTONOMOUS, and the ::XMR_HOLDOVER_STATUS::remote_watchdog
+ * starts to count down. If the watchdog expires before a remote switch command
+ * has been received the device switches to ::XMR_HLDOVR_AUTONOMOUS.
+ */
+typedef struct
+{
+ uint8_t mode; ///< XMR/holdover mode, see ::XMR_HOLDOVER_STATUS_MODES
+ int8_t curr_prio; ///< current priority level, 0..::XMULTI_REF_INSTANCES::n_xmr_settings, or ::XMR_PRIO_LVL_UNSPEC
+ int8_t nxt_prio; ///< next priority level after holdover, 0..::XMULTI_REF_INSTANCES::n_xmr_settings, or ::XMR_PRIO_LVL_UNSPEC
+ uint8_t remote_watchdog; ///< counts down in ::XMR_HLDOVR_PRE_AUTONOMOUS mode
+ uint32_t time_offset_ns; ///< estimated time offset in holdover operation
+ XMR_HOLDOVER_INTV elapsed; ///< elapsed time in holdover mode, only valid if ::XMR_HLDOVR_MSK_IN_HOLDOVER is set
+ XMR_HOLDOVER_INTV interval; ///< current holdover interval, only valid if ::XMR_HLDOVR_MSK_IN_HOLDOVER is set
+ uint32_t flags; ///< holdover status flags, see ::XMR_HOLDOVER_STATUS_FLAG_MASKS
+
+} XMR_HOLDOVER_STATUS;
+
+#define _mbg_swab_xmr_holdover_status( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->mode ); \
+ _mbg_swab8( &(_p)->curr_prio ); \
+ _mbg_swab8( &(_p)->nxt_prio ); \
+ _mbg_swab8( &(_p)->remote_watchdog ); \
+ _mbg_swab32( &(_p)->time_offset_ns ); \
+ _mbg_swab_xmr_holdover_intv( &(_p)->elapsed ); \
+ _mbg_swab_xmr_holdover_intv( &(_p)->interval ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+
+/**
+ * @brief XMR holdover status modes
+ *
+ * Used with ::XMR_HOLDOVER_STATUS::mode.
+ *
+ * @see ::XMR_HOLDOVER_STATUS_MODE_NAMES
+ */
+enum XMR_HOLDOVER_STATUS_MODES
+{
+ XMR_HLDOVR_AUTONOMOUS, ///< autonomous mode, XMR sources are selected automatically by the device
+ XMR_HLDOVR_PRE_AUTONOMOUS, ///< going to switch to autonomous mode when ::XMR_HOLDOVER_STATUS::remote_watchdog reaches 0
+ XMR_HLDOVR_REMOTE, ///< remote mode, XMR switching done by external command/control
+ N_XMR_HOLDOVER_STATUS_MODES ///< the number of known modes
+};
+
+
+/**
+ * @brief String initializers for XMR holdover status mode
+ *
+ * @see ::XMR_HOLDOVER_STATUS_MODES
+ */
+#define XMR_HOLDOVER_STATUS_MODE_NAMES \
+{ \
+ "Autonomous", \
+ "Pre-Autonomous", \
+ "Remote" \
+}
+
+
+
+/**
+ * @brief XMR holdover status flag bits
+ *
+ * Used to define ::XMR_HOLDOVER_STATUS_FLAG_MASKS.
+ */
+enum XMR_HOLDOVER_STATUS_FLAG_BITS
+{
+ XMR_HLDOVR_BIT_IN_HOLDOVER, ///< the device is currently in holdover mode
+ XMR_HLDOVR_BIT_TRANSITION_ENBD, ///< timebase is in transition (being slewed) after sources have been switched
+ XMR_HLDOVR_BIT_IN_TRANSITION, ///< transition is currently active, slewing in progress
+ XMR_HLDOVR_BIT_TIME_OFFS_VALID, ///< values in field ::XMR_HOLDOVER_STATUS::time_offset_ns are valid
+ N_XMR_HOLDOVER_STATUS_FLAG_BITS ///< the number of known status flags
+};
+
+
+/**
+ * @brief XMR holdover status flag masks
+ *
+ * Used with ::XMR_HOLDOVER_STATUS::flags.
+ */
+enum XMR_HOLDOVER_STATUS_FLAG_MASKS
+{
+ XMR_HLDOVR_MSK_IN_HOLDOVER = ( 1UL << XMR_HLDOVR_BIT_IN_HOLDOVER ), ///< see ::XMR_HLDOVR_BIT_IN_HOLDOVER
+ XMR_HLDOVR_MSK_TRANSITION_ENBD = ( 1UL << XMR_HLDOVR_BIT_TRANSITION_ENBD ), ///< see ::XMR_HLDOVR_BIT_TRANSITION_ENBD
+ XMR_HLDOVR_MSK_IN_TRANSITION = ( 1UL << XMR_HLDOVR_BIT_IN_TRANSITION ), ///< see ::XMR_HLDOVR_BIT_IN_TRANSITION
+ XMR_HLDOVR_MSK_TIME_OFFS_VALID = ( 1UL << XMR_HLDOVR_BIT_TIME_OFFS_VALID ) ///< see ::XMR_HLDOVR_BIT_TIME_OFFS_VALID
+};
+
+
+
+/**
+ * @brief XMR source feature flag bits
+ *
+ * Used to define ::XMR_EXT_SRC_FEAT_FLAG_MSKS
+ */
+enum XMR_EXT_SRC_FEAT_FLAG_BITS
+{
+ XMR_EXT_SRC_FEAT_FLAG_BIT_STATS, ///< XMR source provides ::XMR_STATS
+ XMR_EXT_SRC_FEAT_FLAG_BIT_METRICS, ///< XMR source provides ::XMR_METRICS
+ N_XMR_EXT_SRC_FEAT_FLAG_BITS
+};
+
+
+
+/**
+ * @brief XMR source feature flag bit masks
+ *
+ * Used with ::XMR_EXT_SRC_INFO::feat_flags.
+ *
+ * @see ::XMR_EXT_SRC_FEAT_FLAG_BITS
+ */
+enum XMR_EXT_SRC_FEAT_FLAG_MSKS
+{
+ XMR_EXT_SRC_FEAT_FLAG_MSK_STATS = ( 1UL << XMR_EXT_SRC_FEAT_FLAG_BIT_STATS ), ///< see ::XMR_EXT_SRC_FEAT_FLAG_BIT_STATS
+ XMR_EXT_SRC_FEAT_FLAG_MSK_METRICS = ( 1UL << XMR_EXT_SRC_FEAT_FLAG_BIT_METRICS ) ///< see ::XMR_EXT_SRC_FEAT_FLAG_BIT_METRICS
+};
+
+
+
+typedef struct
+{
+ uint16_t supp_flags; ///< indicates which flags are supported by ::XMULTI_REF_SETTINGS::flags, see ::XMR_SETTINGS_FLAG_MSKS
+ uint16_t feat_flags; ///< see ::XMR_EXT_SRC_FEAT_FLAG_MSKS
+ uint32_t reserved_0;
+
+} XMR_EXT_SRC_INFO;
+
+#define _mbg_swab_xmr_ext_src_info( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->supp_flags ); \
+ _mbg_swab16( &(_p)->feat_flags ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint16_t idx; //
+ XMR_EXT_SRC_INFO info; //
+
+} XMR_EXT_SRC_INFO_IDX; //
+
+#define _mbg_swab_xmr_ext_src_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_xmr_ext_src_info( &(_p)->info ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief XMR statistics for a particular source
+ *
+ * This structure is only provided by an XMR source which has
+ * ::XMR_EXT_SRC_FEAT_FLAG_MSK_STATS set in ::XMR_EXT_SRC_INFO::feat_flags.
+ *
+ * @see ::XMR_STATS_IDX
+ * @see ::XMR_EXT_SRC_INFO::feat_flags
+ * @see ::XMR_EXT_SRC_FEAT_FLAG_MSK_STATS
+ */
+typedef struct
+{
+ uint32_t timestamp; ///< time stamp when the record was taken, UTC, seconds since 1970
+ NANO_TIME last_mue; ///< mean value (mue) of prev. interval
+ NANO_TIME last_sigma; ///< standard deviation (sigma) of prev. interval
+ NANO_TIME last_max; ///< maximum value within interval
+ NANO_TIME last_min; ///< minimum value within interval
+ NANO_TIME reserved_0; ///< currently reserved, unused, always 0
+ NANO_TIME step_comp_val; ///< current step compensation value
+ NANO_TIME auto_bias; ///< current time automatic bias compensation
+ uint32_t reserved_1; ///< currently reserved, unused, always 0
+ uint32_t reserved_2; ///< currently reserved, unused, always 0
+ uint32_t flags; ///< see ::XMR_STATS_FLAGS_MSKS
+
+} XMR_STATS;
+
+#define _mbg_swab_xmr_stats( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->timestamp ); \
+ _mbg_swab_nano_time( &(_p)->last_mue ); \
+ _mbg_swab_nano_time( &(_p)->last_sigma ); \
+ _mbg_swab_nano_time( &(_p)->last_max ); \
+ _mbg_swab_nano_time( &(_p)->last_min ); \
+ _mbg_swab_nano_time( &(_p)->reserved_0 ); \
+ _mbg_swab_nano_time( &(_p)->step_comp_val ); \
+ _mbg_swab_nano_time( &(_p)->auto_bias ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of bits used to define ::XMR_STATS_FLAGS_MSKS
+ *
+ * @see ::XMR_STATS_FLAGS_MSKS
+ */
+enum XMR_STATS_FLAGS_BITS
+{
+ XMR_STATS_FLAG_BIT_STEP_DETECTED, ///< A time step was detected at the input source
+ XMR_STATS_FLAG_BIT_STEP_COMPENSATED, ///< A time step was compensated at the input source
+ XMR_STATS_FLAG_BIT_AUTO_BIAS_VALID, ///< The value in ::XMR_STATS::auto_bias is valid
+ N_XMR_STATS_FLAGS_BITS
+};
+
+
+
+/**
+ * @brief Flag bit masks used with ::XMR_STATS::flags
+ *
+ * @see ::XMR_STATS_FLAGS_BITS
+ */
+enum XMR_STATS_FLAGS_MSKS
+{
+ XMR_STATS_FLAG_MSK_STEP_DETECTED = ( 1UL << XMR_STATS_FLAG_BIT_STEP_DETECTED ), ///< see ::XMR_STATS_FLAG_BIT_STEP_DETECTED
+ XMR_STATS_FLAG_MSK_STEP_COMPENSATED = ( 1UL << XMR_STATS_FLAG_BIT_STEP_COMPENSATED ), ///< see ::XMR_STATS_FLAG_BIT_STEP_COMPENSATED
+ XMR_STATS_FLAG_MSK_AUTO_BIAS_VALID = ( 1UL << XMR_STATS_FLAG_BIT_AUTO_BIAS_VALID ) ///< see ::XMR_STATS_FLAG_BIT_AUTO_BIAS_VALID
+};
+
+
+
+/**
+ * @brief String initializers for XMR Stats Flags
+ *
+ * @see ::XMR_STATS_FLAGS_MSKS
+ */
+#define DEFAULT_XMR_STATS_FLAG_NAMES \
+{ \
+ "Step Detected", \
+ "Step Compensated", \
+ "Auto BIAS valid" \
+}
+
+
+
+/**
+ * @brief XMR statistics for a particular source, with index
+ *
+ * @see ::XMR_STATS
+ */
+typedef struct
+{
+ uint16_t idx; ///< the priority level index (highest == 0), 0..::XMULTI_REF_INSTANCES::n_xmr_settings-1
+ XMR_STATS stats; ///< XMR statistics of the particular source
+
+} XMR_STATS_IDX;
+
+#define _mbg_swab_xmr_stats_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_xmr_stats( &(_p)->stats ); \
+} while ( 0 )
+
+
+
+#define MAX_XMR_METRICS 20
+
+typedef struct
+{
+ uint32_t timestamp;
+ uint32_t flags; ///< idx bit set if mtie[idx] is valid
+ uint8_t mtie_scale; ///< scale factors of MTIE
+ uint8_t tdev_scale; ///< scale factors of TDEV
+ uint16_t reserved_0; ///< currently unused
+ uint32_t reserved_1; ///< currently unused
+ uint32_t reserved_2; ///< currently unused
+ uint32_t mtie[MAX_XMR_METRICS]; ///< mtie scaled 32 bit fixed point unsigned
+ uint32_t tdev[MAX_XMR_METRICS]; ///< tdev scaled 32 bit fixed point unsigned
+
+} XMR_METRICS;
+
+#define _mbg_swab_xmr_metrics( _p ) \
+do \
+{ \
+ int i; \
+ \
+ _mbg_swab32( &(_p)->timestamp ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab8( &(_p)->mtie_scale ); \
+ _mbg_swab8( &(_p)->tdev_scale ); \
+ _mbg_swab16( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ \
+ for ( i = 0; i < MAX_XMR_METRICS; i++ ) \
+ _mbg_swab32( &(_p)->mtie[i] ); \
+ \
+ for ( i = 0; i < MAX_XMR_METRICS; i++ ) \
+ _mbg_swab32( &(_p)->tdev[i] ); \
+ \
+} while ( 0 )
+
+
+
+// conversion factor scaled FPU32 to double
+#define _fpu32_to_double_fac( _x ) ( 1.0 / ( 4294967296.0 * ( _x ) ) )
+
+
+
+/**
+ * @brief XMR timing metrics for a particular source, with index
+ *
+ * @see ::XMR_METRICS
+ */
+typedef struct
+{
+ uint16_t idx;
+ XMR_METRICS metrics;
+
+} XMR_METRICS_IDX;
+
+#define _mbg_swab_xmr_metrics_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_xmr_metrics( &(_p)->metrics ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of ITU limit masks
+ *
+ * Used for detection of ::XMR_METRICS mask violation.
+ *
+ * @see ::ITU_LIMIT_MASKS
+ * @see ::XMR_METRICS
+ */
+enum ITU_LIMITS
+{
+ ITU_LIMIT_G811_PRC,
+ ITU_LIMIT_G823_SSU,
+ ITU_LIMIT_G823_SEC,
+ ITU_LIMIT_G8272_PRTC,
+ ITU_LIMIT_G82721_EPRTC,
+ N_ITU_LIMITS
+} ;
+
+
+
+/**
+ * @brief Enumeration of ITU limit masks
+ *
+ * Used for detection of ::XMR_METRICS mask violation.
+ *
+ * @see ::ITU_LIMITS
+ * @see ::XMR_METRICS
+ */
+enum ITU_LIMIT_MASKS
+{
+ MSK_ITU_LIMIT_G811_PRC = ( 1UL << ITU_LIMIT_G811_PRC ),
+ MSK_ITU_LIMIT_G823_SSU = ( 1UL << ITU_LIMIT_G823_SSU ),
+ MSK_ITU_LIMIT_G823_SEC = ( 1UL << ITU_LIMIT_G823_SEC ),
+ MSK_ITU_LIMIT_G8272_PRTC = ( 1UL << ITU_LIMIT_G8272_PRTC ),
+ MSK_ITU_LIMIT_G82721_EPRTC = ( 1UL << ITU_LIMIT_G82721_EPRTC )
+};
+
+
+
+/**
+ * @brief String initializers for ITU limit masks
+ *
+ * Used for detection of ::XMR_METRICS mask violation.
+ *
+ * @see ::ITU_LIMITS
+ * @see ::XMR_METRICS
+ */
+#define ITU_LIMIT_SHORT_STRS \
+{ \
+ "G811 (PRC)", \
+ "G823 (SSU)", \
+ "G823 (SEC)", \
+ "G8272 (PRTC)", \
+ "G82721 (ePRTC)" \
+}
+
+
+
+/**
+ * @brief supported limits for qualtity metrics
+ *
+ * @see ::XMR_METRICS
+ */
+typedef struct
+{
+ uint8_t ql_mask; ///< see :ITU_LIMIT_MASKS
+ uint8_t hysteresis; ///< hysteresis (percent) between yellow and red alarm
+ uint16_t reserved_0;
+ uint32_t reserved_1;
+
+} XMR_QL_SETTINGS;
+
+
+
+typedef struct
+{
+ uint32_t supp_ql_masks; ///< see :ITU_LIMIT_MASKS
+ uint32_t reserved_0;
+ uint32_t reserved_1;
+ XMR_QL_SETTINGS settings;
+
+} XMR_QL_INFO;
+
+
+
+typedef struct
+{
+ uint16_t idx;
+ XMR_QL_SETTINGS settings;
+
+} XMR_QL_SETTINGS_IDX;
+
+
+
+typedef struct
+{
+ uint16_t idx;
+ XMR_QL_INFO info;
+
+} XMR_QL_INFO_IDX;
+
+
+/** @} defgroup group_multi_ref_ext */
+
+/** @} defgroup group_multi_ref_all */
/**
* @defgroup group_gpio GPIO port configuration stuff
*
* @note This is only supported if ::GPS_HAS_GPIO is set
- * in the RECEIVER_INFO::features mask.
+ * in the ::RECEIVER_INFO::features mask.
*
* @{ */
@@ -4258,17 +7954,53 @@ typedef uint32_t XMR_HOLDOVER_INTV; ///< [s] */
* @brief General GPIO config info to be read from a device
*
* Used to query from a device how many GPIO ports are supported
- * by the device, then index 0..num_io-1 configuration or status
- * records can be read from or written to the device.
+ * by the device, then index 0..::MBG_GPIO_CFG_LIMITS::num_io-1
+ * configuration or status records can be read from or written to
+ * the device.
*/
typedef struct
{
- uint32_t num_io; /**< number of supported GPIO ports */
- uint32_t reserved; /**< currently always 0 */
- uint32_t flags; /**< currently always 0 */
+ uint32_t num_io; ///< number of supported GPIO ports
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< see ::MBG_GPIO_CFG_LIMIT_FLAG_MASKS
} MBG_GPIO_CFG_LIMITS;
+#define _mbg_swab_mbg_gpio_cfg_limits( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->num_io ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief GPIO limits flag bits used to define ::MBG_GPIO_CFG_LIMIT_FLAG_MASKS
+ *
+ * @see ::MBG_GPIO_CFG_LIMIT_FLAG_MASKS
+ */
+enum MBG_GPIO_CFG_LIMIT_FLAG_BITS
+{
+ MBG_GPIO_CFG_LIMIT_FLAG_BIT_STATUS_SUPP, ///< indicates that ::MBG_GPIO_STATUS is supported
+ N_MBG_GPIO_CFG_LIMIT_FLAG_BITS
+};
+
+
+
+/**
+ * @brief GPIO limits flag masks associated with ::MBG_GPIO_CFG_LIMIT_FLAG_BITS
+ *
+ * Used with ::MBG_GPIO_CFG_LIMITS::flags
+ *
+ * @see ::MBG_GPIO_CFG_LIMIT_FLAG_BITS
+ */
+enum MBG_GPIO_CFG_LIMIT_FLAG_MASKS
+{
+ MBG_GPIO_CFG_LIMIT_FLAG_MASK_STATUS_SUPP = ( 1UL << MBG_GPIO_CFG_LIMIT_FLAG_BIT_STATUS_SUPP ), ///< see ::MBG_GPIO_CFG_LIMIT_FLAG_BIT_STATUS_SUPP
+};
+
/**
@@ -4277,48 +8009,89 @@ typedef struct
* Usually a specific GPIO port can only be either an input
* or an output, and supports only a single signal type.
* This is due to hardware limitations, i.e. input or output
- * circuitry required for the given signal
+ * circuitry required for the given signal.
+ *
+ * @see ::DEFAULT_GPIO_TYPES_SHORT_STRS
*/
enum MBG_GPIO_TYPES
{
- MBG_GPIO_TYPE_FREQ_IN, /**< variable frequency input */
- MBG_GPIO_TYPE_FREQ_OUT, /**< variable frequency output */
- MBG_GPIO_TYPE_FIXED_FREQ_OUT, /**< fixed frequency output */
- MBG_GPIO_TYPE_BITS_IN, /**< framed data stream input */
- MBG_GPIO_TYPE_BITS_OUT, /**< framed data stream output */
- N_MBG_GPIO_TYPES /**< number of known types */
+ MBG_GPIO_TYPE_FREQ_IN, ///< Variable frequency input, freq == 0 if input not used
+ MBG_GPIO_TYPE_FREQ_OUT, ///< Variable frequency output
+ MBG_GPIO_TYPE_FIXED_FREQ_OUT, ///< Fixed frequency output
+ MBG_GPIO_TYPE_BITS_IN, ///< Framed data stream input
+ MBG_GPIO_TYPE_BITS_OUT, ///< Framed data stream output
+ MBG_GPIO_TYPE_VIDEO_OUT, ///< Video signal output (PAL, NTSC, ...)
+ MBG_GPIO_TYPE_VIDEO_SYNC_OUT, ///< Video sync signal output (H-Sync, V-Sync, ...)
+ MBG_GPIO_TYPE_STUDIO_CLOCK_OUT, ///< Studio clock output
+ MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT, ///< Digital Audio output (DARS, ...)
+ N_MBG_GPIO_TYPES ///< Number of known types
};
-#define DEFAULT_GPIO_TYPES_SHORT_STRS \
-{ \
- "Freq. In", \
- "Freq. Out", \
- "Fixed Freq Out", \
- "BITS In", \
- "BITS Out" \
+
+#define DEFAULT_GPIO_TYPES_SHORT_STRS \
+{ \
+ "Freq. In", \
+ "Freq. Out", \
+ "Fixed Freq Out", \
+ "BITS In", \
+ "BITS Out", \
+ "Video Out", \
+ "Video Sync Out", \
+ "Studio Clock Out", \
+ "Digital Audio Out" \
}
/**
- * @brief Enumeration of signal shapes
+ * @brief Enumeration of known signal shapes
*
* Used to specify the signal shape of an input or output
* frequency signal.
+ *
+ * @see ::MBG_GPIO_SIGNAL_SHAPE_MASKS
+ * @see ::DEFAULT_GPIO_SIGNAL_SHAPE_NAMES
*/
enum MBG_GPIO_SIGNAL_SHAPES
{
- MBG_GPIO_SIGNAL_SHAPE_UNSPECIFIED, /**< unknown or unspecified signal shape */
- MBG_GPIO_SIGNAL_SHAPE_SINE, /**< sine wave */
- MBG_GPIO_SIGNAL_SHAPE_SQUARE, /**< square wave */
- N_MBG_GPIO_SIGNAL_SHAPES /**< number of known signal shapes */
+ MBG_GPIO_SIGNAL_SHAPE_UNSPECIFIED, ///< unknown or unspecified signal shape
+ MBG_GPIO_SIGNAL_SHAPE_SINE, ///< sine wave
+ MBG_GPIO_SIGNAL_SHAPE_SQUARE, ///< square wave
+ N_MBG_GPIO_SIGNAL_SHAPES ///< number of known signal shapes
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_SIGNAL_SHAPES
+ *
+ * Used e.g. with ::MBG_GPIO_FREQ_IN_SUPP::supp_shapes,
+ * ::MBG_GPIO_FREQ_OUT_SUPP::supp_shapes,
+ * and ::MBG_GPIO_FIXED_FREQ_OUT_SUPP::supp_shapes.
+ *
+ * @see ::MBG_GPIO_SIGNAL_SHAPES
+ */
+enum MBG_GPIO_SIGNAL_SHAPE_MASKS
+{
+ MBG_GPIO_SIGNAL_SHAPE_MSK_UNSPECIFIED = ( 1UL << MBG_GPIO_SIGNAL_SHAPE_UNSPECIFIED ), ///< see ::MBG_GPIO_SIGNAL_SHAPE_UNSPECIFIED
+ MBG_GPIO_SIGNAL_SHAPE_MSK_SINE = ( 1UL << MBG_GPIO_SIGNAL_SHAPE_SINE ), ///< see ::MBG_GPIO_SIGNAL_SHAPE_SINE
+ MBG_GPIO_SIGNAL_SHAPE_MSK_SQUARE = ( 1UL << MBG_GPIO_SIGNAL_SHAPE_SQUARE ) ///< see ::MBG_GPIO_SIGNAL_SHAPE_SQUARE
};
-/** Bit masks of signal shapes, corresponding to enum MBG_GPIO_SIGNAL_SHAPES */
-#define MBG_GPIO_SIGNAL_SHAPE_MSK_UNSPECIFIED ( 1UL << MBG_GPIO_SIGNAL_SHAPE_UNSPECIFIED )
-#define MBG_GPIO_SIGNAL_SHAPE_MSK_SINE ( 1UL << MBG_GPIO_SIGNAL_SHAPE_SINE )
-#define MBG_GPIO_SIGNAL_SHAPE_MSK_SQUARE ( 1UL << MBG_GPIO_SIGNAL_SHAPE_SQUARE )
+
+
+/**
+ * @brief String initializers for GPIO signal shapes
+ *
+ * @see ::MBG_GPIO_SIGNAL_SHAPES
+ */
+#define DEFAULT_GPIO_SIGNAL_SHAPE_NAMES \
+{ \
+ "(unspec. shape)", \
+ "Sine wave", \
+ "Rectangle Pulse" \
+}
@@ -4329,376 +8102,1626 @@ enum MBG_GPIO_SIGNAL_SHAPES
*/
typedef struct
{
- uint32_t hz; /**< integral number, Hz */
- uint32_t frac; /**< fractional part, binary */
+ uint32_t hz; ///< integral number [Hz]
+ uint32_t frac; ///< fractional part, binary (0x80000000 --> 0.5, 0xFFFFFFFF --> 0.9999999...)
} MBG_GPIO_FREQ;
+#define _mbg_swab_mbg_gpio_freq( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->hz ); \
+ _mbg_swab32( &(_p)->frac); \
+} while ( 0 )
+
/**
* @brief Configuration of a GPIO variable frequency input
*
- * @see MBG_GPIO_TYPE_FREQ_IN
+ * Used as sub-structure of ::MBG_GPIO_SETTINGS.
+ *
+ * @see ::MBG_GPIO_TYPE_FREQ_IN
+ * @see ::MBG_GPIO_SETTINGS
*/
typedef struct
{
- MBG_GPIO_FREQ freq; /**< frequency */
- uint32_t csc_limit; /**< max. cycle slip [1/1000 cycle units] */
- uint32_t shape; /**< signal shape, see ::MBG_GPIO_SIGNAL_SHAPES */
- uint32_t reserved; /**< currently always 0 */
- uint32_t flags; /**< currently always 0 */
+ MBG_GPIO_FREQ freq; ///< frequency in range ::MBG_GPIO_FREQ_IN_SUPP::freq_min..::MBG_GPIO_FREQ_IN_SUPP::freq_max, or 0 if input is not used
+ uint32_t csc_limit; ///< max. cycle slip [1/1000 cycle units], see ::MBG_GPIO_FREQ_IN_SUPP::csc_limit_max
+ uint32_t shape; ///< selected signal shape, see ::MBG_GPIO_SIGNAL_SHAPES
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< reserved, currently always 0
} MBG_GPIO_FREQ_IN_SETTINGS;
+#define _mbg_swab_mbg_gpio_freq_in_settings( _p ) \
+do \
+{ \
+ _mbg_swab_mbg_gpio_freq( &(_p)->freq ); \
+ _mbg_swab32( &(_p)->csc_limit ); \
+ _mbg_swab32( &(_p)->shape ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
/**
* @brief Supported options for a variable frequency GPIO input
*
- * @see MBG_GPIO_TYPE_FREQ_IN
+ * Used as sub-structure of ::MBG_GPIO_LIMITS.
+ *
+ * @see ::MBG_GPIO_TYPE_FREQ_IN
+ * @see ::MBG_GPIO_LIMITS
*/
typedef struct
{
- //##++++++++++++++++
- uint32_t freq_min; /**< minimum output frequency [Hz] */
- uint32_t freq_max; /**< maximum output frequency [Hz] */
- uint32_t csc_limit_max; /**< max. milli_phase, unspecified if 0 */
- uint32_t supp_shapes; /**< bit mask of supported signal shapes, see ::MBG_GPIO_SIGNAL_SHAPES */
- uint32_t reserved; /**< currently always 0 */
- uint32_t flags; /**< currently always 0 */
+ uint32_t freq_min; ///< minimum output frequency [Hz]
+ uint32_t freq_max; ///< maximum output frequency [Hz]
+ uint32_t csc_limit_max; ///< 1/1000 units of the signal period, limited due to 10 ns sampling interval, see ::MBG_GPIO_FREQ_IN_SETTINGS::csc_limit //##++++++++++++++++
+ uint32_t supp_shapes; ///< bit mask of supported signal shapes, see ::MBG_GPIO_SIGNAL_SHAPE_MASKS
+ uint32_t supp_limits; ///< supported ITU limit masks for BITS signal see ::ITU_LIMIT_MASKS
+ uint32_t flags; ///< reserved, currently always 0
} MBG_GPIO_FREQ_IN_SUPP;
+#define _mbg_swab_mbg_gpio_freq_in_supp( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->freq_min ); \
+ _mbg_swab32( &(_p)->freq_max ); \
+ _mbg_swab32( &(_p)->csc_limit_max ); \
+ _mbg_swab32( &(_p)->supp_shapes ); \
+ _mbg_swab32( &(_p)->supp_limits ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
/**
* @brief Configuration of a GPIO variable frequency output
*
- * @see MBG_GPIO_TYPE_FREQ_OUT
+ * Used as sub-structure of ::MBG_GPIO_SETTINGS.
+ *
+ * @see ::MBG_GPIO_TYPE_FREQ_OUT
+ * @see ::MBG_GPIO_SETTINGS
*/
typedef struct
{
- MBG_GPIO_FREQ freq; /**< frequency */
- int32_t milli_phase; /**< phase [1/1000 degree units] */
- uint32_t shape; /**< signal shape, see ::MBG_GPIO_SIGNAL_SHAPES */
- uint32_t reserved; /**< currently always 0 */
- uint32_t flags; /**< currently always 0 */
+ MBG_GPIO_FREQ freq; ///< frequency, see ::MBG_GPIO_FREQ_OUT_SUPP::freq_min and ::MBG_GPIO_FREQ_OUT_SUPP::freq_max
+ int32_t milli_phase; ///< phase [1/1000 degree units], see ::MBG_GPIO_FREQ_OUT_SUPP::milli_phase_max
+ uint32_t shape; ///< selected signal shape, see ::MBG_GPIO_SIGNAL_SHAPES
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< reserved, currently always 0
} MBG_GPIO_FREQ_OUT_SETTINGS;
+#define _mbg_swab_mbg_gpio_freq_out_settings( _p ) \
+do \
+{ \
+ _mbg_swab_mbg_gpio_freq( &(_p)->freq ); \
+ _mbg_swab32( &(_p)->milli_phase ); \
+ _mbg_swab32( &(_p)->shape ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
/**
* @brief Supported options for a variable frequency GPIO output
*
- * @see MBG_GPIO_TYPE_FREQ_OUT
+ * Used as sub-structure of ::MBG_GPIO_LIMITS.
+ *
+ * @see ::MBG_GPIO_TYPE_FREQ_OUT
+ * @see ::MBG_GPIO_LIMITS
*/
typedef struct
{
- uint32_t freq_min; /**< minimum output frequency [Hz] */
- uint32_t freq_max; /**< maximum output frequency [Hz] */
- uint32_t freq_resolution; /**< frequency resolution [Hz], unspecified if 0 */
- uint32_t milli_phase_max; /**< max. abs. milli_phase */
- uint32_t supp_shapes; /**< bit mask of supported signal shapes, see ::MBG_GPIO_SIGNAL_SHAPES */
- uint32_t reserved; /**< currently always 0 */
- uint32_t flags; /**< currently always 0 */
+ uint32_t freq_min; ///< minimum output frequency [Hz], see ::MBG_GPIO_FREQ_OUT_SETTINGS::freq
+ uint32_t freq_max; ///< maximum output frequency [Hz], see ::MBG_GPIO_FREQ_OUT_SETTINGS::freq
+ uint32_t freq_resolution; ///< frequency resolution [Hz], unspecified if 0
+ uint32_t milli_phase_max; ///< max. abs. milli_phase, see ::MBG_GPIO_FREQ_OUT_SETTINGS::milli_phase
+ uint32_t supp_shapes; ///< bit mask of supported signal shapes, see ::MBG_GPIO_SIGNAL_SHAPE_MASKS
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< reserved, currently always 0
} MBG_GPIO_FREQ_OUT_SUPP;
+#define _mbg_swab_mbg_gpio_freq_out_supp( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->freq_min ); \
+ _mbg_swab32( &(_p)->freq_max ); \
+ _mbg_swab32( &(_p)->freq_resolution ); \
+ _mbg_swab32( &(_p)->milli_phase_max ); \
+ _mbg_swab32( &(_p)->supp_shapes ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
/**
- * @brief Supported fixed frequencies
+ * @brief Enumeration of predefined fixed frequencies
+ *
+ * @see ::MBG_GPIO_FIXED_FREQ_MASKS
+ * @see ::MBG_GPIO_FIXED_FREQ_STRS
*/
-enum MBG_GPIO_FIXED_FREQ
+enum MBG_GPIO_FIXED_FREQS
{
- MBG_GPIO_FIXED_FREQ_8kHz, /**< 8kHz */
- MBG_GPIO_FIXED_FREQ_48kHz, /**< 48kHz */
- MBG_GPIO_FIXED_FREQ_1MHz, /**< 1MHz */
- MBG_GPIO_FIXED_FREQ_1544kHz, /**< 1.544MHz */
- MBG_GPIO_FIXED_FREQ_2048kHz, /**< 2.048MHz */
- MBG_GPIO_FIXED_FREQ_5MHz, /**< 5MHz */
- MBG_GPIO_FIXED_FREQ_10MHz, /**< 10MHz */
- MBG_GPIO_FIXED_FREQ_19440kHz, /**< 19.44MHz */
- N_MBG_GPIO_FIXED_FREQ /**< number of known frequencies */
+ MBG_GPIO_FIXED_FREQ_8kHz, ///< 8 kHz
+ MBG_GPIO_FIXED_FREQ_48kHz, ///< 48 kHz
+ MBG_GPIO_FIXED_FREQ_1MHz, ///< 1 MHz
+ MBG_GPIO_FIXED_FREQ_1544kHz, ///< 1.544 MHz
+ MBG_GPIO_FIXED_FREQ_2048kHz, ///< 2.048 MHz
+ MBG_GPIO_FIXED_FREQ_5MHz, ///< 5 MHz
+ MBG_GPIO_FIXED_FREQ_10MHz, ///< 10 MHz
+ MBG_GPIO_FIXED_FREQ_19440kHz, ///< 19.44 MHz
+ N_MBG_GPIO_FIXED_FREQ ///< number of predefined fixed frequencies
};
-/** Bit masks of supported fixed frequencies */
-#define MSK_MBG_GPIO_FIXED_FREQ_8kHz ( 1UL << MBG_GPIO_FIXED_FREQ_8kHz )
-#define MSK_MBG_GPIO_FIXED_FREQ_48kHz ( 1UL << MBG_GPIO_FIXED_FREQ_48kHz )
-#define MSK_MBG_GPIO_FIXED_FREQ_1MHz ( 1UL << MBG_GPIO_FIXED_FREQ_1MHz )
-#define MSK_MBG_GPIO_FIXED_FREQ_1544kHz ( 1UL << MBG_GPIO_FIXED_FREQ_1544kHz )
-#define MSK_MBG_GPIO_FIXED_FREQ_2048kHz ( 1UL << MBG_GPIO_FIXED_FREQ_2048kHz )
-#define MSK_MBG_GPIO_FIXED_FREQ_5MHz ( 1UL << MBG_GPIO_FIXED_FREQ_5MHz )
-#define MSK_MBG_GPIO_FIXED_FREQ_10MHz ( 1UL << MBG_GPIO_FIXED_FREQ_10MHz )
-#define MSK_MBG_GPIO_FIXED_FREQ_19440kHz ( 1UL << MBG_GPIO_FIXED_FREQ_19440kHz )
-/*
- * Initializers for GPIO fixed frequency strings.
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_FIXED_FREQS
+ *
+ * @see ::MBG_GPIO_FIXED_FREQS
+ * @see ::MBG_GPIO_FIXED_FREQ_STRS
+ */
+enum MBG_GPIO_FIXED_FREQ_MASKS
+{
+ MSK_MBG_GPIO_FIXED_FREQ_8kHz = ( 1UL << MBG_GPIO_FIXED_FREQ_8kHz ), ///< see ::MBG_GPIO_FIXED_FREQ_8kHz
+ MSK_MBG_GPIO_FIXED_FREQ_48kHz = ( 1UL << MBG_GPIO_FIXED_FREQ_48kHz ), ///< see ::MBG_GPIO_FIXED_FREQ_48kHz
+ MSK_MBG_GPIO_FIXED_FREQ_1MHz = ( 1UL << MBG_GPIO_FIXED_FREQ_1MHz ), ///< see ::MBG_GPIO_FIXED_FREQ_1MHz
+ MSK_MBG_GPIO_FIXED_FREQ_1544kHz = ( 1UL << MBG_GPIO_FIXED_FREQ_1544kHz ), ///< see ::MBG_GPIO_FIXED_FREQ_1544kHz
+ MSK_MBG_GPIO_FIXED_FREQ_2048kHz = ( 1UL << MBG_GPIO_FIXED_FREQ_2048kHz ), ///< see ::MBG_GPIO_FIXED_FREQ_2048kHz
+ MSK_MBG_GPIO_FIXED_FREQ_5MHz = ( 1UL << MBG_GPIO_FIXED_FREQ_5MHz ), ///< see ::MBG_GPIO_FIXED_FREQ_5MHz
+ MSK_MBG_GPIO_FIXED_FREQ_10MHz = ( 1UL << MBG_GPIO_FIXED_FREQ_10MHz ), ///< see ::MBG_GPIO_FIXED_FREQ_10MHz
+ MSK_MBG_GPIO_FIXED_FREQ_19440kHz = ( 1UL << MBG_GPIO_FIXED_FREQ_19440kHz ) ///< see ::MBG_GPIO_FIXED_FREQ_19440kHz
+};
+
+
+/**
+ * @brief Initializers for an array of GPIO fixed frequency name strings
+ *
+ * @see ::MBG_GPIO_FIXED_FREQS
+ * @see ::MBG_GPIO_FIXED_FREQ_MASKS
*/
#define MBG_GPIO_FIXED_FREQ_STRS \
{ \
- "8kHz", \
- "48kHz", \
- "1MHz", \
- "1544kHz", \
- "2048kHz", \
- "5MHz", \
- "10MHz", \
- "19440kHz" \
+ "8 kHz", \
+ "48 kHz", \
+ "1 MHz", \
+ "1544 kHz", \
+ "2048 kHz", \
+ "5 MHz", \
+ "10 MHz", \
+ "19440 kHz" \
}
+
/**
* @brief Configuration of a GPIO fixed frequency output
*
- * @see MBG_GPIO_TYPE_FIXED_FREQ_OUT
+ * Used as sub-structure of ::MBG_GPIO_SETTINGS.
+ *
+ * @see ::MBG_GPIO_TYPE_FIXED_FREQ_OUT
+ * @see ::MBG_GPIO_SETTINGS
*/
typedef struct
{
- uint32_t freq_idx; /**< fixed frequency index, see ::MBG_GPIO_FIXED_FREQ */
- uint32_t shape; /**< signal shape, see ::MBG_GPIO_SIGNAL_SHAPES */
- uint32_t reserved; /**< currently always 0 */
- uint32_t flags; /**< currently always 0 */
+ uint32_t freq_idx; ///< fixed frequency index, see ::MBG_GPIO_FIXED_FREQS
+ uint32_t shape; ///< selected signal shape, see ::MBG_GPIO_SIGNAL_SHAPES
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< reserved, currently always 0
} MBG_GPIO_FIXED_FREQ_OUT_SETTINGS;
+#define _mbg_swab_mbg_gpio_fixed_freq_out_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->freq_idx ); \
+ _mbg_swab32( &(_p)->shape ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
/**
* @brief Supported options for a fixed frequency output
*
- * @see MBG_GPIO_TYPE_FIXED_FREQ_OUT
+ * Used as sub-structure of ::MBG_GPIO_LIMITS.
+ *
+ * @see ::MBG_GPIO_TYPE_FIXED_FREQ_OUT
+ * @see ::MBG_GPIO_LIMITS
*/
typedef struct
{
- uint32_t supp_freq; /**< bit mask of supported fixed frequencies, see ::MBG_GPIO_FIXED_FREQ */
- uint32_t supp_shapes; /**< bit mask of supported signal shapes, see ::MBG_GPIO_SIGNAL_SHAPES */
- uint32_t reserved; /**< currently always 0 */
- uint32_t supp_flags; /**< currently always 0 */
+ uint32_t supp_freq; ///< bit mask of supported fixed frequencies, see ::MBG_GPIO_FIXED_FREQ_MASKS
+ uint32_t supp_shapes; ///< bit mask of supported signal shapes, see ::MBG_GPIO_SIGNAL_SHAPE_MASKS
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t supp_flags; ///< reserved, currently always 0
} MBG_GPIO_FIXED_FREQ_OUT_SUPP;
+#define _mbg_swab_mbg_gpio_fixed_freq_out_supp( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_freq ); \
+ _mbg_swab32( &(_p)->supp_shapes ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+} while ( 0 )
+
/**
- * @brief Definitions for MBG_GPIO_BITS::format
+ * @brief Enumeration of BITS signal formats
+ *
+ * Used with ::MBG_GPIO_BITS_IN_SETTINGS::format and ::MBG_GPIO_BITS_OUT_SETTINGS::format
+ *
+ * @see ::MBG_GPIO_BITS_FORMAT_MASKS
*/
enum MBG_GPIO_BITS_FORMATS
{
- MBG_GPIO_BITS_E1_FRAMED, /**< 2.048MBit */
- MBG_GPIO_BITS_T1_FRAMED, /**< 1.544MBit */
- MBG_GPIO_BITS_E1_TIMING, /**< 2.048MHz */
- MBG_GPIO_BITS_T1_TIMING, /**< 2.048MHz */
- N_MBG_GPIO_BITS_FORMATS /**< number of formats */
+ MBG_GPIO_BITS_E1_FRAMED, ///< 2.048 MBit
+ MBG_GPIO_BITS_T1_FRAMED, ///< 1.544 MBit
+ MBG_GPIO_BITS_E1_TIMING, ///< 2.048 MHz
+ MBG_GPIO_BITS_T1_TIMING, ///< 2.048 MHz
+ N_MBG_GPIO_BITS_FORMATS ///< number of defined formats
+};
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_BITS_FORMATS
+ *
+ * Used with ::MBG_GPIO_BITS_IN_SUPP::supp_fmts and ::MBG_GPIO_BITS_OUT_SUPP::supp_fmts.
+ *
+ * @see ::MBG_GPIO_BITS_FORMATS
+ */
+enum MBG_GPIO_BITS_FORMAT_MASKS
+{
+ MSK_MBG_GPIO_BITS_E1_FRAMED = ( 1UL << MBG_GPIO_BITS_E1_FRAMED ), ///< see ::MBG_GPIO_BITS_E1_FRAMED
+ MSK_MBG_GPIO_BITS_T1_FRAMED = ( 1UL << MBG_GPIO_BITS_T1_FRAMED ), ///< see ::MBG_GPIO_BITS_T1_FRAMED
+ MSK_MBG_GPIO_BITS_E1_TIMING = ( 1UL << MBG_GPIO_BITS_E1_TIMING ), ///< see ::MBG_GPIO_BITS_E1_TIMING
+ MSK_MBG_GPIO_BITS_T1_TIMING = ( 1UL << MBG_GPIO_BITS_T1_TIMING ) ///< see ::MBG_GPIO_BITS_T1_TIMING
+};
+
+
+/**
+ * @brief Initializers for an array of GPIO bit format strings
+ *
+ * @see ::MBG_GPIO_BITS_FORMATS
+ * @see ::MBG_GPIO_BITS_FORMAT_MASKS
+ */
+#define MBG_GPIO_BITS_FORMAT_STRS \
+{ \
+ "E1 Framed", \
+ "T1 Framed", \
+ "E1 Timing", \
+ "T1 Timing" \
+}
+
+
+
+/**
+ * @brief Minimum and maximum known SSM values
+ *
+ * Values according to ITU G.704-1998
+ *
+ * Used with ::MBG_GPIO_BITS_IN_SETTINGS::quality::e1.ssm
+ * and ::MBG_GPIO_BITS_OUT_SETTINGS::ssm.
+ */
+enum GPIO_SSM_VALS
+{
+ GPIO_SSM_UNKNOWN, ///< Quality unknown, existing synchronization network
+ GPIO_SSM_RSVD_1, ///< (reserved)
+ GPIO_SSM_G_811, ///< Rec. G.811
+ GPIO_SSM_RSVD_3, ///< (reserved)
+ GPIO_SSM_SSU_A, ///< SSU-A
+ GPIO_SSM_RSVD_5, ///< (reserved)
+ GPIO_SSM_RSVD_6, ///< (reserved)
+ GPIO_SSM_RSVD_7, ///< (reserved)
+ GPIO_SSM_SSU_B, ///< SSU-B
+ GPIO_SSM_RSVD_9, ///< (reserved)
+ GPIO_SSM_RSVD_10, ///< (reserved)
+ GPIO_SSM_RSVD_SETS, ///< Synchronous Equipment Timing Source (SETS)
+ GPIO_SSM_RSVD_12, ///< (reserved)
+ GPIO_SSM_RSVD_13, ///< (reserved)
+ GPIO_SSM_RSVD_14, ///< (reserved)
+ GPIO_SSM_DONT_USE, ///< don't use
+ N_GPIO_SSM_VALS
};
-#define MSK_MBG_GPIO_BITS_E1_FRAMED ( 1UL << MBG_GPIO_BITS_E1_FRAMED )
-#define MSK_MBG_GPIO_BITS_T1_FRAMED ( 1UL << MBG_GPIO_BITS_T1_FRAMED )
-#define MSK_MBG_GPIO_BITS_E1_TIMING ( 1UL << MBG_GPIO_BITS_E1_TIMING )
-#define MSK_MBG_GPIO_BITS_T1_TIMING ( 1UL << MBG_GPIO_BITS_T1_TIMING )
+
+
+/**
+ * @brief Minimum and maximum SA BITS groups
+ *
+ * Used with ::MBG_GPIO_BITS_IN_SETTINGS::quality::e1::sa_bits
+ * and ::MBG_GPIO_BITS_OUT_SETTINGS::sa_bits.
+ */
+enum GPIO_SA_BITS_GROUPS
+{
+ MIN_SA_BITS_GROUP = 4,
+ MAX_SA_BITS_GROUP = 8
+};
/**
* @brief Configuration of a GPIO as BITS input module
*
- * @see MBG_GPIO_TYPE_BITS_IN
+ * Used as sub-structure of ::MBG_GPIO_SETTINGS.
+ *
+ * @see ::MBG_GPIO_TYPE_BITS_IN
+ * @see ::MBG_GPIO_SETTINGS
*/
typedef struct
{
- uint32_t format; /**< signal type, see ::MBG_GPIO_BITS_FORMATS */
- uint32_t reserved;
- uint32_t csc_limit; /**< max. cycle slip [1/1000 cycle units] */
+ uint32_t format; ///< signal format, see ::MBG_GPIO_BITS_FORMATS
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t csc_limit; ///< max. cycle slip [1/1000 cycle units]
- union
+ union quality
{
- struct
+ struct e1
{
- uint8_t ssm; /**< minimum E1 SSM ( 0...15 ) for acceptance */
- uint8_t sa_bits; /**< Sa Bits group ( 4...8 ) carrying SSM */
- uint16_t reserve;
- } e1; /**< used with E1 formats */
+ uint8_t ssm; ///< minimum E1 SSM for acceptance, 0..::N_GPIO_SSM_VALS-1
+ uint8_t sa_bits; ///< sa bits group carrying SSM, ::MIN_SA_BITS_GROUP..::MAX_SA_BITS_GROUP
+ uint16_t reserved; ///< reserved, currently always 0
+ } e1; ///< used with E1 formats
- struct
+ struct t1
{
uint8_t min_boc;
- uint8_t reserve_0;
- uint16_t reserve_1;
- } t1; /**< used with T1 formats */
+ uint8_t reserved_0; ///< reserved, currently always 0
+ uint16_t reserved_1; ///< reserved, currently always 0
+ } t1; ///< used with T1 formats
- uint32_t u32; /**< dummy to force at least 32 bit alignment */
+ uint32_t u32; ///< dummy to force at least 32 bit alignment
} quality;
- uint32_t err_msk; /**< controls which types of error can be ignored, see enum MBG_GPIO_BITS_ERR */
- uint32_t flags; /**< currently always 0 */
+ uint32_t err_msk; ///< controls which types of error can be ignored, see ::MBG_GPIO_BITS_ERR_MASKS
+ uint32_t flags; ///< reserved, currently always 0
} MBG_GPIO_BITS_IN_SETTINGS;
+#define _mbg_swab_mbg_gpio_bits_in_settings( _p, _recv ) \
+do \
+{ \
+ uint32_t f = (_p)->format; \
+ if ( (_recv) ) \
+ _mbg_swab32( &f); \
+ _mbg_swab32( &(_p)->format ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->csc_limit ); \
+ switch( f ) \
+ { \
+ case MBG_GPIO_BITS_E1_FRAMED : \
+ case MBG_GPIO_BITS_E1_TIMING : \
+ _mbg_swab8( &(_p)->quality.e1.ssm ); \
+ _mbg_swab8( &(_p)->quality.e1.sa_bits ); \
+ _mbg_swab16( &(_p)->quality.e1.reserved ); \
+ break; \
+ \
+ case MBG_GPIO_BITS_T1_FRAMED : \
+ case MBG_GPIO_BITS_T1_TIMING : \
+ _mbg_swab8( &(_p)->quality.t1.min_boc ); \
+ _mbg_swab8( &(_p)->quality.t1.reserved_0 ); \
+ _mbg_swab16( &(_p)->quality.t1.reserved_1 ); \
+ break; \
+ \
+ default: \
+ break; \
+ } \
+ _mbg_swab32( &(_p)->err_msk ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of BITS input error conditions
+ */
+enum MBG_GPIO_BITS_ERRS
+{
+ MBG_GPIO_BITS_ERR_LOS, ///< loss of signal
+ MBG_GPIO_BITS_ERR_LOF, ///< loss of frame
+ N_MBG_GPIO_BITS_ERRS ///< number of known errors
+};
+
/**
- * @brief Definitions for MBG_GPIO_BITS_IN_SETTINGS::err_msk
+ * @brief Bit masks associated with BITS input error conditions
+ *
+ * Used with ::MBG_GPIO_BITS_IN_SETTINGS::err_msk
+ *
+ * @see ::MBG_GPIO_BITS_ERRS
*/
-enum MBG_GPIO_BITS_ERR
+enum MBG_GPIO_BITS_ERR_MASKS
{
- MBG_GPIO_BITS_ERR_LOS, /**< loss of signal error */
- MBG_GPIO_BITS_ERR_LOF, /**< loss of frame */
- N_MBG_GPIO_BITS_ERR /**< number of formats */
+ MSK_MBG_GPIO_BITS_ERR_LOS = ( 1UL << MBG_GPIO_BITS_ERR_LOS ), ///< see ::MBG_GPIO_BITS_ERR_LOS
+ MSK_MBG_GPIO_BITS_ERR_LOF = ( 1UL << MBG_GPIO_BITS_ERR_LOF ) ///< see ::MBG_GPIO_BITS_ERR_LOF
};
-#define MSK_MBG_GPIO_BITS_ERR_LOS ( 1UL << MBG_GPIO_BITS_ERR_LOS )
-#define MSK_MBG_GPIO_BITS_ERR_LOF ( 1UL << MBG_GPIO_BITS_ERR_LOF )
-
/**
* @brief Supported options of a BITS GPIO input
*
- * @see MBG_GPIO_TYPE_BITS_IN
+ * Used as sub-structure of ::MBG_GPIO_LIMITS.
+ *
+ * @see ::MBG_GPIO_TYPE_BITS_IN
+ * @see ::MBG_GPIO_LIMITS
*/
typedef struct
{
- uint32_t supp_fmts; ///< bit mask of supported formats, see ::MBG_GPIO_BITS_FORMATS
- uint32_t reserved; ///< reserved, currently always 0
+ uint32_t supp_fmts; ///< bit mask of supported formats, see ::MBG_GPIO_BITS_FORMAT_MASKS
+ uint32_t reserved; ///< reserved, currently always 0
} MBG_GPIO_BITS_IN_SUPP;
+#define _mbg_swab_mbg_gpio_bits_in_supp( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_fmts ); \
+ _mbg_swab32( &(_p)->reserved ); \
+} while ( 0 )
+
/**
* @brief Configuration of a GPIO as BITS output module
*
- * @see MBG_GPIO_TYPE_BITS_OUT
+ * Used as sub-structure of ::MBG_GPIO_SETTINGS.
+ *
+ * @see ::MBG_GPIO_TYPE_BITS_OUT
+ * @see ::MBG_GPIO_SETTINGS
*/
typedef struct
{
- uint32_t format; /**< signal type, enum MBG_GPIO_BITS_FORMATS */
- uint32_t flags; /**< flags for encoder control etc. */
- uint8_t sa_bits; /**< number of SA Bit group for E1 SSM ( 4...8 ) */
- uint8_t ssm; /**< ssm for E1 mode 0..0x0F */
- uint8_t boc; /**< boc for T1 mode 0..0x1F */
- uint8_t reserved_0;
- uint32_t reserved_1;
- uint32_t reserved_2;
- uint32_t reserved_3;
+ uint32_t format; ///< signal format, see ::MBG_GPIO_BITS_FORMATS
+ uint32_t flags; ///< flags for encoder control etc., see ::MBG_GPIO_BITS_OUT_FLAG_MASKS
+ uint8_t sa_bits; ///< number of SA bit group for E1 SSM, ::MIN_SA_BITS_GROUP..::MAX_SA_BITS_GROUP
+ uint8_t ssm; ///< ssm for E1 mode, 0..::N_GPIO_SSM_VALS-1
+ uint8_t boc; ///< boc for T1 mode, 0..0x1F //##++++++++++++++
+ uint8_t reserved_0; ///< reserved, currently always 0
+ uint32_t reserved_1; ///< reserved, currently always 0
+ uint32_t reserved_2; ///< reserved, currently always 0
+ uint32_t reserved_3; ///< reserved, currently always 0
} MBG_GPIO_BITS_OUT_SETTINGS;
+#define _mbg_swab_mbg_gpio_bits_out_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->format ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab8( &(_p)->sa_bits ); \
+ _mbg_swab8( &(_p)->ssm ); \
+ _mbg_swab8( &(_p)->boc ); \
+ _mbg_swab8( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+} while ( 0 )
+
+
/**
- * @brief Definitions for MBG_GPIO_BITS_OUT_SETTINGS::flags
+ * @brief Enumeration of flags used with BITS type GPIO outputs
+ *
+ * @see ::MBG_GPIO_BITS_OUT_FLAG_MASKS
+ * @see ::MBG_GPIO_BITS_OUT_FLAG_STRS
*/
-enum MBG_GPIO_BITS_OUT_FLAG
+enum MBG_GPIO_BITS_OUT_FLAGS
{
- MBG_GPIO_BITS_OUT_FLAG_HDB3, /**< enable HDB3 encoding ( E1 mode only ) */
- MBG_GPIO_BITS_OUT_FLAG_B8ZS, /**< enable B8ZS encoding ( T1 mode only ) */
- N_MBG_GPIO_BITS_OUT_FLAG /**< number of flags */
+ MBG_GPIO_BITS_OUT_FLAG_HDB3, ///< enable HDB3 encoding (E1 mode only)
+ MBG_GPIO_BITS_OUT_FLAG_B8ZS, ///< enable B8ZS encoding (T1 mode only)
+ N_MBG_GPIO_BITS_OUT_FLAGS ///< number of known flags
};
-#define MSK_MBG_GPIO_BITS_OUT_FLAG_HDB3 ( 1UL << MBG_GPIO_BITS_OUT_FLAG_HDB3 )
-#define MSK_MBG_GPIO_BITS_OUT_FLAG_B8ZS ( 1UL << MBG_GPIO_BITS_OUT_FLAG_B8ZS )
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_BITS_OUT_FLAGS
+ *
+ * Used with ::MBG_GPIO_BITS_OUT_SETTINGS::flags
+ *
+ * @see ::MBG_GPIO_BITS_OUT_FLAGS
+ * @see ::MBG_GPIO_BITS_OUT_FLAG_STRS
+ */
+enum MBG_GPIO_BITS_OUT_FLAG_MASKS
+{
+ MSK_MBG_GPIO_BITS_OUT_FLAG_HDB3 = ( 1UL << MBG_GPIO_BITS_OUT_FLAG_HDB3 ), ///< see ::MBG_GPIO_BITS_OUT_FLAG_HDB3
+ MSK_MBG_GPIO_BITS_OUT_FLAG_B8ZS = ( 1UL << MBG_GPIO_BITS_OUT_FLAG_B8ZS ) ///< see ::MBG_GPIO_BITS_OUT_FLAG_B8ZS
+};
/**
- * @brief Supported options of a BITS GPIO output
+ * @brief String initializers for an array of GPIO BITS out flags
*
- * @see MBG_GPIO_TYPE_BITS_OUT
+ * @see ::MBG_GPIO_BITS_OUT_FLAGS
+ * @see ::MBG_GPIO_BITS_OUT_FLAG_MASKS
+ */
+#define MBG_GPIO_BITS_OUT_FLAG_STRS \
+{ \
+ "HDB3", \
+ "B8ZS" \
+}
+
+
+/**
+ * @brief Supported options of a BITS type GPIO output
+ *
+ * Used as sub-structure of ::MBG_GPIO_LIMITS.
+ *
+ * @see ::MBG_GPIO_TYPE_BITS_OUT
+ * @see ::MBG_GPIO_LIMITS
*/
typedef struct
{
- uint32_t supp_fmts; /**< bit mask of supported formats, see ::MBG_GPIO_BITS_FORMATS */
- uint32_t reserved; /**< currently always 0 */
+ uint32_t supp_fmts; ///< bit mask of supported formats, see ::MBG_GPIO_BITS_FORMAT_MASKS
+ uint32_t supp_flags; ///< bit mask of supported flags, see ::MBG_GPIO_BITS_OUT_FLAG_MASKS
+
} MBG_GPIO_BITS_OUT_SUPP;
+#define _mbg_swab_mbg_gpio_bits_out_supp( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_fmts ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of Video signal formats
+ *
+ * Used with ::MBG_GPIO_VIDEO_OUT_SETTINGS::format
+ *
+ * @see ::MBG_GPIO_VIDEO_FORMAT_MASKS
+ */
+enum MBG_GPIO_VIDEO_FORMATS
+{
+ MBG_GPIO_VIDEO_FORMAT_OFF, ///< OFF
+ MBG_GPIO_VIDEO_SD_FORMAT_NTSC, ///< NTSC 525i
+ MBG_GPIO_VIDEO_SD_FORMAT_PAL, ///< PAL standard (Germany) 625i
+ MBG_GPIO_VIDEO_HD_FORMAT_720_P_50Hz, ///< SMPTE296M-3 720p at 50 Hz
+ MBG_GPIO_VIDEO_HD_FORMAT_1080_I_50Hz, ///< SMPTE274M-6 1080i at 50 Hz
+ MBG_GPIO_VIDEO_HD_FORMAT_720_P_59_94Hz, ///< SMPTE296M-1 720p at 59.94 Hz
+ MBG_GPIO_VIDEO_HD_FORMAT_1080_I_59_94Hz, ///< SMPTE274M-7 1080i at 59.94 Hz
+ MBG_GPIO_VIDEO_SD_FORMAT_PAL_M, ///< PAL M (Brazil) 525i
+ N_MBG_GPIO_VIDEO_FORMATS ///< number of defined video formats
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_VIDEO_FORMATS
+ *
+ * Used with ::MBG_GPIO_VIDEO_OUT_SUPP::supp_formats
+ *
+ * @see ::MBG_GPIO_VIDEO_FORMATS
+ */
+enum MBG_GPIO_VIDEO_FORMAT_MASKS
+{
+ MSK_MBG_GPIO_VIDEO_FORMAT_OFF = ( 1UL << MBG_GPIO_VIDEO_FORMAT_OFF ), ///< see ::MBG_GPIO_VIDEO_FORMAT_OFF
+ MSK_MBG_GPIO_VIDEO_SD_FORMAT_NTSC = ( 1UL << MBG_GPIO_VIDEO_SD_FORMAT_NTSC ), ///< see ::MBG_GPIO_VIDEO_SD_FORMAT_NTSC
+ MSK_MBG_GPIO_VIDEO_SD_FORMAT_PAL = ( 1UL << MBG_GPIO_VIDEO_SD_FORMAT_PAL ), ///< see ::MBG_GPIO_VIDEO_SD_FORMAT_PAL
+ MSK_MBG_GPIO_VIDEO_HD_FORMAT_720_P_50Hz = ( 1UL << MBG_GPIO_VIDEO_HD_FORMAT_720_P_50Hz ), ///< see ::MBG_GPIO_VIDEO_HD_FORMAT_720_P_50Hz
+ MSK_MBG_GPIO_VIDEO_HD_FORMAT_1080_I_50Hz = ( 1UL << MBG_GPIO_VIDEO_HD_FORMAT_1080_I_50Hz ), ///< see ::MBG_GPIO_VIDEO_HD_FORMAT_1080_I_50Hz
+ MSK_MBG_GPIO_VIDEO_HD_FORMAT_720_P_59_94Hz = ( 1UL << MBG_GPIO_VIDEO_HD_FORMAT_720_P_59_94Hz ), ///< see ::MBG_GPIO_VIDEO_HD_FORMAT_720_P_59_94Hz
+ MSK_MBG_GPIO_VIDEO_HD_FORMAT_1080_I_59_94Hz = ( 1UL << MBG_GPIO_VIDEO_HD_FORMAT_1080_I_59_94Hz ), ///< see ::MBG_GPIO_VIDEO_HD_FORMAT_1080_I_59_94Hz
+ MSK_MBG_GPIO_VIDEO_SD_FORMAT_PAL_M = ( 1UL << MBG_GPIO_VIDEO_SD_FORMAT_PAL_M ) ///< see ::MBG_GPIO_VIDEO_SD_FORMAT_PAL_M
+};
+
+
+/**
+ * @brief A combination of bit masks for SD video formats
+ * @see ::MBG_GPIO_VIDEO_FORMAT_MASKS
+ */
+#define MBG_GPIO_VIDEO_SD_FORMATS ( MSK_MBG_GPIO_VIDEO_FORMAT_OFF | MSK_MBG_GPIO_VIDEO_SD_FORMAT_NTSC | MSK_MBG_GPIO_VIDEO_SD_FORMAT_PAL | \
+ MSK_MBG_GPIO_VIDEO_SD_FORMAT_PAL_M )
+
+/**
+ * @brief A combination of bit masks for HD video formats
+ * @see ::MBG_GPIO_VIDEO_FORMAT_MASKS
+ */
+#define MBG_GPIO_VIDEO_HD_FORMATS ( MSK_MBG_GPIO_VIDEO_FORMAT_OFF | MSK_MBG_GPIO_VIDEO_HD_FORMAT_720_P_50Hz | MSK_MBG_GPIO_VIDEO_HD_FORMAT_1080_I_50Hz | \
+ MSK_MBG_GPIO_VIDEO_HD_FORMAT_720_P_59_94Hz | MSK_MBG_GPIO_VIDEO_HD_FORMAT_1080_I_59_94Hz )
+
+
+
+/**
+ * @brief Initializers for an array of video output name strings
+ *
+ * @see ::MBG_GPIO_VIDEO_FORMATS
+ * @see ::MBG_GPIO_VIDEO_FORMAT_MASKS
+ */
+#define MBG_GPIO_VIDEO_OUT_STRS \
+{ \
+ "OFF", \
+ "NTSC (525i)", \
+ "PAL (625i)", \
+ "720p 50 Hz", \
+ "1080i 50 Hz", \
+ "720p 59.94 Hz", \
+ "1080i 59.94 Hz", \
+ "PAL M (525i)" \
+}
+
+
+
+/**
+ * @brief Enumeration of flags used with video type GPIO outputs
+ */
+enum MBG_GPIO_VIDEO_OUT_FLAGS
+{
+ MBG_GPIO_VIDEO_OUT_HAS_NO_FREE_CONF, ///< if set, Out1: HD, Out2: SD
+ MBG_GPIO_VIDEO_OUT_HAS_TC_SD, ///< supports Time Code for SD Black Bursts
+ N_MBG_GPIO_VIDEO_OUT_FLAGS ///< number of known flags
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_VIDEO_OUT_FLAGS
+ *
+ * Used with ::MBG_GPIO_VIDEO_OUT_SETTINGS::flags
+ *
+ * @see ::MBG_GPIO_VIDEO_OUT_FLAGS
+ */
+enum MBG_GPIO_VIDEO_OUT_FLAG_MASKS
+{
+ MSK_MBG_GPIO_VIDEO_OUT_HAS_NO_FREE_CONF = ( 1UL << MBG_GPIO_VIDEO_OUT_HAS_NO_FREE_CONF ), ///< see ::MBG_GPIO_VIDEO_OUT_HAS_NO_FREE_CONF
+ MSK_MBG_GPIO_VIDEO_OUT_HAS_TC_SD = ( 1UL << MBG_GPIO_VIDEO_OUT_HAS_TC_SD ) ///< see ::MBG_GPIO_VIDEO_OUT_HAS_TC_SD
+};
+
+
+
+/**
+ * @brief Enumeration of epochs used with video type GPIO outputs
+ *
+ * Used with ::MBG_GPIO_VIDEO_OUT_SETTINGS::epoch, and used to
+ * define ::MBG_GPIO_VIDEO_EPOCH_MASKS
+ *
+ * @see ::MBG_GPIO_VIDEO_EPOCH_MASKS
+ * @see ::MBG_GPIO_VIDEO_EPOCH_STRS
+ */
+enum MBG_GPIO_VIDEO_EPOCHS
+{
+ SMPTE_TAI_EPOCH_1970, ///< 1970-01-01 00:00:00
+ SMPTE_TAI_EPOCH_1958, ///< 1958-01-01 00:00:00
+ SMPTE_UTC_EPOCH_1972, ///< 1972-01-01 00:00:00
+ SMPTE_GPS_EPOCH_1980, ///< 1980-01-06 00:00:00
+ N_MBG_GPIO_VIDEO_EPOCHS ///< number of known epochs
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_VIDEO_EPOCHS
+ *
+ * Used with :: MBG_GPIO_VIDEO_OUT_SUPP::supp_epochs
+ *
+ * @see ::MBG_GPIO_VIDEO_EPOCHS
+ */
+enum MBG_GPIO_VIDEO_EPOCH_MASKS
+{
+ MSK_SMPTE_TAI_EPOCH_1970 = ( 1UL << SMPTE_TAI_EPOCH_1970 ), ///< see ::SMPTE_TAI_EPOCH_1970
+ MSK_SMPTE_TAI_EPOCH_1958 = ( 1UL << SMPTE_TAI_EPOCH_1958 ), ///< see ::SMPTE_TAI_EPOCH_1958
+ MSK_SMPTE_UTC_EPOCH_1972 = ( 1UL << SMPTE_UTC_EPOCH_1972 ), ///< see ::SMPTE_UTC_EPOCH_1972
+ MSK_SMPTE_GPS_EPOCH_1980 = ( 1UL << SMPTE_GPS_EPOCH_1980 ) ///< see ::SMPTE_GPS_EPOCH_1980
+};
+
+
+
+/**
+ * @brief Initializers for an array of video epoch strings
+ *
+ * @see ::MBG_GPIO_VIDEO_EPOCHS
+ */
+#define MBG_GPIO_VIDEO_EPOCH_STRS \
+{ \
+ "TAI D1970-01-01 T00:00:00", \
+ "TAI D1958-01-01 T00:00:00", \
+ "UTC D1972-01-01 T00:00:00", \
+ "GPS D1980-01-06 T00:00:00" \
+}
+
+
+
+/**
+ * @brief Enumeration of time code modes used with video type GPIO outputs
+ *
+ * Used with ::MBG_GPIO_VIDEO_OUT_SETTINGS::tc_mode
+ *
+ */
+enum MBG_GPIO_VIDEO_TC_MODES
+{
+ MBG_GPIO_VIDEO_TC_MODE_NONE, ///< None
+ MBG_GPIO_VIDEO_TC_MODE_VITC, ///< Vertical Interval Time Code
+ N_MBG_GPIO_VIDEO_TC_MODES
+};
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_VIDEO_TC_MODES
+ *
+ * Used with ::MBG_GPIO_VIDEO_OUT_SETTINGS::tc_mode
+ *
+ */
+enum MBG_GPIO_VIDEO_TC_MODE_MASKS
+{
+ MSK_MBG_GPIO_VIDEO_TC_MODE_NONE = ( 1UL << MBG_GPIO_VIDEO_TC_MODE_NONE ), ///< see ::MBG_GPIO_VIDEO_TC_MODE_NONE
+ MSK_MBG_GPIO_VIDEO_TC_MODE_VITC = ( 1UL << MBG_GPIO_VIDEO_TC_MODE_VITC ) ///< see ::MBG_GPIO_VIDEO_TC_MODE_VITC
+};
+
+
+/**
+ * @brief Initializers for an array of video time code modes
+ *
+ * @see ::MBG_GPIO_VIDEO_TC_MODES
+ */
+#define MBG_GPIO_VIDEO_TC_MODE_STRS \
+{ \
+ "None", \
+ "VITC" \
+}
+
+
/**
- * @brief A generic structure used to configure a GPIO port
+ * @brief Configuration of a GPIO as video output module
+ *
+ * Used as sub-structure of ::MBG_GPIO_SETTINGS.
+ *
+ * @see ::MBG_GPIO_TYPE_VIDEO_OUT
+ * @see ::MBG_GPIO_SETTINGS
*/
typedef struct
{
- uint32_t type; /**< GPIO type, see ::MBG_GPIO_TYPES */
- uint32_t reserved; /**< currently always 0 */
- uint32_t flags; /**< currently always 0 */
+ uint32_t format; ///< video format, see ::MBG_GPIO_VIDEO_FORMATS
+ uint32_t flags; ///< flags, see ::MBG_GPIO_VIDEO_OUT_FLAG_MASKS
+ int32_t phase_offset; ///< Phase offset in [ns]
+ uint8_t epoch; ///< epoch, see ::MBG_GPIO_VIDEO_EPOCHS
+
+ uint8_t tc_mode; ///< time code mode, see ::MBG_GPIO_VIDEO_TC_MODES
+ uint8_t tc_line0; ///< first time code line location, valid lines: 6-22
+ uint8_t tc_line1; ///< second time code line location, valid lines: 6-22
+
+ uint32_t reserved0; ///< reserved, currently always 0
+ uint32_t reserved1; ///< reserved, currently always 0
+
+} MBG_GPIO_VIDEO_OUT_SETTINGS;
+
+#define _mbg_swab_mbg_gpio_video_out_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->format ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab32( &(_p)->phase_offset ); \
+ _mbg_swab8( &(_p)->epoch ); \
+ _mbg_swab8( &(_p)->tc_mode ); \
+ _mbg_swab8( &(_p)->tc_line0 ); \
+ _mbg_swab8( &(_p)->tc_line1 ); \
+ _mbg_swab32( &(_p)->reserved0 ); \
+ _mbg_swab32( &(_p)->reserved1 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Supported options of a video type GPIO output
+ *
+ * Used as sub-structure of ::MBG_GPIO_LIMITS.
+ *
+ * @see ::MBG_GPIO_TYPE_VIDEO_OUT
+ * @see ::MBG_GPIO_LIMITS
+ */
+typedef struct
+{
+ uint32_t supp_formats; ///< supported video formats, see ::MBG_GPIO_VIDEO_FORMAT_MASKS
+ uint32_t supp_flags; ///< supported flags, see ::MBG_GPIO_VIDEO_OUT_FLAG_MASKS
+ uint32_t supp_epochs; ///< supported epochs, see ::MBG_GPIO_VIDEO_EPOCH_MASKS
+
+ uint8_t supp_tc_modes; ///< supported tc_modes, see ::MBG_GPIO_VIDEO_TC_MODE_MASKS
+
+ uint8_t reserved0; ///< reserved, currently always 0
+ uint8_t reserved2; ///< reserved, currently always 0
+ uint16_t reserved3; ///< reserved, currently always 0
+ uint32_t reserved1; ///< reserved, currently always 0
+
+} MBG_GPIO_VIDEO_OUT_SUPP;
+
+#define _mbg_swab_mbg_gpio_video_out_supp( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_formats ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ _mbg_swab32( &(_p)->supp_epochs ); \
+ _mbg_swab8( &(_p)->supp_tc_modes ); \
+ _mbg_swab8( &(_p)->reserved0 ); \
+ _mbg_swab16( &(_p)->reserved2 ); \
+ _mbg_swab16( &(_p)->reserved3 ); \
+ _mbg_swab32( &(_p)->reserved1 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of types used with video sync GPIO outputs
+ * Depends on configured video output
+ */
+enum MBG_GPIO_VIDEO_SYNC_TYPES
+{
+ MBG_GPIO_VIDEO_SYNC_TYPE_OFF, ///< Output Off
+ MBG_GPIO_VIDEO_SYNC_TYPE_SD_HSYNC, ///< SD horizontal sync
+ MBG_GPIO_VIDEO_SYNC_TYPE_SD_VSYNC, ///< SD vertical sync
+ MBG_GPIO_VIDEO_SYNC_TYPE_SD_FRAME, ///< SD frame/field sync
+ MBG_GPIO_VIDEO_SYNC_TYPE_SD_BLANK, ///< SD blanking interval
+ MBG_GPIO_VIDEO_SYNC_TYPE_HD_HSYNC, ///< HD horizontal sync
+ MBG_GPIO_VIDEO_SYNC_TYPE_HD_VSYNC, ///< HD vertical sync
+ MBG_GPIO_VIDEO_SYNC_TYPE_HD_FRAME, ///< HD frame/field sync
+ MBG_GPIO_VIDEO_SYNC_TYPE_HD_BLANK, ///< HD blanking interval
+ N_MBG_GPIO_VIDEO_SYNC_TYPES ///< number of known types
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_VIDEO_SYNC_TYPES
+ *
+ * Used with ::MBG_GPIO_VIDEO_SYNC_OUT_SUPP::supp_types
+ *
+ * @see ::MBG_GPIO_VIDEO_SYNC_TYPES
+ */
+enum MBG_GPIO_VIDEO_SYNC_TYPE_MASKS
+{
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_OFF = ( 1UL << MBG_GPIO_VIDEO_SYNC_TYPE_OFF ),
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_SD_HSYNC = ( 1UL << MBG_GPIO_VIDEO_SYNC_TYPE_SD_HSYNC ),
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_SD_VSYNC = ( 1UL << MBG_GPIO_VIDEO_SYNC_TYPE_SD_VSYNC ),
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_SD_FRAME = ( 1UL << MBG_GPIO_VIDEO_SYNC_TYPE_SD_FRAME ),
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_SD_BLANK = ( 1UL << MBG_GPIO_VIDEO_SYNC_TYPE_SD_BLANK ),
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_HD_HSYNC = ( 1UL << MBG_GPIO_VIDEO_SYNC_TYPE_HD_HSYNC ),
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_HD_VSYNC = ( 1UL << MBG_GPIO_VIDEO_SYNC_TYPE_HD_VSYNC ),
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_HD_FRAME = ( 1UL << MBG_GPIO_VIDEO_SYNC_TYPE_HD_FRAME ),
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_HD_BLANK = ( 1UL << MBG_GPIO_VIDEO_SYNC_TYPE_HD_BLANK )
+};
- union /**< settings depending on the GPIO type, see ::MBG_GPIO_TYPES */
+
+
+/**
+ * @brief Initializers for an array of video sync output name strings
+ *
+ * @see ::MBG_GPIO_VIDEO_SYNC_TYPES
+ * @see ::MBG_GPIO_VIDEO_SYNC_TYPE_MASKS
+ */
+#define MBG_GPIO_VIDEO_SYNC_OUT_STRS \
+{ \
+ "OFF", \
+ "SD H-Sync", \
+ "SD V-Sync", \
+ "SD Frame", \
+ "SD Blank", \
+ "HD H-Sync", \
+ "HD V-Sync", \
+ "HD Frame", \
+ "HD Blank" \
+}
+
+
+
+/**
+ * @brief A combination of bit masks for SD video sync types
+ * @see ::MBG_GPIO_VIDEO_SYNC_TYPE_MASKS
+ */
+#define MBG_GPIO_VIDEO_SYNC_SD_TYPES ( MSK_MBG_GPIO_VIDEO_SYNC_TYPE_OFF | MSK_MBG_GPIO_VIDEO_SYNC_TYPE_SD_HSYNC | MSK_MBG_GPIO_VIDEO_SYNC_TYPE_SD_VSYNC | \
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_SD_FRAME | MSK_MBG_GPIO_VIDEO_SYNC_TYPE_SD_BLANK )
+
+/**
+ * @brief A combination of bit masks for HD video sync types
+ * @see ::MBG_GPIO_VIDEO_SYNC_TYPE_MASKS
+ */
+#define MBG_GPIO_VIDEO_SYNC_HD_TYPES ( MSK_MBG_GPIO_VIDEO_SYNC_TYPE_OFF | MSK_MBG_GPIO_VIDEO_SYNC_TYPE_HD_HSYNC | MSK_MBG_GPIO_VIDEO_SYNC_TYPE_HD_VSYNC | \
+ MSK_MBG_GPIO_VIDEO_SYNC_TYPE_HD_FRAME | MSK_MBG_GPIO_VIDEO_SYNC_TYPE_HD_BLANK )
+
+
+
+/**
+ * @brief Configuration of a GPIO as sync output module
+ *
+ * Used as sub-structure of ::MBG_GPIO_SETTINGS.
+ *
+ * @see ::MBG_GPIO_TYPE_VIDEO_SYNC_OUT
+ * @see ::MBG_GPIO_SETTINGS
+ */
+typedef struct
+{
+ uint32_t type; ///< sync type, see :: MBG_GPIO_SYNC_TYPES
+ uint32_t flags; ///< flags, currently always 0
+ uint32_t reserved0; ///< reserved, currently always 0
+ uint32_t reserved1; ///< reserved, currently always 0
+ uint32_t reserved2; ///< reserved, currently always 0
+ uint32_t reserved3; ///< reserved, currently always 0
+
+} MBG_GPIO_VIDEO_SYNC_OUT_SETTINGS;
+
+#define _mbg_swab_mbg_gpio_video_sync_out_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->type ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab32( &(_p)->reserved0 ); \
+ _mbg_swab32( &(_p)->reserved1 ); \
+ _mbg_swab32( &(_p)->reserved2 ); \
+ _mbg_swab32( &(_p)->reserved3 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Supported options of a sync type GPIO output
+ *
+ * Used as sub-structure of ::MBG_GPIO_LIMITS.
+ *
+ * @see ::MBG_GPIO_TYPE_VIDEO_SYNC_OUT
+ * @see ::MBG_GPIO_LIMITS
+ */
+typedef struct
+{
+ uint32_t supp_types; ///< supported types, see ::MBG_GPIO_VIDEO_SYNC_TYPE_MASKS
+ uint32_t supp_flags; ///< supported flags, currently always 0
+ uint32_t reserved0; ///< reserved, currently always 0
+ uint32_t reserved1; ///< reserved, currently always 0
+
+} MBG_GPIO_VIDEO_SYNC_OUT_SUPP;
+
+#define _mbg_swab_mbg_gpio_video_sync_out_supp( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_types ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ _mbg_swab32( &(_p)->reserved0 ); \
+ _mbg_swab32( &(_p)->reserved1 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of studio clock base frequencies
+ *
+ * Used with ::MBG_GPIO_STUDIO_CLOCK_OUT_SETTINGS::base_freq
+ *
+ * @see ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_MASKS
+ */
+enum MBG_GPIO_STUDIO_CLOCK_BASE_FREQS
+{
+ MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_32KHZ, ///< 32 kHz base frequency
+ MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_44_1KHZ, ///< 44.1 kHz base frequency
+ MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_48KHZ, ///< 48 kHz base frequency
+ N_MBG_GPIO_STUDIO_CLOCK_BASE_FREQS ///< number of defined base frequencies
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQS
+ *
+ * Used with ::MBG_GPIO_STUDIO_CLOCK_OUT_SUPP::supp_base_freqs
+ *
+ * @see ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQS
+ */
+enum MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_MASKS
+{
+ MSK_MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_32KHZ = ( 1UL << MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_32KHZ ), ///< see ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_32KHZ
+ MSK_MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_44_1KHZ = ( 1UL << MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_44_1KHZ ), ///< see ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_44_1KHZ
+ MSK_MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_48KHZ = ( 1UL << MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_48KHZ ) ///< see ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_48KHZ
+};
+
+
+
+/**
+ * @brief Initializers for an array of base frequencies of studio clock output name strings
+ *
+ * @see ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQS
+ * @see ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_MASKS
+ */
+#define MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_STRS \
+{ \
+ "32 kHz", \
+ "44.1 kHz", \
+ "48 kHz" \
+}
+
+
+
+/**
+ * @brief Enumeration of studio clock scales
+ *
+ * Used with ::MBG_GPIO_STUDIO_CLOCK_OUT_SETTINGS::scale
+ * Multiply scale with base frequency
+ *
+ * @see ::MBG_GPIO_STUDIO_CLOCK_SCALE_MASKS
+ */
+enum MBG_GPIO_STUDIO_CLOCK_SCALES
+{
+ MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_32,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_16,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_8,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_4,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_2,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_1,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_2,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_4,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_8,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_16,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_32,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_64,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_128,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_256,
+ MBG_GPIO_STUDIO_CLOCK_SCALE_512,
+ N_MBG_GPIO_STUDIO_CLOCK_SCALES ///< number of defined scales
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_STUDIO_CLOCK_SCALES
+ *
+ * Used with ::MBG_GPIO_STUDIO_CLOCK_OUT_SUPP::supp_scales[N_MBG_GPIO_STUDIO_CLOCK_BASE_FREQS]
+ *
+ * @see ::MBG_GPIO_STUDIO_CLOCK_SCALES
+ */
+enum MBG_GPIO_STUDIO_CLOCK_SCALE_MASKS
+{
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_32 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_32 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_32
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_16 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_16 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_16
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_8 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_8 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_8
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_4 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_4 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_4
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_2 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_2 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_1_DIV_2
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_1 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_1 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_1
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_2 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_2 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_2
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_4 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_4 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_4
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_8 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_8 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_8
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_16 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_16 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_16
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_32 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_32 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_32
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_64 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_64 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_64
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_128 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_128 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_128
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_256 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_256 ), ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_256
+ MSK_MBG_GPIO_STUDIO_CLOCK_SCALE_512 = ( 1U << MBG_GPIO_STUDIO_CLOCK_SCALE_512 ) ///< see ::MBG_GPIO_STUDIO_CLOCK_SCALE_512
+};
+
+
+
+/**
+ * @brief Initializers for an array of scales of studio clock output name strings
+ *
+ * @see ::MBG_GPIO_STUDIO_CLOCK_SCALES
+ * @see ::MBG_GPIO_STUDIO_CLOCK_SCALE_MASKS
+ */
+#define MBG_GPIO_STUDIO_CLOCK_SCALE_STRS \
+{ \
+ "1/32", \
+ "1/16", \
+ "1/8", \
+ "1/4", \
+ "1/2", \
+ "1", \
+ "2", \
+ "4", \
+ "8", \
+ "16", \
+ "32", \
+ "64", \
+ "128", \
+ "256", \
+ "512" \
+}
+
+
+
+/**
+ * @brief Enumeration of flags used with studio clock type GPIO outputs
+ */
+enum MBG_GPIO_STUDIO_CLOCK_FLAGS
+{
+ MBG_GPIO_STUDIO_CLOCK_OUTPUT_ENABLED, ///< if set, enables output
+ N_MBG_GPIO_STUDIO_CLOCK_FLAGS ///< number of known flags
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_STUDIO_CLOCK_FLAGS
+ *
+ * Used with ::MBG_GPIO_STUDIO_CLOCK_OUT_SETTINGS::flags
+ *
+ * @see ::MBG_GPIO_STUDIO_CLOCK_FLAGS
+ */
+enum MBG_GPIO_STUDIO_CLOCK_FLAG_MASKS
+{
+ MSK_MBG_GPIO_STUDIO_CLOCK_OUTPUT_ENABLED = ( 1UL << MBG_GPIO_STUDIO_CLOCK_OUTPUT_ENABLED ) ///< see ::MBG_GPIO_STUDIO_CLOCK_OUTPUT_ENABLED
+};
+
+
+
+/**
+ * @brief Configuration of a GPIO as studio clock output module
+ *
+ * Used as sub-structure of ::MBG_GPIO_SETTINGS.
+ *
+ * @see ::MBG_GPIO_TYPE_STUDIO_CLOCK_OUT
+ * @see ::MBG_GPIO_SETTINGS
+ */
+typedef struct
+{
+ uint32_t base_freq; ///< base frequency, see ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQS
+ uint32_t scale; ///< scale, see ::MBG_GPIO_STUDIO_CLOCK_SCALES
+ uint32_t flags; ///< flags, see ::MBG_GPIO_STUDIO_CLOCK_FLAGS
+ uint32_t reserved0; ///< reserved, currently always 0
+ uint32_t reserved1; ///< reserved, currently always 0
+
+} MBG_GPIO_STUDIO_CLOCK_OUT_SETTINGS;
+
+#define _mbg_swab_mbg_gpio_studio_clock_out_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->base_freq ); \
+ _mbg_swab32( &(_p)->scale ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab32( &(_p)->reserved0 ); \
+ _mbg_swab32( &(_p)->reserved1 ); \
+} while ( 0 )
+
+
+
+#define MAX_SUPP_BASE_FREQUENCIES 8 ///< max. supported base frequencies for studio clock outputs
+
+/**
+ * @brief Configuration of a GPIO as studio clock output module
+ *
+ * Used as sub-structure of ::MBG_GPIO_LIMITS.
+ *
+ * @see ::MBG_GPIO_TYPE_STUDIO_CLOCK_OUT
+ * @see ::MBG_GPIO_LIMITS
+ */
+typedef struct
+{
+ uint8_t supp_base_freqs; ///< supported base frequencies, see ::MBG_GPIO_STUDIO_CLOCK_BASE_FREQ_MASKS
+ uint8_t reserved0; ///< reserved, currently always 0
+ uint16_t reserved1; ///< reserved, currently always 0
+ uint16_t supp_scales[MAX_SUPP_BASE_FREQUENCIES]; ///< supported scales for each base frequency, see ::MBG_GPIO_STUDIO_CLOCK_SCALE_MASKS
+ uint32_t supp_flags; ///< supported flags, see::MBG_GPIO_STUDIO_CLOCK_FLAG_MASKS
+ uint32_t reserved2; ///< reserved, currently always 0
+
+} MBG_GPIO_STUDIO_CLOCK_OUT_SUPP;
+
+#define _mbg_swab_mbg_gpio_studio_clock_out_supp( _p ) \
+do \
+{ \
+ uint8_t idx; \
+ _mbg_swab8( &(_p)->supp_base_freqs ); \
+ _mbg_swab8( &(_p)->reserved0 ); \
+ _mbg_swab16( &(_p)->reserved1 ); \
+ for( idx = 0; idx < MAX_SUPP_BASE_FREQUENCIES; idx++ ) \
+ _mbg_swab16( &(_p)->supp_scales[idx] ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ _mbg_swab32( &(_p)->reserved2 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of types used with GPIO type digital audio outputs
+ *
+ * Used with ::MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT_SETTINGS::type, and used to
+ * define ::MBG_GPIO_DIGITAL_AUDIO_TYPE_MASKS
+ *
+ * @see ::MBG_GPIO_DIGITAL_AUDIO_TYPE_MASKS
+ * @see ::MBG_GPIO_DIGITAL_AUDIO_TYPE_STRS
+ */
+enum MBG_GPIO_DIGITAL_AUDIO_TYPES
+{
+ MBG_GPIO_DIGITAL_AUDIO_TYPE_OFF,
+ MBG_GPIO_DIGITAL_AUDIO_TYPE_DARS, ///< DARS
+ N_MBG_GPIO_DIGITAL_AUDIO_TYPES ///< number of known types
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_DIGITAL_AUDIO_TYPES
+ *
+ * Used with :: MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT_SUPP::supp_types
+ *
+ * @see ::MBG_GPIO_DIGITAL_AUDIO_TYPES
+ */
+enum MBG_GPIO_DIGITAL_AUDIO_TYPE_MASKS
+{
+ MSK_MBG_GPIO_DIGITAL_AUDIO_TYPE_OFF = ( 1UL << MBG_GPIO_DIGITAL_AUDIO_TYPE_OFF ), ///< see ::MBG_GPIO_DIGITAL_AUDIO_TYPE_OFF
+ MSK_MBG_GPIO_DIGITAL_AUDIO_TYPE_DARS = ( 1UL << MBG_GPIO_DIGITAL_AUDIO_TYPE_DARS ) ///< see ::MBG_GPIO_DIGITAL_AUDIO_TYPE_DARS
+};
+
+
+
+/**
+ * @brief Initializers for an array of video epoch strings
+ *
+ * @see ::MBG_GPIO_VIDEO_EPOCHS
+ */
+#define MBG_GPIO_DIGITAL_AUDIO_TYPE_STRS \
+{ \
+ "OFF", \
+ "DARS" \
+}
+
+
+
+/**
+ * @brief Enumeration of flags used with GPIO type digital audio outputs
+ */
+enum MBG_GPIO_DIGITAL_AUDIO_FLAGS
+{
+ MBG_GPIO_DIGITAL_AUDIO_RESERVED_FLAG, ///< reserved
+ N_MBG_GPIO_DIGITAL_AUDIO_FLAGS ///< number of known flags
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_DIGITAL_AUDIO_FLAGS
+ *
+ * Used with ::MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT_SETTINGS::flags
+ *
+ * @see ::MBG_GPIO_DIGITAL_AUDIO_FLAGS
+ */
+enum MBG_GPIO_DIGITAL_AUDIO_FLAG_MASKS
+{
+ MSK_MBG_GPIO_DIGITAL_AUDIO_RESERVED_FLAG = ( 1UL << MBG_GPIO_DIGITAL_AUDIO_RESERVED_FLAG ) ///< see ::MBG_GPIO_DIGITAL_AUDIO_RESERVED_FLAG
+};
+
+
+
+/**
+ * @brief Configuration of a GPIO digital audio output
+ *
+ * Used as sub-structure of ::MBG_GPIO_SETTINGS.
+ *
+ * @see ::MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT
+ * @see ::MBG_GPIO_SETTINGS
+ */
+typedef struct
+{
+ uint32_t type; ///< digital audio type, see ::MBG_GPIO_DIGITAL_AUDIO_TYPES
+ uint32_t flags; ///< reserved, currently always 0
+ uint32_t reserved0; ///< reserved, currently always 0
+ uint32_t reserved1; ///< reserved, currently always 0
+ uint32_t reserved2; ///< reserved, currently always 0
+
+} MBG_GPIO_DIGITAL_AUDIO_OUT_SETTINGS;
+
+#define _mbg_swab_mbg_gpio_digital_audio_out_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->type ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab32( &(_p)->reserved0 ); \
+ _mbg_swab32( &(_p)->reserved1 ); \
+ _mbg_swab32( &(_p)->reserved2 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Supported options for digital audio output
+ *
+ * Used as sub-structure of ::MBG_GPIO_LIMITS.
+ *
+ * @see ::MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT
+ * @see ::MBG_GPIO_LIMITS
+ */
+typedef struct
+{
+ uint32_t supp_types; ///< supported digital audio types, see ::MBG_GPIO_DIGITAL_AUDIO_TYPE_MASKS
+ uint32_t supp_flags; ///< reserved, currently always 0
+ uint32_t reserved0; ///< reserved, currently always 0
+ uint32_t reserved1; ///< reserved, currently always 0
+ uint32_t reserved2; ///< reserved, currently always 0
+
+} MBG_GPIO_DIGITAL_AUDIO_OUT_SUPP;
+
+#define _mbg_swab_mbg_gpio_digital_audio_out_supp( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_types ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ _mbg_swab32( &(_p)->reserved0 ); \
+ _mbg_swab32( &(_p)->reserved1 ); \
+ _mbg_swab32( &(_p)->reserved2 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of general flags used with a GPIO
+ *
+ * @see ::MBG_GPIO_FLAG_MASKS
+ */
+enum MBG_GPIO_FLAGS
+{
+ MBG_GPIO_DEPENDS_ON_ASS_IO_IDX, ///< indicates that this output depends on GPIO with ::MBG_GPIO_SETTINGS::ass_io_idx and may not be configured independently
+ N_MBG_GPIO_FLAGS ///< number of known flags
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::MBG_GPIO_FLAGS
+ *
+ * Used with ::MBG_GPIO_LIMITS::flags and ::MBG_GPIO_SETTINGS::flags
+ *
+ * @see ::MBG_GPIO_FLAGS
+ */
+enum MBG_GPIO_FLAG_MASKS
+{
+ MSK_MBG_GPIO_DEPENDS_ON_ASS_IO_IDX = ( 1UL << MBG_GPIO_DEPENDS_ON_ASS_IO_IDX ) ///< see ::MBG_GPIO_DEPENDS_ON_ASS_IO_IDX
+};
+
+
+
+/**
+ * @brief A generic structure used to hold a GPIO port's settings
+ */
+typedef struct
+{
+ uint32_t type; ///< GPIO type, see ::MBG_GPIO_TYPES
+
+ uint16_t reserved_1; ///< reserved, currently always 0
+ uint8_t reserved_2; ///< reserved, currently always 0
+ uint8_t ass_io_idx; ///< associated GPIO index, only valid if ::MSK_MBG_GPIO_DEPENDS_ON_ASS_IO_IDX is set in flags field
+
+ uint32_t flags; ///< flags, see ::MBG_GPIO_FLAG_MASKS
+
+ /// settings depending on the GPIO type, see ::MBG_GPIO_TYPES
+ union
{
- MBG_GPIO_FREQ_IN_SETTINGS freq_in; /**< if type is MBG_GPIO_TYPE_FREQ_IN */
- MBG_GPIO_FREQ_OUT_SETTINGS freq_out; /**< if type is MBG_GPIO_TYPE_FREQ_OUT */
- MBG_GPIO_FIXED_FREQ_OUT_SETTINGS ff_out; /**< if type is MBG_GPIO_TYPE_FIXED_FREQ_OUT */
- MBG_GPIO_BITS_IN_SETTINGS bits_in; /**< if type is MBG_GPIO_TYPE_BITS_IN */
- MBG_GPIO_BITS_OUT_SETTINGS bits_out; /**< if type is MBG_GPIO_TYPE_BITS_OUT */
+ MBG_GPIO_FREQ_IN_SETTINGS freq_in; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_FREQ_IN
+ MBG_GPIO_FREQ_OUT_SETTINGS freq_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_FREQ_OUT
+ MBG_GPIO_FIXED_FREQ_OUT_SETTINGS ff_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_FIXED_FREQ_OUT
+ MBG_GPIO_BITS_IN_SETTINGS bits_in; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_BITS_IN
+ MBG_GPIO_BITS_OUT_SETTINGS bits_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_BITS_OUT
+ MBG_GPIO_VIDEO_OUT_SETTINGS video_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_VIDEO_OUT
+ MBG_GPIO_VIDEO_SYNC_OUT_SETTINGS video_sync_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_VIDEO_SYNC_OUT
+ MBG_GPIO_STUDIO_CLOCK_OUT_SETTINGS studio_clk_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_STUDIO_CLOCK_OUT
+ MBG_GPIO_DIGITAL_AUDIO_OUT_SETTINGS digital_audio_out; ///< if ::MBG_GPIO_SETTINGS::type is ::;MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT
} u;
} MBG_GPIO_SETTINGS;
+#define _mbg_swab_mbg_gpio_settings( _p, _recv ) \
+do \
+{ \
+ uint32_t t = (_p)->type; \
+ if ( (_recv) ) \
+ _mbg_swab32( &t ); \
+ _mbg_swab32( &(_p)->type ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ _mbg_swab8( &(_p)->reserved_2 ); \
+ _mbg_swab8( &(_p)->ass_io_idx ); \
+ _mbg_swab32( &(_p)->flags ); \
+ switch( t ) \
+ { \
+ case MBG_GPIO_TYPE_FREQ_IN : _mbg_swab_mbg_gpio_freq_in_settings( &(_p)->u.freq_in ); break; \
+ case MBG_GPIO_TYPE_FREQ_OUT : _mbg_swab_mbg_gpio_freq_out_settings( &(_p)->u.freq_out ); break; \
+ case MBG_GPIO_TYPE_FIXED_FREQ_OUT : _mbg_swab_mbg_gpio_fixed_freq_out_settings( &(_p)->u.ff_out ); break; \
+ case MBG_GPIO_TYPE_BITS_IN : _mbg_swab_mbg_gpio_bits_in_settings( &(_p)->u.bits_in, (_recv) ); break; \
+ case MBG_GPIO_TYPE_BITS_OUT : _mbg_swab_mbg_gpio_bits_out_settings( &(_p)->u.bits_out ); break; \
+ case MBG_GPIO_TYPE_VIDEO_OUT : _mbg_swab_mbg_gpio_video_out_settings( &(_p)->u.video_out ); break; \
+ case MBG_GPIO_TYPE_VIDEO_SYNC_OUT : _mbg_swab_mbg_gpio_video_sync_out_settings( &(_p)->u.video_sync_out ); break; \
+ case MBG_GPIO_TYPE_STUDIO_CLOCK_OUT : _mbg_swab_mbg_gpio_studio_clock_out_settings( &(_p)->u.studio_clk_out ); break; \
+ case MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT : _mbg_swab_mbg_gpio_digital_audio_out_settings( &(_p)->u.digital_audio_out ); break; \
+ default : break; \
+ } \
+} while ( 0 )
+
+
+
+/**
+ * @brief A GPIO port's current settings, plus port index
+ */
+typedef struct
+{
+ uint32_t idx; ///< port index, 0..::MBG_GPIO_CFG_LIMITS::num_io-1
+ MBG_GPIO_SETTINGS settings; ///< current settings
+
+} MBG_GPIO_SETTINGS_IDX;
+
+#define _mbg_swab_mbg_gpio_settings_idx( _p, _recv ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_mbg_gpio_settings( &(_p)->settings, (_recv ) ); \
+} while ( 0 )
+
/**
- * @brief A generic structure used to describe a GPIO ports limiting values
+ * @brief A generic structure used to specify a GPIO port's limits
*/
typedef struct
{
- uint32_t type; /**< GPIO type, see ::MBG_GPIO_TYPES */
- uint32_t reserved; /**< currently always 0 */
- uint32_t supp_flags; /**< supported flags */
+ uint32_t type; ///< GPIO type, see ::MBG_GPIO_TYPES
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t supp_flags; ///< supported flags, see ::MBG_GPIO_FLAG_MASKS
- union /**< limits depending on the GPIO type, see ::MBG_GPIO_TYPES */
+ /// limits depending on the GPIO type, see ::MBG_GPIO_TYPES
+ union
{
- MBG_GPIO_FREQ_IN_SUPP freq_in; /**< if type is MBG_GPIO_TYPE_FREQ_IN */
- MBG_GPIO_FREQ_OUT_SUPP freq_out; /**< if type is MBG_GPIO_TYPE_FREQ_OUT */
- MBG_GPIO_FIXED_FREQ_OUT_SUPP ff_out; /**< if type is MBG_GPIO_TYPE_FIXED_FREQ_OUT */
- MBG_GPIO_BITS_IN_SUPP bits_in; /**< if type is MBG_GPIO_TYPE_BITS_IN */
- MBG_GPIO_BITS_OUT_SUPP bits_out; /**< if type is MBG_GPIO_TYPE_BITS_OUT */
+ MBG_GPIO_FREQ_IN_SUPP freq_in; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_FREQ_IN
+ MBG_GPIO_FREQ_OUT_SUPP freq_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_FREQ_OUT
+ MBG_GPIO_FIXED_FREQ_OUT_SUPP ff_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_FIXED_FREQ_OUT
+ MBG_GPIO_BITS_IN_SUPP bits_in; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_BITS_IN
+ MBG_GPIO_BITS_OUT_SUPP bits_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_BITS_OUT
+ MBG_GPIO_VIDEO_OUT_SUPP video_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_VIDEO_OUT
+ MBG_GPIO_VIDEO_SYNC_OUT_SUPP video_sync_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_VIDEO_SYNC_OUT
+ MBG_GPIO_STUDIO_CLOCK_OUT_SUPP studio_clk_out; ///< if ::MBG_GPIO_SETTINGS::type is ::MBG_GPIO_TYPE_STUDIO_CLOCK_OUT
+ MBG_GPIO_DIGITAL_AUDIO_OUT_SUPP digital_audio_out; ///< if ::MBG_GPIO_SETTINGS::type is ::;MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT
} u;
} MBG_GPIO_LIMITS;
+#define _mbg_swab_mbg_gpio_limits( _p, _recv ) \
+do \
+{ \
+ uint32_t t = (_p)->type; \
+ if ( (_recv) ) \
+ _mbg_swab32( &t ); \
+ _mbg_swab32( &(_p)->type ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ switch( t ) \
+ { \
+ case MBG_GPIO_TYPE_FREQ_IN : _mbg_swab_mbg_gpio_freq_in_supp( &(_p)->u.freq_in ); break; \
+ case MBG_GPIO_TYPE_FREQ_OUT : _mbg_swab_mbg_gpio_freq_out_supp( &(_p)->u.freq_out ); break; \
+ case MBG_GPIO_TYPE_FIXED_FREQ_OUT : _mbg_swab_mbg_gpio_fixed_freq_out_supp( &(_p)->u.ff_out ); break; \
+ case MBG_GPIO_TYPE_BITS_IN : _mbg_swab_mbg_gpio_bits_in_supp( &(_p)->u.bits_in ); break; \
+ case MBG_GPIO_TYPE_BITS_OUT : _mbg_swab_mbg_gpio_bits_out_supp( &(_p)->u.bits_out ); break; \
+ case MBG_GPIO_TYPE_VIDEO_OUT : _mbg_swab_mbg_gpio_video_out_supp( &(_p)->u.video_out ); break; \
+ case MBG_GPIO_TYPE_VIDEO_SYNC_OUT : _mbg_swab_mbg_gpio_video_sync_out_supp( &(_p)->u.video_sync_out ); break; \
+ case MBG_GPIO_TYPE_STUDIO_CLOCK_OUT : _mbg_swab_mbg_gpio_studio_clock_out_supp( &(_p)->u.studio_clk_out ); break; \
+ case MBG_GPIO_TYPE_DIGITAL_AUDIO_OUT : _mbg_swab_mbg_gpio_digital_audio_out_supp( &(_p)->u.digital_audio_out ); break; \
+ default : break; \
+ } \
+} while ( 0 )
+
+
+
+/**
+ * @brief A GPIO port's current settings and limits
+ */
+typedef struct
+{
+ MBG_GPIO_SETTINGS settings; ///< current settings
+ MBG_GPIO_LIMITS limits; ///< limits of this GPIO port
+
+} MBG_GPIO_INFO;
+
+
+#define _mbg_swab_mbg_gpio_info( _p, _recv ) \
+do \
+{ \
+ _mbg_swab_mbg_gpio_settings( &(_p)->settings, (_recv) ); \
+ _mbg_swab_mbg_gpio_limits( &(_p)->limits, (_recv) ); \
+} while ( 0 )
/**
- * @brief A structure used to configure a specific GPIO port
+ * @brief A GPIO port's current settings and limits, plus port index
*/
typedef struct
{
- uint32_t idx; /**< port number, 0..(MBG_GPIO_CFG_LIMITS::num_io - 1) */
- MBG_GPIO_SETTINGS settings; /**< configuration settings */
+ uint32_t idx; ///< port index, 0..::MBG_GPIO_CFG_LIMITS::num_io-1
+ MBG_GPIO_INFO info; ///< limits and current settings of this GPIO port
-} MBG_GPIO_SETTINGS_IDX;
+} MBG_GPIO_INFO_IDX;
+
+#define _mbg_swab_mbg_gpio_info_idx( _p, _recv ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_mbg_gpio_info( &(_p)->info, (_recv) ); \
+} while ( 0 )
/**
- * @brief A structure used query the current GPIO port settings and capabilities
+ * @brief Status information on a single GPIO port
*/
typedef struct
{
- MBG_GPIO_SETTINGS settings; /**< current configuration */
- MBG_GPIO_LIMITS limits; /**< supp. and max. values */
+ uint8_t port_state; ///< see ::MBG_GPIO_PORT_STATES
+ uint8_t reserved_0; ///< reserved, currently unused and always 0
+ uint16_t reserved_1; ///< reserved, currently unused and always 0
+ uint32_t reserved_2; ///< reserved, currently unused and always 0
+ uint32_t reserved_3; ///< reserved, currently unused and always 0
-} MBG_GPIO_INFO;
+} MBG_GPIO_STATUS;
+
+#define _mbg_swab_mbg_gpio_status( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->port_state ); \
+ _mbg_swab8( &(_p)->reserved_0 ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+} while ( 0 )
/**
- * @brief A structure used to query configuration and capabilities of a specific GPIO port
+ * @brief Status information on a specific GPIO port
*/
typedef struct
{
- uint32_t idx; /**< port number, 0..(MBG_GPIO_CFG_LIMITS::num_io - 1) */
- MBG_GPIO_INFO info; /**< current settings and capabilities of this GPIO port */
+ uint16_t idx; ///< port index, 0..::MBG_GPIO_CFG_LIMITS::num_io-1
+ MBG_GPIO_STATUS status; ///< status information
-} MBG_GPIO_INFO_IDX;
+} MBG_GPIO_STATUS_IDX;
+#define _mbg_swab_mbg_gpio_status_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_mbg_gpio_status( &(_p)->status ); \
+} while ( 0 )
-/** @} group_gpio */
+
+
+/**
+ * @brief GPIO port states
+ *
+ * Used with ::MBG_GPIO_STATUS::port_state
+ *
+ * @see ::DEFAULT_GPIO_PORT_STATE_NAMES
+ */
+enum MBG_GPIO_PORT_STATES
+{
+ MBG_GPIO_PORT_UNUSED, ///< configured as unused input
+ MBG_GPIO_PORT_OUTPUT_ENBD, ///< configured output signal enabled
+ MBG_GPIO_INPUT_SIG_AVAIL, ///< input signal is available
+ N_MBG_GPIO_PORT_STATES ///< number of known port states
+};
/**
- * @defgroup group_havequick GPIO port configuration stuff
+ * @brief String initializers for GPIO port state names
+ *
+ * @see ::MBG_GPIO_PORT_STATES
+ */
+#define DEFAULT_GPIO_PORT_STATE_NAMES \
+{ \
+ "unused", \
+ "output enabled", \
+ "input signal available" \
+}
+
+
+/** @} defgroup group_gpio */
+
+
+
+/**
+ * @defgroup group_havequick HaveQuick definitions
*
* @note This is only supported if the ::GPS_HAS_HAVEQUICK bit is set
- * in the RECEIVER_INFO::features mask.
+ * in the ::RECEIVER_INFO::features mask.
*
* @{ */
@@ -4706,8 +9729,8 @@ typedef struct
/**
* @brief Enumeration of HaveQuick formats
*
- * @see HAVEQUICK_SETTINGS::format
- * @see HAVEQUICK_FORMAT_MASKS
+ * @see ::HAVEQUICK_SETTINGS::format
+ * @see ::HAVEQUICK_FORMAT_MASKS
*/
enum HAVEQUICK_FORMATS
{
@@ -4722,10 +9745,10 @@ enum HAVEQUICK_FORMATS
/**
- * @brief Bit masks associated to enumerated HaveQuick formats
+ * @brief Bit masks associated with the enumerated HaveQuick formats
*
- * @see HAVEQUICK_INFO::supp_formats
- * @see HAVEQUICK_FORMATS
+ * @see ::HAVEQUICK_INFO::supp_formats
+ * @see ::HAVEQUICK_FORMATS
*/
enum HAVEQUICK_FORMAT_MASKS
{
@@ -4756,7 +9779,7 @@ enum HAVEQUICK_FORMAT_MASKS
/*
* The definition below can be used to initialize
- * an array of N_HQ_FMT name strings.
+ * an array of ::N_HQ_FMT name strings.
*/
#define DEFAULT_HQ_FMT_NAMES \
{ \
@@ -4789,17 +9812,19 @@ typedef struct
uint16_t flags; ///< see ::HAVEQUICK_FLAG_MASKS
int32_t offset; ///< Tx: unused, Rx: offset of incoming time in [s]
uint32_t reserved_0; ///< reserved, currently always 0
- uint32_t reserved_1; ///< reserved, currently always 0
+ uint32_t reserved_1; ///< reserved, currently always 0
+
} HAVEQUICK_SETTINGS;
#define _mbg_swab_havequick_settings( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->format ); \
_mbg_swab16( &(_p)->flags ); \
_mbg_swab32( &(_p)->offset ); \
_mbg_swab32( &(_p)->reserved_0 ); \
_mbg_swab32( &(_p)->reserved_1 ); \
-}
+} while ( 0 )
/**
* @brief Current settings and capabilities of a HaveQuick input or output
@@ -4810,21 +9835,23 @@ typedef struct
uint32_t supp_formats; ///< see ::HAVEQUICK_FORMAT_MASKS
uint16_t supp_flags; ///< mask of flags supported in settings, see ::HAVEQUICK_FLAG_MASKS
uint16_t reserved; ///< reserved, currently always 0
+
} HAVEQUICK_INFO;
#define _mbg_swab_havequick_info( _p ) \
+do \
{ \
_mbg_swab_havequick_settings( &(_p)->settings ); \
_mbg_swab32( &(_p)->supp_formats ); \
_mbg_swab16( &(_p)->supp_flags ); \
_mbg_swab16( &(_p)->reserved ); \
-}
+} while ( 0 )
/**
* @brief Known HaveQuick control flags
*
- * @see HAVEQUICK_FLAG_MASKS
+ * @see ::HAVEQUICK_FLAG_MASKS
*/
enum HAVEQUICK_FLAG_BITS
{
@@ -4836,11 +9863,11 @@ enum HAVEQUICK_FLAG_BITS
/**
- * @brief Bit masks associated to HaveQuick control flags
+ * @brief Bit masks associated with HaveQuick control flags
*
- * @see HQ_SETTINGS::flags
- * @see HQ_INFO::flags
- * @see HAVEQUICK_FLAG_BITS
+ * @see ::HAVEQUICK_SETTINGS::flags
+ * @see ::HAVEQUICK_INFO::supp_flags
+ * @see ::HAVEQUICK_FLAG_BITS
*/
enum HAVEQUICK_FLAG_MASKS
{
@@ -4849,59 +9876,64 @@ enum HAVEQUICK_FLAG_MASKS
HQ_MSK_USE_EXT_PPS = ( 1UL << HQ_FLAG_USE_EXT_PPS ) ///< see ::HQ_FLAG_USE_EXT_PPS
};
-
-/** @} group_havequick */
+/** @} defgroup group_havequick */
/**
* @defgroup group_evt_log Event logging support
*
- * @note This is only available if ::GPS_HAS_EVT_LOG is set in RECEIVER_INFO::features.
+ * @note This is only available if ::GPS_HAS_EVT_LOG is set in ::RECEIVER_INFO::features.
*
* @{ */
-/** @brief Number of event log entries that can be stored and yet have been saved */
+/**
+ * @brief Number of event log entries that can be stored and yet have been saved
+ */
typedef struct
{
- uint32_t used; /**< current number of saved log entries */
- uint32_t max; /**< max number of log entries which can be saved */
+ uint32_t used; ///< current number of saved log entries
+ uint32_t max; ///< max number of log entries which can be saved
+
} MBG_NUM_EVT_LOG_ENTRIES;
#define _mbg_swab_mbg_num_evt_log_entries( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->used ); \
_mbg_swab32( &(_p)->max ); \
-}
+} while ( 0 )
typedef uint16_t MBG_EVT_CODE;
-#define _mbg_swab_evt_code( _p ) _mbg_swab16( _p );
+#define _mbg_swab_evt_code( _p ) _mbg_swab16( _p )
typedef uint16_t MBG_EVT_INFO;
-#define _mbg_swab_evt_info( _p ) _mbg_swab16( _p );
+#define _mbg_swab_evt_info( _p ) _mbg_swab16( _p )
/**
* @brief An event log entry
*/
- typedef struct
- {
- uint32_t time; /**< like time_t, seconds since 1970 */
- MBG_EVT_CODE code; /**< event ID or'ed with severity level */
- MBG_EVT_INFO info; /**< optional event info, depending on event ID */
- } MBG_EVT_LOG_ENTRY;
+typedef struct
+{
+ uint32_t time; ///< like time_t, seconds since 1970
+ MBG_EVT_CODE code; ///< event ID or'ed with severity level, see @ref MBG_EVENT_CODES
+ MBG_EVT_INFO info; ///< optional event info, depending on event ID
+
+} MBG_EVT_LOG_ENTRY;
#define _mbg_swab_mbg_evt_log_entry( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->time ); \
_mbg_swab_evt_code( &(_p)->code ); \
_mbg_swab_evt_info( &(_p)->info ); \
-}
+} while ( 0 )
-// MBG_EVT_LOG_ENTRY::code is a combination of some bits used for the ID,
+// ::MBG_EVT_LOG_ENTRY::code is a combination of some bits used for the ID,
// plus some bits used for the severity/level. The sum of bits must not
-// exceed (8 * sizeof MBG_EVT_LOG_ENTRY::code):
+// exceed (8 * sizeof ::MBG_EVT_LOG_ENTRY::code):
#define MBG_EVT_ID_BITS 13
#define MBG_EVT_LVL_BITS 3
@@ -4926,19 +9958,23 @@ typedef uint16_t MBG_EVT_INFO;
/**
* @brief Enumeration of event IDs
+ *
+ * @see @ref MBG_EVENT_CODES
+ * @see @ref MBG_EVT_ID_BITS
+ * @see @ref MBG_EVT_LVL_BITS
*/
enum MBG_EVT_IDS
{
- MBG_EVT_ID_NONE, /**< no event (empty entry) */
- MBG_EVT_ID_POW_UP_RES, /**< power up reset */
- MBG_EVT_ID_WDOG_RES, /**< watchdog reset */
- MBG_EVT_ID_COLD_BOOT, /**< entering cold boot mode */
- MBG_EVT_ID_WARM_BOOT, /**< entering warm boot mode */
- MBG_EVT_ID_NORMAL_OP, /**< entering normal operation */
- MBG_EVT_ID_ANT_DISCONN, /**< antenna disconnect detected */
- MBG_EVT_ID_ANT_SHORT, /**< antenna short circuit detected */
- MBG_EVT_ID_ANT_OK, /**< antenna OK after failure */
- MBG_EVT_ID_LOW_SATS, /**< no satellites can be received though antenna not failing */
+ MBG_EVT_ID_NONE, ///< no event (empty entry)
+ MBG_EVT_ID_POW_UP_RES, ///< power up reset
+ MBG_EVT_ID_WDOG_RES, ///< watchdog reset
+ MBG_EVT_ID_COLD_BOOT, ///< entering cold boot mode
+ MBG_EVT_ID_WARM_BOOT, ///< entering warm boot mode
+ MBG_EVT_ID_NORMAL_OP, ///< entering normal operation
+ MBG_EVT_ID_ANT_DISCONN, ///< antenna disconnect detected
+ MBG_EVT_ID_ANT_SHORT, ///< antenna short circuit detected
+ MBG_EVT_ID_ANT_OK, ///< antenna OK after failure
+ MBG_EVT_ID_LOW_SATS, ///< no satellites can be received though antenna not failing
N_MBG_EVT_ID
};
@@ -4973,6 +10009,10 @@ enum MBG_EVT_IDS
/**
* @brief Enumeration of event severity levels
+ *
+ * @see @ref MBG_EVENT_CODES
+ * @see @ref MBG_EVT_ID_BITS
+ * @see @ref MBG_EVT_LVL_BITS
*/
enum MBG_EVT_LVLS
{
@@ -5005,7 +10045,13 @@ enum MBG_EVT_LVLS
}
-/** @brief Predefined event codes with associated severity levels */
+/**
+ * @brief Predefined event codes with associated severity levels
+ *
+ * @see ::MBG_EVT_IDS
+ * @see ::MBG_EVT_LVLS
+ *
+ * @anchor MBG_EVENT_CODES @{ */
#define MBG_EVT_NONE _mbg_mk_evt_code( MBG_EVT_ID_NONE, MBG_EVT_LVL_NONE )
#define MBG_EVT_POW_UP_RES _mbg_mk_evt_code( MBG_EVT_ID_POW_UP_RES, MBG_EVT_LVL_WARN )
@@ -5018,14 +10064,16 @@ enum MBG_EVT_LVLS
#define MBG_EVT_ANT_OK _mbg_mk_evt_code( MBG_EVT_ID_ANT_OK, MBG_EVT_LVL_INFO )
#define MBG_EVT_LOW_SATS _mbg_mk_evt_code( MBG_EVT_ID_LOW_SATS, MBG_EVT_LVL_WARN )
-/** @} group_evt_log */
+/** @} anchor MBG_EVENT_CODES */
+
+/** @} defgroup group_evt_log */
/**
* @defgroup group_ims IMS support
*
- * @note This is only available if ::GPS_HAS_IMS is set in RECEIVER_INFO::features.
+ * @note This is only supported if ::GPS_HAS_IMS is set in ::RECEIVER_INFO::features.
*
* @{ */
@@ -5034,20 +10082,45 @@ enum MBG_EVT_LVLS
*/
typedef struct
{
- uint8_t chassis_id; /**< chassis ID, 0 if installed on the backplane */
- uint8_t slot_id; /**< slot number on the chassis */
- uint16_t num_sensors; /**< number of sensors provided by the device */
- uint32_t reserved; /**< currently unused, always 0 */
- uint32_t flags; /**< currently unused, always 0 */
+ uint8_t chassis_id; ///< chassis ID, 0 if installed on the backplane
+ uint8_t slot_id; ///< slot number on the chassis
+ uint16_t num_sensors; ///< number of sensors provided by the device
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< see ::MBG_IMS_STATE_FLAG_MASKS
} MBG_IMS_STATE;
#define _mbg_swab_mbg_ims_state( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->num_sensors ); \
_mbg_swab32( &(_p)->reserved ); \
_mbg_swab32( &(_p)->flags ); \
-}
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of bits used to define ::MBG_IMS_STATE_FLAG_MASKS
+ *
+ * @see ::MBG_IMS_STATE_FLAG_MASKS
+ */
+enum MBG_IMS_STATE_FLAG_BITS
+{
+ MBG_IMS_STATE_FLAG_BIT_HAS_FDM, ///< device supports FDM API
+ N_MBG_IMS_STATE_FLAG_BITS
+};
+
+
+/**
+ * @brief Bit masks used with ::MBG_IMS_STATE::flags
+ *
+ * @see ::MBG_IMS_STATE_FLAG_BITS
+ */
+enum MBG_IMS_STATE_FLAG_MASKS
+{
+ MBG_IMS_STATE_FLAG_MSK_HAS_FDM = ( 1UL << MBG_IMS_STATE_FLAG_BIT_HAS_FDM ) ///< see ::MBG_IMS_STATE_FLAG_BIT_HAS_FDM
+};
@@ -5056,16 +10129,17 @@ typedef struct
*/
typedef struct
{
- uint16_t type; /**< sensor type, see ::MBG_IMS_SENSORS */
- uint16_t idx; /**< index of the sensor of this type */
- int32_t val; /**< sensor value, in units according to the type */
- int16_t exp; /**< 10s exponent of the sensor value */
- uint16_t reserved; /**< currently unused, always 0 */
- uint32_t flags; /**< currently unused, always 0 */
+ uint16_t type; ///< sensor type, see ::MBG_IMS_SENSORS
+ uint16_t idx; ///< index of the sensor of this type
+ int32_t val; ///< sensor value, in units according to the type
+ int16_t exp; ///< 10s exponent of the sensor value
+ uint16_t reserved; ///< currently unused, always 0
+ uint32_t flags; ///< currently unused, always 0
} MBG_IMS_SENSOR_STATE;
#define _mbg_swab_mbg_ims_sensor_state( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->type ); \
_mbg_swab16( &(_p)->idx ); \
@@ -5073,7 +10147,7 @@ typedef struct
_mbg_swab16( &(_p)->exp ); \
_mbg_swab16( &(_p)->reserved ); \
_mbg_swab32( &(_p)->flags ); \
-}
+} while ( 0 )
/**
@@ -5081,43 +10155,470 @@ typedef struct
*/
typedef struct
{
- uint32_t idx; /**< sensor index, 0..MBG_IMS_STATE::num_sensors - 1 */
- MBG_IMS_SENSOR_STATE state; /**< sensor state */
+ uint32_t idx; ///< sensor index, 0..::MBG_IMS_STATE::num_sensors-1
+ MBG_IMS_SENSOR_STATE state; ///< sensor state
} MBG_IMS_SENSOR_STATE_IDX;
#define _mbg_swab_mbg_ims_sensor_state_idx( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->idx ); \
_mbg_swab_mbg_ims_sensor_state( &(_p)->state ); \
-}
+} while ( 0 )
/**
* @brief IMS sensor types
+ *
+ * Used with ::MBG_IMS_SENSOR_STATE::type
*/
enum MBG_IMS_SENSORS
{
- MBG_IMS_SENSOR_TEMP_C, /**< temperature in degrees C */
- MBG_IMS_SENSOR_VOLTAGE, /**< voltage in val/exp, output state in flags */
- MBG_IMS_SENSOR_PLL, /**< control voltage in val/exp, lock state in flags */
- N_MBG_IMS_SENSORS /**< number of supported sensor types */
+ MBG_IMS_SENSOR_TEMP_C, ///< temperature in degrees Celsius
+ MBG_IMS_SENSOR_VOLTAGE, ///< voltage in val/exp, output state in flags
+ MBG_IMS_SENSOR_PLL, ///< control voltage in val/exp, lock state in flags
+ N_MBG_IMS_SENSORS ///< number of supported sensor types
+};
+
+
+
+/**
+ * @brief IMS sensor state flags for voltage
+ *
+ * Used with ::MBG_IMS_SENSOR_STATE::flags in case ::MBG_IMS_SENSOR_STATE::type
+ * is ::MBG_IMS_SENSOR_VOLTAGE.
+ */
+enum MBG_IMS_SENSOR_STATE_FLAG_MASK_VOLTAGE
+{
+ MBG_IMS_SENSOR_VOLTAGE_OUT_ENB = 0x01, ///< output is enabled
+ MBG_IMS_SENSOR_VOLTAGE_OUT_OVR = 0x02 ///< output overload
+};
+
+
+/**
+ * @brief IMS sensor state flags for PLL
+ *
+ * Used with ::MBG_IMS_SENSOR_STATE::flags in case ::MBG_IMS_SENSOR_STATE::type
+ * is ::MBG_IMS_SENSOR_PLL.
+ */
+enum MBG_IMS_SENSOR_STATE_FLAG_MASK_PLL
+{
+ MBG_IMS_SENSOR_PLL_LOCKED = 0x01 ///< PLL is locked
+};
+
+
+
+/**
+ * @brief DAC limit specs
+ */
+typedef struct
+{
+ int32_t dac_val_min; ///< min. possible DAC Value, positive or negative
+ int32_t dac_val_max; ///< max. possible DAC Value, positive or negative
+
+ int32_t u_min; ///< min. possible real voltage range [mV], positive or negative, depending on ::MBG_DAC_SPECS::dac_val_min
+ int32_t u_max; ///< max. possible real voltage range [mV], positive or negative, depending on ::MBG_DAC_SPECS::dac_val_max
+
+ uint32_t reserved_0; ///< reserved, currently always 0
+ uint32_t reserved_1; ///< reserved, currently always 0
+
+} MBG_DAC_SPECS;
+
+#define _mbg_swab_mbg_dac_specs( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->dac_val_min ); \
+ _mbg_swab32( &(_p)->dac_val_max ); \
+ _mbg_swab32( &(_p)->u_min ); \
+ _mbg_swab32( &(_p)->u_max ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Output state of FDM device.
+ *
+ * @note This is only supported if ::MBG_IMS_STATE_FLAG_MSK_HAS_FDM is set in ::MBG_IMS_STATE::flags
+ */
+typedef struct
+{
+ int32_t dac_val; ///< current DAC value, positive or negative
+ uint32_t mode; ///< current output mode, see ::MBG_IMS_FDM_OUTPUT_MODES
+
+ MBG_DAC_SPECS dac_specs; ///< DAC specific limits
+
+ uint32_t reserved_0; ///< reserved, currently always 0
+ uint32_t reserved_1; ///< reserved, currently always 0
+
+} MBG_IMS_FDM_OUTPUT_STATE;
+
+#define _mbg_swab_mbg_ims_fdm_output_state( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->dac_val ); \
+ _mbg_swab32( &(_p)->mode ); \
+ _mbg_swab_mbg_dac_specs( &(_p)->dac_specs ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Output state of FDM device plus index.
+ */
+typedef struct
+{
+ uint32_t idx;
+ MBG_IMS_FDM_OUTPUT_STATE state;
+
+} MBG_IMS_FDM_OUTPUT_STATE_IDX;
+
+#define _mbg_swab_mbg_ims_fdm_output_state_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_mbg_ims_fdm_output_state( &(_p)->state ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Output settings of FDM device
+ *
+ * @note This is only supported if ::MBG_IMS_STATE_FLAG_MSK_HAS_FDM is set in ::MBG_IMS_STATE::flags
+ */
+typedef struct
+{
+ uint32_t mode; ///< mode, see ::MBG_IMS_FDM_OUTPUT_MODES
+ uint32_t reserved; ///< reserved, currently always 0
+
+} MBG_IMS_FDM_OUTPUT_SETTINGS;
+
+#define _mbg_swab_mbg_ims_fdm_output_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->mode ); \
+ _mbg_swab32( &(_p)->reserved ); \
+} while ( 0 )
+
+
+/**
+ * @brief Output settings for FDM devices plus index.
+ */
+typedef struct
+{
+ uint32_t idx;
+ MBG_IMS_FDM_OUTPUT_SETTINGS settings;
+
+} MBG_IMS_FDM_OUTPUT_SETTINGS_IDX;
+
+#define _mbg_swab_mbg_ims_fdm_output_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_mbg_ims_fdm_output_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Specific output settings and limits.
+ */
+typedef struct
+{
+ MBG_IMS_FDM_OUTPUT_SETTINGS settings; ///< current settings
+ uint32_t supp_modes; ///< supported modes, see ::MBG_IMS_FDM_OUTPUT_MODE_MASKS
+ MBG_DAC_SPECS dac_specs; ///< DAC specific limits
+
+} MBG_IMS_FDM_OUTPUT_INFO;
+
+#define _mbg_swab_mbg_ims_fdm_output_info( _p ) \
+do \
+{ \
+ _mbg_swab_mbg_ims_fdm_output_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->supp_modes ); \
+ _mbg_swab_mbg_dac_specs( &(_p)->dac_specs ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Specific output settings and limits, plus index.
+ */
+typedef struct
+{
+ uint32_t idx;
+ MBG_IMS_FDM_OUTPUT_INFO info;
+
+} MBG_IMS_FDM_OUTPUT_INFO_IDX;
+
+#define _mbg_swab_mbg_ims_fdm_output_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_mbg_ims_fdm_output_info( &(_p)->info ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of known output modes
+ *
+ * Used with ::MBG_IMS_FDM_OUTPUT_STATE::mode
+ *
+ * @see ::MBG_IMS_FDM_OUTPUT_MODE_MASKS
+ */
+enum MBG_IMS_FDM_OUTPUT_MODES
+{
+ MBG_IMS_FDM_OUTPUT_MODE_FD, ///< Analog output reflects frequency deviation
+ MBG_IMS_FDM_OUTPUT_MODE_TD, ///< Analog output reflects time deviation
+ N_MBG_IMS_FDM_OUTPUT_MODES ///< Number of known output modes
+};
+
+
+
+/**
+ * @brief Bit masks used with ::MBG_IMS_FDM_OUTPUT_STATE::mode
+ *
+ * @see ::MBG_IMS_FDM_OUTPUT_MODES
+ */
+enum MBG_IMS_FDM_OUTPUT_MODE_MASKS
+{
+ MBG_IMS_FDM_OUTPUT_MODE_MSK_FD = ( 1UL << MBG_IMS_FDM_OUTPUT_MODE_FD ), ///< see ::MBG_IMS_FDM_OUTPUT_MODE_FD
+ MBG_IMS_FDM_OUTPUT_MODE_MSK_TD = ( 1UL << MBG_IMS_FDM_OUTPUT_MODE_TD ) ///< see ::MBG_IMS_FDM_OUTPUT_MODE_TD
};
-// Definitions used with MBG_IMS_SENSOR_STATE::flags:
+/**
+ * @brief A generic structure used to specify FDM limits
+ */
+typedef struct
+{
+ uint8_t n_outputs; ///< number of outputs per module
+ uint8_t reserved_0; ///< reserved, currently always 0
+ uint16_t reserved_1; ///< reserved, currently always 0
+
+ uint32_t fd_neg_limit; ///< min. frequency deviation limit, 1/::MBG_IMS_FDM_LIMITS::fd_scale Hz units
+ uint32_t fd_pos_limit; ///< max. frequency deviation limit, 1/::MBG_IMS_FDM_LIMITS::fd_scale Hz units
+ uint32_t fd_scale; ///< scale for ::MBG_IMS_FDM_LIMITS::fd_neg_limit and ::MBG_IMS_FDM_LIMITS::fd_pos_limit
+
+ uint32_t td_neg_limit; ///< min. time deviation limit, 1/::MBG_IMS_FDM_LIMITS::td_scale s units
+ uint32_t td_pos_limit; ///< max. time deviation limit, 1/::MBG_IMS_FDM_LIMITS::td_scale s units
+ uint32_t td_scale; ///< scale for ::MBG_IMS_FDM_LIMITS::td_neg_limit and ::MBG_IMS_FDM_LIMITS::td_pos_limit
+
+ uint32_t reserved_2; ///< reserved, currently always 0
+
+} MBG_IMS_FDM_LIMITS;
+
+#define _mbg_swab_mbg_ims_fdm_limits( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->n_outputs ); \
+ _mbg_swab8( &(_p)->reserved_0 ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ \
+ _mbg_swab32( &(_p)->fd_neg_limit ); \
+ _mbg_swab32( &(_p)->fd_pos_limit ); \
+ _mbg_swab32( &(_p)->fd_scale ); \
+ \
+ _mbg_swab32( &(_p)->td_neg_limit ); \
+ _mbg_swab32( &(_p)->td_pos_limit ); \
+ _mbg_swab32( &(_p)->td_scale ); \
+ \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+} while ( 0 )
+
+
-// if MBG_IMS_SENSOR_STATE::type == MBG_IMS_SENSOR_VOLTAGE:
-#define MBG_IMS_SENSOR_VOLTAGE_OUT_ENB 0x01 // output is enabled
-#define MBG_IMS_SENSOR_VOLTAGE_OUT_OVR 0x02 // output overload
+/**
+ * @brief State of FDM device
+ *
+ * @note This is only supported if ::MBG_IMS_STATE_FLAG_MSK_HAS_FDM is set in ::MBG_IMS_STATE::flags.
+ *
+ */
+typedef struct
+{
+ MBG_GPIO_FREQ freq; ///< Current frequency
-// if MBG_IMS_SENSOR_STATE::type == MBG_IMS_SENSOR_PLL:
-#define MBG_IMS_SENSOR_PLL_LOCKED 0x01
+ NANO_TIME_64 t_ref; ///< Current reference time
+ NANO_TIME_64 t_plt; ///< Current power line time
+ NANO_TIME_64 t_sync; ///< Last sync Time (reference time)
+ uint32_t line_freq; ///< Nominal line frequency, see ::MBG_IMS_FDM_LINE_FREQS
+ uint32_t flags; ///< Flags, see ::MBG_IMS_FDM_STATE_FLAG_MASKS
+ uint32_t reserved; ///< Reserved, currently always 0
-/** @} group_ims */
+} MBG_IMS_FDM_STATE;
+
+#define _mbg_swab_mbg_ims_fdm_state( _p ) \
+do \
+{ \
+ _mbg_swab_mbg_gpio_freq( &(_p)->freq ); \
+ _mbg_swab_nano_time_64( &(_p)->t_ref ); \
+ _mbg_swab_nano_time_64( &(_p)->t_plt ); \
+ _mbg_swab_nano_time_64( &(_p)->t_sync ); \
+ _mbg_swab32( &(_p)->line_freq ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab32( &(_p)->reserved ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration known line frequencies
+ *
+ * Used with ::MBG_IMS_FDM_STATE::line_freq
+ *
+ * @see ::MBG_IMS_FDM_LINE_FREQ_MASKS
+ */
+enum MBG_IMS_FDM_LINE_FREQS
+{
+ MBG_IMS_FDM_LINE_FREQ_AUTO, ///< Auto detect line frequency
+ MBG_IMS_FDM_LINE_FREQ_50HZ, ///< 50Hz line frequency
+ MBG_IMS_FDM_LINE_FREQ_60HZ, ///< 60Hz line frequency
+ N_MBG_IMS_FDM_LINE_FREQS ///< number of known line frequencies
+};
+
+
+/**
+ * @brief Bit masks corresponding to defined line frequencies
+ *
+ * @see ::MBG_IMS_FDM_LINE_FREQS
+ */
+enum MBG_IMS_FDM_LINE_FREQ_MASKS
+{
+ MBG_IMS_FDM_LINE_FREQ_MSK_AUTO = ( 1UL << MBG_IMS_FDM_LINE_FREQ_AUTO ), ///< see ::MBG_IMS_FDM_LINE_FREQ_AUTO
+ MBG_IMS_FDM_LINE_FREQ_MSK_50HZ = ( 1UL << MBG_IMS_FDM_LINE_FREQ_50HZ ), ///< see ::MBG_IMS_FDM_LINE_FREQ_50HZ
+ MBG_IMS_FDM_LINE_FREQ_MSK_60HZ = ( 1UL << MBG_IMS_FDM_LINE_FREQ_60HZ ) ///< see ::MBG_IMS_FDM_LINE_FREQ_60HZ
+};
+
+
+/**
+ * @brief Initializers for an array of line freq. name strings
+ *
+ * @see ::MBG_IMS_FDM_LINE_FREQS
+ */
+#define MBG_IMS_FDM_LINE_FREQ_STRS \
+{ \
+ "Auto", \
+ "50 Hz", \
+ "60 Hz", \
+}
+
+
+/**
+ * @brief Enumeration of flag bits used to define ::MBG_IMS_FDM_STATE_FLAG_MASKS
+ */
+enum MBG_IMS_FDM_STATE_FLAG_BITS
+{
+ MBG_IMS_FDM_STATE_FLAG_BIT_SYNC_AFTER_RESET, ///< if sync'ed after reset
+ MBG_IMS_FDM_STATE_FLAG_BIT_PLT_IS_LOCKED, ///< Power Line Time is locked
+ MBG_IMS_FDM_STATE_FLAG_BIT_FD_OVERFLOW, ///< Frequency deviation overflow occurred
+ MBG_IMS_FDM_STATE_FLAG_BIT_TD_OVERFLOW, ///< Time deviation overflow occurred
+ N_MBG_IMS_FDM_STATE_FLAG_BITS ///< number of known state flag bits
+};
+
+
+/**
+ * @brief Bit masks used with ::MBG_IMS_FDM_STATE::flags
+ *
+ * @see ::MBG_IMS_FDM_STATE_FLAG_BITS
+ */
+enum MBG_IMS_FDM_STATE_FLAG_MASKS
+{
+ MBG_IMS_FDM_STATE_FLAG_MSK_SYNC_AFTER_RESET = ( 1UL << MBG_IMS_FDM_STATE_FLAG_BIT_SYNC_AFTER_RESET ), ///< see ::MBG_IMS_FDM_STATE_FLAG_BIT_SYNC_AFTER_RESET
+ MBG_IMS_FDM_STATE_FLAG_MSK_PLT_IS_LOCKED = ( 1UL << MBG_IMS_FDM_STATE_FLAG_BIT_PLT_IS_LOCKED ), ///< see ::MBG_IMS_FDM_STATE_FLAG_BIT_PLT_IS_LOCKED
+ MBG_IMS_FDM_STATE_FLAG_MSK_FD_OVERFLOW = ( 1UL << MBG_IMS_FDM_STATE_FLAG_BIT_FD_OVERFLOW ), ///< see ::MBG_IMS_FDM_STATE_FLAG_BIT_FD_OVERFLOW
+ MBG_IMS_FDM_STATE_FLAG_MSK_TD_OVERFLOW = ( 1UL << MBG_IMS_FDM_STATE_FLAG_BIT_TD_OVERFLOW ) ///< see ::MBG_IMS_FDM_STATE_FLAG_BIT_TD_OVERFLOW
+};
+
+
+
+/**
+ * @brief FDM device settings
+ *
+ * @note This is only supported if ::MBG_IMS_STATE_FLAG_BIT_HAS_FDM is set in ::MBG_IMS_STATE::flags.
+ *
+ */
+typedef struct
+{
+ uint32_t fd_neg_limit; ///< min. frequency deviation limit in 1 mHz steps
+ uint32_t fd_pos_limit; ///< max. frequency deviation limit in 1 mHz steps
+
+ uint32_t td_neg_limit; ///< min. time deviation limit in 1 ms steps
+ uint32_t td_pos_limit; ///< max. time deviation limit in 1 ms steps
+
+ uint32_t line_freq; ///< nominal line frequency, see ::MBG_IMS_FDM_LINE_FREQS
+ uint32_t reserved; ///< reserved, currently always 0
+
+} MBG_IMS_FDM_SETTINGS;
+
+#define _mbg_swab_mbg_ims_fdm_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->fd_neg_limit ); \
+ _mbg_swab32( &(_p)->fd_pos_limit ); \
+ _mbg_swab32( &(_p)->td_neg_limit ); \
+ _mbg_swab32( &(_p)->td_pos_limit ); \
+ _mbg_swab32( &(_p)->line_freq ); \
+ _mbg_swab32( &(_p)->reserved ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief IMS FDM flags
+ *
+ * @see ::MBG_IMS_FDM_FLAG_MASKS
+ */
+enum MBG_IMS_FDM_FLAGS
+{
+ MBG_IMS_FDM_FLAG_CAN_SET_TDEV, ///< Device supports command GPS_FDM_SET_TD
+ N_MBG_IMS_FDM_FLAGS ///< Number of known FDM flags
+};
+
+
+
+/**
+ * @brief IMS FDM flag masks
+ *
+ * @see ::MBG_IMS_FDM_FLAGS
+ */
+enum MBG_IMS_FDM_FLAG_MASKS
+{
+ MBG_IMS_FDM_FLAG_MASK_CAN_SET_TDEV = ( 1UL << MBG_IMS_FDM_FLAG_CAN_SET_TDEV ) ///< see ::MBG_IMS_FDM_FLAG_CAN_SET_TDEV
+};
+
+
+
+/**
+ * @brief Specific FDM settings and limits.
+ */
+typedef struct
+{
+ MBG_IMS_FDM_SETTINGS settings;
+ uint32_t supp_line_freqs; ///< Bit mask of supported line frequencies, see ::MBG_IMS_FDM_LINE_FREQ_MASKS
+ uint32_t reserved; ///< Reserved, currently always 0
+ uint32_t flags; ///< Flags, see ::MBG_IMS_FDM_FLAG_MASKS
+
+} MBG_IMS_FDM_INFO;
+
+#define _mbg_swab_mbg_ims_fdm_info( _p ) \
+do \
+{ \
+ _mbg_swab_mbg_ims_fdm_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->supp_line_freqs ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+/** @} defgroup group_ims */
@@ -5131,9 +10632,9 @@ enum MBG_IMS_SENSORS
* _pcps_has_generic_io() or the corresponding function
* mbg_dev_has_generic_io() should be used by applications to
* check whether a particular bus-level device supports this.
+ *
* @{ */
-
typedef uint16_t GEN_IO_INFO_TYPE;
#define _mbg_swab_gen_io_info_type( _p ) \
@@ -5142,58 +10643,52 @@ typedef uint16_t GEN_IO_INFO_TYPE;
/**
- * @brief The data structure used with the PCPS_GEN_IO_GET_INFO command
+ * @brief The data structure used with the ::PCPS_GEN_IO_GET_INFO command
*
- * type specifier in order to query from a device which of the other
- * specified types is supported, and how many data sets are being
- * used by the device. The GEN_IO_INFO_TYPE must be passed to the
- * call which returns a GEN_IO_INFO structure filled by the device.
+ * Used to determine how many data sets of a specific type are supported
+ * by the device.
*/
typedef struct
{
- GEN_IO_INFO_TYPE type; // a PCPS_GEN_IO_GET_INFO type from the enum above
+ GEN_IO_INFO_TYPE type; // see ::PCPS_GEN_IO_TYPES
uint16_t num; // supported number of data sets of the specified type
} GEN_IO_INFO;
#define _mbg_swab_gen_io_info( _p ) \
+do \
{ \
_mbg_swab_gen_io_info_type( &(_p)->type ); \
_mbg_swab16( &(_p)->num ); \
-}
+} while ( 0 )
/**
- * @brief Data types used with GEN_IO_INFO::type
+ * @brief Data types used with ::GEN_IO_INFO::type
*
- * The first type specifier, PCPS_GEN_IO_GET_INFO, can
+ * The first type specifier, ::PCPS_GEN_IO_GET_INFO, can
* be used to find out which of the other data types are
* supported, and how many data sets of the specified type
* are supported by a device.
*/
enum PCPS_GEN_IO_TYPES
{
- PCPS_GEN_IO_GET_INFO, /**< GEN_IO_INFO (read only) */
- PCPS_GEN_IO_CAL_REC_IRIG_RX_COMP, /**< CAL_REC_IRIG_RX_COMP (read/write) */
- N_PCPS_GEN_IO_TYPE /**< number of known types */
+ PCPS_GEN_IO_GET_INFO, ///< ::GEN_IO_INFO (read only)
+ PCPS_GEN_IO_CAL_REC_IRIG_RX_COMP, ///< ::CAL_REC_IRIG_RX_COMP (read/write)
+ N_PCPS_GEN_IO_TYPE ///< number of known types
};
-/** @} group_generic_io */
-
+/** @} defgroup group_generic_io */
-/*------------------------------------------------------------------------*/
-/*
- * The types below are not used with all devices:
- */
typedef uint16_t ROM_CSUM; /* The ROM checksum */
-typedef uint16_t RCV_TIMEOUT; /* [min] (only if HAS_RCV_TIMEOUT) */
-typedef uint16_t IGNORE_LOCK; /* (only if GPS_HAS_IGNORE_LOCK) */
+typedef uint16_t RCV_TIMEOUT; /* [min] (only if ::HAS_RCV_TIMEOUT) */
+typedef uint16_t IGNORE_LOCK; /* (only if ::GPS_HAS_IGNORE_LOCK) */
/*
- * Originally IGNORE_LOG above has been a boolean value (equal or
+ * Originally ::IGNORE_LOG above has been a boolean value (equal or
* not equal 0) which was evaluated the same way for all ports.
*
* Due to special firmware requirements it has been changed to a
@@ -5222,53 +10717,111 @@ typedef uint16_t IGNORE_LOCK; /* (only if GPS_HAS_IGNORE_LOCK) */
( (_il) & ( _ignore_lock_for_port(_n) | IGNORE_LOCK_FOR_ALL_PORTS ) )
-/*------------------------------------------------------------------------*/
-/*
+/**
+ * @defgroup group_scu Definitions used with SCU devices
+ *
* The structures below are used with the SCU multiplexer board
- * in a redundant system:
- */
+ * in a redundant system.
+ *
+ * @see ::GPS_MODEL_IS_SCU
+ *
+ * @{ */
typedef struct
{
- uint32_t hw_id; // hardware identification
- uint32_t fw_id; // firmware identification
- uint16_t flags; // reserved currently 0
- uint8_t clk0_info; // reference clock 0 type
- uint8_t clk1_info; // reference clock 1 type
- uint16_t epld_status; // epld status word, see defintions below
- uint16_t epld_control; // epld control word, see defintions below
+ uint32_t hw_id; ///< hardware identification
+ uint32_t fw_id; ///< firmware identification
+ uint16_t flags; ///< reserved currently 0
+ uint8_t clk0_info; ///< reference clock 0 type
+ uint8_t clk1_info; ///< reference clock 1 type
+ uint16_t epld_status; ///< EPLD status word, see ::SCU_STAT_MASKS
+ uint16_t epld_control; ///< EPLD control word, see ::SCU_CTRL_MASKS
+
} SCU_STAT_INFO;
+#define _mbg_swab_scu_stat_info( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->hw_id ); \
+ _mbg_swab32( &(_p)->fw_id ); \
+ _mbg_swab16( &(_p)->flags ); \
+ _mbg_swab8( &(_p)->clk0_info ); \
+ _mbg_swab8( &(_p)->clk1_info ); \
+ _mbg_swab16( &(_p)->epld_status ); \
+ _mbg_swab16( &(_p)->epld_control ); \
+} while ( 0 )
+
+
+
typedef struct
{
- uint16_t epld_control_mask; // control mask, determines which bit is to be changed
- uint16_t epld_control_value; // control value, determines value of bits to be changed
- uint32_t flags; // reserved, currently 0
+ uint16_t epld_control_mask; ///< control mask, determines which bit is to be changed, see ::SCU_CTRL_MASKS
+ uint16_t epld_control_value; ///< control value, determines value of bits to be changed, see ::SCU_CTRL_MASKS
+ uint32_t flags; ///< reserved, currently 0
+
} SCU_STAT_SETTINGS;
-// definitions for status word bit masks
-#define MSK_EPLD_STAT_TS1 0x0001 // state of time sync signal clk_1
-#define MSK_EPLD_STAT_TS2 0x0002 // state of time sync signal clk_2
-#define MSK_EPLD_STAT_TL_ERROR 0x0004 // state of time limit error input
-#define MSK_EPLD_STAT_PSU1_OK 0x0008 // state of power supply 1 monitoring input
-#define MSK_EPLD_STAT_PSU2_OK 0x0010 // state of power supply 2 monitoring input
-#define MSK_EPLD_STAT_AUTO 0x0020 // AUTOMATIC/REMOTE or MANUAL Mode
-#define MSK_EPLD_STAT_SEL 0x0040 // select bit for output MUX, ( clk_1 = 0 )
-#define MSK_EPLD_STAT_ENA 0x0080 // enable Bit for output MUX, set if enabled
-#define MSK_EPLD_STAT_ACO 0x4000 // Access control override bit
-#define MSK_EPLD_STAT_WDOG_OK 0x8000 // WDT_OK set to zero if watchdog expired
+#define _mbg_swab_scu_stat_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->epld_control_mask ); \
+ _mbg_swab16( &(_p)->epld_control_value ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
-#define MSK_EPLD_CNTL_SEL_REM 0x0800 // remote select for output MUX ( clk_1 = 0 )
-#define MSK_EPLD_CNTL_DIS_REM 0x1000 // remote disable for output MUX
-#define MSK_EPLD_CNTL_REMOTE 0x2000 // must be set to enable remote operation
-#define MSK_EPLD_CNTL_SEL_SNMP 0x4000 // select clk for comm. ( clk1 = 0 )
-#define MSK_EPLD_CNTL_ENA_SNMP 0x8000 // connect COM0 channels to XPORT
+/**
+ * @brief Bit masks used to check the SCU EPLD status
+ *
+ * Used with ::SCU_STAT_INFO::epld_status
+ */
+enum SCU_STAT_MASKS
+{
+ MSK_EPLD_STAT_TS1 = 0x0001, ///< state of time sync signal clk_1
+ MSK_EPLD_STAT_TS2 = 0x0002, ///< state of time sync signal clk_2
+ MSK_EPLD_STAT_TL_ERROR = 0x0004, ///< state of time limit error input
+ MSK_EPLD_STAT_PSU1_OK = 0x0008, ///< state of power supply 1 monitoring input
+ MSK_EPLD_STAT_PSU2_OK = 0x0010, ///< state of power supply 2 monitoring input
+ MSK_EPLD_STAT_AUTO = 0x0020, ///< AUTOMATIC/REMOTE or MANUAL Mode
+ MSK_EPLD_STAT_SEL = 0x0040, ///< select bit for output MUX, ( clk_1 = 0 )
+ MSK_EPLD_STAT_ENA = 0x0080, ///< enable Bit for output MUX, set if enabled
+ MSK_EPLD_STAT_HAS_LAN = 0x0100, ///< indicates that the device has a network interface
+ MSK_EPLD_STAT_RESERVED0 = 0x0200, ///< reserved, DO NOT USE!
+ MSK_EPLD_STAT_RESERVED1 = 0x0400, ///< reserved, DO NOT USE!
+ MSK_EPLD_STAT_HAS_4_PSUS = 0x0800, ///< indicates 4 power supplies instead of 2
+ MSK_EPLD_STAT_PSU3_OK = 0x1000, ///< state of power supply 3 monitoring input
+ MSK_EPLD_STAT_PSU4_OK = 0x2000, ///< state of power supply 4 monitoring input
+ MSK_EPLD_STAT_ACO = 0x4000, ///< Access control override bit
+ MSK_EPLD_STAT_WDOG_OK = 0x8000 ///< WDT_OK set to zero if watchdog expired
+};
+
/**
- * @brief Definitions for SCU_STAT_INFO::clk0_info and SCU_STAT_INFO::clk1_info
+ * @brief Bit masks used to control the SCU EPLD
+ *
+ * Used with ::SCU_STAT_INFO::epld_control, ::SCU_STAT_SETTINGS::epld_control_mask,
+ * and ::SCU_STAT_SETTINGS::epld_control_value.
+ */
+enum SCU_CTRL_MASKS
+{
+ MSK_EPLD_CTL_DISB_SERIAL = 0x0001, ///< disable serial output on error
+ MSK_EPLD_CTL_DISB_PPS = 0x0002, ///< disable PPS output on error
+ MSK_EPLD_CTL_DISB_10MHZ = 0x0004, ///< disable 10 MHz output on error
+
+ MSK_EPLD_CNTL_SEL_REM = 0x0800, ///< remote select for output MUX (clk_1 = 0)
+ MSK_EPLD_CNTL_DIS_REM = 0x1000, ///< remote disable for output MUX
+ MSK_EPLD_CNTL_REMOTE = 0x2000, ///< must be set to enable remote operation
+ MSK_EPLD_CNTL_SEL_SNMP = 0x4000, ///< select clk for comm. (clk1 = 0)
+ MSK_EPLD_CNTL_ENA_SNMP = 0x8000, ///< connect COM0 channels to XPORT
+};
+
+
+
+/**
+ * @brief Definitions for ::SCU_STAT_INFO::clk0_info and ::SCU_STAT_INFO::clk1_info
*
* Can be used to determine the reference clock type connected to the SCU input channels.
*/
@@ -5281,36 +10834,41 @@ enum SCU_CLK_INFO_TYPES
N_SCU_CLK_INFO ///< number of known types
};
+/** @} defgroup group_scu */
+
/*------------------------------------------------------------------------*/
+#define REMOTE 0x10
+#define BOOT 0x20
+
/**
* @brief Satellite receiver modes of operation.
*
- * @note Some of the code combinations are obsolete with recent
+ * @note Some of the code combinations are deprecated with recent
* satellite receivers. However, this doesn't matter since the mode
* is just read from the receiver.
*/
-#define REMOTE 0x10
-#define BOOT 0x20
-
-#define TRACK ( 0x01 )
-#define AUTO_166 ( 0x02 )
-#define WARM_166 ( 0x03 | BOOT )
-#define COLD_166 ( 0x04 | BOOT )
-#define AUTO_BC ( 0x05 | REMOTE )
-#define WARM_BC ( 0x06 | REMOTE | BOOT )
-#define COLD_BC ( 0x07 | REMOTE | BOOT )
-#define UPDA_166 ( 0x08 | BOOT )
-#define UPDA_BC ( 0x09 | REMOTE | BOOT )
+enum RECEIVER_MODES
+{
+ TRACK = ( 0x01 ),
+ AUTO_166 = ( 0x02 ),
+ WARM_166 = ( 0x03 | BOOT ),
+ COLD_166 = ( 0x04 | BOOT ),
+ AUTO_BC = ( 0x05 | REMOTE ),
+ WARM_BC = ( 0x06 | REMOTE | BOOT ),
+ COLD_BC = ( 0x07 | REMOTE | BOOT ),
+ UPDA_166 = ( 0x08 | BOOT ),
+ UPDA_BC = ( 0x09 | REMOTE | BOOT )
+};
typedef int16_t DAC_VAL;
#define _mbg_swab_dac_val( _p ) \
- _mbg_swab16( _p );
+ _mbg_swab16( _p )
@@ -5319,21 +10877,23 @@ typedef int16_t DAC_VAL;
*/
typedef struct
{
- uint16_t mode; /**< Mode of operation, see predefined codes */
- uint16_t good_svs; /**< Numb. of satellites that can currently be received and used */
- uint16_t svs_in_view; /**< Numb. of satellites that should be in view according to the almanac data */
- DAC_VAL dac_val; /**< Oscillator fine DAC value */
- DAC_VAL dac_cal; /**< Oscillator calibration DAC value ( see #OSC_DAC_RANGE, #OSC_DAC_BIAS ) */
+ uint16_t mode; ///< Mode of operation, see ::RECEIVER_MODES
+ uint16_t good_svs; ///< Numb. of satellites that can currently be received and used
+ uint16_t svs_in_view; ///< Numb. of satellites that should be visible above the horizon
+ DAC_VAL dac_val; ///< Oscillator fine DAC value
+ DAC_VAL dac_cal; ///< Oscillator calibration DAC value ( see ::OSC_DAC_RANGE, ::OSC_DAC_BIAS )
+
} STAT_INFO;
#define _mbg_swab_stat_info( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->mode ); \
_mbg_swab16( &(_p)->good_svs ); \
_mbg_swab16( &(_p)->svs_in_view ); \
_mbg_swab_dac_val( &(_p)->dac_val ); \
_mbg_swab_dac_val( &(_p)->dac_cal ); \
-}
+} while ( 0 )
#define OSC_DAC_RANGE 4096UL
@@ -5343,6 +10903,9 @@ typedef struct
/**
* @brief An enumeration of known satellite navigation systems
+ *
+ * @see ::MBG_GNSS_TYPE_MASKS
+ * @see ::GNSS_TYPE_STRS
*/
enum MBG_GNSS_TYPES
{
@@ -5350,89 +10913,362 @@ enum MBG_GNSS_TYPES
GNSS_TYPE_GLONASS, ///< GLONASS, Russia
GNSS_TYPE_BEIDOU, ///< BEIDOU, China
GNSS_TYPE_GALILEO, ///< GALILEO, Europe
+ GNSS_TYPE_WAAS, ///< WAAS, Wide Area Augmentation System
+ GNSS_TYPE_EGNOS, ///< EGNOS, European Geostationary Navigation Overlay Service
+ GNSS_TYPE_QZSS, ///< QZSS, Quasi Zenit Satellite System
N_GNSS_TYPES ///< Number of defined codes
};
+
+/**
+ * @brief Bit masks associated with ::MBG_GNSS_TYPES
+ *
+ * @see ::MBG_GNSS_TYPES
+ */
+enum MBG_GNSS_TYPE_MASKS
+{
+ MBG_GNSS_TYPE_MSK_GPS = ( 1UL << GNSS_TYPE_GPS ), ///< see ::GNSS_TYPE_GPS
+ MBG_GNSS_TYPE_MSK_GLONASS = ( 1UL << GNSS_TYPE_GLONASS ), ///< see ::GNSS_TYPE_GLONASS
+ MBG_GNSS_TYPE_MSK_BEIDOU = ( 1UL << GNSS_TYPE_BEIDOU ), ///< see ::GNSS_TYPE_BEIDOU
+ MBG_GNSS_TYPE_MSK_GALILEO = ( 1UL << GNSS_TYPE_GALILEO ), ///< see ::GNSS_TYPE_GALILEO
+ MBG_GNSS_TYPE_MSK_WAAS = ( 1UL << GNSS_TYPE_WAAS ), ///< see ::GNSS_TYPE_WAAS
+ MBG_GNSS_TYPE_MSK_EGNOS = ( 1UL << GNSS_TYPE_EGNOS ), ///< see ::GNSS_TYPE_EGNOS
+ MBG_GNSS_TYPE_MSK_QZSS = ( 1UL << GNSS_TYPE_QZSS ) ///< see ::GNSS_TYPE_QZSS
+};
+
+
+/**
+ * @brief Name strings for the the known satellite navigation systems
+ *
+ * @see ::MBG_GNSS_TYPES
+ */
#define GNSS_TYPE_STRS \
{ \
"GPS", \
"GLONASS", \
- "BEIDOU" , \
- "GALILEO" \
+ "BEIDOU", \
+ "GALILEO", \
+ "WAAS", \
+ "EGNOS", \
+ "QZSS" \
}
-#define MBG_GNSS_TYPE_MSK_GPS ( 1UL << GNSS_TYPE_GPS )
-#define MBG_GNSS_TYPE_MSK_GLONASS ( 1UL << GNSS_TYPE_GLONASS )
-#define MBG_GNSS_TYPE_MSK_BEIDOU ( 1UL << GNSS_TYPE_BEIDOU )
-#define MBG_GNSS_TYPE_MSK_GALILEO ( 1UL << GNSS_TYPE_GALILEO )
-
#define N_GNSS_MODE_PRIO 8
+/**
+ * @brief GNSS mode settings
+ *
+ * @see ::MBG_GNSS_TYPES
+ */
typedef struct
{
- uint32_t gnss_set; /**< current set of GNSS types */
- uint8_t prio[N_GNSS_MODE_PRIO]; /**< index 0 for highest priority, use GNSS enumeration above, init with 0xFF if not supported */
- uint32_t flags; /**< see below */
+ uint32_t gnss_set; ///< bit mask of currently used GNSS systems, see ::MBG_GNSS_TYPE_MASKS
+ uint8_t prio[N_GNSS_MODE_PRIO]; ///< see ::MBG_GNSS_TYPES, unused fields set to 0xFF, idx 0 is highest prio
+ uint32_t flags; ///< unused, currently always 0 (should be named MBG_GNSS_MODE_SETTINGS_FLAG_MASKS)
+
} MBG_GNSS_MODE_SETTINGS;
#define _mbg_swab_mbg_gnss_mode_settings( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->gnss_set ); \
_mbg_swab32( &(_p)->flags ); \
-}
+} while ( 0 )
typedef struct
{
- MBG_GNSS_MODE_SETTINGS settings; /**< current GNSS mode settings */
- uint32_t supp_gnss_types; /**< bit masks of supported GNSS types */
- uint32_t flags; /**< indicates which of the defined flags are supported by the device */
+ MBG_GNSS_MODE_SETTINGS settings; ///< Current GNSS mode settings
+ uint32_t supp_gnss_types; ///< Bit masks of supported GNSS types, see ::MBG_GNSS_TYPE_MASKS
+ uint16_t flags; ///< See ::MBG_GNSS_MODE_INFO_FLAG_MASKS
+ uint16_t n_sv_status; ///< Number of ::GNSS_SV_STATUS_IDX structures that can be read (only if ::MBG_GNSS_FLAG_MSK_HAS_SV_STATUS)
+
} MBG_GNSS_MODE_INFO;
#define _mbg_swab_mbg_gnss_mode_info( _p ) \
+do \
{ \
_mbg_swab_mbg_gnss_mode_settings( &(_p)->settings ); \
_mbg_swab32( &(_p)->supp_gnss_types ); \
- _mbg_swab32( &(_p)->flags ); \
-}
+ _mbg_swab16( &(_p)->flags ); \
+ _mbg_swab16( &(_p)->n_sv_status ); \
+} while ( 0 )
+
/**
- * @brief Flags used with MBG_GNSS_MODE_SETTINGS::flags and MBG_GNSS_MODE_INFO::flags
+ * @brief Flag bits used to define ::MBG_GNSS_MODE_INFO_FLAG_MASKS
+ *
+ * @see ::MBG_GNSS_MODE_INFO_MASKS
*/
-enum MBG_GNSS_MODE_FLAG_BITS
+enum MBG_GNSS_MODE_INFO_FLAG_BITS
{
- MBG_GNSS_FLAG_EXCLUSIVE, ///< (read only) only one of the supported GNSS systems can be used at the same time
- MBG_GNSS_FLAG_HAS_PRIORITY, ///< (read only) priority can be configured using the MBG_GNSS_MODE_SETTINGS::prio field
+ MBG_GNSS_FLAG_EXCLUSIVE, ///< Only one of the supported GNSS systems can be used at the same time
+ MBG_GNSS_FLAG_HAS_PRIORITY, ///< Priority can be configured using the ::MBG_GNSS_MODE_SETTINGS::prio field
+ MBG_GNSS_FLAG_SAT_INFO_IDX_SUPP_SER, ///< The ::GNSS_SAT_INFO_IDX structure is supported by the device
+ MBG_GNSS_FLAG_HAS_SV_STATUS, ///< The ::GNSS_SV_STATUS_IDX structure is supported by the device
N_MBG_GNSS_FLAGS
};
-#define MBG_GNSS_FLAG_MSK_EXCLUSIVE ( 1UL << MBG_GNSS_FLAG_EXCLUSIVE )
-#define MBG_GNSS_FLAG_MSK_HAS_PRIORITY ( 1UL << MBG_GNSS_FLAG_HAS_PRIORITY )
+/**
+ * @brief Flag masks used with MBG_GNSS_MODE_INFO::flags
+ *
+ * @see ::MBG_GNSS_MODE_FLAG_BITS
+ */
+enum MBG_GNSS_MODE_INFO_FLAG_MASKS
+{
+ MBG_GNSS_FLAG_MSK_EXCLUSIVE = ( 1UL << MBG_GNSS_FLAG_EXCLUSIVE ), ///< see ::MBG_GNSS_FLAG_EXCLUSIVE
+ MBG_GNSS_FLAG_MSK_HAS_PRIORITY = ( 1UL << MBG_GNSS_FLAG_HAS_PRIORITY ), ///< see ::MBG_GNSS_FLAG_HAS_PRIORITY
+ MBG_GNSS_FLAG_MSK_SAT_INFO_IDX_SUPP_SER = ( 1UL << MBG_GNSS_FLAG_SAT_INFO_IDX_SUPP_SER ), ///< see ::MBG_GNSS_FLAG_SAT_INFO_IDX_SUPP_SER
+ MBG_GNSS_FLAG_MSK_HAS_SV_STATUS = ( 1UL << MBG_GNSS_FLAG_HAS_SV_STATUS ) ///< see ::MBG_GNSS_FLAG_HAS_SV_STATUS
+};
-#define MAX_USED_SATS 32
+
+#define MAX_USED_SATS 32
/**
- * @brief SV information from a certain GNSS type.
+ * @brief Satellite information for a particular GNSS type.
*/
typedef struct
{
- uint8_t gnss_type; /**< GNSS type from the enumeration above */
- uint8_t reserved;
- uint16_t good_svs;
- uint16_t svs_in_view;
- uint8_t svs[MAX_USED_SATS];
+ uint8_t gnss_type; ///< GNSS type as enumerated in ::MBG_GNSS_TYPES
+ uint8_t reserved; ///< Reserved, currently always 0
+ uint16_t good_svs; ///< Num. of satellites that can currently be received and used
+ uint16_t svs_in_view; ///< Num. of satellites that should be visible above the horizon
+ uint8_t svs[MAX_USED_SATS]; ///< IDs of the satellites actually used for navigation, 0 == not used
+
} GNSS_SAT_INFO;
#define _mbg_swab_gnss_sat_info( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->good_svs ); \
_mbg_swab16( &(_p)->svs_in_view ); \
-}
+} while ( 0 )
+
+
+
+/**
+ * @brief One of several sets of satellite information for a particular GNSS type.
+ *
+ *
+ */
+typedef struct
+{
+ /// GNSS system type index according to ::MBG_GNSS_MODE_INFO::supp_gnss_types.
+ /// I.e., idx 0 corresponds to the GNSS system for which the least significant
+ /// bit is set in ::MBG_GNSS_MODE_INFO::supp_gnss_types, idx 1 corresponds to
+ /// GNSS system for which the next higher bit is set, etc. This must *not*
+ /// necessarily match the sequence of the ::MBG_GNSS_TYPES enumeration.
+ uint16_t idx;
+
+ GNSS_SAT_INFO gnss_sat_info; ///< see ::GNSS_SAT_INFO
+
+} GNSS_SAT_INFO_IDX;
+
+#define _mbg_swab_gnss_sat_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_gnss_sat_info( &(_p)->gnss_sat_info ); \
+} while ( 0 )
+
+
+
+/**
+ * @defgroup group_gnss_sv_status GNSS Satellite Status
+ *
+ * @note These structures and associated types are only supported by a device
+ * if ::MBG_XFEATURE_GNSS_SV_INFO is set in the extended device features. // FIXME
+ *
+ * @{ */
+
+/**
+ * @brief Detailed GNSS satellite status
+ *
+ * @see ::GNSS_SV_STATUS_IDX
+ * @see @ref group_gnss_sv_stat_flags
+ */
+typedef struct
+{
+ uint8_t gnss_type; ///< GNSS type as enumerated in ::MBG_GNSS_TYPES
+ uint8_t svno; ///< Satellite number, see ::TODO
+ uint8_t cn_ratio; ///< Carrier-to-noise ratio [dbHz]
+ int8_t elev; ///< Elevation [deg], range: -90..90 deg
+
+ int16_t azim; ///< Azimuth [deg], range: 0..360 deg
+ int16_t pr_residual; ///< Pseudo range residual [m]
+
+ uint32_t stat_flags; ///< see @ref group_gnss_sv_stat_flags
+
+} GNSS_SV_STATUS;
+
+#define _mbg_swab_gnss_sv_status( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->gnss_type ); \
+ _mbg_swab8( &(_p)->svno ); \
+ _mbg_swab8( &(_p)->cn_ratio ); \
+ _mbg_swab8( &(_p)->elev ); \
+ _mbg_swab16( &(_p)->azim ); \
+ _mbg_swab16( &(_p)->pr_residual ); \
+ _mbg_swab32( &(_p)->stat_flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @defgroup group_gnss_sv_stat_flags GNSS status flags encoding
+ *
+ * Used with ::GNSS_SV_STATUS::stat_flags.
+ *
+ * @{ */
+
+/// Bits 0 to 2 are a 3 bit quality indicator, see ::GNSS_SV_STAT_QUALITY_INDS
+#define _gnss_sv_stat_quality_ind( __stat_flags ) \
+ ( (uint8_t) ( (__stat_flags) & 0x00000007UL ) )
+
+/// Bit 3 is set if the SV is actually used for navigation
+#define _gnss_sv_stat_sv_used( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00000008UL ) != 0 )
+
+/// Bits 4 and 5 are a 2 bit health code, see ::GNSS_SV_STAT_HEALTH_CODES
+#define _gnss_sv_stat_health_code( __stat_flags ) \
+ ( (uint8_t) ( ( (__stat_flags) & 0x00000030UL ) >> 4 ) )
+
+/// Bit 6 is set if differential correction is available for this SV
+#define _gnss_sv_stat_diff_corr( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00000040UL ) != 0 )
+
+/// Bit 7 is set if carrier smoothed pseudorange is used for this SV
+#define _gnss_sv_stat_smoothed( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00000080UL ) != 0 )
+
+/// Bits 8 to 10 are a 3 bit code indicating the orbit source, see ::GNSS_SV_STAT_ORBIT_SOURCES
+#define _gnss_sv_stat_orbit_src( __stat_flags ) \
+ ( (uint8_t) ( ( (__stat_flags) & 0x00000700UL ) >> 8 ) )
+
+/// Bit 11 is set if ephemeris parameters are available for this SV
+#define _gnss_sv_stat_eph_avail( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00000800UL ) != 0 )
+
+/// Bit 12 is set if almanac parameters are available for this SV
+#define _gnss_sv_stat_alm_avail( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00001000UL ) != 0 )
+
+/// Bit 13 is set if AssistNow Offline data is available for this SV
+#define _gnss_sv_stat_ano_avail( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00002000UL ) != 0 )
+
+/// Bit 14 is set if AssistNow Autonomous data is available for this SV
+#define _gnss_sv_stat_aop_avail( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00004000UL ) != 0 )
+
+/// Bit 15 is reserved.
+
+/// Bit 16 is set if SBAS corrections have been used for this SV
+#define _gnss_sv_stat_sbas_corr_used( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00010000UL ) != 0 )
+
+/// Bit 17 is set if RTCM corrections have been used for this SV
+#define _gnss_sv_stat_rtcm_corr_used( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00020000UL ) != 0 )
+
+/// Bits 18 and 19 are reserved.
+
+/// Bit 20 is set if pseudorange corrections have been used for this SV
+#define _gnss_sv_stat_pr_corr_used( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00100000UL ) != 0 )
+
+/// Bit 21 is set if carrier range corrections have been used for this SV
+#define _gnss_sv_stat_cr_corr_used( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00200000UL ) != 0 )
+
+/// Bit 22 is set if range rate (doppler) corrections have been used for this SV
+#define _gnss_sv_stat_do_corr_used( __stat_flags ) \
+ ( ( (__stat_flags) & 0x00400000UL ) != 0 )
+
+/// Bits 23 to 31 are reserved.
+
+/** @} defgroup group_gnss_sv_stat_flags */
+
+
+/**
+ * @brief Quality indicators used with ::GNSS_SV_STATUS::sv_stat
+ *
+ * @see ::_gnss_sv_stat_quality_ind
+ */
+enum GNSS_SV_STAT_QUALITY_INDS
+{
+ GNSS_SV_STAT_NO_SIGNAL, ///< No signal
+ GNSS_SV_STAT_SEARCHING, ///< Searching signal
+ GNSS_SV_STAT_ACQUIRED, ///< Signal acquired
+ GNSS_SV_STAT_UNUSABLE, ///< Signal detected but unusable
+ GNSS_SV_STAT_CODE_LOCKED, ///< Code locked and time synchronized
+ GNSS_SV_STAT_CODE_CARRIER_LOCKED, ///< Code and carrier locked, and time synchronized
+ GNSS_SV_STAT_CODE_CARRIER_LOCKED_2, ///< Code and carrier locked, and time synchronized
+ GNSS_SV_STAT_CODE_CARRIER_LOCKED_3 ///< Code and carrier locked, and time synchronized
+};
+
+
+/**
+ * @brief Health indicators used with ::GNSS_SV_STATUS::sv_stat
+ *
+ * @see ::_gnss_sv_stat_health_code
+ */
+enum GNSS_SV_STAT_HEALTH_CODES
+{
+ GNSS_SV_STAT_HEALTH_UNKNOWN, ///< Health status unknown
+ GNSS_SV_STAT_HEALTH_OK, ///< Healthy
+ GNSS_SV_STAT_HEALTH_NOT_OK ///< Unhealthy
+};
+
+
+/**
+ * @brief Orbit source codes used with ::GNSS_SV_STATUS::sv_stat
+ *
+ * @see ::_gnss_sv_stat_orbit_src
+ */
+enum GNSS_SV_STAT_ORBIT_SOURCES
+{
+ GNSS_SV_STAT_ORBIT_SRC_UNKNOWN, ///< Orbit source unknown
+ GNSS_SV_STAT_ORBIT_SRC_EPH, ///< Ephemeris data used for orbit
+ GNSS_SV_STAT_ORBIT_SRC_ALM, ///< Almanac data used for orbit
+ GNSS_SV_STAT_ORBIT_SRC_ASSN_OFFL, ///< AssistNow Offline orbit is used
+ GNSS_SV_STAT_ORBIT_SRC_ASSN_AUTO, ///< AssistNow Autonomous orbit is used
+ GNSS_SV_STAT_ORBIT_OTHER_1, ///< Other orbit information is used
+ GNSS_SV_STAT_ORBIT_OTHER_2, ///< Other orbit information is used
+ GNSS_SV_STAT_ORBIT_OTHER_3 ///< Other orbit information is used
+};
+
+
+
+/**
+ * @brief Detailed GNSS satellite status, plus index
+ *
+ * @see ::GNSS_SV_STATUS
+ */
+typedef struct
+{
+ uint32_t idx; ///< Range 0..::MBG_GNSS_MODE_INFO::n_sv_status-1
+ GNSS_SV_STATUS gnss_sv_status;
+
+} GNSS_SV_STATUS_IDX;
+
+#define _mbg_swab_gnss_sv_status_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_gnss_sv_status( &(_p)->gnss_sv_status ); \
+} while ( 0 )
+
+
+/** @} defgroup group_gnss_sv_status */
+
#ifndef _IDENT_DEFINED
@@ -5448,11 +11284,14 @@ typedef struct
#endif
#define _mbg_swab_ident( _p ) \
+do \
{ \
int i; \
for ( i = 0; i < 4; i++ ) \
_mbg_swab32( &(_p)->lw[i] ); \
-}
+} while ( 0 )
+
+
/**
* @brief A data type used to configure the length of an antenna cable [m]
@@ -5464,14 +11303,28 @@ typedef uint16_t ANT_CABLE_LEN;
/**
- * @defgroup group_ip4_cfg Simple configuration and status
- * of an optional LAN interface.
+ * @defgroup group_net_cfg Network configuration stuff
*
- * @note This is only supported if the flag ::GPS_HAS_LAN_IP4 is set
- * in RECEIVER_INFO::features.
+ * @{ */
+
+/**
+ * @defgroup group_net_basic_types Basic network parameter types
*
* @{ */
+/**
+ * @brief The MAC address of a network interface
+ */
+typedef struct
+{
+ uint8_t b[6];
+
+} MBG_MAC_ADDR;
+
+#define _mbg_swab_mbg_mac_addr( _p ) \
+ _nop_macro_fnc()
+
+
/**
* @brief An IPv4 address
@@ -5479,40 +11332,152 @@ typedef uint16_t ANT_CABLE_LEN;
typedef uint32_t IP4_ADDR;
#define _mbg_swab_ip4_addr( _p ) \
- _mbg_swab32( _p );
+ _mbg_swab32( _p )
+
+/** @brief The number of bits used for an IPv6 address */
+#define IP6_ADDR_BITS 128
+
+/** @brief The number of bytes used for an IPv6 address */
+#define IP6_ADDR_BYTES ( IP6_ADDR_BITS / 8 ) // == 16
+
/**
- * @brief Settings of an IPv4 network interface
+ * @brief An IPv6 address
*/
typedef struct
{
- IP4_ADDR ip_addr; /**< the IP address */
- IP4_ADDR netmask; /**< the network mask */
- IP4_ADDR broad_addr; /**< the broadcast address */
- IP4_ADDR gateway; /**< the default gateway */
- uint16_t flags; /**< flags as specified below */
- uint16_t vlan_cfg; /**< VLAN configuration, see below */
+ uint8_t b[IP6_ADDR_BYTES]; ///< bytes holding the address bits (not the string notation), b[0] == LSBs
-} IP4_SETTINGS;
+} IP6_ADDR;
-#define _mbg_swab_ip4_settings( _p ) \
-{ \
- _mbg_swab_ip4_addr( &(_p)->ip_addr ); \
- _mbg_swab_ip4_addr( &(_p)->netmask ); \
- _mbg_swab_ip4_addr( &(_p)->broad_addr ); \
- _mbg_swab_ip4_addr( &(_p)->gateway ); \
- _mbg_swab16( &(_p)->flags ); \
- _mbg_swab16( &(_p)->vlan_cfg ); \
+#define _mbg_swab_ip6_addr( _p ) _nop_macro_fnc()
+
+
+
+/**
+ * @brief An IPv6 address plus number of netmask bits
+ */
+typedef struct
+{
+ IP6_ADDR addr; ///< bit mask of the bytes holding the address bits, b[0] == LSBs
+ uint8_t prefix; ///< Number of subnet mask bits for CIDR notation, e.g. 24 for /24
+ uint8_t reserved[3]; ///< Reserved, alignment, currently 0
+
+} IP6_ADDR_CIDR;
+
+
+
+/** @brief The max number of chars required for an IPv6 address string */
+#define MAX_IP6_ADDR_STR_LEN 43 ///< e.g. 2001:0db8:85a3:08d3:1319:8a2e:0370:7344/128
+
+/** @brief Buffer size required to store an IPv6 address string */
+#define IP6_ADDR_STR_SIZE ( MAX_IP6_ADDR_STR_LEN + 1 ) ///< ::MAX_IP6_ADDR_STR_LEN + terminating 0
+
+/** @brief A buffer for an IPv6 address string */
+typedef char IP6_ADDR_STR[IP6_ADDR_STR_SIZE];
+
+
+
+/**
+ * @brief Possible IPv6 Multicast Scopes
+ *
+ * If the first (most significant) byte of an IPv6 address is 0xFF this
+ * indicates that the address is a multicast address, and in this case
+ * the second byte determines the scope for which the specified address
+ * is valid. These scope ID numbers are assigned in RFC 7346 which
+ * supersedes RFC 4291.
+ *
+ * @see ::IPV6_MULTICAST_SCOPE_NAME_TABLE_ENTRIES
+ */
+enum IPV6_MULTICAST_SCOPES
+{
+ IPV6_MULTICAST_SCOPE_INTF_LOCAL = 0x01, ///< Interface-Local scope
+ IPV6_MULTICAST_SCOPE_LINK_LOCAL, ///< Link-Local scope
+ IPV6_MULTICAST_SCOPE_REALM_LOCAL, ///< Realm-Local scope
+ IPV6_MULTICAST_SCOPE_ADMIN_LOCAL, ///< Admin-Local scope
+ IPV6_MULTICAST_SCOPE_SITE_LOCAL, ///< Site-Local scope
+ IPV6_MULTICAST_SCOPE_ORGA_LOCAL = 0x08, ///< Organization-Local scope
+ IPV6_MULTICAST_SCOPE_GLOBAL_SCOPE = 0x0E ///< Global scope
+};
+
+
+/**
+ * @brief Name strings for IPv6 multicast scopes
+ *
+ * This can e.g. be used to initialize an array of ::MBG_CODE_NAME_TABLE_ENTRY elements.
+ *
+ * @see ::IPV6_MULTICAST_SCOPES
+ */
+#define IPV6_MULTICAST_SCOPE_NAME_TABLE_ENTRIES \
+{ \
+ { IPV6_MULTICAST_SCOPE_INTF_LOCAL, "FF01 - Interface-Local Scope" }, \
+ { IPV6_MULTICAST_SCOPE_LINK_LOCAL, "FF02 - Link-Local Scope" }, \
+ { IPV6_MULTICAST_SCOPE_REALM_LOCAL, "FF03 - Realm-Local Scope" }, \
+ { IPV6_MULTICAST_SCOPE_ADMIN_LOCAL, "FF04 - Admin-Local Scope" }, \
+ { IPV6_MULTICAST_SCOPE_SITE_LOCAL, "FF05 - Site-Local Scope" }, \
+ { IPV6_MULTICAST_SCOPE_ORGA_LOCAL, "FF08 - Organization-Local Scope" }, \
+ { IPV6_MULTICAST_SCOPE_GLOBAL_SCOPE, "FF0E - Global Scope" }, \
+ { 0, NULL } \
}
+
+/**
+ * @brief The maximum length of a fully qualified host/domain domain name (FQDN)
+ *
+ * In theory each single component (host name, domain name, top level domain name)
+ * of a FQDN can have up to 63 characters, but the overall length is limited to
+ * 255 characters (see RFC-1123). We specify one more character for the trailing 0.
+ */
+#define MBG_MAX_HOSTNAME_LEN 256
+
+
+/**
+ * @brief A buffer for a fully qualified domain name (FQDN) or a numeric IP address string
+ */
+typedef char MBG_HOSTNAME[MBG_MAX_HOSTNAME_LEN]; ///< ASCIIZ format
+
+#define _mbg_swab_mbg_host_name( _p ) _nop_macro_fnc()
+
+
+/** @} defgroup group_net_basic_types */
+
+
+
/**
- * @brief Definitions used with IP4_SETTINGS::vlan_cfg
+ * @brief The maximum length of an interface name
*
- * @note IP4_SETTINGS::vlan_cfg contains a combination of
- * a VLAN ID number plus a VLAN priority code.
+ * We use an extra name here for the Meinberg-specific structures
+ * to avoid a name clash with system definitions, e.g. Linux systems
+ * define IFNAMSIZ usually as 16 in linux/if.h.
*/
+#define MBG_IFNAMSIZ 16
+
+
+/**
+ * @brief Hardware type for identification of physical interfaces
+ *
+ * Use own definition for use under Windows,
+ * original ARPHRD_ETHER comes from linux/if_arp.h
+ */
+#define MBG_ARPHRD_ETHER 1
+
+
+/**
+ * @defgroup group_vlan_cfg Definitions used with VLAN configuration
+ *
+ * @{ */
+
+/**
+ * @brief VLAN configuration
+ *
+ * @note This is a combination of a VLAN ID number plus a VLAN priority code.
+ */
+typedef uint16_t MBG_VLAN_CFG;
+
+#define _mbg_swab_mbg_vlan_cfg( _p ) _mbg_swab16( _p )
+
#define VLAN_ID_BITS 12 ///< number of bits to hold the ID
#define N_VLAN_ID ( 1 << VLAN_ID_BITS ) ///< number of ID values
#define MIN_VLAN_ID 0 ///< minimum ID value
@@ -5529,7 +11494,7 @@ typedef struct
#define MAX_VLAN_PRIORITY ( N_VLAN_PRIORITY - 1 ) ///< maximum priority
// vlan_priority = ( vlan_cfg >> VLAN_PRIORITY_SHIFT ) & VLAN_PRIORITY_MSK
-#define VLAN_PRIORITY_SHIFT ( ( 8 * sizeof( uint16_t ) ) - VLAN_PRIORITY_BITS )
+#define VLAN_PRIORITY_SHIFT ( ( 8 * sizeof( MBG_VLAN_CFG ) ) - VLAN_PRIORITY_BITS )
#define VLAN_PRIORITY_MSK ( ( 1 << VLAN_PRIORITY_BITS ) - 1 )
/**
@@ -5539,142 +11504,1406 @@ typedef struct
#define _decode_vlan_priority( _cfg ) ( ( (_cfg) >> VLAN_PRIORITY_SHIFT ) & VLAN_PRIORITY_MSK )
#define _encode_vlan_cfg( _id, _prty ) ( ( (_id) << VLAN_ID_SHIFT ) | ( (_prty) << VLAN_PRIORITY_SHIFT ) )
+/** @} defgroup group_vlan_cfg */
-#if 0 //##++ currently not used
-/* Misc configuration */
+/**
+ * @defgroup group_ip4_cfg Simple IPv4-only configuration or status
+ *
+ * This is only supported if the flag ::GPS_HAS_LAN_IP4 is set
+ * in ::RECEIVER_INFO::features.
+ * @see @ref group_ext_net_cfg Extended network configuration and status
+ *
+ * @{ */
+
+/**
+ * @brief Settings of an IPv4-only network interface
+ */
typedef struct
{
- uint16_t id; /* service ID, see below */
- uint16_t index; /* used if several same svcs must be cfg'd, e.g. DNS */
- char host[50]; /* see below */
+ IP4_ADDR ip_addr; ///< the IP address
+ IP4_ADDR netmask; ///< the network mask
+ IP4_ADDR broad_addr; ///< the broadcast address
+ IP4_ADDR gateway; ///< the default gateway
+ uint16_t flags; ///< see ::MBG_IP4_FLAG_MASKS
+ MBG_VLAN_CFG vlan_cfg; ///< VLAN configuration
-} IP_CFG;
+} IP4_SETTINGS;
+#define _mbg_swab_ip4_settings( _p ) \
+do \
+{ \
+ _mbg_swab_ip4_addr( &(_p)->ip_addr ); \
+ _mbg_swab_ip4_addr( &(_p)->netmask ); \
+ _mbg_swab_ip4_addr( &(_p)->broad_addr ); \
+ _mbg_swab_ip4_addr( &(_p)->gateway ); \
+ _mbg_swab16( &(_p)->flags ); \
+ _mbg_swab_mbg_vlan_cfg( &(_p)->vlan_cfg ); \
+} while ( 0 )
-/* Description of a service running on a device */
+/**
+ * @brief Simple LAN interface information
+ *
+ * This structure can be retrieved from a device
+ * to check the device's capabilities.
+ *
+ * It is only supported if the flag ::GPS_HAS_LAN_IP4 is set
+ * in ::RECEIVER_INFO::features.
+ *
+ * @see @ref group_ext_net_cfg Extended network configuration and status
+ */
typedef struct
{
- uint16_t id; /* service ID, see below */
- uint16_t socket; /* the socket on which the service is listening */
- uint32_t flags; /* see below */
+ uint16_t type; ///< type of LAN interface, see ::LAN_IF_TYPES
+ MBG_MAC_ADDR mac_addr; ///< MAC address
+ uint16_t ver_code; ///< version number (hex)
+ char ver_str[GPS_ID_STR_SIZE]; ///< version string
+ char sernum[GPS_ID_STR_SIZE]; ///< serial number
+ uint32_t rsvd_0; ///< reserved, currently always 0
+ uint16_t flags; ///< see ::MBG_IP4_FLAG_MASKS
+ uint16_t rsvd_1; ///< reserved, currently always 0
-} IP_SERVICE;
+} LAN_IF_INFO;
-#endif // 0
+#define _mbg_swab_lan_if_info( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->type ); \
+ _mbg_swab16( &(_p)->ver_code ); \
+ _mbg_swab32( &(_p)->rsvd_0 ); \
+ _mbg_swab16( &(_p)->flags ); \
+ _mbg_swab16( &(_p)->rsvd_1 ); \
+} while ( 0 )
+/**
+ * @brief Codes used with ::LAN_IF_INFO::type
+ */
+enum LAN_IF_TYPES
+{
+ LAN_IF_TYPE_XPORT, ///< LAN interface on an XPORT, superseded by RSC devices
+ LAN_IF_TYPE_PTP, ///< LAN interface is a special PTP interface
+ LAN_IF_TYPE_RSC, ///< RSC device, supersedes XPORT
+ N_LAN_IF_TYPE ///< number of defined LAN interface types
+};
-/** @brief The number of bits used for an IPv6 address */
-#define IP6_ADDR_BITS 128
-/** @brief The number of bytes used for an IPv6 address */
-#define IP6_ADDR_BYTE ( IP6_ADDR_BITS / 8 ) // == 16
+/**
+ * @brief Enumeration of flag bits used with ::IP4_SETTINGS::flags and ::LAN_IF_INFO::flags
+ *
+ * @see ::MBG_IP4_FLAG_MASKS
+ */
+enum MBG_IP4_FLAG_BITS
+{
+ /// In ::LAN_IF_INFO::flags this reports if DHCP is supported by the device.
+ /// If supported then it can also be used with ::IP4_SETTINGS::flags to enable
+ /// or disable DHCP for the network interface.
+ IP4_BIT_DHCP,
+
+ /// Only used with ::IP4_SETTINGS::flags. Set if port link has been established.
+ IP4_BIT_LINK,
+
+ /// In ::LAN_IF_INFO::flags this reports if VLAN is supported by the device.
+ /// If supported then it can also be used with ::IP4_SETTINGS::flags to enable
+ /// or disable VLAN for the network interface.
+ IP4_BIT_VLAN,
+
+ N_IP4_BIT ///< number of defined flag bits
+};
+
/**
- * @brief An IPv6 address
+ * @brief Bit masks used with ::IP4_SETTINGS::flags and ::LAN_IF_INFO::flags
+ *
+ * @see ::MBG_IP4_FLAG_BITS
+ */
+enum MBG_IP4_FLAG_MASKS
+{
+ IP4_MSK_DHCP = ( 1UL << IP4_BIT_DHCP ), ///< see ::IP4_BIT_DHCP
+ IP4_MSK_LINK = ( 1UL << IP4_BIT_LINK ), ///< see ::IP4_BIT_LINK
+ IP4_MSK_VLAN = ( 1UL << IP4_BIT_VLAN ), ///< see ::IP4_BIT_VLAN
+};
+
+/** @} defgroup group_ip4_cfg */
+
+
+
+/**
+ * @defgroup group_ext_net_cfg_types Types used for extended network configuration and status
+ *
+ * @{ */
+
+/**
+ * @brief Enumeration of types used with ::MBG_IP_ADDR::type
+ */
+enum MBG_IP_ADDR_TYPES
+{
+ MBG_IP_ADDR_TYPE_UNKNOWN,
+ MBG_IP_ADDR_TYPE_IP4,
+ MBG_IP_ADDR_TYPE_IP6,
+ N_MBG_IP_ADDR_TYPES
+};
+
+/*
+ * Default initializers for English mode string names. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_IP_ADDR_TYPE_STR_ENG_UNKNOWN "unknown"
+#define MBG_IP_ADDR_TYPE_STR_ENG_IP4 "IPv4"
+#define MBG_IP_ADDR_TYPE_STR_ENG_IP6 "IPv6"
+
+#define MBG_IP_ADDR_TYPE_NAMES_ENG \
+{ \
+ MBG_IP_ADDR_TYPE_STR_ENG_UNKNOWN, \
+ MBG_IP_ADDR_TYPE_STR_ENG_IP4, \
+ MBG_IP_ADDR_TYPE_STR_ENG_IP6 \
+}
+
+
+/**
+ * @brief Feature flag bits used to define ::MBG_NET_GLB_CFG_INFO_MASKS
+ *
+ * @see ::MBG_NET_GLB_CFG_INFO_MASKS
+ */
+enum MBG_NET_GLB_CFG_INFO_FLAGS
+{
+ MBG_NET_GLB_SUPP_STAGE_2, ///< Supports commands which have been added in stage 2
+ MBG_NET_GLB_SUPP_BONDING, ///< Supports bonding
+ N_MBG_NET_GLB_INFO_FLAGS
+};
+
+
+/**
+ * @brief Flag masks used with ::MBG_NET_GLB_CFG_INFO::feat_flags
+ *
+ * @see ::MBG_NET_GLB_CFG_INFO_FLAGS
+ */
+enum MBG_NET_GLB_CFG_INFO_MASKS
+{
+ MBG_NET_GLB_SUPP_STAGE_2_MASK = (1UL << MBG_NET_GLB_SUPP_STAGE_2), ///< see ::MBG_NET_GLB_SUPP_STAGE_2
+ MBG_NET_GLB_SUPP_BONDING_MASK = (1UL << MBG_NET_GLB_SUPP_BONDING) ///< see ::MBG_NET_GLB_SUPP_BONDING
+};
+
+
+
+/**
+ * @brief Network interface link speed mode enumeration
+ *
+ * @see @ref MBG_NET_INTF_LINK_SPEED_MODE_MASKS
+ */
+enum MBG_NET_INTF_LINK_SPEED_MODES
+{
+ MBG_NET_INTF_LINK_SPEED_MODE_UNKNOWN, ///< Unknown speed mode
+ MBG_NET_INTF_LINK_SPEED_MODE_10_T_HALF, ///< 10baseT Half Duplex (10 MBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_10_T_FULL, ///< 10baseT Full Duplex (10 MBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_100_T_HALF, ///< 100baseT Half Duplex (100 MBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_100_T_FULL, ///< 100baseT Full Duplex (100 MBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_1000_T_HALF, ///< 1000baseT Half Duplex (1 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_1000_T_FULL, ///< 1000baseT Full Duplex (1 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_1000_KX_FULL, ///< 1000baseKX Full Duplex (1 GBit/s)
+
+ MBG_NET_INTF_LINK_SPEED_MODE_2500_X_FULL, ///< 2500baseX Full Duplex (2.5 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_10000_T_FULL, ///< 10000baseT Full Duplex (10 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_10000_KX4_FULL, ///< 10000baseKX4 Full Duplex (10 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_10000_KR_FULL, ///< 10000baseKR Full Duplex (10 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_10000_R_FEC, ///< 10000baseR FEC (forward error correction) (10 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_20000_MLD2_FULL, ///< 20000baseMLD2 Full Duplex (20 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_20000_KR2_FULL, ///< 20000baseKR2 Full Duplex (20 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_40000_KR4_FULL, ///< 40000baseKR4 Full Duplex (40 GBit/s)
+
+ MBG_NET_INTF_LINK_SPEED_MODE_40000_CR4_FULL, ///< 40000baseCR4 Full Duplex (40 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_40000_SR4_FULL, ///< 40000baseSR4 Full Duplex (40 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_40000_LR4_FULL, ///< 40000baseLR4 Full Duplex (40 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_56000_KR4_FULL, ///< 56000baseKR4 Full Duplex (56 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_56000_CR4_FULL, ///< 56000baseCR4 Full Duplex (56 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_56000_SR4_FULL, ///< 56000baseSR4 Full Duplex (56 GBit/s)
+ MBG_NET_INTF_LINK_SPEED_MODE_56000_LR4_FULL, ///< 56000baseLR4 Full Duplex (56 GBit/s)
+
+ N_MBG_NET_INTF_LINK_SPEED_MODES
+};
+
+
+
+/**
+ * @brief Network interface link speed mode masks
+ *
+ * @see ::MBG_NET_INTF_LINK_SPEED_MODES
+ *
+ * @anchor MBG_NET_INTF_LINK_SPEED_MODE_MASKS @{ */
+
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_UNKNOWN ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_UNKNOWN ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_UNKNOWN
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_HALF ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_10_T_HALF ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_10_T_HALF
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_10_T_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_10_T_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_10_T_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_HALF ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_100_T_HALF ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_100_T_HALF
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_100_T_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_100_T_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_100_T_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_1000_T_HALF ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_1000_T_HALF ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_1000_T_HALF
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_1000_T_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_1000_T_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_1000_T_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_1000_KX_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_1000_KX_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_1000_KX_FULL
+
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_2500_X_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_2500_X_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_2500_X_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_10000_T_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_10000_T_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_10000_T_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_10000_KX4_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_10000_KX4_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_10000_KX4_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_10000_KR_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_10000_KR_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_10000_KR_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_10000_R_FEC ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_10000_R_FEC ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_10000_R_FEC
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_20000_MLD2_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_20000_MLD2_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_20000_MLD2_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_20000_KR2_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_20000_KR2_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_20000_KR2_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_40000_KR4_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_40000_KR4_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_40000_KR4_FULL
+
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_40000_CR4_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_40000_CR4_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_40000_CR4_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_40000_SR4_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_40000_SR4_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_40000_SR4_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_40000_LR4_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_40000_LR4_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_40000_LR4_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_56000_KR4_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_56000_KR4_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_56000_KR4_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_56000_CR4_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_56000_CR4_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_56000_CR4_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_56000_SR4_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_56000_SR4_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_56000_SR4_FULL
+#define MBG_NET_INTF_LINK_SPEED_MODE_MASK_56000_LR4_FULL ( 1UL << MBG_NET_INTF_LINK_SPEED_MODE_56000_LR4_FULL ) ///< see ::MBG_NET_INTF_LINK_SPEED_MODE_56000_LR4_FULL
+
+/** @} anchor MBG_NET_INTF_LINK_SPEED_MODE_MASKS */
+
+
+
+/**
+ * @brief Network interface link speeds [Mb/s]
+ *
+ * @see @ref MBG_NET_INTF_LINK_SPEED_MODE_MASKS
+ */
+enum MBG_NET_INTF_LINK_SPEEDS
+{
+ MBG_NET_INTF_LINK_SPEED_UNKNOWN = 0UL,
+ MBG_NET_INTF_LINK_SPEED_10 = 10UL,
+ MBG_NET_INTF_LINK_SPEED_100 = 100UL,
+ MBG_NET_INTF_LINK_SPEED_1000 = 1000UL,
+ MBG_NET_INTF_LINK_SPEED_2500 = 2500UL,
+ MBG_NET_INTF_LINK_SPEED_10000 = 10000UL,
+ MBG_NET_INTF_LINK_SPEED_20000 = 20000UL,
+ MBG_NET_INTF_LINK_SPEED_40000 = 40000UL,
+ MBG_NET_INTF_LINK_SPEED_56000 = 56000UL
+};
+
+
+
+/**
+ * @brief Network interface link port types
+ *
+ * @see ::MBG_NET_INTF_LINK_PORT_TYPE_MASKS
+ */
+enum MBG_NET_INTF_LINK_PORT_TYPES
+{
+ MBG_NET_INTF_LINK_PORT_TYPE_UNKNOWN, ///< Unknown port type
+ MBG_NET_INTF_LINK_PORT_TYPE_TP, ///< Twisted Pair (TP) copper cable
+ MBG_NET_INTF_LINK_PORT_TYPE_FIBRE, ///< Fibre Optic (FO) cable
+ MBG_NET_INTF_LINK_PORT_TYPE_BNC, ///< Coaxial BNC cable
+ MBG_NET_INTF_LINK_PORT_TYPE_AUI, ///< Attachment Unit Interface (AUI), externel transceiver
+ MBG_NET_INTF_LINK_PORT_TYPE_MII, ///< Media Independent Interface (MII), external receiver
+ MBG_NET_INTF_LINK_PORT_TYPE_DA, ///< Direct attach SFP+ connection
+ N_MBG_NET_INTF_LINK_PORT_TYPES
+};
+
+
+
+/**
+ * @brief Network interface link port masks
+ *
+ * @see ::MBG_NET_INTF_LINK_PORT_TYPES
+ */
+enum MBG_NET_INTF_LINK_PORT_TYPE_MASKS
+{
+ MBG_NET_INTF_LINK_PORT_TYPE_MASK_UNKNOWN = ( 1UL << MBG_NET_INTF_LINK_PORT_TYPE_UNKNOWN ), ///< see ::MBG_NET_INTF_LINK_PORT_TYPE_UNKNOWN
+ MBG_NET_INTF_LINK_PORT_TYPE_MASK_TP = ( 1UL << MBG_NET_INTF_LINK_PORT_TYPE_TP ), ///< see ::MBG_NET_INTF_LINK_PORT_TYPE_TP
+ MBG_NET_INTF_LINK_PORT_TYPE_MASK_FIBRE = ( 1UL << MBG_NET_INTF_LINK_PORT_TYPE_FIBRE ), ///< see ::MBG_NET_INTF_LINK_PORT_TYPE_FIBRE
+ MBG_NET_INTF_LINK_PORT_TYPE_MASK_BNC = ( 1UL << MBG_NET_INTF_LINK_PORT_TYPE_BNC ), ///< see ::MBG_NET_INTF_LINK_PORT_TYPE_BNC
+ MBG_NET_INTF_LINK_PORT_TYPE_MASK_AUI = ( 1UL << MBG_NET_INTF_LINK_PORT_TYPE_AUI ), ///< see ::MBG_NET_INTF_LINK_PORT_TYPE_AUI
+ MBG_NET_INTF_LINK_PORT_TYPE_MASK_MII = ( 1UL << MBG_NET_INTF_LINK_PORT_TYPE_MII ), ///< see ::MBG_NET_INTF_LINK_PORT_TYPE_MII
+ MBG_NET_INTF_LINK_PORT_TYPE_MASK_DA = ( 1UL << MBG_NET_INTF_LINK_PORT_TYPE_DA ) ///< see ::MBG_NET_INTF_LINK_PORT_TYPE_DA
+};
+
+
+
+/**
+ * @brief Initializers for network interface link port type long strings
+ *
+ * @see ::MBG_NET_INTF_LINK_PORT_TYPE
+ */
+#define MBG_NET_INTF_LINK_PORT_TYPE_LONG_STRS \
+{ \
+ "Unknown", \
+ "Twisted Pair", \
+ "Fibre Optic", \
+ "Coaxial BNC", \
+ "Attachment Unit Interface", \
+ "Media Independent Interface", \
+ "Direct Attach SFP+" \
+}
+
+
+/**
+ * @brief Initializers for network interface link port type short strings
+ *
+ * @see ::MBG_NET_INTF_LINK_PORT_TYPE
+ */
+#define MBG_NET_INTF_LINK_PORT_TYPE_SHORT_STRS \
+{ \
+ "Unknown", \
+ "TP", \
+ "FO", \
+ "BNC", \
+ "AUI", \
+ "MII", \
+ "DA" \
+}
+
+
+
+/**
+ * @brief Network interface link state bits
+ *
+ * @see @ref MBG_NET_INTF_LINK_STATE_MASKS
+ *
+ * @note See official Linux kernel documentation
+ * https://www.kernel.org/doc/Documentation/networking/operstates.txt
+ * for states below and explanations. Windows supports this in nearly the same way
+ * using similar names struct IP_ADAPTER_ADDRESSES which is explained at
+ * http://msdn.microsoft.com/en-us/library/windows/desktop/aa366058%28v=vs.85%29.aspx
+ */
+enum MBG_NET_INTF_LINK_STATE_BITS
+{
+ MBG_NET_INTF_LINK_STATE_BIT_UP,
+ MBG_NET_INTF_LINK_STATE_BIT_RUNNING,
+ MBG_NET_INTF_LINK_STATE_BIT_LOWER_UP,
+ MBG_NET_INTF_LINK_STATE_BIT_DORMANT,
+ MBG_NET_INTF_LINK_STATE_BIT_BROADCAST,
+ MBG_NET_INTF_LINK_STATE_BIT_MULTICAST,
+ MBG_NET_INTF_LINK_STATE_BIT_ALL_MULTI,
+ MBG_NET_INTF_LINK_STATE_BIT_DEBUG,
+
+ MBG_NET_INTF_LINK_STATE_BIT_LOOPBACK,
+ MBG_NET_INTF_LINK_STATE_BIT_POINT_TO_POINT,
+ MBG_NET_INTF_LINK_STATE_BIT_NO_ARP,
+ MBG_NET_INTF_LINK_STATE_BIT_PROMISC,
+ MBG_NET_INTF_LINK_STATE_BIT_MASTER,
+ MBG_NET_INTF_LINK_STATE_BIT_SLAVE,
+ MBG_NET_INTF_LINK_STATE_BIT_PORT_SEL,
+ MBG_NET_INTF_LINK_STATE_BIT_AUTO_MEDIA,
+
+ MBG_NET_INTF_LINK_STATE_BIT_ECHO,
+ MBG_NET_INTF_LINK_STATE_BIT_DYNAMIC,
+ MBG_NET_INTF_LINK_STATE_BIT_NO_TRAILERS,
+
+ N_MBG_NET_INTF_LINK_STATE_BITS
+};
+
+
+
+/**
+ * @brief Network interface link state masks
+ *
+ * @see ::MBG_NET_INTF_LINK_STATE_BITS (reclined to Linux' if.h, Windows is similiar)
+ *
+ * @anchor MBG_NET_INTF_LINK_STATE_MASKS @{ */
+
+#define MBG_NET_INTF_LINK_STATE_MASK_UP ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_UP ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_UP
+#define MBG_NET_INTF_LINK_STATE_MASK_RUNNING ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_RUNNING ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_RUNNING
+#define MBG_NET_INTF_LINK_STATE_MASK_LOWER_UP ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_LOWER_UP ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_LOWER_UP
+#define MBG_NET_INTF_LINK_STATE_MASK_DORMANT ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_DORMANT ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_DORMANT
+#define MBG_NET_INTF_LINK_STATE_MASK_BROADCAST ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_BROADCAST ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_BROADCAST
+#define MBG_NET_INTF_LINK_STATE_MASK_MULTICAST ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_MULTICAST ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_MULTICAST
+#define MBG_NET_INTF_LINK_STATE_MASK_ALL_MULTI ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_ALL_MULTI ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_ALL_MULTI
+#define MBG_NET_INTF_LINK_STATE_MASK_DEBUG ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_DEBUG ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_DEBUG
+
+#define MBG_NET_INTF_LINK_STATE_MASK_LOOPBACK ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_LOOPBACK ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_LOOPBACK
+#define MBG_NET_INTF_LINK_STATE_MASK_POINT_TO_POINT ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_POINT_TO_POINT ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_POINT_TO_POINT
+#define MBG_NET_INTF_LINK_STATE_MASK_NO_ARP ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_NO_ARP ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_NO_ARP
+#define MBG_NET_INTF_LINK_STATE_MASK_PROMISC ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_PROMISC ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_PROMISC
+#define MBG_NET_INTF_LINK_STATE_MASK_MASTER ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_MASTER ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_MASTER
+#define MBG_NET_INTF_LINK_STATE_MASK_SLAVE ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_SLAVE ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_SLAVE
+#define MBG_NET_INTF_LINK_STATE_MASK_PORT_SEL ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_PORT_SEL ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_PORT_SEL
+#define MBG_NET_INTF_LINK_STATE_MASK_AUTO_MEDIA ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_AUTO_MEDIA ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_AUTO_MEDIA
+
+#define MBG_NET_INTF_LINK_STATE_MASK_ECHO ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_ECHO ) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_ECHO
+#define MBG_NET_INTF_LINK_STATE_MASK_DYNAMIC ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_DYNAMIC) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_DYNAMIC
+#define MBG_NET_INTF_LINK_STATE_MASK_NO_TRAILERS ( 1UL << MBG_NET_INTF_LINK_STATE_BIT_NO_TRAILERS) ///< see ::MBG_NET_INTF_LINK_STATE_BIT_NO_TRAILERS
+
+/** @} anchor MBG_NET_INTF_LINK_STATE_MASKS */
+
+
+
+/**
+ * @brief Network interface link option bits
+ *
+ * @see ::MBG_NET_INTF_LINK_OPT_MASKS
+ */
+enum MBG_NET_INTF_LINK_OPTS
+{
+ MBG_NET_INTF_LINK_OPT_CAN_SET_MAC,
+ MBG_NET_INTF_LINK_OPT_CAN_SYNCE_IN,
+ MBG_NET_INTF_LINK_OPT_CAN_SYNCE_OUT,
+ MBG_NET_INTF_LINK_OPT_CAN_AUTONEG,
+ MBG_NET_INTF_LINK_OPT_CAN_NTP_HW_TS,
+ MBG_NET_INTF_LINK_OPT_CAN_PTP_HW_TS,
+ N_MBG_NET_INTF_LINK_OPTS
+};
+
+
+
+/**
+ * @brief Network interface link option masks
+ *
+ * @see ::MBG_NET_INTF_LINK_OPTS
+ */
+enum MBG_NET_INTF_LINK_OPT_MASKS
+{
+ MBG_NET_INTF_LINK_OPT_MASK_CAN_SET_MAC = ( 1UL << MBG_NET_INTF_LINK_OPT_CAN_SET_MAC ), ///< see ::MBG_NET_INTF_LINK_OPT_CAN_SET_MAC
+ MBG_NET_INTF_LINK_OPT_MASK_CAN_SYNCE_IN = ( 1UL << MBG_NET_INTF_LINK_OPT_CAN_SYNCE_IN ), ///< see ::MBG_NET_INTF_LINK_OPT_CAN_SYNCE_IN
+ MBG_NET_INTF_LINK_OPT_MASK_CAN_SYNCE_OUT = ( 1UL << MBG_NET_INTF_LINK_OPT_CAN_SYNCE_OUT ), ///< see ::MBG_NET_INTF_LINK_OPT_CAN_SYNCE_OUT
+ MBG_NET_INTF_LINK_OPT_MASK_CAN_AUTONEG = ( 1UL << MBG_NET_INTF_LINK_OPT_CAN_AUTONEG ), ///< see ::MBG_NET_INTF_LINK_OPT_CAN_AUTONEG
+ MBG_NET_INTF_LINK_OPT_MASK_CAN_NTP_HW_TS = ( 1UL << MBG_NET_INTF_LINK_OPT_CAN_NTP_HW_TS ), ///< see ::MBG_NET_INTF_LINK_OPT_CAN_NTP_HW_TS
+ MBG_NET_INTF_LINK_OPT_MASK_CAN_PTP_HW_TS = ( 1UL << MBG_NET_INTF_LINK_OPT_CAN_PTP_HW_TS ) ///< see ::MBG_NET_INTF_LINK_OPT_CAN_PTP_HW_TS
+};
+
+
+
+/**
+ * @brief Network interface link bonding mode
+ *
+ * Used with ::MBG_NET_INTF_LINK_SETTINGS::bond_mode
+ *
+ * @note if_bonding.h contains bonding modes under Linux, found no hint under Windows.
+ * BUT: Something similiar (concerning naming) can be configured under Windows
+ * via GUI in device manager, if supported.
+ */
+enum MBG_NET_INTF_LINK_BOND_MODES
+{
+ MBG_NET_INTF_LINK_BOND_MODE_ROUNDROBIN,
+ MBG_NET_INTF_LINK_BOND_MODE_ACTIVEBACKUP,
+ MBG_NET_INTF_LINK_BOND_MODE_XOR,
+ MBG_NET_INTF_LINK_BOND_MODE_BROADCAST,
+ MBG_NET_INTF_LINK_BOND_MODE_8023AD,
+ MBG_NET_INTF_LINK_BOND_MODE_TLB,
+ MBG_NET_INTF_LINK_BOND_MODE_ALB,
+ N_MBG_NET_INTF_LINK_BOND_MODES
+};
+
+
+
+/**
+ * @brief Network interface link bonding mode masks
+ *
+ * @see ::MBG_NET_INTF_LINK_BOND_MODES
+ */
+enum MBG_NET_INTF_LINK_BOND_MODE_MASKS
+{
+ MBG_NET_INTF_LINK_BOND_MODE_MASK_ROUNDROBIN = ( 1UL << MBG_NET_INTF_LINK_BOND_MODE_ROUNDROBIN ), ///< see ::MBG_NET_INTF_LINK_BOND_MODE_ROUNDROBIN
+ MBG_NET_INTF_LINK_BOND_MODE_MASK_ACTIVEBACKUP = ( 1UL << MBG_NET_INTF_LINK_BOND_MODE_ACTIVEBACKUP ), ///< see ::MBG_NET_INTF_LINK_BOND_MODE_ACTIVEBACKUP
+ MBG_NET_INTF_LINK_BOND_MODE_MASK_XOR = ( 1UL << MBG_NET_INTF_LINK_BOND_MODE_XOR ), ///< see ::MBG_NET_INTF_LINK_BOND_MODE_XOR
+ MBG_NET_INTF_LINK_BOND_MODE_MASK_BROADCAST = ( 1UL << MBG_NET_INTF_LINK_BOND_MODE_BROADCAST ), ///< see ::MBG_NET_INTF_LINK_BOND_MODE_BROADCAST
+ MBG_NET_INTF_LINK_BOND_MODE_MASK_8023AD = ( 1UL << MBG_NET_INTF_LINK_BOND_MODE_8023AD ), ///< see ::MBG_NET_INTF_LINK_BOND_MODE_8023AD
+ MBG_NET_INTF_LINK_BOND_MODE_MASK_TLB = ( 1UL << MBG_NET_INTF_LINK_BOND_MODE_TLB ), ///< see ::MBG_NET_INTF_LINK_BOND_MODE_TLB
+ MBG_NET_INTF_LINK_BOND_MODE_MASK_ALB = ( 1UL << MBG_NET_INTF_LINK_BOND_MODE_ALB ), ///< see ::MBG_NET_INTF_LINK_BOND_MODE_ALB
+};
+
+
+
+/**
+ * @brief Network interface link bonding mode name strings
+ *
+ * @see ::MBG_NET_INTF_LINK_BOND_MODES
+ */
+#define MBG_NET_INTF_LINK_BOND_MODE_STRS \
+{ \
+ "Round Robin", \
+ "Active Backup", \
+ "XOR", \
+ "Broadcast", \
+ "802.3ad (LACP)", \
+ "TLB", \
+ "ALB" \
+}
+
+
+
+/**
+ * @brief Network interface link bonding states
+ *
+ * Used with ::MBG_NET_INTF_LINK_SETTINGS::bond_state
+ */
+enum MBG_NET_INTF_LINK_BOND_STATES
+{
+ MBG_NET_INTF_LINK_BOND_STATE_ACTIVE,
+ MBG_NET_INTF_LINK_BOND_STATE_BACKUP,
+ N_MBG_NET_INTF_LINK_BOND_STATES
+};
+
+
+/**
+ * @brief Network interface link type bits
+ *
+ * Used with ::MBG_NET_INTF_LINK_SETTINGS::type
+ *
+ * @see ::MBG_NET_INTF_LINK_TYPE_MASKS
+ */
+enum MBG_NET_INTF_LINK_TYPES
+{
+ MBG_NET_INTF_LINK_TYPE_PHYS, ///< Real physical network interface
+ MBG_NET_INTF_LINK_TYPE_VLAN, ///< VLAN interface, assigned to physical interface
+ MBG_NET_INTF_LINK_TYPE_BOND, ///< Bonding interface, which acts as bonding master
+ N_MBG_NET_INTF_LINK_TYPE_BITS
+};
+
+
+/**
+ * @brief Network interface link type masks
+ *
+ * Used with ::MBG_NET_INTF_LINK_INFO::supp_types
+ *
+ * @see ::MBG_NET_INTF_LINK_TYPES
+ */
+enum MBG_NET_INTF_LINK_TYPE_MASKS
+{
+ MBG_NET_INTF_LINK_TYPE_MASK_PHYS = ( 1UL << MBG_NET_INTF_LINK_TYPE_PHYS ), ///< see ::MBG_NET_INTF_LINK_TYPE_PHYS
+ MBG_NET_INTF_LINK_TYPE_MASK_VLAN = ( 1UL << MBG_NET_INTF_LINK_TYPE_VLAN ), ///< see ::MBG_NET_INTF_LINK_TYPE_VLAN
+ MBG_NET_INTF_LINK_TYPE_MASK_BOND = ( 1UL << MBG_NET_INTF_LINK_TYPE_BOND ) ///< see ::MBG_NET_INTF_LINK_TYPE_BOND
+};
+
+
+/**
+ * @brief Network interface address bits
+ *
+ * @see ::MBG_NET_INTF_ADDR_MASKS
+ *
+ * Used with ::MBG_NET_INTF_ADDR_INFO::supp_flags and ::MBG_NET_INTF_ADDR_SETTINGS::flags
+ */
+enum MBG_NET_INTF_ADDR_BITS
+{
+ MBG_NET_INTF_ADDR_BIT_DHCP4, ///< Address has been automatically assigned by DHCP via IPv4
+ MBG_NET_INTF_ADDR_BIT_DHCP6, ///< Address has been automatically assigned by DHCP via IPv6
+ N_MBG_NET_INTF_ADDR_FLAGS
+};
+
+
+
+/**
+ * @brief Network interface address masks
+ *
+ * @see ::MBG_NET_INTF_ADDR_BITS
+ */
+enum MBG_NET_INTF_ADDR_MASKS
+{
+ MBG_NET_INTF_ADDR_MASK_DHCP4 = ( 1UL << MBG_NET_INTF_ADDR_BIT_DHCP4 ), ///< see ::MBG_NET_INTF_ADDR_BIT_DHCP4
+ MBG_NET_INTF_ADDR_MASK_DHCP6 = ( 1UL << MBG_NET_INTF_ADDR_BIT_DHCP6 ) ///< see ::MBG_NET_INTF_ADDR_BIT_DHCP6
+};
+
+
+enum MBG_NET_INTF_ROUTE_TYPES
+{
+ MBG_NET_INTF_ROUTE_TYPE_UNKNOWN,
+ MBG_NET_INTF_ROUTE_TYPE_DEFAULT_GATEWAY,
+ MBG_NET_INTF_ROUTE_TYPE_DEST_GATEWAY,
+ MBG_NET_INTF_ROUTE_TYPE_DEST_ADDR,
+ N_MBG_NET_INTF_ROUTE_TYPES
+};
+
+/** @} defgroup group_ext_net_cfg_types */
+
+
+
+/**
+ * @defgroup group_ext_net_cfg Extended network configuration and status
+ *
+ * This is only supported if the flag ::GPS_HAS_NET_CFG is set
+ * in ::RECEIVER_INFO::features.
+ *
+ * @{ */
+
+/**
+ * @brief Global network configuration settings
*/
typedef struct
{
- uint8_t b[IP6_ADDR_BYTE]; ///< bytes holding the address bits, b[0] == LSBs
- uint8_t cidr_net_mask; ///< number of CIDR net mask bits, 0..IP6_ADDR_BITS
- uint8_t reserved; ///< not yet used, always 0
- uint16_t flags; ///< not yet used, always 0
-} IP6_ADDR;
+ MBG_HOSTNAME hostname; ///< hostname, eventually FQDN including domain name
+ uint8_t num_intf_link; ///< number of detected/configured physical network interfaces (links), see ::MBG_NET_INTF_LINK_INFO_IDX
+ uint8_t num_intf_addr; ///< number of configured interface addresses, see ::MBG_NET_INTF_ADDR_INFO_IDX
+ uint8_t num_dns_srvr; ///< number of configured DNS servers, see ::MBG_IP_ADDR_IDX
+ uint8_t num_dns_srch_dom; ///< number of configured DNS search domains, see ::MBG_NET_NAME_IDX
+ uint8_t num_intf_route; ///< number of configured interface routes, see ::MBG_NET_INTF_ROUTE_INFO_IDX
+ uint8_t reserved; ///< currently reserved, always 0
+ uint16_t flags; ///< currently reserved, always 0
-/** @brief The max number of chars required for an IPv6 address string */
-#define MAX_IP6_ADDR_STR_LEN 43 ///< e.g. 2001:0db8:85a3:08d3:1319:8a2e:0370:7344/128
+} MBG_NET_GLB_CFG_SETTINGS;
-/** @brief Buffer size required to store an IPv6 address string */
-#define IP6_ADDR_STR_SIZE ( MAX_IP6_ADDR_STR_LEN + 1 ) ///< MAX_IP6_ADDR_STR_LEN + terminating 0
+#define _mbg_swab_net_glb_cfg_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
-/** @brief A buffer for an IPv6 address string */
-typedef char IP6_ADDR_STR[IP6_ADDR_STR_SIZE];
+
+/**
+ * @brief Global current network settings and supported features
+ */
+typedef struct
+{
+ MBG_NET_GLB_CFG_SETTINGS glb_settings;
+ uint16_t n_supp_intf_link; ///< max. number of supported physical network interfaces (links), see ::MBG_NET_INTF_LINK_SETTINGS_IDX, ::MBG_NET_INTF_LINK_INFO_IDX
+ uint16_t n_supp_intf_addr; ///< max. number of supported interface addresses, see ::MBG_NET_INTF_ADDR_SETTINGS_IDX, ::MBG_NET_INTF_ADDR_INFO_IDX
+ uint16_t n_supp_dns_srvr; ///< max. number of supported DNS server addresses, using ::MBG_IP_ADDR_IDX records
+ uint16_t n_supp_dns_srch_dom; ///< max. number of supported DNS search domain records, using ::MBG_NET_NAME_IDX records
+ uint16_t n_supp_intf_route; ///< max. number of supported interface routes, see ::MBG_NET_INTF_ROUTE_SETTINGS_IDX, ::MBG_NET_INTF_ROUTE_INFO_IDX
+ uint16_t max_hostname_len; ///< max. length of hostname including trailing 0; if set to 0, max. length is 256 (see rfc1123)
+ uint32_t reserved_1; ///< currently reserved, always 0
+ uint32_t reserved_2; ///< currently reserved, always 0
+ uint32_t feat_flags; ///< Feature flags, see ::MBG_NET_GLB_CFG_INFO_MASKS
+ uint32_t flags_2; ///< currently reserved, always 0
+
+} MBG_NET_GLB_CFG_INFO;
+
+#define _mbg_swab_net_glb_cfg_info( _p ) \
+do \
+{ \
+ _mbg_swab_net_glb_cfg_settings( &(_p)->glb_settings ); \
+ _mbg_swab16( &(_p)->n_supp_intf_link ); \
+ _mbg_swab16( &(_p)->n_supp_intf_addr ); \
+ _mbg_swab16( &(_p)->n_supp_dns_srvr ); \
+ _mbg_swab16( &(_p)->n_supp_dns_srch_dom ); \
+ _mbg_swab16( &(_p)->n_supp_intf_route ); \
+ _mbg_swab16( &(_p)->max_hostname_len ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->feat_flags ); \
+ _mbg_swab32( &(_p)->flags_2 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief An IPv4 or IPv6 network address
+ */
+typedef struct
+{
+ uint8_t type; ///< see ::MBG_IP_ADDR_TYPES
+ uint8_t reserved_1; ///< reserved, currently always 0 @todo Do we need this as scope indicator?
+ uint16_t reserved_2; ///< reserved, currently always 0
+
+ union u_addr
+ {
+ IP4_ADDR ip4_addr; ///< IPv4 address if ::MBG_IP_ADDR::type == MBG_IP_ADDR_TYPE_IP4
+ IP6_ADDR ip6_addr; ///< IPv6 address if ::MBG_IP_ADDR::type == MBG_IP_ADDR_TYPE_IP6
+ } u_addr;
+
+} MBG_IP_ADDR;
+
+#define _mbg_swab_ip_addr( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->type ); \
+ _mbg_swab8( &(_p)->reserved_1 ); \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+ \
+ switch ( (_p)->type ) \
+ { \
+ case MBG_IP_ADDR_TYPE_IP4: \
+ _mbg_swab_ip4_addr( &(_p)->u_addr.ip4_addr ); \
+ break; \
+ \
+ case MBG_IP_ADDR_TYPE_IP6: \
+ _mbg_swab_ip6_addr( &(_p)->u_addr.ip6_addr ); \
+ break; \
+ } \
+ \
+} while ( 0 )
/**
- * @brief A structure to holds the MAC address of a LAN interface
+ * @brief An IPv4 or IPv6 network address, plus index
*/
typedef struct
{
- uint8_t b[6];
-} MBG_MAC_ADDR;
+ uint16_t idx;
+ MBG_IP_ADDR addr; ///< network address
+
+} MBG_IP_ADDR_IDX;
+
+#define _mbg_swab_ip_addr_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ip_addr( &(_p)->addr ); \
+} while ( 0 )
+
+
+/**
+ * @brief An IPv4 or IPv6 network address plus UDP or TCP port number
+ */
+typedef struct
+{
+ MBG_IP_ADDR addr; ///< see ::MBG_IP_ADDR
+
+ uint16_t port; ///< UDP or TCP port
+ uint16_t flags; ///< currently always 0
+ //##+++++ TODO should the flags field indicate if the port is UDP and/or TCP?
+
+} MBG_IP_ADDR_PORT;
+
+#define _mbg_swab_ip_addr_port( _p ) \
+do \
+{ \
+ _mbg_swab_ip_addr( &(_p)->addr ); \
+ _mbg_swab16( &(_p)->port ); \
+ _mbg_swab16( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Network host or domain name
+ */
+typedef struct
+{
+ MBG_HOSTNAME name;
+
+} MBG_NET_NAME;
+
+#define _mbg_swab_net_name( _p ) \
+do \
+{ \
+ _mbg_swab_mbg_host_name( &(_p)->name ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Network host or domain name, plus index
+ */
+typedef struct
+{
+ uint16_t idx;
+ MBG_NET_NAME net_name;
+
+} MBG_NET_NAME_IDX;
+
+#define _mbg_swab_net_name_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_net_name( &(_p)->net_name ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Physical network interface link specific settings
+ */
+typedef struct
+{
+ char name[MBG_IFNAMSIZ]; ///< Interface name
+ MBG_MAC_ADDR mac_addr; ///< Physical hardware address
+ MBG_MAC_ADDR broadcast; ///< Physical broadcast address
+
+ uint32_t if_index; ///< Interface index assigned by the kernel
+ uint32_t common_if_index; ///< Common interface index assigned by the lib (associated with the MAC address),
+ ///< Valid if ::MBG_NET_INTF_LINK_SETTINGS::type is ::MBG_NET_INTF_LINK_TYPE_PHYS
+ uint32_t ass_if_index; ///< Interface index of the associated physical interface link,
+ ///< Valid if ::MBG_NET_INTF_LINK_SETTINGS::type is ::MBG_NET_INTF_LINK_TYPE_VLAN
+
+ uint32_t flags; ///< Reserved, currently 0
+ uint32_t states; ///< see @ref MBG_NET_INTF_LINK_STATE_MASKS
+
+ uint32_t hw_type; ///< Hardware type of interface (see linux/if_arp.h, i.e. ARPHRD_ETHER) ::TODO
+ uint32_t mtu; ///< Max. packet size in bytes
+ uint32_t txqlen; ///< Transmission queue length (number of packets)
+ uint32_t speed; ///< Link speed in MBit/s
+
+ uint8_t type; ///< see ::MBG_NET_INTF_LINK_TYPES
+ uint8_t duplex; ///< Duplex mode, half (0) or full (1)
+ uint8_t autoneg; ///< Indicates, whether autonegotiation is enabled or disabled
+ uint8_t port_type; ///< see ::MBG_NET_INTF_LINK_PORT_TYPES
+
+ uint8_t bond_mode; ///< Bonding mode, see ::MBG_NET_INTF_LINK_BOND_MODES
+ ///< Valid if ::MBG_NET_INTF_LINK_STATE_MASK_MASTER is set in ::MBG_NET_INTF_LINK_SETTINGS::states
+ uint8_t bond_state; ///< Status of this interface in the bonding group, see ::MBG_NET_INTF_LINK_BOND_STATES
+ ///< Valid if MBG_NET_INTF_LINK_STATE_MASK_SLAVE is set in ::MBG_NET_INTF_LINK_SETTINGS::states
+ uint16_t bond_idx; ///< Interface index of the bonding master link, see ::MBG_NET_INTF_LINK_SETTINGS::if_index
+ ///< Valid, if MBG_NET_INTF_LINK_STATE_MASK_SLAVE is set in ::MBG_NET_INTF_LINK_SETTINGS::states
+
+ uint16_t vlan_cfg; ///< VLAN configuration options, see ::MBG_VLAN_CFG
+ ///< Valid if ::MBG_NET_INTF_LINK_SETTINGS::type is ::MBG_NET_INTF_LINK_TYPE_VLAN
+ uint16_t reserved_1; ///< Reserved, currently 0
+
+ uint32_t reserved_2; ///< Reserved, currently 0
+ uint32_t reserved_3; ///< Reserved, currently 0
+
+} MBG_NET_INTF_LINK_SETTINGS;
+
+#define _mbg_swab_net_intf_link_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->if_index ); \
+ _mbg_swab32( &(_p)->common_if_index ); \
+ _mbg_swab32( &(_p)->ass_if_index ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab32( &(_p)->states ); \
+ _mbg_swab32( &(_p)->hw_type ); \
+ _mbg_swab32( &(_p)->mtu ); \
+ _mbg_swab32( &(_p)->txqlen ); \
+ _mbg_swab32( &(_p)->speed ); \
+ _mbg_swab16( &(_p)->bond_idx ); \
+ _mbg_swab16( &(_p)->vlan_cfg ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Link (physical interface) specific settings, plus index
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_NET_GLB_CFG_INFO::n_supp_intf_link-1
+ MBG_NET_INTF_LINK_SETTINGS settings;
+
+} MBG_NET_INTF_LINK_SETTINGS_IDX;
+
+#define _mbg_swab_net_intf_link_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_net_intf_link_settings( &(_p)->settings ); \
+} while ( 0 )
/**
- * @brief LAN interface information
+ * @brief Link (physical interface) specific settings, flags and supported features
+ */
+typedef struct
+{
+ MBG_NET_INTF_LINK_SETTINGS link_settings; ///< see ::MBG_NET_INTF_LINK_SETTINGS
+ uint32_t supp_flags; ///< Reserved, currently 0
+ uint32_t supp_states; ///< see @ref MBG_NET_INTF_LINK_STATE_MASKS
+ uint32_t supp_types; ///< see ::MBG_NET_INTF_LINK_TYPE_MASKS
+ uint32_t supp_speed_modes; ///< see @ref MBG_NET_INTF_LINK_SPEED_MODE_MASKS
+ uint32_t supp_port_types; ///< see ::MBG_NET_INTF_LINK_PORT_TYPE_MASKS
+ uint32_t supp_opts; ///< see ::MBG_NET_INTF_LINK_OPT_MASKS
+ uint32_t supp_bond_modes; ///< see ::MBG_NET_INTF_LINK_BOND_MODE_MASKS
+ uint32_t reserved_1;
+ uint32_t reserved_2;
+ uint32_t reserved_3;
+ uint32_t reserved_4;
+} MBG_NET_INTF_LINK_INFO;
+
+#define _mbg_swab_net_intf_link_info( _p ) \
+do \
+{ \
+ _mbg_swab_net_intf_link_settings( &(_p)->link_settings ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ _mbg_swab32( &(_p)->supp_states ); \
+ _mbg_swab32( &(_p)->supp_types ); \
+ _mbg_swab32( &(_p)->supp_speed_modes ); \
+ _mbg_swab32( &(_p)->supp_port_types ); \
+ _mbg_swab32( &(_p)->supp_opts ); \
+ _mbg_swab32( &(_p)->supp_bond_modes ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+ _mbg_swab32( &(_p)->reserved_4 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Query MBG_NET_INTF_LINK_INFO by its index
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_NET_GLB_CFG_SETTINGS::num_intf_link-1
+ MBG_NET_INTF_LINK_INFO info; ///< see ::MBG_NET_INTF_LINK_INFO
+
+} MBG_NET_INTF_LINK_INFO_IDX;
+
+#define _mbg_swab_net_intf_link_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_net_intf_link_info( &(_p)->info ); \
+} while ( 0 )
+
+
+/**
+ * @brief Network interface address specific settings, flags and supported features
*
- * This structure can be retrieved from a device
- * to check the device's capabilities.
+ * @note Use if_index to identify uniquely its associated network link.
*/
typedef struct
{
- uint16_t type; ///< type of LAN interface, see below
- MBG_MAC_ADDR mac_addr; ///< MAC address
- uint16_t ver_code; ///< version number, high byte.low byte, in hex
- char ver_str[GPS_ID_STR_SIZE]; ///< version string
- char sernum[GPS_ID_STR_SIZE]; ///< serial number
- uint32_t rsvd_0; ///< reserved, currently always 0
- uint16_t flags; ///< flags as specified below
- uint16_t rsvd_1; ///< reserved, currently always 0
+ char label[MBG_IFNAMSIZ]; ///< Interface label
-} LAN_IF_INFO;
+ uint32_t addr_index; ///< Index of the address on the physical interface it is assigned to
+ uint32_t ass_if_index; ///< Index of the associated interface link, see ::MBG_NET_INTF_LINK_SETTINGS::if_index
-#define _mbg_swab_lan_if_info( _p ) \
-{ \
- _mbg_swab16( &(_p)->type ); \
- _mbg_swab16( &(_p)->ver_code ); \
- _mbg_swab32( &(_p)->rsvd_0 ); \
- _mbg_swab16( &(_p)->flags ); \
- _mbg_swab16( &(_p)->rsvd_1 ); \
-}
+ uint32_t flags; ///< see ::MBG_NET_INTF_ADDR_MASKS
+
+ MBG_IP_ADDR ip; ///< IP address associated with this interface
+ MBG_IP_ADDR broadcast; ///< Broadcast address associated with this interface
+
+ uint8_t prefix_bits; ///< Number of subnet mask bits for CIDR notation, e.g. 24 for /24
+ uint8_t reserved_1; ///< Reserved, currently 0
+ uint16_t reserved_2; ///< Reserved, currently 0
+ uint32_t reserved_3; ///< Reserved, currently 0
+ uint32_t reserved_4; ///< Reserved, currently 0
+ uint32_t reserved_5; ///< Reserved, currently 0
+
+} MBG_NET_INTF_ADDR_SETTINGS;
+
+#define _mbg_swab_net_intf_addr_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->addr_index ); \
+ _mbg_swab32( &(_p)->ass_if_index ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab_ip_addr( &(_p)->ip ); \
+ _mbg_swab_ip_addr( &(_p)->broadcast ); \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+ _mbg_swab32( &(_p)->reserved_4 ); \
+ _mbg_swab32( &(_p)->reserved_5 ); \
+} while ( 0 )
/**
- * @brief Codes used with LAN_IF_INFO::type
+ * @brief Query MBG_NET_INTF_ADDR_SETTINGS by its index
*/
-enum LAN_IF_TYPES
+typedef struct
{
- LAN_IF_TYPE_XPORT, ///< LAN interface on an XPORT
- LAN_IF_TYPE_PTP, ///< LAN interface is a special PTP interface
- N_LAN_IF_TYPE ///< number of defined LAN interface types
+ uint16_t idx; ///< 0..::MBG_NET_GLB_CFG_SETTINGS::num_intf_addr-1
+ MBG_NET_INTF_ADDR_SETTINGS settings; ///< see ::MBG_NET_INTF_ADDR_SETTINGS
+
+} MBG_NET_INTF_ADDR_SETTINGS_IDX;
+
+#define _mbg_swab_net_intf_addr_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_net_intf_addr_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+/**
+ * @brief Network interface address specific settings, flags and supported features
+ */
+typedef struct
+{
+ MBG_NET_INTF_ADDR_SETTINGS addr_settings; ///< see ::MBG_NET_INTF_ADDR_SETTINGS
+ uint32_t supp_flags; ///< see ::MBG_NET_INTF_ADDR_MASKS
+ uint32_t reserved_1; ///< Reserved, currently 0
+ uint32_t reserved_2; ///< Reserved, currently 0
+
+} MBG_NET_INTF_ADDR_INFO;
+
+#define _mbg_swab_net_intf_addr_info( _p ) \
+do \
+{ \
+ _mbg_swab_net_intf_addr_settings( &(_p)->addr_settings ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+} while ( 0 )
+
+
+/**
+ * @brief Query MBG_NET_INTF_ADDR_INFO by its index
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_NET_GLB_CFG_SETTINGS::num_intf_addr-1
+ MBG_NET_INTF_ADDR_INFO info; ///< see ::MBG_NET_INTF_ADDR_INFO
+
+} MBG_NET_INTF_ADDR_INFO_IDX;
+
+#define _mbg_swab_net_intf_addr_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_net_intf_addr_info( &(_p)->info ); \
+} while ( 0 )
+
+
+/**
+ * @brief Network interface route specific settings
+ *
+ * @note Use link_mac and ass_addr_idx to identify the associated network address and network link (via address)
+ */
+typedef struct
+{
+ uint8_t type; ///< Type of the route entry, see ::MBG_NET_INTF_ROUTE_TYPES
+ uint8_t reserved_1; ///< Reserved, currently 0
+ uint16_t reserved_2; ///< Reserved, currently 0
+
+ MBG_IP_ADDR gateway; ///< Gateway IP address, only used if type is
+ ///< ::MBG_NET_INTF_ROUTE_TYPE_DEFAULT_GATEWAY or ::MBG_NET_INTF_ROUTE_TYPE_DEST_GATEWAY
+ MBG_IP_ADDR dst; ///< Destination IP address, only used if ::MBG_NET_INTF_ROUTE_SETTINGS::type is
+ ///< ::MBG_NET_INTF_ROUTE_TYPE_DEST_GATEWAY or ::MBG_NET_INTF_ROUTE_TYPE_DEST_ADDR
+ uint8_t dst_prefix_bits; ///< Prefix Bits for the destination address
+
+ uint32_t ass_if_index; ///< Index of the associated interface link, see ::MBG_NET_INTF_LINK_SETTINGS::if_index
+ uint32_t ass_addr_index; ///< Index of the associated interface address, see ::MBG_NET_INTF_ADDR_SETTINGS::addr_index,
+ ///< Valid if ::MBG_NET_INTF_ROUTE_SETTINGS::type is ::MBG_NET_INTF_ROUTE_TYPE_DEST_GATEWAY or ::MBG_NET_INTF_ROUTE_TYPE_DEST_ADDR
+
+ uint32_t reserved_3; ///< Reserved, currently 0
+ uint32_t reserved_4; ///< Reserved, currently 0
+ uint32_t reserved_5; ///< Reserved, currently 0
+
+} MBG_NET_INTF_ROUTE_SETTINGS;
+
+#define _mbg_swab_net_intf_route_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+ _mbg_swab_ip_addr( &(_p)->gateway ); \
+ _mbg_swab_ip_addr( &(_p)->dst ); \
+ _mbg_swab32( &(_p)->ass_if_index ); \
+ _mbg_swab32( &(_p)->ass_addr_index ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+ _mbg_swab32( &(_p)->reserved_4 ); \
+ _mbg_swab32( &(_p)->reserved_5 ); \
+} while ( 0 )
+
+
+/**
+ * @brief Query MBG_NET_INTF_ROUTE_SETTINGS by its index
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_NET_GLB_CFG_SETTINGS::num_intf_route-1
+ MBG_NET_INTF_ROUTE_SETTINGS settings; ///< see ::MBG_NET_INTF_ROUTE_SETTINGS
+
+} MBG_NET_INTF_ROUTE_SETTINGS_IDX;
+
+#define _mbg_swab_net_intf_route_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_net_intf_route_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+/**
+ * @brief Network interface address specific settings
+ */
+typedef struct
+{
+ MBG_NET_INTF_ROUTE_SETTINGS route_settings; ///< see ::MBG_NET_INTF_ROUTE_SETTINGS
+ uint32_t reserved_1; ///< Reserved, currently 0
+ uint32_t reserved_2; ///< Reserved, currently 0
+ uint32_t reserved_3; ///< Reserved, currently 0
+ uint32_t reserved_4; ///< Reserved, currently 0
+} MBG_NET_INTF_ROUTE_INFO;
+
+#define _mbg_swab_net_intf_route_info( _p ) \
+do \
+{ \
+ _mbg_swab_net_intf_route_settings( &(_p)->route_settings ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+ _mbg_swab32( &(_p)->reserved_4 ); \
+} while ( 0 )
+
+
+/**
+ * @brief Query MBG_NET_INTF_ROUTE_INFO by its index
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_NET_GLB_CFG_SETTINGS::num_intf_route-1
+ MBG_NET_INTF_ROUTE_INFO info; ///< see ::MBG_NET_INTF_ROUTE_INFO
+
+} MBG_NET_INTF_ROUTE_INFO_IDX;
+
+#define _mbg_swab_net_intf_route_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_net_intf_route_info( &(_p)->info ); \
+} while ( 0 )
+
+
+/** @} defgroup group_ext_net_cfg */
+
+/** @} defgroup group_net_cfg */
+
+
+
+
+
+/**
+ * @defgroup group_ucap_net User Captures via Network
+ *
+ * @note Group for the user capture via network feature
+ * Only supported if ::MBG_XFEATURE_UCAP_NET is set in extended features
+ * Corresponding GPS commands are ::GPS_UCAP_NET_GLB_INFO and ::GPS_UCAP_NET_RECV_INFO_IDX
+ *
+ * @{ */
+
+
+#define MBG_UCAP_NET_DEFAULT_UDP_PORT 50815
+
+/**
+ * @brief Transfer mode for user captures via network
+ *
+ * @see ::MBG_UCAP_NET_TRANSF_MODE_MASKS
+ *
+ * Used with ::MBG_UCAP_NET_RECV_SETTINGS::mode
+ */
+enum MBG_UCAP_NET_TRANSF_MODE
+{
+ MBG_UCAP_NET_TRANSF_MODE_UNKNOWN, ///< Unknown transfer mode
+ MBG_UCAP_NET_TRANSF_MODE_ON_REQ, ///< User captures will be transferred on request only
+ MBG_UCAP_NET_TRANSF_MODE_AUTO, ///< User captures are being transferred automatically
+ N_MBG_UCAP_NET_TRANSF_MODES
};
/**
- * @brief Enumeration of flag bits used with IP4_SETTINGS::flags and LAN_IF_INFO::flags
+ * @brief Masks for transfer mode used with ::MBG_UCAP_NET_GLB_INFO::supp_modes
*
- * @see MBG_IP4_FLAG_MASKS
+ * @see ::MBG_UCAP_NET_TRANSF_MODE
*/
-enum MBG_IP4_FLAG_BITS
+enum MBG_UCAP_NET_TRANSF_MODE_MASKS
{
- IP4_BIT_DHCP, ///< DHCP supported (LAN_IF_INFO) / enabled (IP4_SETTINGS)
- IP4_BIT_LINK, ///< used only in IP4_SETTINGS to report link state
- IP4_BIT_VLAN, ///< VLAN supported (LAN_IF_INFO) / enabled (IP4_SETTINGS)
- N_IP4_BIT ///< number of defined flag bits
+ MBG_UCAP_NET_TRANSF_MODE_MASK_UNKNOWN = ( 1UL << MBG_UCAP_NET_TRANSF_MODE_UNKNOWN ), ///< see ::MBG_UCAP_NET_TRANSF_MODE_UNKNOWN
+ MBG_UCAP_NET_TRANSF_MODE_MASK_ON_REQ = ( 1UL << MBG_UCAP_NET_TRANSF_MODE_ON_REQ ), ///< see ::MBG_UCAP_NET_TRANSF_MODE_ON_REQ
+ MBG_UCAP_NET_TRANSF_MODE_MASK_AUTO = ( 1UL << MBG_UCAP_NET_TRANSF_MODE_AUTO ) ///< see ::MBG_UCAP_NET_TRANSF_MODE_AUTO
};
+
+
/**
- * @brief Bit masks used with IP4_SETTINGS::flags and LAN_IF_INFO::flags
+ * @brief Transfer protocol for user captures via network
*
- * @see MBG_IP4_FLAG_BITS
+ * @see ::MBG_UCAP_NET_TRANSF_PROTO_MASKS
+ *
+ * Used with ::MBG_UCAP_NET_RECV_SETTINGS::proto
*/
-enum MBG_IP4_FLAG_MASKS
+enum MBG_UCAP_NET_TRANSF_PROTO
{
- IP4_MSK_DHCP = ( 1UL << IP4_BIT_DHCP ), ///< see ::IP4_BIT_DHCP
- IP4_MSK_LINK = ( 1UL << IP4_BIT_LINK ), ///< see ::IP4_BIT_LINK
- IP4_MSK_VLAN = ( 1UL << IP4_BIT_VLAN ), ///< see ::IP4_BIT_VLAN
+ MBG_UCAP_NET_TRANSF_PROTO_UNKNOWN, ///< Unknown transfer mode
+ MBG_UCAP_NET_TRANSF_PROTO_UDP, ///< User captures are transferred via UDP
+ N_MBG_UCAP_NET_TRANSF_PROTOS
};
-/** @} group_ip4_cfg */
+
+/**
+ * @brief Masks for transfer protocol used with ::MBG_UCAP_NET_GLB_INFO::supp_protos
+ *
+ * @see ::MBG_UCAP_NET_TRANSF_PROTO
+ */
+enum MBG_UCAP_NET_TRANSF_PROTO_MASKS
+{
+ MBG_UCAP_NET_TRANSF_PROTO_MASK_UNKNOWN = ( 1UL << MBG_UCAP_NET_TRANSF_PROTO_UNKNOWN ), ///< see ::MBG_UCAP_NET_TRANSF_PROTO_UNKNOWN
+ MBG_UCAP_NET_TRANSF_PROTO_MASK_UDP = ( 1UL << MBG_UCAP_NET_TRANSF_PROTO_UDP ) ///< see ::MBG_UCAP_NET_TRANSF_PROTO_UDP
+};
+
+
+
+/**
+ * @brief Supported flags for user captures via network
+ *
+ * @see ::MBG_UCAP_NET_SUPP_FLAG_MASKS
+ */
+enum MBG_UCAP_NET_SUPP_FLAGS
+{
+ MBG_UCAP_NET_SUPP_FLAG_IPV6,
+ N_MBG_UCAP_NET_SUPP_FLAGS
+};
+
+
+/**
+ * @brief Masks for supported flags used with ::MBG_UCAP_NET_GLB_INFO::supp_flags
+ *
+ * @see ::MBG_UCAP_NET_TRANSF_PROTO
+ */
+enum MBG_UCAP_NET_SUPP_FLAG_MASKS
+{
+ MBG_UCAP_NET_SUPP_FLAG_MASK_IPV6 = ( 1UL << MBG_UCAP_NET_SUPP_FLAG_IPV6 ) ///< see ::MBG_UCAP_NET_SUPP_FLAG_IPV6
+};
+
+
+/**
+ * @brief Global settings for user captures via network
+ *
+ * @note This structure shall be used to set the current global settings of a device
+ * with GPS command ::GPS_UCAP_NET_GLB_INFO.
+ */
+typedef struct
+{
+ uint32_t num_recvs; ///< Number of configured network receivers, see ::MBG_UCAP_NET_RECV_INFO_IDX
+ uint32_t reserved_0; ///< Reserved, currently always 0
+ uint32_t reserved_1; ///< Reserved, currently always 0
+ uint32_t reserved_2; ///< Reserved, currently always 0
+
+} MBG_UCAP_NET_GLB_SETTINGS;
+
+
+#define _mbg_swab_ucap_net_glb_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->num_recvs ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Global settings, features and flags for user captures via network
+ *
+ * @note This structure shall be used to read the current global settings from a device
+ * with GPS command ::GPS_UCAP_NET_GLB_INFO.
+ */
+typedef struct
+{
+ MBG_UCAP_NET_GLB_SETTINGS settings; ///< see ::MBG_UCAP_NET_GLB_SETTINGS
+
+ uint32_t n_supp_recvs; ///< Number of supported network receivers, see ::MBG_UCAP_NET_RECV_INFO_IDX
+ uint32_t supp_modes; ///< Supported transfer modes, see ::MBG_UCAP_NET_TRANSF_MODE_MASKS
+ uint32_t supp_protos; ///< Supported transfer protocols, see ::MBG_UCAP_NET_TRANSF_PROTO_MASKS
+ uint32_t reserved_0; ///< Reserved, currently always 0
+ uint32_t reserved_1; ///< Reserved, currently always 0
+ uint32_t supp_flags; ///< Supported flags, see ::MBG_UCAP_NET_SUPP_FLAG_MASKS
+
+} MBG_UCAP_NET_GLB_INFO;
+
+
+#define _mbg_swab_ucap_net_glb_info( _p ) \
+do \
+{ \
+ _mbg_swab_ucap_net_glb_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->n_supp_recvs ); \
+ _mbg_swab32( &(_p)->supp_modes ); \
+ _mbg_swab32( &(_p)->supp_protos ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Settings for receivers of user captures via network
+ */
+typedef struct
+{
+ uint8_t mode; ///< Transfer mode, see ::MBG_UCAP_NET_TRANSF_MODE
+ uint8_t proto; ///< Transfer protocol, see ::MBG_UCAP_NET_TRANSF_PROTO
+ uint16_t reserved_1; ///< Reserved, currently always 0
+
+ uint32_t reserved_2; ///< Reserved, currently always 0
+ uint32_t reserved_3; ///< Reserved, currently always 0
+ uint32_t ucaps; ///< Bit mask for active user captures
+
+ MBG_IP_ADDR_PORT addr; ///< Destination IP and port address of the network receiver, see ::MBG_IP_ADDR_PORT
+
+} MBG_UCAP_NET_RECV_SETTINGS;
+
+
+#define _mbg_swab_ucap_net_recv_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+ _mbg_swab32( &(_p)->ucaps ); \
+ _mbg_swab_ip_addr_port( &(_p)->addr ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Settings for receivers of user captures via network
+ *
+ * @note This structure shall be used to write the settings to the device
+ * with GPS command ::GPS_UCAP_NET_RECV_INFO_IDX.
+ * This can be done for index 0 to ::MBG_UCAP_NET_GLB_SETTINGS::num_recvs-1.
+ *
+ * @see ::MBG_UCAP_NET_RECV_SETTINGS
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_UCAP_NET_GLB_SETTINGS::num_recvs-1
+ MBG_UCAP_NET_RECV_SETTINGS settings; ///< see ::MBG_UCAP_NET_RECV_SETTINGS
+
+} MBG_UCAP_NET_RECV_SETTINGS_IDX;
+
+
+#define _mbg_swab_ucap_net_recv_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ucap_net_recv_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Settings, features and flags for receivers of user captures via network
+ */
+typedef struct
+{
+ MBG_UCAP_NET_RECV_SETTINGS settings; ///< see ::MBG_UCAP_NET_RECV_SETTINGS
+
+ uint32_t reserved_0; ///< Reserved, currently always 0
+ uint32_t reserved_1; ///< Reserved, currently always 0
+ uint32_t reserved_2; ///< Reserved, currently always 0
+ uint32_t reserved_3; ///< Reserved, currently always 0
+
+} MBG_UCAP_NET_RECV_INFO;
+
+
+#define _mbg_swab_ucap_net_recv_info( _p ) \
+do \
+{ \
+ _mbg_swab_ucap_net_recv_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Settings, features and flags for receivers of user captures via network
+ *
+ * @note This structure shall be used to read the current settings from the device
+ * with GPS command ::GPS_UCAP_NET_RECV_INFO_IDX.
+ * This can be done for index 0 to ::MBG_UCAP_NET_GLB_SETTINGS::num_recvs-1.
+ *
+ * @see ::MBG_UCAP_NET_RECV_INFO
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_UCAP_NET_GLB_INFO::n_supp_recvs-1
+ MBG_UCAP_NET_RECV_INFO info; ///< see ::MBG_UCAP_NET_RECV_INFO
+
+} MBG_UCAP_NET_RECV_INFO_IDX;
+
+
+#define _mbg_swab_ucap_net_recv_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ucap_net_recv_info( &(_p)->info ); \
+} while ( 0 )
+
+/** @} defgroup ext_ucap */
@@ -5686,7 +12915,7 @@ enum MBG_IP4_FLAG_MASKS
/**
* @brief Enumeration of protocols possibly used with PTP
*
- * @see PTP_NW_PROT_MASKS
+ * @see ::PTP_NW_PROT_MASKS
*/
enum PTP_NW_PROTS
{
@@ -5704,7 +12933,7 @@ enum PTP_NW_PROTS
/**
* @brief Bit masks for enumerated protocols possibly used with PTP
*
- * @see PTP_NW_PROTS
+ * @see ::PTP_NW_PROTS
*/
enum PTP_NW_PROT_MASKS
{
@@ -5722,7 +12951,7 @@ enum PTP_NW_PROT_MASKS
/**
* @brief Name strings for the protocols possibly used with PTP
*
- * @see PTP_NW_PROTS
+ * @see ::PTP_NW_PROTS
*/
#define PTP_NW_PROT_STRS \
{ \
@@ -5739,7 +12968,7 @@ enum PTP_NW_PROT_MASKS
/**
* @brief Short name strings for the protocols possibly used with PTP
*
- * @see PTP_NW_PROTS
+ * @see ::PTP_NW_PROTS
*/
#define PTP_NW_PROT_STRS_SHORT \
{ \
@@ -5797,6 +13026,7 @@ typedef struct
{
uint8_t value; ///< the parameter value
const char *name; ///< the parameter name
+
} PTP_TABLE;
@@ -5808,8 +13038,8 @@ typedef struct
* in the published specs for IEEE1588. In addition, the specs
* define code 0x14 for "disabled".
*
- * @see PTP_DELAY_MECH_MASKS
- * @see PTP_DELAY_MECH_NAMES
+ * @see ::PTP_DELAY_MECH_MASKS
+ * @see ::PTP_DELAY_MECH_NAMES
*/
enum PTP_DELAY_MECHS
{
@@ -5820,14 +13050,14 @@ enum PTP_DELAY_MECHS
/**
- * @brief Bit masks associated to enumerated PTP delay mechanisms
+ * @brief Bit masks associated with enumerated PTP delay mechanisms
*
- * @see PTP_DELAY_MECH_MASKS
+ * @see ::PTP_DELAY_MECH_MASKS
*/
enum PTP_DELAY_MECH_MASKS
{
PTP_DELAY_MECH_MSK_E2E = ( 1UL << PTP_DELAY_MECH_E2E ), ///< see ::PTP_DELAY_MECH_E2E
- PTP_DELAY_MECH_MSK_P2P = ( 1UL << PTP_DELAY_MECH_E2E ) ///< see ::PTP_DELAY_MECH_E2E
+ PTP_DELAY_MECH_MSK_P2P = ( 1UL << PTP_DELAY_MECH_P2P ) ///< see ::PTP_DELAY_MECH_P2P
};
@@ -5837,7 +13067,7 @@ enum PTP_DELAY_MECH_MASKS
/**
* @brief Name strings for the PTP delay mechanisms
*
- * @see PTP_DELAY_MECHS
+ * @see ::PTP_DELAY_MECHS
*/
#define PTP_DELAY_MECH_NAMES \
{ \
@@ -5853,7 +13083,7 @@ enum PTP_DELAY_MECH_MASKS
* @note This enumeration does not start at 0 but with a bias
* specified by ::PTP_CLOCK_ACCURACY_NUM_BIAS.
*
- * @see PTP_CLOCK_ACCURACY_STRS
+ * @see ::PTP_CLOCK_ACCURACY_STRS
*/
enum PTP_CLOCK_ACCURACIES
{
@@ -5881,6 +13111,8 @@ enum PTP_CLOCK_ACCURACIES
PTP_CLOCK_ACCURACY_RESERVED_3,
PTP_CLOCK_ACCURACY_RESERVED_4,
N_PTP_CLOCK_ACCURACY
+ //##++++ TODO: Add a code for 0xFE (unknown), or eventually
+ // redesign the lookup of associated strings completely.
};
@@ -5891,7 +13123,7 @@ enum PTP_CLOCK_ACCURACIES
* specified by ::PTP_CLOCK_ACCURACY_NUM_BIAS, so this bias needs
* to be accounted for when accessing a string table.
*
- * @see PTP_CLOCK_ACCURACIES
+ * @see ::PTP_CLOCK_ACCURACIES
*/
#define PTP_CLOCK_ACCURACY_STRS \
{ \
@@ -5924,7 +13156,7 @@ enum PTP_CLOCK_ACCURACIES
/**
* @brief Codes to specify the type of a time source used with PTP
*
- * @see PTP_TIME_SOURCE_TABLE
+ * @see ::PTP_TIME_SOURCE_TABLE
*/
enum PTP_TIME_SOURCES
{
@@ -5943,7 +13175,7 @@ enum PTP_TIME_SOURCES
/**
* @brief A table of PTP time source codes plus associated name strings
*
- * @see PTP_TIME_SOURCES
+ * @see ::PTP_TIME_SOURCES
*/
#define PTP_TIME_SOURCE_TABLE \
{ \
@@ -5962,12 +13194,17 @@ enum PTP_TIME_SOURCES
/**
* @brief An enumeration of roles which can be taken by a PTP node
*
- * @note A role in this context specifies a certain mode of operation.
+ * A role in this context specifies a certain mode of operation.
* Depending on its specification a devices may not be able to take
* each of the specified roles.
*
- * @see PTP_ROLE_STRS
- * @see PTP_ROLE_STRS_SHORT
+ * @note: A device in MULTICAST_AUTO role can be either master or slave,
+ * so the port state needs to be checked to determine the current
+ * mode of operation.
+ *
+ * @see ::PTP_ROLE_MASKS
+ * @see ::PTP_ROLE_STRS
+ * @see ::PTP_ROLE_STRS_SHORT
*/
enum PTP_ROLES
{
@@ -5977,29 +13214,60 @@ enum PTP_ROLES
PTP_ROLE_UNICAST_MASTER, ///< unicast master
PTP_ROLE_MULTICAST_AUTO, ///< multicast master or slave (auto selection)
PTP_ROLE_BOTH_MASTER, ///< simultanous multicast and unicast master
- PTP_ROLE_HYBRID_MASTER, ///< multicast sync and unicast delay response as master
- PTP_ROLE_HYBRID_SLAVE, ///< multicast sync and unicast delay request as slave
+ PTP_ROLE_NTP_SERVER, ///< NTP Unicast Server
+ PTP_ROLE_NTP_CLIENT, ///< NTP Unicast Client
+ PTP_ROLE_TIME_MONITOR, ///< Time Monitor for external PTP or NTP devices
+ PTP_ROLE_V1_MASTER, ///< PTPv1 Master in Multicast mode
+ PTP_ROLE_V1_SLAVE, ///< PTPv1 Slave in Multicast mode
N_PTP_ROLES ///< number of defined roles
};
-#define PTP_ROLE_MSK_MULTICAST_SLAVE ( 1UL << PTP_ROLE_MULTICAST_SLAVE )
-#define PTP_ROLE_MSK_UNICAST_SLAVE ( 1UL << PTP_ROLE_UNICAST_SLAVE )
-#define PTP_ROLE_MSK_MULTICAST_MASTER ( 1UL << PTP_ROLE_MULTICAST_MASTER )
-#define PTP_ROLE_MSK_UNICAST_MASTER ( 1UL << PTP_ROLE_UNICAST_MASTER )
-#define PTP_ROLE_MSK_MULTICAST_AUTO ( 1UL << PTP_ROLE_MULTICAST_AUTO )
-#define PTP_ROLE_MSK_BOTH_MASTER ( 1UL << PTP_ROLE_BOTH_MASTER )
-#define PTP_ROLE_MSK_HYBRID_MASTER ( 1UL << PTP_ROLE_HYBRID_MASTER )
-#define PTP_ROLE_MSK_HYBRID_SLAVE ( 1UL << PTP_ROLE_HYBRID_SLAVE )
-#define PTP_ROLE_MSK_SLAVES ( PTP_ROLE_MSK_MULTICAST_SLAVE | PTP_ROLE_MSK_UNICAST_SLAVE )
-#define PTP_ROLE_MSK_MASTERS ( PTP_ROLE_MSK_MULTICAST_MASTER | PTP_ROLE_MSK_UNICAST_MASTER )
+/**
+ * @brief Bit mask associated with ::PTP_ROLES
+ *
+ * A role in this context specifies a certain mode of operation.
+ * Depending on its specification a devices may not be able to take
+ * each of the specified roles.
+ *
+ * @note: A device in MULTICAST_AUTO role can be either master or slave,
+ * so the port state needs to be checked to determine the current
+ * mode of operation.
+ *
+ * @see ::PTP_ROLES
+ * @see ::get_supp_ptp_role_mask
+ */
+enum PTP_ROLE_MASKS
+{
+ PTP_ROLE_MSK_MULTICAST_SLAVE = ( 1UL << PTP_ROLE_MULTICAST_SLAVE ), ///< see ::PTP_ROLE_MULTICAST_SLAVE
+ PTP_ROLE_MSK_UNICAST_SLAVE = ( 1UL << PTP_ROLE_UNICAST_SLAVE ), ///< see ::PTP_ROLE_UNICAST_SLAVE
+ PTP_ROLE_MSK_MULTICAST_MASTER = ( 1UL << PTP_ROLE_MULTICAST_MASTER ), ///< see ::PTP_ROLE_MULTICAST_MASTER
+ PTP_ROLE_MSK_UNICAST_MASTER = ( 1UL << PTP_ROLE_UNICAST_MASTER ), ///< see ::PTP_ROLE_UNICAST_MASTER
+ PTP_ROLE_MSK_MULTICAST_AUTO = ( 1UL << PTP_ROLE_MULTICAST_AUTO ), ///< see ::PTP_ROLE_MULTICAST_AUTO
+ PTP_ROLE_MSK_BOTH_MASTER = ( 1UL << PTP_ROLE_BOTH_MASTER ), ///< see ::PTP_ROLE_BOTH_MASTER
+ PTP_ROLE_MSK_NTP_SERVER = ( 1UL << PTP_ROLE_NTP_SERVER ), ///< see ::PTP_ROLE_NTP_SERVER
+ PTP_ROLE_MSK_NTP_CLIENT = ( 1UL << PTP_ROLE_NTP_CLIENT ), ///< see ::PTP_ROLE_NTP_CLIENT
+ PTP_ROLE_MSK_TIME_MONITOR = ( 1UL << PTP_ROLE_TIME_MONITOR ), ///< see ::PTP_ROLE_TIME_MONITOR
+ PTP_ROLE_MSK_V1_MASTER = ( 1UL << PTP_ROLE_V1_MASTER ), ///< see ::PTP_ROLE_MULTICAST_MASTER
+ PTP_ROLE_MSK_V1_SLAVE = ( 1UL << PTP_ROLE_V1_SLAVE ) ///< see ::PTP_ROLE_UNICAST_SLAVE
+};
+
+
+#define PTP_ROLE_MSK_SLAVES ( PTP_ROLE_MSK_MULTICAST_SLAVE \
+ | PTP_ROLE_MSK_UNICAST_SLAVE \
+ | PTP_ROLE_MSK_MULTICAST_AUTO )
+
+#define PTP_ROLE_MSK_MASTERS ( PTP_ROLE_MSK_MULTICAST_MASTER \
+ | PTP_ROLE_MSK_UNICAST_MASTER \
+ | PTP_ROLE_MSK_MULTICAST_AUTO \
+ | PTP_ROLE_BOTH_MASTER )
/**
* @brief Name strings for defined PTP roles
*
- * @see PTP_ROLES
- * @see PTP_ROLE_STRS_SHORT
+ * @see ::PTP_ROLES
+ * @see ::PTP_ROLE_STRS_SHORT
*/
#define PTP_ROLE_STRS \
{ \
@@ -6007,18 +13275,21 @@ enum PTP_ROLES
"Unicast Slave", \
"Multicast Master", \
"Unicast Master", \
- "Multicast (Auto)" \
- "UC/MC Master" \
- "Hybrid Master" \
- "Hybrid Slave" \
+ "Multicast (Auto)", \
+ "UC+MC Master", \
+ "NTP Server", \
+ "NTP Client", \
+ "Time Monitor", \
+ "V1 Master", \
+ "V1 Slave" \
}
/**
* @brief Short name strings for defined PTP roles
*
- * @see PTP_ROLES
- * @see PTP_ROLE_STRS
+ * @see ::PTP_ROLES
+ * @see ::PTP_ROLE_STRS
*/
#define PTP_ROLE_STRS_SHORT \
{ \
@@ -6026,10 +13297,13 @@ enum PTP_ROLES
"UCS", \
"MCM", \
"UCM", \
- "MC" \
- "UMM" \
- "HM" \
- "HS" \
+ "MCA", \
+ "UMM", \
+ "NSV", \
+ "NCL", \
+ "MON", \
+ "V1M", \
+ "V1S" \
}
@@ -6042,6 +13316,7 @@ enum PTP_ROLES
typedef struct
{
uint8_t b[8];
+
} PTP_CLOCK_ID;
#define _mbg_swab_ptp_clock_id( _p ) _nop_macro_fnc() // nothing to swap
@@ -6051,9 +13326,6 @@ typedef struct
/**
* @brief A PTP port ID
- *
- * @note This usually consists of a 6 byte MAC address with
- * 2 fixed bytes inserted, or all ones as wildcard.
*/
typedef uint16_t PTP_PORT_ID;
@@ -6063,6 +13335,70 @@ typedef uint16_t PTP_PORT_ID;
/**
+ * @brief A PTP port identity
+ *
+ * @note For further information, see IEEE 1588-2008, chapter 5.3.5
+ *
+ * @see ::PTP_CLOCK_ID
+ * @see ::PTP_PORT_ID
+ */
+typedef struct
+{
+ PTP_CLOCK_ID clock_identity;
+ PTP_PORT_ID port_number;
+
+} PTP_PORT_IDENTITY;
+
+
+#define _mbg_swab_ptp_port_identity( _p ) \
+{ \
+ _mbg_swab_ptp_clock_id( &(_p)->clock_identity ); \
+ _mbg_swab_ptp_port_id( &(_p)->port_number ); \
+}
+
+
+/**
+ * @brief PTP clock quality
+ *
+ * @note For further information, see IEEE 1588-2008, chapter 5.3.7
+ */
+typedef struct
+{
+ uint8_t clock_class; ///< PTP clock class representing the current sync status
+ int8_t clock_accuracy; ///< see ::PTP_CLOCK_ACCURACIES
+ uint16_t log_variance; ///< PTP offset scaled log variance representing the time stability
+
+} PTP_CLOCK_QUALITY;
+
+
+#define _mbg_swab_ptp_clock_quality( _p ) \
+{ \
+ _mbg_swab8( &(_p)->clock_class ); \
+ _mbg_swab8( &(_p)->clock_accuracy ); \
+ _mbg_swab16( &(_p)->log_variance ); \
+}
+
+
+/**
+ * @brief PTP time interval
+ *
+ * @note For further information, see IEEE 1588-2008, chapter 5.3.2
+ *
+ */
+typedef struct
+{
+ int64_t scaled_nanoseconds;
+
+} PTP_TIME_INTERVAL;
+
+
+#define _mbg_swab_ptp_time_interval( _p ) \
+{ \
+ _mbg_swab64( &(_p)->scaled_nanoseconds ); \
+}
+
+
+/**
* @brief An enumeration of time scales used with PTP
*
* @note The standard time scale used by PTP is TAI, which is a linear time scale.
@@ -6070,8 +13406,8 @@ typedef uint16_t PTP_PORT_ID;
* can observe leap seconds. For the arbitrary time scale the %UTC offset is unspecified,
* so arbitrary time can be %UTC, or something else.
*
- * @see PTP_TIMESCALE_NAMES
- * @see PTP_TIMESCALE_NAMES_SHORT
+ * @see ::PTP_TIMESCALE_NAMES
+ * @see ::PTP_TIMESCALE_NAMES_SHORT
*/
enum PTP_TIME_SCALES
{
@@ -6097,8 +13433,8 @@ enum PTP_TIME_SCALES
/**
* @brief A table of name strings for the PTP time scales
*
- * @see PTP_TIME_SCALES
- * @see PTP_TIMESCALE_NAMES_SHORT
+ * @see ::PTP_TIME_SCALES
+ * @see ::PTP_TIMESCALE_NAMES_SHORT
*/
#define PTP_TIMESCALE_NAMES \
{ \
@@ -6109,8 +13445,8 @@ enum PTP_TIME_SCALES
/**
* @brief A table of short name strings for the PTP time scales
*
- * @see PTP_TIME_SCALES
- * @see PTP_TIMESCALE_NAMES
+ * @see ::PTP_TIME_SCALES
+ * @see ::PTP_TIMESCALE_NAMES
*/
#define PTP_TIMESCALE_NAMES_SHORT \
{ \
@@ -6140,7 +13476,7 @@ typedef struct
uint8_t clock_class;
uint8_t clock_accuracy; ///< see ::PTP_CLOCK_ACCURACIES
- uint32_t reserved_1; ///< reserved, currently always 0
+ uint32_t tsu_secs; ///< current seconds value of time stamp unit
uint32_t reserved_2; ///< reserved, currently always 0
uint8_t domain_number; ///< the PTP clock domain number, 0:3
@@ -6151,11 +13487,15 @@ typedef struct
int16_t utc_offset; ///< %UTC offset observed against TAI
DAC_VAL osc_dac_cal; ///< disciplination value of the oscillator
- uint32_t reserved_3; ///< reserved, currently always 0
+ uint8_t parent_clock_class; ///< clock class of the parent node
+ uint8_t parent_clock_accuracy; ///< clock accuracy of the parent node, see ::PTP_CLOCK_ACCURACIES
+
+ uint16_t reserved_3; ///< reserved, currently always 0
} PTP_STATE;
#define _mbg_swab_ptp_state( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->nw_prot ); \
_mbg_swab32( &(_p)->flags ); \
@@ -6165,18 +13505,18 @@ typedef struct
_mbg_swab_nano_time( &(_p)->delay_asymmetry ); \
_mbg_swab_ptp_clock_id( &(_p)->gm_id ); \
_mbg_swab16( &(_p)->clock_offset_scaled_log_variance ); \
- _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->tsu_secs ); \
_mbg_swab32( &(_p)->reserved_2 ); \
_mbg_swab16( &(_p)->utc_offset ); \
_mbg_swab_dac_val( &(_p)->osc_dac_cal ); \
- _mbg_swab32( &(_p)->reserved_3 ); \
-}
+ _mbg_swab16( &(_p)->reserved_3 ); \
+} while ( 0 )
/**
* @brief Flags bits used with PTP_STATE::flags
*
- * @see PTP_STATE_FLAG_MASKS
+ * @see ::PTP_STATE_FLAG_MASKS
*/
enum PTP_STATE_FLAGS
{
@@ -6194,7 +13534,7 @@ enum PTP_STATE_FLAGS
/**
* @brief Flags masks used with PTP_STATE::flags
*
- * @see PTP_STATE_FLAGS
+ * @see ::PTP_STATE_FLAGS
*/
enum PTP_STATE_FLAG_MASKS
{
@@ -6239,22 +13579,23 @@ typedef struct
uint32_t upper_bound; ///< sync state set to false if above this limit [ns]
uint32_t lower_bound; ///< sync state set to true if below this limit [ns]
- uint32_t reserved_2; ///< reserved, currently always 0
- uint32_t flags; ///< see ::PTP_CFG_FLAGS
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< see @ref PTP_CFG_FLAG_MASKS
} PTP_CFG_SETTINGS;
-#define _mbg_swab_ptp_cfg_settings( _p ) \
-{ \
- _mbg_swab16( &(_p)->nw_prot ); \
- _mbg_swab16( &(_p)->sync_intv ); \
- _mbg_swab16( &(_p)->ann_intv ); \
- _mbg_swab16( &(_p)->delay_req_intv ); \
- _mbg_swab32( &(_p)->upper_bound ); \
- _mbg_swab32( &(_p)->lower_bound ); \
- _mbg_swab32( &(_p)->reserved_3 ); \
- _mbg_swab32( &(_p)->flags ); \
-}
+#define _mbg_swab_ptp_cfg_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->nw_prot ); \
+ _mbg_swab16( &(_p)->sync_intv ); \
+ _mbg_swab16( &(_p)->ann_intv ); \
+ _mbg_swab16( &(_p)->delay_req_intv ); \
+ _mbg_swab32( &(_p)->upper_bound ); \
+ _mbg_swab32( &(_p)->lower_bound ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
@@ -6264,7 +13605,7 @@ typedef struct
enum PTP_ANN_RCPT_TIMEOUT_LIMITS
{
PTP_ANN_RCPT_TIMEOUT_MIN = 2,
- PTP_ANN_RCPT_TIMEOUT_MAX = 255,
+ PTP_ANN_RCPT_TIMEOUT_MAX = 8,
DEFAULT_PTP_ANN_RCPT_TIMEOUT = 3
};
@@ -6288,7 +13629,7 @@ typedef struct
int16_t delay_req_intv_min; ///< log2 of minimum delay request interval [s]
int16_t delay_req_intv_max; ///< log2 of maximum delay request interval [s]
- uint32_t supp_flags; ///< a bit mask of supported features, see ::PTP_CFG_FLAGS
+ uint32_t supp_flags; ///< a bit mask of supported features, see @ref PTP_CFG_FLAG_MASKS
uint32_t supp_nw_prot; ///< a bit mask of supported network protocols, see ::PTP_NW_PROT_MASKS
uint32_t supp_opt_ext; ///< a bit mask of supported optional extensions, see ::PTP_OPT_EXT_MASKS
uint32_t supp_delay_mech; ///< a bit mask of supported delay mechanisms, see ::PTP_DELAY_MECH_MASKS
@@ -6296,6 +13637,7 @@ typedef struct
} PTP_CFG_INFO;
#define _mbg_swab_ptp_cfg_info( _p ) \
+do \
{ \
_mbg_swab_ptp_cfg_settings( &(_p)->settings ); \
_mbg_swab16( &(_p)->reserved_2 ); \
@@ -6307,166 +13649,263 @@ typedef struct
_mbg_swab16( &(_p)->delay_req_intv_max ); \
_mbg_swab32( &(_p)->supp_flags ); \
_mbg_swab32( &(_p)->supp_nw_prot ); \
- _mbg_swab32( &(_p)->supp_profiles ); \
+ _mbg_swab32( &(_p)->supp_opt_ext ); \
_mbg_swab32( &(_p)->supp_delay_mech ); \
-}
+} while ( 0 )
/**
- * @brief Flags used with PTP_CFG_SETTINGS::flags and PTP_CFG_INFO::supp_flags
+ * @brief Flags bits used with PTP configuration
+ *
+ * Flags labeled [R/-] can only be used with ::PTP_CFG_INFO::supp_flags
+ * to indicate that the associated feature is supported in general.
+ *
+ * If a flag labeled [R/W] is set in ::PTP_CFG_INFO::supp_flags then
+ * this flag can also be used with ::PTP_CFG_SETTINGS::flags to control
+ * the associated feature.
*
- * @see PTP_CFG_FLAG_MASKS
+ * @note Originally, all devices supported the multicast slave role, so
+ * there was no extra flag to indicate this. However, some newer devices
+ * may not support the multicast slave role, so two new flags have been
+ * introduced to cope with this:
+ * If ::PTP_CFG_SUPP_MCAST_SLAVE_FLAG is set then a different flag
+ * ::PTP_CFG_CAN_BE_MULTICAST_SLAVE needs to be checked to tell if
+ * the multicast slave role is supported, or not.
+ * If ::PTP_CFG_SUPP_MCAST_SLAVE_FLAG is not set then the device
+ * definitely supports the multicast slave role.
+ *
+ * @see @ref PTP_CFG_FLAG_MASKS
*/
enum PTP_CFG_FLAGS
{
- PTP_CFG_TIME_SCALE_IS_PTP, ///< time scale is PTP/TAI, else arbitrary
- PTP_CFG_V1_HW_COMPAT, ///< maybe required for certain NIC chips, not used by Meinberg
- PTP_CFG_CAN_BE_UNICAST_SLAVE, ///< the PTP port can take the role of a unicast slave
- PTP_CFG_CAN_BE_MULTICAST_MASTER, ///< the PTP port can take the role of a multicast master
- PTP_CFG_CAN_BE_UNICAST_MASTER, ///< the PTP port can take the role of a unicast master
- PTP_CFG_CAN_BE_MULTICAST_AUTO, ///< the PTP port can automatically become multicast master or slave
- PTP_CFG_SUPP_UTC_VALID, ///< %UTC valid bit in PTP_STATE::flags is supported
- PTP_CFG_CAN_BE_BOTH_MASTER, ///< the PTP port can take the role of a unicast and multicast master
- PTP_CFG_CAN_BE_HYBRID_MASTER, ///< the PTP port can take the role of a hybrid master
- PTP_CFG_CAN_BE_HYBRID_SLAVE, ///< the PTP port can take the role of a hybrid slave
- PTP_CFG_ONE_STEP_MASTER, ///< the PTP port supports one-step clock in master mode
- PTP_CFG_MNGMNT_MSGS_DISB, ///< disable PTP management messages
+ PTP_CFG_TIME_SCALE_IS_PTP, ///< [R/W] time scale is PTP/TAI, else arbitrary
+ PTP_CFG_V1_HW_COMPAT, ///< [R/W] maybe required for certain NIC chips, not used by Meinberg
+ PTP_CFG_CAN_BE_UNICAST_SLAVE, ///< [R/-] supports unicast slave role, see ::PTP_ROLE_UNICAST_SLAVE
+ PTP_CFG_CAN_BE_MULTICAST_MASTER, ///< [R/-] supports multicast master role, see ::PTP_ROLE_MULTICAST_MASTER
+ PTP_CFG_CAN_BE_UNICAST_MASTER, ///< [R/-] supports unicast master, see ::PTP_ROLE_UNICAST_MASTER
+ PTP_CFG_CAN_BE_MULTICAST_AUTO, ///< [R/-] can automatically become multicast master or slave, see ::PTP_CFG_CAN_BE_MULTICAST_AUTO
+ PTP_CFG_SUPP_UTC_VALID, ///< [R/-] ::PTP_FLAG_UTC_VALID bit in ::PTP_STATE::flags is supported
+ PTP_CFG_CAN_BE_BOTH_MASTER, ///< [R/-] supports unicast and multicast master role at the same time, see ::PTP_CFG_CAN_BE_BOTH_MASTER
+
+ PTP_CFG_HYBRID_MASTER, ///< [R/W] supports hybrid mode in master roles
+ PTP_CFG_HYBRID_SLAVE, ///< [R/W] supports hybrid mode in slave roles
+ PTP_CFG_ONE_STEP_MASTER, ///< [R/W] supports one-step mode in master roles
+ PTP_CFG_MNGMNT_MSGS_DISB, ///< [R/W] supports disabling of PTP management messages
+ PTP_CFG_SUPP_MCAST_SLAVE_FLAG, ///< [R/-] indicates that ::PTP_CFG_CAN_BE_MULTICAST_SLAVE flag is supported and can be checked
+ PTP_CFG_CAN_BE_MULTICAST_SLAVE, ///< [R/-] if ::PTP_CFG_SUPP_MCAST_SLAVE_FLAG bit set, indicates if multicast slave role is supported
+ PTP_CFG_ONE_STEP_L2, ///< [R/-] supports the combination of One-Step and Layer2 mode
+ PTP_CFG_ONE_STEP_P2P, ///< [R/-] supports the combination of One-Step and P2P Delay Mechanism
+
+ PTP_CFG_TSU_RESET, ///< [R/-] supports TSU reset via register cmd
+ PTP_CFG_NTP_HW_TS_MASTER, ///< [R/-] supports the NTP HW time stamping in Master mode
+ PTP_CFG_NTP_HW_TS_SLAVE, ///< [R/-] supports the NTP HW time stamping in Slave mode
+ PTP_CFG_SYNCE_MASTER, ///< [R/-] Hardware supports Synchronous Ethernet Out
+ PTP_CFG_SYNCE_SLAVE, ///< [R/-] Hardware supports Synchronous Ethernet In
+ PTP_CFG_HAS_MUX, ///< [R/-] Hardware supports multiplexed signal outputs
+ PTP_CFG_CAN_BE_TIME_MONITOR, ///< [R/-] can be Monitoring device for external PTP or NTP devices //### TODO Shouldn't this be an XFEATURE flag?
+ PTP_CFG_HAS_STATISTICS, ///< [R/-] ::MBG_PTP_STATISTICS_INFO can be queried
+
+ PTP_CFG_CAN_BE_V1_MASTER, ///< [R/-] supports PTPv1 MASTER role
+ PTP_CFG_CAN_BE_V1_SLAVE, ///< [R/-] supports PTPv1 SLAVE role
+ PTP_CFG_HAS_V2_COMMON_DATASETS, ///< [R/-] PTPv2 common dataset structures (see IEEE1588-2008, chapter 8.2) can be queried
+ PTP_CFG_HAS_V1_COMMON_DATASETS, ///< [R/-] PTPv1 common dataset structures can be queried
+
N_PTP_CFG_FLAGS ///< the number of defined flags
};
/**
- * @brief Bit masks associated to ::PTP_CFG_FLAGS
- */
-enum PTP_CFG_FLAG_MASKS
-{
- PTP_CFG_MSK_TIME_SCALE_IS_PTP = ( 1UL << PTP_CFG_TIME_SCALE_IS_PTP ), ///< see ::PTP_CFG_TIME_SCALE_IS_PTP
- PTP_CFG_MSK_V1_HW_COMPAT = ( 1UL << PTP_CFG_V1_HW_COMPAT ), ///< see ::PTP_CFG_V1_HW_COMPAT
- PTP_CFG_MSK_CAN_BE_UNICAST_SLAVE = ( 1UL << PTP_CFG_CAN_BE_UNICAST_SLAVE ), ///< see ::PTP_CFG_CAN_BE_UNICAST_SLAVE
- PTP_CFG_MSK_CAN_BE_MULTICAST_MASTER = ( 1UL << PTP_CFG_CAN_BE_MULTICAST_MASTER ), ///< see ::PTP_CFG_CAN_BE_MULTICAST_MASTER
- PTP_CFG_MSK_CAN_BE_UNICAST_MASTER = ( 1UL << PTP_CFG_CAN_BE_UNICAST_MASTER ), ///< see ::PTP_CFG_CAN_BE_UNICAST_MASTER
- PTP_CFG_MSK_CAN_BE_MULTICAST_AUTO = ( 1UL << PTP_CFG_CAN_BE_MULTICAST_AUTO ), ///< see ::PTP_CFG_CAN_BE_MULTICAST_AUTO
- PTP_CFG_MSK_SUPP_UTC_VALID = ( 1UL << PTP_CFG_SUPP_UTC_VALID ), ///< see ::PTP_CFG_SUPP_UTC_VALID
- PTP_CFG_MSK_CAN_BE_BOTH_MASTER = ( 1UL << PTP_CFG_CAN_BE_BOTH_MASTER ), ///< see ::PTP_CFG_CAN_BE_BOTH_MASTER
- PTP_CFG_MSK_CAN_BE_HYBRID_MASTER = ( 1UL << PTP_CFG_CAN_BE_HYBRID_MASTER ), ///< see ::PTP_CFG_CAN_BE_HYBRID_MASTER
- PTP_CFG_MSK_CAN_BE_HYBRID_SLAVE = ( 1UL << PTP_CFG_CAN_BE_HYBRID_SLAVE ), ///< see ::PTP_CFG_CAN_BE_HYBRID_SLAVE
- PTP_CFG_MSK_ONE_STEP_MASTER = ( 1UL << PTP_CFG_ONE_STEP_MASTER ), ///< see ::PTP_CFG_ONE_STEP_MASTER
- PTP_CFG_MSK_MNGMNT_MSGS_DISB = ( 1UL << PTP_CFG_MNGMNT_MSGS_DISB ) ///< see ::PTP_CFG_MNGMNT_MSGS_DISB
-};
+ * @defgroup group_PTP_CFG_FLAG_MASKS Bit masks used with PTP_CFG_INFO::supp_flags and PTP_CFG_SETTINGS::flags
+ *
+ * @see ::PTP_CFG_INFO::supp_flags
+ * @see ::PTP_CFG_SETTINGS::flags
+ * @see ::PTP_CFG_FLAGS
+ *
+ * @anchor PTP_CFG_FLAG_MASKS
+ *
+ * @{ */
+
+#define PTP_CFG_MSK_TIME_SCALE_IS_PTP ( 1UL << PTP_CFG_TIME_SCALE_IS_PTP ) ///< see ::PTP_CFG_TIME_SCALE_IS_PTP
+#define PTP_CFG_MSK_V1_HW_COMPAT ( 1UL << PTP_CFG_V1_HW_COMPAT ) ///< see ::PTP_CFG_V1_HW_COMPAT
+#define PTP_CFG_MSK_CAN_BE_UNICAST_SLAVE ( 1UL << PTP_CFG_CAN_BE_UNICAST_SLAVE ) ///< see ::PTP_CFG_CAN_BE_UNICAST_SLAVE
+#define PTP_CFG_MSK_CAN_BE_MULTICAST_MASTER ( 1UL << PTP_CFG_CAN_BE_MULTICAST_MASTER ) ///< see ::PTP_CFG_CAN_BE_MULTICAST_MASTER
+#define PTP_CFG_MSK_CAN_BE_UNICAST_MASTER ( 1UL << PTP_CFG_CAN_BE_UNICAST_MASTER ) ///< see ::PTP_CFG_CAN_BE_UNICAST_MASTER
+#define PTP_CFG_MSK_CAN_BE_MULTICAST_AUTO ( 1UL << PTP_CFG_CAN_BE_MULTICAST_AUTO ) ///< see ::PTP_CFG_CAN_BE_MULTICAST_AUTO
+#define PTP_CFG_MSK_SUPP_UTC_VALID ( 1UL << PTP_CFG_SUPP_UTC_VALID ) ///< see ::PTP_CFG_SUPP_UTC_VALID
+#define PTP_CFG_MSK_CAN_BE_BOTH_MASTER ( 1UL << PTP_CFG_CAN_BE_BOTH_MASTER ) ///< see ::PTP_CFG_CAN_BE_BOTH_MASTER
+
+#define PTP_CFG_MSK_HYBRID_MASTER ( 1UL << PTP_CFG_HYBRID_MASTER ) ///< see ::PTP_CFG_HYBRID_MASTER
+#define PTP_CFG_MSK_HYBRID_SLAVE ( 1UL << PTP_CFG_HYBRID_SLAVE ) ///< see ::PTP_CFG_HYBRID_SLAVE
+#define PTP_CFG_MSK_ONE_STEP_MASTER ( 1UL << PTP_CFG_ONE_STEP_MASTER ) ///< see ::PTP_CFG_ONE_STEP_MASTER
+#define PTP_CFG_MSK_MNGMNT_MSGS_DISB ( 1UL << PTP_CFG_MNGMNT_MSGS_DISB ) ///< see ::PTP_CFG_MNGMNT_MSGS_DISB
+#define PTP_CFG_MSK_SUPP_MCAST_SLAVE_FLAG ( 1UL << PTP_CFG_SUPP_MCAST_SLAVE_FLAG ) ///< see ::PTP_CFG_SUPP_MCAST_SLAVE_FLAG
+#define PTP_CFG_MSK_CAN_BE_MULTICAST_SLAVE ( 1UL << PTP_CFG_CAN_BE_MULTICAST_SLAVE ) ///< see ::PTP_CFG_CAN_BE_MULTICAST_SLAVE
+#define PTP_CFG_MSK_ONE_STEP_L2 ( 1UL << PTP_CFG_ONE_STEP_L2 ) ///< see ::PTP_CFG_ONE_STEP_L2
+#define PTP_CFG_MSK_ONE_STEP_P2P ( 1UL << PTP_CFG_ONE_STEP_P2P ) ///< see ::PTP_CFG_ONE_STEP_P2P
+
+#define PTP_CFG_MSK_TSU_RESET ( 1UL << PTP_CFG_TSU_RESET ) ///< see ::PTP_CFG_TSU_RESET
+#define PTP_CFG_MSK_NTP_HW_TS_MASTER ( 1UL << PTP_CFG_NTP_HW_TS_MASTER ) ///< see ::PTP_CFG_NTP_HW_TS_MASTER
+#define PTP_CFG_MSK_NTP_HW_TS_SLAVE ( 1UL << PTP_CFG_NTP_HW_TS_SLAVE) ///< see ::PTP_CFG_NTP_HW_TS_SLAVE
+#define PTP_CFG_MSK_SYNCE_MASTER ( 1UL << PTP_CFG_SYNCE_MASTER ) ///< see ::PTP_CFG_SYNCE_MASTER
+#define PTP_CFG_MSK_SYNCE_SLAVE ( 1UL << PTP_CFG_SYNCE_SLAVE ) ///< see ::PTP_CFG_SYNCE_SLAVE
+#define PTP_CFG_MSK_HAS_MUX ( 1UL << PTP_CFG_HAS_MUX ) ///< see ::PTP_CFG_HAS_MUX
+#define PTP_CFG_MSK_CAN_BE_TIME_MONITOR ( 1UL << PTP_CFG_CAN_BE_TIME_MONITOR ) ///< see ::PTP_CFG_CAN_BE_TIME_MONITOR
+#define PTP_CFG_MSK_HAS_STATISTICS ( 1UL << PTP_CFG_HAS_STATISTICS ) ///< see ::PTP_CFG_HAS_STATISTICS
+
+#define PTP_CFG_MSK_CAN_BE_V1_MASTER ( 1UL << PTP_CFG_CAN_BE_V1_MASTER ) ///< see ::PTP_CFG_CAN_BE_V1_MASTER
+#define PTP_CFG_MSK_CAN_BE_V1_SLAVE ( 1UL << PTP_CFG_CAN_BE_V1_SLAVE ) ///< see ::PTP_CFG_CAN_BE_V1_SLAVE
+#define PTP_CFG_MSK_HAS_V2_COMMON_DATASETS ( 1UL << PTP_CFG_HAS_V2_COMMON_DATASETS ) ///< see ::PTP_CFG_HAS_V2_COMMON_DATASETS
+#define PTP_CFG_MSK_HAS_V1_COMMON_DATASETS ( 1UL << PTP_CFG_HAS_V1_COMMON_DATASETS ) ///< see ::PTP_CFG_HAS_V1_COMMON_DATASETS
+
+/** @} defgroup group_PTP_CFG_FLAG_MASKS */
+
-/** @brief A bit mask of the role bits within the flag bits */
-#define PTP_CFG_MSK_SUPPORT_PTP_ROLES ( PTP_CFG_MSK_CAN_BE_UNICAST_SLAVE | \
- PTP_CFG_MSK_CAN_BE_MULTICAST_MASTER | \
- PTP_CFG_MSK_CAN_BE_UNICAST_MASTER | \
- PTP_CFG_MSK_CAN_BE_MULTICAST_AUTO )
/** @brief A bit mask of the unicast role bits within the flag bits */
#define PTP_CFG_MSK_SUPPORT_PTP_UNICAST ( PTP_CFG_MSK_CAN_BE_UNICAST_SLAVE | \
PTP_CFG_MSK_CAN_BE_UNICAST_MASTER )
+
+
+/**
+ * @brief Register in TSU-GbE FPGA to determine board features of the current TSU board revision
+ */
+typedef uint16_t PTP_HW_FEATURES;
+
+
+
/**
- * @brief Derive a "supported PTP roles" bit mask from PTP_CFG_INFO::supp_flags
+ * @brief Bits used to define ::PTP_HW_FEAT_MASKS
+ */
+enum PTP_HW_FEAT_BITS
+{
+ PTP_FEAT_SYNCE_EXT_MUX, ///< [R] supports SyncE and external signal multiplexer
+ N_PTP_HW_FEAT ///< the number of defined features
+};
+
+
+// TODO fix comment linkage
+/**
+ * @brief Bit masks used with ::PTP_HW_FEATURES
*
- * There's no explicite flag to indicate that the role of a multicast slave
- * is supported, since this role is always supported. The sequence of flags
- * indicating that a specific optional role is supported matches the enumerated
- * roles above, but don't start at bit 0. So we compine the optional flag bits
- * with the LSB always set for the implicite multicast slave role to yield
- * a bit mask which according to the enumerated roles.
+ * @see ::PTP_HW_FEAT_BITS
*/
-#define _get_supp_ptp_role_idx_msk( _f ) \
- ( 1UL | ( ( (_f) & PTP_CFG_MSK_SUPPORT_PTP_ROLES ) >> ( PTP_CFG_CAN_BE_UNICAST_SLAVE - 1 ) ) )
+enum PTP_HW_FEAT_MASKS
+{
+ PTP_HW_FEAT_MSK_SYNCE_EXT_MUX = ( 1UL << PTP_FEAT_SYNCE_EXT_MUX ) ///< see ::PTP_FEAT_SYNCE_EXT_MUX
+};
/**
* @brief Known optional PTP protocol extensions, see ::PTP_CFG_SETTINGS::opt_ext
*
- * @see PTP_PROFILE_STRS
- * @see PTP_OPT_EXT_MASKS
+ * @see ::PTP_OPT_EXT_MASKS
*/
enum PTP_OPT_EXTS
{
- PTP_OPT_EXT_NONE, ///< no extension used
- PTP_OPT_EXT_POWER, ///< IEEE C37.238 profile extension
- PTP_OPT_EXT_TELECOM, ///< ITU-T G.8265.1 profile extension
- N_PTP_OPT_EXT ///< number of known optional extension
+ PTP_OPT_EXT_NONE, ///< no extension used
+ PTP_OPT_EXT_POWER, ///< IEEE C37.238-2011 profile extension
+ PTP_OPT_EXT_TELECOM, ///< ITU-T G.8265.1 profile extension
+ PTP_OPT_EXT_TELECOM_PHASE, ///< ITU-T G.8275.1 profile extension
+ PTP_OPT_EXT_SMPTE, ///< SMPTE ST 2059-2 profile extension
+ PTP_OPT_EXT_8021AS, ///< IEEE 802.1AS profile extension
+ PTP_OPT_EXT_6185093, ///< IEC/IEEE FDIS 61850-9-3 Power Utility profile extension
+ PTP_OPT_EXT_TELECOM_PTS, ///< ITU-T G.8275.2 profile extension
+ N_PTP_OPT_EXT ///< number of known optional extensions
};
/**
- * @brief Flag masks used with PTP_CFG_INFO::supp_opt_ext
+ * @brief Flag masks used with ::PTP_CFG_INFO::supp_opt_ext
*
- * @see PTP_OPT_EXTS
+ * @see ::PTP_OPT_EXTS
*/
enum PTP_OPT_EXT_MASKS
{
- // no bit mask is used for PTP_OPT_EXT_NONE, so bit 0 corresponds to
- PTP_MSK_OPT_EXT_NONE = ( 1UL << PTP_OPT_EXT_NONE ), ///< this is actually not used, see ::PTP_OPT_EXT_NONE
- PTP_MSK_OPT_EXT_POWER = ( 1UL << PTP_OPT_EXT_POWER ), ///< see ::PTP_OPT_EXT_POWER
- PTP_MSK_OPT_EXT_TELECOM = ( 1UL << PTP_OPT_EXT_TELECOM ) ///< see ::PTP_OPT_EXT_TELECOM
+ PTP_MSK_OPT_EXT_NONE = ( 1UL << PTP_OPT_EXT_NONE ), ///< this is actually not used, see ::PTP_OPT_EXT_NONE
+ PTP_MSK_OPT_EXT_POWER = ( 1UL << PTP_OPT_EXT_POWER ), ///< see ::PTP_OPT_EXT_POWER
+ PTP_MSK_OPT_EXT_TELECOM = ( 1UL << PTP_OPT_EXT_TELECOM ), ///< see ::PTP_OPT_EXT_TELECOM
+ PTP_MSK_OPT_EXT_TELECOM_PHASE = ( 1UL << PTP_OPT_EXT_TELECOM_PHASE ), ///< see ::PTP_OPT_EXT_TELECOM_PHASE
+ PTP_MSK_OPT_EXT_SMPTE = ( 1UL << PTP_OPT_EXT_SMPTE ), ///< see ::PTP_OPT_EXT_SMPTE
+ PTP_MSK_OPT_EXT_8021AS = ( 1UL << PTP_OPT_EXT_8021AS ), ///< see ::PTP_OPT_EXT_8021AS
+ PTP_MSK_OPT_EXT_6185093 = ( 1UL << PTP_OPT_EXT_6185093 ), ///< see ::PTP_OPT_EXT_6185093
+ PTP_MSK_OPT_EXT_TELECOM_PTS = ( 1UL << PTP_OPT_EXT_TELECOM_PTS ) ///< see ::PTP_OPT_EXT_TELECOM_PTS
};
-#if !defined( USE_NEW_PTP_PRESETS )
- //##++++ by default use definitions in ptp2_cnf.h for now
- #define USE_NEW_PTP_PRESETS 1
-#endif
-
-#if USE_NEW_PTP_PRESETS
-
/**
- * @brief Enumeration of PTP configuration presets
+ * @brief Enumeration of PTP cfg presets used with ::PTP_CFG_SETTINGS::selected_presets
*
- * This can be used by configuration programs
+ * This can be used by configuration programs to determine
+ * the last recently selected presets.
*
- * @see PTP_PRESETS_STRS
- * @see PTP_PRESETS_MASKS
+ * @see ::PTP_PRESETS_STRS
+ * @see ::PTP_PRESETS_MASKS
*/
enum PTP_PRESETS
{
- PTP_PRESETS_CUSTOM, ///< customizable, always supported
- PTP_PRESETS_DFLT_E2E, ///< pure IEEE1588-2008 (PTPv2) with E2E
- PTP_PRESETS_DFLT_P2P, ///< pure IEEE1588-2008 (PTPv2) with P2P
- PTP_PRESETS_POWER, ///< IEEE C37.238 profile extension, only if ::PTP_MSK_OPT_EXT_POWER is set
- PTP_PRESETS_TELECOM, ///< ITU-T G.8265.1 profile extension, only if ::PTP_MSK_OPT_EXT_TELECOM is set
- N_PTP_PRESETS ///< number of supported profiles
+ PTP_PRESETS_CUSTOM, ///< customizable, always supported
+ PTP_PRESETS_DFLT_E2E, ///< pure IEEE1588-2008 (PTPv2) with E2E
+ PTP_PRESETS_DFLT_P2P, ///< pure IEEE1588-2008 (PTPv2) with P2P
+ PTP_PRESETS_POWER, ///< IEEE C37.238 profile extension, only if ::PTP_MSK_OPT_EXT_POWER is set
+ PTP_PRESETS_TELECOM, ///< ITU-T G.8265.1 profile extension, only if ::PTP_MSK_OPT_EXT_TELECOM is set
+ PTP_PRESETS_TELECOM_PHASE, ///< ITU-T G.8275.1 profile extension, only if ::PTP_MSK_OPT_EXT_TELECOM_PHASE is set
+ PTP_PRESETS_SMPTE, ///< SMPTE ST 2059-2 profile extension, only if ::PTP_MSK_OPT_EXT_SMPTE is set
+ PTP_PRESETS_AES67, ///< AES67 media profile
+ PTP_PRESETS_8021AS, ///< IEEE 802.1AS -like profile, only if ::PTP_MSK_OPT_EXT_8021AS is set
+ PTP_PRESETS_6185093, ///< IEC/IEEE FDIS 61850-9-3, only if ::PTP_MSK_OPT_EXT_6185093 is set
+ PTP_PRESETS_TELECOM_PTS, ///< ITU-T G.8275.2 profile extension, only if ::PTP_MSK_OPT_EXT_TELECOM_PTS is set
+ PTP_PRESETS_DOCSIS_31, ///< only if ::PTP_MSK_OPT_EXT_TELECOM_PHASE is set
+ N_PTP_PRESETS ///< number of supported presets
};
/**
- * @brief Flags used with PTP_CFG_SETTINGS::profile and PTP_CFG_INFO::supp_profiles
+ * @brief Flag masks used with ::PTP_CFG_INFO::supp_opt_ext
*
- * @see PTP_PRESETS
+ * @see ::PTP_PRESETS
*/
enum PTP_PRESETS_MASKS
{
- PTP_MSK_PRESETS_CUSTOM = ( 1UL << PTP_PRESETS_CUSTOM ), ///< see ::PTP_PRESETS_CUSTOM
- PTP_MSK_PRESETS_DFLT_E2E = ( 1UL << PTP_PRESETS_DFLT_E2E ), ///< see ::PTP_PRESETS_DFLT_E2E
- PTP_MSK_PRESETS_DFLT_P2P = ( 1UL << PTP_PRESETS_DFLT_P2P ), ///< see ::PTP_PRESETS_DFLT_P2P
- PTP_MSK_PRESETS_POWER = ( 1UL << PTP_PRESETS_POWER ), ///< see ::PTP_PRESETS_POWER
- PTP_MSK_PRESETS_TELECOM = ( 1UL << PTP_PRESETS_TELECOM ) ///< see ::PTP_PRESETS_TELECOM
+ PTP_MSK_PRESETS_CUSTOM = ( 1UL << PTP_PRESETS_CUSTOM ), ///< see ::PTP_PRESETS_CUSTOM
+ PTP_MSK_PRESETS_DFLT_E2E = ( 1UL << PTP_PRESETS_DFLT_E2E ), ///< see ::PTP_PRESETS_DFLT_E2E
+ PTP_MSK_PRESETS_DFLT_P2P = ( 1UL << PTP_PRESETS_DFLT_P2P ), ///< see ::PTP_PRESETS_DFLT_P2P
+ PTP_MSK_PRESETS_POWER = ( 1UL << PTP_PRESETS_POWER ), ///< see ::PTP_PRESETS_POWER
+ PTP_MSK_PRESETS_TELECOM = ( 1UL << PTP_PRESETS_TELECOM ), ///< see ::PTP_PRESETS_TELECOM
+ PTP_MSK_PRESETS_TELECOM_PHASE = ( 1UL << PTP_PRESETS_TELECOM_PHASE ), ///< see ::PTP_PRESETS_TELECOM_PHASE
+ PTP_MSK_PRESETS_SMPTE = ( 1UL << PTP_PRESETS_SMPTE ), ///< see ::PTP_PRESETS_SMPTE
+ PTP_MSK_PRESETS_AES67 = ( 1UL << PTP_PRESETS_AES67 ), ///< see ::PTP_PRESETS_AES67
+ PTP_MSK_PRESETS_8021AS = ( 1UL << PTP_PRESETS_8021AS ), ///< see ::PTP_PRESETS_8021AS
+ PTP_MSK_PRESETS_6185093 = ( 1UL << PTP_PRESETS_6185093), ///< see ::PTP_PRESETS_6185093
+ PTP_MSK_PRESETS_TELECOM_PTS = ( 1UL << PTP_PRESETS_TELECOM_PTS), ///< see ::PTP_PRESETS_TELECOM_PTS
+ PTP_MSK_PRESETS_DOCSIS_31 = ( 1UL << PTP_PRESETS_DOCSIS_31) ///< see ::PTP_PRESETS_DOCSIS_31
};
/**
- * @brief Name strings for defined PTP profiles
+ * @brief Name strings for defined PTP presets
*
- * @see PTP_PRESETS
+ * @see ::PTP_PRESETS
*/
-#define PTP_PRESETS_STRS \
-{ \
- "Custom", \
- "Default E2E", \
- "Default P2P", \
- "Power", \
- "Telecom" \
+#define PTP_PRESETS_STRS \
+{ \
+ "Custom", \
+ "Default E2E IEEE1588-2008", \
+ "Default P2P IEEE1588-2008", \
+ "Power IEEE C37.238", \
+ "Telecom ITU-T G.8265.1", \
+ "Telecom ITU-T G.8275.1", \
+ "SMPTE ST 2059-2", \
+ "AES67 Media Profile", \
+ "IEEE 802.1AS", \
+ "Utility IEC 61850-9-3", \
+ "Telecom ITU-T G.8275.2", \
+ "DOCSIS 3.1" \
}
-#endif // USE_NEW_PTP_PRESETS
-
/**
@@ -6478,7 +13917,7 @@ enum PTP_PRESETS_MASKS
typedef struct
{
uint32_t network_incaccuracy; ///< Pre-defined network inaccuracy from master in [ns]
- uint8_t grandmaster_id; ///< [PTP_POWER_PROFILE_GM_ID_MIN..PTP_POWER_PROFILE_GM_ID_MAX]
+ uint8_t grandmaster_id; ///< [::PTP_POWER_PROFILE_GM_ID_MIN..::PTP_POWER_PROFILE_GM_ID_MAX]
uint8_t reserved_1;
uint16_t reserved_2;
TZDL tzdl;
@@ -6486,6 +13925,7 @@ typedef struct
} PTP_POWER_PROFILE_CFG;
#define _mbg_swab_ptp_power_profile_cfg( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->network_incaccuracy ); \
_mbg_swab8( &(_p)->grandmaster_id ); \
@@ -6493,18 +13933,488 @@ typedef struct
_mbg_swab16( &(_p)->reserved_2 ); \
_mbg_swab_tzdl( &(_p)->tzdl ); \
_mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+#if defined( _PRELIMINARY_CODE )
+
+// TODO: These definitions are preliminary and maybe subject to changes.
+
+/**
+ * @brief SMPTE System Frame Rates according to SMPTE ST 2059-2
+ *
+ * @see ::TODO
+ */
+enum SMPTE_SYSTEM_FRAME_RATES
+{
+ SMPTE_23_98HZ,
+ SMPTE_24HZ,
+ SMPTE_25HZ,
+ SMPTE_29_97HZ,
+ SMPTE_50HZ,
+ SMPTE_59_94HZ,
+ N_SMPTE_SYSTEM_FRAME_RATES
+};
+
+
+#define SMPTE_SYSTEM_FRAME_RATE_STR \
+{ \
+ "24Hz (23.98)", \
+ "24Hz", \
+ "25Hz", \
+ "30Hz (29.97)", \
+ "50Hz", \
+ "60Hz (59.94)" \
+}
+
+
+#define SMPTE_FRAME_RATE_NUM \
+{ \
+ 24000, \
+ 24000, \
+ 25000, \
+ 30000, \
+ 50000, \
+ 60000, \
}
+#define SMPTE_FRAME_RATE_DENUM \
+{ \
+ 1001, \
+ 1000, \
+ 1000, \
+ 1001, \
+ 1000, \
+ 1001, \
+}
/**
- * @brief A host's fully qualified domain name (FQDN), or a numeric IP address string
+ * @brief Additional parameters for SMPTE ST 2059-2 profile
*
- * In theory each single component (host name, domain name, top level domain name)
- * of a FQDN can have up to 63 characters, but the overall length is limited to
- * 255 characters. We specify one more character for the trailing 0.
+ * This stucture holds the synchronization metadata required for the SMPTE profile.
+ * This structure is only used for internal storage of the data. The data is
+ * distributed through a network by using management messages and the dedicated
+ * organization extension TLV defined in the SMPTE profile.
+ */
+typedef struct
+{
+ /// Default system frame rate
+ /// Default video frame rate of the slave system as a lowest term rational.
+ /// The data type shall be composed of a pair of unsigned Int32 values coded
+ /// in big-endian form where the first shall be the numerator and the second
+ /// shall be the denominator. The denominator shall be the smallest value
+ /// that represents the frame rate denominator
+ /// For example, 29.97 Hz: (30000/1001) or 25 Hz: (25/1).
+ uint32_t defaultSystemFrameRateNum;
+ uint32_t defaultSystemFrameRateDenum;
+ /// Master locking status
+ /// Complementary information to clockClass (0: Not in use, 1: Free Run,
+ /// 2: Cold Locking, 3: Warm Locking, 4: Locked)
+ uint8_t masterLockingStatus;
+ /// Time Address Flags
+ /// Indicates the intended ST 12-1 flags.
+ /// Bit 0: Drop frame (0: Non-drop-frame, 1: Drop-frame)
+ /// Bit 1: Color Frame Identification (0: Not in use, 1: In use)
+ /// Bits 2-7: Reserved
+ uint8_t timeAddressFlags;
+ /// Current local offset
+ /// Offset in seconds of Local Time from grandmaster PTP time. For example,
+ /// if Local Time is Eastern Standard Time (North America) UTC-5 and the
+ /// number of leap seconds is 35, the value will be -18035 (decimal).
+
+ uint8_t reserved_1;
+ uint8_t reserved_2;
+
+ int32_t currentLocalOffset;
+ /// Jump seconds
+ /// The size of the next discontinuity, in seconds, of Local Time. A value
+ /// of zero indicates that no discontinuity is expected. A positive value
+ /// indicates that the discontinuity will cause the currentLocalOffset to increase.
+ int32_t jumpSeconds;
+ /// Time of next jump
+ /// The value of the seconds portion of the grandmastermaster PTP time at the time
+ /// that the next discontinuity of the currentLocalOffset will occur. The
+ /// discontinuity occurs at the start of the second indicated
+ uint8_t timeOfNextJump[6];
+ /// Time of next jam
+ /// The value of the seconds portion of the PTP time corresponding to the next
+ /// scheduled occurrence of the Daily Jam. If no Daily Jam is scheduled, the
+ /// value of timeOfNextJam shall be zero.
+ uint8_t timeOfNextJam[6];
+ /// Time of previous jam
+ /// The value of the seconds portion of the PTP time corresponding to the
+ /// previous occurrence of the Daily Jam.
+ uint8_t timeOfPreviousJam[6];
+ /// Previous jam local offset
+ /// The value of currentLocalOffset at the previous daily jam time.
+ /// If a discontinuity of Local Time occurs at the jam time, this parameter
+ /// reflects the offset after the discontinuity.
+ uint8_t reserved_3;
+ uint8_t reserved_4;
+ uint32_t reserved_5;
+
+ int32_t previousJamLocalOffset;
+ /// Daylight saving
+ /// Bit 0: Current Daylight Saving (0: Not in effect, 1: In effect)
+ /// Bit 1: Daylight Saving at next discontinuity (0: Not in effect, 1: In effect)
+ /// Bit 2: Daylight Saving at previous daily jam time (0: Not in effect, 1: In effect)
+ /// Bits 3-7: Reserved
+ uint8_t daylightSaving;
+ /// Leap second jump
+ /// The reason for the forthcoming discontinuity of currentLocalOffset indicated by
+ /// timeOfNextJump
+ /// Bit 0:
+ /// 0: Other than a change in the number of leap seconds (default)
+ /// 1: A change in number of leap seconds
+ /// Bits 1-7: Reserved
+ uint8_t leapSecondJump;
+
+ uint8_t reserved_6;
+ uint8_t reserved_7;
+
+ uint32_t reserved_8;
+ uint32_t reserved_9;
+ uint32_t reserved_10;
+
+} PTP_SMPTE_PROFILE_CFG;
+
+
+
+/**
+ * @brief Additional parameters for Telecom8275.1 profile
*/
-typedef char MBG_HOSTNAME[256];
+typedef struct
+{
+ uint8_t use_alternate_multicast_address;
+ uint8_t reserved_1;
+ uint8_t reserved_2;
+ uint8_t reserved_3;
+ uint32_t reserved_4;
+
+} PTP_TELECOMG8275_PROFILE_CFG;
+
+#define _mbg_swab_ptp_telecom8275_profile_cfg( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->use_alternate_multicast_mac_address ); \
+ _mbg_swab8( &(_p)->reserved_1 ); \
+ _mbg_swab8( &(_p)->reserved_2 ); \
+ _mbg_swab8( &(_p)->reserved_3 ); \
+ _mbg_swab32( &(_p)->reserved_4 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief A type which holds one of the ITU-T SSM codes
+ *
+ * @see ::ITU_SSM_CODES
+ */
+typedef uint16_t ITU_SSM_CODE;
+
+
+
+/**
+ * @brief ITU-T SSM codes acc. to Recommendation G.781
+ *
+ * @see ::ITU_SSM_CODE
+ */
+enum ITU_SSM_CODES
+{
+ ITU_SSM_CODE_STU_UKN,
+ ITU_SSM_CODE_PRS,
+ ITU_SSM_CODE_PRC,
+ ITU_SSM_CODE_INV3,
+ ITU_SSM_CODE_SSU_A_TNC,
+ ITU_SSM_CODE_INV5,
+ ITU_SSM_CODE_INV6,
+ ITU_SSM_CODE_ST2,
+ ITU_SSM_CODE_SSU_B,
+ ITU_SSM_CODE_INV9,
+ ITU_SSM_CODE_ST3,
+ ITU_SSM_CODE_SEC,
+ ITU_SSM_CODE_SMC,
+ ITU_SSM_CODE_ST3E,
+ ITU_SSM_CODE_PROV,
+ ITU_SSM_CODE_DNU_DUS,
+ N_ITU_SSM_CODES
+};
+
+
+#define N_SSM_CODES_OPTION_1 5
+#define N_SSM_CODES_OPTION_2 9
+
+
+/**
+ * @brief Name strings for SSM codes, network option I
+ *
+ * @see ::ITU_SSM_CODES
+ */
+#define ITU_SSM_CODE_OPT_1_STRS \
+{ \
+ "", \
+ "", \
+ "QL-PRC", \
+ "", \
+ "QL-SSU-A", \
+ "", \
+ "", \
+ "", \
+ "QL-SSU-B", \
+ "", \
+ "", \
+ "QL-SEC", \
+ "", \
+ "", \
+ "", \
+ "QL-DNU" \
+}
+
+
+
+/**
+ * @brief Name strings for SSM codes, network option II
+ *
+ * @see ::ITU_SSM_CODES
+ */
+#define ITU_SSM_CODE_OPT_2_STRS \
+{ \
+ "QL-STU", \
+ "QL-PRS", \
+ "", \
+ "", \
+ "QL-TNC", \
+ "", \
+ "", \
+ "QL-ST2", \
+ "", \
+ "", \
+ "QL-ST3", \
+ "", \
+ "QL-SMC", \
+ "QL-ST3E", \
+ "QL-PROV", \
+ "QL-DUS" \
+}
+
+
+
+/**
+ * @brief Name strings for SSM codes, option I and II combined
+ *
+ * @see ::ITU_SSM_CODES
+ */
+#define ITU_SSM_CODE_STRS_COMBINED \
+{ \
+ "QL-STU/UKN", \
+ "QL-PRS", \
+ "QL-PRC", \
+ "QL-INV3", \
+ "QL-SSU-A/TNC", \
+ "QL-INV5", \
+ "QL-INV6", \
+ "QL-ST2", \
+ "QL-SSU-B", \
+ "QL-INV9", \
+ "QL-EEC2/ST3", \
+ "QL-EEC1/SEC", \
+ "QL-SMC", \
+ "QL-ST3E", \
+ "QL-PROV", \
+ "QL-DNU/DUS", \
+}
+
+
+
+/**
+ * @brief Maximum T1 SSM only quality levels
+ *
+ * @see ::T1_SSM_QLVL
+ * @see ::T1_SSM_QLVL_STRS
+ * @see ::T1_SSM_QLVL_ARRAY
+ */
+#define MAX_T1_SSM_QLVL 8
+
+
+
+/**
+ * @brief T1 SSM only quality level (6 bit encoded)
+ *
+ * @see ::MAX_T1_SSM_QLVL
+ * @see ::T1_SSM_QLVL_STRS
+ * @see ::T1_SSM_QLVL_ARRAY
+ */
+enum T1_SSM_QLVL
+{
+ T1_SSM_QLVL_ST1_TRACE = 2,
+ T1_SSM_QLVL_SYNC_TRACE_UNKNOWN = 4,
+ T1_SSM_QLVL_ST2_TRACE = 6,
+ T1_SSM_QLVL_ST3_TRACE = 8,
+ T1_SSM_QLVL_SONET_MIN_CLOCK_TRACE = 17,
+ T1_SSM_QLVL_ST4_TRACE = 20,
+ T1_SSM_QLVL_DNU_FOR_SYNC = 24,
+ T1_SSM_QLVL_RESERVED = 32
+};
+
+
+
+/**
+ * @brief T1 SSM only quality level array
+ *
+ * @see ::MAX_T1_SSM_QLVL
+ * @see ::T1_SSM_QLVL_STRS
+ * @see ::T1_SSM_QLVL
+ */
+#define T1_SSM_QLVL_ARRAY \
+{ \
+ T1_SSM_QLVL_ST1_TRACE, \
+ T1_SSM_QLVL_SYNC_TRACE_UNKNOWN, \
+ T1_SSM_QLVL_ST2_TRACE, \
+ T1_SSM_QLVL_ST3_TRACE, \
+ T1_SSM_QLVL_SONET_MIN_CLOCK_TRACE, \
+ T1_SSM_QLVL_ST4_TRACE, \
+ T1_SSM_QLVL_DNU_FOR_SYNC, \
+ T1_SSM_QLVL_RESERVED \
+}
+
+
+
+/**
+ * @brief Name strings for T1 SSM quality levels
+ *
+ * @see ::MAX_T1_SSM_QLVL
+ * @see ::T1_SSM_QLVL
+ * @see ::T1_SSM_QLVL_ARRAY
+ */
+#define T1_SSM_QLVL_STRS \
+{ \
+ "Stratum 1 traceable", \
+ "Synchronized traceability unknown", \
+ "Stratum 2 traceable", \
+ "Stratum 3 traceable", \
+ "SONET minimum clock traceable", \
+ "Stratum 4 traceable", \
+ "Do not use for sync", \
+ "Reserved for network sync" \
+}
+
+
+
+/**
+ * @brief SDH network options
+ *
+ * @see ::SDH_NETWORK_OPTION_MASKS
+ */
+enum SDH_NETWORK_OPTIONS
+{
+ SDH_NETWORK_OPTION_1,
+ SDH_NETWORK_OPTION_2,
+ N_SDH_NETWORK_OPTIONS
+
+};
+
+
+
+/**
+ * @brief Flag masks used with ::MBG_SYNC_E_INFO::supp_sdh_network_opts
+ *
+ * @see ::SDH_NETWORK_OPTIONS
+ */
+enum SDH_NETWORK_OPTION_MASKS
+{
+ SDH_NETWORK_OPTION_1_MSK = ( 1UL << SDH_NETWORK_OPTION_1 ), ///< see ::SDH_NETWORK_OPTION_1
+ SDH_NETWORK_OPTION_2_MSK = ( 1UL << SDH_NETWORK_OPTION_2 ), ///< see ::SDH_NETWORK_OPTION_2
+};
+
+
+
+/**
+ * @brief Name strings for SDH network options
+ *
+ * @see ::SDH_NETWORK_OPTION
+ */
+#define SDH_NETWORK_OPTION_STRS \
+{ \
+ "SDH Network Opt. 1", \
+ "SDH Network Opt. 2", \
+}
+
+
+
+//##++++ TODO: shouldn't this be merged with / replaced by MBG_NET_LINK_MODES?
+/**
+ * @brief Link modes for SyncE on a 1000BASE-T interface
+ *
+ * @see ::GBIT_LINK_COPPER_MODE_MASKS
+ */
+enum GBIT_LINK_COPPER_MODES
+{
+ GBIT_LINK_COPPER_AUTO, // valid if synce is disabled
+ GBIT_LINK_COPPER_FORCE_SYNCE_AUTO,
+ GBIT_LINK_COPPER_FORCE_OR_IS_MASTER, // Used in both structures, settings and status
+ GBIT_LINK_COPPER_FORCE_OR_IS_SLAVE, // Used in both structures, settings and status
+ GBIT_LINK_COPPER_PREFER_MASTER,
+ GBIT_LINK_COPPER_PREFER_SLAVE,
+ N_GBIT_LINK_COPPER_MODES
+};
+
+
+
+/**
+ * @brief Flag masks used with ::MBG_SYNC_E_INFO::supp_gbit_link_copper_modes
+ *
+ * @see ::GBIT_LINK_COPPER_MODES
+ */
+enum GBIT_LINK_COPPER_MODE_MASKS
+{
+ GBIT_LINK_COPPER_AUTO_MSK = ( 1UL << GBIT_LINK_COPPER_AUTO ), ///< see ::GBIT_LINK_COPPER_AUTO_MSK
+ GBIT_LINK_COPPER_FORCE_SYNCE_AUTO_MSK = ( 1UL << GBIT_LINK_COPPER_FORCE_SYNCE_AUTO ), ///< see ::GBIT_LINK_COPPER_FORCE_SYNCE_AUTO
+ GBIT_LINK_COPPER_FORCE_OR_IS_MASTER_MSK = ( 1UL << GBIT_LINK_COPPER_FORCE_OR_IS_MASTER ), ///< see ::GBIT_LINK_COPPER_FORCE_OR_IS_MASTER
+ GBIT_LINK_COPPER_FORCE_OR_IS_SLAVE_MSK = ( 1UL << GBIT_LINK_COPPER_FORCE_OR_IS_SLAVE ), ///< see ::GBIT_LINK_COPPER_FORCE_OR_IS_SLAVE
+ GBIT_LINK_COPPER_PREFER_MASTER_MSK = ( 1UL << GBIT_LINK_COPPER_PREFER_MASTER ), ///< see ::GBIT_LINK_COPPER_PREFER_MASTER
+ GBIT_LINK_COPPER_PREFER_SLAVE_MSK = ( 1UL << GBIT_LINK_COPPER_PREFER_SLAVE ) ///< see ::GBIT_LINK_COPPER_PREFER_SLAVE
+};
+
+
+
+//##++++ TODO: shouldn't this be merged with MBG_NET_LINK_ROLE_BITS / MBG_NET_LINK_ROLE_MASKS?
+/**
+ * @brief Link status for SyncE on a 1000BASE-T interface
+ *
+ * @see ::TODO
+ */
+enum GBIT_LINK_STATUS
+{
+ GBIT_LINK_COPPER_IS_MASTER, ///< GBIT Link is currently clock master
+ GBIT_LINK_COPPER_IS_SLAVE, ///< GBIT Link is currently clock slave
+ GBIT_LINK_COPPER_CFG_FAULT, ///< GBIT Link has a configruation fault (conflict with link partner
+ GBIT_LINK_COPPER_IS_FE, ///< Link is running on Fast Ethernet (no MASTER/SLAVE decision)
+ GBIT_LINK_DOWN, ///< Currently no link
+ GBIT_LINK_FIBER, ///< GBIT Linkup on SFP interface
+ N_GBIT_LINK_STATUS
+};
+
+
+#define GBIT_LINK_STATUS_STRS \
+{ \
+ "MASTER (1000BASE-T)", \
+ "SLAVE (1000BASE-T)", \
+ "CFG FAULT", \
+ "AUTO (100BASE-TX)", \
+ "LINK DOWN", \
+ "AUTO (SFP LINK UP)", \
+}
+
+#else // !defined( _PRELIMINARY_CODE ), dummy declarations
+
+typedef int PTP_SMPTE_PROFILE_CFG;
+typedef int PTP_TELECOMG8275_PROFILE_CFG;
+typedef int ITU_SSM_CODE;
+
+#endif // defined( _PRELIMINARY_CODE )
+
/**
@@ -6526,6 +14436,7 @@ typedef struct
} PTP_UC_MASTER_CFG_LIMITS;
#define _mbg_swab_ptp_uc_master_cfg_limits( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->n_supp_master ); \
_mbg_swab16( &(_p)->sync_intv_min ); \
@@ -6537,7 +14448,8 @@ typedef struct
_mbg_swab16( &(_p)->reserved_0 ); \
_mbg_swab32( &(_p)->supp_flags ); \
_mbg_swab32( &(_p)->reserved_1 ); \
-}
+} while ( 0 )
+
/**
@@ -6546,7 +14458,7 @@ typedef struct
* This structure is used on a unicast slave to specify the settings of
* a unicast master polled by the slave. The number of unicast masters
* which can be specified depends on the capabilities of the slave device
- * and is returned in PTP_UC_MASTER_CFG_LIMITS::n_supp_master.
+ * and is returned in ::PTP_UC_MASTER_CFG_LIMITS::n_supp_master.
*
* The structure ::PTP_UC_MASTER_SETTINGS_IDX should be sent to the device
* to save the configuration.
@@ -6568,6 +14480,7 @@ typedef struct
} PTP_UC_MASTER_SETTINGS;
#define _mbg_swab_ptp_uc_master_settings( _p ) \
+do \
{ \
_mbg_swab_ptp_clock_id( &(_p)->gm_clock_id ); \
_mbg_swab_ptp_port_id( &(_p)->gm_port_id ); \
@@ -6579,7 +14492,8 @@ typedef struct
_mbg_swab16( &(_p)->reserved_0 ); \
_mbg_swab32( &(_p)->reserved_1 ); \
_mbg_swab32( &(_p)->flags ); \
-}
+} while ( 0 )
+
/**
@@ -6606,16 +14520,18 @@ enum PTP_UC_MSG_DURATION_LIMITS
*/
typedef struct
{
- uint32_t idx; ///< index, 0..PTP_UC_MASTER_CFG_LIMITS::n_supp_master - 1
+ uint32_t idx; ///< index, 0..PTP_UC_MASTER_CFG_LIMITS::n_supp_master-1
PTP_UC_MASTER_SETTINGS settings; ///< specification for the unicast master with that index
} PTP_UC_MASTER_SETTINGS_IDX;
#define _mbg_swab_ptp_uc_master_settings_idx( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->idx ); \
_mbg_swab_ptp_uc_master_settings( &(_p)->settings ); \
-}
+} while ( 0 )
+
/**
@@ -6633,11 +14549,13 @@ typedef struct
} PTP_UC_MASTER_INFO;
#define _mbg_swab_ptp_uc_master_info( _p ) \
+do \
{ \
_mbg_swab_ptp_uc_master_settings( &(_p)->settings ); \
_mbg_swab32( &(_p)->reserved ); \
_mbg_swab32( &(_p)->flags ); \
-}
+} while ( 0 )
+
/**
@@ -6655,19 +14573,3114 @@ typedef struct
*/
typedef struct
{
- uint32_t idx; ///< index, 0..PTP_UC_MASTER_CFG_LIMITS::n_supp_master - 1
+ uint32_t idx; ///< index, 0..PTP_UC_MASTER_CFG_LIMITS::n_supp_master-1
PTP_UC_MASTER_INFO info; ///< capabilities and current settings
} PTP_UC_MASTER_INFO_IDX;
#define _mbg_swab_ptp_uc_master_info_idx( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->idx ); \
_mbg_swab_ptp_uc_master_info( &(_p)->info ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t counter_cfg;
+ uint32_t flags;
+ uint32_t reserved_1;
+ uint32_t reserved_2;
+
+} MBG_PTP_STATISTICS_SETTINGS;
+
+
+
+typedef struct
+{
+ MBG_PTP_STATISTICS_SETTINGS settings;
+ uint32_t supp_flags; ///< Supported settings, currently 0
+ uint32_t reserved_1;
+
+} MBG_PTP_STATISTICS_INFO;
+
+
+
+typedef struct
+{
+ uint32_t status; ///< status word flags (use PacketCounterStat_e)
+ uint32_t rx; ///< overall Rx packet counter
+ uint32_t rxPerSec; ///< overall Rx packet counter
+ uint32_t tx; ///< overall Tx packet counter
+ uint32_t txPerSec; ///< overall Tx packet counter
+ /// invalid Rx packet counter
+ /// Indicates one of the following issues: wrong PTP version, wrong domain number,
+ /// message from self, message from other BC port, multicast message in unicast mode
+ /// or message extraction error (size error or inconsistent format).
+ uint32_t errorRx;
+ uint32_t announceMsgRx; ///< Accepted Announce message Rx counter
+ uint32_t announceMsgPerSecRx; ///< Accepted Announce message Rx counter
+ uint32_t announceMsgTx; ///< Announce message Tx counter
+ uint32_t announceMsgPerSecTx; ///< Announce message Tx counter
+ uint32_t syncMsgRx; ///< Accepted Sync message Rx counter
+ uint32_t syncMsgPerSecRx; ///< Accepted Sync message Rx counter
+ uint32_t syncMsgTx; ///< Sync message Tx counter
+ uint32_t syncMsgPerSecTx; ///< Sync message Tx counter
+ uint32_t followUpMsgRx; ///< Accepted Follow-up message Rx counter
+ uint32_t followUpMsgPerSecRx; ///< Accepted Follow-up message Rx counter
+ uint32_t followUpMsgTx; ///< Follow-up message Tx counter
+ uint32_t followUpMsgPerSecTx; ///< Follow-up message Tx counter
+ uint32_t dlyReqMsgRx; ///< Accepted Delay request message Rx counter
+ uint32_t dlyReqMsgPerSecRx; ///< Accepted Delay request message Rx counter
+ uint32_t dlyReqMsgTx; ///< Delay request message Tx counter
+ uint32_t dlyReqMsgPerSecTx; ///< Delay request message Tx counter
+ uint32_t dlyRespMsgRx; ///< Accepted Delay response message Rx counter
+ uint32_t dlyRespMsgPerSecRx; ///< Accepted Delay response message Rx counter
+ uint32_t dlyRespMsgTx; ///< Delay response message Tx counter
+ uint32_t dlyRespMsgPerSecTx; ///< Delay response message Tx counter
+ uint32_t pDlyReqMsgRx; ///< Accepted PDelay Request message Rx counter
+ uint32_t pDlyReqMsgPerSecRx; ///< Accepted PDelay Request message Rx counter
+ uint32_t pDlyReqMsgTx; ///< PDelay Request message Tx counter
+ uint32_t pDlyReqMsgPerSecTx; ///< PDelay Request message Tx counter
+ uint32_t pDlyRespMsgRx; ///< Accepted PDelay Response message Rx counter
+ uint32_t pDlyRespMsgPerSecRx; ///< Accepted PDelay Response message Rx counter
+ uint32_t pDlyRespMsgTx; ///< PDelay Response message Tx counter
+ uint32_t pDlyRespMsgPerSecTx; ///< PDelay Response message Tx counter
+ uint32_t pDlyFollowUpRx; ///< Accepted PDelay Follow-Up message Rx counter
+ uint32_t pDlyFollowUpPerSecRx; ///< Accepted PDelay Follow-Up message Rx counter
+ uint32_t pDlyFollowUpTx; ///< PDelay Follow-Up message Tx counter
+ uint32_t pDlyFollowUpPerSecTx; ///< PDelay Follow-Up message Tx counter
+ uint32_t signallingRx; ///< Accepted Signalling message Rx counter
+ uint32_t signallingPerSecRx; ///< Accepted Signalling message Rx counter
+ uint32_t signallingTx; ///< Signalling message Tx counter
+ uint32_t signallingPerSecTx; ///< Signalling message Tx counter
+ uint32_t mgmtRx; ///< Accepted Management message Rx counter
+ uint32_t mgmtPerSecRx; ///< Accepted Management message Rx counter
+ uint32_t mgmtTx; ///< Management message Tx counter
+ uint32_t mgmtPerSecTx; ///< Management message Tx counter
+ uint32_t mgmtErr; ///< Management error counter (rx)
+ uint32_t annReceptTout; ///< Announce recept timeout count
+
+ uint32_t numUcConn; ///< Number of current Unicast client connections
+ uint32_t maxNumUcConn; ///< Maximum Number of Unicast client connections (due to licence or CPU performance)
+ uint32_t numMsgPerSec; ///< Number of all messages per second (TX/RX)
+ uint32_t maxMsgPerSec; ///< max allowed number of all messages per second in Multicast/Hybrid mode (due to licence or CPU performance)
+
+} MBG_PTP_STATISTICS_STATUS;
+
+
+
+enum PTP_V1_COMM_IDS
+{
+ V1_PTP_CLOSED,
+ V1_PTP_ETHER,
+ /* reserved */
+ V1_PTP_FFBUS = 4,
+ V1_PTP_PROFIBUS,
+ V1_PTP_LON,
+ V1_PTP_DNET,
+ V1_PTP_SDS,
+ V1_PTP_CONTROLNET,
+ V1_PTP_CANOPEN,
+ /* reserved */
+ V1_PTP_IEEE1394 = 243,
+ V1_PTP_IEEE802_11A,
+ V1_PTP_IEEE_WIRELESS,
+ V1_PTP_INFINIBAND,
+ V1_PTP_BLUETOOTH,
+ V1_PTP_IEEE802_15_1,
+ V1_PTP_IEEE1451_3,
+ V1_PTP_IEEE1451_5,
+ V1_PTP_USB,
+ V1_PTP_ISA,
+ V1_PTP_PCI,
+ V1_PTP_VXI,
+ V1_PTP_DEFAULT
+};
+
+
+
+#define PTP_CODE_STRING_LENGTH 4
+#define PTP_SUBDOMAIN_NAME_LENGTH 16
+
+
+/**
+ * @brief PTPv1 UUID structure used in ::MBG_PTP_V1_DEFAULT_DATASET
+ *
+ * @see ::MBG_PTP_V1_DEFAULT_DATASET
+ */
+typedef struct
+{
+ uint8_t communication_technology;
+ uint8_t reserved_1;
+ uint16_t reserved_2;
+ PTP_CLOCK_ID clock_uuid;
+ PTP_PORT_ID port_id;
+ uint16_t reserved_3;
+} PTP_V1_UUID;
+
+
+#define _mbg_swab_ptp_v1_uuid( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+ _mbg_swab_ptp_clock_id( &(_p)->clock_uuid ); \
+ _mbg_swab_ptp_port_id( &(_p)->port_id ); \
+ _mbg_swab16( &(_p)->reserved_3 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief PTPv1 default dataset flags
+ *
+ * @see ::PTP_V1_DEFAULT_DATASET_FLAGS_MASKS
+ */
+enum PTP_V1_DEFAULT_DATASET_FLAGS
+{
+ V1_DFLT_CLK_FOLLOWUP_CAPABLE,
+ V1_DFLT_PREFERRED,
+ V1_DFLT_INITIALIZABLE,
+ V1_DFLT_EXT_TIMING,
+ V1_DFLT_IS_BC
+};
+
+
+
+/**
+ * @brief PTPv1 default dataset flag masks used with ::MBG_PTP_V1_DEFAULT_DATASET::flags
+ *
+ * @see ::PTP_V1_DEFAULT_DATASET_FLAGS
+ */
+enum PTP_V1_DEFAULT_DATASET_FLAGS_MASKS
+{
+ V1_DFLT_MSK_CLK_FOLLOWUP_CAPABLE = ( 1UL << V1_DFLT_CLK_FOLLOWUP_CAPABLE ), ///< see ::V1_DFLT_CLK_FOLLOWUP_CAPABLE
+ V1_DFLT_MSK_PREFERRED = ( 1UL << V1_DFLT_PREFERRED ), ///< see ::V1_DFLT_PREFERRED
+ V1_DFLT_MSK_INITIALIZABLE = ( 1UL << V1_DFLT_INITIALIZABLE ), ///< see ::V1_DFLT_INITIALIZABLE
+ V1_DFLT_MSK_EXT_TIMING = ( 1UL << V1_DFLT_EXT_TIMING), ///< see ::V1_DFLT_EXT_TIMING
+ V1_DFLT_MSK_IS_BC = ( 1UL << V1_DFLT_IS_BC ) ///< see ::V1_DFLT_IS_BC
+};
+
+
+
+/**
+ * @brief PTPv1 default dataset containing global information about the device
+ *
+ * @see ::PTP_V1_UUID
+ */
+typedef struct {
+ PTP_V1_UUID uuid;
+ uint8_t clock_stratum;
+ uint8_t clock_identifier[PTP_CODE_STRING_LENGTH];
+ uint16_t clock_variance;
+ int8_t sync_interval;
+ uint8_t subdomain_name[PTP_SUBDOMAIN_NAME_LENGTH];
+ uint16_t number_ports;
+ uint16_t number_foreign_records;
+ uint32_t flags;
+} MBG_PTP_V1_DEFAULT_DATASET;
+
+
+#define _mbg_swab_ptp_v1_default_dataset( _p ) \
+do \
+{ \
+ _mbg_swab_ptp_v1_uuid( &(_p)->uuid ); \
+ _mbg_swab16( &(_p)->clock_variance ); \
+ _mbg_swab16( &(_p)->number_ports ); \
+ _mbg_swab16( &(_p)->number_foreign_records ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief PTPv1 current dataset containing information about the synchronization status of the device
+ *
+ * @see ::NANO_TIME
+ */
+typedef struct
+{
+ uint16_t steps_removed;
+ uint16_t reserved_1;
+ NANO_TIME offset_from_master;
+ NANO_TIME one_way_delay;
+} MBG_PTP_V1_CURRENT_DATASET;
+
+
+#define _mbg_swab_ptp_v1_current_dataset( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->steps_removed ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ _mbg_swab_nano_time( &(_p)->offset_from_master ); \
+ _mbg_swab_nano_time( &(_p)->one_way_delay ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief PTPv1 parent dataset flags
+ *
+ * @see ::PTP_V1_PARENT_DATASET_FLAGS_MASKS
+ */
+enum PTP_V1_PARENT_DATASET_FLAGS
+{
+ V1_PARENT_FOLLOWUP_CAPABLE,
+ V1_PARENT_EXT_TIMING,
+ V1_PARENT_STATS,
+ V1_PARENT_UTC_REASONABLE,
+ V1_PARENT_GM_PREFERRED,
+ V1_PARENT_GM_IS_BC
+};
+
+
+
+/**
+ * @brief PTPv1 parent dataset flag masks used with ::MBG_PTP_V1_PARENT_DATASET::flags
+ *
+ * @see ::PTP_V1_PARENT_DATASET_FLAGS
+ */
+enum PTP_V1_PARENT_DATASET_FLAGS_MASKS
+{
+ V1_PARENT_MSK_FOLLOWUP_CAPABLE = ( 1UL << V1_PARENT_FOLLOWUP_CAPABLE ), ///< see ::V1_PARENT_FOLLOWUP_CAPABLE
+ V1_PARENT_MSK_EXT_TIMING = ( 1UL << V1_PARENT_EXT_TIMING ), ///< see ::V1_PARENT_EXT_TIMING
+ V1_PARENT_MSK_STATS = ( 1UL << V1_PARENT_STATS ), ///< see ::V1_PARENT_STATS
+ V1_PARENT_MSK_UTC_REASONABLE = ( 1UL << V1_PARENT_UTC_REASONABLE ), ///< see ::V1_PARENT_UTC_REASONABLE
+ V1_PARENT_MSK_GM_PREFERRED = ( 1UL << V1_PARENT_GM_PREFERRED ), ///< see ::V1_PARENT_GM_PREFERRED
+ V1_PARENT_MSK_GM_IS_BC = ( 1UL << V1_PARENT_GM_IS_BC ) ///< see ::V1_PARENT_GM_IS_BC
+};
+
+
+
+/**
+ * @brief PTPv1 parent dataset containing information about the master (parent) of the device
+ *
+ * @see ::PTP_V1_UUID
+ */
+typedef struct
+{
+ PTP_V1_UUID uuid;
+ uint16_t parent_last_sync_sequence_number;
+ int16_t parent_variance;
+ int16_t observed_variance;
+ uint16_t reserved_1;
+ int32_t observed_drift;
+ PTP_V1_UUID grandmaster_uuid;
+ uint8_t grandmaster_stratum;
+ uint8_t grandmaster_identifier[PTP_CODE_STRING_LENGTH];
+ int16_t grandmaster_variance;
+ uint16_t grandmaster_sequence_number;
+ uint16_t reserved_2;
+ uint32_t flags;
+} MBG_PTP_V1_PARENT_DATASET;
+
+
+#define _mbg_swab_ptp_v1_parent_dataset( _p ) \
+do \
+{ \
+ _mbg_swab_ptp_v1_uuid( &(_p)->uuid ); \
+ _mbg_swab16( &(_p)->parent_last_sync_sequence_number ); \
+ _mbg_swab16( &(_p)->parent_variance ); \
+ _mbg_swab16( &(_p)->observed_variance ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->observed_drift ); \
+ _mbg_swab_ptp_v1_uuid( &(_p)->grandmaster_uuid ); \
+ _mbg_swab16( &(_p)->grandmaster_variance ); \
+ _mbg_swab16( &(_p)->grandmaster_sequence_number ); \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief PTPv1 time drop dataset flags
+ *
+ * @see ::PTP_V1_TIME_PROP_DATASET_FLAGS_MASKS
+ */
+enum PTP_V1_TIME_PROP_DATASET_DATASET_FLAGS
+{
+ V1_TPROP_LEAP_59,
+ V1_TPROP_LEAP_61,
+};
+
+
+
+/**
+ * @brief PTPv1 time drop dataset flag masks used with ::MBG_PTP_V1_TIME_PROP_DATASET::flags
+ *
+ * @see ::PTP_V1_TIME_PROP_DATASET_DATASET_FLAGS
+ */
+enum PTP_V1_TIME_PROP_DATASET_FLAGS_MASKS
+{
+ V1_TPROP_MSK_LEAP_59 = ( 1UL << V1_TPROP_LEAP_59 ), ///< see ::V1_TPROP_LEAP_59
+ V1_TPROP_MSK_LEAP_61 = ( 1UL << V1_TPROP_LEAP_61 ), ///< see ::V1_TPROP_LEAP_61
+};
+
+
+
+/**
+ * @brief PTPv1 time drop dataset
+ *
+ */
+typedef struct
+{
+ int16_t current_utc_offset;
+ uint16_t epoch_number;
+ uint32_t flags;
+} MBG_PTP_V1_TIME_PROPERTIES_DATASET;
+
+
+#define _mbg_swab_ptp_v1_time_properties_dataset( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->current_utc_offset ); \
+ _mbg_swab16( &(_p)->epoch_number ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief PTPv1 port dataset flags
+ *
+ * @see ::PTP_V1_PORT_DATASET_FLAGS_MASKS
+ */
+enum PTP_V1_PORT_DATASET_DATASET_FLAGS
+{
+ V1_PORT_DATASET_BURST_ENB,
+};
+
+
+
+/**
+ * @brief PTPv1 port dataset flag masks used with ::MBG_PTP_V1_PORT_DATASET::flags
+ *
+ * @see ::PTP_V1_PORT_DATASET_DATASET_FLAGS
+ */
+enum PTP_V1_PORT_DATASET_FLAGS_MASKS
+{
+ V1_PORT_DATASET_MSK_BURST_ENB = ( 1UL << V1_PORT_DATASET_BURST_ENB ), ///< see ::V1_PORT_DATASET_BURST_ENB
+};
+
+
+
+/**
+ * @brief PTPv1 port dataset containing information about the appropriate port of the device
+ *
+ * @see ::PTP_V1_UUID
+ */
+typedef struct
+{
+ uint8_t port_state;
+ uint8_t reserved_1;
+ uint16_t last_sync_event_sequence_number;
+ uint16_t last_general_event_sequence_number;
+ uint16_t reserved_2;
+ uint32_t subdomain_address;
+ uint16_t event_port_address;
+ uint16_t general_port_address;
+ PTP_V1_UUID uuid;
+ uint32_t flags;
+} MBG_PTP_V1_PORT_DATASET;
+
+
+#define _mbg_swab_ptp_v1_port_dataset( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->last_sync_event_sequence_number ); \
+ _mbg_swab16( &(_p)->last_general_event_sequence_number ); \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->subdomain_address ); \
+ _mbg_swab16( &(_p)->event_port_address ); \
+ _mbg_swab16( &(_p)->general_port_address ); \
+ _mbg_swab_ptp_v1_uuid( &(_p)->uuid ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Index structure for PTPv1 port dataset
+ *
+ * @note Port dataset with index 0..::MBG_PTP_V1_DEFAULT_DATASET::number_ports - 1 can be queried from a device
+ *
+ * @see ::MBG_PTP_V1_PORT_DATASET
+ */
+typedef struct
+{
+ uint16_t idx; ///< Index of the port dataset, 0..::MBG_PTP_V1_DEFAULT_DATASET::number_ports - 1
+ MBG_PTP_V1_PORT_DATASET port_dataset; ///< see ::MBG_PTP_V1_PORT_DATASET
+
+} MBG_PTP_V1_PORT_DATASET_IDX;
+
+
+#define _mbg_swab_ptp_v1_port_dataset_idx( _p ) \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ptp_v1_port_dataset( &(_p)->port_dataset ); \
+}
+
+
+/**
+ * @brief Flags structure for the PTPv2 default dataset
+ *
+ * @note For further information, see IEEE 1588-2008, chapters 8.2.1 and 15.5.3.3.1
+ *
+ * @see ::MBG_PTP_V2_DEFAULT_DATASET
+ */
+typedef struct
+{
+ uint8_t two_step : 1; ///< indicates, whether the clock is a two-step clock
+ uint8_t slave_only : 1; ///< indicates, whether the clock is a slave-only clock
+ uint8_t reserved : 6; ///< reserved, currently always 0
+
+} MBG_PTP_V2_DEFAULT_DATASET_FLAGS;
+
+#define _mbg_swab_ptp_v2_default_dataset_flags( _p ) \
+ _nop_macro_fnc()
+
+
+/**
+ * @brief PTPv2 default dataset
+ *
+ * @note For further information, see IEEE 1588-2008, chapters 8.2.1 and 15.5.3.3.1
+ *
+ * @see ::MBG_PTP_V2_DEFAULT_DATASET_FLAGS
+ * @see ::PTP_CLOCK_QUALITY
+ * @see ::PTP_CLOCK_ID
+ */
+typedef struct
+{
+ MBG_PTP_V2_DEFAULT_DATASET_FLAGS flags; ///< flags field, see ::MBG_PTP_V2_DEFAULT_DATASET_FLAGS
+ uint8_t reserved_1; ///< reserved, currently always 0
+ uint16_t number_ports; ///< number of PTP ports on the device
+ uint8_t priority_1; ///< priority 1 attribute for the local clock
+ PTP_CLOCK_QUALITY clock_quality; ///< quality of the local clock, see ::PTP_CLOCK_QUALITY
+ uint8_t priority_2; ///< priority 2 attribute for the local clock
+ PTP_CLOCK_ID clock_identity; ///< identity of the local clock, see ::PTP_CLOCK_ID
+ uint8_t domain_number; ///< domain attribute of the local clock
+ uint8_t reserved_2; ///< reserved, currently always 0
+
+} MBG_PTP_V2_DEFAULT_DATASET;
+
+
+#define _mbg_swab_ptp_v2_default_dataset( _p ) \
+{ \
+ _mbg_swab_ptp_v2_default_dataset_flags( &(_p)->flags ); \
+ _mbg_swab8( &(_p)->reserved_1 ); \
+ _mbg_swab16( &(_p)->number_ports ); \
+ _mbg_swab8( &(_p)->priority_1 ); \
+ _mbg_swab_ptp_clock_quality( &(_p)->clock_quality ); \
+ _mbg_swab8( &(_p)->priority_2 ); \
+ _mbg_swab_ptp_clock_id( &(_p)->clock_identity ); \
+ _mbg_swab8( &(_p)->domain_number ); \
+ _mbg_swab8( &(_p)->reserved_2 ); \
+}
+
+
+/**
+ * @brief PTPv2 current dataset
+ *
+ * @note For further information, see IEEE 1588-2008, chapters 8.2.2 and 15.5.3.4.1
+ *
+ * @see ::PTP_TIME_INTERVAL
+ */
+typedef struct
+{
+ uint16_t steps_removed; ///< number of communication paths between local clock and grandmaster
+ PTP_TIME_INTERVAL offset_from_master; ///< current time difference between master and slave, see ::PTP_TIME_INTERVAL
+ PTP_TIME_INTERVAL mean_path_delay; ///< current mean propagation time between master and slave, see ::PTP_TIME_INTERVAL
+
+} MBG_PTP_V2_CURRENT_DATASET;
+
+
+#define _mbg_swab_ptp_v2_current_dataset( _p ) \
+{ \
+ _mbg_swab16( &(_p)->steps_removed ); \
+ _mbg_swab_ptp_time_interval( &(_p)->offset_from_master ); \
+ _mbg_swab_ptp_time_interval( &(_p)->mean_path_delay ); \
+}
+
+
+/**
+ * @brief Flags structure for the PTPv2 parent dataset
+ *
+ * @note For further information, see IEEE 1588-2008, chapters 8.2.3.3 and 15.5.3.5.1.2
+ *
+ * @see ::MBG_PTP_V2_PARENT_DATASET
+ */
+typedef struct
+{
+ uint8_t parent_stats : 1; ///< indicates, whether the variance and change rate values are valid
+ uint8_t reserved : 7; ///< reserved, currently always 0
+
+} MBG_PTP_V2_PARENT_DATASET_FLAGS;
+
+#define _mbg_swab_ptp_v2_parent_dataset_flags( _p )\
+ _nop_macro_fnc()
+
+
+
+/**
+ * @brief PTPv2 parent dataset
+ *
+ * @note For further information, see IEEE 1588-2008, chapters 8.2.3 and 15.5.3.5.1
+ *
+ * @see ::PTP_PORT_IDENTITY
+ * @see ::MBG_PTP_V2_PARENT_DATASET_FLAGS
+ * @see ::PTP_CLOCK_QUALITY
+ * @see ::PTP_CLOCK_ID
+ */
+typedef struct
+{
+ PTP_PORT_IDENTITY parent_port_identity; ///< identity of the master port, that issues the sync messages, see ::PTP_PORT_IDENTITY
+ MBG_PTP_V2_PARENT_DATASET_FLAGS flags; ///< flags field, see ::MBG_PTP_V2_PARENT_DATASET_FLAGS
+ uint8_t reserved; ///< reserved, currently always 0
+ uint16_t parent_log_variance; ///< estimate of the parent clock's PTP variance, only valid if ::flags::parent_stats is set
+ int32_t parent_phase_change_rate; ///< estimate of the parent clock's phase change rate, only valid if ::flags::parent_stats is set
+ uint8_t grandmaster_priority_1; ///< priority 1 attribute of the grandmaster clock
+ PTP_CLOCK_QUALITY grandmaster_clock_quality; ///< quality of the grandmaster clock, see ::PTP_CLOCK_QUALITY
+ uint8_t grandmaster_priority_2; ///< priority 2 attribute of the grandmaster clock
+ PTP_CLOCK_ID grandmaster_identity; ///< identity of the grandmaster clock, see ::PTP_CLOCK_ID
+
+} MBG_PTP_V2_PARENT_DATASET;
+
+
+#define _mbg_swab_ptp_v2_parent_dataset( _p ) \
+{ \
+ _mbg_swab_ptp_port_identity( &(_p)->parent_port_identity ); \
+ _mbg_swab_ptp_v2_parent_dataset_flags( &(_p)->flags ); \
+ _mbg_swab8( &(_p)->reserved ); \
+ _mbg_swab16( &(_p)->parent_log_variance ); \
+ _mbg_swab32( &(_p)->parent_phase_change_rate ); \
+ _mbg_swab8( &(_p)->grandmaster_priority_1 ); \
+ _mbg_swab_ptp_clock_quality( &(_p)->grandmaster_clock_quality ); \
+ _mbg_swab8( &(_p)->grandmaster_priority_2 ); \
+ _mbg_swab_ptp_clock_id( &(_p)->grandmaster_identity ); \
+}
+
+
+/**
+ * @brief Flags structure for the PTPv2 time properties dataset
+ *
+ * @note For further information, see IEEE 1588-2008, chapters 8.2.4 and 15.5.3.6.1
+ *
+ * @see ::MBG_PTP_V2_TIME_PROPERTIES_DATASET
+ */
+typedef struct
+{
+ uint8_t leap_61 : 1; ///< set, if the last minute of the current UTC day containts 61 seconds
+ uint8_t leap_59 : 1; ///< set, if the last minute of the current UTC day containts 59 seconds
+ uint8_t utc_offset_valid : 1; ///< set, if the current UTC offset is known to be correct
+ uint8_t ptp_timescale : 1; ///< set, if the timescale of the grandmaster clock is PTP
+ uint8_t time_traceable : 1; ///< set, if timescale and utc offset are traceable to a primary reference
+ uint8_t frequency_traceable : 1; ///< set, if the frequency determining the timescale is traceable to a primary reference
+ uint8_t reserved : 2; ///< reserved, currently always 0
+
+} MBG_PTP_V2_TIME_PROPERTIES_DATASET_FLAGS;
+
+
+#define _mbg_swab_ptp_v2_time_properties_dataset_flags( _p ) \
+ _nop_macro_fnc()
+
+
+/**
+ * @brief PTPv2 time properties dataset
+ *
+ * @note For further information, see IEEE 1588-2008, chapters 8.2.4 and 15.5.3.6.1
+ *
+ * @see ::MBG_PTP_V2_TIME_PROPERTIES_DATASET_FLAGS
+ */
+typedef struct
+{
+ int16_t current_utc_offset; ///< offset between TAI and UTC in seconds
+ MBG_PTP_V2_TIME_PROPERTIES_DATASET_FLAGS flags; ///< flags field, see ::MBG_PTP_V2_TIME_PROPERTIES_DATASET_FLAGS
+ uint8_t time_source; ///< source of time used by the grandmaster clock, see ::PTP_TIME_SOURCES
+
+} MBG_PTP_V2_TIME_PROPERTIES_DATASET;
+
+
+#define _mbg_swab_ptp_v2_time_properties_dataset( _p ) \
+{ \
+ _mbg_swab16( &(_p)->current_utc_offset ); \
+ _mbg_swab_ptp_v2_time_properties_dataset_flags( &(_p)->flags ); \
+ _mbg_swab8( &(_p)->time_source ); \
+}
+
+
+/**
+ * @brief PTPv2 port dataset
+ *
+ * @note For further information, see IEEE 1588-2008, chapters 8.2.5 and 15.5.3.7.1
+ *
+ * @see ::PTP_PORT_IDENTITY
+ * @see ::PTP_TIME_INTERVAL
+ * @see ::MBG_PTP_V2_PORT_DATASET_IDX
+ */
+typedef struct
+{
+ PTP_PORT_IDENTITY port_identity; ///< identity of the local port, see ::PTP_PORT_IDENTITY
+ uint8_t port_state; ///< state of the protocol engine associated with this port, see ::PTP_PORT_STATES
+ int8_t log_min_delay_req_interval; ///< minimum delay request interval for this port
+ PTP_TIME_INTERVAL peer_mean_path_delay; ///< estimate of the current one-way propagation delay on the link, only valid if P2P is used, see ::PTP_TIME_INTERVAL
+ int8_t log_announce_interval; ///< announce interval to be used by this port
+ uint8_t announce_receipt_timeout; ///< shall be an integral multiple of ::announce_interval
+ int8_t log_sync_interval; ///< mean sync interval to be used for multicast messages
+ uint8_t delay_mechanism; ///< propagation delay measuring option, see ::PTP_DELAY_MECHS
+ int8_t log_min_pdelay_req_interval; ///< minimum peer delay request interval for this port
+ uint8_t version_number : 4; ///< PTP version in use on the port
+ uint8_t reserved : 4; ///< reserved, currently always 0
+
+} MBG_PTP_V2_PORT_DATASET;
+
+
+#define _mbg_swab_ptp_v2_port_dataset( _p ) \
+{ \
+ _mbg_swab_ptp_port_identity( &(_p)->port_identity ); \
+ _mbg_swab8( &(_p)->port_state ); \
+ _mbg_swab8( &(_p)->log_min_delay_req_interval ); \
+ _mbg_swab_ptp_time_interval( &(_p)->peer_mean_path_delay ); \
+ _mbg_swab8( &(_p)->log_announce_interval ); \
+ _mbg_swab8( &(_p)->announce_receipt_timeout ); \
+ _mbg_swab8( &(_p)->log_sync_interval ); \
+ _mbg_swab8( &(_p)->delay_mechanism ); \
+ _mbg_swab8( &(_p)->log_min_pdelay_req_interval ); \
+}
+
+
+/**
+ * @brief Index structure for PTPv2 port dataset
+ *
+ * @note Port dataset with index 0..::MBG_PTP_V2_DEFAULT_DATASET::number_ports - 1 can be queried from a device
+ *
+ * @see ::MBG_PTP_V2_PORT_DATASET
+ */
+typedef struct
+{
+ uint16_t idx; ///< Index of the port dataset, 0..::MBG_PTP_V2_DEFAULT_DATASET::number_ports - 1
+ MBG_PTP_V2_PORT_DATASET port_dataset; ///< see ::MBG_PTP_V2_PORT_DATASET
+
+} MBG_PTP_V2_PORT_DATASET_IDX;
+
+
+#define _mbg_swab_ptp_v2_port_dataset_idx( _p ) \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ptp_v2_port_dataset( &(_p)->port_dataset ); \
+}
+
+
+/** @} defgroup group_ptp */
+
+
+
+/**
+ * @defgroup group_ntp Definitions used with NTP
+ *
+ * @{ */
+
+
+/**
+ * @brief Enumeration of known NTP roles
+ *
+ * @see ::NTP_GLB_SETTINGS::ntp_role
+ */
+enum NTP_ROLES
+{
+ NTP_ROLE_NONE = 0, ///< NTP services disabled
+ NTP_ROLE_CLIENT, ///< NTP client
+ NTP_ROLE_SERVER, ///< NTP server
+ NTP_ROLE_CLIENT_SERVER, ///< both NTP client and server
+ N_NTP_ROLES ///< number of supported roles
+};
+
+
+/**
+ * @brief Flag masks associated with NTP roles
+ *
+ * @see ::NTP_GLB_INFO::supp_ntp_roles
+ */
+enum NTP_ROLE_MASKS
+{
+ NTP_MSK_ROLE_NONE = ( 1UL << NTP_ROLE_NONE ), ///< see ::NTP_ROLE_NONE
+ NTP_MSK_ROLE_CLIENT = ( 1UL << NTP_ROLE_CLIENT ), ///< see ::NTP_ROLE_CLIENT
+ NTP_MSK_ROLE_SERVER = ( 1UL << NTP_ROLE_SERVER ), ///< see ::NTP_ROLE_SERVER
+ NTP_MSK_ROLE_CLIENT_SERVER = ( 1UL << NTP_ROLE_CLIENT_SERVER ), ///< see ::NTP_ROLE_CLIENT_SERVER
+};
+
+
+/**
+ * @brief Enumeration of global NTP flags
+ *
+ * @see @ref NTP_FLAG_MASKS
+ */
+enum NTP_FLAGS
+{
+ NTP_IPV4, ///< NTP via IPv4/UDP
+ NTP_IPV6, ///< NTP via IPv6/UDP
+ NTP_SYMM_KEYS, ///< support symmetric key authentication (MD5)
+ NTP_AUTOKEY, ///< include authentication fields encrypted using the autokey scheme
+ NTP_BURST, ///< send a burst of eight packets at each polling cycle
+ NTP_IBURST, ///< send a burst of eight packets at the first polling cycle
+ NTP_NO_SELECT, ///< marks a server as not to be selected for time synchronization
+ NTP_PREEMPT, ///< specifies the association as preemptable rather than the default persistent
+ NTP_PREFER, ///< marks a server as preferred peer for time synchronization
+ NTP_TRUE, ///< force the association to assume truechimer status; always survive the selection and clustering algorithms
+ NTP_BROADCAST, ///< transmission via broadcast, point to multipoint
+ NTP_MULTICAST, ///< transmission via multicast, point to multipoint
+ NTP_MANYCAST, ///< transmission via manycast, point to multipoint
+ NTP_POOL, ///< peer shall be treated as a pool server
+ NTP_PEER, ///< specifies a symmetric-active association should be used with this server
+ NTP_BROADCASTCLIENT, ///< receive broadcast messages on all interfaces
+ NTP_MULTICASTCLIENT, ///< receive messages from the given multicast group
+ NTP_MANYCASTCLIENT, ///< manycast shall be used on the given multicast address to discover peers
+ NTP_RESTRICTIONS, ///< NTP supports restrictions
+ NTP_DISCARD, ///< NTP supports "discard" rate limiting
+ NTP_REFCLOCKS, ///< NTP supports refclocks
+ NTP_STATISTICS, ///< NTP supports statistics (e.g. clockstats, loopstats, etc...)
+ NTP_MISCELLANEOUS, ///< NTP supports misc options (e.g. tinker, driftfile, orphan mode, etc...)
+ NTP_TRUSTED_KEYS, ///< NTP supports specifying trusted symmetric keys
+ NTP_FIXED_REFCLOCKS, ///< NTP refclocks not configurable
+
+ N_NTP_FLAGS
+};
+
+
+
+/**
+ * @brief Flag masks associated with ::NTP_FLAGS
+ *
+ * Used with ::NTP_GLB_INFO::supp_flags, ::NTP_GLB_SETTINGS::flags, NTP_CLNT_MODE_INFO::supp_flags,
+ * ::NTP_CLNT_MODE_INFO::supp_peer_flags, ::NTP_CLNT_MODE_SETTINGS::flags, ::NTP_PEER_SETTINGS::flags,
+ * ::NTP_SRV_MODE_SETTINGS::flags, and ::NTP_SRV_MODE_INFO::supp_flags.
+ *
+ * @todo We may need structures to configure symmetric keys, and autokey certificates.
+ *
+ * @see ::NTP_FLAGS
+ *
+ * @anchor NTP_FLAG_MASKS @{ */
+
+#define NTP_MSK_IPV4 ( 1UL << NTP_IPV4 ) ///< see ::NTP_IPV4
+#define NTP_MSK_IPV6 ( 1UL << NTP_IPV6 ) ///< see ::NTP_IPV6
+#define NTP_MSK_SYMM_KEYS ( 1UL << NTP_SYMM_KEYS ) ///< see ::NTP_SYMM_KEYS; if set, ::NTP_SYMM_KEY_LIMITS can be queried
+#define NTP_MSK_AUTOKEY ( 1UL << NTP_AUTOKEY ) ///< see ::NTP_AUTOKEY
+#define NTP_MSK_BURST ( 1UL << NTP_BURST ) ///< see ::NTP_BURST
+#define NTP_MSK_IBURST ( 1UL << NTP_IBURST ) ///< see ::NTP_IBURST
+#define NTP_MSK_NO_SELECT ( 1UL << NTP_NO_SELECT ) ///< see ::NTP_NO_SELECT
+#define NTP_MSK_PREEMPT ( 1UL << NTP_PREEMPT ) ///< see ::NTP_PREEMPT
+#define NTP_MSK_PREFER ( 1UL << NTP_PREFER ) ///< see ::NTP_PREFER
+#define NTP_MSK_TRUE ( 1UL << NTP_TRUE ) ///< see ::NTP_TRUE
+#define NTP_MSK_BROADCAST ( 1UL << NTP_BROADCAST ) ///< see ::NTP_BROADCAST
+#define NTP_MSK_MULTICAST ( 1UL << NTP_MULTICAST ) ///< see ::NTP_MULTICAST
+#define NTP_MSK_MANYCAST ( 1UL << NTP_MANYCAST ) ///< see ::NTP_MANYCAST
+#define NTP_MSK_POOL ( 1UL << NTP_POOL ) ///< see ::NTP_POOL
+#define NTP_MSK_PEER ( 1UL << NTP_PEER ) ///< see ::NTP_PEER
+#define NTP_MSK_BROADCASTCLIENT ( 1UL << NTP_BROADCASTCLIENT) ///< see ::NTP_BROADCASTCLIENT
+#define NTP_MSK_MULTICASTCLIENT ( 1UL << NTP_MULTICASTCLIENT) ///< see ::NTP_MULTICASTCLIENT
+#define NTP_MSK_MANYCASTCLIENT ( 1UL << NTP_MANYCASTCLIENT) ///< see ::NTP_MANYCASTCLIENT
+#define NTP_MSK_RESTRICTIONS ( 1UL << NTP_RESTRICTIONS ) ///< see ::NTP_RESTRICTIONS
+#define NTP_MSK_DISCARD ( 1UL << NTP_DISCARD ) ///< see ::NTP_DISCARD
+#define NTP_MSK_REFCLOCKS ( 1UL << NTP_REFCLOCKS ) ///< see ::NTP_REFCLOCKS
+#define NTP_MSK_STATISTICS ( 1UL << NTP_STATISTICS ) ///< see ::NTP_STATISTICS; if set, ::NTP_STATS_GLB_INFO can be queried
+#define NTP_MSK_MISCELLANEOUS ( 1UL << NTP_MISCELLANEOUS ) ///< see ::NTP_MISCELLANEOUS
+#define NTP_MSK_TRUSTED_KEYS ( 1UL << NTP_TRUSTED_KEYS ) ///< see ::NTP_TRUSTED_KEYS
+#define NTP_MSK_FIXED_REFCLOCKS ( 1UL << NTP_FIXED_REFCLOCKS ) ///< see ::NTP_FIXED_REFCLOCKS
+
+
+/** @} anchor NTP_FLAG_MASKS */
+
+
+
+/**
+ * @brief Global configuration settings of an NTP device (client/server)
+ *
+ * This structure should be sent to an NTP device to configure global settings
+ */
+typedef struct
+{
+ uint8_t ntp_role; ///< one of the supported NTP roles, see ::NTP_ROLES
+ uint8_t num_symm_keys; ///< number of configured symm keys
+ uint8_t num_trusted_keys; ///< number of activated symm keys
+ uint8_t reserved_1; ///< reserved, currently 0
+
+ uint32_t reserved_2; ///< reserved, currently 0
+ uint32_t reserved_3; ///< reserved, currently 0
+
+ uint32_t flags; ///< NTP flags, see @ref NTP_FLAG_MASKS
+
+} NTP_GLB_SETTINGS;
+
+#define _mbg_swab_ntp_glb_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+/**
+ * @brief Global configuration info of an NTP device (client/server)
+ *
+ * This structure can be used to determine possible configurations of an NTP device
+ */
+typedef struct
+{
+ NTP_GLB_SETTINGS settings; ///< current configuration settings
+
+ uint8_t max_symm_keys; ///< number of available symm keys that can be generated, see ::NTP_SYMM_KEY_INFO_IDX
+ uint8_t max_trusted_keys; ///< number of available trusted keys, see ::NTP_TRUSTED_KEY_INFO_IDX
+
+ uint16_t reserved_2; ///< reserved, currently 0
+ uint32_t reserved_3; ///< reserved, currently 0
+
+ uint32_t supp_ntp_roles; ///< supported NTP roles, see ::NTP_ROLE_MASKS
+ uint32_t supp_flags; ///< supported NTP flags, see @ref NTP_FLAG_MASKS
+
+} NTP_GLB_INFO;
+
+#define _mbg_swab_ntp_glb_info( _p ) \
+do \
+{ \
+ _mbg_swab_ntp_glb_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->supp_ntp_roles ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+} while ( 0 )
+
+
+#if defined( _PRELIMINARY_CODE )
+
+/**
+ * @brief Enumeration of supported NTP restriction types/keywords
+ *
+ * Used with ::NTP_RESTR::type
+ *
+ * @see https://www.eecis.udel.edu/~mills/ntp/html/accopt.html#restrict
+ * @see ::NTP_RESTR_TYPE_MSKS
+ */
+enum NTP_RESTR_TYPES
+{
+ NTP_RESTR_TYPE_DEFAULT,
+ NTP_RESTR_TYPE_SOURCE,
+ NTP_RESTR_TYPE_ADDRESS,
+ N_NTP_RESTR_TYPES
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::NTP_RESTR_TYPES
+ *
+ * Used with ::NTP_RESTR_LIMITS::supp_types
+ *
+ * @see ::NTP_RESTR_TYPES
+ */
+enum NTP_RESTR_TYPE_MSKS
+{
+ NTP_RESTR_TYPE_MSK_DEFAULT = ( 1UL << NTP_RESTR_TYPE_DEFAULT ), ///< see ::NTP_RESTR_TYPE_DEFAULT
+ NTP_RESTR_TYPE_MSK_SOURCE = ( 1UL << NTP_RESTR_TYPE_SOURCE ), ///< see ::NTP_RESTR_TYPE_SOURCE
+ NTP_RESTR_TYPE_MSK_ADDRESS = ( 1UL << NTP_RESTR_TYPE_ADDRESS ) ///< see ::NTP_RESTR_TYPE_ADDRESS
+};
+
+
+
+/**
+ * @brief Enumeration of supported NTP restriction flags
+ *
+ * Used to define ::NTP_RESTR_FLAG_MSKS
+ *
+ * @see https://www.eecis.udel.edu/~mills/ntp/html/accopt.html#restrict
+ * @see ::NTP_RESTR_FLAG_MSKS
+ */
+enum NTP_RESTR_FLAGS
+{
+ NTP_RESTR_FLAG_FLAKE,
+ NTP_RESTR_FLAG_IGNORE,
+ NTP_RESTR_FLAG_KOD,
+ NTP_RESTR_FLAG_LIMITED,
+ NTP_RESTR_FLAG_LOWPRIOTRAP,
+ NTP_RESTR_FLAG_MSSNTP,
+ NTP_RESTR_FLAG_NOMODIFY,
+ NTP_RESTR_FLAG_NOQUERY,
+ NTP_RESTR_FLAG_NOPEER,
+ NTP_RESTR_FLAG_NOSERVE,
+ NTP_RESTR_FLAG_NOTRAP,
+ NTP_RESTR_FLAG_NOTRUST,
+ NTP_RESTR_FLAG_NTPPORT,
+ NTP_RESTR_FLAG_VERSION,
+ NTP_RESTR_FLAG_IPV4, ///< This default restriction only applies to IPv4
+ NTP_RESTR_FLAG_IPV6, ///< This default restriction only applies to IPv6
+ N_NTP_RESTR_FLAGS
+};
+
+
+
+/**
+ * @brief Flag masks associated with ::NTP_RESTR_FLAGS
+ *
+ * Used with ::NTP_RESTR::flags and ::NTP_RESTR_LIMITS::supp_flags
+ *
+ * @see ::NTP_RESTR_FLAGS
+ */
+enum NTP_RESTR_FLAG_MSKS
+{
+ NTP_RESTR_FLAG_MSK_FLAKE = ( 1UL << NTP_RESTR_FLAG_FLAKE ), ///< see ::NTP_RESTR_FLAG_FLAKE
+ NTP_RESTR_FLAG_MSK_IGNORE = ( 1UL << NTP_RESTR_FLAG_IGNORE ), ///< see ::NTP_RESTR_FLAG_IGNORE
+ NTP_RESTR_FLAG_MSK_KOD = ( 1UL << NTP_RESTR_FLAG_KOD ), ///< see ::NTP_RESTR_FLAG_KOD
+ NTP_RESTR_FLAG_MSK_LIMITED = ( 1UL << NTP_RESTR_FLAG_LIMITED ), ///< see ::NTP_RESTR_FLAG_LIMITED
+ NTP_RESTR_FLAG_MSK_LOWPRIOTRAP = ( 1UL << NTP_RESTR_FLAG_LOWPRIOTRAP ),///< see ::NTP_RESTR_FLAG_LOWPRIOTRAP
+ NTP_RESTR_FLAG_MSK_MSSNTP = ( 1UL << NTP_RESTR_FLAG_MSSNTP ), ///< see ::NTP_RESTR_FLAG_MSSNTP
+ NTP_RESTR_FLAG_MSK_NOMODIFY = ( 1UL << NTP_RESTR_FLAG_NOMODIFY ), ///< see ::NTP_RESTR_FLAG_NOMODIFY
+ NTP_RESTR_FLAG_MSK_NOQUERY = ( 1UL << NTP_RESTR_FLAG_NOQUERY ), ///< see ::NTP_RESTR_FLAG_NOQUERY
+ NTP_RESTR_FLAG_MSK_NOPEER = ( 1UL << NTP_RESTR_FLAG_NOPEER ), ///< see ::NTP_RESTR_FLAG_NOPEER
+ NTP_RESTR_FLAG_MSK_NOSERVE = ( 1UL << NTP_RESTR_FLAG_NOSERVE ), ///< see ::NTP_RESTR_FLAG_NOSERVE
+ NTP_RESTR_FLAG_MSK_NOTRAP = ( 1UL << NTP_RESTR_FLAG_NOTRAP ), ///< see ::NTP_RESTR_FLAG_NOTRAP
+ NTP_RESTR_FLAG_MSK_NOTRUST = ( 1UL << NTP_RESTR_FLAG_NOTRUST ), ///< see ::NTP_RESTR_FLAG_NOTRUST
+ NTP_RESTR_FLAG_MSK_NTPPORT = ( 1UL << NTP_RESTR_FLAG_NTPPORT ), ///< see ::NTP_RESTR_FLAG_NTPPORT
+ NTP_RESTR_FLAG_MSK_VERSION = ( 1UL << NTP_RESTR_FLAG_VERSION ), ///< see ::NTP_RESTR_FLAG_VERSION
+ NTP_RESTR_FLAG_MSK_IPV4 = ( 1UL << NTP_RESTR_FLAG_IPV4 ), ///< see ::NTP_RESTR_FLAG_IPV4
+ NTP_RESTR_FLAG_MSK_IPV6 = ( 1UL << NTP_RESTR_FLAG_IPV6 ) ///< see ::NTP_RESTR_FLAG_IPV6
+};
+
+
+
+/**
+ * @brief General NTP restriction limits to be read from a device
+ *
+ * Used to query from a device how many NTP restrictions are supported
+ * by the device, then index 0..::NTP_RESTR_LIMITS::cur_restrs-1
+ * restriction records can be read from a device. A maximum of
+ * ::NTP_RESTR_LIMITS::max_restrs can be configured at all.
+ */
+typedef struct
+{
+ uint16_t max_restrs; ///< Number of maximum supported restrictions
+ uint16_t cur_restrs; ///< Number of currently configured restrictions
+ uint32_t supp_types; ///< Supported restriction types, see ::NTP_RESTR_TYPE_MSKS
+ uint32_t supp_flags; ///< Supported restriction flags, see ::NTP_RESTR_FLAG_MSKS
+ uint32_t reserved; ///< Future use
+
+} NTP_RESTR_LIMITS;
+
+#define _mbg_swab_ntp_restr_limits( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->max_restrs ); \
+ _mbg_swab16( &(_p)->cur_restrs ); \
+ _mbg_swab32( &(_p)->supp_types ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ _mbg_swab32( &(_p)->reserved ); \
+} while ( 0 )
+
+/**
+ * @brief NTP restriction
+ *
+ * Structure contains all flags and information needed for a valid NTP restriction
+ * as described at ntp.org's manual page.
+ */
+typedef struct
+{
+ uint8_t type; ///< Restriction type, see ::NTP_RESTR_TYPES
+ uint8_t reserved_1; ///< Future use
+ uint16_t reserved_2; ///< Future use
+ uint32_t flags; ///< Restriction flags, see ::NTP_RESTR_FLAG_MSKS
+
+ MBG_HOSTNAME addr; ///< used if ::NTP_RESTR::type == ::NTP_RESTR_TYPE_ADDRESS
+ ///< can contain a hostname, or an IPv4 or IPv6 address
+ ///< with or without CIDR extension (eg. 172.16.0.0/16).
+} NTP_RESTR;
+
+#define _mbg_swab_ntp_restr( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab_ntp_restr_discard( &(_p)->u.discard ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief NTP restriction, plus index
+ *
+ * @see ::NTP_RESTR
+ */
+typedef struct
+{
+ uint16_t idx;
+ NTP_RESTR restr;
+
+} NTP_RESTR_IDX;
+
+#define _mbg_swab_ntp_restr_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ntp_restr( &(_p)->restr ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief General NTP "discard" rate limiting limits to be read from a device
+ *
+ * Used to query from a device what range of values is supported
+ * for the NTP "discard" rate limiting configuration.
+ */
+typedef struct
+{
+ uint8_t avg_min; ///< Minimum value for avg
+ uint8_t avg_max; ///< Maximum value for avg
+ uint8_t min_min; ///< Minimum value for min
+ uint8_t min_max; ///< Maximum value for min
+ uint16_t monitor_min; ///< Maximum value for min
+ uint16_t monitor_max; ///< Maximum value for min
+
+ uint32_t reserved; ///< Future use
+
+} NTP_DISCARD_LIMITS;
+
+#define _mbg_swab_ntp_discard_limits( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->monitor_min ); \
+ _mbg_swab16( &(_p)->monitor_max ); \
+ _mbg_swab32( &(_p)->reserved ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief NTP "discard" rate limiting settings as described at ntp.org's manual
+ */
+typedef struct
+{
+ uint8_t avg; ///< Specify the minimum average interpacket spacing in log2 s.
+ uint8_t min; ///< Specify the minimum interpacket spacing (guard time) in seconds.
+ uint16_t monitor; ///< ### TODO Which is the unit of this field?
+ uint32_t reserved; ///< Possible future use
+
+} NTP_DISCARD_SETTINGS;
+
+#define _mbg_swab_ntp_discard_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->monitor ); \
+ _mbg_swab32( &(_p)->reserved ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of supported refclock types
+ *
+ * Used with ::NTP_REFCLK_CFG_SETTINGS::type
+ *
+ * @see https://www.eecis.udel.edu/~mills/ntp/html/refclock.html
+ * @see ::NTP_REFCLK_TYPE_MSKS
+ */
+enum NTP_REFCLK_TYPES
+{
+ NTP_REFCLK_TYPE_LOCAL, ///< NTP local clock
+ NTP_REFCLK_TYPE_TRUETIME, ///< NTP Truetime driver
+ NTP_REFCLK_TYPE_PARSE, ///< NTP parse driver
+ NTP_REFCLK_TYPE_NMEA, ///< NTP NMEA driver
+ NTP_REFCLK_TYPE_PPS, ///< NTP atom driver (standalone PPS)
+ NTP_REFCLK_TYPE_SHM, ///< NTP shared memory driver
+ N_NTP_REFCLK_TYPES
+};
+
+
+
+/**
+ * @brief Bit masks associated with ::NTP_REFCLK_TYPES
+ *
+ * Used with ::NTP_REFCLK_CFG_INFO::supp_refclk_types
+ *
+ * @see ::NTP_REFCLK_TYPES
+ */
+enum NTP_REFCLK_TYPE_MSKS
+{
+ NTP_REFCLK_TYPE_MSK_LOCAL = ( 1UL << NTP_REFCLK_TYPE_LOCAL ), ///< see ::NTP_REFCLK_TYPE_LOCAL
+ NTP_REFCLK_TYPE_MSK_TRUETIME = ( 1UL << NTP_REFCLK_TYPE_TRUETIME ), ///< see ::NTP_REFCLK_TYPE_TRUETIME
+ NTP_REFCLK_TYPE_MSK_PARSE = ( 1UL << NTP_REFCLK_TYPE_PARSE ), ///< see ::NTP_REFCLK_TYPE_PARSE
+ NTP_REFCLK_TYPE_MSK_NMEA = ( 1UL << NTP_REFCLK_TYPE_NMEA ), ///< see ::NTP_REFCLK_TYPE_NMEA
+ NTP_REFCLK_TYPE_MSK_PPS = ( 1UL << NTP_REFCLK_TYPE_PPS ), ///< see ::NTP_REFCLK_TYPE_PPS
+ NTP_REFCLK_TYPE_MSK_SHM = ( 1UL << NTP_REFCLK_TYPE_SHM ) ///< see ::NTP_REFCLK_TYPE_SHM
+};
+
+
+
+
+
+/**
+ * @brief Numbers related to the "fudge" flags used with ntpd's refclock interface
+ *
+ * Used with ::NTP_REFCLK_CFG_SETTINGS::drv_flags_enable
+ * and ::NTP_REFCLK_CFG_SETTINGS::drv_flags_value
+ *
+ * The refclock interface provided by ntpd supports a number of flags
+ * (flag1..flag4) which can be "fudged" in ntp.conf to control specific
+ * features of a particular refclock driver, e.g.:
+ * "fudge 127.127.8.0 flag1 1"
+ *
+ * Which feature is controlled by which flag depends on the refclock
+ * driver type, so usually each flag has a different meaning for
+ * different refclock types.
+ *
+ * There are different cases to be distinguished:
+ *
+ * - if a flag is not specified at all in ntp.conf then
+ * the controlled feature is enabled or disabled
+ * according to the driver's default settings
+ *
+ * - if a flag is specified as '0' or '1' in ntp.conf then
+ * the controlled feature is enabled or disabled
+ * according to the flag's setting.
+ *
+ * Thus, the bit mask in ::NTP_REFCLK_CFG_SETTINGS::drv_flags_enable
+ * controls if the associated fudge flag should be specified in ntp.conf,
+ * and if it is specified then the associated bit in
+ * ::NTP_REFCLK_CFG_SETTINGS::drv_flags_value controls if the fudge flag
+ * is set to 0 or 1.
+ *
+ * @anchor NTP_FUDGE_FLAG_NUMBERS @{ */
+
+#define NTP_MIN_REFCLOCK_FUDGE_FLAG 1 ///< minimum refclock fudge flag number, associated with bit 0
+#define N_NTP_REFCLOCK_FUDGE_FLAGS 4 ///< the number of supported fudge flags
+
+/** @} anchor NTP_FUDGE_FLAG_NUMBERS */
+
+
+
+/**
+ * @brief NTP refclock specific settings
+ *
+ * Used to configure a NTP refclock.
+ */
+typedef struct
+{
+ uint8_t type; ///< See ::NTP_REFCLK_TYPES
+ uint8_t instance; ///< Refclock instance of the specified type. Usually up to 4 instances of the same type are supported by ntpd.
+ uint8_t mode; ///< Driver specific "mode" //### TODO Flag to enable "mode"?
+ int8_t stratum; ///< Stratum number to be fudged; -1 if unspecified and thus default is to be used
+
+ int8_t refid[4]; ///< Reference id used by driver //### TODO Flag to enable "refid"?
+
+ uint8_t minpoll; ///< Minimum polling interval, [log2 seconds], 0 if unused/unspecified
+ uint8_t maxpoll; ///< Maximum polling interval, [log2 seconds], 0 if unused/unspecified
+ uint8_t reserved_1; ///< Reserved for future use
+ uint8_t reserved_2; ///< Future use
+
+ NANO_TIME_64 time1; ///< Driver specific
+ NANO_TIME_64 time2; ///< Driver specific
+
+ uint16_t drv_flags_enable; ///< Enable/disable driver specific flags, see @ref NTP_FUDGE_FLAG_NUMBERS
+ uint16_t drv_flags_value; ///< 0 or 1, if (drv_flags_enable & x) == 1, see @ref NTP_FUDGE_FLAG_NUMBERS
+
+ uint32_t flags; ///< See @ref NTP_FLAG_MASKS. Only flags specified in ::TODO can be used here.
+
+ uint32_t reserved_3; ///< Future use
+
+} NTP_REFCLK_CFG_SETTINGS;
+
+#define _mbg_swab_ntp_refclk_cfg_settings( _p ) \
+do \
+{ \
+ _mbg_swab_nano_time_64( &(_p)->time1 ); \
+ _mbg_swab_nano_time_64( &(_p)->time2 ); \
+ _mbg_swab16( &(_p)->drv_flags_enable ); \
+ _mbg_swab16( &(_p)->drv_flags_value ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief NTP refclock settings index
+ *
+ * @see ::NTP_REFCLK_CFG_SETTINGS
+ */
+typedef struct
+{
+ uint16_t idx;
+ NTP_REFCLK_CFG_SETTINGS settings; ///< See ::NTP_REFCLK_CFG_SETTINGS
+
+} NTP_REFCLK_CFG_SETTINGS_IDX;
+
+#define _mbg_swab_ntp_refclk_cfg_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ntp_refclk_cfg_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief NTP refclock configuration and supported refclock types
+ *
+ * This structure can be used to set a NTP refclock's configuration
+ * and get to know its overall supported refclocks.
+ */
+typedef struct
+{
+ NTP_REFCLK_CFG_SETTINGS settings; ///< See ::NTP_REFCLK_CFG_SETTINGS
+
+ uint32_t supp_refclk_types; ///< See ::NTP_REFCLK_TYPE_MSKS
+
+} NTP_REFCLK_CFG_INFO;
+
+#define _mbg_swab_ntp_refclk_cfg_info( _p ) \
+do \
+{ \
+ _mbg_swab_ntp_refclk_cfg_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->supp_refclk_types ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief NTP refclock info, with index
+ *
+ * @see ::NTP_REFCLK_CFG_INFO
+ */
+typedef struct
+{
+ uint16_t idx;
+ NTP_REFCLK_CFG_INFO info;
+
+} NTP_REFCLK_CFG_INFO_IDX;
+
+#define _mbg_swab_ntp_refclk_cfg_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ntp_refclk_cfg_info( &(_p)->info ); \
+} while ( 0 )
+
+
+/**
+ * @brief Enumeration of NTP supported symmetric key hashing algorithms
+ *
+ * @see ::NTP_SYMM_KEY_HASH_MASKS
+ *
+ * @note Support of external libraries (e.g.: OpenSSL) may be needed for
+ * some hashing algorithms.
+ */
+enum NTP_SYMM_KEY_HASHES
+{
+ NTP_SYMM_KEY_HASH_MD5, ///< NTP supports MD5 as key hashing algorithm
+ NTP_SYMM_KEY_HASH_SHA1, ///< NTP supports SHA1 as key hashing algorithm
+ N_NTP_SYMM_KEY_HASHES
+};
+
+
+
+/**
+ * @brief Flag masks associated with ::NTP_SYMM_KEY_HASHES
+ *
+ * @see ::NTP_SYMM_KEY_HASHES
+ */
+enum NTP_SYMM_KEY_HASH_MASKS
+{
+ NTP_SYMM_KEY_HASH_MSK_MD5 = ( 1UL << NTP_SYMM_KEY_HASH_MD5 ), ///< see ::NTP_SYMM_KEY_HASH_MD5
+ NTP_SYMM_KEY_HASH_MSK_SHA1 = ( 1UL << NTP_SYMM_KEY_HASH_SHA1 ), ///< see ::NTP_SYMM_KEY_HASH_SHA1
+};
+
+
+/**
+ * @brief Name strings for defined NTP symm key hashes
+ *
+ * @see ::NTP_SYMM_KEY_HASHES
+ */
+#define NTP_SYMM_KEY_HASHES_STRS \
+{ \
+ "MD5", \
+ "SHA1" \
}
-/** @} group_ptp */
+
+/**
+ * @brief General NTP symmetric key limits to be read from a device
+ *
+ * ::NTP_SYMM_KEY_LIMITS::supp_hashes specifies supported hashing algorithms
+ * to create keys with. See ::NTP_SYMM_KEY_HASH_MASKS. Structure can be queried
+ * if ::NTP_MSK_SYMM_KEYS is set in ::NTP_GLB_INFO::supp_flags
+ */
+typedef struct
+{
+ uint16_t supp_hashes; ///< See ::NTP_SYMM_KEY_HASH_MASKS
+ uint16_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+ uint32_t reserved_3; ///< Future use
+ uint32_t reserved_4; ///< Future use
+
+} NTP_SYMM_KEY_LIMITS;
+
+#define _mbg_swab_ntp_symm_key_limits( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->supp_hashes ); \
+} while ( 0 )
+
+
+
+/// Maximum length of a symmetric key. 128 byte was chosen to be
+/// prepared for hash algorithms like SHA256, SH384, up to SHA512.
+#define N_NTP_SYMM_KEY_LEN 128
+
+
+/**
+ * @brief NTP symmetric key specific settings
+ *
+ * This structure is used to configure a symmetric key for NTP.
+ */
+typedef struct
+{
+ uint16_t id; ///< Configurable key id (1..65534)
+ uint8_t hash; ///< See ::NTP_SYMM_KEY_HASHES
+ uint8_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+ uint8_t key[N_NTP_SYMM_KEY_LEN]; ///< Hashed phrase, see ::N_NTP_SYMM_KEY_LEN
+
+} NTP_SYMM_KEY_SETTINGS;
+
+#define _mbg_swab_ntp_symm_key_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->id ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief NTP symmetric key settings, with index
+ *
+ * @see ::NTP_SYMM_KEY_SETTINGS
+ */
+typedef struct
+{
+ uint16_t idx;
+ NTP_SYMM_KEY_SETTINGS settings;
+
+} NTP_SYMM_KEY_SETTINGS_IDX;
+
+#define _mbg_swab_ntp_symm_key_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ntp_symm_key_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+/**
+ * @brief NTP symmkey info
+ *
+ * This structure is used to query a symmetric key for NTP.
+ */
+typedef struct
+{
+ NTP_SYMM_KEY_SETTINGS settings;
+
+ uint32_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+ uint32_t reserved_3; ///< Future use
+ uint32_t reserved_4; ///< Future use
+
+} NTP_SYMM_KEY_INFO;
+
+#define _mbg_swab_ntp_symm_key_info( _p ) \
+do \
+{ \
+ _mbg_swab_ntp_symm_key_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+/**
+ * @brief NTP symm key info, with index
+ *
+ * @see ::NTP_SYMM_KEY_INFO
+ */
+typedef struct
+{
+ uint16_t idx;
+ NTP_SYMM_KEY_INFO info;
+
+} NTP_SYMM_KEY_INFO_IDX;
+
+#define _mbg_swab_ntp_symm_key_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ntp_symm_key_info( &(_p)->info ); \
+} while ( 0 )
+
+
+/**
+ * @brief NTP trusted key settings
+ *
+ * This structure is used to configure a trusted symmetric key for NTP.
+ */
+typedef struct
+{
+ uint16_t id; ///< Configurable key id (1..65534)
+ uint16_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+
+} NTP_TRUSTED_KEY_SETTINGS;
+
+#define _mbg_swab_ntp_trusted_key_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->id ); \
+} while ( 0 )
+
+
+/**
+ * @brief NTP trusted key settings, with index
+ *
+ * @see ::NTP_TRUSTED_KEY_SETTINGS
+ */
+typedef struct
+{
+ uint16_t idx;
+ NTP_TRUSTED_KEY_SETTINGS settings;
+
+} NTP_TRUSTED_KEY_SETTINGS_IDX;
+
+#define _mbg_swab_ntp_trusted_key_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ntp_trusted_key_settings( &(_p)->settings ); \
+} while ( 0 )
+
+/**
+ * @brief NTP trusted key info
+ *
+ * This structure is used to query a trusted symmetric key for NTP.
+ */
+typedef struct
+{
+ NTP_TRUSTED_KEY_SETTINGS settings;
+
+ uint32_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+ uint32_t reserved_3; ///< Future use
+ uint32_t reserved_4; ///< Future use
+
+} NTP_TRUSTED_KEY_INFO;
+
+#define _mbg_swab_ntp_trusted_key_info( _p ) \
+do \
+{ \
+ _mbg_swab_ntp_trusted_key_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+/**
+ * @brief NTP trusted key info, with index
+ *
+ * @see ::NTP_TRUSTED_KEY_INFO
+ */
+typedef struct
+{
+ uint16_t idx;
+ NTP_TRUSTED_KEY_INFO info;
+
+} NTP_TRUSTED_KEY_INFO_IDX;
+
+#define _mbg_swab_ntp_trusted_key_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_ntp_trusted_key_info( &(_p)->info ); \
+} while ( 0 )
+
+
+/**
+ * @brief Enumeration of NTP supported statistics
+ *
+ * @see ::NTP_GLB_STATS_MASKS
+ */
+enum NTP_GLB_STATS_FLAGS
+{
+ NTP_GLB_STATS_FLAG_ENABLE, ///< NTP stats can generally be enabled or disabled
+ NTP_GLB_STATS_FLAG_CLOCKSTATS, ///< NTP supports clockstats
+ NTP_GLB_STATS_FLAG_CRYPTOSTATS, ///< NTP supports cryptostats
+ NTP_GLB_STATS_FLAG_LOOPSTATS, ///< NTP supports loopstats
+ NTP_GLB_STATS_FLAG_PEERSTATS, ///< NTP supports peerstats
+ NTP_GLB_STATS_FLAG_RAWSTATS, ///< NTP supports rawstats
+ NTP_GLB_STATS_FLAG_SYSSTATS, ///< NTP supports sysstats
+ NTP_GLB_STATS_FLAG_FILEGEN, ///< NTP supports sets of files
+ ///< If flag is set there are structures needed
+ ///< that are not avail right now. Future use
+ N_NTP_GLB_STATS_FLAGS
+};
+
+
+
+/**
+ * @brief Flag masks associated with ::NTP_GLB_STATS_FLAGS
+ *
+ * @see ::NTP_GLB_STATS_FLAGS
+ */
+enum NTP_GLB_STATS_MASKS
+{
+ NTP_GLB_STATS_MSK_ENABLE = ( 1UL << NTP_GLB_STATS_FLAG_ENABLE ), ///< See ::NTP_GLB_STATS_FLAG_ENABLE
+ NTP_GLB_STATS_MSK_CLOCKSTATS = ( 1UL << NTP_GLB_STATS_FLAG_CLOCKSTATS ), ///< See ::NTP_GLB_STATS_FLAG_CLOCKSTATS
+ NTP_GLB_STATS_MSK_CRYPTOSTATS = ( 1UL << NTP_GLB_STATS_FLAG_CRYPTOSTATS ), ///< See ::NTP_GLB_STATS_FLAG_CRYPTOSTATS
+ NTP_GLB_STATS_MSK_LOOPSTATS = ( 1UL << NTP_GLB_STATS_FLAG_LOOPSTATS ), ///< See ::NTP_GLB_STATS_FLAG_LOOPSTATS
+ NTP_GLB_STATS_MSK_PEERSTATS = ( 1UL << NTP_GLB_STATS_FLAG_PEERSTATS ), ///< See ::NTP_GLB_STATS_FLAG_PEERSTATS
+ NTP_GLB_STATS_MSK_RAWSTATS = ( 1UL << NTP_GLB_STATS_FLAG_RAWSTATS ), ///< See ::NTP_GLB_STATS_FLAG_RAWSTATS
+ NTP_GLB_STATS_MSK_SYSSTATS = ( 1UL << NTP_GLB_STATS_FLAG_SYSSTATS ), ///< See ::NTP_GLB_STATS_FLAG_SYSSTATS
+ NTP_GLB_STATS_MSK_FILEGEN = ( 1UL << NTP_GLB_STATS_FLAG_FILEGEN ) ///< See ::NTP_GLB_STATS_FLAG_FILEGEN
+};
+
+
+
+/**
+ * @brief Global NTP statistics settings to be read from / written to a device
+ *
+ * ::NTP_GLB_STATS_MSK_ENABLE is the switch to enable / disable statistics in
+ * general. In case the bit is set all other bits stand for special statistic
+ * types that can be enabled or disabled by setting or deleting its specific bit.
+ */
+typedef struct
+{
+ uint32_t flags; ///< See ::NTP_GLB_STATS_MASKS
+ uint32_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+
+} NTP_STATS_GLB_SETTINGS;
+
+#define _mbg_swab_ntp_stats_glb_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief NTP statistics settings
+ *
+ * This structure can be used to determine possible NTP statistic options
+ * and can be queried if ::NTP_MSK_STATISTICS bit is set in ::NTP_GLB_INFO::supp_flags.
+ */
+typedef struct
+{
+ NTP_STATS_GLB_SETTINGS settings; ///< See ::NTP_STATS_GLB_SETTINGS
+
+ uint32_t supp_stats; ///< See ::NTP_GLB_STATS_MASKS
+ uint32_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+ uint32_t reserved_3; ///< Future use
+
+} NTP_STATS_GLB_INFO;
+
+#define _mbg_swab_ntp_stats_glb_info( _p ) \
+do \
+{ \
+ _mbg_swab_ntp_stats_glb_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->supp_stats ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of NTP supported (various) misc options
+ *
+ * @see ::NTP_MISC_MSKS
+ */
+enum NTP_MISC_FLAGS
+{
+ NTP_MISC_FLAG_DRIFTFILE, ///< NTP supports driftfile
+ NTP_MISC_FLAG_ORPHAN_MODE, ///< NTP supports orphan mode
+ NTP_MISC_FLAG_LEAPFILE, ///< NTP supports leapfile
+ N_NTP_MISC_FLAGS
+};
+
+
+
+/**
+ * @brief Flag masks associated with ::NTP_MISC_FLAGS
+ *
+ * @see ::NTP_MISC_FLAGS
+ */
+enum NTP_MISC_MSKS
+{
+ NTP_MISC_MSK_DRIFTFILE = ( 1UL << NTP_MISC_FLAG_DRIFTFILE ), ///< See ::NTP_MISC_FLAG_DRIFTFILE
+ NTP_MISC_MSK_ORPHAN_MODE = ( 1UL << NTP_MISC_FLAG_ORPHAN_MODE ), ///< See ::NTP_MISC_FLAG_ORPHAN_MODE
+ NTP_MISC_MSK_LEAPFILE = ( 1UL << NTP_MISC_FLAG_LEAPFILE ) ///< See ::NTP_MISC_FLAG_LEAPFILE
+};
+
+
+
+/**
+ * @brief General NTP misc limits to be read from a device
+ *
+ * This structure can be used to determine various NTP options
+ * and can be queried if ::NTP_MSK_MISCELLANEOUS bit is set in ::NTP_GLB_INFO::supp_flags.
+ */
+typedef struct
+{
+ uint32_t supp_flags; ///< See ::NTP_MISC_MSKS
+ uint32_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+
+} NTP_MISC_LIMITS;
+
+#define _mbg_swab_ntp_misc_limits( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief NTP driftfile settings to be read from / written to a device
+ *
+ * If ::NTP_MISC_MSK_DRIFTFILE is set in ::NTP_MISC_LIMITS::supp_flags
+ * ::NTP_MISC_DRIFTFILE_SETTINGS can be read / written.
+ */
+typedef struct
+{
+ uint8_t enable; ///< Enable / disable writing a driftfile
+ uint8_t reserved_1; ///< Future use
+ uint16_t reserved_2; ///< Future use
+
+} NTP_MISC_DRIFTFILE_SETTINGS;
+
+#define _mbg_swab_ntp_misc_driftfile_settings( _p ) \
+do \
+{ \
+} while ( 0 )
+
+
+/**
+ * @brief Enumeration of NTP supported (various) misc options
+ *
+ * @see ::NTP_ORPHAN_MODE_MSK
+ */
+enum NTP_ORPHAN_MODE_FLAGS
+{
+ NTP_ORPHAN_MODE_FLAG_SUPP_DISABLE, ///< Orphan Mode support disabling
+
+ N_NTP_ORPHAN_MODE_FLAGS
+};
+
+
+
+/**
+ * @brief Flag masks associated with ::NTP_ORPHAN_MODE_FLAGS
+ *
+ * @see ::NTP_ORPHAN_MODE_FLAGS
+ */
+enum NTP_ORPHAN_MODE_MSK
+{
+ NTP_ORPHAN_MODE_MSK_SUPP_DISABLE = ( 1UL << NTP_ORPHAN_MODE_FLAG_SUPP_DISABLE ) ///< See ::NTP_ORPHAN_MODE_FLAG_SUPP_DISABLE
+};
+
+
+/**
+ * @brief NTP orphan mode settings to be read from / written to a device
+ *
+ * If ::NTP_MISC_MSK_ORPHAN_MODE is set in ::NTP_MISC_LIMITS::supp_flags
+ * ::NTP_MISC_ORPHAN_MODE_SETTINGS can be read / written.
+ */
+typedef struct
+{
+ uint8_t enable; ///< Generally enable / disable orphan mode
+ uint8_t mode; ///< Stratum level when no ref source available
+ uint16_t reserved_1; ///< Future use
+
+ uint32_t reserved_2; ///< Future use
+
+} NTP_MISC_ORPHAN_MODE_SETTINGS;
+
+#define _mbg_swab_ntp_misc_orphan_mode_settings( _p ) \
+do \
+{ \
+} while ( 0 )
+
+
+/**
+ * @brief NTP orphan mode info
+ *
+ */
+typedef struct
+{
+ NTP_MISC_ORPHAN_MODE_SETTINGS settings; ///< See ::NTP_MISC_ORPHAN_MODE_SETTINGS
+
+ uint32_t supp_flags; ///< See ::NTP_ORPHAN_MODE_MSK
+ uint32_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+ uint32_t reserved_3; ///< Future use
+
+} NTP_MISC_ORPHAN_MODE_INFO;
+
+#define _mbg_swab_ntp_misc_orphan_mode_info( _p ) \
+do \
+{ \
+ _mbg_swab_ntp_misc_orphan_mode_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+} while ( 0 )
+
+
+/**
+ * @brief NTP leapfile settings to be read from / written to a device
+ *
+ * If ::NTP_MISC_MSK_LEAPFILE is set in ::NTP_MISC_LIMITS::supp_flags
+ * ::NTP_MISC_LEAPFILE_SETTINGS can be read / written.
+ */
+typedef struct
+{
+ uint8_t enable; ///< Generally enable / disable leapfile
+ uint8_t reserved_1; ///< Stratum level when no ref source available
+ uint16_t reserved_2; ///< Future use
+
+} NTP_MISC_LEAPFILE_SETTINGS;
+
+#define _mbg_swab_ntp_misc_leapfile_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+} while ( 0 )
+
+
+#else // !defined( _PRELIMINARY_CODE ), dummy declarations
+
+ typedef int NTP_RESTR_LIMITS;
+ typedef int NTP_RESTR;
+ typedef int NTP_RESTR_IDX;
+ typedef int NTP_DISCARD_LIMITS;
+ typedef int NTP_DISCARD_SETTINGS;
+ typedef int NTP_REFCLK_CFG_SETTINGS;
+ typedef int NTP_REFCLK_CFG_SETTINGS_IDX;
+ typedef int NTP_REFCLK_CFG_INFO;
+ typedef int NTP_REFCLK_CFG_INFO_IDX;
+ typedef int NTP_SYMM_KEY_LIMITS;
+ typedef int NTP_SYMM_KEY_SETTINGS;
+ typedef int NTP_SYMM_KEY_SETTINGS_IDX;
+ typedef int NTP_SYMM_KEY_INFO;
+ typedef int NTP_SYMM_KEY_INFO_IDX;
+ typedef int NTP_TRUSTED_KEY_SETTINGS;
+ typedef int NTP_TRUSTED_KEY_SETTINGS_IDX;
+ typedef int NTP_TRUSTED_KEY_INFO;
+ typedef int NTP_TRUSTED_KEY_INFO_IDX;
+ typedef int NTP_STATS_GLB_SETTINGS;
+ typedef int NTP_STATS_GLB_INFO;
+ typedef int NTP_MISC_LIMITS;
+ typedef int NTP_MISC_DRIFTFILE_SETTINGS;
+ typedef int NTP_MISC_ORPHAN_MODE_SETTINGS;
+ typedef int NTP_MISC_ORPHAN_MODE_INFO;
+ typedef int NTP_MISC_LEAPFILE_SETTINGS;
+
+#endif // defined( _PRELIMINARY_CODE )
+
+
+/**
+ * @brief Client settings of an NTP device
+ *
+ * This structure should be sent to an NTP client to configure client parameters
+ */
+typedef struct
+{
+ uint8_t num_peers; ///< number available peers
+ uint8_t reserved_1; ///< reserved, currently 0
+ uint16_t reserved_2; ///< reserved, currently 0
+
+ uint32_t reserved_3; ///< reserved, currently 0
+
+ uint32_t flags; ///< NTP flags, see @ref NTP_FLAG_MASKS
+
+} NTP_CLNT_MODE_SETTINGS;
+
+#define _mbg_swab_ntp_clnt_mode_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Client settings info of an NTP device
+ *
+ * This structure can be used to determine possible NTP client settings and the current configuration
+ */
+typedef struct
+{
+ NTP_CLNT_MODE_SETTINGS settings;
+
+ uint8_t n_supp_peers; ///< maximal number of configurable peers
+ uint8_t n_supp_pref_peers; ///< maximal number of configurable preferred ref sources
+ uint8_t poll_intv_min; ///< minimal supported NTP polling interval
+ uint8_t poll_intv_max; ///< maximal supported NTP polling interval
+
+ uint32_t reserved_1; ///< reserved, currently 0
+ uint32_t reserved_2; ///< reserved, currently 0
+
+ uint32_t supp_flags; ///< supported NTP flags, see @ref NTP_FLAG_MASKS
+ uint32_t supp_peer_flags; ///< supported NTP flags for peers, see @ref NTP_FLAG_MASKS
+
+} NTP_CLNT_MODE_INFO;
+
+#define _mbg_swab_ntp_clnt_mode_info( _p ) \
+do \
+{ \
+ _mbg_swab_ntp_clnt_mode_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ _mbg_swab32( &(_p)->supp_peer_flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief General NTP peer settings limits to be read from a device
+ *
+ * Used to query from a device how many NTP associations are supported
+ * by the device, then index 0..::NTP_PEER_LIMITS::n_cur_peers-1
+ * peer records can be read from a device. A maximum of
+ * ::NTP_PEER_LIMITS::n_supp_peers can be configured at all.
+ */
+typedef struct
+{
+ uint16_t n_supp_peers; ///< maximum number of configurable peers
+ uint16_t n_cur_peers; ///< current number of configured peers
+
+ uint8_t poll_intv_min; ///< minimum supported NTP polling interval
+ uint8_t poll_intv_max; ///< maximum supported NTP polling interval
+ uint8_t reserved_1; ///< reserved, currently 0
+ uint8_t reserved_2; ///< reserved, currently 0
+
+ uint32_t supp_assoc_types; ///< supported types of NTP associations
+ uint32_t reserved_3; ///< reserved, currently 0
+
+ uint32_t supp_flags_server; ///< supported flags for unicast associations
+ uint32_t supp_flags_peer; ///< supported flags for unicast symmetric-active assocations
+ uint32_t supp_flags_pool; ///< supported flags for unicast pool associations
+ uint32_t supp_flags_broadcast; ///< supported flags for broadcast associations
+ uint32_t supp_flags_multicast; ///< supported flags for multicast associations
+ uint32_t supp_flags_manycast; ///< supported flags for manycast associations
+ uint32_t supp_flags_broadcastclient; ///< supported flags for broadcast client associations
+ uint32_t supp_flags_multicastclient; ///< supported flags for multicast client associations
+ uint32_t supp_flags_manycastclient; ///< supported flags for manycast client associations
+ uint32_t reserved_4; ///< reserved, currently 0
+ uint32_t reserved_5; ///< reserved, currently 0
+ uint32_t reserved_6; ///< reserved, currently 0
+
+} NTP_PEER_LIMITS;
+
+#define _mbg_swab_ntp_peer_limits( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->n_supp_peers ); \
+ _mbg_swab16( &(_p)->n_cur_peers ); \
+ _mbg_swab32( &(_p)->supp_assoc_types ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+ _mbg_swab32( &(_p)->supp_flags_server ); \
+ _mbg_swab32( &(_p)->supp_flags_peer ); \
+ _mbg_swab32( &(_p)->supp_flags_pool ); \
+ _mbg_swab32( &(_p)->supp_flags_broadcast ); \
+ _mbg_swab32( &(_p)->supp_flags_multicast ); \
+ _mbg_swab32( &(_p)->supp_flags_manycast ); \
+ _mbg_swab32( &(_p)->supp_flags_broadcastclient ); \
+ _mbg_swab32( &(_p)->supp_flags_multicastclient ); \
+ _mbg_swab32( &(_p)->supp_flags_manycastclient ); \
+ _mbg_swab32( &(_p)->reserved_4 ); \
+ _mbg_swab32( &(_p)->reserved_5 ); \
+ _mbg_swab32( &(_p)->reserved_6 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Peer settings for NTP devices to configure an upload NTP server
+ *
+ * This structure should be read from the NTP client device to retrieve the
+ * current settings and capabilities. The number of supported peers is
+ * ::NTP_CLNT_MODE_INFO::n_supp_peers.
+ *
+ * @note The ::NTP_PEER_SETTINGS_IDX structure should be send back
+ * to the device to save the configuration.
+ */
+typedef struct
+{
+ MBG_HOSTNAME hostname; ///< hostname or IP address of the peer, not used
+ ///< when the NTP_BROADCASTCLIENT flag is set
+
+ uint8_t min_poll; ///< minimal configurable NTP polling interval
+ uint8_t max_poll; ///< maximal configurable NTP polling interval
+ uint8_t ttl; ///< time-to-live to use with broadcast/multicast/manycast
+ uint8_t reserved_1; ///< reserved, currently 0
+
+ uint32_t key; ///< ID of the symmetric key used with this association,
+ ///< this must be in the range 1-65534, 0 = disabled
+ uint32_t reserved_3; ///< reserved, currently 0
+ uint32_t reserved_4; ///< reserved, currently 0
+
+ uint32_t flags; ///< additional options configured, see @ref NTP_FLAG_MASKS
+
+} NTP_PEER_SETTINGS;
+
+#define _mbg_swab_ntp_peer_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->key ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+ _mbg_swab32( &(_p)->reserved_4 ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Peer settings for NTP devices
+ *
+ * @see ::NTP_PEER_SETTINGS
+ */
+typedef struct
+{
+ uint32_t idx;
+ NTP_PEER_SETTINGS peer_settings;
+
+} NTP_PEER_SETTINGS_IDX;
+
+#define _mbg_swab_ntp_peer_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_ntp_peer_settings( &(_p)->peer_settings ); \
+} while ( 0 )
+
+
+/**
+ * @brief Server settings of an NTP device
+ *
+ * This structure should be sent to an NTP server to configure server parameters
+ */
+typedef struct
+{
+ uint8_t num_refclks; ///< number of available refclks @ref NTP_REFCLK_CFG_INFO
+ uint8_t reserved_1; ///< reserved, currently 0
+ uint16_t reserved_2; ///< reserved, currently 0
+
+ uint32_t reserved_3; ///< reserved, currently 0
+
+ uint32_t flags; ///< NTP flags, see @ref NTP_FLAG_MASKS
+
+} NTP_SRV_MODE_SETTINGS;
+
+#define _mbg_swab_ntp_srv_mode_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+/**
+ * @brief Server settings info of an NTP device
+ *
+ * This structure should be used to query an NTP server configuration from a device
+ */
+typedef struct
+{
+ NTP_SRV_MODE_SETTINGS settings;
+
+ uint8_t max_refclks; ///< number of supported refclks @ref NTP_REFCLK_CFG_INFO
+ uint8_t reserved_1; ///< reserved, currently 0
+ uint16_t reserved_2; ///< reserved, currently 0
+
+ uint32_t reserved_3; ///< reserved, currently 0
+
+ uint32_t supp_flags; ///< supported NTP flags, see @ref NTP_FLAG_MASKS
+
+} NTP_SRV_MODE_INFO;
+
+#define _mbg_swab_ntp_srv_mode_info( _p ) \
+do \
+{ \
+ _mbg_swab_ntp_srv_mode_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->supp_flags ); \
+} while ( 0 )
+
+
+/**
+ * @brief Structure that represents a timestamp in NTP Short Format
+ *
+ * Maximal value for seconds is 65535.
+ * Resolution of fractions is 15 microseconds.
+ */
+typedef struct
+{
+ uint16_t seconds;
+ uint16_t fractions;
+
+} NTP_SHORT_TSTAMP;
+
+#define _mbg_swab_ntp_short_tstamp( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->seconds ); \
+ _mbg_swab16( &(_p)->fractions ); \
+}
+
+
+
+/**
+ * @brief Structure that represents a timestamp in NTP Timestamp Format
+ */
+typedef struct
+{
+ uint32_t seconds; ///< seconds since NTP epoch, see ::NTP_SEC_BIAS
+ uint32_t fractions; ///< binary fractional part of a second, 0xFFFFFFFF -> 0.9999999... s (resolution 2^-32s =~ 233 ps)
+
+} NTP_TSTAMP;
+
+#define _mbg_swab_ntp_tstamp( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->seconds ); \
+ _mbg_swab32( &(_p)->fractions ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of known NTP implementations
+ *
+ * Used with ::NTP_SYS_STATE::impl_type
+ */
+enum NTP_IMPL
+{
+ NTP_IMPL_UNKNOWN = 0, ///< Unknown NTP implementation
+ NTP_IMPL_NTPD, ///< Network Time Protocol daemon (ntpd)
+ NTP_IMPL_NTPDATE, ///< NTP client only (ntpdate)
+ NTP_IMPL_SNTP, ///< Simple Network Time Protocol (sntp)
+ NTP_IMPL_W32TIME, ///< Windows time service (w32time)
+ NTP_IMPL_MBGNTP, ///< Meinberg NTP implementation (mbgntp)
+ N_NTP_IMPLS
+};
+
+/*
+ * Default initializers for English leapsecond string names. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_IMPL_STR_ENG "Implemetation Type:"
+
+#define MBG_NTP_IMPL_STR_ENG_UNKNOWN "Unknown NTP implementation"
+#define MBG_NTP_IMPL_STR_ENG_NTPD "Network Time Protocol daemon (ntpd)"
+#define MBG_NTP_IMPL_STR_ENG_NTPDATE "NTP client only (ntpdate)"
+#define MBG_NTP_IMPL_STR_ENG_SNTP "Simple Network Time Protocol (sntp)"
+#define MBG_NTP_IMPL_STR_ENG_W32TIME "Windows time service (w32time)"
+#define MBG_NTP_IMPL_STR_ENG_MBGNTP "Meinberg NTP implementation (mbgntp)"
+
+
+#define MBG_NTP_IMPL_NAMES_ENG \
+{ \
+ MBG_NTP_IMPL_STR_ENG_UNKNOWN, \
+ MBG_NTP_IMPL_STR_ENG_NTPD, \
+ MBG_NTP_IMPL_STR_ENG_NTPDATE, \
+ MBG_NTP_IMPL_STR_ENG_SNTP, \
+ MBG_NTP_IMPL_STR_ENG_W32TIME, \
+ MBG_NTP_IMPL_STR_ENG_MBGNTP \
+}
+
+
+
+/**
+ * @brief Enumeration of CPU types using NTP
+ *
+ * Used with ::NTP_SYS_STATE::cpu_type
+ */
+enum NTP_CPU_TYPES
+{
+ NTP_CPU_TYPE_UNKNOWN = 0,
+ NTP_CPU_TYPE_X86,
+ NTP_CPU_TYPE_I386,
+ NTP_CPU_TYPE_I486,
+ NTP_CPU_TYPE_I586,
+ NTP_CPU_TYPE_I686,
+ NTP_CPU_TYPE_X64,
+ NTP_CPU_TYPE_X86_64,
+ NTP_CPU_TYPE_AMD64,
+ NTP_CPU_TYPE_SUN4U,
+ NTP_CPU_TYPE_ARM,
+ N_NTP_CPU_TYPES
+};
+
+
+
+/**
+ * @brief Name strings for known CPU types using NTP
+ *
+ * @see ::NTP_CPU_TYPES
+ */
+#define NTP_CPU_TYPES_STRS \
+{ \
+ "Unknown", \
+ "x86", \
+ "i386", \
+ "i486", \
+ "i586", \
+ "i686", \
+ "x64", \
+ "x86_64", \
+ "amd64", \
+ "sun4u", \
+ "arm" \
+}
+
+
+
+/**
+ * @brief Enumeration of operating systems using NTP
+ *
+ * Used with ::NTP_SYS_STATE::system
+*/
+enum NTP_SYSTEMS
+{
+ NTP_SYSTEM_UNKNOWN = 0,
+ NTP_SYSTEM_NONE,
+ NTP_SYSTEM_WINDOWS,
+ NTP_SYSTEM_LINUX,
+ NTP_SYSTEM_BSD,
+ NTP_SYSTEM_SOLARIS,
+ N_NTP_SYSTEMS
+};
+
+
+
+/**
+ * @brief Name strings for operating systens using NTP
+ *
+ * @see ::NTP_SYSTEMS
+ */
+#define NTP_SYSTEMS_STRS \
+{ \
+ "Unknown", \
+ "No OS", \
+ "Windows", \
+ "Linux", \
+ "BSD", \
+ "Solaris" \
+}
+
+
+
+/**
+ * @brief Enumeration of NTP leap indication bits
+ *
+ * Used with ::NTP_SYS_STATE::leap_ind
+ *
+ */
+enum NTP_LI_BITS
+{
+ NTP_LEAP_NONE = 0, ///< normal synchronized state
+ NTP_LEAP_ADD_SEC, ///< insert second after 23:59:59 of the current day
+ NTP_LEAP_DEL_SEC, ///< delete second 23:59:59 of the current day
+ NTP_LEAP_ALARM, ///< never synchronized
+ N_NTP_LI_BITS
+};
+
+
+
+/*
+ * Default initializers for English leapsecond string names. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_LEAP_STR_ENG "Leapsecond indication:"
+
+#define MBG_NTP_LEAP_STR_ENG_NONE "None"
+#define MBG_NTP_LEAP_STR_ENG_ADD_SEC "Insert second"
+#define MBG_NTP_LEAP_STR_ENG_DEL_SEC "Delete second"
+#define MBG_NTP_LEAP_STR_ENG_ALARM "Alarm"
+
+#define MBG_NTP_LEAP_NAMES_ENG \
+{ \
+ MBG_NTP_LEAP_STR_ENG_NONE, \
+ MBG_NTP_LEAP_STR_ENG_ADD_SEC, \
+ MBG_NTP_LEAP_STR_ENG_DEL_SEC, \
+ MBG_NTP_LEAP_STR_ENG_ALARM \
+}
+
+
+
+/**
+ * @brief Enumeration of NTP synchronization source bits
+ *
+ * Used with ::NTP_SYS_STATE::sys_sync_src
+ *
+ */
+enum NTP_SYNC_SRC_BITS
+{
+ NTP_SYNC_SRC_UNSPEC = 0, ///< not yet synchronized
+ NTP_SYNC_SRC_PPS, ///< pulse-per-second signal (Cs, Ru, GPS, etc.)
+ NTP_SYNC_SRC_LF_RADIO, ///< VLF/LF radio (WWVB, DCF77, etc.)
+ NTP_SYNC_SRC_HF_RADIO, ///< MF/HF radio (WWV, etc.)
+ NTP_SYNC_SRC_UHF_RADIO, ///< VHF/UHF radio/satellite (GPS, Galileo, etc.)
+ NTP_SYNC_SRC_LOCAL, ///< local timecode (IRIG, LOCAL driver, etc.)
+ NTP_SYNC_SRC_NTP, ///< NTP
+ NTP_SYNC_SRC_OTHER, ///< other (IEEE 1588, openntp, crony, etc.)
+ NTP_SYNC_SRC_WRISTWATCH, ///< eyeball and wristwatch
+ NTP_SYNC_SRC_TELEPHONE, ///< telephone modem (ACTS, PTB, etc.)
+ N_NTP_SYNC_SRC_BITS
+};
+
+
+
+/*
+ * Default initializers for English sync source string names. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_SYNC_SRC_STR_ENG_LABEL "Sync Source:"
+
+#define MBG_NTP_SYNC_SRC_STR_ENG_UNSPEC "Not yet synchronized"
+#define MBG_NTP_SYNC_SRC_STR_ENG_PPS "Pulse per second signal"
+#define MBG_NTP_SYNC_SRC_STR_ENG_LF_RADIO "VLF/LF radio"
+#define MBG_NTP_SYNC_SRC_STR_ENG_HF_RADIO "MF/HF radio"
+#define MBG_NTP_SYNC_SRC_STR_ENG_UHF_RADIO "VHF/UHF radio/satellite"
+#define MBG_NTP_SYNC_SRC_STR_ENG_LOCAL "local timecode"
+#define MBG_NTP_SYNC_SRC_STR_ENG_NTP "NTP"
+#define MBG_NTP_SYNC_SRC_STR_ENG_OTHER "other"
+#define MBG_NTP_SYNC_SRC_STR_ENG_WRISTWATCH "eyeball and wristwatch"
+#define MBG_NTP_SYNC_SRC_STR_ENG_TELEPHONE "telephone modem"
+
+#define MBG_NTP_SYNC_SRC_NAMES_ENG \
+{ \
+ MBG_NTP_SYNC_SRC_STR_ENG_UNSPEC, \
+ MBG_NTP_SYNC_SRC_STR_ENG_PPS, \
+ MBG_NTP_SYNC_SRC_STR_ENG_LF_RADIO, \
+ MBG_NTP_SYNC_SRC_STR_ENG_HF_RADIO, \
+ MBG_NTP_SYNC_SRC_STR_ENG_UHF_RADIO, \
+ MBG_NTP_SYNC_SRC_STR_ENG_LOCAL, \
+ MBG_NTP_SYNC_SRC_STR_ENG_NTP, \
+ MBG_NTP_SYNC_SRC_STR_ENG_OTHER, \
+ MBG_NTP_SYNC_SRC_STR_ENG_WRISTWATCH, \
+ MBG_NTP_SYNC_SRC_STR_ENG_TELEPHONE \
+}
+
+
+
+/**
+ * @brief Enumeration of NTP system event message bits
+ *
+ * Used with ::NTP_SYS_STATE::sys_rec_evt
+ *
+ */
+enum NTP_SYS_EVT_BITS
+{
+ NTP_SYS_EVT_UNSPEC = 0, ///< unspecified NTP event
+ NTP_SYS_EVT_FREQ_NOT_SET, ///< frequency file not available
+ NTP_SYS_EVT_FREQ_SET, ///< frequency set from frequency file
+ NTP_SYS_EVT_SPIKE_DETECT, ///< spike detected
+ NTP_SYS_EVT_FREQ_MODE, ///< initial frequency training mode
+ NTP_SYS_EVT_CLOCK_SYNC, ///< clock synchronized
+ NTP_SYS_EVT_RESTART, ///< program restart
+ NTP_SYS_EVT_PANIC_STOP, ///< clock error more than 600 s
+ NTP_SYS_EVT_NO_SYSTEM_PEER, ///< no system peer
+ NTP_SYS_EVT_LEAP_ARMED, ///< leap second armed from file or autokey
+ NTP_SYS_EVT_LEAP_DISARMED, ///< leap second disarmed
+ NTP_SYS_EVT_LEAP_EVENT, ///< leap event
+ NTP_SYS_EVT_CLOCK_STEP, ///< clock stepped
+ NTP_SYS_EVT_KERNEL, ///< kernel information message
+ NTP_SYS_EVT_TAI, ///< leapsecond values update from file
+ NTP_SYS_EVT_STALE_LS_VALUES, ///< new NIST leapseconds file needed
+ N_NTP_SYS_EVT_BITS
+};
+
+
+
+/*
+ * Default initializers for English sync source string names. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_SYS_EVT_STR_ENG_CNT_LABEL "System Event Counter:"
+#define MBG_NTP_SYS_EVT_STR_ENG_MSG_LABEL "System Event Message:"
+
+#define MBG_NTP_SYS_EVT_STR_ENG_UNSPEC "Unspecified NTP event"
+#define MBG_NTP_SYS_EVT_STR_ENG_FREQ_NOT_SET "Frequency file not available"
+#define MBG_NTP_SYS_EVT_STR_ENG_FREQ_SET "Frequency set from frequency file"
+#define MBG_NTP_SYS_EVT_STR_ENG_SPIKE_DETECT "Spike detected"
+#define MBG_NTP_SYS_EVT_STR_ENG_FREQ_MODE "Initial frequency training mode"
+#define MBG_NTP_SYS_EVT_STR_ENG_CLOCK_SYNC "Clock synchronized"
+#define MBG_NTP_SYS_EVT_STR_ENG_RESTART "Program restart"
+#define MBG_NTP_SYS_EVT_STR_ENG_PANIC_STOP "Clock error more than 600 s"
+#define MBG_NTP_SYS_EVT_STR_ENG_NO_SYSTEM_PEER "No system peer"
+#define MBG_NTP_SYS_EVT_STR_ENG_LEAP_ARMED "Leap second armed from file or autokey"
+#define MBG_NTP_SYS_EVT_STR_ENG_LEAP_DISARMED "Leap second disarmed"
+#define MBG_NTP_SYS_EVT_STR_ENG_LEAP_EVENT "Leap event"
+#define MBG_NTP_SYS_EVT_STR_ENG_CLOCK_STEP "Clock stepped"
+#define MBG_NTP_SYS_EVT_STR_ENG_KERNEL "Kernel information message"
+#define MBG_NTP_SYS_EVT_STR_ENG_TAI "Leap second values update from file"
+#define MBG_NTP_SYS_EVT_STR_ENG_STALE_LS_VALUES "New NIST leapseconds file needed"
+
+
+#define MBG_NTP_SYS_EVT_NAMES_ENG \
+{ \
+ MBG_NTP_SYS_EVT_STR_ENG_UNSPEC, \
+ MBG_NTP_SYS_EVT_STR_ENG_FREQ_NOT_SET, \
+ MBG_NTP_SYS_EVT_STR_ENG_FREQ_SET, \
+ MBG_NTP_SYS_EVT_STR_ENG_SPIKE_DETECT, \
+ MBG_NTP_SYS_EVT_STR_ENG_FREQ_MODE, \
+ MBG_NTP_SYS_EVT_STR_ENG_CLOCK_SYNC, \
+ MBG_NTP_SYS_EVT_STR_ENG_RESTART, \
+ MBG_NTP_SYS_EVT_STR_ENG_PANIC_STOP, \
+ MBG_NTP_SYS_EVT_STR_ENG_NO_SYSTEM_PEER, \
+ MBG_NTP_SYS_EVT_STR_ENG_LEAP_ARMED, \
+ MBG_NTP_SYS_EVT_STR_ENG_LEAP_DISARMED, \
+ MBG_NTP_SYS_EVT_STR_ENG_LEAP_EVENT, \
+ MBG_NTP_SYS_EVT_STR_ENG_CLOCK_STEP, \
+ MBG_NTP_SYS_EVT_STR_ENG_KERNEL, \
+ MBG_NTP_SYS_EVT_STR_ENG_TAI, \
+ MBG_NTP_SYS_EVT_STR_ENG_STALE_LS_VALUES \
+}
+
+
+
+/**
+ * @brief Enumeration of supported NTP system state values
+ *
+ * @see ::NTP_SYS_STATE_SUPP_FLAG_MASKS
+ */
+enum NTP_SYS_STATE_SUPP_FLAGS
+{
+ NTP_SYS_STATE_SUPP_STD = 0, ///< supports standard values of ::NTP_SYS_STATE, all fields except below and reserved
+ NTP_SYS_STATE_SUPP_EVENTS, ///< supports sys state events (::NTP_SYS_STATE::sys_evt_cnt, ::NTP_SYS_STATE::sys_rec_evt)
+ NTP_SYS_STATE_SUPP_PRECISION, ///< supports precision indication, see ::NTP_SYS_STATE::precision
+ NTP_SYS_STATE_SUPP_ROOT_DELAY, ///< supports root delay to syspeer, see ::NTP_SYS_STATE::root_delay
+ NTP_SYS_STATE_SUPP_ROOT_DISP, ///< supports root dispersion, see ::NTP_SYS_STATE::root_disp
+ NTP_SYS_STATE_SUPP_FREQ, ///< supports frequency offset, see ::NTP_SYS_STATE::freq
+ NTP_SYS_STATE_SUPP_SYS_JITTER, ///< supports combined jitter, see ::NTP_SYS_STATE::sys_jitter
+ NTP_SYS_STATE_SUPP_CLK_JITTER, ///< supports clock jitter, see ::NTP_SYS_STATE::clk_jitter
+ NTP_SYS_STATE_SUPP_CLK_WANDER, ///< supports clock wander, see ::NTP_SYS_STATE::clk_wander
+ N_NTP_SYS_STATE_SUPP_FLAGS
+};
+
+
+
+/**
+ * @brief Flag masks for NTP_SYS_STATE_SUPP_FLAGS
+ *
+ * Used with ::NTP_SYS_STATE::supp_flags
+ *
+ * @see ::NTP_SYS_STATE_SUPP_FLAGS
+ */
+enum NTP_SYS_STATE_SUPP_FLAG_MASKS
+{
+ NTP_SYS_STATE_SUPP_STD_MSK = ( 1UL << NTP_SYS_STATE_SUPP_STD ), ///< see ::NTP_SYS_STATE_SUPP_STD
+ NTP_SYS_STATE_SUPP_EVENTS_MSK = ( 1UL << NTP_SYS_STATE_SUPP_EVENTS ), ///< see ::NTP_SYS_STATE_SUPP_EVENTS
+ NTP_SYS_STATE_SUPP_PRECISION_MSK = ( 1UL << NTP_SYS_STATE_SUPP_PRECISION ), ///< see ::NTP_SYS_STATE_SUPP_PRECISION
+ NTP_SYS_STATE_SUPP_ROOT_DELAY_MSK = ( 1UL << NTP_SYS_STATE_SUPP_ROOT_DELAY ), ///< see ::NTP_SYS_STATE_SUPP_ROOT_DELAY
+ NTP_SYS_STATE_SUPP_ROOT_DISP_MSK = ( 1UL << NTP_SYS_STATE_SUPP_ROOT_DISP ), ///< see ::NTP_SYS_STATE_SUPP_ROOT_DISP
+ NTP_SYS_STATE_SUPP_FREQ_MSK = ( 1UL << NTP_SYS_STATE_SUPP_FREQ ), ///< see ::NTP_SYS_STATE_SUPP_FREQ
+ NTP_SYS_STATE_SUPP_SYS_JITTER_MSK = ( 1UL << NTP_SYS_STATE_SUPP_SYS_JITTER ), ///< see ::NTP_SYS_STATE_SUPP_SYS_JITTER
+ NTP_SYS_STATE_SUPP_CLK_JITTER_MSK = ( 1UL << NTP_SYS_STATE_SUPP_CLK_JITTER ), ///< see ::NTP_SYS_STATE_SUPP_CLK_JITTER
+ NTP_SYS_STATE_SUPP_CLK_WANDER_MSK = ( 1UL << NTP_SYS_STATE_SUPP_CLK_WANDER ) ///< see ::NTP_SYS_STATE_SUPP_CLK_WANDER
+};
+
+
+
+/**
+ * @brief Structure that represents the current system status of an NTP device
+ *
+ * This structure can be requested from a monitoring program to determine the device system status
+ */
+typedef struct
+{
+ uint32_t supp_flags; ///< Supported NTP system state values, see ::NTP_SYS_STATE_SUPP_FLAG_MASKS
+
+ uint8_t leap_ind; ///< Leap indicator, see ::NTP_LI_BITS
+ uint8_t sys_sync_src; ///< Current synchronization source, see ::NTP_SYNC_SRC_BITS
+ uint8_t sys_evt_cnt; ///< Number of events, since the last time the event code changed
+ uint8_t sys_rec_evt; ///< Most recent event message, see ::NTP_SYS_EVT_BITS
+
+ uint8_t impl_type; ///< NTP implementation type, see ::NTP_IMPL
+ uint8_t major_version; ///< Major version number
+ uint8_t minor_version; ///< Minor version number
+ uint8_t micro_version; ///< Micro version number
+
+ uint16_t patch_lvl; ///< Patch level number
+ uint8_t cpu_type; ///< Processor type, see ::NTP_CPU_TYPES
+ uint8_t system; ///< Operating system, see ::NTP_SYSTEMS
+
+ uint8_t stratum; ///< Current stratum level of the system
+ int8_t precision; ///< Precision of the system clock (2^precision)
+ uint16_t reserved_1; ///< Reserved, currently always 0
+
+ int32_t root_delay; ///< [us] Total roundtrip delay to the system peer
+ int32_t root_disp; ///< [us] Total dispersion to the system peer
+
+ MBG_IP_ADDR ref_id; ///< Reference ID of the current system peer, see ::MBG_IP_ADDR
+
+ NTP_TSTAMP ref_time; ///< Last time the system time has been adjusted, see ::NTP_TSTAMP
+ NTP_TSTAMP sys_time; ///< Current system time, see ::NTP_TSTAMP
+
+ uint16_t sys_peer; ///< Assocation ID of the current system peer
+ uint8_t poll; ///< Current polling interval for the system peer (tc)
+ uint8_t minpoll; ///< Minimal polling interval for the system peer (mintc)
+
+ int64_t offset; ///< [ns] Combined offset to the system peer
+
+ int32_t freq; ///< [ppb] Frequency offset relative to hardware clock
+ int32_t sys_jitter; ///< [us] Combined jitter of the system
+ int32_t clk_jitter; ///< [us] Jitter of the clock
+ int32_t clk_wander; ///< [ppb] Frequency wander of the clock
+
+ uint32_t reserved_2; ///< Reserved, currently always 0
+ uint32_t reserved_3; ///< Reserved, currently always 0
+
+} NTP_SYS_STATE;
+
+#define _mbg_swab_ntp_sys_state( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ \
+ _mbg_swab8( &(_p)->leap_ind ); \
+ _mbg_swab8( &(_p)->sys_sync_src ); \
+ _mbg_swab8( &(_p)->sys_evt_cnt ); \
+ _mbg_swab8( &(_p)->sys_rec_evt ); \
+ \
+ _mbg_swab8( &(_p)->impl_type ); \
+ _mbg_swab8( &(_p)->major_version ); \
+ _mbg_swab8( &(_p)->minor_version ); \
+ _mbg_swab8( &(_p)->micro_version ); \
+ \
+ _mbg_swab16( &(_p)->patch_lvl ); \
+ _mbg_swab8( &(_p)->cpu_type ); \
+ _mbg_swab8( &(_p)->system ); \
+ \
+ _mbg_swab8( &(_p)->stratum ); \
+ _mbg_swab8( &(_p)->precision ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ \
+ _mbg_swab32( &(_p)->root_delay ); \
+ _mbg_swab32( &(_p)->root_disp ); \
+ \
+ _mbg_swab_ip_addr( &(_p)->ref_id ); \
+ \
+ _mbg_swab_ntp_tstamp( &(_p)->ref_time ); \
+ _mbg_swab_ntp_tstamp( &(_p)->sys_time ); \
+ \
+ _mbg_swab16( &(_p)->sys_peer ); \
+ _mbg_swab8( &(_p)->poll ); \
+ _mbg_swab8( &(_p)->minpoll ); \
+ \
+ _mbg_swab64( &(_p)->offset ); \
+ \
+ _mbg_swab32( &(_p)->freq ); \
+ _mbg_swab32( &(_p)->sys_jitter ); \
+ _mbg_swab32( &(_p)->clk_jitter ); \
+ _mbg_swab32( &(_p)->clk_wander ); \
+ \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+ \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of NTP mode bits
+ *
+ * Used with ::NTP_PEER_STATE::host_mode and ::NTP_PEER_STATE::peer_mode
+ *
+ */
+enum NTP_MODE_BITS
+{
+ NTP_MODE_RESERVED = 0,
+ NTP_MODE_SYMM_ACT,
+ NTP_MODE_SYMM_PASS,
+ NTP_MODE_CLIENT,
+ NTP_MODE_SERVER,
+ NTP_MODE_BROADCAST,
+ NTP_MODE_CONTROL,
+ NTP_MODE_PRIVATE,
+ N_NTP_MODE_BITS
+};
+
+
+
+/*
+ * Default initializers for English NTP peer mode string names. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_MODE_STR_ENG_HOST_LABEL "Host Mode:"
+#define MBG_NTP_MODE_STR_ENG_PEER_LABEL "Peer Mode:"
+
+#define MBG_NTP_PEER_MODE_STR_ENG_RESERVED "Reserved"
+#define MBG_NTP_PEER_MODE_STR_ENG_SYMM_ACT "Symm Act"
+#define MBG_NTP_PEER_MODE_STR_ENG_SYMM_PASS "Symm Pass"
+#define MBG_NTP_PEER_MODE_STR_ENG_CLIENT "Client"
+#define MBG_NTP_PEER_MODE_STR_ENG_SERVER "Server"
+#define MBG_NTP_PEER_MODE_STR_ENG_BROADCAST "Broadcast"
+#define MBG_NTP_PEER_MODE_STR_ENG_CONTROL "Control"
+#define MBG_NTP_PEER_MODE_STR_ENG_PRIVATE "Private"
+
+#define MBG_NTP_MODE_STAT_NAMES_ENG \
+{ \
+ MBG_NTP_PEER_MODE_STR_ENG_RESERVED, \
+ MBG_NTP_PEER_MODE_STR_ENG_SYMM_ACT, \
+ MBG_NTP_PEER_MODE_STR_ENG_SYMM_PASS, \
+ MBG_NTP_PEER_MODE_STR_ENG_CLIENT, \
+ MBG_NTP_PEER_MODE_STR_ENG_SERVER, \
+ MBG_NTP_PEER_MODE_STR_ENG_BROADCAST, \
+ MBG_NTP_PEER_MODE_STR_ENG_CONTROL, \
+ MBG_NTP_PEER_MODE_STR_ENG_PRIVATE \
+}
+
+
+
+/**
+ * @brief Enumeration of NTP peer reach status
+ *
+ * Used with ::NTP_PEER_STATE::peer_reach_stat
+ */
+enum NTP_REACH_STAT_BITS
+{
+ NTP_REACH_STAT_UNKNOWN = 0, ///< unknown reach status
+ NTP_REACH_STAT_NO_LINK, ///< no network connection
+ NTP_REACH_STAT_DNS_UNREACH, ///< DNS server could not be reached
+ NTP_REACH_STAT_DNS_UNRESOLVED, ///< DNS name could not be resolved
+ NTP_REACH_STAT_PEER_UNREACH, ///< peer could not be reached
+ NTP_REACH_STAT_PEER_NOT_SYNC, ///< peer is not sync (leap alarm, stratum 16)
+ NTP_REACH_STAT_PEER_BAD_QUALITY, ///< peer has bad quality (dispersion, ...)
+ NTP_REACH_STAT_OK, ///< reach status is fine
+ N_NTP_REACH_STAT_BITS
+};
+
+
+
+/*
+ * Default initializers for English reach status string names. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_PEER_REACH_STAT_STR_ENG_LABEL "Reach State:"
+
+#define MBG_NTP_PEER_REACH_STAT_STR_ENG_UNKNOWN "Unknown"
+#define MBG_NTP_PEER_REACH_STAT_STR_ENG_NO_LINK "No link"
+#define MBG_NTP_PEER_REACH_STAT_STR_ENG_DNS_UNREACH "DNS Server unreached"
+#define MBG_NTP_PEER_REACH_STAT_STR_ENG_DNS_UNRESOLVED "DNS name not resolved"
+#define MBG_NTP_PEER_REACH_STAT_STR_ENG_PEER_UNREACH "Peer not reached"
+#define MBG_NTP_PEER_REACH_STAT_STR_ENG_PEER_NOT_SYNC "Peer not sync"
+#define MBG_NTP_PEER_REACH_STAT_STR_ENG_PEER_BAD_QUALITY "Peer has bad quality"
+#define MBG_NTP_PEER_REACH_STAT_STR_ENG_OK "Good"
+
+#define MBG_NTP_PEER_REACH_STAT_NAMES_ENG \
+{ \
+ MBG_NTP_PEER_REACH_STAT_STR_ENG_UNKNOWN, \
+ MBG_NTP_PEER_REACH_STAT_STR_ENG_NO_LINK, \
+ MBG_NTP_PEER_REACH_STAT_STR_ENG_DNS_UNREACH, \
+ MBG_NTP_PEER_REACH_STAT_STR_ENG_DNS_UNRESOLVED, \
+ MBG_NTP_PEER_REACH_STAT_STR_ENG_PEER_UNREACH, \
+ MBG_NTP_PEER_REACH_STAT_STR_ENG_PEER_NOT_SYNC, \
+ MBG_NTP_PEER_REACH_STAT_STR_ENG_PEER_BAD_QUALITY, \
+ MBG_NTP_PEER_REACH_STAT_STR_ENG_OK \
+}
+
+
+
+/**
+ * @brief Enumeration of NTP peer selection status
+ *
+ * Used with ::NTP_PEER_STATE::peer_sel_stat
+ *
+ */
+enum NTP_PEER_SEL_STATUS_BITS
+{
+ NTP_PEER_SEL_REJECT = 0, ///< discarded as not valid (TEST10-TEST13)
+ NTP_PEER_SEL_FALSETICK, ///< discarded by intersection algorithm
+ NTP_PEER_SEL_EXCESS, ///< discarded by table overflow (not used)
+ NTP_PEER_SEL_OUTLYER, ///< discarded by the cluster algorithm
+ NTP_PEER_SEL_CANDIDATE, ///< included by the combine algorithm
+ NTP_PEER_SEL_BACKUP, ///< backup (more than tos maxclock sources)
+ NTP_PEER_SEL_SYS_PEER, ///< system peer
+ NTP_PEER_SEL_PPS_PEER, ///< PPS peer (when the prefer peer is valid)
+ N_NTP_PEER_SEL_STATUS_BITS
+};
+
+
+
+/*
+ * Default initializers for English peer select status string names. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_PEER_SEL_STATUS_STR_ENG_LABEL "Selected Status:"
+
+#define MBG_NTP_PEER_SEL_STATUS_STR_ENG_REJECT "Not valid"
+#define MBG_NTP_PEER_SEL_STATUS_STR_ENG_FALSETICK "Falsetick"
+#define MBG_NTP_PEER_SEL_STATUS_STR_ENG_EXCESS "Excess"
+#define MBG_NTP_PEER_SEL_STATUS_STR_ENG_OUTLYER "Outlyer"
+#define MBG_NTP_PEER_SEL_STATUS_STR_ENG_CANDIDATE "Candidate"
+#define MBG_NTP_PEER_SEL_STATUS_STR_ENG_BACKUP "Backup"
+#define MBG_NTP_PEER_SEL_STATUS_STR_ENG_SYS_PEER "System Peer"
+#define MBG_NTP_PEER_SEL_STATUS_STR_ENG_PPS_PEER "PPS Peer"
+
+#define MBG_NTP_PEER_SEL_STATUS_NAMES_ENG \
+{ \
+ MBG_NTP_PEER_SEL_STATUS_STR_ENG_REJECT, \
+ MBG_NTP_PEER_SEL_STATUS_STR_ENG_FALSETICK, \
+ MBG_NTP_PEER_SEL_STATUS_STR_ENG_EXCESS, \
+ MBG_NTP_PEER_SEL_STATUS_STR_ENG_OUTLYER, \
+ MBG_NTP_PEER_SEL_STATUS_STR_ENG_CANDIDATE, \
+ MBG_NTP_PEER_SEL_STATUS_STR_ENG_BACKUP, \
+ MBG_NTP_PEER_SEL_STATUS_STR_ENG_SYS_PEER, \
+ MBG_NTP_PEER_SEL_STATUS_STR_ENG_PPS_PEER \
+}
+
+
+
+/**
+ * @brief Enumeration of NTP peer status codes
+ *
+ * @see ::NTP_PEER_STATUS_FLAG_MASKS
+ *
+ */
+enum NTP_PEER_STATUS_FLAGS
+{
+ NTP_PEER_STATUS_BCST = 0, ///< broadcast association
+ NTP_PEER_STATUS_REACH, ///< host reachable
+ NTP_PEER_STATUS_AUTHENB, ///< authentication enabled
+ NTP_PEER_STATUS_AUTH, ///< authentication ok
+ NTP_PEER_STATUS_CONFIG, ///< persistent association
+ N_NTP_PEER_STATUS_FLAGS
+};
+
+
+/**
+ * @brief Flag masks for NTP_PEER_STATUS_FLAGS
+ *
+ * Used with ::NTP_PEER_STATE::peer_status_flags
+ *
+ * @see ::NTP_PEER_STATUS_FLAGS
+ */
+enum NTP_PEER_STATUS_FLAG_MASKS
+{
+ NTP_PEER_STATUS_BCST_MSK = ( 1UL << NTP_PEER_STATUS_BCST ), ///< see ::NTP_PEER_STATUS_BCST
+ NTP_PEER_STATUS_REACH_MSK = ( 1UL << NTP_PEER_STATUS_REACH ), ///< see ::NTP_PEER_STATUS_REACH
+ NTP_PEER_STATUS_AUTHENB_MSK = ( 1UL << NTP_PEER_STATUS_AUTHENB ), ///< see ::NTP_PEER_STATUS_AUTHENB
+ NTP_PEER_STATUS_AUTH_MSK = ( 1UL << NTP_PEER_STATUS_AUTH ), ///< see ::NTP_PEER_STATUS_AUTH
+ NTP_PEER_STATUS_CONFIG_MSK = ( 1UL << NTP_PEER_STATUS_CONFIG ), ///< see ::NTP_PEER_STATUS_CONFIG
+};
+
+
+/*
+ * Default initializers for English peer status string names. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_PEER_STATUS_STR_ENG_LABEL "Peer Status:"
+
+#define MBG_NTP_PEER_STATUS_STR_ENG_BCST "Broadcast association"
+#define MBG_NTP_PEER_STATUS_STR_ENG_REACH "Host reachable"
+#define MBG_NTP_PEER_STATUS_STR_ENG_AUTHENB "Authentication enabled"
+#define MBG_NTP_PEER_STATUS_STR_ENG_CONFIG "Persistant assosiation"
+
+#define MBG_NTP_PEER_STATUS_NAMES_ENG \
+{ \
+ MBG_NTP_PEER_STATUS_STR_ENG_BCST, \
+ MBG_NTP_PEER_STATUS_STR_ENG_REACH, \
+ MBG_NTP_PEER_STATUS_STR_ENG_REACH, \
+ MBG_NTP_PEER_STATUS_STR_ENG_AUTHENB, \
+ MBG_NTP_PEER_STATUS_STR_ENG_CONFIG \
+}
+
+
+
+/**
+ * @brief Enumeration of NTP peer event message codes
+ *
+ * Used with ::NTP_PEER_STATE::peer_rec_evt
+ *
+ */
+enum NTP_PEER_EVT_BITS
+{
+ NTP_PEER_EVT_UNSPEC = 0, ///< unspecified NTP event
+ NTP_PEER_EVT_MOBILIZE, ///< association mobilized
+ NTP_PEER_EVT_DEMOBILIZE, ///< association demobilized
+ NTP_PEER_EVT_UNREACHABLE, ///< server unreachable
+ NTP_PEER_EVT_REACHABLE, ///< server reachable
+ NTP_PEER_EVT_RESTART, ///< association restart
+ NTP_PEER_EVT_NO_REPLY, ///< no server found (ntpdate mode)
+ NTP_PEER_EVT_RATE_EXCEEDED, ///< rate exceeded (kiss code RATE)
+ NTP_PEER_EVT_ACCESS_DENIED, ///< access denied (kiss code DENY)
+ NTP_PEER_EVT_LEAP_ARMED, ///< leap armed from server LI code
+ NTP_PEER_EVT_SYS_PEER, ///< become system peer
+ NTP_PEER_EVT_CLOCK_EVENT, ///< see clock status word
+ NTP_PEER_EVT_BAD_AUTH, ///< authentication failure
+ NTP_PEER_EVT_POPCORN, ///< popcorn spike suppressor
+ NTP_PEER_EVT_INTERLEAVE_MODE, ///< entering interleave mode
+ NTP_PEER_EVT_INTERLEAVE_ERROR, ///< interleave error (recovered)
+ N_NTP_PEER_EVT_BITS
+};
+
+
+
+/*
+ * Default initializers for English event message codes. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_PEER_EVT_STR_ENG_CNT_LABEL "Peer Event Counter:"
+#define MBG_NTP_PEER_EVT_STR_ENG_MSG_LABEL "Peer Event Message:"
+
+#define MBG_NTP_PEER_EVT_STR_ENG_UNSPEC "Unspecified NTP event"
+#define MBG_NTP_PEER_EVT_STR_ENG_MOBILIZE "Association mobilized"
+#define MBG_NTP_PEER_EVT_STR_ENG_DEMOBILIZE "Association demobilized"
+#define MBG_NTP_PEER_EVT_STR_ENG_UNREACHABLE "Server unreachable"
+#define MBG_NTP_PEER_EVT_STR_ENG_REACHABLE "Server reachable"
+#define MBG_NTP_PEER_EVT_STR_ENG_RESTART "Association restart"
+#define MBG_NTP_PEER_EVT_STR_ENG_NO_REPLY "No server found"
+#define MBG_NTP_PEER_EVT_STR_ENG_RATE_EXCEEDED "Rate exceeded"
+#define MBG_NTP_PEER_EVT_STR_ENG_ACCESS_DENIED "Access denied"
+#define MBG_NTP_PEER_EVT_STR_ENG_LEAP_ARMED "Leap second armed from LI code"
+#define MBG_NTP_PEER_EVT_STR_ENG_SYS_PEER "Become system Peer"
+#define MBG_NTP_PEER_EVT_STR_ENG_CLOCK_EVENT "Clock event"
+#define MBG_NTP_PEER_EVT_STR_ENG_BAD_AUTH "Authentication failure"
+#define MBG_NTP_PEER_EVT_STR_ENG_POPCORN "Popcorn Spike suspressor"
+#define MBG_NTP_PEER_EVT_STR_ENG_INTERLEAVE_MODE "Entering Interleave mode"
+#define MBG_NTP_PEER_EVT_STR_ENG_INTERLEAVE_ERROR "Interleave error"
+
+
+#define MBG_NTP_PEER_EVT_NAMES_ENG \
+{ \
+ MBG_NTP_PEER_EVT_STR_ENG_UNSPEC, \
+ MBG_NTP_PEER_EVT_STR_ENG_MOBILIZE, \
+ MBG_NTP_PEER_EVT_STR_ENG_DEMOBILIZE, \
+ MBG_NTP_PEER_EVT_STR_ENG_UNREACHABLE, \
+ MBG_NTP_PEER_EVT_STR_ENG_REACHABLE, \
+ MBG_NTP_PEER_EVT_STR_ENG_RESTART, \
+ MBG_NTP_PEER_EVT_STR_ENG_NO_REPLY, \
+ MBG_NTP_PEER_EVT_STR_ENG_RATE_EXCEEDED, \
+ MBG_NTP_PEER_EVT_STR_ENG_ACCESS_DENIED, \
+ MBG_NTP_PEER_EVT_STR_ENG_LEAP_ARMED, \
+ MBG_NTP_PEER_EVT_STR_ENG_SYS_PEER, \
+ MBG_NTP_PEER_EVT_STR_ENG_CLOCK_EVENT, \
+ MBG_NTP_PEER_EVT_STR_ENG_BAD_AUTH, \
+ MBG_NTP_PEER_EVT_STR_ENG_POPCORN, \
+ MBG_NTP_PEER_EVT_STR_ENG_INTERLEAVE_MODE, \
+ MBG_NTP_PEER_EVT_STR_ENG_INTERLEAVE_ERROR \
+}
+
+
+/**
+ * @brief Enumeration of NTP flash status bit codes
+ *
+ * @see ::NTP_FLASH_STAT_FLAG_MASKS
+ *
+ */
+enum NTP_FLASH_STAT_FLAGS
+{
+ NTP_FLASH_STAT_PKT_DUP = 0, ///< duplicate packet
+ NTP_FLASH_STAT_PKT_BOGUS, ///< bogus packet
+ NTP_FLASH_STAT_PKT_UNSYNC, ///< server not synchronized
+ NTP_FLASH_STAT_PKT_DENIED, ///< access denied
+ NTP_FLASH_STAT_PKT_AUTH, ///< authentication failure
+ NTP_FLASH_STAT_PKT_STRATUM, ///< invalid leap or stratum
+ NTP_FLASH_STAT_PKT_HEADER, ///< header distance exceeded
+ NTP_FLASH_STAT_PKT_AUTOKEY, ///< Autokey sequence error
+ NTP_FLASH_STAT_PKT_CRYPTO, ///< Autokey protocol error
+ NTP_FLASH_STAT_PEER_STRATUM, ///< invalid header or stratum
+ NTP_FLASH_STAT_PEER_DIST, ///< distance threshold exceeded
+ NTP_FLASH_STAT_PEER_LOOP, ///< synchronization loop
+ NTP_FLASH_STAT_PEER_UNREACH, ///< unreachable or nonselect
+ N_NTP_FLASH_STAT_FLAGS
+};
+
+
+
+/**
+ * @brief Flag masks for ::NTP_FLASH_STAT_FLAGS
+ *
+ * Used with ::NTP_PEER_STATE::flash_stat_flags
+ *
+ * @see ::NTP_FLASH_STAT_FLAGS
+ */
+enum NTP_FLASH_STAT_FLAG_MASKS
+{
+ NTP_FLASH_STAT_PKT_DUP_MSK = ( 1UL << NTP_FLASH_STAT_PKT_DUP ), ///< see ::NTP_FLASH_STAT_PKT_DUP
+ NTP_FLASH_STAT_PKT_BOGUS_MSK = ( 1UL << NTP_FLASH_STAT_PKT_BOGUS ), ///< see ::NTP_FLASH_STAT_PKT_BOGUS
+ NTP_FLASH_STAT_PKT_UNSYNC_MSK = ( 1UL << NTP_FLASH_STAT_PKT_UNSYNC ), ///< see ::NTP_FLASH_STAT_PKT_UNSYNC
+ NTP_FLASH_STAT_PKT_DENIED_MSK = ( 1UL << NTP_FLASH_STAT_PKT_DENIED ), ///< see ::NTP_FLASH_STAT_PKT_DENIED
+ NTP_FLASH_STAT_PKT_AUTH_MSK = ( 1UL << NTP_FLASH_STAT_PKT_AUTH ), ///< see ::NTP_FLASH_STAT_PKT_AUTH
+ NTP_FLASH_STAT_PKT_STRATUM_MSK = ( 1UL << NTP_FLASH_STAT_PKT_STRATUM ), ///< see ::NTP_FLASH_STAT_PKT_STRATUM
+ NTP_FLASH_STAT_PKT_HEADER_MSK = ( 1UL << NTP_FLASH_STAT_PKT_HEADER ), ///< see ::NTP_FLASH_STAT_PKT_HEADER
+ NTP_FLASH_STAT_PKT_AUTOKEY_MSK = ( 1UL << NTP_FLASH_STAT_PKT_AUTOKEY ), ///< see ::NTP_FLASH_STAT_PKT_AUTOKEY
+ NTP_FLASH_STAT_PKT_CRYPTO_MSK = ( 1UL << NTP_FLASH_STAT_PKT_CRYPTO ), ///< see ::NTP_FLASH_STAT_PKT_CRYPTO
+ NTP_FLASH_STAT_PEER_STRATUM_MSK = ( 1UL << NTP_FLASH_STAT_PEER_STRATUM ), ///< see ::NTP_FLASH_STAT_PEER_STRATUM
+ NTP_FLASH_STAT_PEER_DIST_MSK = ( 1UL << NTP_FLASH_STAT_PEER_DIST ), ///< see ::NTP_FLASH_STAT_PEER_DIST
+ NTP_FLASH_STAT_PEER_LOOP_MSK = ( 1UL << NTP_FLASH_STAT_PEER_LOOP ), ///< see ::NTP_FLASH_STAT_PEER_LOOP
+ NTP_FLASH_STAT_PEER_UNREACH_MSK = ( 1UL << NTP_FLASH_STAT_PEER_UNREACH ), ///< see ::NTP_FLASH_STAT_PEER_UNREACH
+};
+
+
+
+/*
+ * Default initializers for English ntp flash state mask. Initializers
+ * for multi-language strings can be found in tmonlstr.h.
+ */
+#define MBG_NTP_FLASH_STR_ENG_LABEL "Flash Status:"
+
+#define MBG_NTP_FLASH_STR_ENG_PKT_DUP "Duplicate packet"
+#define MBG_NTP_FLASH_STR_ENG_PKT_BOGUS "Bogus packet"
+#define MBG_NTP_FLASH_STR_ENG_PKT_UNSYNC "Server not synchronized"
+#define MBG_NTP_FLASH_STR_ENG_PKT_DENIED "Access denied"
+#define MBG_NTP_FLASH_STR_ENG_PKT_AUTH "Authentication failure"
+#define MBG_NTP_FLASH_STR_ENG_PKT_STRATUM "Invalid leap or stratum"
+#define MBG_NTP_FLASH_STR_ENG_PKT_HEADER "Header distance exceeded"
+#define MBG_NTP_FLASH_STR_ENG_PKT_AUTOKEY "Autokey sequence error"
+#define MBG_NTP_FLASH_STR_ENG_PKT_CRYPTO "Autokey protocol error"
+#define MBG_NTP_FLASH_STR_ENG_PEER_STRATUM "Invalid header or stratum"
+#define MBG_NTP_FLASH_STR_ENG_PEER_DIST "Distance threshold exceeded"
+#define MBG_NTP_FLASH_STR_ENG_PEER_LOOP "Synchronization loop"
+#define MBG_NTP_FLASH_STR_ENG_PEER_UNREACH "Unreachable or nonselect"
+
+
+#define MBG_NTP_FLASH_NAMES_ENG \
+{ \
+ MBG_NTP_FLASH_STR_ENG_PKT_DUP, \
+ MBG_NTP_FLASH_STR_ENG_PKT_BOGUS, \
+ MBG_NTP_FLASH_STR_ENG_PKT_UNSYNC, \
+ MBG_NTP_FLASH_STR_ENG_PKT_DENIED, \
+ MBG_NTP_FLASH_STR_ENG_PKT_AUTH, \
+ MBG_NTP_FLASH_STR_ENG_PKT_STRATUM, \
+ MBG_NTP_FLASH_STR_ENG_PKT_HEADER, \
+ MBG_NTP_FLASH_STR_ENG_PKT_AUTOKEY, \
+ MBG_NTP_FLASH_STR_ENG_PKT_CRYPTO, \
+ MBG_NTP_FLASH_STR_ENG_PEER_STRATUM, \
+ MBG_NTP_FLASH_STR_ENG_PEER_DIST, \
+ MBG_NTP_FLASH_STR_ENG_PEER_LOOP, \
+ MBG_NTP_FLASH_STR_ENG_PEER_UNREACH \
+}
+
+
+
+/**
+ * @brief Enumeration of supported NTP peer state values
+ *
+ * @see ::NTP_PEER_STATE_SUPP_FLAG_MASKS
+ */
+enum NTP_PEER_STATE_SUPP_FLAGS
+{
+ NTP_PEER_STATE_SUPP_STD, ///< supports standard values of ::NTP_PEER_STATE, all fields except below and reserved
+ NTP_PEER_STATE_SUPP_ASS_ID, ///< supports association ID, see ::NTP_PEER_STATE::ass_id
+ NTP_PEER_STATE_SUPP_EVENTS, ///< supports peer state events (NTP_PEER_STATE::peer_evt_cnt, NTP_PEER_STATE::peer_rec_evt)
+ NTP_PEER_STATE_SUPP_REACH_STAT, ///< supports peer reach status, see ::NTP_PEER_STATE::peer_reach_stat
+ NTP_PEER_STATE_SUPP_PRECISION, ///< supports precision indication, see ::NTP_PEER_STATE::precision
+ NTP_PEER_STATE_SUPP_ROOT_DELAY, ///< supports root delay to syspeer, see ::NTP_PEER_STATE::root_delay
+ NTP_PEER_STATE_SUPP_ROOT_DISP, ///< supports root dispersion, see ::NTP_PEER_STATE::root_disp
+ NTP_PEER_STATE_SUPP_HEADWAY, ///< supports headway, see ::NTP_PEER_STATE::headway
+ NTP_PEER_STATE_SUPP_FLASH_STAT, ///< supports flash status word, see ::NTP_PEER_STATE::flash_stat_flags
+ NTP_PEER_STATE_SUPP_KEY_ID, ///< supports symmetric key id, see ::NTP_PEER_STATE::key_id
+ NTP_PEER_STATE_SUPP_DISP, ///< supports filter dispersion, see ::NTP_PEER_STATE::disp
+ NTP_PEER_STATE_SUPP_JITTER, ///< supports filter jitter, see ::NTP_PEER_STATE::jitter
+ NTP_PEER_STATE_SUPP_XLEAVE, ///< supports interleave delay, see ::NTP_PEER_STATE::xleave
+ N_NTP_PEER_STATE_SUPP_FLAGS
+};
+
+
+/**
+ * @brief Flag masks for NTP_PEER_STATE_SUPP_FLAGS
+ *
+ * Used with ::NTP_PEER_STATE::supp_flags
+ *
+ * @see ::NTP_PEER_STATE_SUPP_FLAGS
+ */
+enum NTP_PEER_STATE_SUPP_FLAG_MASKS
+{
+ NTP_PEER_STATE_SUPP_STD_MSK = ( 1UL << NTP_PEER_STATE_SUPP_STD ), ///< see ::NTP_PEER_STATE_SUPP_STD
+ NTP_PEER_STATE_SUPP_ASS_ID_MSK = ( 1UL << NTP_PEER_STATE_SUPP_ASS_ID ), ///< see ::NTP_PEER_STATE_SUPP_ASS_ID
+ NTP_PEER_STATE_SUPP_EVENTS_MSK = ( 1UL << NTP_PEER_STATE_SUPP_EVENTS ), ///< see ::NTP_PEER_STATE_SUPP_EVENTS
+ NTP_PEER_STATE_SUPP_REACH_STAT_MSK = ( 1UL << NTP_PEER_STATE_SUPP_REACH_STAT ), ///< see ::NTP_PEER_STATE_SUPP_REACH_STAT
+ NTP_PEER_STATE_SUPP_PRECISION_MSK = ( 1UL << NTP_PEER_STATE_SUPP_PRECISION ), ///< see ::NTP_PEER_STATE_SUPP_PRECISION
+ NTP_PEER_STATE_SUPP_ROOT_DELAY_MSK = ( 1UL << NTP_PEER_STATE_SUPP_ROOT_DELAY ), ///< see ::NTP_PEER_STATE_SUPP_ROOT_DELAY
+ NTP_PEER_STATE_SUPP_ROOT_DISP_MSK = ( 1UL << NTP_PEER_STATE_SUPP_ROOT_DISP ), ///< see ::NTP_PEER_STATE_SUPP_ROOT_DISP
+ NTP_PEER_STATE_SUPP_HEADWAY_MSK = ( 1UL << NTP_PEER_STATE_SUPP_HEADWAY ), ///< see ::NTP_PEER_STATE_SUPP_HEADWAY
+ NTP_PEER_STATE_SUPP_FLASH_STAT_MSK = ( 1UL << NTP_PEER_STATE_SUPP_FLASH_STAT ), ///< see ::NTP_PEER_STATE_SUPP_FLASH_STAT
+ NTP_PEER_STATE_SUPP_KEY_ID_MSK = ( 1UL << NTP_PEER_STATE_SUPP_KEY_ID ), ///< see ::NTP_PEER_STATE_SUPP_KEY_ID
+ NTP_PEER_STATE_SUPP_DISP_MSK = ( 1UL << NTP_PEER_STATE_SUPP_DISP ), ///< see ::NTP_PEER_STATE_SUPP_DISP
+ NTP_PEER_STATE_SUPP_JITTER_MSK = ( 1UL << NTP_PEER_STATE_SUPP_JITTER ), ///< see ::NTP_PEER_STATE_SUPP_JITTER
+ NTP_PEER_STATE_SUPP_XLEAVE_MSK = ( 1UL << NTP_PEER_STATE_SUPP_XLEAVE ), ///< see ::NTP_PEER_STATE_SUPP_XLEAVE
+};
+
+
+
+/**
+ * @brief Structure that represents the status of an NTP peer
+ *
+ * This structure should be requested via ::NTP_PEER_STATE_IDX
+ *
+ * @see ::NTP_PEER_STATE_IDX
+ */
+typedef struct
+{
+ uint32_t supp_flags; ///< Supported NTP peer state values, see ::NTP_PEER_STATE_SUPP_FLAG_MASKS
+
+ uint16_t ass_id; ///< Association ID of the peer
+ uint16_t peer_status_flags; ///< Peer status flags, see ::NTP_PEER_STATUS_FLAG_MASKS
+
+ uint8_t leap_ind; ///< Leap indicator, see ::NTP_LI_BITS
+ uint8_t peer_sel_stat; ///< Current selection status of the peer, see ::NTP_PEER_SEL_STATUS_BITS
+ uint8_t peer_evt_cnt; ///< Number of events, since the last time the event code changed
+ uint8_t peer_rec_evt; ///< Most recent event message, see ::NTP_PEER_EVT_BITS
+
+ uint8_t peer_reach_stat; ///< Current reach status of the peer, see ::NTP_REACH_STAT_BITS
+ uint8_t reserved_1; ///< Reserved, currently always 0
+ uint16_t reserved_2; ///< Reserved, currently always 0
+
+ MBG_IP_ADDR_PORT src_addr; ///< Source address of the NTP peer, see ::MBG_IP_ADDR_PORT
+ MBG_IP_ADDR_PORT dst_addr; ///< Destination address of the NTP peer, see ::MBG_IP_ADDR_PORT
+
+ uint8_t stratum; ///< Current stratum level of the NTP peer
+ int8_t precision; ///< Precision of the peer clock (2^precision)
+ uint16_t reserved_3; ///< Reserved, currently always 0
+
+ int32_t root_delay; ///< [us] Total roundtrip delay to the system peer of the NTP peer
+ int32_t root_disp; ///< [us] Total dispersion to the system peer of the NTP peer
+
+ MBG_IP_ADDR ref_id; ///< Reference ID of the NTP peer, see ::MBG_IP_ADDR
+
+ NTP_TSTAMP ref_time; ///< Last time the NTP peers time has been adjusted, see ::NTP_TSTAMP
+ NTP_TSTAMP rec_time; ///< Current system time of the NTP peer, see ::NTP_TSTAMP
+
+ uint8_t reach; ///< Shift register for the last 8 polling intervals
+ uint8_t reserved_4; ///< Reserved, currently always 0
+ uint16_t unreach; ///< Counter for the number of unsuccessful polling intervals
+
+ uint8_t host_mode; ///< NTP mode of the requesting host, see ::NTP_MODE_BITS
+ uint8_t peer_mode; ///< NTP mode of the peer, see ::NTP_MODE_BITS
+ uint8_t host_poll; ///< Host NTP polling interval
+ uint8_t peer_poll; ///< Peer NTP polling interval
+
+ uint8_t headway; ///< Indicator for the KoD packet, TODO: further investigation
+ uint8_t reserved_5; ///< Reserved, currently always 0
+ uint16_t flash_stat_flags; ///< Flash status flags, see ::NTP_FLASH_STAT_FLAG_MASKS
+
+ uint16_t key_id; ///< ID of symmetric authentication key
+ uint16_t reserved_6; ///< Reserved, currently always 0
+
+ int64_t offset; ///< [ns] filter offset to this NTP peer
+ int64_t delay; ///< [ns] filter delay to this NTP peer
+
+ int32_t disp; ///< [us] filter dispersion of the NTP peer
+ int32_t jitter; ///< [us] filter jitter of the NTP peer
+
+ uint32_t xleave; ///< [ns] interleave delay of the NTP peer
+
+ uint8_t n_filter_values; ///< Number of filter values available, currently always 0
+ uint8_t reserved_7; ///< Reserved, currently always 0
+ uint16_t reserved_8; ///< Reserved, currently always 0
+
+ uint32_t reserved_9; ///< Reserved, currently always 0
+
+} NTP_PEER_STATE;
+
+
+
+#define _mbg_swab_ntp_peer_state( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_flags ); \
+ \
+ _mbg_swab16( &(_p)->ass_id ); \
+ _mbg_swab16( &(_p)->peer_status_flags ); \
+ \
+ _mbg_swab8( &(_p)->leap_ind ); \
+ _mbg_swab8( &(_p)->peer_sel_stat ); \
+ _mbg_swab8( &(_p)->peer_evt_cnt ); \
+ _mbg_swab8( &(_p)->peer_rec_evt ); \
+ \
+ _mbg_swab8( &(_p)->peer_reach_stat ); \
+ _mbg_swab8( &(_p)->reserved_1 ); \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+ \
+ _mbg_swab_ip_addr_port( &(_p)->src_addr ); \
+ _mbg_swab_ip_addr_port( &(_p)->dst_addr ); \
+ \
+ _mbg_swab8( &(_p)->stratum ); \
+ _mbg_swab8( &(_p)->precision ); \
+ _mbg_swab16( &(_p)->reserved_3 ); \
+ \
+ _mbg_swab32( &(_p)->root_delay ); \
+ _mbg_swab32( &(_p)->root_disp ); \
+ \
+ _mbg_swab_ip_addr( &(_p)->ref_id ); \
+ \
+ _mbg_swab_ntp_tstamp( &(_p)->ref_time ); \
+ _mbg_swab_ntp_tstamp( &(_p)->rec_time ); \
+ \
+ _mbg_swab8( &(_p)->reach ); \
+ _mbg_swab8( &(_p)->reserved_4 ); \
+ _mbg_swab16( &(_p)->unreach ); \
+ \
+ _mbg_swab8( &(_p)->host_mode ); \
+ _mbg_swab8( &(_p)->peer_mode ); \
+ _mbg_swab8( &(_p)->host_poll ); \
+ _mbg_swab8( &(_p)->peer_poll ); \
+ \
+ _mbg_swab8( &(_p)->headway ); \
+ _mbg_swab8( &(_p)->reserved_5 ); \
+ _mbg_swab16( &(_p)->flash_stat_flags ); \
+ \
+ _mbg_swab16( &(_p)->key_id ); \
+ _mbg_swab16( &(_p)->reserved_6 ); \
+ \
+ _mbg_swab64( &(_p)->offset ); \
+ _mbg_swab64( &(_p)->delay ); \
+ \
+ _mbg_swab32( &(_p)->disp ); \
+ _mbg_swab32( &(_p)->jitter ); \
+ \
+ _mbg_swab32( &(_p)->xleave ); \
+ \
+ _mbg_swab8( &(_p)->n_filter_values ); \
+ _mbg_swab8( &(_p)->reserved_7 ); \
+ _mbg_swab16( &(_p)->reserved_8 ); \
+ \
+ _mbg_swab32( &(_p)->reserved_9 ); \
+ \
+} while ( 0 )
+
+
+
+/**
+ * @brief Structure that contains an index value and the NTP peer state
+ *
+ * This structure can be requested by a monitoring program to observe the status of configured NTP peers
+ *
+ * @see ::NTP_PEER_STATE
+ */
+typedef struct
+{
+ uint32_t idx; ///< The index of the observed NTP peer
+ NTP_PEER_STATE peer_state; ///< Peer state, see ::NTP_PEER_STATE
+
+} NTP_PEER_STATE_IDX;
+
+#define _mbg_swab_ntp_peer_state_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_ntp_peer_state( &(_p)->peer_state ); \
+} while ( 0 )
+
+
+/** @} defgroup group_ntp */
+
/**
@@ -6694,6 +17707,7 @@ typedef struct
} LNO_STATE;
#define _mbg_swab_lno_state( _p ) \
+do \
{ \
int i; \
\
@@ -6703,7 +17717,7 @@ typedef struct
_mbg_swab_16( &(_p)->max_sine_lvl ); \
_mbg_swab_16( &(_p)->reserved_0 ); \
_mbg_swab_16( &(_p)->flags ); \
-}
+} while ( 0 )
/**
@@ -6717,10 +17731,773 @@ enum LNO_STATE_FLAG_BITS
#define LNO_FLAG_PLL_LOCKED ( 1UL << LNO_FLAG_BIT_PLL_LOCKED )
-/** @} group_lno */
+/** @} defgroup group_lno */
+
+
+
+/**
+ * @defgroup group_vst Definitions used with Versatile Storage
+ *
+ * Versatile storage is used to store binary data on a device where the storage
+ * device must not necessarily know about the data structure. It just stores
+ * a piece of data, and retrieves it on demand.
+ *
+ * The structures and associated API calls are only supported if the
+ * ::GPS_HAS_VST bit is set in ::RECEIVER_INFO::features.
+ *
+ * @{ */
+
+/**
+ * @brief Known common VST data types
+ */
+enum VST_DATA_TYPES
+{
+ VST_DATA_TYPE_MAC_ADDR, //##++++++++++++ This is just an example. More to be added.
+ N_VST_DATA_TYPES
+};
+
+
+/**
+ * @brief
+ */
+typedef struct
+{
+ uint16_t data_type; ///< data type identifier, see ::VST_DATA_TYPES for common types
+ uint16_t idx; ///< Index for several sets of the same type
+ uint16_t data_len; ///< length of the data set appended to the header
+ uint16_t reserved; ///< reserved, currently always 0
+
+} VST_HEADER;
+
+#define _mbg_swab_vst_header( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->data_type ); \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab16( &(_p)->data_len ); \
+ _mbg_swab16( &(_p)->reserved ); \
+} while ( 0 )
+
+/** @} defgroup group_vst */
+
+
+
+/**
+ * @defgroup group_shs Definitions used with SHS devices
+ *
+ * An SHS (Secure Hybrid System) device compares the times from 2 sources
+ * and eventually sets an alarm (warning and/or error) flag if the difference
+ * between the 2 time sources exceeds a configurable limit.
+ *
+ * These structures and associated definitions are used to query the SHS
+ * capabilities, configure the SHS device according to its capabilities,
+ * and query the SHS status.
+ *
+ * The structures and associated API calls are only supported if the
+ * ::GPS_HAS_SHS bit is set in ::RECEIVER_INFO::features.
+ *
+ * The ::SHS_INFO structure can be read to retrieve the capabilities and
+ * current settings of the device. The ::SHS_SETTINGS structure can then
+ * be set up according to the capabilities, and be written back to configure
+ * the device.
+ *
+ * If ::SHS_SETTINGS::err_limit and/or ::SHS_SETTINGS::warn_limit are
+ * not 0 then the SHS device checks if the time difference between the
+ * 2 clocks exceeds these limits and sets ::SHS_STATUS::shs_state
+ * as appropriate.
+ *
+ * If indicated by ::SHS_INFO::supp_flags the SHS device can also take
+ * certain actions if the time difference exceeds the error limit.
+ * If this happens then the same flags are set in ::SHS_STATUS::flags
+ * to indicate the action has been taken.
+ *
+ * @{ */
+
+/**
+ * @brief Current configuration of an SHS controller
+ *
+ * @see ::SHS_INFO
+ * @see ::SHS_STATUS
+ */
+typedef struct
+{
+ NANO_TIME err_limit; ///< time difference limit above which an error is indicated
+ NANO_TIME warn_limit; ///< time difference limit above which a warning is indicated
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t flags; ///< see ::SHS_FLAG_MASKS
+
+} SHS_SETTINGS;
+
+#define _mbg_swab_shs_settings( _p ) \
+do \
+{ \
+ _mbg_swab_nano_time( &(_p)->err_limit ); \
+ _mbg_swab_nano_time( &(_p)->warn_limit ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Current SHS settings and general SHS capabilities
+ *
+ * @see ::SHS_SETTINGS
+ * @see ::SHS_STATUS
+ */
+typedef struct
+{
+ SHS_SETTINGS settings; ///< current configuration settings
+ NANO_TIME max_limit; ///< if not 0, the max. allowed value for ::SHS_SETTINGS::err_limit and ::SHS_SETTINGS::warn_limit
+ uint32_t reserved; ///< reserved, currently always 0
+ uint32_t supp_flags; ///< indicates which flags are supported for ::SHS_SETTINGS::flags, see ::SHS_FLAG_MASKS
+
+} SHS_INFO;
+
+#define _mbg_swab_shs_info( _p ) \
+do \
+{ \
+ _mbg_swab_shs_settings( &(_p)->settings ); \
+ _mbg_swab_nano_time( &(_p)->max_limit ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Current SHS status
+ */
+typedef struct
+{
+ NANO_TIME time_diff; ///< current time difference between the 2 clocks
+ TM_STATUS_EXT clk_status_1; ///< status of first clock
+ TM_STATUS_EXT clk_status_2; ///< status of second clock
+ uint8_t shs_state; ///< see ::SHS_STATES
+ uint8_t reserved_1; ///< reserved, currently always 0
+ uint16_t reserved_2; ///< reserved, currently always 0
+ uint32_t flags; ///< see ::SHS_FLAG_MASKS
+
+} SHS_STATUS;
+
+#define _mbg_swab_shs_status( _p ) \
+do \
+{ \
+ _mbg_swab_nano_time( &(_p)->time_diff ); \
+ _mbg_swab32( &(_p)->clk_status_1 ); \
+ _mbg_swab32( &(_p)->clk_status_2 ); \
+ _mbg_swab16( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief SHS configuration flag bits
+ *
+ * Codes used with ::SHS_STATUS::shs_state
+ */
+enum SHS_STATES
+{
+ SHS_STATE_DISABLED, ///< time difference not checked, eventually no limits configured
+ SHS_STATE_OK, ///< time difference OK, below warning limit
+ SHS_STATE_WARNING, ///< time difference exceeds warning limit
+ SHS_STATE_ERROR, ///< time difference exceeds error limit
+ SHS_STATE_FATAL, ///< one or both time sources disconnected
+ N_SHS_STATES
+};
+
+
+
+/**
+ * @brief SHS flag bits
+ *
+ * @see ::SHS_FLAG_MASKS
+ */
+enum SHS_FLAG_BITS
+{
+ SHS_FLAG_BIT_DISB_SERIAL, ///< disable serial output in state ::SHS_STATE_ERROR
+ SHS_FLAG_BIT_DISB_PPS, ///< disable PPS output in state ::SHS_STATE_ERROR
+ SHS_FLAG_BIT_DISB_10MHZ, ///< disable 10 MHz output in state ::SHS_STATE_ERROR
+ N_SHS_FLAG_BITS
+};
+
+
+/**
+ * @brief SHS flag masks
+ *
+ * With ::SHS_INFO::supp_flags these flags indicate what is supported
+ * by the SHS controller, e.g. what action can be taken automatically.
+ * Each bit set in ::SHS_INFO::supp_flags can be set by a configuration
+ * tool in ::SHS_SETTINGS::flags to enable the associated feature.
+ * If a corresponding bit is set in ::SHS_STATUS::flags this means the
+ * associated feature has been enabled, e.g. an action has been taken.
+ *
+ * @see ::SHS_FLAG_BITS
+ */
+enum SHS_FLAG_MASKS
+{
+ SHS_FLAG_DISB_SERIAL = ( 1UL << SHS_FLAG_BIT_DISB_SERIAL ), ///< see ::SHS_FLAG_BIT_DISB_SERIAL
+ SHS_FLAG_DISB_PPS = ( 1UL << SHS_FLAG_BIT_DISB_PPS ), ///< see ::SHS_FLAG_BIT_DISB_PPS
+ SHS_FLAG_DISB_10MHZ = ( 1UL << SHS_FLAG_BIT_DISB_10MHZ ) ///< see ::SHS_FLAG_BIT_DISB_10MHZ
+};
+
+/** @} defgroup group_shs */
+
+
+
+/**
+ * @defgroup group_xbp eXtended Binary Protocol definitions
+ *
+ * @note These structures are only supported if ::GPS_HAS_XBP is set
+ * in ::RECEIVER_INFO::features.
+ *
+ * @{ */
+
+/**
+ * @brief An XBP port specifier
+ *
+ * Each controller can provide up to 255 ports with numbers 0..254.
+ * XBP port number ::XBP_PORT_RESERVED is reserved to mark unused ports.
+ */
+typedef uint8_t XBP_PORT;
+
+
+/**
+ * @brief An identifier used to mark an XBP port unused
+ */
+#define XBP_PORT_RESERVED ( (XBP_PORT) -1 )
+
+
+/**
+ * @brief Maximum XBP bus/controller cascading level
+ *
+ * Should be 7 so the total size of ::XBP_ADDR is 8 bytes.
+ */
+#define MAX_XBP_CASC_LVL 7
+
+
+/**
+ * @brief An XBP address specifier
+ *
+ * A generic scheme to address devices connected to cascaded controllers.
+ */
+typedef struct
+{
+ uint8_t hop_count; ///< Used as index to the addr array
+ XBP_PORT addr[MAX_XBP_CASC_LVL]; ///< An array of port numbers on cascaded controllers
+
+} XBP_ADDR;
+
+#define _mbg_swab_xbp_addr( _p ) _nop_macro_fnc() // only single bytes
+
+
+
+/**
+ * @brief A structure used to report XBP features and limits
+ */
+typedef struct
+{
+ uint32_t features; ///< Mask of XBP features, see ::XBP_FEAT_MASKS
+ uint32_t flags; ///< XBP flags, currently not used
+ uint32_t reserved_0; ///< reserved, currently not used
+ uint32_t reserved_1; ///< reserved, currently not used
+ uint32_t reserved_2; ///< reserved, currently not used
+ uint32_t reserved_3; ///< reserved, currently not used
+
+} XBP_LIMITS;
+
+#define _mbg_swab_xbp_limits( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->features ); \
+ _mbg_swab32( &(_p)->flags ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of bits used to define ::XBP_FEAT_MASKS
+ */
+enum XBP_FEAT_BITS
+{
+ XBP_FEAT_BIT_NODES, ///< Supports ::XBP_NODE_LIMITS and associated structures
+ N_XBP_FEAT_BITS
+};
+
+
+/**
+ * @brief XBP feature masks used with ::XBP_LIMITS::features
+ *
+ * @see ::XBP_FEAT_BITS
+ */
+enum XBP_FEAT_MASKS
+{
+ XBP_FEAT_MASK_NODES = ( 1UL << XBP_FEAT_BIT_NODES ) ///< See ::XBP_FEAT_BIT_NODES
+};
+
+
+
+/**
+ * @brief Information on available XBP nodes
+ *
+ * Only supported if ::XBP_FEAT_MASK_NODES is set in ::XBP_LIMITS::features.
+ */
+typedef struct
+{
+ uint32_t node_count; ///< Number of XBP nodes available in the system
+ uint32_t reserved_0; ///< Currently reserved, always 0
+ uint32_t reserved_1; ///< Currently reserved, always 0
+ // TODO: do we need additional fields here?
+
+} XBP_NODE_LIMITS;
+
+#define _mbg_swab_xbp_node_limits( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->node_count ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Possible states of an XBP device
+ *
+ * Used with ::XBP_NODE_INFO::state.
+ */
+enum XBP_DEVICE_STATES
+{
+ XBP_DEVICE_STATE_UNKNOWN,
+ XBP_DEVICE_STATE_NOT_AVAILABLE,
+ XBP_DEVICE_STATE_INITIALIZING,
+ XBP_DEVICE_STATE_AVAILABLE,
+ XBP_DEVICE_STATE_DISCONNECTED,
+ N_XBP_DEVICE_STATES
+};
+
+
+
+/**
+ * @brief Information on a specific XBP node
+ *
+ * Only supported if ::XBP_FEAT_MASK_NODES is set in ::XBP_LIMITS::features.
+ * The number of instances supported by a device is specified
+ * in ::XBP_NODE_LIMITS::node_count.
+ */
+typedef struct
+{
+ XBP_ADDR addr; ///< The address of the specific node
+
+ /// ::RECEIVER_INFO of the device connected to this node.
+ /// If no device is available then ::RECEIVER_INFO::model_code
+ /// is set to ::GPS_MODEL_UNKNOWN (== 0).
+ RECEIVER_INFO ri;
+
+ uint8_t state; ///< The device state, see ::XBP_DEVICE_STATES
+ uint8_t reserved; ///< Currently reserved, always 0
+ uint32_t flags; ///< Currently reserved, always 0
+
+} XBP_NODE_INFO;
+
+#define _mbg_swab_xbp_node_info( _p ) \
+do \
+{ \
+ _mbg_swab_xbp_addr( &(_p)->addr ); \
+ _mbg_swab_receiver_info( &(_p)->ri ); \
+ _mbg_swab8( &(_p)->state ); \
+ _mbg_swab8( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Information on an XBP node with specific index
+ *
+ * Only supported if ::XBP_FEAT_MASK_NODES is set in ::XBP_LIMITS::features.
+ */
+typedef struct
+{
+ uint32_t idx; ///< node index, 0..::XBP_NODE_LIMITS::node_count-1
+ XBP_NODE_INFO node_info; ///< ::RECEIVER_INFO of the device behind this node
+
+} XBP_NODE_INFO_IDX;
+
+#define _mbg_swab_xbp_node_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_xbp_node_info( &(_p)->node_info ); \
+} while ( 0 )
+
+
+/** @} defgroup group_xbp */
+
+
+
+/**
+ * @defgroup group_tlv_api Meinberg TLV API definitions
+ *
+ * @note These structures and definitions are only supported by a device
+ * if ::MBG_XFEATURE_TLV_API is set in the extended device features.
+ *
+ * @{ */
+
+
+/**
+ * @brief A data type used to hold a unique ID (UID) for a TLV transaction
+ */
+typedef uint32_t MBG_TLV_UID;
+
+#define _mbg_swab_tlv_uid( _p ) \
+ _mbg_swab32( _p )
-/*------------------------------------------------------------------------*/
+
+/**
+ * @brief A data type to hold one of the ::MBG_TLV_TYPES or ::MBG_TLV_FEAT_TYPES
+ *
+ * @see ::MBG_TLV_TYPES
+ * @see ::MBG_TLV_FEAT_TYPES
+ */
+typedef uint32_t MBG_TLV_TYPE;
+
+#define _mbg_swab_tlv_type( _p ) \
+ _mbg_swab32( _p )
+
+
+
+/**
+ * @defgroup group_tlv_feat Meinberg TLV feature definitions
+ *
+ * @{ */
+
+
+/**
+ * @brief The maximum number of TLV feature types.
+ *
+ * Warning: Changing this number breaks API compatibility!
+ *
+ * @see ::MBG_TLV_FEAT_TYPES
+ */
+#define MAX_MBG_TLV_FEAT_TYPES 128 //### TODO Is this sufficient?
+
+
+/**
+ * @brief Enumeration of known TLV feature types.
+ *
+ * TLV feature types are used to specify the content of a binary TLV message
+ * so that the receiver knows how to interpret the content.
+ *
+ * Used with ::MBG_TLV_INFO::supp_tlv_feat and ::MBG_TLV_DATA::type. ### TODO
+ *
+ * @see ::MBG_TLV_FEAT_BUFFER
+ * @see ::MBG_TLV_FEAT_TYPE_NAMES
+ * @see ::MBG_TLV_TYPES
+ * @see ::MBG_TLV_TYPE
+ */
+enum MBG_TLV_FEAT_TYPES
+{
+ /// Expects two TLV types in order:
+ /// 1) ::MBG_TLV_TYPE_STR => Firmware version as string
+ /// 2) ::MBG_TLV_TYPE_FILE => Firmware file as data blob
+ MBG_TLV_FEAT_TYPE_FW_UPDATE,
+
+ /// If announce message's total bytes are 0, it is a diagnostics file
+ /// request. If its total bytes are not 0, TLV type ::MBG_TLV_TYPE_FILE
+ /// is expected and it should contain a file as data blob.
+ MBG_TLV_FEAT_TYPE_DIAG_FILE,
+
+ /// Only used as action trigger on a remote site, expects no data.
+ MBG_TLV_FEAT_TYPE_FW_ROLLBACK,
+
+ /// Expects two TLV types in order:
+ /// 1) ::MBG_TLV_TYPE_STR => Full qualified path including filename on target system
+ /// 2) ::MBG_TLV_TYPE_FILE => File as data blob
+ MBG_TLV_FEAT_TYPE_FILE_TRANSFER,
+
+ /// 1) ::MBG_TLV_TYPE_STR => Command line call as string
+ MBG_TLV_FEAT_TYPE_EXEC_CMD,
+
+ /// 1) ::MBG_TLV_TYPE_FILE => Encrypted license file as data blob
+ MBG_TLV_FEAT_TYPE_LICENSE_UPGRADE,
+
+ /// 1) ::MBG_TLV_TYPE_BLOB => ::MBG_LICENSE_LIMITS, see @ref group_license_limits
+ MBG_TLV_FEAT_TYPE_LICENSE_LIMITS,
+
+ /// 1) ::MBG_TLV_TYPE_BLOB => ::MBG_LICENSE_PTPV2_IDX, see @ref group_license_limits
+ MBG_TLV_FEAT_TYPE_LICENSE_PTPV2_IDX,
+
+ /// 1) ::MBG_TLV_TYPE_BLOB => ::MBG_LICENSE_NTP_IDX, see @ref group_license_limits
+ MBG_TLV_FEAT_TYPE_LICENSE_NTP_IDX,
+
+ /// Expects two TLV types in order:
+ /// 1) ::MBG_TLV_TYPE_STR => Full qualified path including filename on target system
+ MBG_TLV_FEAT_TYPE_FILE_REQUEST,
+
+ /// 1) ::MBG_TLV_TYPE_BLOB => ::MBG_LICENSE_PTPV1_IDX, see @ref group_license_limits
+ MBG_TLV_FEAT_TYPE_LICENSE_PTPV1_IDX,
+
+ /// 1) ::MBG_TLV_TYPE_BLOB => ::MBG_LICENSE_TIME_MONITOR_IDX, see @ref group_license_limits
+ MBG_TLV_FEAT_TYPE_LICENSE_TIME_MONITOR_IDX,
+
+ N_MBG_TLV_FEAT_TYPES
+ // NOTE If new TLV feature types are appended here then an appropriate
+ // name string has to be appended to ::MBG_TLV_FEAT_TYPE_NAMES, and care must
+ // be taken that ::N_MBG_TLV_FEAT_TYPES doesn't exceed ::MAX_MBG_TLV_FEAT_TYPES.
+};
+
+
+/**
+ * @brief Names of TLV API features
+ *
+ * Can be used to initialize a string array of ::N_MBG_TLV_FEAT_TYPES entries,
+ * so the number of strings must correspond to ::N_MBG_TLV_FEAT_TYPES.
+ *
+ * @see ::MBG_TLV_FEAT_TYPES
+ */
+#define MBG_TLV_FEAT_TYPE_NAMES \
+{ \
+ "TLV Firmware Update", \
+ "TLV Diagnostics File", \
+ "TLV Firmware Rollback", \
+ "TLV File Transfer", \
+ "TLV Execute Command", \
+ "TLV License Upgrade", \
+ "TLV License Limits", \
+ "TLV License PTPV2", \
+ "TLV License NTP", \
+ "TLV File Request", \
+ "TLV License PTPV1 IDX", \
+ "TLV License Time Monitor" \
+}
+
+
+
+/**
+ * @brief Array size required to store up to ::MAX_MBG_TLV_FEAT_TYPES bits
+ *
+ * The number of bytes required to store up to ::MAX_MBG_TLV_FEAT_TYPES
+ * feature bits in a byte array.
+ */
+#define MAX_MBG_TLV_FEAT_BYTES ( MAX_MBG_TLV_FEAT_TYPES / 8 )
+
+
+/**
+ * @brief A structure used to store a bit mask of supported TLV context types.
+ *
+ * Bit masks for up to ::MAX_MBG_TLV_FEAT_TYPES totally can be stored,
+ * but only ::N_MBG_TLV_FEAT_TYPES types are currently defined.
+ * The ::_set_tlv_feat_bit macro should be used by the firmware
+ * to set a bit mask in the buffer, and the ::check_tlv_feat_supp
+ * function should be used to implement API calls which test if an
+ * extended TLV context type is supported.
+ *
+ * @see ::_set_tlv_feat_bit
+ * @see ::check_tlv_feat_supp
+ */
+typedef struct
+{
+ uint8_t b[MAX_MBG_TLV_FEAT_BYTES];
+
+} MBG_TLV_FEAT_BUFFER;
+
+
+
+/**
+ * @brief Set a TLV context type bit in a ::MBG_TLV_FEAT_BUFFER
+ *
+ * Should be used by the firmware only to set one of the ::MBG_TLV_FEAT_TYPES
+ * bits in an ::MBG_TLV_FEAT_BUFFER after power-up.
+ *
+ * @param[in] _tlv_feat_type One of the ::MBG_TLV_FEAT_TYPES
+ * @param[in] _tlv_feat_buffp Pointer to a ::MBG_TLV_FEAT_BUFFER
+ */
+#define _set_tlv_feat_bit( _tlv_feat_type, _tlv_feat_buffp ) \
+ _set_array_bit( _tlv_feat_type, (_tlv_feat_buffp)->b, MAX_MBG_TLV_FEAT_BYTES )
+
+
+/** @} defgroup group_tlv_feat */
+
+
+
+/**
+ * @brief A structure used to query current TLV capabilities
+ *
+ * This is only supported by a device if the ::MBG_XFEATURE_TLV_API bit
+ * is set in the extended device features.
+ */
+typedef struct
+{
+ uint32_t reserved; ///< Future use
+ uint32_t flags; ///< Future use
+ MBG_TLV_FEAT_BUFFER supp_tlv_feat; ///< A byte array of supported TLV feature bits, see ::MBG_TLV_FEAT_TYPES
+
+} MBG_TLV_INFO;
+
+#define _mbg_swab_tlv_info( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Enumeration of known TLV types
+ *
+ * Used with ::MBG_TLV_TYPE types, e.g. in ::MBG_TLV_HDR::tlv_type
+ * or ::MBG_TLV_DATA::type.
+ *
+ * @see ::MBG_TLV_FEAT_TYPES
+ * @see ::MBG_TLV_TYPE
+ */
+enum MBG_TLV_TYPES
+{
+ MBG_TLV_TYPE_STR,
+ MBG_TLV_TYPE_FILE,
+ MBG_TLV_TYPE_BLOB, ///< In fact, a file is also a blob but
+ ///< give the child a different name to avoid confusion.
+ ///< Use this for getting/setting fixed structures!
+ N_MBG_TLV_TYPES
+};
+
+
+
+/**
+ * @brief General TLV data structure
+ *
+ * Structure containing common, additional data required to send
+ * an announce message for following TLVs.
+ */
+typedef struct
+{
+ MBG_TLV_UID uid; ///< Unique ID identifying following TLVs, 0 if empty/not set.
+ MBG_TLV_TYPE type; ///< One of the ::MBG_TLV_TYPES or ::MBG_TLV_FEAT_TYPES depending on the type of message.
+ uint32_t total_bytes; ///< Number of all bytes including header(s) that are related to a TLV block transaction.
+ uint32_t reserved_1; ///< Reserved for future use
+
+} MBG_TLV_DATA;
+
+#define _mbg_swab_tlv_data( _p ) \
+do \
+{ \
+ _mbg_swab_tlv_uid( &(_p)->uid ); \
+ _mbg_swab_tlv_type( &(_p)->type ); \
+ _mbg_swab32( &(_p)->total_bytes ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Structure containing state information while reading TLV data.
+ */
+typedef struct
+{
+ MBG_TLV_DATA data; ///< See ::MBG_TLV_DATA
+ uint32_t read_bytes; ///< Number of bytes read
+ uint32_t reserved_1; ///< Future use
+
+} MBG_TLV_RCV_STATE;
+
+
+
+/**
+ * @brief A structure initiating a TLV transfer
+ *
+ * ::MBG_TLV_ANNOUNCE should be sent first, before starting a
+ * TLV transfer, to inform the remote site about following TLVs.
+ * Following sequence of TLVs is not fixed and implementation
+ * dependent.
+ */
+typedef struct
+{
+ MBG_TLV_DATA data; ///< See ::MBG_TLV_DATA
+ uint32_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+
+} MBG_TLV_ANNOUNCE;
+
+#define _mbg_swab_tlv_announce( _p ) \
+do \
+{ \
+ _mbg_swab_tlv_data( &(_p)->data ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+} while ( 0 )
+
+
+
+#define MSG_TLV_MAX_VALUE_SIZE 480
+
+/**
+ * @brief TLV header structure containing information on current TLV transaction
+ */
+typedef struct
+{
+ MBG_TLV_UID uid; ///< Unique source ID. See ::MBG_TLV_DATA::uid
+ MBG_TLV_UID tlv_type; ///< "Subtype" identifying current TLV, see ::MBG_TLV_TYPES
+ uint32_t cur_bytes; ///< Number of bytes in ::MBG_TLV::value
+ uint32_t trans_bytes; ///< Number of bytes transferred so far related to this TLV type.
+ uint32_t total_bytes; ///< Number of total bytes (size) of this TLV type without header.
+ ///< It is fixed and must not be changed during a TLV transaction.
+ uint32_t reserved_1; ///< Future use
+ uint32_t reserved_2; ///< Future use
+ uint32_t reserved_3; ///< Future use
+
+} MBG_TLV_HDR;
+
+#define _mbg_swab_tlv_header( _p ) \
+do \
+{ \
+ _mbg_swab_tlv_uid( &(_p)->uid ); \
+ _mbg_swab_tlv_type( &(_p)->tlv_type ); \
+ _mbg_swab32( &(_p)->cur_bytes ); \
+ _mbg_swab32( &(_p)->trans_bytes ); \
+ _mbg_swab32( &(_p)->total_bytes ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief TLV structure containing information on current TLV transaction and its current data.
+ */
+typedef struct
+{
+ MBG_TLV_HDR hdr; ///< See ::MBG_TLV_HDR
+ uint8_t value[MSG_TLV_MAX_VALUE_SIZE]; ///< See ::MSG_TLV_MAX_VALUE_SIZE
+
+} MBG_TLV;
+
+#define _mbg_swab_tlv( _p ) \
+do \
+{ \
+ _mbg_swab_tlv_header( &(_p)->hdr ); \
+} while ( 0 )
+
+/** @} defgroup group_tlv_api */
+
+
+
+/**
+ * @defgroup group_gps_nav_data Definitions used with navigational data received from GPS satellites
+ *
+ * @note These structures and definitions are only supported by a device
+ * if ::GPS_MODEL_IS_GPS is set in the @ref GPS_BUILTIN_FEATURE_MASKS
+ *
+ * @{ */
+
/**
* @brief Ephemeris parameters of one specific satellite
@@ -6767,6 +18544,7 @@ typedef struct
uint8_t L2code; ///< code on L2 channel [---]
uint8_t L2flag; ///< L2 P data flag [---]
+
} EPH;
@@ -6796,6 +18574,7 @@ typedef struct
double deltai; ///< +- [rad]
double af0; ///< +- Clock Correction Coefficient 0 [sec]
double af1; ///< +- Clock Correction Coefficient 1 [sec/sec]
+
} ALM;
@@ -6805,15 +18584,16 @@ typedef struct
*/
typedef struct
{
- CSUM csum; ///< checksum of the remaining bytes
- int16_t valid; ///< flag data are valid
+ CSUM csum; ///< checksum of the remaining bytes
+ int16_t valid; ///< flag data are valid
- T_GPS tot_51; ///< time of transmission, page 51
- T_GPS tot_63; ///< time of transmission, page 63
- T_GPS t0a; ///< complete reference time almanac
+ T_GPS tot_51; ///< time of transmission, page 51
+ T_GPS tot_63; ///< time of transmission, page 63
+ T_GPS t0a; ///< complete reference time almanac
+
+ CFG cfg[N_SVNO_GPS]; ///< 4 bit SV configuration code from page 63
+ HEALTH health[N_SVNO_GPS]; ///< 6 bit SV health codes from pages 51, 63
- CFG cfg[N_SVNO]; ///< SV configuration from page 63
- HEALTH health[N_SVNO]; ///< SV health from pages 51, 63
} CFGH;
@@ -6841,17 +18621,18 @@ typedef struct
* after the next leap second event defined by WNlsf and DNt.
*
* The fields WNlsf and DNt specify the GPS week number and the day number
- * in that week at the end of which a leap second is scheduled.
+ * in that week for the end of which a leap second has been scheduled.
*
* @note: The satellites transmit WNlsf only as a signed 8 bit value, so it
- * can only define a point in time which is ± 127 weeks off the current time.
+ * can only define a point in time which is +/- 127 weeks off the current time.
* The firmware tries to expand this based on the current week number, but
* the result is ambiguous if the leap second occurs or occurred more
* than 127 weeks in the future or past.
*
- * So the leap second date should only be evaluated if the fields delta_tls
- * and delta_tlsf are different, in which case there is an actual leap second
- * announcement inside the ± 127 week range.
+ * So the leap second date should <b>only</b> be evaluated and displayed
+ * in a user interface if the fields delta_tls and delta_tlsf have
+ * different values, in which case there is indeed a leap second announcement
+ * inside the +/- 127 week range.
*/
typedef struct
{
@@ -6866,9 +18647,11 @@ typedef struct
int16_t DNt; ///< The day number at the end of which a leap second occurs
int8_t delta_tls; ///< Current %UTC offset to GPS system time [sec]
int8_t delta_tlsf; ///< Future %UTC offset to GPS system time after next leap second transition [sec]
+
} UTC;
#define _mbg_swab_utc_parm( _p ) \
+do \
{ \
_mbg_swab_csum( &(_p)->csum ); \
_mbg_swab16( &(_p)->valid ); \
@@ -6877,7 +18660,7 @@ typedef struct
_mbg_swab_double( &(_p)->A1 ); \
_mbg_swab16( &(_p)->WNlsf ); \
_mbg_swab16( &(_p)->DNt ); \
-}
+} while ( 0 )
@@ -6898,6 +18681,7 @@ typedef struct
double beta_1; ///< Ionosph. Corr. Coeff. Beta 1 [sec/deg]
double beta_2; ///< Ionosph. Corr. Coeff. Beta 2 [sec/deg^2]
double beta_3; ///< Ionosph. Corr. Coeff. Beta 3 [sec/deg^3]
+
} IONO;
@@ -6910,8 +18694,11 @@ typedef struct
CSUM csum; ///< checksum of the remaining bytes */
int16_t valid; ///< flag data are valid
char s[23]; ///< 22 chars GPS ASCII message plus trailing zero
+
} ASCII_MSG;
+/** @} defgroup group_gps_nav_data */
+
enum GPS_PLATFORMS
@@ -6963,11 +18750,13 @@ typedef struct
int32_t fixedPosY; // cm
int32_t fixedPosZ; // cm
uint32_t fixedPosVar; // cm
- uint32_t flags; // currently 0
- uint32_t reserved; // currently 0
+ uint32_t flags; // currently 0
+ uint32_t reserved; // currently 0
+
} NAV_TIME_MODE_SETTINGS;
+
/**
* Navigation Engine settings to set configuration
* parameters of a dynamic platform model.
@@ -6983,9 +18772,2910 @@ typedef struct
uint32_t flags; // currently 0
uint32_t reserved; // currently 0
NAV_TIME_MODE_SETTINGS nav_time_mode_settings;
+
} NAV_ENGINE_SETTINGS;
+
+/**
+ * @defgroup group_led_api Meinberg TLV API definitions
+ *
+ * @note These structures and definitions are only supported by a device
+ * if ::MBG_XFEATURE_LED_API is set in the extended device features.
+ *
+ * @{ */
+
+
+/**
+ * @brief General LED info to be read from a device
+ *
+ * Used to query from a device how many LEDs are supported
+ * by the device, then index 0..::MBG_LED_LIMITS::num_leds-1
+ * ::MBG_LED_INFO_IDX or ::MBG_LED_SETTINGS_IDX structures
+ * can be read from or written to the device.
+ *
+ * @see ::MBG_LED_SETTINGS_IDX
+ * @see ::MBG_LED_INFO_IDX
+ */
+typedef struct
+{
+ uint8_t num_leds; ///< Number of supported LEDs, see ::MBG_LED_SETTINGS_IDX::idx and ::MBG_LED_INFO_IDX::idx
+ uint8_t reserved_0; ///< Currently reserved, unused, always 0
+ uint16_t reserved_1; ///< Currently reserved, unused, always 0
+ uint32_t reserved_2; ///< Currently reserved, unused, always 0
+
+} MBG_LED_LIMITS;
+
+#define _mbg_swab_mbg_led_limits( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->num_leds ); \
+ _mbg_swab8( &(_p)->reserved_0 ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Possible modes of LEDs
+ *
+ * Used with ::MBG_LED_SETTINGS::mode
+ *
+ * @see ::MBG_LED_MODE_MASKS
+ */
+enum MBG_LED_MODES
+{
+ MBG_LED_MODE_OFF,
+ MBG_LED_MODE_ON,
+ MBG_LED_MODE_FLASH,
+ MBG_LED_MODE_FLASH_5S,
+ N_MBG_LED_MODES
+};
+
+
+
+/**
+ * @brief Bit masks associated with LED modes
+ *
+ * Used with ::MBG_LED_INFO::supp_modes
+ *
+ * @see ::MBG_LED_MODES
+ */
+enum MBG_LED_MODE_MASKS
+{
+ MBG_LED_MODE_MASK_OFF = ( 1UL << MBG_LED_MODE_OFF ), ///< see ::MBG_LED_MODE_OFF
+ MBG_LED_MODE_MASK_ON = ( 1UL << MBG_LED_MODE_ON ), ///< see ::MBG_LED_MODE_ON
+ MBG_LED_MODE_MASK_FLASH = ( 1UL << MBG_LED_MODE_FLASH ), ///< see ::MBG_LED_MODE_FLASH
+ MBG_LED_MODE_MASK_FLASH_5S = ( 1UL << MBG_LED_MODE_FLASH_5S ) ///< see ::MBG_LED_MODE_FLASH_5S
+};
+
+
+/**
+ * @brief Names of LED modes
+ *
+ * Can be used to initialize a string array of ::N_MBG_LED_MODES entries,
+ * so the number of strings must correspond to ::N_MBG_LED_MODES.
+ *
+ * @see ::MBG_LED_MODES
+ * @see ::MBG_LED_MODE_MASKS
+ */
+#define MBG_LED_MODE_STRS \
+{ \
+ "Off", \
+ "On", \
+ "Flash", \
+ "Flash 5s" \
+}
+
+
+
+/**
+ * @brief Possible colors of LEDs
+ *
+ * Used with ::MBG_LED_SETTINGS::color
+ *
+ * @see ::MBG_LED_COLOR_MASKS
+ */
+enum MBG_LED_COLORS
+{
+ MBG_LED_COLOR_GREEN,
+ MBG_LED_COLOR_RED,
+ MBG_LED_COLOR_YELLOW,
+ MBG_LED_COLOR_BLUE,
+ N_MBG_LED_COLORS
+};
+
+
+
+/**
+ * @brief Bit masks of possible LED colors
+ *
+ * Used with ::MBG_LED_INFO::supp_colors
+ *
+ * @see ::MBG_LED_COLORS
+ */
+enum MBG_LED_COLOR_MASKS
+{
+ MBG_LED_COLOR_MASK_GREEN = ( 1UL << MBG_LED_COLOR_GREEN ), ///< see ::MBG_LED_COLOR_GREEN
+ MBG_LED_COLOR_MASK_RED = ( 1UL << MBG_LED_COLOR_RED ), ///< see ::MBG_LED_COLOR_RED
+ MBG_LED_COLOR_MASK_YELLOW = ( 1UL << MBG_LED_COLOR_YELLOW ), ///< see ::MBG_LED_COLOR_YELLOW
+ MBG_LED_COLOR_MASK_BLUE = ( 1UL << MBG_LED_COLOR_BLUE ) ///< see ::MBG_LED_COLOR_BLUE
+};
+
+
+
+/**
+ * @brief Names of LED colors
+ *
+ * Can be used to initialize a string array of ::N_MBG_LED_COLORS entries,
+ * so the number of strings must correspond to ::N_MBG_LED_COLORS.
+ *
+ * @see ::MBG_LED_COLORS
+ * @see ::MBG_LED_COLOR_MASKS
+ */
+#define MBG_LED_COLOR_STRS \
+{ \
+ "Green", \
+ "Red", \
+ "Yellow", \
+ "Blue" \
+}
+
+
+
+/**
+ * @brief Configuration settings for a single LED
+ *
+ * @see ::MBG_LED_SETTINGS_IDX
+ */
+typedef struct
+{
+ uint8_t mode; ///< LED mode, see ::MBG_LED_MODES
+ uint8_t color; ///< LED color, see ::MBG_LED_COLORS
+ uint16_t reserved; ///< Currently reserved, unused, always 0
+
+} MBG_LED_SETTINGS;
+
+#define _mbg_swab_mbg_led_settings( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->mode ); \
+ _mbg_swab8( &(_p)->color ); \
+ _mbg_swab16( &(_p)->reserved ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Configuration settings for a single LED, plus index
+ *
+ * @see ::MBG_LED_SETTINGS
+ * @see ::MBG_LED_LIMITS
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_LED_LIMITS::num_leds-1
+ MBG_LED_SETTINGS settings; ///< LED settings
+
+} MBG_LED_SETTINGS_IDX;
+
+#define _mbg_swab_mbg_led_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_mbg_led_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Current settings and general capabilities of an LED
+ *
+ * This structure should be read from the device to retrieve the
+ * current settings of an LED plus its capabilities, e.g. the
+ * supported modes, colors, etc.
+ *
+ * @see ::MBG_LED_INFO_IDX
+ */
+typedef struct
+{
+ MBG_LED_SETTINGS settings; ///< Current LED settings
+ uint32_t supp_modes; ///< Supported modes, see ::MBG_LED_MODE_MASKS
+ uint32_t supp_colors; ///< Supported colors, see ::MBG_LED_COLOR_MASKS
+ uint32_t reserved; ///< Currently reserved, unused, always 0
+ uint32_t flags; ///< Currently reserved, unused, always 0
+
+} MBG_LED_INFO;
+
+#define _mbg_swab_mbg_led_info( _p ) \
+do \
+{ \
+ _mbg_swab_mbg_led_settings( &(_p)->settings ); \
+ _mbg_swab32( &(_p)->supp_modes ); \
+ _mbg_swab32( &(_p)->supp_colors ); \
+ _mbg_swab32( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Current settings and general capabilities of an LED, plus index
+ *
+ * @see ::MBG_LED_INFO
+ * @see ::MBG_LED_LIMITS
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_LED_LIMITS::num_leds-1
+ MBG_LED_INFO info; ///< LED info
+
+} MBG_LED_INFO_IDX;
+
+#define _mbg_swab_mbg_led_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_mbg_led_info( &(_p)->info ); \
+} while ( 0 )
+
+/** @} defgroup group_led_api */
+
+
+
+/**
+ * @defgroup group_lne_api Definitions specific to LNE devices
+ *
+ * @note These structures and definitions are only supported by a device
+ * if ::MBG_XFEATURE_LNE_API is set in the extended device features.
+ *
+ * @{ */
+
+
+/**
+ * @brief General info to be read from an LNE device
+ *
+ * Used to query from a device e.g. how many LNE ports are provided
+ * by the device, then index 0..::MBG_LNE_LIMITS::num_ports-1
+ * ::MBG_LNE_PORT_INFO_IDX or ::MBG_LNE_PORT_SETTINGS_IDX structures
+ * can be read from or written to the device.
+ *
+ * @see ::MBG_LNE_PORT_SETTINGS_IDX
+ * @see ::MBG_LNE_PORT_INFO_IDX
+ */
+typedef struct
+{
+ uint8_t num_ports; ///< Number of supported ports, see ::MBG_LNE_PORT_SETTINGS_IDX::idx and ::MBG_LNE_PORT_INFO_IDX::idx
+ uint8_t reserved_0; ///< Currently reserved, unused, always 0
+ uint16_t reserved_1; ///< Currently reserved, unused, always 0
+ uint32_t features; // ### TODO Mask of supported features, see ::MBG_LNE_FEAT_MASKS
+ ///< Currently reserved, unused, always 0
+ uint32_t reserved_2; ///< Currently reserved, unused, always 0
+
+} MBG_LNE_LIMITS;
+
+#define _mbg_swab_mbg_lne_limits( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->num_ports ); \
+ _mbg_swab8( &(_p)->reserved_0 ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->features ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+} while ( 0 )
+
+
+
+#if 0 //### TODO //#################
+
+/**
+ * @brief LNE feature bits
+ *
+ * Used to define ::MBG_LNE_FEAT_MASKS
+ *
+ * @see ::MBG_LNE_FEAT_MASKS
+ */
+enum MBG_LNE_FEAT_BITS
+{
+ MBG_LNE_FEAT_BIT_SWITCH_PWR, ///< Power switching off all LNE ports at once supported, see ::MBG_LNE_PWR_STATE
+ N_MBG_LNE_FEAT_BITS
+};
+
+
+
+/**
+ * @brief LNE feature bit masks
+ *
+ * Used with ::MBG_LNE_LIMITS::features
+ *
+ * @see ::MBG_LNE_FEAT_BITS
+ */
+enum MBG_LNE_FEAT_MASKS
+{
+ MBG_LNE_FEAT_MASK_SWITCH_PWR = ( 1UL << MBG_LNE_FEAT_BIT_SWITCH_PWR ) ///< see ::MBG_LNE_FEAT_BIT_SWITCH_PWR
+};
+
+#endif
+
+
+
+/**
+ * @brief Configuration settings for a single LNE port
+ *
+ * @see ::MBG_LNE_PORT_SETTINGS_IDX
+ */
+typedef struct
+{
+ uint32_t reserved_0; ///< currently reserved, unused, always 0
+ uint32_t reserved_1; ///< currently reserved, unused, always 0
+ uint32_t reserved_2; ///< currently reserved, unused, always 0
+ uint32_t flags; ///< currently reserved, unused, always 0
+
+} MBG_LNE_PORT_SETTINGS;
+
+#define _mbg_swab_mbg_lne_port_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Configuration settings for a single LNE port, plus index
+ *
+ * @see ::MBG_LNE_PORT_SETTINGS
+ * @see ::MBG_LNE_LIMITS
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_LNE_LIMITS::num_ports-1
+ MBG_LNE_PORT_SETTINGS settings; ///< LNE settings
+
+} MBG_LNE_PORT_SETTINGS_IDX;
+
+#define _mbg_swab_mbg_lne_port_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_mbg_lne_port_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Current settings and general capabilities of an LNE port
+ *
+ * This structure should be read from the device to retrieve the
+ * current settings of an LNE port plus its capabilities, ### e.g. the
+ * supported modes, colors, etc.
+ *
+ * @see ::MBG_LNE_PORT_INFO_IDX
+ */
+typedef struct
+{
+ MBG_LNE_PORT_SETTINGS settings; ///< Current LNE port settings
+ MBG_MAC_ADDR mac_addr; ///< The MAC address assigned to this port
+ uint32_t reserved_0; ///< currently reserved, unused, always 0
+ uint32_t reserved_1; ///< currently reserved, unused, always 0
+ uint32_t reserved_2; ///< currently reserved, unused, always 0
+ uint32_t flags; ///< see ::LNE_PORT_FLAG_MASKS
+
+} MBG_LNE_PORT_INFO;
+
+#define _mbg_swab_mbg_lne_port_info( _p ) \
+do \
+{ \
+ _mbg_swab_mbg_lne_port_settings( &(_p)->settings ); \
+ _mbg_swab_mbg_mac_addr( &(_p)->mac_addr ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Current settings and general capabilities of an LNE port, plus index
+ *
+ * @see ::MBG_LNE_PORT_INFO
+ * @see ::MBG_LNE_LIMITS
+ */
+typedef struct
+{
+ uint16_t idx; ///< 0..::MBG_LED_LIMITS::num_leds-1
+ MBG_LNE_PORT_INFO info; ///< LNE port info
+
+} MBG_LNE_PORT_INFO_IDX;
+
+#define _mbg_swab_mbg_lne_port_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_mbg_lne_port_info( &(_p)->info ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief LNE port flag bits
+ *
+ * Used to define ::LNE_PORT_FLAG_MASKS
+ *
+ * @see ::LNE_PORT_FLAG_MASKS
+ */
+enum LNE_PORT_FLAG_BITS
+{
+ LNE_PORT_FLAG_BIT_IS_SFP,
+ N_LNE_PORT_FLAG_BITS
+};
+
+
+
+/**
+ * @brief LNE port flag bit masks
+ *
+ * Used with ::MBG_LNE_PORT_INFO::flags
+ *
+ * @see ::LNE_PORT_FLAG_BITS
+ */
+enum LNE_PORT_FLAG_MASKS
+{
+ LNE_PORT_FLAG_MASK_IS_SFP = ( 1UL << LNE_PORT_FLAG_BIT_IS_SFP ) ///< see ::LNE_PORT_FLAG_BIT_IS_SFP
+};
+
+
+/** @} defgroup group_lne_api */
+
+
+
+/**
+ * @defgroup group_pwr_ctl_api Definitions for power control API
+ *
+ * @note These structures and definitions are only supported by a device
+ * if ::MBG_XFEATURE_PWR_CTL_API is set in the extended device features.
+ *
+ * @{ */
+
+
+/**
+ * @brief Device power states
+ *
+ * Used with ::MBG_PWR_CTL::state.
+ */
+enum MBG_PWR_STATES
+{
+ MBG_PWR_STATE_OFF,
+ MBG_PWR_STATE_ON,
+ N_MBG_PWR_STATES
+};
+
+
+
+/**
+ * @brief Device power control
+ *
+ * Used to change or retrieve a device's power state
+ */
+typedef struct
+{
+ uint8_t state; ///< see ::MBG_PWR_STATES
+ uint8_t reserved_0; ///< Currently reserved, unused, always 0
+ uint16_t reserved_1; ///< Currently reserved, unused, always 0
+
+} MBG_PWR_CTL;
+
+#define _mbg_swab_mbg_pwr_ctl( _p ) \
+do \
+{ \
+ _mbg_swab8( &(_p)->state ); \
+ _mbg_swab8( &(_p)->reserved_0 ); \
+ _mbg_swab16( &(_p)->reserved_1 ); \
+} while ( 0 )
+
+/** @} defgroup group_pwr_ctl_api */
+
+
+
+
+/**
+ * @defgroup group_ext_sys_info Extended system information
+ *
+ * @note This structure and its definitions are only supported by a device
+ * if ::MBG_XFEATURE_EXT_SYS_INFO is set in the extended device features.
+ *
+ * @{ */
+
+
+/**
+ * @brief Bits used to define ::MBG_EXT_SYS_INFO_MSKS
+ *
+ * @see ::MBG_EXT_SYS_INFO_MSKS
+ */
+enum MBG_EXT_SYS_INFO_BITS
+{
+ MBG_EXT_SYS_INFO_BIT_SW_REV,
+ MBG_EXT_SYS_INFO_BIT_HW_REV,
+ MBG_EXT_SYS_INFO_BIT_OS_REV,
+ MBG_EXT_SYS_INFO_BIT_FPGA_REV,
+ MBG_EXT_SYS_INFO_BIT_CORE_MOD_REV,
+ N_MBG_EXT_SYS_INFO_BITS
+};
+
+
+
+/**
+ * @brief Bit masks of supported revision numbers
+ *
+ * Used with ::MBG_EXT_SYS_INFO::supp_members
+ *
+ * @see ::MBG_EXT_SYS_INFO_BITS
+ */
+enum MBG_EXT_SYS_INFO_MSKS
+{
+ MBG_EXT_SYS_INFO_MSK_SW_REV = ( 1UL << MBG_EXT_SYS_INFO_BIT_SW_REV ), ///< see ::MBG_EXT_SYS_INFO_BIT_SW_REV
+ MBG_EXT_SYS_INFO_MSK_HW_REV = ( 1UL << MBG_EXT_SYS_INFO_BIT_HW_REV ), ///< see ::MBG_EXT_SYS_INFO_BIT_HW_REV
+ MBG_EXT_SYS_INFO_MSK_OS_REV = ( 1UL << MBG_EXT_SYS_INFO_BIT_OS_REV ), ///< see ::MBG_EXT_SYS_INFO_BIT_OS_REV
+ MBG_EXT_SYS_INFO_MSK_FPGA_REV = ( 1UL << MBG_EXT_SYS_INFO_BIT_FPGA_REV ), ///< see ::MBG_EXT_SYS_INFO_BIT_FPGA_REV
+ MBG_EXT_SYS_INFO_MSK_CORE_MOD_REV = ( 1UL << MBG_EXT_SYS_INFO_BIT_CORE_MOD_REV ) ///< see ::MBG_EXT_SYS_INFO_BIT_CORE_MOD_REV
+};
+
+
+enum MBG_EXT_SYS_INFO_PROC_TYPES
+{
+ MBG_EXT_SYS_INFO_PROC_TYPE_NONE,
+ MBG_EXT_SYS_INFO_PROC_TYPE_CORTEX_A9,
+ MBG_EXT_SYS_INFO_PROC_TYPE_CORTEX_SAM3u,
+ MBG_EXT_SYS_INFO_PROC_TYPE_CORTEX_SAM3s,
+ MBG_EXT_SYS_INFO_PROC_TYPE_CORTEX_STM32F4,
+ N_MBG_EXT_SYS_INFO_PROC_TYPES
+};
+
+#define MBG_EXT_SYS_INFO_PROC_STRS \
+{ \
+ "None", \
+ "Cortex A9", \
+ "Cortex SAM3u", \
+ "Cortex SAM3s", \
+ "Cortex STM32F4" \
+}
+
+enum MBG_EXT_SYS_INFO_FPGA_TYPES
+{
+ MBG_EXT_SYS_INFO_FPGA_TYPE_NONE,
+ MBG_EXT_SYS_INFO_FPGA_TYPE_CYCLONE5_SOC, ///< System on chip
+ MBG_EXT_SYS_INFO_FPGA_TYPE_CYCLONE5, ///< Stand alone FPGA
+ MBG_EXT_SYS_INFO_FPGA_TYPE_CYCLONE4GX15,
+ MBG_EXT_SYS_INFO_FPGA_TYPE_CYLCONE4CE22,
+ N_MBG_EXT_SYS_INFO_FPGA_TYPES
+};
+
+#define MBG_EXT_SYS_INFO_FPGA_STRS \
+{ \
+ "None", \
+ "Cyclone5 SoC", \
+ "Cyclone5", \
+ "Cyclone4GX15", \
+ "Cyclone4CE22" \
+}
+
+enum MBG_EXT_SYS_INFO_CORE_MOD_TYPES
+{
+ MBG_EXT_SYS_INFO_CORE_MOD_TYPE_NONE,
+ MBG_EXT_SYS_INFO_CORE_MOD_TYPE_UBX_LEA_M8F, ///< u-blox GNSS module without Galileo support
+ MBG_EXT_SYS_INFO_CORE_MOD_TYPE_UBX_LEA_M8T, ///< u-blox GNSS module with Galileo support
+ N_MBG_EXT_SYS_INFO_CORE_MOD_TYPES
+};
+
+#define MBG_EXT_SYS_INFO_CORE_MOD_STRS \
+{ \
+ "None", \
+ "u-blox LEA-M8F", \
+ "u-blox LEA-M8T" \
+}
+
+typedef struct
+{
+ uint32_t supp_members; ///< ::MBG_EXT_SYS_INFO_MSKS
+
+ uint32_t sw_rev;
+ uint32_t hw_rev;
+ uint32_t os_rev;
+ uint32_t fpga_rev;
+
+ uint16_t proc_type; ///< See ::MBG_EXT_SYS_INFO_PROC_TYPES
+ uint16_t fpga_type; ///< See ::MBG_EXT_SYS_INFO_FPGA_TYPES
+ uint16_t core_mod_type; ///< See ::MBG_EXT_SYS_INFO_CORE_MOD_TYPES
+ uint16_t reserved;
+
+ uint32_t core_mod_rev;
+
+ /* Reserved for future use, currently 0 */
+ uint32_t reserved_rev_3;
+ uint32_t reserved_rev_4;
+ uint32_t reserved_rev_5;
+ uint32_t reserved_rev_6;
+ uint32_t reserved_rev_7;
+ uint32_t reserved_rev_8;
+ uint32_t reserved_rev_9;
+ uint32_t reserved_rev_10;
+ uint32_t reserved_rev_11;
+
+} MBG_EXT_SYS_INFO;
+
+#define _mbg_swab_ext_sys_info( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_members ); \
+ _mbg_swab32( &(_p)->sw_rev ); \
+ _mbg_swab32( &(_p)->hw_rev ); \
+ _mbg_swab32( &(_p)->os_rev ); \
+ _mbg_swab32( &(_p)->fpga_rev ); \
+ _mbg_swab16( &(_p)->proc_type ); \
+ _mbg_swab16( &(_p)->fpga_type ); \
+ _mbg_swab16( &(_p)->core_mod_type ); \
+ _mbg_swab16( &(_p)->reserved ); \
+ _mbg_swab32( &(_p)->core_mod_rev ); \
+} while ( 0 )
+
+
+#define _mbg_encode_revision( _major, _minor, _patch ) \
+ ( ( (_major) << 24) | ( (_minor) << 16 ) | (_patch) )
+
+
+#define _mbg_decode_revision( _rev, _major, _minor, _patch ) \
+{ \
+ (_major) = ( (_rev) >> 24 ) & 0xff; \
+ (_minor) = ( (_rev) >> 16 ) & 0xff; \
+ (_patch) = (_rev) & 0xffff; \
+}
+
+
+/** @} defgroup group_ext_sys_info */
+
+
+/**
+ * @defgroup group_license_limits License information
+ *
+ * @note This structure and its definitions are only supported by a device
+ * if ::MBG_XFEATURE_LICENSE_LIMITS is set in the extended device features.
+ *
+ * @{ */
+
+
+#define MBG_MAX_LICENSES 32
+
+
+/**
+ * @brief General license information to be read from a device
+ *
+ * Used to query from a device how many and which different license types
+ * are supported. If a special type is supported (licenses[MBG_LICENSE_BASE_TYPES] > 0), its
+ * license specific information can be queried from 0..licenses[MBG_LICENSE_BASE_TYPES]-1 via
+ * its license specific [...]_IDX structures and TLV API command codes.
+ * See ::MBG_XFEATURE_TLV_API and ::MBG_TLV_FEAT_TYPES.
+ */
+typedef struct
+{
+ uint8_t licenses[MBG_MAX_LICENSES]; ///< To get the number of supported licenses
+ ///< of a specific type you need to access the array
+ ///< with the specififc license index defined at ::MBG_LICENSE_BASE_TYPES.
+} MBG_LICENSE_LIMITS;
+
+
+enum MBG_LICENSE_BASE_TYPES
+{
+ MBG_LICENSE_BASE_TYPE_PTPV2,
+ MBG_LICENSE_BASE_TYPE_NTP,
+ MBG_LICENSE_BASE_TYPE_PTPV1,
+ MBG_LICENSE_BASE_TYPE_TIME_MONITOR,
+ N_MBG_LICENSE_BASE_TYPES
+};
+
+
+/**
+ * @brief Bits used to define ::MBG_LICENSE_BASE_MSKS
+ *
+ * @see ::MBG_LICENSE_BASE_MSKS
+ */
+enum MBG_LICENSE_BASE_FLAGS
+{
+ MBG_LICENSE_BASE_FLAG_SUPP_UPGRADE, ///< License supports upgrading / modifying
+ N_MBG_LICENSE_BASE_FLAGS
+};
+
+
+/**
+ * @brief Bit masks of common supported base license flags
+ *
+ * Used with ::MBG_LICENSE_BASE::supp_flags
+ *
+ * @see ::MBG_LICENSE_BASE_FLAGS
+ */
+enum MBG_LICENSE_BASE_MSKS
+{
+ MBG_LICENSE_BASE_MSK_SUPP_UPGRADE = ( 1UL << MBG_LICENSE_BASE_FLAG_SUPP_UPGRADE ) ///< See ::MBG_LICENSE_BASE_FLAG_SUPP_UPGRADE
+};
+
+
+/**
+ * @brief Common license information
+ *
+ * Should be part of each individual license type.
+ */
+typedef struct
+{
+ uint8_t type; ///< See ::MBG_LICENSE_BASE_TYPES
+ uint8_t reserved_1; ///< Reserved for future use, currently 0
+ uint16_t reserved_2; ///< Reserved for future use, currently 0
+ uint32_t supp_flags; ///< See ::MBG_LICENSE_BASE_MSKS
+ uint32_t reserved_3; ///< Reserved for future use, currently 0
+ uint32_t reserved_4; ///< Reserved for future use, currently 0
+
+} MBG_LICENSE_BASE;
+
+#define _mbg_swab_license_base( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_flags ); \
+} while ( 0 )
+
+
+/**
+ * @brief Bits used to define ::MBG_LICENSE_PTPV2_MEMBER_MSKS
+ *
+ * @see ::MBG_LICENSE_PTPV2_MEMBER_MSKS
+ */
+enum MBG_LICENSE_PTPV2_MEMBERS
+{
+ MBG_LICENSE_PTPV2_MEMBER_MAX_UCLIENTS,
+ MBG_LICENSE_PTPV2_MEMBER_MAX_MTRANS,
+ N_MBG_LICENSE_PTPV2_MEMBERS
+};
+
+
+/**
+ * @brief Bit masks of PTPV2 license specific members
+ *
+ * Used with ::MBG_LICENSE_PTPV2::supp_members
+ *
+ * @see ::MBG_LICENSE_PTPV2_MEMBERS
+ */
+enum MBG_LICENSE_PTPV2_MEMBER_MSKS
+{
+ MBG_LICENSE_PTPV2_MEMBER_MSK_MAX_UCLIENTS = ( 1UL << MBG_LICENSE_PTPV2_MEMBER_MAX_UCLIENTS ), ///< See ::MBG_LICENSE_PTPV2_MEMBER_MAX_UCLIENTS
+ MBG_LICENSE_PTPV2_MEMBER_MSK_MAX_MTRANS = ( 1UL << MBG_LICENSE_PTPV2_MEMBER_MAX_MTRANS ) ///< See ::MBG_LICENSE_PTPV2_MEMBER_MAX_MTRANS
+};
+
+
+/**
+ * @brief PTPV2 specific license information
+ *
+ */
+typedef struct
+{
+ MBG_LICENSE_BASE base; ///< See ::MBG_LICENSE_BASE
+ uint32_t supp_members; ///< See ::MBG_LICENSE_PTPV2_MEMBER_MSKS
+ uint32_t reserved_1; ///< Reserved for future use, currently 0
+ uint16_t max_uclients; ///< Maximal number of supported unicast clients.
+ uint16_t reserved_2; ///< Reserved for future use, currently 0
+ uint32_t max_mtrans; ///< Maximal number of supported multicast transactions per second.
+ uint32_t reserved_3; ///< Reserved for future use, currently 0
+ uint32_t reserved_4; ///< Reserved for future use, currently 0
+ uint32_t reserved_5; ///< Reserved for future use, currently 0
+ uint32_t reserved_6; ///< Reserved for future use, currently 0
+
+} MBG_LICENSE_PTPV2;
+
+#define _mbg_swab_license_ptpv2( _p ) \
+do \
+{ \
+ _mbg_swab_license_base( &(_p)->base ); \
+ _mbg_swab32( &(_p)->supp_members ); \
+ _mbg_swab16( &(_p)->max_uclients ); \
+ _mbg_swab32( &(_p)->max_mtrans ); \
+} while ( 0 )
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_LICENSE_PTPV2 license;
+
+} MBG_LICENSE_PTPV2_IDX;
+
+#define _mbg_swab_license_ptpv2_idx( _p ) \
+do \
+{ \
+ _mbg_swab_license_ptpv2( &(_p)->license ); \
+ _mbg_swab32( &(_p)->idx ); \
+} while ( 0 )
+
+
+/**
+ * @brief Bits used to define ::MBG_LICENSE_NTP_MEMBER_MSKS
+ *
+ * @see ::MBG_LICENSE_NTP_MEMBER_MSKS
+ */
+enum MBG_LICENSE_NTP_MEMBERS
+{
+ MBG_LICENSE_NTP_MEMBER_MAX_RPS,
+ N_MBG_LICENSE_NTP_MEMBERS
+};
+
+
+/**
+ * @brief Bit masks of NTP license specific members
+ *
+ * Used with ::MBG_LICENSE_NTP::supp_members
+ *
+ * @see ::MBG_LICENSE_PTPV2_MEMBERS
+ */
+enum MBG_LICENSE_NTP_MEMBER_MSKS
+{
+ MBG_LICENSE_NTP_MEMBER_MSK_MAX_RPS = ( 1UL << MBG_LICENSE_NTP_MEMBER_MAX_RPS ) ///< See ::MBG_LICENSE_NTP_MEMBER_MAX_RPS
+};
+
+
+/**
+ * @brief NTP specific license information
+ */
+typedef struct
+{
+ MBG_LICENSE_BASE base; ///< See ::MBG_LICENSE_BASE
+ uint32_t supp_members; ///< See ::MBG_LICENSE_NTP_MEMBER_MSKS
+ uint32_t max_rps; ///< Maximum number of supported NTP requests per second
+ uint32_t reserved_1; ///< Reserved for future use, currently 0
+ uint32_t reserved_2; ///< Reserved for future use, currently 0
+ uint32_t reserved_3; ///< Reserved for future use, currently 0
+ uint32_t reserved_4; ///< Reserved for future use, currently 0
+ uint32_t reserved_5; ///< Reserved for future use, currently 0
+ uint32_t reserved_6; ///< Reserved for future use, currently 0
+
+} MBG_LICENSE_NTP;
+
+#define _mbg_swab_license_ntp( _p ) \
+do \
+{ \
+ _mbg_swab_license_base( &(_p)->base ); \
+ _mbg_swab32( &(_p)->supp_members ); \
+ _mbg_swab32( &(_p)->max_rps ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_LICENSE_NTP license;
+
+} MBG_LICENSE_NTP_IDX;
+
+#define _mbg_swab_license_ntp_idx( _p ) \
+do \
+{ \
+ _mbg_swab_license_ntp( &(_p)->license ); \
+ _mbg_swab32( &(_p)->idx ); \
+} while ( 0 )
+
+/**
+ * @brief Bits used to define ::MBG_LICENSE_PTPV1_MEMBER_MSKS
+ *
+ * @see ::MBG_LICENSE_PTPV1_MEMBER_MSKS
+ */
+enum MBG_LICENSE_PTPV1_MEMBERS
+{
+ MBG_LICENSE_PTPV1_MEMBER_MAX_RPS,
+ N_MBG_LICENSE_PTPV1_MEMBERS
+};
+
+
+/**
+ * @brief Bit masks of PTPV1 license specific members
+ *
+ * Used with ::MBG_LICENSE_PTPV1::supp_members
+ *
+ * @see ::MBG_LICENSE_PTPV2_MEMBERS
+ */
+enum MBG_LICENSE_PTPV1_MEMBER_MSKS
+{
+ MBG_LICENSE_PTPV1_MEMBER_MSK_MAX_RPS = ( 1UL << MBG_LICENSE_PTPV1_MEMBER_MAX_RPS ) ///< See ::MBG_LICENSE_PTPV1_MEMBER_MAX_RPS
+};
+
+
+/**
+ * @brief NTP specific license information
+ */
+typedef struct
+{
+ MBG_LICENSE_BASE base; ///< See ::MBG_LICENSE_BASE
+ uint32_t supp_members; ///< See ::MBG_LICENSE_PTPV1_MEMBER_MSKS
+ uint32_t max_rps; ///< Maximum number of supported PTPv1 delay requests per second
+ uint32_t reserved_1; ///< Reserved for future use, currently 0
+ uint32_t reserved_2; ///< Reserved for future use, currently 0
+ uint32_t reserved_3; ///< Reserved for future use, currently 0
+ uint32_t reserved_4; ///< Reserved for future use, currently 0
+ uint32_t reserved_5; ///< Reserved for future use, currently 0
+ uint32_t reserved_6; ///< Reserved for future use, currently 0
+
+} MBG_LICENSE_PTPV1;
+
+#define _mbg_swab_license_ptpv1( _p ) \
+do \
+{ \
+ _mbg_swab_license_base( &(_p)->base ); \
+ _mbg_swab32( &(_p)->supp_members ); \
+ _mbg_swab32( &(_p)->max_rps ); \
+} while ( 0 )
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_LICENSE_PTPV1 license;
+
+} MBG_LICENSE_PTPV1_IDX;
+
+#define _mbg_swab_license_ptpv1_idx( _p ) \
+do \
+{ \
+ _mbg_swab_license_ptpv1( &(_p)->license ); \
+ _mbg_swab32( &(_p)->idx ); \
+} while ( 0 )
+
+/**
+ * @brief Bits used to define ::MBG_LICENSE_TIME_MONITOR_MEMBER_MSKS
+ *
+ * @see ::MBG_LICENSE_TIME:MONITOR_MEMBER_MSKS
+ */
+enum MBG_LICENSE_TIME_MONITOR_MEMBERS
+{
+ MBG_LICENSE_TIME_MONITOR_MEMBER_MAX_PTPV2_CLIENTS,
+ MBG_LICENSE_TIME_MONITOR_MEMBER_MAX_NTP_CLIENTS,
+ N_MBG_LICENSE_TIME_MONITOR_MEMBERS
+};
+
+
+/**
+ * @brief Bit masks of Time Monitor license specific members
+ *
+ * Used with ::MBG_LICENSE_TIME_MONITOR::supp_members
+ *
+ * @see ::MBG_LICENSE_TIME_MONITOR_MEMBERS
+ */
+enum MBG_LICENSE_TIME_MONITOR_MEMBER_MSKS
+{
+ MBG_LICENSE_TIME_MONITOR_MEMBER_MSK_MAX_PTPV2_CLIENTS = ( 1UL << MBG_LICENSE_TIME_MONITOR_MEMBER_MAX_PTPV2_CLIENTS ), ///< See ::MBG_LICENSE_TIME_MONITOR_MEMBER_MAX_PTPV2_CLIENTS
+ MBG_LICENSE_TIME_MONITOR_MEMBER_MSK_MAX_NTP_CLIENTS = ( 1UL << MBG_LICENSE_TIME_MONITOR_MEMBER_MAX_NTP_CLIENTS ) ///< See ::MBG_LICENSE_TIME_MONITOR_MEMBER_MAX_NTP_CLIENTS
+};
+
+
+/**
+ * @brief Time Monitor specific license information
+ *
+ */
+typedef struct
+{
+ MBG_LICENSE_BASE base; ///< See ::MBG_LICENSE_BASE
+ uint32_t supp_members; ///< See ::MBG_LICENSE_TIME_MONITOR_MEMBER_MSKS
+ uint32_t reserved_1; ///< Reserved for future use, currently 0
+ uint16_t max_ptpv2_clients; ///< Maximum number of supported PTPv2 clients to be monitored
+ uint16_t max_ntp_clients; ///< Maximum number of supported NTP clients to be monitored
+ uint32_t reserved_2; ///< Reserved for future use, currently 0
+ uint32_t reserved_3; ///< Reserved for future use, currently 0
+ uint32_t reserved_4; ///< Reserved for future use, currently 0
+ uint32_t reserved_5; ///< Reserved for future use, currently 0
+ uint32_t reserved_6; ///< Reserved for future use, currently 0
+
+} MBG_LICENSE_TIME_MONITOR;
+
+#define _mbg_swab_license_time_monitor( _p ) \
+do \
+{ \
+ _mbg_swab_license_base( &(_p)->base ); \
+ _mbg_swab32( &(_p)->supp_members ); \
+ _mbg_swab16( &(_p)->max_ptpv2_clients ); \
+ _mbg_swab16( &(_p)->max_ntp_clients ); \
+} while ( 0 )
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_LICENSE_TIME_MONITOR license;
+
+} MBG_LICENSE_TIME_MONITOR_IDX;
+
+#define _mbg_swab_license_time_monitor_idx( _p ) \
+do \
+{ \
+ _mbg_swab_license_time_monitor( &(_p)->license ); \
+ _mbg_swab32( &(_p)->idx ); \
+} while ( 0 )
+
+/** @} defgroup group_license_limits */
+
+
+
+/**
+ * @defgroup group_clk_res_info Clock resolution info
+ *
+ * @note This structure and its definitions are only supported by a device
+ * if ::MBG_XFEATURE_CLK_RES_INFO is set in the extended device features.
+ *
+ * @{ */
+
+/**
+ * @brief Clock resolution information
+ *
+ * @see @ref group_clk_res_info
+ */
+typedef struct
+{
+ uint32_t base_clk; ///< Base clock of the internal time base [MHz]
+ uint32_t num_clk_phase; ///< Number of multi-phase clock signals
+ uint32_t reserved_9;
+ uint32_t reserved_8;
+ uint32_t reserved_7;
+ uint32_t reserved_6;
+ uint32_t reserved_5;
+ uint32_t reserved_4;
+ uint32_t reserved_3;
+ uint32_t reserved_2;
+ uint32_t reserved_1;
+ uint32_t reserved_0;
+
+} MBG_CLK_RES_INFO;
+
+#define _mbg_swab_mbg_clk_res_info( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->base_clk ); \
+ _mbg_swab32( &(_p)->num_clk_phase ); \
+ _mbg_swab32( &(_p)->reserved_9 ); \
+ _mbg_swab32( &(_p)->reserved_8 ); \
+ _mbg_swab32( &(_p)->reserved_7 ); \
+ _mbg_swab32( &(_p)->reserved_6 ); \
+ _mbg_swab32( &(_p)->reserved_5 ); \
+ _mbg_swab32( &(_p)->reserved_4 ); \
+ _mbg_swab32( &(_p)->reserved_3 ); \
+ _mbg_swab32( &(_p)->reserved_2 ); \
+ _mbg_swab32( &(_p)->reserved_1 ); \
+ _mbg_swab32( &(_p)->reserved_0 ); \
+} while ( 0 )
+
+/** @} defgroup group_clk_res_info */
+
+
+
+/**
+ * @brief Type of upcoming transaction sequence
+ *
+ * Used in combination with ::GPS_BEGIN_TRANSACTION and ::GPS_END_TRANSACTION
+ * to announce which type of transaction is going to be started. Thus the receiver
+ * can prepare for following actions.
+ */
+enum MBG_TRANSACTION_TYPES
+{
+ MBG_TRANSACTION_TYPE_NONE,
+ /* ### TODO FIXME
+ * Network transaction requires at least and as first command:
+ * - ::GPS_NET_GLB_CFG (::MBG_NET_GLB_CFG_INFO)
+ * Depending on ::MBG_NET_GLB_CFG_INFO::glb_settings and its num_[...]
+ * members there are a couple of index commands which should be handled in any order:
+ * - ::GPS_NET_DNS_SRVR (::MBG_IP_ADDR_IDX)
+ * - ::GPS_NET_DNS_SRCH_DOM (::MBG_NET_NAME_IDX)
+ * - ::GPS_NET_INTF_LINK_IDX (::MBG_NET_INTF_LINK_INFO_IDX)
+ * - ::GPS_NET_INTF_ADDR_IDX (::MBG_NET_INTF_ADDR_INFO_IDX)
+ * - ::GPS_NET_INTF_ROUTE_IDX (::MBG_NET_INTF_ROUTE_INFO_IDX)
+ */
+ MBG_TRANSACTION_TYPE_NETWORK,
+ MBG_TRANSACTION_TYPE_PTP,
+ /*
+ * Commands in any order if supp. by ::MBG_SNMP_GLB_INFO::max_[...]
+ * and ::MBG_SNMP_GLB_INFO::supp_versions
+ *
+ * Should be used within ::MBG_TRANSACTION_TYPE_MONITORING but may also be
+ * used stand-alone.
+ *
+ * - ::GPS_SNMP_GLB_SETTINGS
+ * - ::GPS_SNMP_V12_SETTINGS_IDX
+ * - ::GPS_SNMP_V12_TRAP_SETTINGS_IDX
+ * - ::GPS_SNMP_V3_SETTINGS_IDX
+ * - ::GPS_SNMP_V3_TRAP_SETTINGS_IDX
+ */
+ MBG_TRANSACTION_TYPE_MONITORING_SNMP,
+ /*
+ * NTP transaction requires at least and as first command:
+ * ::GPS_NTP_GLB_CFG
+ * Commands in any order if supp. by ::MBG_NTP_GLB_INFO
+ * and ::MBG_SNMP_GLB_INFO::supp_versions
+ *
+ * - ::GPS_NTP_REFCLK_CFG
+ * - ::GPS_NTP_MISC_LIMITS
+ * - ::GPS_NTP_MISC_ORPHAN_MODE
+ * - ::GPS_NTP_SYMM_KEY_LIMITS
+ * - ::GPS_NTP_SYMM_KEY_CFG
+ * - ::GPS_NTP_TRUSTED_KEY_CFG
+ * - ::GPS_NTP_CLNT_MODE_CFG
+ * - ::GPS_NTP_SRV_MODE_CFG
+ * - ::GPS_NTP_PEER_SETTINGS_IDX
+ * - ::GPS_NTP_SYS_STATE
+ * - ::GPS_NTP_PEER_STATE_IDX
+ */
+ MBG_TRANSACTION_TYPE_NTP,
+ /*
+ * IO Port transaction used to read or write ALL_IO_PORT_INFO
+ * Commands related to this transaction:
+ *
+ * - ::GPS_IO_PORT_LIMITS
+ * - ::GPS_IO_PORT_SETTINGS_IDX
+ * - ::GPS_IO_PORT_INFO_IDX
+ * - ::GPS_IO_PORT_TYPE_INFO_IDX
+ * - ::GPS_IO_PORT_STATUS_IDX
+ */
+ MBG_TRANSACTION_TYPE_IO_PORT,
+ /*
+ * Commands in any order if ::MBG_XFEATURE_MONITORING is set in
+ * ::MBG_XFEATURE_BUFFER.
+ *
+ * Transactions ::MBG_TRANSACTION_TYPE_MONITORING_SNMP and
+ * ::MBG_TRANSACTION_TYPE_EVENTS may also be opened within
+ * ::MBG_TRANSACTION_TYPE_MONITORING transaction.
+ *
+ * - ::GPS_MONITORING_LIMITS
+ * - ::GPS_MONITORING_STATUS
+ */
+ MBG_TRANSACTION_TYPE_MONITORING,
+ /*
+ * Commands in any order if ::MBG_XFEATURE_MONITORING is set in
+ * ::MBG_XFEATURE_BUFFER.
+ *
+ * Should be used within ::MBG_TRANSACTION_TYPE_MONITORING but may also be
+ * used stand-alone.
+ *
+ * - ::GPS_EVENT_IDX
+ * - ::GPS_EVENT_STAT_IDX
+ */
+ MBG_TRANSACTION_TYPE_EVENTS,
+
+ MAX_MBG_TRANSACTION_TYPES
+};
+
+
+#define MBG_TRANSACTION_MSK_SET 0x8000
+#define _mbg_is_set_transaction( _type ) ( ( _type ) & MBG_TRANSACTION_MSK_SET )
+#define _mbg_transaction_type_set( _type ) ( ( _type ) |= MBG_TRANSACTION_MSK_SET )
+
+
+/**
+ * @defgroup group_io_ports IO Port API
+ *
+ * @note This structure and its definitions are only supported by a device
+ * if ::MBG_XFEATURE_IO_PORTS is set in the extended device features.
+ *
+ * @{ */
+
+/**
+ * @brief Port types
+ *
+ * Used with ::MBG_IO_PORT_TYPE_INFO::type and
+ * :: MBG_IO_PORT_SETTINGS::type
+ */
+enum MBG_IO_PORT_TYPES
+{
+ MBG_IO_PORT_TYPE_NONE = -1, ///< Only use this for ::MBG_IO_PORT_SETTINGS::type if ::MBG_IO_PORT_SETTINGS::op_mode is ::MBG_IO_PORT_OP_MODE_NONE
+ MBG_IO_PORT_TYPE_PPS,
+ MBG_IO_PORT_TYPE_10MHz,
+ MBG_IO_PORT_TYPE_2048KHz,
+ MBG_IO_PORT_TYPE_GPIO,
+ MBG_IO_PORT_TYPE_ETHERNET,
+ MBG_IO_PORT_TYPE_TERMINAL,
+ MBG_IO_PORT_TYPE_MULTI,
+ MBG_IO_PORT_TYPE_POUT,
+ N_MBG_IO_PORT_TYPES
+};
+
+
+/**
+ * @brief Strings descriptions for ::MBG_IO_PORT_TYPES
+ *
+ * Can be used to initialize a string array of ::N_MBG_IO_PORT_TYPES entries,
+ * so the number of strings must correspond to ::N_MBG_IO_PORT_TYPES.
+ *
+ * @see ::MBG_IO_PORT_TYPES
+ */
+#define MBG_IO_PORT_TYPE_STRS \
+{ \
+ "PPS", \
+ "10 MHz", \
+ "2048 KHz", \
+ "GPIO", \
+ "Ethernet", \
+ "Terminal", \
+ "Multi", \
+ "Prog. Output" \
+}
+
+
+/**
+ * @brief Port directions (input or output)
+ *
+ * @see ::MBG_IO_PORT_DIR_MSKS
+ */
+enum MBG_IO_PORT_DIRS
+{
+ MBG_IO_PORT_DIR_NONE = -1, ///< Only use this for ::MBG_IO_PORT_SETTINGS::direction if ::MBG_IO_PORT_SETTINGS::op_mode is ::MBG_IO_PORT_OP_MODE_NONE
+ MBG_IO_PORT_DIR_IN, ///< Port is input like PPS In
+ MBG_IO_PORT_DIR_OUT, ///< Port is output like 10Mhz
+ MBG_IO_PORT_DIR_IN_OUT, ///< Port can be in- & output in parallel like network port
+ N_MBG_IO_PORT_DIRS
+};
+
+
+/**
+ * @brief Strings descriptions for ::MBG_IO_PORT_DIRS
+ *
+ * Can be used to initialize a string array of ::N_MBG_IO_PORT_DIRS entries,
+ * so the number of strings must correspond to ::N_MBG_IO_PORT_DIRS.
+ *
+ * @see ::MBG_IO_PORT_DIRS
+ */
+#define MBG_IO_PORT_DIR_STRS \
+{ \
+ "Input", \
+ "Output", \
+ "Input/Output" \
+}
+
+
+/**
+ * @brief Bit masks of Meinberg I/O port directions
+ *
+ * Used with ::MBG_IO_PORT_TYPE_INFO::supp_dirs
+ *
+ * @see ::MBG_IO_PORT_DIRS
+ */
+enum MBG_IO_PORT_DIR_MSKS
+{
+ MBG_IO_PORT_MSK_DIR_IN = ( 1UL << MBG_IO_PORT_DIR_IN ), ///< See ::MBG_IO_PORT_DIR_IN
+ MBG_IO_PORT_MSK_DIR_OUT = ( 1UL << MBG_IO_PORT_DIR_OUT ), ///< See ::MBG_IO_PORT_DIR_OUT
+ MBG_IO_PORT_MSK_DIR_IN_OUT = ( 1UL << MBG_IO_PORT_DIR_IN_OUT ) ///< See ::MBG_IO_PORT_DIR_IN_OUT
+};
+
+
+/**
+ * @brief Port type sources
+ *
+ * Configurable sources for an I/O port type
+ *
+ * @see ::MBG_IO_PORT_SRC_MSKS
+ */
+enum MBG_IO_PORT_SRCS
+{
+ MBG_IO_PORT_SRC_NONE = -1, ///< Only use this for ::MBG_IO_PORT_SETTINGS::source if ::MBG_IO_PORT_SETTINGS::op_mode is ::MBG_IO_PORT_OP_MODE_NONE
+ MBG_IO_PORT_SRC_STATIC, ///< Static, not configurable
+ MBG_IO_PORT_SRC_LOCAL, ///< Locally generated, e.g. on (carrier) board
+ MBG_IO_PORT_SRC_ASSOC_CLOCK, ///< Fixed (wired) clock from back plane (e.g. refclock 1 in M500 IMS)
+ MBG_IO_PORT_SRC_ACTIVE_CLOCK, ///< Switched clock from back plane (e.g. selected by RSC)
+ MBG_IO_PORT_SRC_CLK1, ///< Clock 1 fixed (CPU board only)
+ MBG_IO_PORT_SRC_CLK2, ///< Clock 2 fixed (CPU board only)
+ MBG_IO_PORT_SRC_ARC, ///< Any rate converter
+ MBG_IO_PORT_SRC_OSC, ///< Oscillator
+ MBG_IO_PORT_SRC_SYNCE, ///< SyncE
+ N_MBG_IO_PORT_SRCS
+};
+
+
+/**
+ * @brief Strings descriptions for ::MBG_IO_PORT_SRCS
+ *
+ * Can be used to initialize a string array of ::N_MBG_IO_PORT_SRCS entries,
+ * so the number of strings must correspond to ::N_MBG_IO_PORT_SRCS.
+ *
+ * @see ::MBG_IO_PORT_SRCS
+ */
+#define MBG_IO_PORT_SRC_STRS \
+{ \
+ "Static", \
+ "Locally generated", \
+ "Associated clock", \
+ "Active clock", \
+ "Clock 1 fixed", \
+ "Clock 2 fixed", \
+ "Any rate converter", \
+ "Oscillator", \
+ "SyncE" \
+}
+
+
+/**
+ * @brief Bit masks of Meinberg I/O port attitudes
+ *
+ * Used with ::MBG_IO_PORT_TYPE_INFO::supp_srcs
+ *
+ * @see ::MBG_IO_PORT_SRCS
+ */
+enum MBG_IO_PORT_SRC_MSKS
+{
+ MBG_IO_PORT_SRC_MSK_STATIC = (1UL << MBG_IO_PORT_SRC_STATIC), ///< See ::MBG_IO_PORT_SRC_STATIC
+ MBG_IO_PORT_SRC_MSK_LOCAL = (1UL << MBG_IO_PORT_SRC_LOCAL), ///< See ::MBG_IO_PORT_SRC_LOCAL
+ MBG_IO_PORT_SRC_MSK_ASSOC_CLOCK = (1UL << MBG_IO_PORT_SRC_ASSOC_CLOCK), ///< See ::MBG_IO_PORT_SRC_ASSOC_CLOCK
+ MBG_IO_PORT_SRC_MSK_ACTIVE_CLOCK = (1UL << MBG_IO_PORT_SRC_ACTIVE_CLOCK), ///< See ::MBG_IO_PORT_SRC_ACTIVE_CLOCK
+ MBG_IO_PORT_SRC_MSK_CLK1 = (1UL << MBG_IO_PORT_SRC_CLK1), ///< See ::MBG_IO_PORT_SRC_CLK1
+ MBG_IO_PORT_SRC_MSK_CLK2 = (1UL << MBG_IO_PORT_SRC_CLK2), ///< See ::MBG_IO_PORT_SRC_CLK2
+ MBG_IO_PORT_SRC_MSK_ARC = (1UL << MBG_IO_PORT_SRC_ARC), ///< See ::MBG_IO_PORT_SRC_ARC
+ MBG_IO_PORT_SRC_MSK_OSC = (1UL << MBG_IO_PORT_SRC_OSC), ///< See ::MBG_IO_PORT_SRC_OSC
+ MBG_IO_PORT_SRC_MSK_SYNCE = (1UL << MBG_IO_PORT_SRC_SYNCE) ///< See ::MBG_IO_PORT_SRC_SYNCE
+};
+
+
+/**
+ * @brief Port connector types
+ *
+ * Used with ::MBG_IO_PORT_TYPE_INFO::conn_type
+ *
+ */
+enum MBG_IO_PORT_CONN_TYPES
+{
+ MBG_IO_PORT_CONN_TYPE_SMA,
+ MBG_IO_PORT_CONN_TYPE_BNC,
+ MBG_IO_PORT_CONN_TYPE_DSUB25,
+ MBG_IO_PORT_CONN_TYPE_RJ45,
+ MBG_IO_PORT_CONN_TYPE_SFP,
+ MBG_IO_PORT_CONN_TYPE_USB_MICRO_B,
+ MBG_IO_PORT_CONN_TYPE_USB_A,
+ MBG_IO_PORT_CONN_TYPE_USB_B,
+ MBG_IO_PORT_CONN_TYPE_SMA_ANT,
+ MBG_IO_PORT_CONN_TYPE_RJ45_ETH,
+ MBG_IO_PORT_CONN_TYPE_2_PIN_DFK,
+ MBG_IO_PORT_CONN_TYPE_3_PIN_DFK,
+ MBG_IO_PORT_CONN_TYPE_16_PIN_DFK,
+ MBG_IO_PORT_CONN_TYPE_BNC_ISO,
+ MBG_IO_PORT_CONN_TYPE_DSUB9,
+ MBG_IO_PORT_CONN_TYPE_FIBRE_ST,
+ MBG_IO_PORT_CONN_TYPE_XHE_SPI,
+ N_MBG_IO_PORT_CONN_TYPES
+};
+
+
+/**
+ * @brief Strings descriptions for ::MBG_IO_PORT_CONN_TYPES
+ *
+ * Can be used to initialize a string array of ::N_MBG_IO_PORT_CONN_TYPES entries,
+ * so the number of strings must correspond to ::N_MBG_IO_PORT_CONN_TYPES.
+ *
+ * @see ::MBG_IO_PORT_CONN_TYPES
+ */
+#define MBG_IO_PORT_CONN_TYPE_STRS \
+{ \
+ "SMA", \
+ "BNC", \
+ "D-Sub 25", \
+ "RJ45", \
+ "SFP", \
+ "USB Micro B", \
+ "USB A", \
+ "USB B", \
+ "SMA Antenna", \
+ "RJ45 Ethernet", \
+ "DFK 2-Pin", \
+ "DFK 3-Pin", \
+ "DFK 16-Pin", \
+ "BNC isolated", \
+ "D-Sub 9", \
+ "Fibre ST", \
+ "XHE SPI" \
+}
+
+
+/**
+ * @brief Position of a port on a card
+ *
+ * Used with ::MBG_IO_PORT_INFO::position
+ *
+ */
+enum MBG_IO_PORT_POS
+{
+ MBG_IO_PORT_POS_FRONT_COL_1, ///> Connector column 1, front
+ MBG_IO_PORT_POS_REAR_COL_1, ///> Connector column 1, rear
+ MBG_IO_PORT_POS_FRONT_COL_2, ///> Connector column 2, front
+ MBG_IO_PORT_POS_REAR_COL_2, ///> Connector column 2, rear
+ MBG_IO_PORT_POS_FRONT_COL_3, ///> Connector column 3, front
+ MBG_IO_PORT_POS_REAR_COL_3, ///> Connector column 3, rear
+ MBG_IO_PORT_POS_FRONT_COL_4, ///> Connector column 4, front
+ MBG_IO_PORT_POS_REAR_COL_4, ///> Connector column 4, rear
+ N_MBG_IO_PORT_POS
+};
+
+
+/**
+ * @brief Bit masks of Meinberg I/O port attitudes
+ *
+ * Used with ::MBG_IO_PORT_TYPE_INFO::supp_srcs
+ *
+ * @see ::MBG_IO_PORT_POS
+ */
+enum MBG_IO_PORT_POS_MSKS
+{
+ MBG_IO_PORT_POS_MSK_FRONT_COL_1 = (1UL << MBG_IO_PORT_POS_FRONT_COL_1), ///< See ::MBG_IO_PORT_POS_FRONT_COL_1
+ MBG_IO_PORT_POS_MSK_REAR_COL_1 = (1UL << MBG_IO_PORT_POS_REAR_COL_1), ///< See ::MBG_IO_PORT_POS_REAR_COL_1
+ MBG_IO_PORT_POS_MSK_FRONT_COL_2 = (1UL << MBG_IO_PORT_POS_FRONT_COL_2), ///< See ::MBG_IO_PORT_POS_FRONT_COL_2
+ MBG_IO_PORT_POS_MSK_REAR_COL_2 = (1UL << MBG_IO_PORT_POS_REAR_COL_2), ///< See ::MBG_IO_PORT_POS_REAR_COL_2
+ MBG_IO_PORT_POS_MSK_FRONT_COL_3 = (1UL << MBG_IO_PORT_POS_FRONT_COL_3), ///< See ::MBG_IO_PORT_POS_FRONT_COL_3
+ MBG_IO_PORT_POS_MSK_REAR_COL_3 = (1UL << MBG_IO_PORT_POS_REAR_COL_3), ///< See ::MBG_IO_PORT_POS_REAR_COL_3
+ MBG_IO_PORT_POS_MSK_FRONT_COL_4 = (1UL << MBG_IO_PORT_POS_FRONT_COL_4), ///< See ::MBG_IO_PORT_POS_FRONT_COL_4
+ MBG_IO_PORT_POS_MSK_REAR_COL_4 = (1UL << MBG_IO_PORT_POS_REAR_COL_4) ///< See ::MBG_IO_PORT_POS_REAR_COL_4
+};
+
+
+/**
+ * @brief IO Port Limits
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_INFO
+ * @see ::MBG_IO_PORT_INFO_U
+ * @see ::MBG_IO_PORT_INFO_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ */
+typedef struct
+{
+ uint8_t num_ports;
+ uint8_t reserved_1[3]; ///< Reserved, currently 0
+ uint32_t supp_positions; ///< Determines the size of the card (i.e. 2 rows, front/rear) See ::MBG_IO_PORT_POS_MSKS
+ uint32_t reserved_2[10]; ///< Reserved, currently 0
+
+} MBG_IO_PORT_LIMITS;
+
+#define _mbg_swab_io_port_limits( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->supp_positions ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Port Operation Bits
+ *
+ * Used with ::MBG_IO_PORT_SETTINGS::op_mode
+ *
+ * For now, there is a per port operation mode setting which
+ * is quite equal to ::ENABLE_FLAGS.
+ *
+ * @see ::MBG_IO_PORT_OP_MODE_MSKS
+ */
+enum MBG_IO_PORT_OP_MODE_BITS
+{
+ MBG_IO_PORT_OP_MODE_NONE = -1, ///< Current mode cannot be determined
+ MBG_IO_PORT_OP_MODE_DISABLED, ///< Disabled port
+ MBG_IO_PORT_OP_MODE_ALWAYS, ///< Always enable port
+ MBG_IO_PORT_OP_MODE_IF_SYNC_ONLY, ///< Enable port if sync only
+ MBG_IO_PORT_OP_MODE_AFTER_SYNC, ///< Always enable port after being sync once
+ N_MBG_IO_PORT_OP_MODE_BITS
+};
+
+
+/**
+ * @brief Strings descriptions for ::MBG_IO_PORT_OP_MODE_BITS
+ *
+ * Can be used to initialize a string array of ::N_MBG_IO_PORT_OP_MODE_BITS entries,
+ * so the number of strings must correspond to ::N_MBG_IO_PORT_OP_MODE_BITS.
+ *
+ * @see ::MBG_IO_PORT_OP_MODE_BITS
+ */
+#define MBG_IO_PORT_OP_MODE_STRS \
+{ \
+ "Disabled", \
+ "Always enabled", \
+ "If sync only", \
+ "Always after sync" \
+}
+
+
+
+/**
+ * @brief Masks for ::MBG_IO_PORT_OP_MODE_BITS
+ *
+ * Used with ::MBG_IO_PORT_INFO::supp_op_modes
+ *
+ * @see ::MBG_IO_PORT_OP_MODE_BITS
+ */
+enum MBG_IO_PORT_OP_MODE_MSKS
+{
+ MBG_IO_PORT_OP_MODE_MSK_DISABLED = (1UL << MBG_IO_PORT_OP_MODE_DISABLED), ///< See ::MBG_IO_PORT_OP_MODE_DISABLED
+ MBG_IO_PORT_OP_MODE_MSK_ALWAYS = (1UL << MBG_IO_PORT_OP_MODE_ALWAYS), ///< See ::MBG_IO_PORT_OP_MODE_ALWAYS
+ MBG_IO_PORT_OP_MODE_MSK_IF_SYNC_ONLY = (1UL << MBG_IO_PORT_OP_MODE_IF_SYNC_ONLY), ///< See ::MBG_IO_PORT_OP_MODE_IF_SYNC_ONLY
+ MBG_IO_PORT_OP_MODE_MSK_AFTER_SYNC = (1UL << MBG_IO_PORT_OP_MODE_AFTER_SYNC) ///< See ::MBG_IO_PORT_OP_MODE_AFTER_SYNC
+};
+
+
+/**
+ * @brief Physical or logical group role bits
+ *
+ * Used with ::MBG_IO_PORT_STATUS::phys_grp_role, ::MBG_IO_PORT_STATUS::log_grp_role
+ *
+ * @see ::MBG_IO_PORT_GRP_ROLE_MSKS
+ */
+enum MBG_IO_PORT_GRP_ROLE_BITS
+{
+ MBG_IO_PORT_GRP_ROLE_NONE, ///< No group role, only possible if port is not assigned to any group
+ MBG_IO_PORT_GRP_ROLE_MASTER, ///< Master port in group, i.e. configurable port of LIU
+ MBG_IO_PORT_GRP_ROLE_SLAVE, ///< Slave port in group, i.e. non-configurable port of LIU
+ MBG_IO_PORT_GRP_ROLE_PASSIVE, ///< Passive port in group, i.e. passive port of network group (i.e. SFP or RJ45)
+ N_MBG_IO_PORT_GRP_ROLE_BITS
+};
+
+
+/**
+ * @brief Strings descriptions for ::MBG_IO_PORT_GRP_ROLE_BITS
+ *
+ * Can be used to initialize a string array of ::N_MBG_IO_PORT_GRP_ROLE_BITS entries,
+ * so the number of strings must correspond to ::N_MBG_IO_PORT_GRP_ROLE_BITS.
+ *
+ * @see ::MBG_IO_PORT_GRP_ROLE_BITS
+ */
+#define MBG_IO_PORT_GRP_ROLE_STRS \
+{ \
+ "None", \
+ "Master", \
+ "Slave", \
+ "Passive" \
+}
+
+
+/**
+ * @brief Masks for ::MBG_IO_PORT_GRP_ROLE_BITS
+ *
+ * Used with ::MBG_IO_PORT_INFO::supp_phys_grp_roles
+ *
+ * @see ::MBG_IO_PORT_GRP_ROLE_BITS
+ */
+enum MBG_IO_PORT_GRP_ROLE_MSKS
+{
+ MBG_IO_PORT_GRP_ROLE_MSK_NONE = (1UL << MBG_IO_PORT_GRP_ROLE_NONE), ///< See ::MBG_IO_PORT_GRP_ROLE_NONE
+ MBG_IO_PORT_GRP_ROLE_MSK_MASTER = (1UL << MBG_IO_PORT_GRP_ROLE_MASTER), ///< See ::MBG_IO_PORT_GRP_ROLE_MASTER
+ MBG_IO_PORT_GRP_ROLE_MSK_SLAVE = (1UL << MBG_IO_PORT_GRP_ROLE_SLAVE), ///< See ::MBG_IO_PORT_GRP_ROLE_SLAVE
+ MBG_IO_PORT_GRP_ROLE_MSK_PASSIVE = (1UL << MBG_IO_PORT_GRP_ROLE_PASSIVE) ///< See ::MBG_IO_PORT_GRP_ROLE_PASSIVE
+};
+
+
+/**
+ * @brief IO Port Settings Union
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_INFO
+ * @see ::MBG_IO_PORT_INFO_U
+ * @see ::MBG_IO_PORT_INFO_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ */
+typedef union
+{
+ MBG_GPIO_SETTINGS gpio_settings;
+ POUT_SETTINGS pout_settings;
+
+} MBG_IO_PORT_SETTINGS_U;
+
+#define _mbg_swab_io_port_settings_u( _type, _p, _recv ) \
+do \
+{ \
+ switch ( (_type) ) \
+ { \
+ case MBG_IO_PORT_TYPE_GPIO: \
+ _mbg_swab_mbg_gpio_settings( &(_p)->gpio_settings, (_recv) ); \
+ break; \
+ \
+ case MBG_IO_PORT_TYPE_POUT: \
+ if ( _recv ) \
+ _mbg_swab_pout_settings_on_get( &(_p)->pout_settings ); \
+ else _mbg_swab_pout_settings_on_set( &(_p)->pout_settings ); \
+ break; \
+ \
+ default: break; \
+ } \
+} while ( 0 )
+
+
+#define MBG_IO_PORT_SETTINGS_MIN_SIZE 32
+
+
+/**
+ * @brief IO Port Settings
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_INFO
+ * @see ::MBG_IO_PORT_INFO_U
+ * @see ::MBG_IO_PORT_INFO_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ */
+typedef struct
+{
+ uint16_t type; ///< ::MBG_IO_PORT_TYPES
+ uint8_t direction; ///< ::MBG_IO_PORT_DIRS
+ uint8_t source; ///< ::MBG_IO_PORT_SRCS
+ uint8_t op_mode; ///< ::MBG_IO_PORT_OP_MODE_BITS
+ uint8_t reserved_1[3]; ///< Future use and padding, currently 0
+ uint32_t reserved_2[6]; ///< Future use and padding, currently 0
+
+ /*
+ * Struct members above represent minimum amount of data to be sent.
+ * See ::MBG_IO_PORT_SETTINGS_MIN_SIZE
+ */
+
+ MBG_IO_PORT_SETTINGS_U data; ///< Data union for setting's type
+
+} MBG_IO_PORT_SETTINGS;
+
+#define _mbg_swab_io_port_settings( _p, _recv ) \
+do \
+{ \
+ uint16_t t = (_p)->type; \
+ if ( (_recv) ) \
+ _mbg_swab16( &t ); \
+ _mbg_swab16( &(_p)->type ); \
+ _mbg_swab_io_port_settings_u( t, &(_p)->data, (_recv) ); \
+} while ( 0 )
+
+
+
+
+/**
+ * @brief IO Port Settings Index
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_INFO
+ * @see ::MBG_IO_PORT_INFO_U
+ * @see ::MBG_IO_PORT_INFO_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ *
+ * Indexes from 0..::MBG_IO_PORT_LIMITS::num_ports - 1 are used
+ * to set ::MBG_IO_PORT_SETTINGS wrapped in ::MBG_IO_PORT_SETTINGS_IDX.
+ */
+typedef struct
+{
+ uint32_t idx;
+ MBG_IO_PORT_SETTINGS settings;
+
+} MBG_IO_PORT_SETTINGS_IDX;
+
+#define _mbg_swab_io_port_settings_idx( _p, _recv ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_io_port_settings( &(_p)->settings, (_recv) ); \
+} while ( 0 )
+
+
+#define MBG_IO_PORT_SETTINGS_IDX_MIN_SIZE (MBG_IO_PORT_SETTINGS_MIN_SIZE + sizeof( uint32_t ))
+
+
+#define MBG_IO_PORT_SETTINGS_IDX_SIZES \
+{ \
+ MBG_IO_PORT_SETTINGS_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_PPS */ \
+ MBG_IO_PORT_SETTINGS_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_10MHz */ \
+ MBG_IO_PORT_SETTINGS_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_2048KHz */ \
+ MBG_IO_PORT_SETTINGS_IDX_MIN_SIZE + sizeof( MBG_GPIO_SETTINGS ), /* MBG_IO_PORT_TYPE_GPIO */ \
+ MBG_IO_PORT_SETTINGS_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_ETHERNET */ \
+ MBG_IO_PORT_SETTINGS_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_TERMINAL */ \
+ MBG_IO_PORT_SETTINGS_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_MULTI */ \
+ MBG_IO_PORT_SETTINGS_IDX_MIN_SIZE + sizeof( POUT_SETTINGS ) /* MBG_IO_PORT_TYPE_POUT */ \
+}
+
+
+#define MBG_NO_PHYS_GROUP 0xFF
+#define MBG_NO_LOG_GROUP 0xFF
+
+/**
+ * @brief IO Port Info
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_INFO_U
+ * @see ::MBG_IO_PORT_INFO_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ */
+typedef struct
+{
+ uint8_t num_types; ///< See ::MBG_IO_PORT_TYPE_INFO
+ uint8_t conn_type; ///< See ::MBG_IO_PORT_CONN_TYPES
+ uint8_t position; ///< See ::MBG_IO_PORT_POS
+ uint8_t reserved_1; ///< Future use and padding, currently 0
+ uint16_t supp_op_modes; ///< See ::MBG_IO_PORT_OP_MODE_MSKS
+ uint16_t supp_phys_grp_roles; ///< Supported roles in ::MBG_IO_PORT_STATUS::phys_grp_role, see ::MBG_IO_PORT_GRP_ROLE_MSKS
+ uint8_t phys_grp; ///< Physical group number (i.e. SFP/RJ45 on HPS100), or ::MBG_NO_PHYS_GROUP
+ uint8_t reserved_2[3]; ///< Future use and padding, currently 0
+ uint32_t reserved_3[8]; ///< Future use and padding, currently 0
+ char rel_str[16]; ///< Indicates internal relation, i.e. "lan0", "fpga0" or "/dev/ttyS0"
+ MBG_IO_PORT_SETTINGS settings; ///< See ::MBG_IO_PORT_SETTINGS
+
+} MBG_IO_PORT_INFO;
+
+#define _mbg_port_has_phys_group( _p ) ( ( _p )->phys_grp != MBG_NO_PHYS_GROUP )
+
+#define _mbg_swab_io_port_info( _p, _recv ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->supp_op_modes ); \
+ _mbg_swab16( &(_p)->supp_phys_grp_roles ); \
+ _mbg_swab_io_port_settings( &(_p)->settings, (_recv) ); \
+} while ( 0 )
+
+
+
+#define MBG_IO_PORT_INFO_MIN_SIZE ( 60 + MBG_IO_PORT_SETTINGS_MIN_SIZE )
+
+
+/**
+ * @brief IO Port Info Index
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_U
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ *
+ * Indexes from 0..::MBG_IO_PORT_LIMITS::num_ports - 1 are used
+ * to query ::MBG_IO_PORT_INFO wrapped in ::MBG_IO_PORT_INFO_IDX.
+ */
+typedef struct
+{
+ uint32_t idx;
+ MBG_IO_PORT_INFO info;
+
+} MBG_IO_PORT_INFO_IDX;
+
+#define _mbg_swab_io_port_info_idx( _p, _recv ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_io_port_info( &(_p)->info, (_recv) ); \
+} while ( 0 )
+
+
+
+#define MBG_IO_PORT_INFO_IDX_MIN_SIZE (MBG_IO_PORT_INFO_MIN_SIZE + sizeof( uint32_t ))
+
+
+#define MBG_IO_PORT_INFO_IDX_SIZES \
+{ \
+ MBG_IO_PORT_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_PPS */ \
+ MBG_IO_PORT_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_10MHz */ \
+ MBG_IO_PORT_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_2048KHz */ \
+ MBG_IO_PORT_INFO_IDX_MIN_SIZE + sizeof( MBG_GPIO_SETTINGS ), /* MBG_IO_PORT_TYPE_GPIO */ \
+ MBG_IO_PORT_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_ETHERNET */ \
+ MBG_IO_PORT_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_TERMINAL */ \
+ MBG_IO_PORT_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_MULTI */ \
+ MBG_IO_PORT_INFO_IDX_MIN_SIZE + sizeof( POUT_SETTINGS ) /* MBG_IO_PORT_TYPE_POUT */ \
+}
+
+
+/**
+ * @brief IO Port Type Info Union
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_INFO
+ * @see ::MBG_IO_PORT_INFO_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ */
+typedef union
+{
+ MBG_GPIO_LIMITS gpio_limits;
+ POUT_INFO pout_info;
+
+} MBG_IO_PORT_TYPE_INFO_U;
+
+#define _mbg_swab_io_port_type_info_u( _type, _p, _recv ) \
+do \
+{ \
+ switch ( (_type) ) \
+ { \
+ case MBG_IO_PORT_TYPE_GPIO: \
+ _mbg_swab_mbg_gpio_limits( &(_p)->gpio_limits, (_recv) ); \
+ break; \
+ \
+ case MBG_IO_PORT_TYPE_POUT: \
+ _mbg_swab_pout_info_on_get( &(_p)->pout_info ); \
+ break; \
+ \
+ default: break; \
+ } \
+} while ( 0 )
+
+
+
+#define MBG_IO_PORT_TYPE_INFO_MIN_SIZE 32
+
+
+/**
+ * @brief IO Port Type Info
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_INFO_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO_U
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ */
+typedef struct
+{
+ uint16_t port_type; ///< See ::MBG_IO_PORT_TYPES
+ uint16_t reserved_1; ///< Future use and padding, currently 0
+ uint8_t supp_dirs; ///< See ::MBG_IO_PORT_DIR_MSKS
+ uint8_t reserved_2[3]; ///< Future use and padding, currently 0
+ uint32_t supp_srcs; ///< See ::MBG_IO_PORT_SRC_MSKS
+ uint32_t reserved_3[5]; ///< Future use and padding, currently 0
+
+ /*
+ * Struct members above represent minimum amount of data to be sent.
+ * See ::MBG_IO_PORT_TYPE_INFO_MIN_SIZE
+ */
+
+ MBG_IO_PORT_TYPE_INFO_U data; ///< Port type specific data
+
+} MBG_IO_PORT_TYPE_INFO;
+
+#define _mbg_swab_io_port_type_info( _p, _recv ) \
+do \
+{ \
+ uint16_t t = (_p)->port_type; \
+ if ( (_recv) ) \
+ _mbg_swab16( &t ); \
+ _mbg_swab16( &(_p)->port_type ); \
+ _mbg_swab_io_port_type_info_u( t, &(_p)->data, (_recv) ); \
+ _mbg_swab32( &(_p)->supp_srcs ); \
+} while ( 0 )
+
+
+#define MBG_IO_PORT_TYPE_INFO_IDX_MIN_SIZE (MBG_IO_PORT_TYPE_INFO_MIN_SIZE + 2 * sizeof( uint32_t ))
+
+
+#define MBG_IO_PORT_TYPE_INFO_IDX_SIZES \
+{ \
+ MBG_IO_PORT_TYPE_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_PPS */ \
+ MBG_IO_PORT_TYPE_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_10MHz */ \
+ MBG_IO_PORT_TYPE_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_2048KHz */ \
+ MBG_IO_PORT_TYPE_INFO_IDX_MIN_SIZE + sizeof( MBG_GPIO_LIMITS ), /* MBG_IO_PORT_TYPE_GPIO */ \
+ MBG_IO_PORT_TYPE_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_ETHERNET */ \
+ MBG_IO_PORT_TYPE_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_TERMINAL */ \
+ MBG_IO_PORT_TYPE_INFO_IDX_MIN_SIZE, /* MBG_IO_PORT_TYPE_MULTI */ \
+ MBG_IO_PORT_TYPE_INFO_IDX_MIN_SIZE + sizeof( POUT_INFO ) /* MBG_IO_PORT_TYPE_POUT */ \
+}
+
+
+/**
+ * @brief IO Port Type Info Index
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_U
+ * @see ::MBG_IO_PORT_STATUS
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ *
+ * Indexes from 0..::MBG_IO_PORT_INFO::num_types - 1 are used
+ * to query ::MBG_IO_PORT_TYPE_INFO wrapped in ::MBG_IO_PORT_TYPE_INFO_IDX.
+ *
+ */
+typedef struct
+{
+ uint32_t port_idx;
+ uint32_t port_type_idx;
+ MBG_IO_PORT_TYPE_INFO info;
+
+} MBG_IO_PORT_TYPE_INFO_IDX;
+
+#define _mbg_swab_io_port_type_info_idx( _p, _recv ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->port_idx ); \
+ _mbg_swab32( &(_p)->port_type_idx ); \
+ _mbg_swab_io_port_type_info( &(_p)->info, (_recv) ); \
+} while ( 0 )
+
+
+
+#define MAX_IO_PORT_STATUS_BITS 64
+
+
+/**
+ * @brief Port Type Status Bits
+ *
+ */
+enum MBG_IO_PORT_STATUS_BITS
+{
+ MBG_IO_PORT_STATUS_BIT_DISABLED, ///< See ::MBG_IO_PORT_OP_MODE_DISABLED. Other bits should be 0 in this case
+ MBG_IO_PORT_STATUS_BIT_CARRIER_DETECTED, ///< Port has physical carrier connection (e.g. BNC cable in BPE's case)
+ MBG_IO_PORT_STATUS_BIT_INPUT_SIGNAL_NEVER_AVAIL, ///< Input signal has NEVER been avail
+ MBG_IO_PORT_STATUS_BIT_INPUT_SIGNAL_AVAIL, ///< Input signal is avail right now
+ MBG_IO_PORT_STATUS_BIT_INPUT_SIGNAL_LOST, ///< Input signal is currently not avail, but has been avail before
+ MBG_IO_PORT_STATUS_BIT_SHORT_CIRCUIT, ///< Short circuit
+ N_MBG_IO_PORT_STATUS_BITS
+};
+
+
+/**
+ * @brief Strings descriptions for ::MBG_IO_PORT_STATUS_BITS
+ *
+ * Can be used to initialize a string array of ::N_MBG_IO_PORT_STATUS_BITS entries,
+ * so the number of strings must correspond to ::N_MBG_IO_PORT_STATUS_BITS.
+ *
+ * @see ::MBG_IO_PORT_STATUS_BITS
+ */
+#define MBG_IO_PORT_STATUS_STRS \
+{ \
+ "Disabled", \
+ "Carrier detected", \
+ "Input signal has never been avail", \
+ "Input signal is avail", \
+ "Input signal is currently lost", \
+ "Short circuit" \
+}
+
+
+/**
+ * @brief Array size required to store all status bits
+ *
+ * The number of bytes required to store up to ::MAX_IO_PORT_STATUS_BITS
+ * feature bits in a byte array.
+ */
+#define MAX_IO_PORT_STATUS_BYTES ( MAX_IO_PORT_STATUS_BITS / 8 )
+
+
+/**
+ * @brief A structure used to store port status bits
+ *
+ * Up to ::MAX_IO_PORT_STATUS_BITS totally can be stored, but only
+ * ::N_MBG_IO_PORT_STATUS_BITS are currently defined.
+ *
+ * The ::_set_io_port_status_bit macro should be used by the firmware
+ * to set a status bit in the buffer, and the ::check_byte_array_bit
+ * to check if a bit is set
+ *
+ * @see ::_set_io_port_status_bit
+ * @see ::check_byte_array_bit
+ */
+typedef struct
+{
+ uint8_t b[MAX_IO_PORT_STATUS_BYTES];
+
+} MBG_IO_PORT_STATUS_BUFFER;
+
+#define _mbg_swab_io_port_status_buffer( _p ) \
+ _nop_macro_fnc()
+
+
+
+/**
+ * @brief Set an port status bit in a ::MBG_IO_PORT_STATUS_BUFFER
+ *
+ * Should be used by the firmware only to set one of the ::N_MBG_IO_PORT_STATUS_BITS
+ * in an ::MBG_IO_PORT_STATUS_BUFFER after power-up.
+ *
+ * @param[in] _status_bit One of the ::MBG_IO_PORT_STATUS_BITS
+ * @param[in] _status_buffp Pointer to an ::MBG_IO_PORT_STATUS_BUFFER
+ */
+#define _set_io_port_status_bit( _status_bit, _status_buffp ) \
+ _set_array_bit( _status_bit, (_status_buffp)->b, MAX_IO_PORT_STATUS_BYTES )
+
+
+/**
+ * @brief IO Port Type Status
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_U
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS_IDX
+ *
+ */
+typedef struct
+{
+ MBG_IO_PORT_STATUS_BUFFER supp_stati; ///< Supported ::MBG_IO_PORT_STATUS_BITS in ::MBG_IO_PORT_STATUS_BUFFER
+ MBG_IO_PORT_STATUS_BUFFER status; ///< See ::MBG_IO_PORT_STATUS_BUFFER
+
+ uint8_t cfg_counter; ///< Updated (increased) when config changes
+ uint8_t phys_grp_role; ///< Physical group role state, see ::MBG_IO_PORT_GRP_ROLE_BITS
+ uint8_t log_grp; ///< Logical group number (i.e. bond0), or ::MBG_NO_LOG_GROUP
+ uint8_t log_grp_role; ///< Logical group role (i.e. bond master, bond slave), see ::MBG_IO_PORT_GRP_ROLE_BITS
+
+ uint32_t reserved_2[4]; ///< Future use, currently 0
+
+} MBG_IO_PORT_STATUS;
+
+#define _mbg_port_has_log_group( _p ) ( ( _p )->log_grp != MBG_NO_LOG_GROUP )
+
+#define _mbg_swab_io_port_status( _p ) \
+do \
+{ \
+ _mbg_swab_io_port_status_buffer( &(_p)->supp_stati ); \
+ _mbg_swab_io_port_status_buffer( &(_p)->status ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief IO Port Type Status
+ *
+ * @see @ref group_io_ports
+ * @see ::MBG_IO_PORT_SETTINGS_U
+ * @see ::MBG_IO_PORT_LIMITS
+ * @see ::MBG_IO_PORT_SETTINGS
+ * @see ::MBG_IO_PORT_SETTINGS_IDX
+ * @see ::MBG_IO_PORT_TYPE_INFO
+ * @see ::MBG_IO_PORT_TYPE_INFO_U
+ * @see ::MBG_IO_PORT_TYPE_INFO_IDX
+ * @see ::MBG_IO_PORT_STATUS
+ *
+ * Indexes from 0..::MBG_IO_PORT_INFO::num_types - 1 are used
+ * to query ::MBG_IO_PORT_TYPE_INFO wrapped in ::MBG_IO_PORT_TYPE_INFO_IDX.
+ *
+ */
+typedef struct
+{
+ uint32_t idx;
+ MBG_IO_PORT_STATUS status;
+
+} MBG_IO_PORT_STATUS_IDX;
+
+#define _mbg_swab_io_port_status_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_io_port_status( &(_p)->status ); \
+} while ( 0 )
+
+
+/** @} defgroup group_io_ports */
+
+
+
+/**
+ * @defgroup group_monitoring Monitoring / notification
+ *
+ * @note This structure and its definitions are only supported by a device
+ * if ::MBG_XFEATURE_MONITORING is set in the extended device features.
+ *
+ * TODO: Add proper Doxygen documentation
+ *
+ * @{ */
+
+
+#define MBG_MONITORING_STR_SIZE 32
+
+enum MBG_MONITORING_TYPES
+{
+ MBG_MONITORING_TYPE_SNMP,
+ MBG_MONITORING_TYPE_EMAIL,
+ MBG_MONITORING_TYPE_SYSLOG,
+ N_MBG_MONITORING_TYPES
+};
+
+#define MBG_MONITORING_TYPE_STRS \
+{ \
+ "SNMP", \
+ "Email", \
+ "Syslog" \
+}
+
+enum MBG_MONITORING_TYPE_MSKS
+{
+ MBG_MONITORING_TYPE_MSK_SNMP = (1UL << MBG_MONITORING_TYPE_SNMP),
+ MBG_MONITORING_TYPE_MSK_EMAIL = (1UL << MBG_MONITORING_TYPE_EMAIL),
+ MBG_MONITORING_TYPE_MSK_SYSLOG = (1UL << MBG_MONITORING_TYPE_SYSLOG)
+};
+
+
+
+typedef struct
+{
+ uint16_t supp_types; ///< See ::MBG_MONITORING_TYPE_MSKS
+ uint16_t supp_num_events; ///< Supported number of events. See ::MBG_EVENT_TYPES
+ uint32_t reserved_2[3];
+
+} MBG_MONITORING_LIMITS;
+
+#define _mbg_swab_monitoring_limits( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->supp_types ); \
+ _mbg_swab16( &(_p)->supp_num_events ); \
+} while ( 0 )
+
+
+
+/* If ::MBG_MONITORING_TYPE_MSK_SNMP is set in ::MBG_MONITORING_LIMITS::supp_types */
+
+enum MBG_SNMP_VERSIONS
+{
+ MBG_SNMP_VERSION_V1,
+ MBG_SNMP_VERSION_V2c,
+ MBG_SNMP_VERSION_V3,
+ N_MBG_SNMP_VERSIONS
+};
+
+#define MBG_SNMP_VERSION_STRS \
+{ \
+ "Version 1", \
+ "Version 2c", \
+ "Version 3" \
+}
+
+enum MBG_SNMP_VERSION_MSKS
+{
+ MBG_SNMP_VERSION_MSK_V1 = (1UL << MBG_SNMP_VERSION_V1),
+ MBG_SNMP_VERSION_MSK_V2c = (1UL << MBG_SNMP_VERSION_V2c),
+ MBG_SNMP_VERSION_MSK_V3 = (1UL << MBG_SNMP_VERSION_V3)
+};
+
+
+
+typedef struct
+{
+ uint8_t num_v12_settings; ///< Number of configured v1/v2 settings, see ::MBG_SNMP_V12_INFO_IDX
+ uint8_t num_v3_settings; ///< Number of configured v1/v2 trap receivers, see ::MBG_SNMP_V12_TRAP_INFO_IDX
+ uint8_t num_v12_trap_receivers; ///< Number of configured v3 settings, see ::MBG_SNMP_V3_INFO_IDX
+ uint8_t num_v3_trap_receivers; ///< Number of configured v3 trap receivers, see ::MBG_SNMP_V3_TRAP_INFO_IDX
+ uint16_t listening_port; ///< snmpd listening port, 161 by default
+ uint16_t reserved_1;
+ uint32_t reserved_2[3];
+ char location[MBG_MONITORING_STR_SIZE];
+ char contact[MBG_MONITORING_STR_SIZE];
+ char name[MBG_MONITORING_STR_SIZE];
+ char reserved_3[MBG_MONITORING_STR_SIZE]; ///< Future use
+ char reserved_4[MBG_MONITORING_STR_SIZE]; ///< Future use
+
+} MBG_SNMP_GLB_SETTINGS;
+
+#define _mbg_swab_snmp_glb_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->listening_port ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ MBG_SNMP_GLB_SETTINGS settings;
+ uint8_t supp_versions; ///< See ::MBG_SNMP_VERSION_MSKS
+ uint8_t max_v12_settings; ///< Only valid if ::supp_versions contains ::MBG_SNMP_VERSION_MSK_V1 or ::MBG_SNMP_VERSION_MSK_V2c
+ uint8_t max_v3_settings; ///< Only valid if ::supp_versions contains ::MBG_SNMP_VERSION_MSK_V3
+ uint8_t max_v12_trap_receivers; ///< Only valid if ::supp_versions contains ::MBG_SNMP_VERSION_MSK_V1 or ::MBG_SNMP_VERSION_MSK_V2c
+ uint8_t max_v3_trap_receivers; ///< Only valid if ::supp_versions contains ::MBG_SNMP_VERSION_MSK_V3
+ uint8_t reserved_1[3];
+ uint32_t reserved_2[2];
+
+} MBG_SNMP_GLB_INFO;
+
+#define _mbg_swab_snmp_glb_info( _p ) \
+do \
+{ \
+ _mbg_swab_snmp_glb_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+enum MBG_SNMP_ACCESS_TYPES
+{
+ MBG_SNMP_ACCESS_TYPE_RO,
+ MBG_SNMP_ACCESS_TYPE_RW,
+ N_MBG_SNMP_ACCESS_TYPES
+};
+
+
+#define MBG_SNMP_ACCESS_TYPE_STRS \
+{ \
+ "Read-only", \
+ "Read-write" \
+}
+
+
+
+typedef struct
+{
+ uint8_t version; ///< See ::MBG_MONITORING_SNMP_VERSIONS (1 or 2)
+ uint8_t access_type; ///< See ::MBG_SNMP_ACCESS_TYPES, ignore in trap settings
+ uint8_t reserved_1[2];
+ uint32_t reserved_2[3];
+ char community[MBG_MONITORING_STR_SIZE];
+
+} MBG_SNMP_V12_SETTINGS;
+
+#define _mbg_swab_snmp_v12_settings( _p ) \
+do \
+{ \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_SNMP_V12_SETTINGS settings;
+
+} MBG_SNMP_V12_SETTINGS_IDX;
+
+#define _mbg_swab_snmp_v12_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_snmp_v12_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ MBG_SNMP_V12_SETTINGS settings;
+ uint32_t reserved_1[4];
+
+} MBG_SNMP_V12_INFO;
+
+#define _mbg_swab_snmp_v12_info( _p ) \
+do \
+{ \
+ _mbg_swab_snmp_v12_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_SNMP_V12_INFO info;
+
+} MBG_SNMP_V12_INFO_IDX;
+
+#define _mbg_swab_snmp_v12_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_snmp_v12_info( &(_p)->info ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint8_t timeout; ///< In seconds
+ uint8_t retries;
+ uint16_t reserved_1;
+ uint32_t reserved_2[3];
+ char reserved_3[MBG_MONITORING_STR_SIZE]; ///< Future use
+ char reserved_4[MBG_MONITORING_STR_SIZE]; ///< Future use
+ MBG_SNMP_V12_SETTINGS v12_settings;
+ MBG_HOSTNAME receiver_addr;
+ uint16_t dest_port; ///< receiver destination port, 162 by default
+ uint16_t reserved_5;
+
+} MBG_SNMP_V12_TRAP_SETTINGS;
+
+#define _mbg_swab_snmp_v12_trap_settings( _p ) \
+do \
+{ \
+ _mbg_swab_snmp_v12_settings( &(_p)->v12_settings ); \
+ _mbg_swab16( &(_p)->dest_port ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_SNMP_V12_TRAP_SETTINGS settings;
+
+} MBG_SNMP_V12_TRAP_SETTINGS_IDX;
+
+#define _mbg_swab_snmp_v12_trap_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_snmp_v12_trap_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ MBG_SNMP_V12_TRAP_SETTINGS settings;
+ uint32_t reserved_1[4];
+
+} MBG_SNMP_V12_TRAP_INFO;
+
+#define _mbg_swab_snmp_v12_trap_info( _p ) \
+do \
+{ \
+ _mbg_swab_snmp_v12_trap_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_SNMP_V12_TRAP_INFO info;
+
+} MBG_SNMP_V12_TRAP_INFO_IDX;
+
+#define _mbg_swab_snmp_v12_trap_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_snmp_v12_trap_info( &(_p)->info ); \
+} while ( 0 )
+
+
+
+enum MBG_SNMP_V3_SEC_LEVELS
+{
+ MBG_SNMP_V3_SEC_LEVEL_NO_AUTH_NO_PRIV,
+ MBG_SNMP_V3_SEC_LEVEL_AUTH_NO_PRIV,
+ MBG_SNMP_V3_SEC_LEVEL_AUTH_PRIV,
+ N_MBG_SNMP_V3_SEC_LEVELS
+};
+
+#define MBG_SNMP_V3_SEC_LEVEL_STRS \
+{ \
+ "No auth no priv", \
+ "Auth no priv", \
+ "Auth priv" \
+}
+
+
+enum MBG_SNMP_V3_AUTH_PROTOCOLS
+{
+ MBG_SNMP_V3_AUTH_PROTOCOL_NONE,
+ MBG_SNMP_V3_AUTH_PROTOCOL_MD5,
+ MBG_SNMP_V3_AUTH_PROTOCOL_SHA,
+ N_MBG_SNMP_V3_AUTH_PROTOCOLS
+};
+
+#define MBG_SNMP_V3_AUTH_PROTOCOL_STRS \
+{ \
+ "None", \
+ "MD5", \
+ "SHA" \
+}
+
+
+enum MBG_SNMP_V3_PRIV_PROTOCOLS
+{
+ MBG_SNMP_V3_PRIV_PROTOCOL_NONE,
+ MBG_SNMP_V3_PRIV_PROTOCOL_DES,
+ MBG_SNMP_V3_PRIV_PROTOCOL_AES,
+ N_MBG_SNMP_V3_PRIV_PROTOCOLS
+};
+
+
+#define MBG_SNMP_V3_PRIV_PROTOCOL_STRS \
+{ \
+ "None", \
+ "DES", \
+ "AES" \
+}
+
+
+
+typedef struct
+{
+ uint8_t access_type; ///< See ::MBG_SNMP_ACCESS_TYPES, ignore in trap settings
+ uint8_t sec_level; ///< See ::MBG_SNMP_V3_SEC_LEVEL
+ uint8_t auth_protocol; ///< See ::MBG_SNMP_V3_AUTH_PROTOCOLS if ::sec_level is
+ ///< ::MBG_SNMP_V3_SEC_LEVEL_AUTH_NO_PRIV or ::MBG_SNMP_V3_SEC_LEVEL_AUTH_PRIV
+ uint8_t priv_protocol; ///< See ::MBG_SNMP_V3_PRIV_PROTOCOLS if ::sec_level is
+ ///< ::MBG_SNMP_V3_SEC_LEVEL_AUTH_PRIV
+ uint32_t reserved_1[3];
+ char user_name[MBG_MONITORING_STR_SIZE]; ///< Must be set
+ char auth_passwd[MBG_MONITORING_STR_SIZE]; ///< Passwd is for user if ::auth_protocol is ::MBG_SNMP_V3_SEC_LEVEL_AUTH_NO_PRIV or ::MBG_SNMP_V3_SEC_LEVEL_AUTH_PRIV
+ char sec_engine_id[MBG_MONITORING_STR_SIZE]; ///< Mandatory
+ char context_engine_id[MBG_MONITORING_STR_SIZE]; ///< Ignore
+ char context_name[MBG_MONITORING_STR_SIZE]; ///< Ignore
+ char reserved_2[MBG_MONITORING_STR_SIZE]; ///< Future use
+ char reserved_3[MBG_MONITORING_STR_SIZE]; ///< Future use
+ char priv_passwd[MBG_MONITORING_STR_SIZE]; /// Encryption passwd if ::auth_protocol is ::MBG_SNMP_V3_SEC_LEVEL_AUTH_PRIV
+ uint32_t boots; ///< Number of system/deamon restarts -> Ignore
+ uint32_t time; ///< Timeticks since last "boots" event -> Ignore
+ uint32_t reserved_4[2];
+
+} MBG_SNMP_V3_SETTINGS;
+
+#define _mbg_swab_snmp_v3_settings( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->boots ); \
+ _mbg_swab32( &(_p)->time ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_SNMP_V3_SETTINGS settings;
+
+} MBG_SNMP_V3_SETTINGS_IDX;
+
+#define _mbg_swab_snmp_v3_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_snmp_v3_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ MBG_SNMP_V3_SETTINGS settings;
+ uint32_t reserved_1[4];
+
+} MBG_SNMP_V3_INFO;
+
+#define _mbg_swab_snmp_v3_info( _p ) \
+do \
+{ \
+ _mbg_swab_snmp_v3_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_SNMP_V3_INFO info;
+
+} MBG_SNMP_V3_INFO_IDX;
+
+#define _mbg_swab_snmp_v3_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_snmp_v3_info( &(_p)->info ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint8_t timeout; ///< In seconds
+ uint8_t retries;
+ uint8_t reserved_1[2];
+ uint32_t reserved_2[3];
+ MBG_SNMP_V3_SETTINGS v3_settings;
+ MBG_HOSTNAME receiver_addr;
+ uint16_t dest_port; ///< receiver destination port, 162 by default
+ uint16_t reserved_3;
+
+} MBG_SNMP_V3_TRAP_SETTINGS;
+
+#define _mbg_swab_snmp_v3_trap_settings( _p ) \
+do \
+{ \
+ _mbg_swab_snmp_v3_settings( &(_p)->v3_settings ); \
+ _mbg_swab16( &(_p)->dest_port ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_SNMP_V3_TRAP_SETTINGS settings;
+
+} MBG_SNMP_V3_TRAP_SETTINGS_IDX;
+
+#define _mbg_swab_snmp_v3_trap_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_snmp_v3_trap_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ MBG_SNMP_V3_TRAP_SETTINGS settings;
+ uint32_t reserved_1[4];
+
+} MBG_SNMP_V3_TRAP_INFO;
+
+#define _mbg_swab_snmp_v3_trap_info( _p ) \
+do \
+{ \
+ _mbg_swab_snmp_v3_trap_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint32_t idx;
+ MBG_SNMP_V3_TRAP_INFO info;
+
+} MBG_SNMP_V3_TRAP_INFO_IDX;
+
+#define _mbg_swab_snmp_v3_trap_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_snmp_v3_trap_info( &(_p)->info ); \
+} while ( 0 )
+
+
+
+enum MBG_EVENT_TYPES
+{
+ MBG_EVENT_TYPE_NTP_STOPPED,
+ MBG_EVENT_TYPE_NTP_NOT_SYNC,
+ MBG_EVENT_TYPE_NTP_SYNC,
+ MBG_EVENT_TYPE_LINK_DOWN,
+ MBG_EVENT_TYPE_LINK_UP,
+ MBG_EVENT_TYPE_HEARTBEAT,
+ N_MBG_EVENT_TYPES
+};
+
+#define MBG_EVENT_TYPE_STRS \
+{ \
+ "NTP stopped", \
+ "NTP not synchronized", \
+ "NTP synchronized", \
+ "Network link down", \
+ "Network link up", \
+ "Heartbeat" \
+}
+
+enum MBG_EVENT_SEVERITIES
+{
+ MBG_EVENT_SEVERITY_CRITICAL,
+ MBG_EVENT_SEVERITY_ERROR,
+ MBG_EVENT_SEVERITY_WARNING,
+ MBG_EVENT_SEVERITY_INFO,
+ MBG_EVENT_SEVERITY_SUCCESS,
+ N_MBG_EVENT_SEVERITIES
+};
+
+#define MBG_EVENT_SEVERITY_STRS \
+{ \
+ "Critical", \
+ "Error", \
+ "Warning", \
+ "Info", \
+ "Success" \
+}
+
+enum MBG_EVENT_SEVERITY_MSKS
+{
+ MBG_EVENT_SEVERITY_MSK_CRITICAL = (1UL << MBG_EVENT_SEVERITY_CRITICAL),
+ MBG_EVENT_SEVERITY_MSK_ERROR = (1UL << MBG_EVENT_SEVERITY_ERROR),
+ MBG_EVENT_SEVERITY_MSK_WARNING = (1UL << MBG_EVENT_SEVERITY_WARNING),
+ MBG_EVENT_SEVERITY_MSK_INFO = (1UL << MBG_EVENT_SEVERITY_INFO),
+ MBG_EVENT_SEVERITY_MSK_SUCCESS = (1UL << MBG_EVENT_SEVERITY_SUCCESS)
+};
+
+typedef struct
+{
+ uint8_t severity; ///< See ::MBG_EVENT_SEVERITIES
+ uint8_t reserved_1;
+ uint16_t triggers; ///< See ::MBG_MONITORING_TYPE_MSKS if set in ::MBG_MONITORING_LIMITS::supp_types
+ uint16_t interval; ///< In seconds if ::MBG_EVENT_FLAG_MSK_INTERVAL is set in ::MBG_EVENT_INFO::supp_flags. 0 otherwise
+ uint16_t reserved_2;
+ uint32_t reserved_3[6];
+
+} MBG_EVENT_SETTINGS;
+
+#define _mbg_swab_event_settings( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->triggers ); \
+ _mbg_swab16( &(_p)->interval ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Structure for monitoring event settings
+ *
+ * @see ::MBG_EVENT_INFO_IDX
+ */
+typedef struct
+{
+ uint32_t idx;
+ MBG_EVENT_SETTINGS settings;
+
+} MBG_EVENT_SETTINGS_IDX;
+
+#define _mbg_swab_event_settings_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_event_settings( &(_p)->settings ); \
+} while ( 0 )
+
+
+
+enum MBG_EVENT_SUPP_FLAGS
+{
+ MBG_EVENT_SUPP_FLAG_INTERVAL, ///< Event can be sent cyclical
+ N_MBG_EVENT_SUPP_FLAGS
+};
+
+
+enum MBG_EVENT_SUPP_FLAG_MSKS
+{
+ MBG_EVENT_SUPP_FLAG_MSK_INTERVAL = ( 1UL << MBG_EVENT_SUPP_FLAG_INTERVAL )
+};
+
+
+
+enum MBG_EVENT_FLAGS
+{
+ MBG_EVENT_FLAG_NOT_AVAIL, ///< Event is currently not available, i.e. card in slot has been removed
+ N_MBG_EVENT_FLAGS
+};
+
+
+enum MBG_EVENT_FLAG_MSKS
+{
+ MBG_EVENT_FLAG_MSK_NOT_AVAIL = ( 1UL << MBG_EVENT_FLAG_NOT_AVAIL )
+};
+
+#define MBG_OWN_EVENT_CHASSIS 0xFF
+#define MBG_OWN_EVENT_SLOT 0xFF
+#define MBG_INV_EVENT_PORT 0xFF
+
+
+
+typedef struct
+{
+ MBG_EVENT_SETTINGS settings;
+ uint16_t type; ///< See ::MBG_EVENT_TYPES
+ uint8_t chassis_idx; ///< Index of the associated IMS chassis
+ uint8_t slot_idx; ///< Index of the associated IMS slot
+ uint8_t port_idx; ///< Index of the associated IO port
+ uint8_t reserved_1; ///< Reserved, currently 0
+ uint16_t reserved_2; ///< Reserved, currently 0
+
+ uint16_t supp_severities; ///< See ::MBG_EVENT_SEVERITY_MSKS
+ uint16_t supp_flags; ///< See ::MBG_EVENT_SUPP_FLAG_MSKS
+ uint16_t supp_triggers; ///< See ::MBG_MONITORING_TYPE_MSKS
+ uint16_t flags; ///< See ::MBG_EVENT_FLAG_MSKS
+
+ uint32_t reserved_3[4];
+
+} MBG_EVENT_INFO;
+
+#define _mbg_swab_event_info( _p ) \
+do \
+{ \
+ _mbg_swab_event_settings( &(_p)->settings ); \
+ _mbg_swab16( &(_p)->type ); \
+ _mbg_swab16( &(_p)->supp_severities ); \
+ _mbg_swab16( &(_p)->supp_flags ); \
+ _mbg_swab16( &(_p)->supp_triggers ); \
+ _mbg_swab16( &(_p)->flags ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Structure for monitoring event info
+ *
+ * @note idx represents the event type, see ::MBG_EVENT_TYPES
+ * Before requesting the struct, its availability should be checked
+ * in ::MBG_MONITORING_LIMITS::supp_events.
+ *
+ * @see ::MBG_EVENT_TYPES
+ * @see ::MBG_MONITORING_LIMITS
+ */
+typedef struct
+{
+ uint32_t idx;
+ MBG_EVENT_INFO info;
+
+} MBG_EVENT_INFO_IDX;
+
+#define _mbg_swab_event_info_idx( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->idx ); \
+ _mbg_swab_event_info( &(_p)->info ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint8_t snmp_cfg_counter; ///< Updated (increased) when SNMP config changes
+ uint8_t email_cfg_counter; ///< Updated (increased) when Email config changes
+ uint8_t syslog_cfg_counter; ///< Updated (increased) when Syslog config changes
+ uint8_t event_cfg_counter; ///< Updated (increased) when event config changes
+ uint32_t reserved_2[3];
+
+} MBG_MONITORING_STATUS;
+
+#define _mbg_swab_monitoring_status( _p ) \
+do \
+{ \
+} while ( 0 )
+
+
+
+enum MBG_EVENT_STATUS_FLAGS
+{
+ MBG_EVENT_STATUS_FLAG_ACTIVE, ///< Event is currently active
+ N_MBG_EVENT_STATUS_FLAGS
+};
+
+
+enum MBG_EVENT_STATUS_FLAG_MSKS
+{
+ MBG_EVENT_STATUS_FLAG_MSK_ACTIVE = (1UL << MBG_EVENT_STATUS_FLAG_ACTIVE)
+};
+
+
+
+typedef struct
+{
+ uint16_t flags; ///< See ::MBG_EVENT_STATUS_FLAGS
+ uint16_t reserved_1;
+ uint32_t last_triggered; ///< Unix timestamp when this event has been triggered
+ uint32_t reserved_2[6];
+
+} MBG_EVENT_STATUS;
+
+#define _mbg_swab_event_status( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->flags ); \
+ _mbg_swab32( &(_p)->last_triggered ); \
+} while ( 0 )
+
+
+
+typedef struct
+{
+ uint16_t idx;
+ MBG_EVENT_STATUS status;
+
+} MBG_EVENT_STATUS_IDX;
+
+#define _mbg_swab_event_status_idx( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->idx ); \
+ _mbg_swab_event_status( &(_p)->status ); \
+} while ( 0 )
+
+/** @} defgroup group_monitoring */
+
+
+/**
+ * @defgroup group_usb_lock
+ *
+ * @note This structure and its definitions are only supported by a device
+ * if ::MBG_XFEATURE_USB_LOCK is set in the extended device features.
+ * Feature can electrically disconnect an USB slave device from
+ * the USB host bus. It cannot be reset via software, it's a one way action only.
+ *
+ * TODO: Add proper Doxygen documentation
+ *
+ * @{ */
+
+
+enum MBG_USB_LOCK_FLAGS
+{
+ MBG_USB_LOCK_FLAG_ACTIVE, ///< USB Connection is interrupted
+ N_MBG_USB_LOCK_FLAGS
+};
+
+
+enum MBG_USB_LOCK_FLAG_MSKS
+{
+ MBG_USB_LOCK_FLAG_MSK_ACTIVE = (1UL << MBG_USB_LOCK_FLAG_ACTIVE) ///< See ::MBG_USB_LOCK_FLAG_ACTIVE
+};
+
+
+typedef struct
+{
+ uint8_t flags; ///< ::MBG_USB_LOCK_FLAG_MSKS
+ uint8_t reserved_1[3];
+ uint32_t reserved_2[3];
+
+} MBG_USB_LOCK_SETTINGS;
+
+#define _mbg_swab_usb_lock_settings( _p ) do {} while ( 0 )
+
+
+typedef struct
+{
+ MBG_USB_LOCK_SETTINGS settings;
+ uint8_t supp_flags; ///< ::MBG_USB_LOCK_FLAG_MSKS
+ uint8_t reserved_1[3];
+ uint32_t reserved_2[3];
+
+} MBG_USB_LOCK_INFO;
+
+#define _mbg_swab_usb_lock_info( _p ) \
+do \
+{ \
+ _mbg_swab_usb_lock_settings( _p ); \
+} while ( 0 )
+
+
+typedef struct
+{
+ uint8_t flags; ///< ::MBG_USB_LOCK_FLAG_MSKS
+ uint8_t reserved_1[3];
+ uint32_t reserved_2[3];
+
+} MBG_USB_LOCK_STATUS;
+
+#define _mbg_swab_usb_lock_status( _p ) do {} while ( 0 )
+
+
+/** @} defgroup group_usb_lock */
+
+
#if defined( _USING_BYTE_ALIGNMENT )
#pragma pack() // set default alignment
#undef _USING_BYTE_ALIGNMENT
diff --git a/mbglib/common/gpsutils.c b/mbglib/common/gpsutils.c
index c5083ef..2388df3 100755
--- a/mbglib/common/gpsutils.c
+++ b/mbglib/common/gpsutils.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: gpsutils.c 1.9 2013/01/30 16:10:08 martin REL_M $
+ * $Id: gpsutils.c 1.9.1.7 2016/08/11 12:45:54 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,16 @@
*
* -----------------------------------------------------------------------
* $Log: gpsutils.c $
+ * Revision 1.9.1.7 2016/08/11 12:45:54 martin
+ * Revision 1.9.1.6 2016/08/09 15:56:50Z martin
+ * Fixed format bug.
+ * Revision 1.9.1.5 2016/07/22 09:57:11 martin
+ * Quieted some compiler warninges.
+ * Revision 1.9.1.4 2015/09/07 09:19:58 martin
+ * Revision 1.9.1.3 2015/08/27 16:24:41 martin
+ * Revision 1.9.1.2 2015/08/25 15:34:48 martin
+ * Use save string functions from str_util.c.
+ * Revision 1.9.1.1 2015/08/21 14:21:57 martin
* Revision 1.9 2013/01/30 16:10:08 martin
* Exclude some code from compiling by default, and
* thus don't require pcpslstr.h by default.
@@ -38,32 +48,71 @@
#include <gpsutils.h>
#undef _GPSUTILS
-#if !defined( USE_SPRINTF )
- #define USE_SPRINTF 0
+#if defined( USE_SPRINTF )
+ #error USE_SPRINTF was obsoleted by USE_SNPRINTF. Please update project settings.
#endif
-#if USE_SPRINTF
- #include <pcpslstr.h>
+#if !defined( USE_SNPRINTF )
+ #define USE_SNPRINTF 0
+#endif
+
+#if !defined( _USE_GPSUTILS_FULL )
+ #if defined( MBG_TGT_WIN32 ) && defined( __BORLANDC__ )
+ #define _USE_GPSUTILS_FULL 1
+ #else
+ #define _USE_GPSUTILS_FULL 0
+ #endif
+#endif
+
+#if USE_SNPRINTF
+ #include <str_util.h>
+// #include <pcpslstr.h>
+#define DEG "deg"
+#endif
+
+#if _USE_GPSUTILS_FULL
+ #include <str_util.h>
+ #include <math.h>
#endif
#include <stdio.h>
#include <string.h>
-#include <math.h>
-#define _eos( _s ) ( &(_s)[strlen( _s )] )
+#if USE_SNPRINTF || _USE_GPSUTILS_FULL
+
+static const char str_na[] = "N/A";
+
+#endif
+
/*HDR*/
-void swap_double( double *d )
+/**
+ * @brief Swap the bytes of a single variable of type "double"
+ *
+ * The memory layout of a "double" on Meinberg bus level devices
+ * and computers usually differs. This function can be used to
+ * fix this and is usually called from inside API functions,
+ * if required.
+ *
+ * @param[in,out] p Pointer to a "double" to be swapped
+ *
+ * @see ::swap_eph_doubles
+ * @see ::swap_alm_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_iono_doubles
+ * @see ::swap_pos_doubles
+ */
+void swap_double( double *p )
{
uint16_t *wp1;
uint16_t *wp2;
uint16_t w;
int i;
- wp1 = (uint16_t *) d;
- wp2 = ( (uint16_t *) d ) + 3;
+ wp1 = (uint16_t *) p;
+ wp2 = ( (uint16_t *) p ) + 3;
for ( i = 0; i < 2; i++ )
{
@@ -74,158 +123,284 @@ void swap_double( double *d )
wp2--;
}
-} /* swap_double */
+} // swap_double
/*HDR*/
-void swap_eph_doubles( EPH *ephp )
+/**
+ * @brief Swap the "double" fields in an ::EPH structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to an ::EPH structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_alm_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_iono_doubles
+ * @see ::swap_pos_doubles
+ */
+void swap_eph_doubles( EPH *p )
{
- swap_double( &ephp->sqrt_A );
- swap_double( &ephp->e );
- swap_double( &ephp->M0 );
- swap_double( &ephp->omega );
- swap_double( &ephp->i0 );
- swap_double( &ephp->OMEGA0 );
- swap_double( &ephp->OMEGADOT );
-
- swap_double( &ephp->deltan );
- swap_double( &ephp->idot );
-
- swap_double( &ephp->crc );
- swap_double( &ephp->crs );
- swap_double( &ephp->cuc );
- swap_double( &ephp->cus );
- swap_double( &ephp->cic );
- swap_double( &ephp->cis );
-
- swap_double( &ephp->af0 );
- swap_double( &ephp->af1 );
- swap_double( &ephp->af2 );
-
- swap_double( &ephp->tgd );
+ swap_double( &p->sqrt_A );
+ swap_double( &p->e );
+ swap_double( &p->M0 );
+ swap_double( &p->omega );
+ swap_double( &p->i0 );
+ swap_double( &p->OMEGA0 );
+ swap_double( &p->OMEGADOT );
+
+ swap_double( &p->deltan );
+ swap_double( &p->idot );
+
+ swap_double( &p->crc );
+ swap_double( &p->crs );
+ swap_double( &p->cuc );
+ swap_double( &p->cus );
+ swap_double( &p->cic );
+ swap_double( &p->cis );
+
+ swap_double( &p->af0 );
+ swap_double( &p->af1 );
+ swap_double( &p->af2 );
+
+ swap_double( &p->tgd );
} /* swap_eph_doubles */
/*HDR*/
-void swap_alm_doubles( ALM *almp )
+/**
+ * @brief Swap the "double" fields in an ::ALM structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to an ::ALM structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_eph_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_iono_doubles
+ * @see ::swap_pos_doubles
+ */
+void swap_alm_doubles( ALM *p )
{
- swap_double( &almp->sqrt_A );
- swap_double( &almp->e );
- swap_double( &almp->deltai );
- swap_double( &almp->OMEGA0 );
- swap_double( &almp->OMEGADOT );
- swap_double( &almp->omega );
- swap_double( &almp->M0 );
- swap_double( &almp->af0 );
- swap_double( &almp->af1 );
+ swap_double( &p->sqrt_A );
+ swap_double( &p->e );
+ swap_double( &p->deltai );
+ swap_double( &p->OMEGA0 );
+ swap_double( &p->OMEGADOT );
+ swap_double( &p->omega );
+ swap_double( &p->M0 );
+ swap_double( &p->af0 );
+ swap_double( &p->af1 );
} /* swap_alm_doubles */
/*HDR*/
-void swap_utc_doubles( UTC *utcp )
+/**
+ * @brief Swap the "double" fields in a ::UTC structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to a ::UTC structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_eph_doubles
+ * @see ::swap_alm_doubles
+ * @see ::swap_iono_doubles
+ * @see ::swap_pos_doubles
+ */
+void swap_utc_doubles( UTC *p )
{
- swap_double( &utcp->A0 );
- swap_double( &utcp->A1 );
+ swap_double( &p->A0 );
+ swap_double( &p->A1 );
} /* swap_utc_doubles */
/*HDR*/
-void swap_iono_doubles( IONO *ionop )
+/**
+ * @brief Swap the "double" fields in a ::IONO structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to a ::IONO structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_eph_doubles
+ * @see ::swap_alm_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_pos_doubles
+ */
+void swap_iono_doubles( IONO *p )
{
- swap_double( &ionop->alpha_0 );
- swap_double( &ionop->alpha_1 );
- swap_double( &ionop->alpha_2 );
- swap_double( &ionop->alpha_3 );
+ swap_double( &p->alpha_0 );
+ swap_double( &p->alpha_1 );
+ swap_double( &p->alpha_2 );
+ swap_double( &p->alpha_3 );
- swap_double( &ionop->beta_0 );
- swap_double( &ionop->beta_1 );
- swap_double( &ionop->beta_2 );
- swap_double( &ionop->beta_3 );
+ swap_double( &p->beta_0 );
+ swap_double( &p->beta_1 );
+ swap_double( &p->beta_2 );
+ swap_double( &p->beta_3 );
} /* swap_iono_doubles */
/*HDR*/
-void swap_pos_doubles( POS *posp )
+/**
+ * @brief Swap the "double" fields in a ::POS structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to a ::POS structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_eph_doubles
+ * @see ::swap_alm_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_iono_doubles
+ */
+void swap_pos_doubles( POS *p )
{
int i;
for ( i = 0; i < N_XYZ; i++ )
- swap_double( &posp->xyz[i] );
+ swap_double( &p->xyz[i] );
for ( i = 0; i < N_LLA; i++ )
- swap_double( &posp->lla[i] );
+ swap_double( &p->lla[i] );
- swap_double( &posp->longitude.sec );
- swap_double( &posp->latitude.sec );
+ swap_double( &p->longitude.sec );
+ swap_double( &p->latitude.sec );
} /* swap_pos_doubles */
-#if USE_SPRINTF
+#if USE_SNPRINTF
/*HDR*/
-void sprint_dms( char *s, DMS *pdms, int prec )
+/**
+ * @brief Print the ::DMS part of a geo position into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p Pointer to a ::DMS structure to be printed
+ * @param[in] prec Precision, i.e. number of fractions of the seconds
+ *
+ * @return Length of the string in the buffer
+ *
+ * @see snprint_dms
+ * @see snprint_alt
+ * @see snprint_pos_geo
+ * @see snprint_fixed_freq
+ */
+size_t snprint_dms( char *s, size_t max_len, const DMS *p, int prec )
{
- sprintf( s, "%c %i" DEG "%02i'%02.*f\"",
- pdms->prefix,
- pdms->deg,
- pdms->min,
- prec,
- pdms->sec
- );
+ size_t n = snprintf_safe( s, max_len, "%c %i" DEG "%02i'%02.*f\"",
+ p->prefix, p->deg, p->min,
+ prec, p->sec );
+
+ return n;
-} /* sprint_dms */
+} // snprint_dms
/*HDR*/
-void sprint_alt( char *s, double alt )
+/**
+ * @brief Print the altitude part of a geo position into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] alt The altitude value to be printed, in [m]
+ *
+ * @return Length of the string in the buffer
+ *
+ * @see snprint_dms
+ * @see snprint_pos_geo
+ * @see snprint_fixed_freq
+ */
+size_t snprint_alt( char *s, size_t max_len, double alt )
{
- sprintf( s, "%.0fm", alt );
+ size_t n = snprintf_safe( s, max_len, "%.0fm", alt );
-} /* sprint_dms */
+ return n;
+
+} // snprint_alt
/*HDR*/
-void sprint_pos_geo( char *s, POS *ppos, const char *sep, int prec )
+/**
+ * @brief Print a geo position in ::POS format into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p Pointer to a ::POS structure to be printed
+ * @param[in] sep Separator character for the ::DMS part
+ * @param[in] prec Precision, i.e. number of fractions of the seconds of the ::DMS part
+ *
+ * @return Length of the string in the buffer
+ *
+ * @see snprint_dms
+ * @see snprint_alt
+ * @see snprint_fixed_freq
+ */
+size_t snprint_pos_geo( char *s, size_t max_len, const POS *p, char sep, int prec )
{
- if ( ppos->lla[LON] && ppos->lla[LAT] && ppos->lla[ALT] )
+ size_t n = 0;
+
+ if ( p->lla[LON] && p->lla[LAT] && p->lla[ALT] )
{
- sprint_dms( s, &ppos->latitude, prec );
- strcat( s, sep );
- sprint_dms( _eos( s ), &ppos->longitude, prec );
- strcat( s, sep );
- sprint_alt( _eos( s ), ppos->lla[ALT] );
+ n += snprint_dms( &s[n], max_len - n, &p->latitude, prec );
+ n += snprintf_safe( &s[n], max_len - n, "%c", sep );
+ n += snprint_dms( &s[n], max_len - n, &p->longitude, prec );
+ n += snprintf_safe( &s[n], max_len - n, "%c", sep );
+ n += snprint_alt( &s[n], max_len - n, p->lla[ALT] );
}
else
- strcpy( s, "N/A" );
+ n = sn_cpy_str_safe( s, max_len, str_na );
-} /* sprint_pos_geo */
+ return n;
-#endif
+} // sprint_pos_geo
+#endif // USE_SNPRINTF
-#if defined( MBG_TGT_WIN32 ) && defined( __BORLANDC__ )
+
+#if _USE_GPSUTILS_FULL
/*HDR*/
-void sprint_fixed_freq( char *s, FIXED_FREQ_INFO *p_ff )
+/**
+ * @brief Print a formatted ::FIXED_FREQ_INFO into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_ff Pointer to a ::FIXED_FREQ_INFO structure to be printed
+ *
+ * @return Length of the string in the buffer
+ *
+ * @see snprint_dms
+ * @see snprint_alt
+ * @see snprint_pos_geo
+ */
+size_t snprint_fixed_freq( char *s, size_t max_len, FIXED_FREQ_INFO *p_ff )
{
double freq;
int range;
ushort unit;
ushort format;
+ size_t n = 0;
// Before re-calculating frequency, range is the base 10 exponent
// to the frequency value which is represented in kHz.
@@ -298,19 +473,20 @@ void sprint_fixed_freq( char *s, FIXED_FREQ_INFO *p_ff )
// calculate display value
freq = freq / pow( 10, ( ( 3 * unit ) - 3 ) );
- sprintf( s, fmt_str[format], freq, unit_str[unit] );
- return;
+ n = snprintf_safe( s, max_len, fmt_str[format], freq, unit_str[unit] );
}
else
{
// out of range display fequency in Hz
- sprintf( s, "%lfHz", freq );
+ n = snprintf_safe( s, max_len, "%fHz", freq );
}
}
else
- strcpy( s, "N/A" );
+ n = sn_cpy_str_safe( s, max_len, str_na );
+
+ return n;
-} /* sprint_fixed_freq */
+} // snprint_fixed_freq
-#endif // defined( MBG_TGT_WIN32 ) && defined( __BORLANDC__ )
+#endif // _USE_GPSUTILS_FULL
diff --git a/mbglib/common/gpsutils.h b/mbglib/common/gpsutils.h
index fdac213..6fe959a 100755
--- a/mbglib/common/gpsutils.h
+++ b/mbglib/common/gpsutils.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: gpsutils.h 1.7 2010/07/15 09:32:09 martin REL_M $
+ * $Id: gpsutils.h 1.7.1.4 2016/08/11 13:50:01 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,12 @@
*
* -----------------------------------------------------------------------
* $Log: gpsutils.h $
+ * Revision 1.7.1.4 2016/08/11 13:50:01 martin
+ * Include stddef.h.
+ * Revision 1.7.1.3 2015/08/27 16:24:41Z martin
+ * Revision 1.7.1.2 2015/08/25 15:34:48 martin
+ * Use save string functions from str_util.c.
+ * Revision 1.7.1.1 2015/08/21 14:22:06 martin
* Revision 1.7 2010/07/15 09:32:09 martin
* Use DEG character definition from pcpslstr.h.
* Revision 1.6 2005/02/18 10:32:33Z martin
@@ -34,6 +40,8 @@
#include <mbggeo.h>
+#include <stddef.h>
+
#ifdef _GPSUTILS
#define _ext
@@ -57,16 +65,163 @@ extern "C" {
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
- void swap_double( double *d ) ;
- void swap_eph_doubles( EPH *ephp ) ;
- void swap_alm_doubles( ALM *almp ) ;
- void swap_utc_doubles( UTC *utcp ) ;
- void swap_iono_doubles( IONO *ionop ) ;
- void swap_pos_doubles( POS *posp ) ;
- void sprint_dms( char *s, DMS *pdms, int prec ) ;
- void sprint_alt( char *s, double alt ) ;
- void sprint_pos_geo( char *s, POS *ppos, const char *sep, int prec ) ;
- void sprint_fixed_freq( char *s, FIXED_FREQ_INFO *p_ff ) ;
+ /**
+ * @brief Swap the bytes of a single variable of type "double"
+ *
+ * The memory layout of a "double" on Meinberg bus level devices
+ * and computers usually differs. This function can be used to
+ * fix this and is usually called from inside API functions,
+ * if required.
+ *
+ * @param[in,out] p Pointer to a "double" to be swapped
+ *
+ * @see ::swap_eph_doubles
+ * @see ::swap_alm_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_iono_doubles
+ * @see ::swap_pos_doubles
+ */
+ void swap_double( double *p ) ;
+
+ /**
+ * @brief Swap the "double" fields in an ::EPH structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to an ::EPH structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_alm_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_iono_doubles
+ * @see ::swap_pos_doubles
+ */
+ void swap_eph_doubles( EPH *p ) ;
+
+ /**
+ * @brief Swap the "double" fields in an ::ALM structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to an ::ALM structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_eph_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_iono_doubles
+ * @see ::swap_pos_doubles
+ */
+ void swap_alm_doubles( ALM *p ) ;
+
+ /**
+ * @brief Swap the "double" fields in a ::UTC structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to a ::UTC structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_eph_doubles
+ * @see ::swap_alm_doubles
+ * @see ::swap_iono_doubles
+ * @see ::swap_pos_doubles
+ */
+ void swap_utc_doubles( UTC *p ) ;
+
+ /**
+ * @brief Swap the "double" fields in a ::IONO structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to a ::IONO structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_eph_doubles
+ * @see ::swap_alm_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_pos_doubles
+ */
+ void swap_iono_doubles( IONO *p ) ;
+
+ /**
+ * @brief Swap the "double" fields in a ::POS structure
+ *
+ * See comments for ::swap_double
+ *
+ * @param[in,out] p Pointer to a ::POS structure to be converted
+ *
+ * @see ::swap_double
+ * @see ::swap_eph_doubles
+ * @see ::swap_alm_doubles
+ * @see ::swap_utc_doubles
+ * @see ::swap_iono_doubles
+ */
+ void swap_pos_doubles( POS *p ) ;
+
+ /**
+ * @brief Print the ::DMS part of a geo position into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p Pointer to a ::DMS structure to be printed
+ * @param[in] prec Precision, i.e. number of fractions of the seconds
+ *
+ * @return Length of the string in the buffer
+ *
+ * @see snprint_dms
+ * @see snprint_alt
+ * @see snprint_pos_geo
+ * @see snprint_fixed_freq
+ */
+ size_t snprint_dms( char *s, size_t max_len, const DMS *p, int prec ) ;
+
+ /**
+ * @brief Print the altitude part of a geo position into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] alt The altitude value to be printed, in [m]
+ *
+ * @return Length of the string in the buffer
+ *
+ * @see snprint_dms
+ * @see snprint_pos_geo
+ * @see snprint_fixed_freq
+ */
+ size_t snprint_alt( char *s, size_t max_len, double alt ) ;
+
+ /**
+ * @brief Print a geo position in ::POS format into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p Pointer to a ::POS structure to be printed
+ * @param[in] sep Separator character for the ::DMS part
+ * @param[in] prec Precision, i.e. number of fractions of the seconds of the ::DMS part
+ *
+ * @return Length of the string in the buffer
+ *
+ * @see snprint_dms
+ * @see snprint_alt
+ * @see snprint_fixed_freq
+ */
+ size_t snprint_pos_geo( char *s, size_t max_len, const POS *p, char sep, int prec ) ;
+
+ /**
+ * @brief Print a formatted ::FIXED_FREQ_INFO into a string buffer
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_ff Pointer to a ::FIXED_FREQ_INFO structure to be printed
+ *
+ * @return Length of the string in the buffer
+ *
+ * @see snprint_dms
+ * @see snprint_alt
+ * @see snprint_pos_geo
+ */
+ size_t snprint_fixed_freq( char *s, size_t max_len, FIXED_FREQ_INFO *p_ff ) ;
+
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/lan_util.c b/mbglib/common/lan_util.c
index bdda51c..19cbcfc 100755
--- a/mbglib/common/lan_util.c
+++ b/mbglib/common/lan_util.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: lan_util.c 1.7 2013/05/22 16:49:42 martin REL_M $
+ * $Id: lan_util.c 1.11.1.14 2017/04/10 13:05:16 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,52 @@
*
* -----------------------------------------------------------------------
* $Log: lan_util.c $
+ * Revision 1.11.1.14 2017/04/10 13:05:16 martin
+ * Fixed some compiler warnings.
+ * Revision 1.11.1.13 2017/02/23 15:24:22Z martin
+ * Fixed macro definition syntax to avoid clang compiler warnings.
+ * Revision 1.11.1.12 2016/10/31 17:39:47 martin
+ * Only return standard MBG_RETURN_CODES.
+ * Removed definitions of old MBG_LU_... return codes.
+ * Renamed check_octets_not_all_zero() to octets_are_all_zero(), which returns a bool now.
+ * Renamed check_mac_addr_not_all_zero() to mac_addr_all_zero(), which returns a bool now.
+ * Removed get_port_mac_addr_check().
+ * Updated doxygen comments.
+ * Revision 1.11.1.11 2016/09/22 12:25:26 thomas-b
+ * Fixed compiler warning for uninitialized vars
+ * Revision 1.11.1.10 2016/08/10 12:25:54 martin
+ * Check for MBG_TGT_POSIX instead of MBG_TGT_UNIX.
+ * Revision 1.11.1.9 2016/08/09 07:10:22 martin
+ * *** empty log message ***
+ * Revision 1.11.1.8 2015/12/01 11:35:31 martin
+ * Doxygen fixes.
+ * Revision 1.11.1.7 2015/11/11 18:16:08 martin
+ * New function snprint_ptp_clock_id().
+ * Revision 1.11.1.6 2015/11/04 17:06:35Z martin
+ * *** empty log message ***
+ * Revision 1.11.1.5 2015/09/17 10:06:30 martin
+ * Revision 1.11.1.4 2015/08/31 10:26:26Z martin
+ * Revision 1.11.1.3 2015/08/27 16:23:16Z martin
+ * Use safe string functions from str_util.c.
+ * Cleanup.
+ * Revision 1.11.1.2 2015/04/13 15:26:50 hannes
+ * Added all function defintions for IP6.
+ * FIX: Fixed snprint_ip4_cidr_mask to behave as expected.
+ * It will concatenate the cidr mask bits to the ip address now.
+ * Revision 1.11.1.1 2015/04/02 15:28:31 hannes
+ * Started adding the ipv4 functions for ipv6.
+ * Revision 1.11 2015/04/01 14:31:14 hannes
+ * Fix: cidr_str_to_ip4_addr_and_net_mask: Defaults correctly to
+ * netmask 0.0.0.0 (/0) for no CIDR extension in cidr_str.
+ * Revision 1.10 2014/10/17 12:45:48 martin
+ * Let str_to_ip4_addr() return 0 if an empty string has been passed.
+ * Revision 1.9 2014/09/24 08:31:00 martin
+ * Exclude get_ip4_gateway() from build if USE_MBG_TSU is defined.
+ * Fixed some compiler warnings.
+ * Added and modified some comments.
+ * Revision 1.8 2013/10/02 07:19:13 martin
+ * New function get_port_intf_idx.
+ * Fixed naming.of local netlink support functions.
* Revision 1.7 2013/05/22 16:49:42 martin
* Fixed some return codes.
* Revision 1.6 2013/03/19 10:24:51 martin
@@ -36,12 +82,17 @@
#include <lan_util.h>
#undef _LAN_UTIL
+#include <words.h>
+#include <str_util.h>
+#include <mbgerror.h>
+
#include <stdio.h>
#include <string.h>
+#include <ctype.h>
-#if defined ( MBG_TGT_UNIX )
+#if defined( MBG_TGT_POSIX )
- #if defined ( MBG_TGT_LINUX )
+ #if defined( MBG_TGT_LINUX )
#include <linux/types.h>
@@ -62,8 +113,8 @@
#endif
#include <unistd.h>
+ #include <syslog.h>
#include <sys/ioctl.h>
- #include <sys/errno.h>
#include <arpa/inet.h>
#include <netinet/in.h>
@@ -82,7 +133,11 @@
#if !defined( DEBUG_NETLINK )
- #define DEBUG_NETLINK ( 0 && defined( DEBUG ) && defined( MBG_TGT_LINUX ) )
+ #if ( 0 && defined( DEBUG ) && defined( MBG_TGT_LINUX ) )
+ #define DEBUG_NETLINK 1
+ #else
+ #define DEBUG_NETLINK 0
+ #endif
#endif
@@ -92,7 +147,7 @@
#include <ptp2_cnf.h> // for mbglog() from the ARM PTP projects
#else
// to be provided by the application
- extern void mbglog( int priority, const char *fmt, ... );
+ extern __attribute__( ( format( printf, 2, 3 ) ) ) void mbglog( int priority, const char *fmt, ... );
#endif
#endif // DEBUG_NETLINK
@@ -104,7 +159,7 @@
#define MAX_IP4_ADDR_STR_SIZE 16
-#if defined ( MBG_TGT_LINUX )
+#if defined( MBG_TGT_LINUX )
struct route_info
{
@@ -117,45 +172,19 @@ struct route_info
#endif
-#if defined( __BORLANDC__ ) \
- && ( __BORLANDC__ <= 0x410 ) // BC3.1 defines 0x410 !
-
-#include <stdarg.h>
-
-// Declare a snprintf() function if not provided by the
-// build environment, though this implementation actually
-// does not check the string length ...
-
-static /*HDR*/
-int snprintf( char *s, size_t max_len, const char *fmt, ... )
-{
- int n;
- va_list arg_list;
-
- va_start( arg_list, fmt );
- n = vsprintf( s, fmt, arg_list );
- va_end( arg_list );
-
- return n;
-
-} // snprintf
-
-#endif
-
-
/*HDR*/
/**
- * @brief Count the number of sequential bits set starting from MSB
+ * @brief Count the number of sequential bits in an IPv4 net mask
*
- * E.g. for 0xC0 and 0xC1 the results are both 2 since only
- * the 2 MSBs are sequentially set.
+ * Counting starts from MSB, i.e. for 0xC0 and 0xC1 the results
+ * are both 2 since only the 2 MSBs are sequentially set.
*
- * @param p_mask The IP4 net mask
+ * @param[in] p_mask The IPv4 net mask to be evaluated
*
- * @return The number of sequential MSB bits set in val
+ * @return The number of sequential MSB bits set in *p_mask
*
- * @see ip4_net_mask_from_cidr
+ * @see ::ip4_net_mask_from_cidr
*/
int get_ip4_net_mask_bits( const IP4_ADDR *p_mask )
{
@@ -178,30 +207,30 @@ int get_ip4_net_mask_bits( const IP4_ADDR *p_mask )
/*HDR*/
/**
- * @brief Print an IPv4 address to a dotted quad format string.
+ * @brief Print an IPv4 address to a dotted quad formatted string
*
- * @param s The string buffer into which to print
- * @param max_len Maximum length of the string, i.e. size of the buffer
- * @param p_addr The IPv4 address
- * @param info An optional string which is prepended to the string, or NULL
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv4 address to be evaluated
+ * @param[in] info An optional string which is prepended to the string, or NULL
*
* @return The overall number of characters printed to the string
*
- * @see snprint_ip4_cidr_addr
- * @see str_to_ip4_addr
- * @see cidr_str_to_ip4_addr_and_net_mask
+ * @see ::snprint_ip4_cidr_addr
+ * @see ::str_to_ip4_addr
+ * @see ::cidr_str_to_ip4_addr_and_net_mask
*/
-int snprint_ip4_addr( char *s, size_t max_len, const IP4_ADDR *p_addr, const char *info )
+size_t snprint_ip4_addr( char *s, size_t max_len, const IP4_ADDR *p_addr, const char *info )
{
- int n = 0;
+ size_t n = 0;
ulong ul = *p_addr;
if ( info )
- n += snprintf( s, max_len, "%s", info );
+ n += snprintf_safe( s, max_len, "%s", info );
// Don't use byte pointers here since this is not safe
// for both little and big endian targets.
- n += snprintf( &s[n], max_len - n, "%lu.%lu.%lu.%lu",
+ n += snprintf_safe( &s[n], max_len - n, "%u.%u.%u.%u",
BYTE_3( ul ), BYTE_2( ul ),
BYTE_1( ul ), BYTE_0( ul )
);
@@ -213,35 +242,33 @@ int snprint_ip4_addr( char *s, size_t max_len, const IP4_ADDR *p_addr, const cha
/*HDR*/
/**
- * @brief Print an IPv4 address plus net mask to string in CIDR notation.
+ * @brief Print an IPv4 address plus net mask in CIDR notation to a string
*
* The printed CIDR string is something like "172.16.3.250/24"
*
- * @param s The string buffer into which to print
- * @param max_len Maximum length of the string, i.e. size of the buffer
- * @param p_addr The IPv4 address
- * @param p_mask The IPv4 net mask
- * @param info An optional string which is prepended to the string, or NULL
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv4 address to be evaluated
+ * @param[in] p_mask The associated IPv4 net mask
+ * @param[in] info An optional string which is prepended to the string, or NULL
*
* @return The overall number of characters printed to the string
*
- * @see snprint_ip4_addr
- * @see str_to_ip4_addr
- * @see cidr_str_to_ip4_addr_and_net_mask
+ * @see ::snprint_ip4_addr
+ * @see ::str_to_ip4_addr
+ * @see ::cidr_str_to_ip4_addr_and_net_mask
*/
-int snprint_ip4_cidr_addr( char *s, size_t max_len, const IP4_ADDR *p_addr,
- const IP4_ADDR *p_mask, const char *info )
+size_t snprint_ip4_cidr_addr( char *s, size_t max_len, const IP4_ADDR *p_addr,
+ const IP4_ADDR *p_mask, const char *info )
{
int cidr_mask_bits;
- IP4_ADDR normalized_addr = ip4_net_part_from_addr( p_addr, p_mask );
-
- int n = snprint_ip4_addr( s, max_len, &normalized_addr, info );
+ size_t n = snprint_ip4_addr( s, max_len, p_addr, info );
cidr_mask_bits = get_ip4_net_mask_bits( p_mask );
if ( ( cidr_mask_bits >= MIN_IP4_CIDR_NETMASK_BITS ) &&
( cidr_mask_bits <= MAX_IP4_CIDR_NETMASK_BITS ) )
- n += snprintf( &s[n], max_len - n, "/%i", cidr_mask_bits );
+ n += snprintf_safe( &s[n], max_len - n, "/%i", cidr_mask_bits );
return n;
@@ -251,49 +278,54 @@ int snprint_ip4_cidr_addr( char *s, size_t max_len, const IP4_ADDR *p_addr,
/*HDR*/
/**
- * @brief Convert a string to an IP4_ADDR.
+ * @brief Convert a string to an ::IP4_ADDR
*
- * @param p_addr Pointer to the IP4_ADDR variable, or NULL, in which case this
- * function can be used to check if the string is formally correct.
- * @param s The string to be converted
+ * If output parameter is specified as NULL then this function
+ * can be used to check if the IPv4 address string is formally correct.
*
- * @return >= 0 on success, number of characters evaluated from the input string
- * -1 if invalid number found in string
- * -2 if separator is not a dot '.'
+ * @param[out] p_addr Pointer to an ::IP4_ADDR variable to be filled, or NULL
+ * @param[in] s An IPv4 address string to be converted
*
- * @see snprint_ip4_addr
- * @see snprint_ip4_cidr_addr
- * @see cidr_str_to_ip4_addr_and_net_mask
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
+ *
+ * @see ::snprint_ip4_addr
+ * @see ::snprint_ip4_cidr_addr
+ * @see ::cidr_str_to_ip4_addr_and_net_mask
*/
int str_to_ip4_addr( IP4_ADDR *p_addr, const char *s )
{
IP4_ADDR tmp_ip4_addr = 0;
- const char *cp;
+ const char *cp = s;
int i;
- for ( i = 0, cp = (char *) s; ; )
+ if ( strlen( s ) )
{
- unsigned long ul = strtoul( (char *) cp, (char **) &cp, 10 );
+ for ( i = 0; ; )
+ {
+ unsigned long ul = strtoul( (char *) cp, (char **) &cp, 10 );
- if ( ul > 255 ) // invalid number
- return -1;
+ if ( ul > 0xFFUL ) // invalid number
+ return MBG_ERR_INV_PARM;
- tmp_ip4_addr |= ul << ( 8 * (3 - i) );
+ tmp_ip4_addr |= ul << ( 8 * (3 - i) );
- if ( ++i >= 4 )
- break; // done
+ if ( ++i >= 4 )
+ break; // done
- if ( *cp != '.' )
- return -2; // invalid string format, dot expected
+ if ( *cp != '.' )
+ return MBG_ERR_INV_PARM; // invalid string format, dot expected
- cp++; // skip dot
+ cp++; // skip dot
+ }
}
if ( p_addr )
*p_addr = tmp_ip4_addr;
// success: return the number of evaluated chars
- return cp - s;
+ return (int) ( cp - s );
} // str_to_ip4_addr
@@ -301,22 +333,24 @@ int str_to_ip4_addr( IP4_ADDR *p_addr, const char *s )
/*HDR*/
/**
- * @brief Convert a string in CIDR notation to an IP4_ADDR and net mask.
- *
- * @param p_addr Pointer to an IP4_ADDR variable for the IP4 address,
- * or NULL, in which case this function can be used
- * to check if the string is formally correct.
- * @param p_mask Pointer to an IP4_ADDR variable for the net mask,
- * or NULL, in which case this function can be used
- * to check if the string is formally correct.
- * @param cidr_str The string to be converted, in CIDR format, e.g. "172.16.3.250/24"
- *
- * @return >= 0 on success, number of characters evaluated from the input string
- * one of the ::MBG_LU_CODES on error
- *
- * @see snprint_ip4_addr
- * @see snprint_ip4_cidr_addr
- * @see str_to_ip4_addr
+ * @brief Convert a string in CIDR notation to an ::IP4_ADDR and net mask
+ *
+ * If output parameters are specified as NULL then this function
+ * can be used to check if the CIDR string is formally correct.
+ *
+ * @param[out] p_addr Pointer to an ::IP4_ADDR variable to be filled with
+ * the IPv4 address, or NULL
+ * @param[out] p_mask Pointer to an ::IP4_ADDR variable to be filled with
+ * the IPv4 net mask, or NULL
+ * @param[in] cidr_str The string to be converted, in CIDR format, e.g. "172.16.3.250/24"
+ *
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
+ *
+ * @see ::snprint_ip4_addr
+ * @see ::snprint_ip4_cidr_addr
+ * @see ::str_to_ip4_addr
*/
int cidr_str_to_ip4_addr_and_net_mask( IP4_ADDR *p_addr, IP4_ADDR *p_mask,
const char *cidr_str )
@@ -327,14 +361,14 @@ int cidr_str_to_ip4_addr_and_net_mask( IP4_ADDR *p_addr, IP4_ADDR *p_mask,
int l;
int rc = str_to_ip4_addr( p_addr, cidr_str );
- if ( rc < 0 ) // return current error
+ if ( mbg_rc_is_error( rc ) )
return rc;
- l = strlen( cidr_str );
+ l = (int) strlen( cidr_str );
if ( l < rc ) // input string too short
- return MBG_LU_ERR_FMT;
+ return MBG_ERR_INV_PARM;
cp = &cidr_str[rc];
@@ -342,14 +376,14 @@ int cidr_str_to_ip4_addr_and_net_mask( IP4_ADDR *p_addr, IP4_ADDR *p_mask,
if ( *cp == 0 ) // end of string
{
// The string has no CIDR extension, so
- // assume "/0", i.e. host mask 255.255.255.255;
- mask = (IP4_ADDR) -1;
+ // assume "/0", i.e. host mask 0.0.0.0;
+ mask = (IP4_ADDR) 0;
goto done;
}
if ( *cp != '/' )
- return MBG_LU_ERR_FMT;
+ return MBG_ERR_INV_PARM;
cp++;
@@ -357,7 +391,7 @@ int cidr_str_to_ip4_addr_and_net_mask( IP4_ADDR *p_addr, IP4_ADDR *p_mask,
if ( ( cidr_mask_bits < MIN_IP4_CIDR_NETMASK_BITS ) ||
( cidr_mask_bits > MAX_IP4_CIDR_NETMASK_BITS ) )
- return MBG_LU_ERR_RANGE;
+ return MBG_ERR_RANGE;
mask = ip4_net_mask_from_cidr( (int) cidr_mask_bits );
@@ -367,7 +401,7 @@ done:
*p_mask = mask;
// success: return the number of evaluated chars
- return cp - cidr_str;
+ return (int) ( cp - cidr_str );
} // cidr_str_to_ip4_addr_and_net_mask
@@ -375,36 +409,605 @@ done:
/*HDR*/
/**
- * @brief Print a MAC ID or similar array of octets to a string.
+ * @brief Count the number of sequential bits in an IPv6 net mask
+ *
+ * Counting starts from MSB, i.e. for 0xC0 and 0xC1 the results
+ * are both 2 since only the 2 MSBs are sequentially set.
+ *
+ * @param[in] p_mask The IPv6 net mask to be evaluated
+ *
+ * @return The number of sequential MSB bits set in *p_mask
+ *
+ * @see ::ip6_net_mask_from_cidr
+ */
+int get_ip6_net_mask_bits( const IP6_ADDR *p_mask )
+{
+ int i;
+ int cnt = 0;
+ uint8_t msb_mask = IP6_MSB_MASK;
+
+ for ( i = IP6_ADDR_BYTES - 1 ; i >= 0; i-- )
+ {
+ if ( p_mask->b[i] == 0xff )
+ cnt += 8;
+ else
+ {
+ for ( ; cnt < MAX_IP6_CIDR_NETMASK_BITS; cnt++ )
+ {
+ if ( ( p_mask->b[i] & msb_mask ) == 0 )
+ break;
+
+ msb_mask >>= 1;
+ }
+ break;
+ }
+ }
+
+ return cnt;
+
+} // get_ip6_net_mask_bits
+
+
+
+/*HDR*/
+/**
+ * @brief Print an IPv6 address in optimized format to a string
*
- * @param s The string buffer into which to print
- * @param max_len Maximum length of the string, i.e. size of the buffer
- * @param octets An array of octets
- * @param num_octets The number of octets to be printed from the array
- * @param sep The separator printed between the bytes, or 0
- * @param info An optional string which is prepended to the output, or NULL
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv6 address to be evaluated
+ * @param[in] info An optional string which is prepended to the string, or NULL
+ *
+ * @return The overall number of characters printed to the string
+ *
+ * @see ::snprint_ip6_cidr_addr
+ * @see ::snprint_ip6_cidr_mask_addr
+ * @see ::str_to_ip6_addr
+ * @see ::cidr_str_to_ip6_addr_and_cidr_bits
+ * @see ::cidr_str_to_ip6_addr_and_net_mask
+ */
+size_t snprint_ip6_addr( char *s, size_t max_len, const IP6_ADDR *p_addr, const char *info )
+{
+ // Copied from inet_ntop.c, and reversed byte order
+
+ IP6_ADDR_STR tmp;
+ char *tp;
+ #define NUM_WORDS ( (int) ( sizeof( IP6_ADDR_STR ) / sizeof( uint16_t ) ) )
+ uint16_t words[NUM_WORDS] = { 0 };
+ int i;
+ size_t n = 0;
+ struct
+ {
+ int base;
+ int len;
+ } best = { 0 }, cur = { 0 };
+
+ /*
+ * Preprocess:
+ * Copy the input (bytewise) array into a wordwise array.
+ * Find the longest run of 0x00's in p_addr->b[] for :: shorthanding.
+ */
+ for ( i = IP6_ADDR_BYTES - 1; i >= 0; i-- )
+ words[(IP6_ADDR_BYTES - 1 - i) / 2] |= (p_addr->b[i] << ((1 - ((IP6_ADDR_BYTES - 1 - i) % 2)) << 3));
+
+ best.base = -1;
+ cur.base = -1;
+
+ for ( i = 0; i < NUM_WORDS; i++ )
+ {
+ if ( words[i] == 0 )
+ {
+ if ( cur.base == -1 )
+ cur.base = i, cur.len = 1;
+ else
+ cur.len++;
+ }
+ else
+ {
+ if ( cur.base != -1 )
+ {
+ if ( best.base == -1 || cur.len > best.len )
+ best = cur;
+
+ cur.base = -1;
+ }
+ }
+ }
+
+ if ( cur.base != -1 )
+ {
+ if ( best.base == -1 || cur.len > best.len )
+ best = cur;
+ }
+
+ if ( best.base != -1 && best.len < 2 )
+ best.base = -1;
+
+ // Format the result.
+
+ tp = tmp;
+
+ for ( i = 0; i < NUM_WORDS; i++ )
+ {
+ /* Are we inside the best run of 0x00's? */
+ if ( best.base != -1 && i >= best.base && i < ( best.base + best.len ) )
+ {
+ if (i == best.base)
+ *tp++ = ':';
+
+ continue;
+ }
+
+ /* Are we following an initial run of 0x00s or any real hex? */
+ if ( i != 0 )
+ *tp++ = ':';
+
+ /* Is this address an encapsulated IPv4? */
+ if ( i == 6 && best.base == 0 && ( best.len == 6 || ( best.len == 5 && words[5] == 0xffff ) ) )
+ return MBG_ERR_INV_PARM; // we don't support ecapsulated IPv4
+
+ sprintf( tp, "%x", words[i] );
+ tp += strlen( tp );
+ }
+
+ /* Was it a trailing run of 0x00's? */
+ if ( best.base != -1 && ( best.base + best.len ) == NUM_WORDS )
+ *tp++ = ':';
+
+ *tp++ = '\0';
+
+ /*
+ * Check for overflow, copy, and we're done.
+ */
+ if ( ( tp - tmp ) > (int) max_len )
+ return MBG_ERR_OVERFLOW;
+
+ if ( info )
+ n += snprintf_safe( s, max_len, "%s", info );
+
+ n += snprintf_safe( &s[n], max_len - n, "%s", tmp );
+
+ return n;
+
+ #undef NUM_WORDS
+
+} // snprint_ip6_addr
+
+
+
+/*HDR*/
+/**
+ * @brief Print an IPv6 address plus net mask to string in CIDR notation
+ *
+ * The printed CIDR string is something like "2001:0DB8:0:CD30:EF45::/64"
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv6 address to be evaluated
+ * @param[in] p_mask The associated IPv6 net mask
+ * @param[in] info An optional string which is prepended to the string, or NULL
+ *
+ * @return The overall number of characters printed to the string
+ *
+ * @see ::snprint_ip6_addr
+ * @see ::snprint_ip6_cidr_mask_addr
+ * @see ::str_to_ip6_addr
+ * @see ::cidr_str_to_ip6_addr_and_cidr_bits
+ * @see ::cidr_str_to_ip6_addr_and_net_mask
+ */
+size_t snprint_ip6_cidr_addr( char *s, size_t max_len, const IP6_ADDR *p_addr,
+ const IP6_ADDR *p_mask, const char *info )
+{
+ size_t n = snprint_ip6_addr( s, max_len, p_addr, info );
+
+ int cidr_mask_bits = get_ip6_net_mask_bits( p_mask );
+
+ if ( ( cidr_mask_bits >= MIN_IP6_CIDR_NETMASK_BITS ) &&
+ ( cidr_mask_bits <= MAX_IP6_CIDR_NETMASK_BITS ) )
+ n += snprintf_safe( &s[n], max_len - n, "/%i", cidr_mask_bits );
+
+ return n;
+
+} // snprint_ip6_cidr_addr
+
+
+
+/*HDR*/
+/**
+ * @brief Print an IPv6 address plus number of net mask bits to string in CIDR notation
+ *
+ * The printed CIDR string is something like "2001:0DB8:0:CD30:EF45::/64"
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv6 address to be evaluated
+ * @param[in] cidr_mask_bits The CIDR number of bits specifying the IPv6 net mask
+ * @param[in] info An optional string which is prepended to the string, or NULL
+ *
+ * @return The overall number of characters printed to the string
+ *
+ * @see ::snprint_ip6_addr
+ * @see ::snprint_ip6_cidr_addr
+ * @see ::str_to_ip6_addr
+ * @see ::cidr_str_to_ip6_addr_and_cidr_bits
+ * @see ::cidr_str_to_ip6_addr_and_net_mask
+ */
+size_t snprint_ip6_cidr_mask_addr( char *s, size_t max_len, const IP6_ADDR *p_addr,
+ const int cidr_mask_bits, const char* info )
+{
+ size_t n;
+ IP6_ADDR mask;
+
+ ip6_net_mask_from_cidr( &mask, cidr_mask_bits );
+
+ n = snprint_ip6_addr( s, max_len, p_addr, info );
+
+ if ( ( cidr_mask_bits >= MIN_IP6_CIDR_NETMASK_BITS ) &&
+ ( cidr_mask_bits <= MAX_IP6_CIDR_NETMASK_BITS ) )
+ n += snprintf_safe( &s[n], max_len - n, "/%i", cidr_mask_bits );
+
+ return n;
+
+} // snprint_ip6_cidr_mask_addr
+
+
+
+/*HDR*/
+/**
+ * @brief Convert a string to an ::IP6_ADDR
+ *
+ * If the output parameter is specified as NULL then this function
+ * can be used to check if the string is formally correct.
+ *
+ * On success ::IP6_ADDR variable contains the IPv6 address
+ * in little endian byte order.
+ *
+ * @param[out] p_addr Pointer to the ::IP6_ADDR variable, or NULL
+ * @param[in] s A string containing an IPv6 address
+ *
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
+ *
+ * @see ::snprint_ip6_addr
+ * @see ::snprint_ip6_cidr_addr
+ * @see ::snprint_ip6_cidr_mask_addr
+ * @see ::str_to_ip6_addr
+ * @see ::cidr_str_to_ip6_addr_and_cidr_bits
+ * @see ::cidr_str_to_ip6_addr_and_net_mask
+ */
+int str_to_ip6_addr( IP6_ADDR *p_addr, const char *s )
+{
+ // copied from inet_pton.c and reversed byte order
+ IP6_ADDR tmp = { { 0 } };
+ static const char xdigits[] = "0123456789abcdef";
+ uint8_t *tp;
+ uint8_t *startp;
+ uint8_t *colonp;
+ int ch;
+ int saw_xdigit;
+ int read_cnt = 0;
+ unsigned int val;
+
+ if ( p_addr )
+ memset( p_addr, 0, sizeof( *p_addr ) ); // set IP address to ::
+
+ startp = tmp.b - 1;
+ tp = startp + sizeof( tmp );
+
+ colonp = NULL;
+
+ /* Leading :: requires some special handling. */
+ if ( *s == ':' )
+ {
+ read_cnt++;
+
+ if ( *++s != ':' )
+ return MBG_ERR_INV_PARM;
+ }
+
+ saw_xdigit = 0;
+ val = 0;
+
+ while ( ( ch = tolower( *s++ ) ) != '\0' )
+ {
+ const char *pch;
+
+ read_cnt++;
+
+ pch = strchr( xdigits, ch );
+
+ if ( pch != NULL )
+ {
+ val <<= 4;
+ val |= ( pch - xdigits );
+
+ if ( val > 0xffff ) //### TODO signed? unsigned?
+ return MBG_ERR_INV_PARM;
+
+ saw_xdigit = 1;
+ continue;
+ }
+
+ if ( ch == ':' )
+ {
+ if ( !saw_xdigit )
+ {
+ if ( colonp )
+ return MBG_ERR_INV_PARM;
+
+ colonp = tp;
+ continue;
+
+ }
+ else
+ if ( *s == '\0' )
+ return MBG_ERR_INV_PARM;
+
+ if ( tp - sizeof( uint16_t ) < startp )
+ return MBG_ERR_INV_PARM;
+
+ *tp-- = (uint8_t) ( val >> 8 ) & 0xff;
+ *tp-- = (uint8_t) val & 0xff;
+ saw_xdigit = 0;
+ val = 0;
+ continue;
+ }
+
+ if ( ch == '/' ) // cidr notation. we reached the end
+ {
+ read_cnt--;
+ break;
+ }
+
+ return MBG_ERR_INV_PARM;
+ }
+
+ if ( saw_xdigit )
+ {
+ if ( tp - sizeof( uint16_t ) < startp )
+ return MBG_ERR_INV_PARM;
+
+ *tp-- = (uint8_t) (val >> 8) & 0xff;
+ *tp-- = (uint8_t) val & 0xff;
+ }
+
+ if ( colonp != NULL )
+ {
+ /*
+ * Since some memmove()'s erroneously fail to handle
+ * overlapping regions, we'll do the shift by hand.
+ */
+ const size_t n = colonp - tp;
+ size_t i;
+
+ if ( tp == startp )
+ return MBG_ERR_INV_PARM;
+
+ for ( i = 0; i <= n; i++ )
+ {
+ startp[i] = colonp[i - n];
+ colonp[i - n] = 0;
+ }
+
+ tp = startp;
+ }
+
+ if ( tp != startp )
+ return MBG_ERR_INV_PARM;
+
+ if ( p_addr )
+ *p_addr = tmp;
+
+ return read_cnt;
+
+} // str_to_ip6_addr
+
+
+
+/*HDR*/
+/**
+ * @brief Convert a string in CIDR notation to an ::IP6_ADDR and net mask
+ *
+ * If output parameters are specified as NULL then this function
+ * can be used to check if the CIDR string is formally correct.
+ *
+ * @param[out] p_addr Pointer to an ::IP6_ADDR variable to be filled up
+ * with the IPv6 address, or NULL
+ * @param[out] p_mask Pointer to an ::IP6_ADDR variable to be filled up
+ with the net mask bits, or NULL
+ * @param[in] cidr_str The string to be converted, in CIDR format, e.g. "2001:0DB8:0:CD30::/64"
+ *
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
+ *
+ * @see ::snprint_ip4_addr
+ * @see ::snprint_ip4_cidr_addr
+ * @see ::str_to_ip4_addr
+ */
+int cidr_str_to_ip6_addr_and_net_mask( IP6_ADDR *p_addr, IP6_ADDR *p_mask, const char *cidr_str )
+{
+ int mask = 0;
+ int rc = cidr_str_to_ip6_addr_and_cidr_bits( p_addr, &mask, cidr_str );
+
+ if ( mbg_rc_is_error( rc ) )
+ return rc;
+
+ if ( p_mask )
+ ip6_net_mask_from_cidr( p_mask, mask );
+
+ return rc;
+
+} // cidr_str_to_ip6_addr_and_net_mask
+
+
+
+/*HDR*/
+/**
+ * @brief Convert a string in CIDR notation to an ::IP6_ADDR and net mask bits
+ *
+ * If output parameters are specified as NULL then this function
+ * can be used to check if the CIDR string is formally correct.
+ *
+ * @param[out] p_addr Pointer to an ::IP6_ADDR variable for the IPv6 address, or NULL
+ * @param[out] p_cidr Pointer to an int variable for the net mask bits, or NULL
+ * @param[in] cidr_str The string to be converted, in CIDR format, e.g. "2001:0DB8:0:CD30::/64"
+ *
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
+ *
+ * @see ::snprint_ip6_addr
+ * @see ::snprint_ip6_cidr_addr
+ * @see ::str_to_ip6_addr
+ */
+int cidr_str_to_ip6_addr_and_cidr_bits( IP6_ADDR *p_addr, int *p_cidr,
+ const char *cidr_str )
+{
+ long cidr_mask_bits;
+ const char *cp;
+ ssize_t l;
+ int rc = str_to_ip6_addr( p_addr, cidr_str );
+
+ if ( mbg_rc_is_error( rc ) )
+ return rc;
+
+ l = strlen( cidr_str );
+
+ if ( l < rc ) // input string too short
+ return MBG_ERR_INV_PARM;
+
+ cp = &cidr_str[rc];
+
+ if ( *cp == 0 ) // end of string
+ {
+ // The string has no CIDR extension, so
+ // assume "/0", i.e. host mask ::
+ cidr_mask_bits = 0;
+ goto done;
+ }
+
+ if ( *cp != '/' )
+ return MBG_ERR_INV_PARM;
+
+ cp++;
+ cidr_mask_bits = strtol( (char *) cp, (char **) &cp, 10 );
+
+ if ( ( cidr_mask_bits < MIN_IP6_CIDR_NETMASK_BITS ) ||
+ ( cidr_mask_bits > MAX_IP6_CIDR_NETMASK_BITS ) )
+ return MBG_ERR_RANGE;
+
+done:
+ if ( p_cidr )
+ *p_cidr = (int) cidr_mask_bits;
+
+ // success: return the number of evaluated chars
+ return (int) ( cp - cidr_str );
+
+} // cidr_str_to_ip6_addr_and_cidr_bits
+
+
+
+/*HDR*/
+/**
+ * @brief Compute an IPv6 net mask according to the number of CIDR netmask bits
+ *
+ * E.g. the 64 bits mentioned in "2001:0DB8:0:CD30::/64" result in 2^64,
+ * corresponding to FFFF:FFFF:FFFF:FFFF:: in IPv6 notation.
+ *
+ * @param[out] p_mask Pointer to an ::IP6_ADDR variable for the IPv6 netmask
+ * @param[in] netmask_bits Number of netmask bits from CIDR notation
+ *
+ * @see ::get_ip6_net_mask_bits
+ */
+void ip6_net_mask_from_cidr( IP6_ADDR *p_mask, int netmask_bits )
+{
+ int i = 0;
+
+ if ( p_mask )
+ {
+ memset( p_mask, 0, sizeof( *p_mask ) );
+
+ if ( netmask_bits < 0 )
+ netmask_bits = 0;
+ else
+ if ( netmask_bits >= IP6_ADDR_BITS )
+ netmask_bits = IP6_ADDR_BITS;
+
+ for ( i = IP6_ADDR_BYTES - 1; i >= 0; i-- )
+ {
+ if ( netmask_bits > 8 )
+ {
+ p_mask->b[i] = 0xff;
+ netmask_bits -= 8;
+ }
+ else
+ {
+ p_mask->b[i] = (0xff << ( 8 - netmask_bits ) ) & 0xff;
+ netmask_bits = 0;
+ }
+ }
+ }
+
+} // ip6_net_mask_from_cidr
+
+
+
+/*HDR*/
+/**
+ * @brief Determine the network part of an IPv6 address based on the net mask
+ *
+ * E.g. IP "2001:0DB8:0:CD30::", net mask "FFFF:FFFF::" yields network part "2001:0DB8::".
+ *
+ * @param[out] p_net_part The extracted network part of the IPv6 address
+ * @param[in] p_addr The IPv6 address to be evaluated
+ * @param[in] p_mask The associated IPv6 net mask
+ */
+void ip6_net_part_from_addr( IP6_ADDR *p_net_part, const IP6_ADDR *p_addr,
+ const IP6_ADDR *p_mask )
+{
+ int i;
+
+ for ( i = IP6_ADDR_BYTES; i-- > 0; )
+ p_net_part->b[i] = p_addr->b[i] & p_mask->b[i];
+
+} // ip6_net_part_from_addr
+
+
+
+/*HDR*/
+/**
+ * @brief Print a MAC ID or similar array of octets to a string
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Maximum length of the string, i.e. size of the buffer
+ * @param[in] octets An array of octets
+ * @param[in] num_octets The number of octets to be printed from the array
+ * @param[in] sep The separator printed between the bytes, or 0
+ * @param[in] info An optional string which is prepended to the output, or NULL
*
* @return The overall number of characters printed to the string
*
- * @see snprint_mac_addr
- * @see str_to_octets
- * @see check_octets_not_all_zero
+ * @see ::snprint_mac_addr
+ * @see ::str_to_octets
+ * @see ::octets_are_all_zero
*/
-int snprint_octets( char *s, size_t max_len, const uint8_t *octets,
- int num_octets, char sep, const char *info )
+size_t snprint_octets( char *s, size_t max_len, const uint8_t *octets,
+ int num_octets, char sep, const char *info )
{
- int n = 0;
+ size_t n = 0;
int i;
if ( info )
- n += snprintf( s, max_len, "%s", info );
+ n += snprintf_safe( s, max_len, "%s", info );
for ( i = 0; i < num_octets; i++ )
{
if ( i && sep )
- n += snprintf( &s[n], max_len - n, "%c", sep );
+ n += snprintf_safe( &s[n], max_len - n, "%c", sep );
- n += snprintf( &s[n], max_len - n, "%02X", octets[i] );
+ n += snprintf_safe( &s[n], max_len - n, "%02X", octets[i] );
}
return n;
@@ -415,19 +1018,41 @@ int snprint_octets( char *s, size_t max_len, const uint8_t *octets,
/*HDR*/
/**
- * @brief Print a MAC address to a string.
+ * @brief Print a ::PTP_CLOCK_ID to a string
+ *
+ * @todo Eventually this function should be moved to a different module.
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Maximum length of the string, i.e. size of the buffer
+ * @param[in] p The ::PTP_CLOCK_ID to be printed
+ *
+ * @return The overall number of characters printed to the string
+ *
+ * @see ::snprint_octets
+ */
+size_t snprint_ptp_clock_id( char *s, size_t max_len, const PTP_CLOCK_ID *p )
+{
+ return snprint_octets( s, max_len, p->b, sizeof( *p ), ':', NULL );
+
+} // snprint_ptp_clock_id
+
+
+
+/*HDR*/
+/**
+ * @brief Print a MAC address to a string
*
- * @param s The string buffer into which to print
- * @param max_len Maximum length of the string, i.e. size of the buffer
- * @param p_mac_addr The MAC address to be printed
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Maximum length of the string, i.e. size of the buffer
+ * @param[in] p_mac_addr The MAC address to be printed
*
* @return The overall number of characters printed to the string
*
- * @see snprint_octets
- * @see str_to_octets
- * @see check_octets_not_all_zero
+ * @see ::snprint_octets
+ * @see ::str_to_octets
+ * @see ::octets_are_all_zero
*/
-int snprint_mac_addr( char *s, size_t max_len, const MBG_MAC_ADDR *p_mac_addr )
+size_t snprint_mac_addr( char *s, size_t max_len, const MBG_MAC_ADDR *p_mac_addr )
{
return snprint_octets( s, max_len, p_mac_addr->b, sizeof( *p_mac_addr ), MAC_SEP_CHAR, NULL );
@@ -437,17 +1062,17 @@ int snprint_mac_addr( char *s, size_t max_len, const MBG_MAC_ADDR *p_mac_addr )
/*HDR*/
/**
- * @brief Set a MAC ID or a similar array of octets from a string.
+ * @brief Set a MAC ID or a similar array of octets from a string
*
- * @param octets An array of octets to be set up
- * @param num_octets The number of octets which can be stored
- * @param s The string to be converted
+ * @param[out] octets An array of octets to be set up
+ * @param[in] num_octets The number of octets which can be stored
+ * @param[in] s The string to be converted
*
* @return The overall number of octets decoded from the string
*
- * @see snprint_octets
- * @see snprint_mac_addr
- * @see check_octets_not_all_zero
+ * @see ::snprint_octets
+ * @see ::snprint_mac_addr
+ * @see ::octets_are_all_zero
*/
int str_to_octets( uint8_t *octets, int num_octets, const char *s )
{
@@ -477,164 +1102,161 @@ int str_to_octets( uint8_t *octets, int num_octets, const char *s )
/*HDR*/
/**
- * @brief Check if an array of octets is valid, i.e. != 0
+ * @brief Check if an array of octets is all zero
*
- * @param octets Pointer to the array of octets
- * @param num_octets Number of octets
+ * @param[in] octets Pointer to the array of octets
+ * @param[in] num_octets Number of octets
*
- * @return MBG_LU_SUCCESS octets are valid, i.e. not all 0
- * MBG_LU_ERR_NOT_SET octets are invalid, i.e. all 0
+ * @return true if all bytes are 0, else false
*
- * @see snprint_octets
- * @see snprint_mac_addr
- * @see str_to_octets
+ * @see ::snprint_octets
+ * @see ::snprint_mac_addr
+ * @see ::str_to_octets
*/
-int check_octets_not_all_zero( const uint8_t *octets, int num_octets )
+bool octets_are_all_zero( const uint8_t *octets, int num_octets )
{
int i;
- // check if any of the MAC adddress bytes is != 0
+ // check if any of the bytes is != 0
for ( i = 0; i < num_octets; i++ )
if ( octets[i] != 0 )
break;
- if ( i == num_octets ) // *all* bytes are 0
- return MBG_LU_ERR_NOT_SET;
+ return i == num_octets; // true if *all* bytes are 0
- return 0;
-
-} // check_octets_not_all_zero
+} // octets_are_all_zero
/*HDR*/
/**
- * @brief Check if an array of octets is valid, i.e. != 0
+ * @brief Check if a MAC address is all zero
*
- * @param p_addr Pointer to a MAC address
+ * @param[in] p_addr Pointer to a MAC address to be checked
*
- * @return MBG_LU_SUCCESS MAC address is valid, i.e. not all 0
- * MBG_LU_ERR_NOT_SET MAC address is invalid, i.e. all 0
+ * @return true if all bytes of the MAC address are 0, else false
*
- * @see check_octets_not_all_zero
+ * @see ::octets_are_all_zero
*/
-int check_mac_addr_not_all_zero( const MBG_MAC_ADDR *p_addr )
+bool mac_addr_is_all_zero( const MBG_MAC_ADDR *p_addr )
{
- return check_octets_not_all_zero( p_addr->b, sizeof( p_addr->b ) );
+ return octets_are_all_zero( p_addr->b, sizeof( p_addr->b ) );
-} // check_mac_addr_not_all_zero
+} // mac_addr_is_all_zero
-#if defined( MBG_TGT_UNIX )
+#if defined( MBG_TGT_POSIX )
/*HDR*/
/**
* @brief Do a SIOCGxxx IOCTL call to read specific information from a LAN interface
*
- * @param if_name Name of the interface
- * @param ioctl_code One of the predefined system SIOCGxxx IOCTL codes
- * @param p_ifreq Pointer to a request buffer
+ * @param[in] if_name Name of the interface
+ * @param[in] ioctl_code One of the predefined system SIOCGxxx IOCTL codes
+ * @param[out] p_ifreq Pointer to a request buffer
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
*/
int do_siocg_ioctl( const char *if_name, int ioctl_code, struct ifreq *p_ifreq )
{
- int fd;
+ int sock_fd;
int rc;
if ( strlen( if_name ) > ( IFNAMSIZ - 1 ) )
- return MBG_LU_ERR_PORT_NAME;
+ return MBG_ERR_INV_PARM;
- fd = socket( AF_INET, SOCK_DGRAM, 0 );
+ sock_fd = socket( AF_INET, SOCK_DGRAM, 0 ); //### TODO: or AF_INET6/PF_INET6 for IPv6
- if ( fd < 0 )
- return MBG_LU_ERR_SOCKET;
+ if ( sock_fd == -1 ) // failed to open socket
+ return mbg_get_last_socket_error( "failed to open socket in do_siocg_ioctl" );
- strcpy( p_ifreq->ifr_name, if_name );
+ strncpy_safe( p_ifreq->ifr_name, if_name, sizeof( p_ifreq->ifr_name ) );
- rc = ioctl( fd, ioctl_code, p_ifreq );
+ rc = ioctl( sock_fd, ioctl_code, p_ifreq );
- close( fd );
+ if ( rc == -1 ) // ioctl failed, errno has been set appropriately
+ rc = mbg_get_last_socket_error( "ioctl failed in do_siocg_ioctl" );
+ else
+ rc = MBG_SUCCESS;
- if ( rc < 0 )
- {
- // errno has been set appropriately
- if ( errno == EADDRNOTAVAIL )
- return MBG_LU_ERR_NOT_SET;
+ close( sock_fd );
- return MBG_LU_ERR_IOCTL;
- }
-
- return MBG_LU_SUCCESS;
+ return rc;
} // do_siocg_ioctl
-#endif // defined( MBG_TGT_UNIX )
+#endif // defined( MBG_TGT_POSIX )
/*HDR*/
/**
- * @brief Retrieve the MAC address of a network interface
- *
- * @param if_name Name of the interface
- * @param p_mac_addr Pointer to the MAC address buffer to be filled up
+ * @brief Retrieve the index of a specific network interface
*
- * @return one of the ::MBG_LU_CODES
- * on error the MAC addr is set to all 0
+ * @param[in] if_name Name of the interface
+ * @param[out] p_intf_idx Pointer to a variable to be filled up
*
- * @see get_port_mac_addr_check
+ * @return One of the @ref MBG_RETURN_CODES.
+ * On error, *p_intf_idx is set to -1.
*/
-int get_port_mac_addr( const char *if_name, MBG_MAC_ADDR *p_mac_addr )
+int get_port_intf_idx( const char *if_name, int *p_intf_idx )
{
- int rc = MBG_LU_ERR_NSUPP;
+ int rc = MBG_ERR_NOT_SUPP_ON_OS;
#if defined( MBG_TGT_LINUX )
struct ifreq ifr = { { { 0 } } };
- rc = do_siocg_ioctl( if_name, SIOCGIFHWADDR, &ifr );
-
- if ( rc != MBG_LU_SUCCESS )
- goto fail;
-
- memcpy( p_mac_addr, ifr.ifr_hwaddr.sa_data, sizeof( *p_mac_addr ) );
-
- return rc;
+ rc = do_siocg_ioctl( if_name, SIOCGIFINDEX, &ifr );
-fail:
+ if ( mbg_rc_is_success( rc ) )
+ {
+ *p_intf_idx = ifr.ifr_ifindex;
+ return rc;
+ }
#endif
- memset( p_mac_addr, 0, sizeof( *p_mac_addr ) );
+ // we get here on error only
+ *p_intf_idx = -1;
return rc;
-} // get_port_mac_addr
+} // get_port_intf_idx
/*HDR*/
/**
- * @brief Retrieve and check the MAC address of a network interface
- *
- * @param if_name Name of the interface
- * @param p_mac_addr Pointer to the MAC address buffer to be filled up
+ * @brief Retrieve the MAC address of a network interface
*
- * @return one of the ::MBG_LU_CODES
- * on error the MAC addr is set to all 0
+ * @param[in] if_name Name of the interface
+ * @param[out] p_mac_addr Pointer to the MAC address buffer to be filled up
*
- * @see get_port_mac_addr
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, the MAC address is set to all 0
*/
-int get_port_mac_addr_check( const char *if_name, MBG_MAC_ADDR *p_mac_addr )
+int get_port_mac_addr( const char *if_name, MBG_MAC_ADDR *p_mac_addr )
{
- int rc = get_port_mac_addr( if_name, p_mac_addr );
+ int rc = MBG_ERR_NOT_SUPP_ON_OS;
+
+ #if defined( MBG_TGT_LINUX )
+ struct ifreq ifr = { { { 0 } } };
+
+ rc = do_siocg_ioctl( if_name, SIOCGIFHWADDR, &ifr );
+
+ if ( mbg_rc_is_success( rc ) )
+ {
+ memcpy( p_mac_addr, ifr.ifr_hwaddr.sa_data, sizeof( *p_mac_addr ) );
+ return rc;
+ }
+ #endif
- if ( rc == MBG_LU_SUCCESS )
- rc = check_octets_not_all_zero( p_mac_addr->b, sizeof( *p_mac_addr ) );
+ // we get here on error only
+ memset( p_mac_addr, 0, sizeof( *p_mac_addr ) );
return rc;
-} // get_port_mac_addr_check
+} // get_port_mac_addr
@@ -642,76 +1264,71 @@ int get_port_mac_addr_check( const char *if_name, MBG_MAC_ADDR *p_mac_addr )
/**
* @brief Check the link state of a network interface
*
- * @param if_name Name of the interface
+ * @param[in] if_name Name of the interface
*
- * @return 1 link detected on port
- * 0 no link detected on port
- * one of the ::MBG_LU_CODES in case of an error
+ * @return 1 if link detected on port,
+ * 0 if no link detected on port,
+ * one of the @ref MBG_ERROR_CODES in case of an error
*/
int check_port_link( const char *if_name )
{
+ int rc = MBG_ERR_NOT_SUPP_ON_OS;
+
#if defined( MBG_TGT_LINUX )
struct ifreq ifr = { { { 0 } } };
struct ethtool_value edata = { 0 };
- int rc;
edata.cmd = ETHTOOL_GLINK; // defined in ethtool.h
ifr.ifr_data = (caddr_t) &edata;
rc = do_siocg_ioctl( if_name, SIOCETHTOOL, &ifr );
- if ( rc == MBG_LU_SUCCESS )
- rc = edata.data != 0;
-
- return rc;
-
- #else
-
- return MBG_LU_ERR_NSUPP;
-
+ if ( mbg_rc_is_success( rc ) )
+ rc = ( edata.data == 0 ) ? 0 : 1;
#endif
+ return rc;
+
} // check_port_link
static /*HDR*/
/**
- * @brief Retrieve some IPv4 address like info from a network interface
- *
- * @param if_name Name of the interface
- * @param p_addr Pointer to address field to be filled up
- * @param sigioc_code the ioctl code associated to the address
- *
- * @return one of the ::MBG_LU_CODES
- *
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
+ * @brief Retrieve some IPv4 address-like info from a network interface
+ *
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr Pointer to address field to be filled up
+ * @param[in] sigioc_code The IOCTL code associated with the address
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, *p_addr is set to all 0.
+ *
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
*/
int get_specific_port_ip4_addr( const char *if_name, IP4_ADDR *p_addr, int sigioc_code )
{
- int rc = MBG_LU_ERR_NSUPP;
+ int rc = MBG_ERR_NOT_SUPP_ON_OS;
#if defined( MBG_TGT_LINUX )
struct ifreq ifr = { { { 0 } } };
rc = do_siocg_ioctl( if_name, sigioc_code, &ifr );
- if ( rc != MBG_LU_SUCCESS )
- goto fail;
-
- *p_addr = ntohl( ( (struct sockaddr_in *) &ifr.ifr_addr )->sin_addr.s_addr );
-
- return rc;
-
-fail:
+ if ( mbg_rc_is_success( rc ) )
+ {
+ *p_addr = ntohl( ( (struct sockaddr_in *) &ifr.ifr_addr )->sin_addr.s_addr );
+ return rc;
+ }
#endif
+ // we get here on error only
*p_addr = 0; // make empty address
return rc;
@@ -724,18 +1341,19 @@ fail:
/**
* @brief Retrieve the IPv4 address of a network interface
*
- * @param if_name Name of the interface
- * @param p_addr Pointer to address field to be filled up
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr Pointer to address field to be filled up
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, *p_addr is set to all 0.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_addr( const char *if_name, IP4_ADDR *p_addr )
{
@@ -749,18 +1367,19 @@ int get_port_ip4_addr( const char *if_name, IP4_ADDR *p_addr )
/**
* @brief Retrieve the IPv4 net mask of a network interface
*
- * @param if_name Name of the interface
- * @param p_addr Pointer to address field to be filled up
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr Pointer to address field to be filled up
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, *p_addr is set to all 0.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_netmask( const char *if_name, IP4_ADDR *p_addr )
{
@@ -774,18 +1393,19 @@ int get_port_ip4_netmask( const char *if_name, IP4_ADDR *p_addr )
/**
* @brief Retrieve the IPv4 broadcast address of a network interface
*
- * @param if_name Name of the interface
- * @param p_addr Pointer to address field to be filled up
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr Pointer to address field to be filled up
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, *p_addr is set to all 0.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_broad_addr( const char *if_name, IP4_ADDR *p_addr )
{
@@ -800,39 +1420,42 @@ int get_port_ip4_broad_addr( const char *if_name, IP4_ADDR *p_addr )
static /*HDR*/
/**
* @brief Read a requested message from the netlink socket
+ *
+ * @return Message length (>= 0) on success, or of the @ref MBG_ERROR_CODES
*/
-int readNlSock( int sockFd, char *bufPtr, size_t buf_size, int seqNum, int pId )
+int nl_read( int sock_fd, char *buf_ptr, size_t buf_size, int seq_num, int pid )
{
- struct nlmsghdr *nlHdr;
- int readLen = 0;
- int msgLen = 0;
+ struct nlmsghdr *nl_hdr;
+ int read_len = 0;
+ int msg_len = 0;
do
{
// receive response from the kernel, can be several chunks
- if ( ( readLen = recv( sockFd, bufPtr, buf_size - msgLen, 0 ) ) < 0 )
+ if ( ( read_len = recv( sock_fd, buf_ptr, buf_size - msg_len, 0 ) ) == -1 )
{
+ int rc = mbg_get_last_socket_error( NULL );
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: Failed to receive netlink packet: %s",
- __func__, strerror( errno ) );
+ __func__, mbg_strerror( rc ) );
#endif
- return -1;
+ return rc;
}
- nlHdr = (struct nlmsghdr *) bufPtr;
+ nl_hdr = (struct nlmsghdr *) buf_ptr;
// check if the header is valid
- if ( ( NLMSG_OK( nlHdr, readLen ) == 0 ) || ( nlHdr->nlmsg_type == NLMSG_ERROR ) )
+ if ( ( NLMSG_OK( nl_hdr, read_len ) == 0 ) || ( nl_hdr->nlmsg_type == NLMSG_ERROR ) )
{
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: Invalid header in received netlink packet",
__func__ );
#endif
- return -1;
+ return MBG_ERR_DATA_FMT;
}
// check if the its the last message
- if ( nlHdr->nlmsg_type == NLMSG_DONE )
+ if ( nl_hdr->nlmsg_type == NLMSG_DONE )
{
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: Reached last message in received packet",
@@ -842,11 +1465,11 @@ int readNlSock( int sockFd, char *bufPtr, size_t buf_size, int seqNum, int pId )
}
// move the pointer to buffer appropriately
- bufPtr += readLen;
- msgLen += readLen;
+ buf_ptr += read_len;
+ msg_len += read_len;
// check if its a multi part message
- if ( ( nlHdr->nlmsg_flags & NLM_F_MULTI ) == 0 )
+ if ( ( nl_hdr->nlmsg_flags & NLM_F_MULTI ) == 0 )
{
// return if it's not a multi part message
#if DEBUG_NETLINK
@@ -856,110 +1479,110 @@ int readNlSock( int sockFd, char *bufPtr, size_t buf_size, int seqNum, int pId )
break;
}
- } while ( ( nlHdr->nlmsg_seq != seqNum ) || ( nlHdr->nlmsg_pid != pId ) );
+ } while ( ( nl_hdr->nlmsg_seq != seq_num ) || ( nl_hdr->nlmsg_pid != pid ) );
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: Received packet has len %i",
- __func__, msgLen );
+ __func__, msg_len );
#endif
- return msgLen;
+ return msg_len;
-} // readNlSock
+} // nl_read
#if DEBUG_NETLINK
static /*HDR*/
-void log_netlink_bytes( const char *fnc, const char *info, const void *p, int n_bytes )
+void nl_log_bytes( const char *fnc, const char *info, const void *p, int n_bytes )
{
char ws[80];
- int n = 0;
+ size_t n = 0;
int i;
for ( i = 0; i < n_bytes; i++ )
- n += snprintf( &ws[n], sizeof( ws ) - n, " %i", BYTE_OF( *p, i ) );
+ n += snprintf_safe( &ws[n], sizeof( ws ) - n, " %i", BYTE_OF( * (uint8_t *) p, i ) );
mbglog( LOG_INFO, "%s: attibute %s, copying %i bytes:%s",
fnc, info, n_bytes, ws );
-} // log_netlink_bytes
+} // nl_log_bytes
#endif
static /*HDR*/
-int parseRoutes( struct nlmsghdr *nlHdr, struct route_info *rtInfo )
+int nl_parse_routes( struct nlmsghdr *nl_hdr, struct route_info *rt_info )
{
// parse the route info returned
- struct rtmsg *rtMsg;
- struct rtattr *rtAttr;
- int rtLen;
+ struct rtmsg *rt_msg;
+ struct rtattr *rt_attr;
+ int rt_len;
- rtMsg = (struct rtmsg *) NLMSG_DATA( nlHdr );
+ rt_msg = (struct rtmsg *) NLMSG_DATA( nl_hdr );
// If the route is not for AF_INET then return.
// This could be also IPv6 routes.
- if ( rtMsg->rtm_family != AF_INET )
+ if ( rt_msg->rtm_family != AF_INET ) //##++ TODO: PF_INET6 for IPv6
{
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: Route is not AF_INET (%li), but %li",
- __func__, (long) AF_INET, (long) rtMsg->rtm_family );
+ __func__, (long) AF_INET, (long) rt_msg->rtm_family );
#endif
return -1;
}
// If the route does not belong to main routing table then return.
- if ( rtMsg->rtm_table != RT_TABLE_MAIN )
+ if ( rt_msg->rtm_table != RT_TABLE_MAIN )
{
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: Route does not belong to main table (%li), but %li",
- __func__, (long) RT_TABLE_MAIN, (long) rtMsg->rtm_table );
+ __func__, (long) RT_TABLE_MAIN, (long) rt_msg->rtm_table );
#endif
return -1;
}
// get the rtattr field
- rtAttr = (struct rtattr *) RTM_RTA( rtMsg );
- rtLen = RTM_PAYLOAD( nlHdr );
+ rt_attr = (struct rtattr *) RTM_RTA( rt_msg );
+ rt_len = RTM_PAYLOAD( nl_hdr );
- for ( ; RTA_OK( rtAttr, rtLen ); rtAttr = RTA_NEXT( rtAttr, rtLen ) )
+ for ( ; RTA_OK( rt_attr, rt_len ); rt_attr = RTA_NEXT( rt_attr, rt_len ) )
{
#if DEBUG_NETLINK
- mbglog( LOG_ERR, "rtAttr at %p, %i bytes left", rtAttr, rtLen );
+ mbglog( LOG_ERR, "rt_attr at %p, %i bytes left", rt_attr, rt_len );
#endif
- switch ( rtAttr->rta_type )
+ switch ( rt_attr->rta_type )
{
case RTA_OIF:
- if_indextoname( *(int *)RTA_DATA( rtAttr ), rtInfo->ifName );
+ if_indextoname( *(int *)RTA_DATA( rt_attr ), rt_info->ifName );
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: attibute RTA_OIF, IF name: %s",
- __func__, rtInfo->ifName );
+ __func__, rt_info->ifName );
#endif
break;
case RTA_GATEWAY:
- memcpy( &rtInfo->gateWay, RTA_DATA( rtAttr ), sizeof( rtInfo->gateWay ) );
+ memcpy( &rt_info->gateWay, RTA_DATA( rt_attr ), sizeof( rt_info->gateWay ) );
#if DEBUG_NETLINK
- log_netlink_bytes( __func__, "RTA_GATEWAY", &rtInfo->gateWay, sizeof( rtInfo->gateWay ) );
+ nl_log_bytes( __func__, "RTA_GATEWAY", &rt_info->gateWay, sizeof( rt_info->gateWay ) );
#endif
break;
case RTA_PREFSRC:
- memcpy( &rtInfo->srcAddr , RTA_DATA( rtAttr ), sizeof( rtInfo->srcAddr ) );
+ memcpy( &rt_info->srcAddr , RTA_DATA( rt_attr ), sizeof( rt_info->srcAddr ) );
#if DEBUG_NETLINK
- log_netlink_bytes( __func__, "RTA_PREFSRC", &rtInfo->srcAddr, sizeof( rtInfo->srcAddr ) );
+ nl_log_bytes( __func__, "RTA_PREFSRC", &rt_info->srcAddr, sizeof( rt_info->srcAddr ) );
#endif
break;
case RTA_DST:
- memcpy( &rtInfo->dstAddr, RTA_DATA( rtAttr ), sizeof( rtInfo->dstAddr ) );
+ memcpy( &rt_info->dstAddr, RTA_DATA( rt_attr ), sizeof( rt_info->dstAddr ) );
#if DEBUG_NETLINK
- log_netlink_bytes( __func__, "RTA_DST", &rtInfo->dstAddr, sizeof( rtInfo->dstAddr ) );
+ nl_log_bytes( __func__, "RTA_DST", &rt_info->dstAddr, sizeof( rt_info->dstAddr ) );
#endif
break;
@@ -977,22 +1600,22 @@ int parseRoutes( struct nlmsghdr *nlHdr, struct route_info *rtInfo )
// used by the compiler. Unfortunately RTA_TABLE is part of an enum, so you
// can't simply use #ifdef RTA_TABLE to include this code conditionally.
uint32_t rta_table;
- memcpy( &rta_table, RTA_DATA( rtAttr ), sizeof( rta_table ) );
+ memcpy( &rta_table, RTA_DATA( rt_attr ), sizeof( rta_table ) );
mbglog( LOG_ERR, "%s: attibute RTA_TABLE %i (%i)",
- __func__, rta_table, rtMsg->rtm_table );
+ __func__, rta_table, rt_msg->rtm_table );
}
break;
default:
mbglog( LOG_ERR, "%s: Found unknown route type %li",
- __func__, (long) rtAttr->rta_type );
+ __func__, (long) rt_attr->rta_type );
#endif
}
}
return 0;
-} // parseRoutes
+} // nl_parse_routes
#endif // defined( MBG_TGT_LINUX )
@@ -1002,87 +1625,87 @@ int parseRoutes( struct nlmsghdr *nlHdr, struct route_info *rtInfo )
/**
* @brief Retrieve the IPv4 gateway (default route)
*
- * @param p_addr Pointer to address field to be filled up
+ * @param[out] p_addr Pointer to address field to be filled up
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, *p_addr is set to all 0.
*/
int get_ip4_gateway( IP4_ADDR *p_addr )
{
- int ret_val = MBG_LU_ERR_NOT_SET;
+ int rc = MBG_ERR_NOT_SUPP_ON_OS;
#if defined( MBG_TGT_LINUX )
- struct nlmsghdr *nlMsg;
+ struct nlmsghdr *nlmsg;
struct route_info route_info;
- char msgBuf[8192]; // pretty large buffer
-
- int sock;
+ char msg_buf[8192]; // pretty large buffer, why 8192 ?
+ int sock_fd;
int len;
- int msgSeq = 0;
+ int msg_seq = 0;
int idx;
// create socket
- if ( ( sock = socket( PF_NETLINK, SOCK_DGRAM, NETLINK_ROUTE ) ) < 0 )
+ if ( ( sock_fd = socket( PF_NETLINK, SOCK_DGRAM, NETLINK_ROUTE ) ) == -1 )
{
+ rc = mbg_get_last_socket_error( NULL );
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: Failed to create netlink socket: %s",
- __func__, strerror( errno ) );
+ __func__, mbg_strerror( rc ) );
#endif
- ret_val = MBG_LU_ERR_SOCKET;
goto out;
}
- // initialize the buffer
- memset( msgBuf, 0, sizeof( msgBuf ) );
+ // initialize buffer with request message
+ memset( msg_buf, 0, sizeof( msg_buf ) );
// point the header and the msg structure pointers into the buffer
- nlMsg = (struct nlmsghdr *) msgBuf;
+ nlmsg = (struct nlmsghdr *) msg_buf;
// fill in the nlmsg header
- nlMsg->nlmsg_len = NLMSG_LENGTH( sizeof( struct rtmsg ) ); // length of message
- nlMsg->nlmsg_type = RTM_GETROUTE; // get the routes from kernel routing table
+ nlmsg->nlmsg_len = NLMSG_LENGTH( sizeof( struct rtmsg ) ); // length of message
+ nlmsg->nlmsg_type = RTM_GETROUTE; // get the routes from kernel routing table
- nlMsg->nlmsg_flags = NLM_F_DUMP | NLM_F_REQUEST; // the message is a request for dump
- nlMsg->nlmsg_seq = msgSeq++; // sequence of the message packet
- nlMsg->nlmsg_pid = getpid(); // PID of process sending the request
+ nlmsg->nlmsg_flags = NLM_F_DUMP | NLM_F_REQUEST; // the message is a request for dump
+ nlmsg->nlmsg_seq = msg_seq++; // sequence of the message packet
+ nlmsg->nlmsg_pid = getpid(); // PID of process sending the request
// send the request
- if ( send( sock, nlMsg, nlMsg->nlmsg_len, 0 ) < 0 )
+ if ( send( sock_fd, nlmsg, nlmsg->nlmsg_len, 0 ) == -1 )
{
+ rc = mbg_get_last_socket_error( NULL );
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: Failed to write to netlink socket: %s",
- __func__, strerror( errno ) );
+ __func__, mbg_strerror( rc ) );
#endif
- ret_val = -1;
goto out;
}
// read the response
- if ( ( len = readNlSock( sock, msgBuf, sizeof( msgBuf ), msgSeq, getpid() ) ) < 0 )
+ if ( ( len = nl_read( sock_fd, msg_buf, sizeof( msg_buf ), msg_seq, getpid() ) ) < 0 )
{
#if DEBUG_NETLINK
mbglog( LOG_ERR, "%s: Failed to read from netlink socket",
__func__ );
#endif
- ret_val = -1;
+ rc = len;
goto out;
}
#if DEBUG_NETLINK
- mbglog( LOG_ERR, "%s: Read %i bytes from netlink socket", __func__ );
+ mbglog( LOG_ERR, "%s: Read %i bytes from netlink socket", __func__, len );
#endif
// parse and print the response
- for ( idx = 0; NLMSG_OK( nlMsg, len ); nlMsg = NLMSG_NEXT( nlMsg, len ), idx ++ )
+ for ( idx = 0; NLMSG_OK( nlmsg, len ); nlmsg = NLMSG_NEXT( nlmsg, len ), idx++ )
{
memset( &route_info, 0, sizeof( route_info ) );
#if DEBUG_NETLINK
- mbglog( LOG_ERR, "\nnlMsg at %p, %i bytes left", nlMsg, len );
+ mbglog( LOG_ERR, "\nnl_msg at %p, %i bytes left", nlmsg, len );
#endif
- if ( parseRoutes( nlMsg, &route_info ) < 0 )
+ if ( nl_parse_routes( nlmsg, &route_info ) < 0 )
continue; // don't check route_info if it has not been set up
#if DEBUG_NETLINK
@@ -1092,9 +1715,10 @@ int get_ip4_gateway( IP4_ADDR *p_addr )
int n = 0;
// inet_ntoa() uses a static buffer which is overwritten on every call
- n += snprintf( &ws[n], l - n, "src %s", (char *) inet_ntoa( route_info.srcAddr ) );
- n += snprintf( &ws[n], l - n, ", dst %s", (char *) inet_ntoa( route_info.dstAddr ) );
- n += snprintf( &ws[n], l - n, ", gw %s", (char *) inet_ntoa( route_info.gateWay ) );
+ //##++ TODO: rather than inet_ntoa use inet_ntop which can also handle IPv6
+ n += snprintf_safe( &ws[n], l - n, "src %s", (char *) inet_ntoa( route_info.srcAddr ) );
+ n += snprintf_safe( &ws[n], l - n, ", dst %s", (char *) inet_ntoa( route_info.dstAddr ) );
+ n += snprintf_safe( &ws[n], l - n, ", gw %s", (char *) inet_ntoa( route_info.gateWay ) );
mbglog( LOG_ERR, "%s: route %i: %s, if \"%s\"",
__func__, idx, ws, route_info.ifName );
@@ -1102,13 +1726,15 @@ int get_ip4_gateway( IP4_ADDR *p_addr )
#endif
// check if default IPv4 gateway
+ //##++ TODO: rather than inet_ntoa use inet_ntop which can also handle IPv6
if ( strstr( (char *) inet_ntoa( route_info.dstAddr ), "0.0.0.0" ) )
{
*p_addr = ntohl( route_info.gateWay.s_addr );
- ret_val = MBG_LU_SUCCESS;
+ rc = MBG_SUCCESS;
// Actually we could stop searching now. However, in case of debug
// we'll continue to examine the rest of the routing message.
#if DEBUG_NETLINK
+ //##++ TODO: rather than inet_ntoa use inet_ntop which can also handle IPv6
mbglog( LOG_ERR, "%s: Default gateway found: %s",
__func__, (char *) inet_ntoa( route_info.gateWay ) );
#else
@@ -1118,16 +1744,15 @@ int get_ip4_gateway( IP4_ADDR *p_addr )
}
out:
- if ( sock >= 0 )
- close( sock );
+ if ( sock_fd >= 0 )
+ close( sock_fd );
#endif // defined( MBG_TGT_LINUX )
-
- if ( ret_val != MBG_LU_SUCCESS )
+ if ( mbg_rc_is_error( rc ) )
*p_addr = 0;
- return ret_val;
+ return rc;
} // get_ip4_gateway
@@ -1137,19 +1762,20 @@ out:
/**
* @brief Retrieve the IPv4 address of a network interface as string
*
- * @param if_name Name of the interface
- * @param p_addr_buf Pointer to the string buffer to be filled up
- * @param buf_size size of the string buffer
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr_buf Pointer to the string buffer to be filled up
+ * @param[in] buf_size size of the string buffer
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, a string according to "0.0.0.0" is generated.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_addr_str( const char *if_name, char *p_addr_buf, int buf_size )
{
@@ -1169,19 +1795,20 @@ int get_port_ip4_addr_str( const char *if_name, char *p_addr_buf, int buf_size )
/**
* @brief Retrieve the IPv4 net mask of a network interface as string
*
- * @param if_name Name of the interface
- * @param p_addr_buf Pointer to the string buffer to be filled up
- * @param buf_size size of the string buffer
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr_buf Pointer to the string buffer to be filled up
+ * @param[in] buf_size size of the string buffer
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, a string according to "0.0.0.0" is generated.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_netmask_str( const char *if_name, char *p_addr_buf, int buf_size )
{
@@ -1201,19 +1828,20 @@ int get_port_ip4_netmask_str( const char *if_name, char *p_addr_buf, int buf_siz
/**
* @brief Retrieve the IPv4 broadcast address of a network interface as string
*
- * @param if_name Name of the interface
- * @param p_addr_buf Pointer to the string buffer to be filled up
- * @param buf_size size of the string buffer
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr_buf Pointer to the string buffer to be filled up
+ * @param[in] buf_size size of the string buffer
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, a string according to "0.0.0.0" is generated.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_broad_addr_str( const char *if_name, char *p_addr_buf, int buf_size )
{
@@ -1233,57 +1861,58 @@ int get_port_ip4_broad_addr_str( const char *if_name, char *p_addr_buf, int buf_
/**
* @brief Retrieve the current IPv4 settings of a network interface
*
- * @param if_name Name of the interface
- * @param p Pointer to a IP4_SETTINGS structure to be filled up
+ * @param[in] if_name Name of the interface
+ * @param[out] p Pointer to a IP4_SETTINGS structure to be filled up
*
- * @return 0 on success, < 0 on error
+ * @return One of the @ref MBG_RETURN_CODES
*
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_settings( const char *if_name, IP4_SETTINGS *p )
{
int link_up;
int rc;
- int ret_val = 0;
memset( p, 0, sizeof( *p ) );
rc = get_port_ip4_addr( if_name, &p->ip_addr );
- if ( ( rc != MBG_LU_SUCCESS ) && ( rc != MBG_LU_ERR_NOT_SET ) )
- ret_val = -1;
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
rc = get_port_ip4_netmask( if_name, &p->netmask );
- if ( ( rc != MBG_LU_SUCCESS ) && ( rc != MBG_LU_ERR_NOT_SET ) )
- ret_val = -1;
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
rc = get_port_ip4_broad_addr( if_name, &p->broad_addr );
- if ( ( rc != MBG_LU_SUCCESS ) && ( rc != MBG_LU_ERR_NOT_SET ) )
- ret_val = -1;
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+#ifndef USE_MBG_TSU
rc = get_ip4_gateway( &p->gateway );
- if ( ( rc != MBG_LU_SUCCESS ) && ( rc != MBG_LU_ERR_NOT_SET ) )
- ret_val = -1;
-
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
+#endif
link_up = check_port_link( if_name );
- if ( link_up )
- p->flags |= IP4_MSK_LINK;
+ if ( mbg_rc_is_success( rc ) )
+ if ( link_up )
+ p->flags |= IP4_MSK_LINK;
-#if 0 //##+++++
+#if 0 //### TODO
// We could also try to check VLAN and DHCP settings here,
// but as of now, this is specific to an application.
@@ -1301,7 +1930,8 @@ int get_port_ip4_settings( const char *if_name, IP4_SETTINGS *p )
p->flags |= IP4_MSK_DHCP;
#endif
- return ret_val;
+out:
+ return rc;
} // get_port_ip4_settings
diff --git a/mbglib/common/lan_util.h b/mbglib/common/lan_util.h
index 6afd21a..106a9a9 100755
--- a/mbglib/common/lan_util.h
+++ b/mbglib/common/lan_util.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: lan_util.h 1.4 2013/02/19 15:15:53 martin REL_M $
+ * $Id: lan_util.h 1.6.1.7 2016/10/31 17:39:47 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,27 @@
*
* -----------------------------------------------------------------------
* $Log: lan_util.h $
+ * Revision 1.6.1.7 2016/10/31 17:39:47 martin
+ * Only return standard MBG_RETURN_CODES.
+ * Removed definitions of old MBG_LU_... return codes.
+ * Renamed check_octets_not_all_zero() to octets_are_all_zero(), which returns a bool now.
+ * Renamed check_mac_addr_not_all_zero() to mac_addr_all_zero(), which returns a bool now.
+ * Removed get_port_mac_addr_check().
+ * Updated doxygen comments.
+ * Revision 1.6.1.6 2015/12/01 11:35:32 martin
+ * Doxygen fixes.
+ * Revision 1.6.1.5 2015/11/11 17:58:13 martin
+ * Revision 1.6.1.4 2015/11/04 17:06:36Z martin
+ * *** empty log message ***
+ * Revision 1.6.1.3 2015/08/27 16:23:23 martin
+ * Revision 1.6.1.2 2015/04/13 15:25:06 hannes
+ * Added defines for IP6 CIDR mask bits.
+ * Revision 1.6.1.1 2015/04/02 15:28:03 hannes
+ * Added most of the ipv4 functions for ipv6.
+ * Revision 1.6 2014/09/24 08:32:58 martin
+ * Fixed a POSIX header file dependency.
+ * Revision 1.5 2013/10/02 07:20:36 martin
+ * Updated function prototypes.
* Revision 1.4 2013/02/19 15:15:53 martin
* Added some inline functions.
* Redefined return codes as named enum.
@@ -30,14 +51,15 @@
/* Other headers to be included */
#include <mbg_tgt.h>
-#include <gpsdefs.h>
+#include <gpsdefs.h> // for some Meinberg data structures
#include <stdlib.h>
-#if defined( MBG_TGT_UNIX )
+#if defined( MBG_TGT_POSIX )
#include <sys/types.h>
#include <sys/socket.h>
#include <net/if.h>
+ #include <ifaddrs.h> // *must* be included *after* net/if.h
#else
// A dummy declaration to prevent from warnings due to usage
// of this type with function prototypes.
@@ -85,24 +107,7 @@ extern "C" {
#endif
-/**
- * @brief Return codes for the LAN utility functions
- */
-enum MBG_LU_CODES
-{
- MBG_LU_SUCCESS = 0, ///< success
- MBG_LU_ERR_NSUPP = -1, ///< function not supported
- MBG_LU_ERR_PORT_NAME = -2, ///< port name exceeds max length
- MBG_LU_ERR_SOCKET = -3, ///< failed to open socket
- MBG_LU_ERR_IOCTL = -4, ///< IOCTL call failed
- MBG_LU_ERR_NOT_SET = -5, ///< octets are all 0
- MBG_LU_ERR_BUFF_SZ = -6, ///< buffer size too small
- MBG_LU_ERR_FMT = -7, ///< parameter format not correct
- MBG_LU_ERR_RANGE = -8 ///< range for some parameter exceeded
-};
-
-
-#define MAX_IP4_BITS ( 8 * sizeof( IP4_ADDR ) )
+#define MAX_IP4_BITS ( 8 * (int) sizeof( IP4_ADDR ) )
#define IP4_MSB_MASK ( 1UL << ( MAX_IP4_BITS - 1 ) )
@@ -110,6 +115,12 @@ enum MBG_LU_CODES
#define MAX_IP4_CIDR_NETMASK_BITS MAX_IP4_BITS
+#define IP6_MSB_MASK ( 1UL << ( 8 - 1 ) )
+
+#define MIN_IP6_CIDR_NETMASK_BITS 0
+#define MAX_IP6_CIDR_NETMASK_BITS IP6_ADDR_BITS
+
+
/**
* @brief Compute an IP4 net mask according to the number of CIDR netmask bits
@@ -119,7 +130,7 @@ enum MBG_LU_CODES
*
* @param netmask_bits Number of netmask bits from CIDR notation
*
- * @return The IP4 net mask
+ * @return The IPv4 net mask
*
* @see get_ip4_net_mask_bits()
*/
@@ -210,349 +221,534 @@ int ip4_net_part_matches( const IP4_ADDR *p_addr1, const IP4_ADDR *p_addr2,
/* by MAKEHDR, do not remove the comments. */
/**
- * @brief Count the number of sequential bits set starting from MSB
+ * @brief Count the number of sequential bits in an IPv4 net mask
*
- * E.g. for 0xC0 and 0xC1 the results are both 2 since only
- * the 2 MSBs are sequentially set.
+ * Counting starts from MSB, i.e. for 0xC0 and 0xC1 the results
+ * are both 2 since only the 2 MSBs are sequentially set.
*
- * @param p_mask The IP4 net mask
+ * @param[in] p_mask The IPv4 net mask to be evaluated
*
- * @return The number of sequential MSB bits set in val
+ * @return The number of sequential MSB bits set in *p_mask
*
- * @see ip4_net_mask_from_cidr
+ * @see ::ip4_net_mask_from_cidr
*/
int get_ip4_net_mask_bits( const IP4_ADDR *p_mask ) ;
/**
- * @brief Print an IPv4 address to a dotted quad format string.
+ * @brief Print an IPv4 address to a dotted quad formatted string
*
- * @param s The string buffer into which to print
- * @param max_len Maximum length of the string, i.e. size of the buffer
- * @param p_addr The IPv4 address
- * @param info An optional string which is prepended to the string, or NULL
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv4 address to be evaluated
+ * @param[in] info An optional string which is prepended to the string, or NULL
*
* @return The overall number of characters printed to the string
*
- * @see snprint_ip4_cidr_addr
- * @see str_to_ip4_addr
- * @see cidr_str_to_ip4_addr_and_net_mask
+ * @see ::snprint_ip4_cidr_addr
+ * @see ::str_to_ip4_addr
+ * @see ::cidr_str_to_ip4_addr_and_net_mask
*/
- int snprint_ip4_addr( char *s, size_t max_len, const IP4_ADDR *p_addr, const char *info ) ;
+ size_t snprint_ip4_addr( char *s, size_t max_len, const IP4_ADDR *p_addr, const char *info ) ;
/**
- * @brief Print an IPv4 address plus net mask to string in CIDR notation.
+ * @brief Print an IPv4 address plus net mask in CIDR notation to a string
*
* The printed CIDR string is something like "172.16.3.250/24"
*
- * @param s The string buffer into which to print
- * @param max_len Maximum length of the string, i.e. size of the buffer
- * @param p_addr The IPv4 address
- * @param p_mask The IPv4 net mask
- * @param info An optional string which is prepended to the string, or NULL
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv4 address to be evaluated
+ * @param[in] p_mask The associated IPv4 net mask
+ * @param[in] info An optional string which is prepended to the string, or NULL
*
* @return The overall number of characters printed to the string
*
- * @see snprint_ip4_addr
- * @see str_to_ip4_addr
- * @see cidr_str_to_ip4_addr_and_net_mask
+ * @see ::snprint_ip4_addr
+ * @see ::str_to_ip4_addr
+ * @see ::cidr_str_to_ip4_addr_and_net_mask
*/
- int snprint_ip4_cidr_addr( char *s, size_t max_len, const IP4_ADDR *p_addr, const IP4_ADDR *p_mask, const char *info ) ;
+ size_t snprint_ip4_cidr_addr( char *s, size_t max_len, const IP4_ADDR *p_addr, const IP4_ADDR *p_mask, const char *info ) ;
/**
- * @brief Convert a string to an IP4_ADDR.
+ * @brief Convert a string to an ::IP4_ADDR
+ *
+ * If output parameter is specified as NULL then this function
+ * can be used to check if the IPv4 address string is formally correct.
*
- * @param p_addr Pointer to the IP4_ADDR variable, or NULL, in which case this
- * function can be used to check if the string is formally correct.
- * @param s The string to be converted
+ * @param[out] p_addr Pointer to an ::IP4_ADDR variable to be filled, or NULL
+ * @param[in] s An IPv4 address string to be converted
*
- * @return >= 0 on success, number of characters evaluated from the input string
- * -1 if invalid number found in string
- * -2 if separator is not a dot '.'
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
*
- * @see snprint_ip4_addr
- * @see snprint_ip4_cidr_addr
- * @see cidr_str_to_ip4_addr_and_net_mask
+ * @see ::snprint_ip4_addr
+ * @see ::snprint_ip4_cidr_addr
+ * @see ::cidr_str_to_ip4_addr_and_net_mask
*/
int str_to_ip4_addr( IP4_ADDR *p_addr, const char *s ) ;
/**
- * @brief Convert a string in CIDR notation to an IP4_ADDR and net mask.
+ * @brief Convert a string in CIDR notation to an ::IP4_ADDR and net mask
+ *
+ * If output parameters are specified as NULL then this function
+ * can be used to check if the CIDR string is formally correct.
*
- * @param p_addr Pointer to an IP4_ADDR variable for the IP4 address,
- * or NULL, in which case this function can be used
- * to check if the string is formally correct.
- * @param p_mask Pointer to an IP4_ADDR variable for the net mask,
- * or NULL, in which case this function can be used
- * to check if the string is formally correct.
- * @param cidr_str The string to be converted, in CIDR format, e.g. "172.16.3.250/24"
+ * @param[out] p_addr Pointer to an ::IP4_ADDR variable to be filled with
+ * the IPv4 address, or NULL
+ * @param[out] p_mask Pointer to an ::IP4_ADDR variable to be filled with
+ * the IPv4 net mask, or NULL
+ * @param[in] cidr_str The string to be converted, in CIDR format, e.g. "172.16.3.250/24"
*
- * @return >= 0 on success, number of characters evaluated from the input string
- * one of the ::MBG_LU_CODES on error
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
*
- * @see snprint_ip4_addr
- * @see snprint_ip4_cidr_addr
- * @see str_to_ip4_addr
+ * @see ::snprint_ip4_addr
+ * @see ::snprint_ip4_cidr_addr
+ * @see ::str_to_ip4_addr
*/
int cidr_str_to_ip4_addr_and_net_mask( IP4_ADDR *p_addr, IP4_ADDR *p_mask, const char *cidr_str ) ;
/**
- * @brief Print a MAC ID or similar array of octets to a string.
+ * @brief Count the number of sequential bits in an IPv6 net mask
+ *
+ * Counting starts from MSB, i.e. for 0xC0 and 0xC1 the results
+ * are both 2 since only the 2 MSBs are sequentially set.
+ *
+ * @param[in] p_mask The IPv6 net mask to be evaluated
+ *
+ * @return The number of sequential MSB bits set in *p_mask
+ *
+ * @see ::ip6_net_mask_from_cidr
+ */
+ int get_ip6_net_mask_bits( const IP6_ADDR *p_mask ) ;
+
+ /**
+ * @brief Print an IPv6 address in optimized format to a string
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv6 address to be evaluated
+ * @param[in] info An optional string which is prepended to the string, or NULL
+ *
+ * @return The overall number of characters printed to the string
+ *
+ * @see ::snprint_ip6_cidr_addr
+ * @see ::snprint_ip6_cidr_mask_addr
+ * @see ::str_to_ip6_addr
+ * @see ::cidr_str_to_ip6_addr_and_cidr_bits
+ * @see ::cidr_str_to_ip6_addr_and_net_mask
+ */
+ size_t snprint_ip6_addr( char *s, size_t max_len, const IP6_ADDR *p_addr, const char *info ) ;
+
+ /**
+ * @brief Print an IPv6 address plus net mask to string in CIDR notation
+ *
+ * The printed CIDR string is something like "2001:0DB8:0:CD30:EF45::/64"
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv6 address to be evaluated
+ * @param[in] p_mask The associated IPv6 net mask
+ * @param[in] info An optional string which is prepended to the string, or NULL
+ *
+ * @return The overall number of characters printed to the string
+ *
+ * @see ::snprint_ip6_addr
+ * @see ::snprint_ip6_cidr_mask_addr
+ * @see ::str_to_ip6_addr
+ * @see ::cidr_str_to_ip6_addr_and_cidr_bits
+ * @see ::cidr_str_to_ip6_addr_and_net_mask
+ */
+ size_t snprint_ip6_cidr_addr( char *s, size_t max_len, const IP6_ADDR *p_addr, const IP6_ADDR *p_mask, const char *info ) ;
+
+ /**
+ * @brief Print an IPv6 address plus number of net mask bits to string in CIDR notation
+ *
+ * The printed CIDR string is something like "2001:0DB8:0:CD30:EF45::/64"
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] p_addr The IPv6 address to be evaluated
+ * @param[in] cidr_mask_bits The CIDR number of bits specifying the IPv6 net mask
+ * @param[in] info An optional string which is prepended to the string, or NULL
+ *
+ * @return The overall number of characters printed to the string
+ *
+ * @see ::snprint_ip6_addr
+ * @see ::snprint_ip6_cidr_addr
+ * @see ::str_to_ip6_addr
+ * @see ::cidr_str_to_ip6_addr_and_cidr_bits
+ * @see ::cidr_str_to_ip6_addr_and_net_mask
+ */
+ size_t snprint_ip6_cidr_mask_addr( char *s, size_t max_len, const IP6_ADDR *p_addr, const int cidr_mask_bits, const char* info ) ;
+
+ /**
+ * @brief Convert a string to an ::IP6_ADDR
+ *
+ * If the output parameter is specified as NULL then this function
+ * can be used to check if the string is formally correct.
+ *
+ * On success ::IP6_ADDR variable contains the IPv6 address
+ * in little endian byte order.
+ *
+ * @param[out] p_addr Pointer to the ::IP6_ADDR variable, or NULL
+ * @param[in] s A string containing an IPv6 address
*
- * @param s The string buffer into which to print
- * @param max_len Maximum length of the string, i.e. size of the buffer
- * @param octets An array of octets
- * @param num_octets The number of octets to be printed from the array
- * @param sep The separator printed between the bytes, or 0
- * @param info An optional string which is prepended to the output, or NULL
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
+ *
+ * @see ::snprint_ip6_addr
+ * @see ::snprint_ip6_cidr_addr
+ * @see ::snprint_ip6_cidr_mask_addr
+ * @see ::str_to_ip6_addr
+ * @see ::cidr_str_to_ip6_addr_and_cidr_bits
+ * @see ::cidr_str_to_ip6_addr_and_net_mask
+ */
+ int str_to_ip6_addr( IP6_ADDR *p_addr, const char *s ) ;
+
+ /**
+ * @brief Convert a string in CIDR notation to an ::IP6_ADDR and net mask
+ *
+ * If output parameters are specified as NULL then this function
+ * can be used to check if the CIDR string is formally correct.
+ *
+ * @param[out] p_addr Pointer to an ::IP6_ADDR variable to be filled up
+ * with the IPv6 address, or NULL
+ * @param[out] p_mask Pointer to an ::IP6_ADDR variable to be filled up
+ with the net mask bits, or NULL
+ * @param[in] cidr_str The string to be converted, in CIDR format, e.g. "2001:0DB8:0:CD30::/64"
+ *
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
+ *
+ * @see ::snprint_ip4_addr
+ * @see ::snprint_ip4_cidr_addr
+ * @see ::str_to_ip4_addr
+ */
+ int cidr_str_to_ip6_addr_and_net_mask( IP6_ADDR *p_addr, IP6_ADDR *p_mask, const char *cidr_str ) ;
+
+ /**
+ * @brief Convert a string in CIDR notation to an ::IP6_ADDR and net mask bits
+ *
+ * If output parameters are specified as NULL then this function
+ * can be used to check if the CIDR string is formally correct.
+ *
+ * @param[out] p_addr Pointer to an ::IP6_ADDR variable for the IPv6 address, or NULL
+ * @param[out] p_cidr Pointer to an int variable for the net mask bits, or NULL
+ * @param[in] cidr_str The string to be converted, in CIDR format, e.g. "2001:0DB8:0:CD30::/64"
+ *
+ * @return A number >= 0 (::MBG_SUCCESS) according to the number of characters evaluated
+ * from the input string, or one of the @ref MBG_ERROR_CODES on error,
+ * specifically ::MBG_ERR_INV_PARM if an invalid number or character was found in the string.
+ *
+ * @see ::snprint_ip6_addr
+ * @see ::snprint_ip6_cidr_addr
+ * @see ::str_to_ip6_addr
+ */
+ int cidr_str_to_ip6_addr_and_cidr_bits( IP6_ADDR *p_addr, int *p_cidr, const char *cidr_str ) ;
+
+ /**
+ * @brief Compute an IPv6 net mask according to the number of CIDR netmask bits
+ *
+ * E.g. the 64 bits mentioned in "2001:0DB8:0:CD30::/64" result in 2^64,
+ * corresponding to FFFF:FFFF:FFFF:FFFF:: in IPv6 notation.
+ *
+ * @param[out] p_mask Pointer to an ::IP6_ADDR variable for the IPv6 netmask
+ * @param[in] netmask_bits Number of netmask bits from CIDR notation
+ *
+ * @see ::get_ip6_net_mask_bits
+ */
+ void ip6_net_mask_from_cidr( IP6_ADDR *p_mask, int netmask_bits ) ;
+
+ /**
+ * @brief Determine the network part of an IPv6 address based on the net mask
+ *
+ * E.g. IP "2001:0DB8:0:CD30::", net mask "FFFF:FFFF::" yields network part "2001:0DB8::".
+ *
+ * @param[out] p_net_part The extracted network part of the IPv6 address
+ * @param[in] p_addr The IPv6 address to be evaluated
+ * @param[in] p_mask The associated IPv6 net mask
+ */
+ void ip6_net_part_from_addr( IP6_ADDR *p_net_part, const IP6_ADDR *p_addr, const IP6_ADDR *p_mask ) ;
+
+ /**
+ * @brief Print a MAC ID or similar array of octets to a string
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Maximum length of the string, i.e. size of the buffer
+ * @param[in] octets An array of octets
+ * @param[in] num_octets The number of octets to be printed from the array
+ * @param[in] sep The separator printed between the bytes, or 0
+ * @param[in] info An optional string which is prepended to the output, or NULL
+ *
+ * @return The overall number of characters printed to the string
+ *
+ * @see ::snprint_mac_addr
+ * @see ::str_to_octets
+ * @see ::octets_are_all_zero
+ */
+ size_t snprint_octets( char *s, size_t max_len, const uint8_t *octets, int num_octets, char sep, const char *info ) ;
+
+ /**
+ * @brief Print a ::PTP_CLOCK_ID to a string
+ *
+ * @todo Eventually this function should be moved to a different module.
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Maximum length of the string, i.e. size of the buffer
+ * @param[in] p The ::PTP_CLOCK_ID to be printed
*
* @return The overall number of characters printed to the string
*
- * @see snprint_mac_addr
- * @see str_to_octets
- * @see check_octets_not_all_zero
+ * @see ::snprint_octets
*/
- int snprint_octets( char *s, size_t max_len, const uint8_t *octets, int num_octets, char sep, const char *info ) ;
+ size_t snprint_ptp_clock_id( char *s, size_t max_len, const PTP_CLOCK_ID *p ) ;
/**
- * @brief Print a MAC address to a string.
+ * @brief Print a MAC address to a string
*
- * @param s The string buffer into which to print
- * @param max_len Maximum length of the string, i.e. size of the buffer
- * @param p_mac_addr The MAC address to be printed
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Maximum length of the string, i.e. size of the buffer
+ * @param[in] p_mac_addr The MAC address to be printed
*
* @return The overall number of characters printed to the string
*
- * @see snprint_octets
- * @see str_to_octets
- * @see check_octets_not_all_zero
+ * @see ::snprint_octets
+ * @see ::str_to_octets
+ * @see ::octets_are_all_zero
*/
- int snprint_mac_addr( char *s, size_t max_len, const MBG_MAC_ADDR *p_mac_addr ) ;
+ size_t snprint_mac_addr( char *s, size_t max_len, const MBG_MAC_ADDR *p_mac_addr ) ;
/**
- * @brief Set a MAC ID or a similar array of octets from a string.
+ * @brief Set a MAC ID or a similar array of octets from a string
*
- * @param octets An array of octets to be set up
- * @param num_octets The number of octets which can be stored
- * @param s The string to be converted
+ * @param[out] octets An array of octets to be set up
+ * @param[in] num_octets The number of octets which can be stored
+ * @param[in] s The string to be converted
*
* @return The overall number of octets decoded from the string
*
- * @see snprint_octets
- * @see snprint_mac_addr
- * @see check_octets_not_all_zero
+ * @see ::snprint_octets
+ * @see ::snprint_mac_addr
+ * @see ::octets_are_all_zero
*/
int str_to_octets( uint8_t *octets, int num_octets, const char *s ) ;
/**
- * @brief Check if an array of octets is valid, i.e. != 0
+ * @brief Check if an array of octets is all zero
*
- * @param octets Pointer to the array of octets
- * @param num_octets Number of octets
+ * @param[in] octets Pointer to the array of octets
+ * @param[in] num_octets Number of octets
*
- * @return MBG_LU_SUCCESS octets are valid, i.e. not all 0
- * MBG_LU_ERR_NOT_SET octets are invalid, i.e. all 0
+ * @return true if all bytes are 0, else false
*
- * @see snprint_octets
- * @see snprint_mac_addr
- * @see str_to_octets
+ * @see ::snprint_octets
+ * @see ::snprint_mac_addr
+ * @see ::str_to_octets
*/
- int check_octets_not_all_zero( const uint8_t *octets, int num_octets ) ;
+ bool octets_are_all_zero( const uint8_t *octets, int num_octets ) ;
/**
- * @brief Check if an array of octets is valid, i.e. != 0
+ * @brief Check if a MAC address is all zero
*
- * @param p_addr Pointer to a MAC address
+ * @param[in] p_addr Pointer to a MAC address to be checked
*
- * @return MBG_LU_SUCCESS MAC address is valid, i.e. not all 0
- * MBG_LU_ERR_NOT_SET MAC address is invalid, i.e. all 0
+ * @return true if all bytes of the MAC address are 0, else false
*
- * @see check_octets_not_all_zero
+ * @see ::octets_are_all_zero
*/
- int check_mac_addr_not_all_zero( const MBG_MAC_ADDR *p_addr ) ;
+ bool mac_addr_is_all_zero( const MBG_MAC_ADDR *p_addr ) ;
/**
* @brief Do a SIOCGxxx IOCTL call to read specific information from a LAN interface
*
- * @param if_name Name of the interface
- * @param ioctl_code One of the predefined system SIOCGxxx IOCTL codes
- * @param p_ifreq Pointer to a request buffer
+ * @param[in] if_name Name of the interface
+ * @param[in] ioctl_code One of the predefined system SIOCGxxx IOCTL codes
+ * @param[out] p_ifreq Pointer to a request buffer
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
*/
int do_siocg_ioctl( const char *if_name, int ioctl_code, struct ifreq *p_ifreq ) ;
/**
- * @brief Retrieve the MAC address of a network interface
+ * @brief Retrieve the index of a specific network interface
*
- * @param if_name Name of the interface
- * @param p_mac_addr Pointer to the MAC address buffer to be filled up
+ * @param[in] if_name Name of the interface
+ * @param[out] p_intf_idx Pointer to a variable to be filled up
*
- * @return one of the ::MBG_LU_CODES
- * on error the MAC addr is set to all 0
- *
- * @see get_port_mac_addr_check
+ * @return One of the @ref MBG_RETURN_CODES.
+ * On error, *p_intf_idx is set to -1.
*/
- int get_port_mac_addr( const char *if_name, MBG_MAC_ADDR *p_mac_addr ) ;
+ int get_port_intf_idx( const char *if_name, int *p_intf_idx ) ;
/**
- * @brief Retrieve and check the MAC address of a network interface
- *
- * @param if_name Name of the interface
- * @param p_mac_addr Pointer to the MAC address buffer to be filled up
+ * @brief Retrieve the MAC address of a network interface
*
- * @return one of the ::MBG_LU_CODES
- * on error the MAC addr is set to all 0
+ * @param[in] if_name Name of the interface
+ * @param[out] p_mac_addr Pointer to the MAC address buffer to be filled up
*
- * @see get_port_mac_addr
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, the MAC address is set to all 0
*/
- int get_port_mac_addr_check( const char *if_name, MBG_MAC_ADDR *p_mac_addr ) ;
+ int get_port_mac_addr( const char *if_name, MBG_MAC_ADDR *p_mac_addr ) ;
/**
* @brief Check the link state of a network interface
*
- * @param if_name Name of the interface
+ * @param[in] if_name Name of the interface
*
- * @return 1 link detected on port
- * 0 no link detected on port
- * one of the ::MBG_LU_CODES in case of an error
+ * @return 1 if link detected on port,
+ * 0 if no link detected on port,
+ * one of the @ref MBG_ERROR_CODES in case of an error
*/
int check_port_link( const char *if_name ) ;
/**
* @brief Retrieve the IPv4 address of a network interface
*
- * @param if_name Name of the interface
- * @param p_addr Pointer to address field to be filled up
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr Pointer to address field to be filled up
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, *p_addr is set to all 0.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_addr( const char *if_name, IP4_ADDR *p_addr ) ;
/**
* @brief Retrieve the IPv4 net mask of a network interface
*
- * @param if_name Name of the interface
- * @param p_addr Pointer to address field to be filled up
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr Pointer to address field to be filled up
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, *p_addr is set to all 0.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_netmask( const char *if_name, IP4_ADDR *p_addr ) ;
/**
* @brief Retrieve the IPv4 broadcast address of a network interface
*
- * @param if_name Name of the interface
- * @param p_addr Pointer to address field to be filled up
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr Pointer to address field to be filled up
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, *p_addr is set to all 0.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_broad_addr( const char *if_name, IP4_ADDR *p_addr ) ;
/**
* @brief Retrieve the IPv4 gateway (default route)
*
- * @param p_addr Pointer to address field to be filled up
+ * @param[out] p_addr Pointer to address field to be filled up
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, *p_addr is set to all 0.
*/
int get_ip4_gateway( IP4_ADDR *p_addr ) ;
/**
* @brief Retrieve the IPv4 address of a network interface as string
*
- * @param if_name Name of the interface
- * @param p_addr_buf Pointer to the string buffer to be filled up
- * @param buf_size size of the string buffer
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr_buf Pointer to the string buffer to be filled up
+ * @param[in] buf_size size of the string buffer
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, a string according to "0.0.0.0" is generated.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_addr_str( const char *if_name, char *p_addr_buf, int buf_size ) ;
/**
* @brief Retrieve the IPv4 net mask of a network interface as string
*
- * @param if_name Name of the interface
- * @param p_addr_buf Pointer to the string buffer to be filled up
- * @param buf_size size of the string buffer
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr_buf Pointer to the string buffer to be filled up
+ * @param[in] buf_size size of the string buffer
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, a string according to "0.0.0.0" is generated.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_netmask_str( const char *if_name, char *p_addr_buf, int buf_size ) ;
/**
* @brief Retrieve the IPv4 broadcast address of a network interface as string
*
- * @param if_name Name of the interface
- * @param p_addr_buf Pointer to the string buffer to be filled up
- * @param buf_size size of the string buffer
+ * @param[in] if_name Name of the interface
+ * @param[out] p_addr_buf Pointer to the string buffer to be filled up
+ * @param[in] buf_size size of the string buffer
*
- * @return one of the ::MBG_LU_CODES
+ * @return One of the @ref MBG_RETURN_CODES
+ * On error, a string according to "0.0.0.0" is generated.
*
- * @see get_port_ip4_settings
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_settings
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_broad_addr_str( const char *if_name, char *p_addr_buf, int buf_size ) ;
/**
* @brief Retrieve the current IPv4 settings of a network interface
*
- * @param if_name Name of the interface
- * @param p Pointer to a IP4_SETTINGS structure to be filled up
+ * @param[in] if_name Name of the interface
+ * @param[out] p Pointer to a IP4_SETTINGS structure to be filled up
*
- * @return 0 on success, < 0 on error
+ * @return One of the @ref MBG_RETURN_CODES
*
- * @see get_port_ip4_addr
- * @see get_port_ip4_addr_str
- * @see get_port_ip4_netmask
- * @see get_port_ip4_netmask_str
- * @see get_port_ip4_broad_addr
- * @see get_port_ip4_broad_addr_str
- * @see get_specific_port_ip4_addr
+ * @see ::get_port_ip4_addr
+ * @see ::get_port_ip4_addr_str
+ * @see ::get_port_ip4_netmask
+ * @see ::get_port_ip4_netmask_str
+ * @see ::get_port_ip4_broad_addr
+ * @see ::get_port_ip4_broad_addr_str
+ * @see ::get_specific_port_ip4_addr
*/
int get_port_ip4_settings( const char *if_name, IP4_SETTINGS *p ) ;
diff --git a/mbglib/common/macioctl.h b/mbglib/common/macioctl.h
index f550a7c..aa4e894 100755
--- a/mbglib/common/macioctl.h
+++ b/mbglib/common/macioctl.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: macioctl.h 1.35 2013/04/11 13:46:05 martin REL_M $
+ * $Id: macioctl.h 1.37.1.9 2017/02/22 15:23:45 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -11,6 +11,24 @@
*
* -----------------------------------------------------------------------
* $Log: macioctl.h $
+ * Revision 1.37.1.9 2017/02/22 15:23:45 martin
+ * Fixed macro definition syntax to avoid clang compiler warnings.
+ * Revision 1.37.1.8 2016/09/20 13:34:38 martin
+ * Typo.
+ * Revision 1.37.1.7 2016/08/09 15:58:02 martin
+ * Attribute always_inline is now in __mbg_inline.
+ * Removed trailing spaces.
+ * Revision 1.37.1.6 2014/07/16 15:19:55 martin
+ * Revision 1.37.1.5 2014/06/26 11:15:38 martin
+ * Revision 1.37.1.4 2014/06/25 08:52:01 martin
+ * Support GPIO status.
+ * Revision 1.37.1.3 2014/06/25 08:31:14Z martin
+ * Revision 1.37.1.2 2014/05/26 16:01:57 martin
+ * Revision 1.37.1.1 2014/05/22 16:16:18 martin
+ * Revision 1.37 2014/05/19 15:57:25 martin
+ * Fixed grammar in a comment.
+ * Revision 1.36 2013/09/26 07:54:22 martin
+ * Support GNSS API.
* Revision 1.35 2013/04/11 13:46:05 martin
* Account for modified spinlock handling under Windows.
* Revision 1.34 2012/10/02 18:29:49Z martin
@@ -38,7 +56,7 @@
* Changes by Frank Kardel: Don't require copyin/copyout under NetBSD.
* Support NetBSD beside FreeBSD.
* Account for modified _pcpc_kfree().
- * Bug fix: Use PCPS_TIME_STAMP with
+ * Bug fix: Use PCPS_TIME_STAMP with
* IOCTL_GET_FAST_HR_TIMESTAMP as output size.
* Specify I/O range number when calling port I/O macros
* so they can be used for different ranges under BSD.
@@ -50,7 +68,7 @@
* Revision 1.33 2009/12/21 16:22:55 martin
* Moved code reading memory mapped timestamps to inline functions.
* Revision 1.32 2009/12/15 15:34:57 daniel
- * Support reading the raw IRIG data bits for firmware versions
+ * Support reading the raw IRIG data bits for firmware versions
* which support this feature.
* Revision 1.31 2009/11/04 14:58:52Z martin
* Conditionally exclude port status query from build.
@@ -84,7 +102,7 @@
* Revision 1.23 2008/12/11 10:30:38Z martin
* _pcps_get_cycles() is now called inside the low level routines
* immediately when the command byte is written.
- * Mutex for hardware access is now acquired/released in _pcps_sem_inc()
+ * Mutex for hardware access is now acquired/released in _pcps_sem_inc()
* and _pcps_sem_dec(), so other IOCTLs which don't access the card
* can be run in parallel.
* Moved definitions of _pcps_sem_inc(), _pcps_sem_dec(), and
@@ -93,14 +111,14 @@
* with certain PEX cards which have IRQs enabled).
* Use _pcps_sem_inc_safe() macro to check if access is safe and
* inhibit access if this is not the case.
- * Consistenly use pcps_drvr_name instead of mbgclock_name
+ * Consistenly use pcps_drvr_name instead of mbgclock_name
* for debug messages.
* Don't return error for unmap_mm...() under Linux.
* Account for ASIC_FEATURES being coded as flags, and account
* for new symbol PCI_ASIC_HAS_MM_IO.
* Handle new IOCTLs IOCTL_HAS_PCI_ASIC_FEATURES, IOCTL_HAS_PCI_ASIC_VERSION,
- * IOCTL_DEV_IS_MSF, IOCTL_DEV_IS_LWR, IOCTL_DEV_IS_WWVB,
- * IOCTL_GET_IRQ_STAT_INFO, IOCTL_GET_CYCLES_FREQUENCY,
+ * IOCTL_DEV_IS_MSF, IOCTL_DEV_IS_LWR, IOCTL_DEV_IS_WWVB,
+ * IOCTL_GET_IRQ_STAT_INFO, IOCTL_GET_CYCLES_FREQUENCY,
* IOCTL_HAS_FAST_HR_TIMESTAMP, and IOCTL_GET_FAST_HR_TIMESTAMP.
* Support mapped I/O resources.
* Revision 1.22 2008/01/17 09:28:49 daniel
@@ -132,17 +150,17 @@
* Revision 1.14 2004/12/09 11:03:36Z martin
* Support configuration of on-board frequency synthesizer.
* Revision 1.13 2004/11/09 12:47:19Z martin
- * Use new macro _pcps_ddev_has_gps_data() to check whether GPS large
+ * Use new macro _pcps_ddev_has_gps_data() to check whether GPS large
* data I/O is supported.
* Changes due to renamed symbols, IRIG RX/TX.
- * Modifications were required in order to be able to configure IRIG
+ * Modifications were required in order to be able to configure IRIG
* settings of cards which provide both IRIG input and output.
- * GPS169PCI cards with IRIG output and early firmware versions
- * used the same codes to configure the IRIG output as the TCR
- * cards use to configure the IRIG input. Those codes are now
+ * GPS169PCI cards with IRIG output and early firmware versions
+ * used the same codes to configure the IRIG output as the TCR
+ * cards use to configure the IRIG input. Those codes are now
* exclusively used to configure the IRIG input. A workaround
- * has been included for those GPS169PCI cards, because otherwise
- * the IRIG configuration would not work properly after a driver
+ * has been included for those GPS169PCI cards, because otherwise
+ * the IRIG configuration would not work properly after a driver
* update, without also doing a firmware update.
* Show debug msg if GPS169PCI workaround for IRIG cfg in effect.
* Use more specific data types than generic types.
@@ -175,7 +193,7 @@
* Support almost all IOCTL codes.
* Support for Win32.
* Revision 1.3 2001/11/30 09:52:47Z martin
- * Added support for event_time which, however, requires
+ * Added support for event_time which, however, requires
* a custom GPS firmware.
* Revision 1.2 2001/09/14 12:01:17 martin
* Decode PCPS_IOCTL_SET_GPS_CMD.
@@ -530,9 +548,14 @@ typedef struct
-#define TEST_MM_ACCESS_TIME ( 0 && defined( MBG_TGT_LINUX ) )
-#define TEST_MM_ACCESS_64 0
-#define TEST_FRAC_ONLY 0
+#if ( 0 && defined( MBG_TGT_LINUX ) )
+ #define TEST_MM_ACCESS_TIME 1
+#else
+ #define TEST_MM_ACCESS_TIME 0
+#endif
+
+#define TEST_MM_ACCESS_64 0
+#define TEST_FRAC_ONLY 0
#if TEST_MM_ACCESS_TIME
#include <pcpsutil.h>
@@ -604,6 +627,18 @@ typedef union
MBG_DEBUG_STATUS debug_status;
MBG_NUM_EVT_LOG_ENTRIES num_evt_log_entries;
MBG_EVT_LOG_ENTRY evt_log_entry;
+ MBG_GNSS_MODE_SETTINGS gnss_mode_settings;
+ MBG_GNSS_MODE_INFO gnss_mode_info;
+ ALL_GNSS_SAT_INFO_IDX all_gnss_sat_info_idx;
+ MBG_GPIO_CFG_LIMITS mbg_gpio_cfg_limits;
+ ALL_GPIO_INFO_IDX all_gpio_info_idx;
+ ALL_GPIO_STATUS_IDX all_gpio_status_idx;
+ MBG_GPIO_SETTINGS_IDX mbg_gpio_settings_idx;
+ XMULTI_REF_INSTANCES xmulti_ref_instances;
+ ALL_XMULTI_REF_STATUS_IDX all_xmulti_ref_status_idx;
+ ALL_XMULTI_REF_INFO_IDX all_xmulti_ref_info_idx;
+ XMULTI_REF_SETTINGS_IDX xmulti_ref_settings_idx;
+ XMR_HOLDOVER_STATUS xmr_holdover_status;
PCPS_MAPPED_MEM mapped_mem;
@@ -622,7 +657,7 @@ typedef union
#if defined( __GNUC__ )
// Avoid "no previous prototype" with some gcc versions.
static __mbg_inline
-void swap_tstamp( PCPS_TIME_STAMP *p_ts ) __attribute__((always_inline));
+void swap_tstamp( PCPS_TIME_STAMP *p_ts );
#endif
static __mbg_inline
@@ -639,7 +674,7 @@ void swap_tstamp( PCPS_TIME_STAMP *p_ts )
#if defined( __GNUC__ )
// Avoid "no previous prototype" with some gcc versions.
static __mbg_inline
-void do_get_fast_hr_timestamp_safe( PCPS_DDEV *pddev, PCPS_TIME_STAMP *p_ts ) __attribute__((always_inline));
+void do_get_fast_hr_timestamp_safe( PCPS_DDEV *pddev, PCPS_TIME_STAMP *p_ts );
#endif
@@ -739,7 +774,7 @@ void do_get_fast_hr_timestamp_safe( PCPS_DDEV *pddev, PCPS_TIME_STAMP *p_ts )
#if defined( __GNUC__ )
// Avoid "no previous prototype" with some gcc versions.
static __mbg_inline
-void do_get_fast_hr_timestamp_cycles_safe( PCPS_DDEV *pddev, PCPS_TIME_STAMP_CYCLES *p_ts_cyc ) __attribute__((always_inline));
+void do_get_fast_hr_timestamp_cycles_safe( PCPS_DDEV *pddev, PCPS_TIME_STAMP_CYCLES *p_ts_cyc );
#endif
static __mbg_inline
@@ -767,21 +802,24 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
#if defined( MBG_TGT_WIN32 )
IRP *pIrp, int *ret_size, uint16_t pout_size,
#endif
- void *pin, void *pout ) __attribute__((always_inline));
+ void *pin, void *pout );
#endif
/**
- * @brief Decode an handle IOCTL commands.
+ * @brief Decode and handle IOCTL commands
*
* This function is called from the OS dependent IOCTL handlers.
*
* @param pddev Pointer to the device structure
- * @param ioctl_code The IOCTL code to be handled
+ * @param ioctl_code The IOCTL code to be handled */
#if defined( MBG_TGT_WIN32 )
- * @param pIrp The IRP associated to the IOCTL call
+/**
+ * @param pIrp The IRP associated with the IOCTL call
* @param ret_size The number of bytes to be returned
* @param pout_size The size of the output buffer
+ */
#endif
+ /**
* @param pin The input buffer
* @param pout The output buffer
*
@@ -1085,6 +1123,15 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
break;
+ #if _MBG_SUPP_VAR_ACC_SIZE // otherwise generic IOCTL functions are used instead
+ case IOCTL_GET_ALL_GNSS_SAT_INFO:
+ _io_read_gps_chk( pddev, PC_GPS_ALL_GNSS_SAT_INFO, all_gnss_sat_info_idx, pout,
+ pout_size, _pcps_ddev_is_gnss( pddev ) );
+ break;
+ #endif
+
+
+
// Commands returning device capabilities and features
case IOCTL_DEV_IS_GPS:
@@ -1112,6 +1159,11 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
break;
+ case IOCTL_DEV_IS_GNSS:
+ _report_cond( _pcps_ddev_is_gnss( pddev ), pout );
+ break;
+
+
case IOCTL_DEV_IS_IRIG_RX:
_report_cond( _pcps_ddev_is_irig_rx( pddev ), pout );
break;
@@ -1302,6 +1354,17 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
break;
+ case IOCTL_DEV_HAS_GPIO:
+ _report_cond( _pcps_ddev_has_gpio( pddev ), pout );
+ break;
+
+
+ case IOCTL_DEV_HAS_XMR:
+ _report_cond( _pcps_ddev_has_xmr( pddev ), pout );
+ break;
+
+
+
// The next codes are somewhat special since they change something
// on the board but do not affect basic operation
@@ -1323,6 +1386,7 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
break;
+
// Status information which may not be available for everybody
case IOCTL_GET_GPS_POS:
@@ -1330,6 +1394,7 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
break;
+
// Codes reading device configuration
case IOCTL_GET_PCPS_SERIAL:
@@ -1465,6 +1530,116 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
break;
+ case IOCTL_PCPS_GENERIC_READ:
+ #if USE_IOCTL_GENERIC_REQ
+ _iob_from_pin_var( iob.req, pin );
+ p_buff_out = _pcps_kmalloc( iob.req.out_sz );
+
+ if ( p_buff_out == NULL )
+ {
+ _mbgddmsg_4( MBG_DBG_INFO, "%s: unable to alloc %lu bytes for %s, cmd: %02lX",
+ pcps_driver_name, (ulong) iob.req.out_sz,
+ "IOCTL_PCPS_GENERIC_READ", (ulong) iob.req.info );
+ goto err_no_mem;
+ }
+
+ _pcps_sem_inc_safe( pddev );
+ rc = _pcps_read( pddev, (uint8_t) iob.req.info, p_buff_out,
+ (uint8_t) iob.req.out_sz );
+ _pcps_sem_dec( pddev );
+
+ if ( rc == MBG_SUCCESS )
+ _frc_iob_to_pout( p_buff_out, iob.req.out_p, iob.req.out_sz );
+
+ _pcps_kfree( p_buff_out, iob.req.out_sz );
+
+ if ( rc != MBG_SUCCESS )
+ goto err_access;
+
+ #else
+
+ _iob_from_pin_var( iob.ctl, pin );
+ buffer_size = sizeof( iob.ctl ) + iob.ctl.data_size_out;
+ p_buff = _pcps_kmalloc( buffer_size );
+
+ if ( p_buff == NULL )
+ goto err_no_mem;
+
+ _pcps_sem_inc_safe( pddev );
+ rc = _pcps_read( pddev, (uint8_t) iob.ctl.info, p_buff->data,
+ (uint8_t) iob.ctl.data_size_out );
+ _pcps_sem_dec( pddev );
+
+ if ( rc == MBG_SUCCESS )
+ {
+ p_buff->ctl = iob.ctl;
+ _iob_to_pout( p_buff, pout, buffer_size ); //##+++++++ need to check this !!
+ }
+
+ _pcps_kfree( p_buff, buffer_size );
+
+ if ( rc != MBG_SUCCESS )
+ goto err_access;
+
+ #endif
+ break;
+
+
+ case IOCTL_PCPS_GENERIC_READ_GPS:
+ #if USE_IOCTL_GENERIC_REQ
+ _iob_from_pin_var( iob.req, pin );
+ p_buff_out = _pcps_kmalloc( iob.req.out_sz );
+
+ if ( p_buff_out == NULL )
+ {
+ _mbgddmsg_4( MBG_DBG_INFO, "%s: unable to alloc %lu bytes for %s, GPS cmd: %02lX",
+ pcps_driver_name, (ulong) iob.req.out_sz,
+ "IOCTL_PCPS_GENERIC_READ_GPS", (ulong) iob.req.info );
+ goto err_no_mem;
+ }
+
+ _pcps_sem_inc_safe( pddev );
+ rc = pcps_read_gps( pddev, (uint8_t) iob.req.info, p_buff_out,
+ (uint16_t) iob.req.out_sz );
+ _pcps_sem_dec( pddev );
+
+ if ( rc == MBG_SUCCESS )
+ _frc_iob_to_pout( p_buff_out, iob.req.out_p, iob.req.out_sz );
+
+ _pcps_kfree( p_buff_out, iob.req.out_sz );
+
+ if ( rc != MBG_SUCCESS )
+ goto err_access;
+
+ #else
+
+ _iob_from_pin_var( iob.ctl, pin );
+ buffer_size = sizeof( iob.ctl ) + iob.ctl.data_size_out;
+ p_buff = _pcps_kmalloc( buffer_size );
+
+ if ( p_buff == NULL )
+ goto err_no_mem;
+
+ _pcps_sem_inc_safe( pddev );
+ rc = pcps_read_gps( pddev, (uint8_t) iob.ctl.info, p_buff->data,
+ (uint16_t) iob.ctl.data_size_out );
+ _pcps_sem_dec( pddev );
+
+ if ( rc == MBG_SUCCESS )
+ {
+ p_buff->ctl = iob.ctl;
+ _iob_to_pout( p_buff, pout, buffer_size ); //##+++++++ need to check this !!
+ }
+
+ _pcps_kfree( p_buff, buffer_size );
+
+ if ( rc != MBG_SUCCESS )
+ goto err_access;
+
+ #endif
+ break;
+
+
#if _MBG_SUPP_VAR_ACC_SIZE
// These codes are only supported on target systems where a variable size of
@@ -1494,9 +1669,55 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
pout, pout_size, _pcps_ddev_has_ptp_unicast( pddev ) );
break;
+
+ case IOCTL_GET_ALL_GPIO_INFO:
+ _io_read_gps_chk( pddev, PC_GPS_ALL_GPIO_INFO, all_gpio_info_idx,
+ pout, pout_size, _pcps_ddev_has_gpio( pddev ) );
+ break;
+
+
+ case IOCTL_GET_ALL_GPIO_STATUS:
+ _io_read_gps_var_chk( pddev, PC_GPS_ALL_GPIO_STATUS, all_gpio_status_idx,
+ pout, _pcps_ddev_has_gpio( pddev ) ); //##++++++++++++++++++++++++ condition??
+ break;
+
+
+ case IOCTL_GET_ALL_XMR_STATUS:
+ _io_read_gps_chk( pddev, PC_GPS_ALL_XMR_STATUS, all_xmulti_ref_status_idx,
+ pout, pout_size, _pcps_ddev_has_xmr( pddev ) );
+ break;
+
+
+ case IOCTL_GET_ALL_XMR_INFO:
+ _io_read_gps_chk( pddev, PC_GPS_ALL_XMR_INFO, all_xmulti_ref_info_idx,
+ pout, pout_size, _pcps_ddev_has_xmr( pddev ) );
+ break;
+
#endif // _MBG_SUPP_VAR_ACC_SIZE
+ case IOCTL_GET_GNSS_MODE_INFO:
+ _io_read_gps_var_chk( pddev, PC_GPS_GNSS_MODE, gnss_mode_info,
+ pout, _pcps_ddev_is_gnss( pddev ) );
+ break;
+
+ case IOCTL_GET_GPIO_CFG_LIMITS:
+ _io_read_gps_var_chk( pddev, PC_GPS_GPIO_CFG_LIMITS, mbg_gpio_cfg_limits,
+ pout, _pcps_ddev_has_gpio( pddev ) );
+ break;
+
+ case IOCTL_GET_XMR_INSTANCES:
+ _io_read_gps_var_chk( pddev, PC_GPS_XMR_INSTANCES, xmulti_ref_instances,
+ pout, _pcps_ddev_has_xmr( pddev ) );
+ break;
+
+ case IOCTL_GET_XMR_HOLDOVER_STATUS:
+ _io_read_gps_var_chk( pddev, PC_GPS_XMR_HOLDOVER_STATUS, xmr_holdover_status,
+ pout, _pcps_ddev_has_xmr( pddev ) );
+ break;
+
+
+
// Codes writing device configuration
case IOCTL_SET_PCPS_SERIAL:
@@ -1616,6 +1837,19 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
break;
+ case IOCTL_SET_GNSS_MODE_SETTINGS:
+ _io_write_gps_var_chk( pddev, PC_GPS_GNSS_MODE, gnss_mode_settings, pin,
+ _pcps_ddev_is_gnss( pddev ) );
+ break;
+
+
+ case IOCTL_SET_GPIO_SETTINGS_IDX:
+ _io_write_var_chk( pddev, PC_GPS_GPIO_SETTINGS_IDX, mbg_gpio_settings_idx,
+ pin, _pcps_ddev_has_gpio( pddev ) );
+ break;
+
+
+
// Operations which may severely affect system operation
case IOCTL_SET_PCPS_TIME:
@@ -1656,62 +1890,13 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
break;
- // Generic read/write operations which can do anything
-
- case IOCTL_PCPS_GENERIC_READ:
- #if USE_IOCTL_GENERIC_REQ
- _iob_from_pin_var( iob.req, pin );
- p_buff_out = _pcps_kmalloc( iob.req.out_sz );
-
- if ( p_buff_out == NULL )
- {
- _mbgddmsg_4( MBG_DBG_INFO, "%s: unable to alloc %lu bytes for %s, cmd: %02lX",
- pcps_driver_name, (ulong) iob.req.out_sz,
- "IOCTL_PCPS_GENERIC_READ", (ulong) iob.req.info );
- goto err_no_mem;
- }
-
- _pcps_sem_inc_safe( pddev );
- rc = _pcps_read( pddev, (uint8_t) iob.req.info, p_buff_out,
- (uint8_t) iob.req.out_sz );
- _pcps_sem_dec( pddev );
-
- if ( rc == MBG_SUCCESS )
- _frc_iob_to_pout( p_buff_out, iob.req.out_p, iob.req.out_sz );
-
- _pcps_kfree( p_buff_out, iob.req.out_sz );
-
- if ( rc != MBG_SUCCESS )
- goto err_access;
-
- #else
-
- _iob_from_pin_var( iob.ctl, pin );
- buffer_size = sizeof( iob.ctl ) + iob.ctl.data_size_out;
- p_buff = _pcps_kmalloc( buffer_size );
-
- if ( p_buff == NULL )
- goto err_no_mem;
-
- _pcps_sem_inc_safe( pddev );
- rc = _pcps_read( pddev, (uint8_t) iob.ctl.info, p_buff->data,
- (uint8_t) iob.ctl.data_size_out );
- _pcps_sem_dec( pddev );
-
- if ( rc == MBG_SUCCESS )
- {
- p_buff->ctl = iob.ctl;
- _iob_to_pout( p_buff, pout, buffer_size ); //##+++++++ need to check this !!
- }
+ case IOCTL_SET_XMR_SETTINGS_IDX:
+ _io_write_gps_var( pddev, PC_GPS_XMR_SETTINGS_IDX, xmulti_ref_settings_idx, pin );
+ break;
- _pcps_kfree( p_buff, buffer_size );
- if ( rc != MBG_SUCCESS )
- goto err_access;
-
- #endif
- break;
+ // Generic read/write operations which can do anything
case IOCTL_PCPS_GENERIC_WRITE:
#if USE_IOCTL_GENERIC_REQ
@@ -1763,61 +1948,6 @@ int ioctl_switch( PCPS_DDEV *pddev, unsigned int ioctl_code,
break;
- case IOCTL_PCPS_GENERIC_READ_GPS:
- #if USE_IOCTL_GENERIC_REQ
- _iob_from_pin_var( iob.req, pin );
- p_buff_out = _pcps_kmalloc( iob.req.out_sz );
-
- if ( p_buff_out == NULL )
- {
- _mbgddmsg_4( MBG_DBG_INFO, "%s: unable to alloc %lu bytes for %s, GPS cmd: %02lX",
- pcps_driver_name, (ulong) iob.req.out_sz,
- "IOCTL_PCPS_GENERIC_READ_GPS", (ulong) iob.req.info );
- goto err_no_mem;
- }
-
- _pcps_sem_inc_safe( pddev );
- rc = pcps_read_gps( pddev, (uint8_t) iob.req.info, p_buff_out,
- (uint16_t) iob.req.out_sz );
- _pcps_sem_dec( pddev );
-
- if ( rc == MBG_SUCCESS )
- _frc_iob_to_pout( p_buff_out, iob.req.out_p, iob.req.out_sz );
-
- _pcps_kfree( p_buff_out, iob.req.out_sz );
-
- if ( rc != MBG_SUCCESS )
- goto err_access;
-
- #else
-
- _iob_from_pin_var( iob.ctl, pin );
- buffer_size = sizeof( iob.ctl ) + iob.ctl.data_size_out;
- p_buff = _pcps_kmalloc( buffer_size );
-
- if ( p_buff == NULL )
- goto err_no_mem;
-
- _pcps_sem_inc_safe( pddev );
- rc = pcps_read_gps( pddev, (uint8_t) iob.ctl.info, p_buff->data,
- (uint16_t) iob.ctl.data_size_out );
- _pcps_sem_dec( pddev );
-
- if ( rc == MBG_SUCCESS )
- {
- p_buff->ctl = iob.ctl;
- _iob_to_pout( p_buff, pout, buffer_size ); //##+++++++ need to check this !!
- }
-
- _pcps_kfree( p_buff, buffer_size );
-
- if ( rc != MBG_SUCCESS )
- goto err_access;
-
- #endif
- break;
-
-
case IOCTL_PCPS_GENERIC_WRITE_GPS:
#if USE_IOCTL_GENERIC_REQ
_iob_from_pin_var( iob.req, pin );
diff --git a/mbglib/common/mbg_arch.h b/mbglib/common/mbg_arch.h
index 726e679..a08ec76 100755
--- a/mbglib/common/mbg_arch.h
+++ b/mbglib/common/mbg_arch.h
@@ -1,15 +1,25 @@
/**************************************************************************
*
- * $Id: mbg_arch.h 1.4 2012/10/02 18:32:00 martin REL_M $
+ * $Id: mbg_arch.h 1.6 2017/01/27 09:03:16 martin REL_M $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
* Description:
* Definitions to support different computer hardware architectures.
*
+ * For a good summary of predefined macros which can be used to determine
+ * the build environment, the target environment, and architecture, see:
+ * http://sourceforge.net/p/predef/wiki/Home/
+ *
* -----------------------------------------------------------------------
* $Log: mbg_arch.h $
+ * Revision 1.6 2017/01/27 09:03:16 martin
+ * Added macros _mbg_swab8() and _mbg_swab64().
+ * Fixed macro syntax.
+ * Modified _swab_dummy() to avoid compiler warnings due to unused variables.
+ * Revision 1.5 2014/03/11 16:01:55 martin
+ * Added a comment.
* Revision 1.4 2012/10/02 18:32:00 martin
* Include words.h and, conditionally, stdlib.h.
* Use generic preprocessor symbol MBG_TGT_KERNEL.
@@ -64,7 +74,7 @@
// to access unaligned data.
#if !defined( _mbg_put_unaligned )
- #define _mbg_put_unaligned( _v, _p ) ((void)( *(_p) = (_v) ))
+ #define _mbg_put_unaligned( _v, _p ) do { ((void)( *(_p) = (_v) )); } while ( 0 )
#endif
#if !defined( _mbg_get_unaligned )
@@ -117,8 +127,9 @@
-// swap a double type variable bytewise e.g. to convert the endianess
-
+/**
+ * @brief Swap a 'double' type variable bytewise e.g. to convert the endianess
+ */
static __mbg_inline
void mbg_swab_double( double *p )
{
@@ -141,22 +152,27 @@ void mbg_swab_double( double *p )
#if defined( MBG_ARCH_BIG_ENDIAN )
- #define _mbg_swab16( _p ) *(_p) = __swab16( *(_p) )
- #define _mbg_swab32( _p ) *(_p) = __swab32( *(_p) )
+ #define _mbg_swab8( _p ) _nop_macro_fnc() // always a dummy, but for completeness ...
+ #define _mbg_swab16( _p ) do { *(_p) = __swab16( *(_p) ); } while ( 0 )
+ #define _mbg_swab32( _p ) do { *(_p) = __swab32( *(_p) ); } while ( 0 )
+ #define _mbg_swab64( _p ) do { *(_p) = __swab64( *(_p) ); } while ( 0 )
#define _mbg_swab_double( _p ) mbg_swab_double( _p )
#define _mbg_swab_doubles( _p, _n ) \
+ do \
{ \
int i; \
for ( i = 0; i < (_n); i++ ) \
_mbg_swab_double( &_p[i] ); \
- }
+ } while ( 0 )
#else
+ #define _mbg_swab8( _p ) _nop_macro_fnc()
#define _mbg_swab16( _p ) _nop_macro_fnc()
#define _mbg_swab32( _p ) _nop_macro_fnc()
+ #define _mbg_swab64( _p ) _nop_macro_fnc()
#define _mbg_swab_double( _p ) _nop_macro_fnc()
@@ -164,4 +180,16 @@ void mbg_swab_double( double *p )
#endif
+
+
+
+/**
+ * @brief A placeholder for yet missing _mbg_swab_..() macros
+ *
+ * We don't just use the _nop_macro_fnc() macros here to avoid
+ * compiler warnings 'unused variable'.
+ */
+#define _mbg_swab_dummy( _x ) do { (void) _x; } while ( 0 )
+
+
#endif /* _MBG_ARCH_H */
diff --git a/mbglib/common/mbg_cof.h b/mbglib/common/mbg_cof.h
new file mode 100755
index 0000000..0c0e96f
--- /dev/null
+++ b/mbglib/common/mbg_cof.h
@@ -0,0 +1,88 @@
+
+/**************************************************************************
+ *
+ * $Id: mbg_cof.h 1.1.1.3 2016/08/10 14:19:00 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Container macros (see Linux Kernel)
+ *
+ * -----------------------------------------------------------------------
+ * $Log: mbg_cof.h $
+ * Revision 1.1.1.3 2016/08/10 14:19:00 martin
+ * *** empty log message ***
+ * Revision 1.1.1.2 2016/08/10 14:15:14 martin
+ * *** empty log message ***
+ * Revision 1.1.1.1 2016/08/09 15:59:01 martin
+ * Preliminary compatibility changes.
+ * Revision 1.1 2015/09/09 10:42:27 martin
+ * Initial revision by philipp.
+ *
+ **************************************************************************/
+
+#ifndef _MBG_COF_H
+#define _MBG_COF_H
+
+/* Other headers to be included */
+
+#include <mbg_tgt.h>
+
+#if !defined( MBG_TGT_KERNEL )
+ #include <stddef.h> // for offsetof()
+#endif
+
+
+#ifdef _MBG_COF
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+#if defined( MBG_TGT_POSIX )
+
+ // A special construct supported by gcc/clang and and implemented
+ // e.g. in the Linux kernel, which is said to be very type-safe:
+ #define mbg_container_of( _ptr, _type, _member ) ({ \
+ const typeof( ((_type *)0)->_member ) *__mptr = (_ptr); \
+ (_type *)((char *)__mptr - offsetof(_type,_member));})
+
+#else
+
+ // A different implementation in ANSI C, which supports type-checking anyway:
+ #define mbg_container_of( _ptr, _type, _member ) \
+ ( (_type *)( (char *)(1 ? (_ptr) : &((_type *)0)->_member) - offsetof( _type, _member )))
+
+#endif
+
+
+/* function prototypes: */
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+/* (no header definitions found) */
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+/* End of header body */
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _MBG_COF_H */
diff --git a/mbglib/common/mbg_daemonize.c b/mbglib/common/mbg_daemonize.c
new file mode 100755
index 0000000..7182138
--- /dev/null
+++ b/mbglib/common/mbg_daemonize.c
@@ -0,0 +1,231 @@
+
+/**************************************************************************
+ *
+ * $Id: mbg_daemonize.c 1.4.1.1 2014/04/15 13:39:36 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * NTP shared memory support functions.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: mbg_daemonize.c $
+ * Revision 1.4.1.1 2014/04/15 13:39:36 martin
+ * Revision 1.4 2013/07/30 15:30:49 martin
+ * Revision 1.3 2013/07/30 12:53:49 martin
+ * Revision 1.2 2013/07/24 15:29:38 martin
+ * Revision 1.1 2013/07/23 16:10:18 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#define _GNU_SOURCE // required for strsignal() in old glibc versions
+
+#define _MBG_DAEMONIZE
+ #include <mbg_daemonize.h>
+#undef _MBG_DAEMONIZE
+
+#include <mbg_pidfile.h>
+
+#include <unistd.h>
+#include <stdlib.h>
+#include <syslog.h>
+#include <errno.h>
+#include <string.h>
+#include <fcntl.h>
+#include <signal.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+
+
+static /*HDR*/
+void close_files_and_redirect_stdio( void )
+{
+ int i;
+
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Going to close all file handles, table size: %i, PID fd: %i",
+ getdtablesize(), glb_pid_fd );
+ #endif
+
+ // close all file descriptors, except the PID file descriptor
+
+ for ( i = getdtablesize(); i >= 0; --i )
+ {
+ if ( i != glb_pid_fd )
+ {
+ int rc = close( i );
+
+ if ( rc < 0 )
+ {
+ #if !defined( DEBUG ) || ( DEBUG < 2 )
+ if ( errno != EBADF )
+ #endif
+ syslog( LOG_DEBUG, "Failed to close fd %i: %s", i, strerror( errno ) );
+ }
+ else
+ {
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "fd %i closed successfully", i );
+ #endif
+ }
+ }
+ else
+ {
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Not closing PID fd %i", i );
+ #endif
+ }
+ }
+
+ // handle standard I/O
+
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Going to open /dev/null as stdin, stdout, and stderr" );
+ #endif
+
+ if ( ( i = open( "/dev/null", O_RDWR ) ) == -1 ) // stdin
+ syslog( LOG_ERR, "Failed to open /dev/null as stdin: %s", strerror( errno ) );
+
+ if ( dup( i ) == -1 ) // stdout
+ syslog( LOG_ERR, "Failed dup stdin as stdout: %s", strerror( errno ) );
+
+ if ( dup( i ) == -1 ) // stderr
+ syslog( LOG_ERR, "Failed dup stdin as stderr: %s", strerror( errno ) );
+
+} // close_files_and_redirect_stdio
+
+
+
+static /*HDR*/
+void set_running_dir( const char *new_dir )
+{
+ // change running dir
+ int rc = chdir( new_dir );
+
+ if ( rc == -1 )
+ syslog( LOG_WARNING, "Failed to chdir to \"%s\": %s", new_dir, strerror( errno ) );
+ else
+ {
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Successfully called chdir to \"%s\"", new_dir );
+ #endif
+ }
+
+} // set_running_dir
+
+
+
+static /*HDR*/
+void set_signal_handling( void (*new_signal_handler)( int sig ) )
+{
+ struct sigaction new_sig_action;
+ sigset_t new_sig_set;
+
+ // Set signal mask - signals we want to block
+ sigemptyset( &new_sig_set );
+ sigaddset( &new_sig_set, SIGCHLD ); // ignore child - i.e. we don't need to wait for it
+ sigaddset( &new_sig_set, SIGTSTP ); // ignore TTY stop signals
+ sigaddset( &new_sig_set, SIGTTOU ); // ignore TTY background writes
+ sigaddset( &new_sig_set, SIGTTIN ); // ignore TTY background reads
+ sigprocmask( SIG_BLOCK, &new_sig_set, NULL ); // block the signals specified above
+
+ // Set up a signal handler
+ new_sig_action.sa_handler = new_signal_handler;
+ sigemptyset(&new_sig_action.sa_mask);
+ new_sig_action.sa_flags = 0;
+
+ // Signals to handle
+ sigaction( SIGHUP, &new_sig_action, NULL ); // catch hangup signal
+ sigaction( SIGTERM, &new_sig_action, NULL ); // catch term signal
+ sigaction( SIGINT, &new_sig_action, NULL ); // catch interrupt signal
+
+} // set_signal_handling
+
+
+
+static /*HDR*/
+void signal_handler( int sig )
+{
+ switch ( sig )
+ {
+ case SIGHUP:
+ syslog( LOG_WARNING, "Received SIGHUP signal." );
+ break;
+
+ case SIGINT:
+ case SIGTERM:
+ syslog( LOG_INFO, "Daemon exiting" );
+ exit( EXIT_SUCCESS );
+ break;
+
+ default:
+ syslog( LOG_WARNING, "Unhandled signal %s", strsignal( sig ) );
+ break;
+
+ } // switch
+
+} // signal_handler
+
+
+
+/*HDR*/
+void mbg_daemonize( const char *running_dir )
+{
+ int i;
+
+ if ( getppid() == 1 ) // already a daemon
+ {
+ syslog( LOG_WARNING, "Already daemon with PID %i when mbg_daemonize() was called", getpid() );
+ return;
+ }
+
+ set_signal_handling( signal_handler );
+
+ i = fork();
+
+ if ( i < 0 ) // failed to fork
+ {
+ syslog( LOG_ERR, "Failed to fork: %s", strerror( errno ) );
+ exit( EXIT_FAILURE );
+ }
+
+ if ( i > 0 ) // we are the parent
+ {
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Child process %i created successfully, parent %i exiting now", i, getpid() );
+ #endif
+ exit( EXIT_SUCCESS ); // parent exits now
+ }
+
+ // we are the child process which continues
+
+ i = setsid(); // get a new process group
+
+ if ( i < 0 ) // failed to fork
+ {
+ syslog( LOG_ERR, "Failed to get new session ID: %s", strerror( errno ) );
+ exit( EXIT_FAILURE );
+ }
+
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Got new session ID %i", i );
+ #endif
+
+
+ close_files_and_redirect_stdio();
+
+
+ // TODO: check if this should be done earlier, right after fork
+ umask( 027 ); // restrict file permissions to 0750
+
+
+ set_running_dir( running_dir ? running_dir : DEFAULT_RUNNING_DIR );
+
+ // we are the first instance, so continue
+
+ if ( mbg_pidfile_write_own_pid() < 0 )
+ exit( EXIT_FAILURE );
+
+} // mbg_daemonize
+
diff --git a/mbglib/common/mbg_daemonize.h b/mbglib/common/mbg_daemonize.h
new file mode 100755
index 0000000..6387d3c
--- /dev/null
+++ b/mbglib/common/mbg_daemonize.h
@@ -0,0 +1,77 @@
+
+/**************************************************************************
+ *
+ * $Id: mbg_daemonize.h 1.2 2013/07/30 15:30:49 martin REL_M $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Definitions and prototypes for mbg_daemonize.c.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: mbg_daemonize.h $
+ * Revision 1.2 2013/07/30 15:30:49 martin
+ * Revision 1.1 2013/07/23 16:10:18 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#ifndef _MBG_DAEMONIZE_H
+#define _MBG_DAEMONIZE_H
+
+
+/* Other headers to be included */
+
+
+
+#ifdef _MBG_DAEMONIZE
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#if 0 && defined( _USE_PACK ) // use default alignment
+ #pragma pack( 1 ) // set byte alignment
+ #define _USING_BYTE_ALIGNMENT
+#endif
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#define DEFAULT_RUNNING_DIR "/"
+#define DEFAULT_PIDFILE_DIR "/var/run/"
+
+
+/* function prototypes: */
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+ void mbg_daemonize( const char *running_dir ) ;
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+
+#if defined( _USING_BYTE_ALIGNMENT )
+ #pragma pack() // set default alignment
+ #undef _USING_BYTE_ALIGNMENT
+#endif
+
+/* End of header body */
+
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _MBG_DAEMONIZE_H */
diff --git a/mbglib/common/mbg_pidfile.c b/mbglib/common/mbg_pidfile.c
new file mode 100755
index 0000000..8e7a9ba
--- /dev/null
+++ b/mbglib/common/mbg_pidfile.c
@@ -0,0 +1,334 @@
+
+/**************************************************************************
+ *
+ * $Id: mbg_pidfile.c 1.5 2014/07/16 15:19:55 martin REL_M $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Functions to handle a PID file.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: mbg_pidfile.c $
+ * Revision 1.5 2014/07/16 15:19:55 martin
+ * Revision 1.4 2013/08/01 16:17:01 martin
+ * Revision 1.3 2013/07/30 15:30:49 martin
+ * Revision 1.2 2013/07/24 15:29:38 martin
+ * Revision 1.1 2013/07/23 16:10:18 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#define _MBG_PIDFILE
+ #include <mbg_pidfile.h>
+#undef _MBG_PIDFILE
+
+#include <unistd.h>
+#include <stdio.h>
+#include <syslog.h>
+#include <errno.h>
+#include <string.h>
+#include <fcntl.h>
+#include <sys/file.h>
+
+
+#define USE_ATEXIT_MBG_PIDFILE 0
+
+
+// PID file handling
+//
+// If we want to make sure that no other instance of this program
+// is running, neither as daemon nor in the foreground only, we want
+// to try to open and lock the PID file *before* the program forks.
+// On the other hand, if running as daemon we need to write our PID
+// to the PID file *after* the fork.
+//
+// So the best approach is to open and lock the PID file before the
+// fork, and write the PID to it after the fork. So we need to make
+// sure that the lock is persistant across the fork.
+//
+// The flopen() call opens and locks a PID file in one step and thus
+// avoids a race condition. It is usually implemented using open()
+// and flock(), so it is persistant across forks. So this call usually
+// meets our requirements, but is not supported on all systems.
+//
+// If flopen() is not supported then we have to call open() first and
+// then some locking function, which can be flock() or lockf().
+//
+// flock() *can* be implemented on top of fcntl() but usually isn't.
+// lockf() *is* usually implemented on top of fcntl() but may be not.
+// fcntl() usually works on NFS mounts, other implementations usually don't.
+// fcntl() usually inn't persistant across forks, but flock() is.
+//
+// PID files are usually not located inside the local file system,
+// not on NFS mounts, thus flopen() the first choice, and using
+// open() plus flock() is the second best choice.
+
+#if !defined( HAVE_FLOPEN )
+ // flopen() is usually supported on *BSD
+ #define HAVE_FLOPEN defined( MBG_TGT_BSD )
+#endif
+
+#if HAVE_FLOPEN
+ #include <libutil.h>
+#else
+ #define USE_FLOCK 1
+#endif
+
+
+// file descriptor for the PID file
+static const char *glb_pid_fn;
+
+// We don't make this static to be able to change this externally,
+// though this is not recommended.
+mode_t pid_file_mode = 0640;
+
+
+
+/*HDR*/
+/**
+ * @brief Close and remove a PID file
+ *
+ * Should be called immediately before a daemon terminates.
+ *
+ * @param[in] info An additional informational string written to the syslog
+ *
+ * @see ::mbg_pidfile_open_and_lock
+ * @see ::mbg_pidfile_write_own_pid
+ */
+void mbg_pidfile_close_and_remove( const char *info )
+{
+ int rc;
+
+ syslog( LOG_INFO, "mbg_pidfile_close_and_remove() called %s", info );
+
+ if ( glb_pid_fd >= 0 )
+ {
+ rc = close( glb_pid_fd );
+
+ if ( rc == -1 )
+ {
+ syslog( LOG_WARNING, "Failed to close PID file %s (fd %i): %s",
+ glb_pid_fn, glb_pid_fd, strerror( errno ) );
+ }
+ else
+ {
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "PID file %s (fd %i) closed",
+ glb_pid_fn, glb_pid_fd );
+ #endif
+ glb_pid_fd = -1;
+ }
+ }
+
+
+ if ( glb_pid_fn )
+ {
+ rc = unlink( glb_pid_fn );
+
+ if ( rc == -1 )
+ {
+ syslog( LOG_WARNING, "Failed to remove PID file %s: %s",
+ glb_pid_fn, strerror( errno ) );
+ }
+ else
+ {
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "PID file %s removed", glb_pid_fn );
+ #endif
+
+ glb_pid_fn = NULL;
+ }
+ }
+
+} // mbg_pidfile_close_and_remove
+
+
+
+#if USE_ATEXIT_MBG_PIDFILE
+
+static /*HDR*/
+void mbg_pidfile_cleanup( void )
+{
+ mbg_pidfile_close_and_remove( "from mbg_pidfile_cleanup()" );
+
+} // mbg_pidfile_cleanup
+
+#endif
+
+
+
+/*HDR*/
+/**
+ * @brief Try to open and lock a PID file
+ *
+ * @note This function can be called before or after a program forks,
+ * which is useful if only a single instance of a program may be
+ * running, either as daemon or in the foreground.
+ *
+ * @param pid_fn File name of the PID file, including path
+ *
+ * @return The file descriptor of the PID file, or -1 on error
+ *
+ * @see ::mbg_pidfile_close_and_remove
+ * @see ::mbg_pidfile_write_own_pid
+ */
+int mbg_pidfile_open_and_lock( const char *pid_fn )
+{
+ int flags = O_RDWR | O_CREAT;
+
+ #if 1 && defined( O_CLOEXEC )
+ flags |= O_CLOEXEC; // TODO: check if this is appropriate
+ #endif
+
+#if HAVE_FLOPEN
+ // This is the preferred method to open and lock a PID file.
+ // flopen() is usually available on *BSD. It does open() and flock()
+ // in one step and thus avoids a race condition between opening and locking.
+ //
+ // If flags includes O_NONBLOCK and the file is already locked,
+ // flopen() will fail and set errno to EWOULDBLOCK.
+ flags |= O_NONBLOCK;
+
+ glb_pid_fd = flopen( pid_fn, flags, pid_file_mode );
+
+ if ( glb_pid_fd < 0 ) // failed to open PID file
+ {
+ syslog( LOG_ERR, "Failed to open PID file %s: %s", pid_fn, strerror( errno ) );
+ goto out_err;
+ }
+
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Successfully opened and locked PID file %s (fd %i)", pid_fn, glb_pid_fd );
+ #endif
+
+#else // flopen() not supported
+
+ glb_pid_fd = open( pid_fn, flags, pid_file_mode );
+
+ if ( glb_pid_fd < 0 ) // failed to open PID file
+ {
+ syslog( LOG_ERR, "Failed to open PID file %s: %s", pid_fn, strerror( errno ) );
+ goto out_err;
+ }
+
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Successfully opened PID file %s (fd %i)", pid_fn, glb_pid_fd );
+ #endif
+
+ #if USE_FLOCK
+ // This is the preferred method to lock a PID file, if flopen()
+ // open()+flock() is what flopen() usually does in one step.
+ // flock() locks are preserved across forks, at least under Linux
+ // where flock() is *not* implemented on top of fcntl().
+ // However, flock() locks usually don't work on NFS mounts
+ // whereas fcntl() locks do.
+ flags = LOCK_EX; // get an exclusive lock
+ flags |= LOCK_NB; // non-blocking, return error if would block
+
+ if ( flock( glb_pid_fd, flags ) < 0 ) // failed to get a lock on PID file
+ {
+ syslog( LOG_ERR, "Failed to get an flock() lock on PID file %s (fd %i): %s",
+ pid_fn, glb_pid_fd, strerror( errno ) );
+ goto out_err_close;
+ }
+
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Got an flock() lock on PID file %s (fd %i)",
+ pid_fn, glb_pid_fd );
+ #endif
+
+ #else
+ // lockf() locks are usually (but not necessarily) implemented on top
+ // of fcntl(), but are *not* preserved across forks.
+ // If implemented on top of fnctl() then locking works also on NFS mounts,
+ // but locks are *not* preserved across forks.
+ //
+ // Try to lock the file using F_TLOCK which never blocks but returns
+ // an error if the file is already locked.
+ if ( lockf( glb_pid_fd, F_TLOCK, 0 ) < 0 ) // failed to get a lock on PID file
+ {
+ syslog( LOG_ERR, "Failed to get a lockf() lock on PID file %s (fd %i): %s",
+ pid_fn, glb_pid_fd, strerror( errno ) );
+ goto out_err_close;
+ }
+
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Got a lockf() lock on PID file %s (fd %i)",
+ pid_fn, glb_pid_fd );
+ #endif
+
+ #endif
+
+#endif
+
+ // save PID file name
+ glb_pid_fn = pid_fn;
+
+#if USE_ATEXIT_MBG_PIDFILE
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Registering exit function %s from %s", "mbg_pidfile_cleanup", __func__ );
+ #endif
+ atexit( mbg_pidfile_cleanup );
+#endif
+ goto out;
+
+
+out_err_close:
+ close( glb_pid_fd );
+
+out_err:
+ glb_pid_fd = -1;
+
+out:
+ return glb_pid_fd;
+
+} // mbg_pidfile_open_and_lock
+
+
+
+/*HDR*/
+/**
+ * @brief Write own process ID to our PID file
+ *
+ * @note If a program runs as daemon, i.e. forks, then this function
+ * has to be called <b>after</b> the fork in order to write the
+ * PID of the forked process to the PID file.
+ *
+ * @return The number of byte written to the PID file, or a negative number on error
+ *
+ * @see ::mbg_pidfile_close_and_remove
+ * @see ::mbg_pidfile_open_and_lock
+ */
+int mbg_pidfile_write_own_pid( void )
+{
+ char tmp_str[64];
+
+ // write single line with PID to PID file
+ int n = snprintf( tmp_str, sizeof( tmp_str ), "%i\n", getpid() );
+ int rc = write( glb_pid_fd, tmp_str, n );
+
+ if ( rc < 0 )
+ syslog( LOG_ERR, "Failed to write to PID file %s (fd %i): %s",
+ glb_pid_fn, glb_pid_fd, strerror( errno ) );
+ else
+ {
+ if ( rc != n )
+ {
+ syslog( LOG_WARNING, "Could only write %i of %i chars to PID file %s (fd %i)",
+ rc, n, glb_pid_fn, glb_pid_fd );
+ rc = -1;
+ }
+ else
+ {
+ #if defined( DEBUG )
+ syslog( LOG_DEBUG, "Wrote own PID to PID file %s (fd %i): %i bytes",
+ glb_pid_fn, glb_pid_fd, n );
+ #endif
+ }
+ }
+
+ return rc;
+
+} // mbg_pidfile_write_own_pid
+
diff --git a/mbglib/common/mbg_pidfile.h b/mbglib/common/mbg_pidfile.h
new file mode 100755
index 0000000..f1b5926
--- /dev/null
+++ b/mbglib/common/mbg_pidfile.h
@@ -0,0 +1,124 @@
+
+/**************************************************************************
+ *
+ * $Id: mbg_pidfile.h 1.4 2014/07/16 15:19:55 martin REL_M $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Definitions and prototypes for mbg_daemonize.c.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: mbg_pidfile.h $
+ * Revision 1.4 2014/07/16 15:19:55 martin
+ * Revision 1.3 2013/07/30 15:30:49 martin
+ * Revision 1.2 2013/07/24 15:29:38 martin
+ * Revision 1.1 2013/07/23 16:10:19 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#ifndef _MBG_PIDFILE_H
+#define _MBG_PIDFILE_H
+
+
+/* Other headers to be included */
+
+
+#ifdef _MBG_PIDFILE
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#if 0 && defined( _USE_PACK ) // use default alignment
+ #pragma pack( 1 ) // set byte alignment
+ #define _USING_BYTE_ALIGNMENT
+#endif
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#define DEFAULT_PIDFILE_DIR "/var/run/"
+
+_ext int glb_pid_fd
+#if defined( _DO_INIT )
+ = -1
+#endif
+;
+
+
+/* function prototypes: */
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+ /**
+ * @brief Close and remove a PID file
+ *
+ * Should be called immediately before a daemon terminates.
+ *
+ * @param[in] info An additional informational string written to the syslog
+ *
+ * @see ::mbg_pidfile_open_and_lock
+ * @see ::mbg_pidfile_write_own_pid
+ */
+ void mbg_pidfile_close_and_remove( const char *info ) ;
+
+ /**
+ * @brief Try to open and lock a PID file
+ *
+ * @note This function can be called before or after a program forks,
+ * which is useful if only a single instance of a program may be
+ * running, either as daemon or in the foreground.
+ *
+ * @param pid_fn File name of the PID file, including path
+ *
+ * @return The file descriptor of the PID file, or -1 on error
+ *
+ * @see ::mbg_pidfile_close_and_remove
+ * @see ::mbg_pidfile_write_own_pid
+ */
+ int mbg_pidfile_open_and_lock( const char *pid_fn ) ;
+
+ /**
+ * @brief Write own process ID to our PID file
+ *
+ * @note If a program runs as daemon, i.e. forks, then this function
+ * has to be called <b>after</b> the fork in order to write the
+ * PID of the forked process to the PID file.
+ *
+ * @return The number of byte written to the PID file, or a negative number on error
+ *
+ * @see ::mbg_pidfile_close_and_remove
+ * @see ::mbg_pidfile_open_and_lock
+ */
+ int mbg_pidfile_write_own_pid( void ) ;
+
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+
+#if defined( _USING_BYTE_ALIGNMENT )
+ #pragma pack() // set default alignment
+ #undef _USING_BYTE_ALIGNMENT
+#endif
+
+/* End of header body */
+
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _MBG_PIDFILE_H */
diff --git a/mbglib/common/mbg_tgt.h b/mbglib/common/mbg_tgt.h
index cbb8b50..93916d6 100755
--- a/mbglib/common/mbg_tgt.h
+++ b/mbglib/common/mbg_tgt.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbg_tgt.h 1.29 2013/02/01 14:50:46 martin REL_M $
+ * $Id: mbg_tgt.h 1.35.1.12 2017/04/19 15:03:38 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -11,6 +11,112 @@
*
* -----------------------------------------------------------------------
* $Log: mbg_tgt.h $
+ * Revision 1.35.1.12 2017/04/19 15:03:38 martin
+ * Evaluate preprocessor symbol KERNEL_HAS_BOOL to avoid
+ * a compiler error due to duplicate definition in specific Linux kernels
+ * patched by the distro maintainers.
+ * Revision 1.35.1.11 2017/04/12 07:50:31 martin
+ * Fixed missing struct timespec for DOS.
+ * Revision 1.35.1.10 2017/04/10 13:37:16Z martin
+ * Fixed some compiler warnings.
+ * Revision 1.35.1.9 2017/02/09 12:38:51Z martin
+ * Fixed missing brace.
+ * Revision 1.35.1.8 2017/02/09 12:31:17 martin
+ * Updated bool handling with Linux kernel.
+ * Revision 1.35.1.7 2017/02/09 10:41:24 martin
+ * Fixed missing 'bool' type for old Linux kernels.
+ * Revision 1.35.1.6 2016/09/27 15:33:30 martin
+ * Added definition for _NO_MBG_API.
+ * Revision 1.35.1.5 2016/09/26 16:17:36 martin
+ * Fixed definitions for Windows kernel mode build.
+ * Revision 1.35.1.4 2016/08/31 08:17:51Z thomas-b
+ * Do not typedef ssize_t if HAVE_SSIZE_T is defined already
+ * Revision 1.35.1.3 2016/08/11 08:27:17 martin
+ * Fixed build for Windows kernel space.
+ * Revision 1.35.1.2 2016/08/10 12:26:49Z martin
+ * *** empty log message ***
+ * Revision 1.35.1.1 2016/08/09 15:59:25 martin
+ * *** empty log message ***
+ * Revision 1.35 2016/08/05 12:21:34 martin
+ * Conditionally define a macro _DEPRECATED_BY which can be used to
+ * tag functions as deprecated, so compilers can emit appropriate warnings.
+ * New symbol MBG_TGT_HAS_ABS64.
+ * Moved some compatibility definitions from gpsserio.h here.
+ * Define ssize_t for Windows, if required.
+ * Conditionally provided struct timespec for Windows.
+ * Added compatible 64 bit type print format specifiers.
+ * Include inttypes.h for all targets providing also stdint.h.
+ * Added some MSVC version code information.
+ * Fixes for FreeBSD.
+ * Fixed some spelling.
+ * Tmp workaround for 2.6.32-5-sparc64.
+ * Proper fix required.
+ * Revision 1.34.1.26 2016/08/05 10:38:10 martin
+ * Revision 1.34.1.25 2016/08/04 14:51:25Z martin
+ * Moved some compatibility definitions from gpsserio.h to mbg_tgt.h.
+ * Revision 1.34.1.24 2016/08/02 13:10:58 martin
+ * Define ssize_t for Windows, if required.
+ * Revision 1.34.1.23 2016/07/18 14:41:27Z martin
+ * New symbol MBG_TGT_HAS_ABS64.
+ * Revision 1.34.1.22 2016/07/14 09:00:58Z martin
+ * Conditionally provided struct timespec for Windows.
+ * Revision 1.34.1.21 2016/07/07 10:01:28Z martin
+ * Modified inclusion of Windows header files.
+ * Revision 1.34.1.20 2016/06/06 12:59:03 thomas-b
+ * Include all necessary Windows headers in the needed sequence
+ * Revision 1.34.1.19 2016/04/26 14:53:06 martin
+ * Revision 1.34.1.18 2016/04/26 13:31:08Z martin
+ * Added compatible 64 bit type print format specifiers.
+ * Revision 1.34.1.17 2016/04/25 14:46:20Z martin
+ * Include inttypes.h for all targets providing also stdint.h.
+ * Revision 1.34.1.16 2016/03/02 12:26:15 martin
+ * *** empty log message ***
+ * Revision 1.34.1.15 2016/02/26 09:12:11 paul
+ * Revision 1.34.1.14 2015/12/10 12:34:14Z martin
+ * *** empty log message ***
+ * Revision 1.34.1.13 2015/12/01 14:55:52 martin
+ * Revision 1.34.1.12 2015/12/01 14:54:08Z martin
+ * *** empty log message ***
+ * Revision 1.34.1.11 2015/12/01 14:52:20 martin
+ * *** empty log message ***
+ * Revision 1.34.1.10 2015/12/01 14:43:44 martin
+ * *** empty log message ***
+ * Revision 1.34.1.9 2015/12/01 13:55:09 martin
+ * Conditionally define a macro _DEPRECATED_BY which can be used to
+ * tag functions as deprecated, so compilers can emit appropriate warnings.
+ * Revision 1.34.1.8 2015/10/28 13:45:25 martin
+ * Added some MSVC version code information.
+ * Revision 1.34.1.7 2015/10/19 09:34:56 martin
+ * Fixed some spelling.
+ * Revision 1.34.1.6 2015/10/15 12:49:10 marvin
+ * Revision 1.34.1.5 2015/10/08 08:55:16Z martin
+ * Revision 1.34.1.4 2015/10/05 15:07:23Z marvin
+ * Unicode support.
+ * Revision 1.34.1.3 2015/09/21 08:58:27Z martin
+ * *** empty log message ***
+ * Revision 1.34.1.2 2015/09/18 14:53:25 martin
+ * Fixes for FreeBSD.
+ * Revision 1.34.1.1 2015/04/07 15:40:59 martin
+ * Tmp workaround for 2.6.32-5-sparc64.
+ * Proper fix required.
+ * Revision 1.34 2015/03/03 13:32:49 martin
+ * Provide __func__ for MS Visual Studio.
+ * Revision 1.33 2015/03/02 11:27:59Z martin
+ * Windows only:
+ * Define _CRT_SECURE_NO_WARNINGS to quiet compiler warnings.
+ * Define WIN32_LEAN_AND_MEAN only if it hasn't been defined before.
+ * Revision 1.32 2014/06/24 09:21:44 martin
+ * Update for newer C++Builder versions.
+ * Revision 1.31 2014/05/27 10:23:33 martin
+ * Finer control of which types are required for or already
+ * available on particular target systems.
+ * First definitions to support SunOS/Solaris.
+ * Revision 1.30 2014/04/01 12:55:58 martin
+ * Define MBG_TGT_WIN32 also for MS resource compiler.
+ * New target MBG_TGT_POSIX.
+ * Always include winsock2.h and windows.h for MBG_TGT_WIN32.
+ * Always include unistd.h for MBG_TGT_POSIX.
+ * Define empty __attribute__ macro for non-gcc environments.
* Revision 1.29 2013/02/01 14:50:46 martin
* Fixed a typo which caused an error under Borland CBuilder 5.
* Revision 1.28 2012/12/12 10:03:16Z martin
@@ -60,9 +166,9 @@
* Recognize DOS target under Watcom compilers.
* Flag Watcom C always supports wchar_t.
* Revision 1.12 2008/01/17 09:38:50Z daniel
- * Added macros to determine whether C language extensions
+ * Added macros to determine whether C language extensions
* (e.g. C94, C99) are supported by the target environment.
- * Added macro to check whether wchar_t and friends are
+ * Added macro to check whether wchar_t and friends are
* supported, and some compatibility stuff.
* Revision 1.11 2007/10/31 16:58:03 martin
* Fixed __mbg_inline for Borland C (DOS).
@@ -71,7 +177,7 @@
* Added MBG_PORT_HANDLE type for serial ports.
* Added macros for unified inline code syntax.
* Revision 1.9 2006/12/08 12:45:54Z martin
- * Under Windows include ntddk.h rather than windows.h
+ * Under Windows include ntddk.h rather than windows.h
* if building kernel driver .
* Revision 1.8 2006/10/25 12:20:45Z martin
* Initial support for FreeBSD, NetBSD, and OpenBSD.
@@ -88,7 +194,7 @@
* Revision 1.3 2003/04/09 13:37:20Z martin
* Added definition for _MBG_API.
* Revision 1.2 2003/02/24 16:08:45Z martin
- * Don't setup for Win32 PNP if explicitely configured non-PNP.
+ * Don't setup for Win32 PNP if explicitly configured non-PNP.
* Revision 1.1 2002/02/19 13:46:20Z MARTIN
* Initial revision
*
@@ -128,7 +234,7 @@
#if ( _WIN32_WINNT >= 0x0500 )
// Win2k and above
#if !defined( MBG_TGT_WIN32_NON_PNP )
- // only if not explicitely disabled
+ // only if not explicitly disabled
#define MBG_TGT_WIN32_PNP
#endif
#endif
@@ -154,6 +260,11 @@
// MS Visual C++
#define MBG_TGT_WIN32
+#elif defined( RC_INVOKED )
+
+ //MS resource compiler
+ #define MBG_TGT_WIN32
+
#elif defined( __WINDOWS_386__ )
// Watcom C/C++ for target Win32
@@ -194,6 +305,17 @@
// GCC for target OpenBSD
#define MBG_TGT_OPENBSD
+#elif defined( __sun ) // Oracle Solaris or other SunOS derived operating system
+
+ // __SUNPRO_C Oracle Solaris Studio C compiler, __SUNPRO_C value is the version number
+ // __SUNPRO_CC Oracle Solaris Studio C++ compiler, __SUNPRO_CC value is the version number
+ // __sparc generate code for SPARC (R) architecture (32-bit or 64-bit)
+ // __sparcv9 generate code for 64-bit SPARC architecture
+ // __i386 generate code for 32-bit x86 architecture
+ // __amd64 generate code for 64-bit x64 architecture
+
+ #define MBG_TGT_SUNOS
+
#elif defined( __QNX__ )
// any compiler for target QNX
@@ -220,7 +342,7 @@
#if defined( MBG_TGT_FREEBSD ) \
- || defined( MBG_TGT_NETBSD ) \
+ || defined( MBG_TGT_NETBSD ) \
|| defined( MBG_TGT_OPENBSD )
#define MBG_TGT_BSD
@@ -230,16 +352,35 @@
#endif
-#if defined( MBG_TGT_LINUX ) \
- || defined( MBG_TGT_BSD )
+#if defined( MBG_TGT_LINUX ) \
+ || defined( MBG_TGT_BSD ) \
+ || defined( MBG_TGT_QNX_NTO ) \
+ || defined( MBG_TGT_SUNOS )
+
+ #define MBG_TGT_POSIX
#define MBG_TGT_UNIX
#endif
+#if defined( MBG_TGT_WIN32 )
+
+ #define _CRT_SECURE_NO_WARNINGS 1
+
+#endif
// Some definitions depending on the build environment ...
-#if defined( __GNUC__ )
+#if defined( __GNUC__ ) || defined( __clang__ )
+
+ #if defined( __clang__ )
+ #define _CLANG_VERSION ( __clang_major__ * 10000 \
+ + __clang_minor__ * 100 \
+ + __clang_patchlevel__ )
+ #endif // defined( __clang__ )
+
+ #define _GCC_VERSION ( __GNUC__ * 10000 \
+ + __GNUC_MINOR__ * 100 \
+ + __GNUC_PATCHLEVEL__ )
#if defined( __i386__ )
@@ -272,26 +413,66 @@
#if defined( MBG_TGT_LINUX )
- #if defined( __KERNEL__ )
+ #if defined( MBG_TGT_KERNEL )
+
#include <linux/types.h>
+ #include <linux/version.h>
+
+ #if ( LINUX_VERSION_CODE <= KERNEL_VERSION( 2, 6, 4 ) ) || \
+ ( LINUX_VERSION_CODE >= KERNEL_VERSION( 2, 6, 4 ) ) // must be true for 2.6.32-5-sparc64
+ #define _ULONG_DEFINED 1
+ #define _USHORT_DEFINED 1
+ #define _UINT_DEFINED 1
+ #endif
+
+ // The 'bool' type is supported by the vanilla Linux kernel 2.6.19 and later.
+ // However, looks like at least the RedHat folks have backported this to 2.6.18,
+ // so KERNEL_HAS_BOOL can be defined to avoid a compiler error due to
+ // duplicate definition.
+ #if ( ( LINUX_VERSION_CODE < KERNEL_VERSION( 2, 6, 19 ) ) && !defined( KERNEL_HAS_BOOL ) )
+ typedef _Bool bool;
+ #define bool bool
+ #endif
+
+ // 'true' and 'false' are also defined by newer kernel versions
+ // as enum in linux/stddef.h, but may not be defined by
+ // older kernels.
+
#else
- #include <sys/types.h>
+
#include <stdint.h>
+ #include <inttypes.h>
#include <stdbool.h>
+
+ #if defined( __u_char_defined )
+ #define _ULONG_DEFINED 1
+ #define _USHORT_DEFINED 1
+ #define _UINT_DEFINED 1
+ #endif
+
#endif
#elif defined( MBG_TGT_BSD )
- #include <sys/types.h>
+ #if defined( MBG_TGT_KERNEL )
+ #include <sys/types.h>
+ #else
+ #include <stdint.h>
+ #include <inttypes.h>
+ #include <stdbool.h>
+ #endif
#elif defined( MBG_TGT_QNX_NTO ) // QNX 6.x (Neutrino)
+ #include <unistd.h>
#include <stdint.h>
+ #include <inttypes.h>
#include <stdbool.h>
#else
#include <stdint.h>
+ #include <inttypes.h>
#include <stdbool.h>
#endif
@@ -300,34 +481,112 @@
#define MBG_TGT_HAS_WCHAR_T 1
- #define __mbg_inline __inline__
+
+ #if defined( __clang__ )
+ #define _DEPRECATED_BY( _s ) __attribute__((deprecated("use \"" _s "\" instead"))) // works with clang 3.4.1
+ #elif ( _GCC_VERSION > 40500 ) // gcc 4.5.0 and newer
+ #define _DEPRECATED_BY( _s ) __attribute__((deprecated("use \"" _s "\" instead")))
+ #elif ( _GCC_VERSION > 30100 ) // gcc 3.1 and newer
+ #define _DEPRECATED_BY( _s ) __attribute__((deprecated))
+ #else
+ // Not supported at all, use empty default definiton below.
+ #endif
+
+ #if ( _GCC_VERSION > 30100 ) // gcc 3.1 and newer
+ #define __mbg_inline __inline__ __attribute__((always_inline))
+ #else
+ // Not supported at all, use empty default definiton below.
+ #define __mbg_inline __inline__
+ #endif
#elif defined( _MSC_VER )
// Known predifined MS compiler version codes:
+ // 1900: MSVC++ 14.0 (Visual Studio 2015)
+ // 1800: MSVC++ 12.0 (Visual Studio 2013)
// 1700: MSVC++ 11.0 (Visual Studio 2012)
// 1600: MSVC++ 10.0 (Visual Studio 2010)
// 1500: MSVC++ 9.0 (Visual Studio 2008)
- // 1400: MSVC++ 8.0 (Visual Studio 2005)
- // 1310: MSVC++ 7.1 (Visual Studio 2003)
- // 1300: MSVC++ 7.0
+ // 1400: MSVC++ 8.0 (Visual Studio 2005, Windows Server 2003 SP1 DDK - AMD64)
+ // 1310: MSVC++ 7.1 (Visual Studio .NET 2003, Windows Server 2003 DDK)
+ // 1300: MSVC++ 7.0 (Visual Studio .NET 2002, Windows XP SP1 DDK)
// 1200: MSVC++ 6.0
// 1100: MSVC++ 5.0
+ // "struct timespec" is supported only since VS2015
+ // If it is then also the symbol TIME_UTC should be defined.
+ // Functions to read the current time as struct timespec
+ // are timespec_get() and friends, which are also only provided
+ // by VS2015 and later.
+ // As of VS2015, only TIME_UTC is supported to read
+ // the UTC system time, there is no equivalent for
+ // the POSIX CLOCK_MONOTONIC. However, QPC can be used
+ // to get monotonic time stamps and intervals.
+ #if ( _MSC_VER < 1900 )
+ #if !defined( HAVE_STRUCT_TIMESPEC )
+ #define MBG_TGT_MISSING_STRUCT_TIMESPEC 1
+ #endif
+ #endif
+
#if ( _MSC_VER >= 1600 )
#include <stdint.h>
- #define MBG_TGT_HAS_EXACT_SIZE_TYPES 1
+ #include <inttypes.h>
+ #define MBG_TGT_HAS_EXACT_SIZE_TYPES 1
#else
- #define MBG_TGT_HAS_INT_8_16_32 1
+ #define MBG_TGT_HAS_INT_8_16_32 1
+ #define MBG_PRE64_PREFIX "I64"
#endif
- // no bool support anyway
- #define MBG_TGT_MISSING_BOOL_TYPE 1
+ #if !defined( __cplusplus )
+ // no bool support anyway
+ #define MBG_TGT_MISSING_BOOL_TYPE 1
+ #endif
- #define MBG_TGT_HAS_WCHAR_T 1
+ #define MBG_TGT_HAS_WCHAR_T 1
#define __mbg_inline __forceinline
+ // At least up to VS2008 the C99 builtin symbol __func__
+ // is not supported. Some VS versions support __FUNCTION__
+ // instead, but at least VC6 doesn't support this, either.
+ // of the current function instead.
+ #if ( _MSC_VER >= 1300 )
+ #define __func__ __FUNCTION__
+ #else
+ #define __func__ "func_???"
+ #endif
+
+ // "deprecated" attribute
+ #if ( _MSC_VER >= 1400 )
+ // This is supported since Visual Studio 2005
+ #define _DEPRECATED_BY( _s ) __declspec(deprecated("deprecated, use \"" _s "\""))
+ #endif
+
+ // availability of _abs64()
+ #if ( _MSC_VER >= 1310 )
+ // This is supported at least since Visual Studio 2008
+ // and Windows Server 2003 SP1 DDK.
+ #define MBG_TGT_HAS_ABS64 1
+ #endif
+
+ #if !defined ( HAVE_SSIZE_T )
+
+ // ssize_t support
+ #if ( _MSC_VER >= 1500 )
+ // ssize_t may not be defined, but SSIZE_T is
+ #include <basetsd.h>
+ typedef SSIZE_T ssize_t;
+ #else
+ // At least VC6 hasn't SIZE_T, either, but size_t
+ // is typedef'ed as unsigned int, so we just typedef
+ // the signed variant here.
+ typedef int ssize_t;
+ #endif
+
+ #define HAVE_SSIZE_T 1
+
+ #endif
+
#elif defined( _CVI_ )
// 1000 for CVI v10.0 (CVI 2010)
@@ -340,6 +599,7 @@
#if ( _CVI_ >= 910 )
// LabWindows/CVI 2009 is the first version providing stdint.h.
#include <stdint.h>
+ #include <inttypes.h>
#define MBG_TGT_HAS_EXACT_SIZE_TYPES 1
#else
#define USE_LONG_FOR_INT32 1
@@ -353,27 +613,57 @@
// Inline code is not supported, though the inline keyword
// is silently accepted since CVI v9.0
-#elif defined( __BORLANDC__ )
+#elif defined( __BORLANDC__ ) // or __CODEGEARC__ in newer versions
- // 0x0570 Borland Developer Studio 2006
- // 0x0550 Borland C/C++ 5.5 (C++ Builder 5.0)
- // 0x0410 Borland C/C++ 3.1
- // 0x0400 Borland C/C++ 3.0
// 0x0200 Borland C/C++ 2.0
-
- #if ( __BORLANDC__ >= 0x570 )
- // at least Borland Developer Studio 2006 supports C99
+ // 0x0400 Borland C/C++ 3.0
+ // 0x0410 Borland C/C++ 3.1
+ // 0x0550 Borland C/C++ 5.5 (C++Builder 5.0)
+
+ // Next codes are in addition defined as __CODEGEARC__
+ // See http://docwiki.embarcadero.com
+
+ // 0x0570 for Borland Developer Studio 2006 (BDS 2006)
+ // 0x0590 for C++Builder 2007
+ // 0x0591 for update 1 to C++Builder 2007
+ // 0x0592 for RAD Studio 2007
+ // 0x0593 for the December update to RAD Studio 2007
+ // 0x0610 for C++Builder 2009 and for C++Builder 2009 Update 1
+ // 0x0620 for C++Builder 2010 and for C++Builder 2010 Update 1
+ // 0x0621 for C++Builder 2010 Update 2
+ // 0x0630 for C++Builder XE
+ // 0x0631 for C++Builder XE Update 1
+ // 0x0640 for C++Builder XE2
+ // 0x0650 for C++Builder XE3
+
+ #if ( __BORLANDC__ >= 0x630 )
+ // C++Builder XE starts to provide stdbool.h
#include <stdint.h>
+ #include <inttypes.h>
#include <stdbool.h>
- #define MBG_TGT_HAS_EXACT_SIZE_TYPES 1
+ #define MBG_TGT_HAS_EXACT_SIZE_TYPES 1
+ #elif ( __BORLANDC__ >= 0x570 )
+ // BDS/Borland C++ Builder 2006 starts to provide at least stdint.h
+ #include <stdint.h>
+ #include <inttypes.h>
+ #define MBG_TGT_HAS_EXACT_SIZE_TYPES 1
+ #if !defined( __cplusplus )
+ #define MBG_TGT_MISSING_BOOL_TYPE 1
+ #endif
#elif ( __BORLANDC__ >= 0x0550 )
- #define MBG_TGT_HAS_INT_8_16_32 1
- #define MBG_TGT_MISSING_BOOL_TYPE 1
+ #define MBG_TGT_HAS_INT_8_16_32 1
+ #define MBG_PRE64_PREFIX "I64"
+ #if !defined( __cplusplus )
+ #define MBG_TGT_MISSING_BOOL_TYPE 1
+ #endif
#else // e.g. BC 3.1 or earlier
#if ( __BORLANDC__ <= 0x410 )
- #define MBG_TGT_MISSING_64_BIT_TYPES 1
- #define MBG_TGT_MISSING_BOOL_TYPE 1
- #define USE_LONG_FOR_INT32 1
+ #define MBG_TGT_MISSING_64_BIT_TYPES 1
+ #define MBG_TGT_MISSING_BOOL_TYPE 1
+ #define USE_LONG_FOR_INT32 1
+ #define MBG_TGT_MISSING_STRUCT_TIMESPEC 1
+
+ typedef int ssize_t;
#endif
#endif
@@ -399,15 +689,16 @@
#include <sys/types.h>
- #define MBG_TGT_MISSING_64_BIT_TYPES 1
+ #define MBG_TGT_MISSING_64_BIT_TYPES 1
#elif ( __WATCOMC__ > 1230 ) // Open Watcom C 1.3 and above
#include <stdint.h>
+ #include <inttypes.h>
#elif !defined( __WATCOM_INT64__ ) // Watcom C 11
- #define MBG_TGT_MISSING_64_BIT_TYPES 1
+ #define MBG_TGT_MISSING_64_BIT_TYPES 1
#endif
@@ -418,11 +709,34 @@
#endif
+// If the build environment doesn't provide a inttypes.h file
+// with print format specifiers for 64 bit fixed size types
+// then MBG_PRE64_PREFIX should be defined which is used
+// to define our own C99 compatible format specifiers.
+// Eventually, similar definitions are required for 32, 16,
+// and 8 bit fixed size types.
+#if defined( MBG_PRE64_PREFIX )
+ #define PRIi64 MBG_PRE64_PREFIX "i"
+ #define PRId64 MBG_PRE64_PREFIX "d"
+ #define PRIo64 MBG_PRE64_PREFIX "o"
+ #define PRIu64 MBG_PRE64_PREFIX "u"
+ #define PRIx64 MBG_PRE64_PREFIX "x"
+ #define PRIX64 MBG_PRE64_PREFIX "X"
+#endif
+
+#if !defined( __GNUC__ ) && !defined( __attribute__ )
+ #define __attribute__( _x )
+#endif
+
+#if !defined( _DEPRECATED_BY )
+ #define _DEPRECATED_BY( _s ) // empty definition
+#endif
+
#if defined( MBG_TGT_WIN32 )
#if defined( _AMD64_ )
- // This is used for AMD64 architecture and for
+ // This is used for AMD64 architecture and for
// Intel XEON CPUs with 64 bit extension.
#define MBG_TGT_WIN32_PNP_X64
#define WIN32_FLAVOR "x64"
@@ -434,9 +748,23 @@
#if defined( _KDD_ )
#define MBG_TGT_KERNEL
#include <ntddk.h>
+
+ #define _MBG_API
#else
// This must not be used for kernel drivers.
+
+ // Prevent inclusion of obsolete winsock.h in windows.h
+ #if !defined( WIN32_LEAN_AND_MEAN )
+ #define WIN32_LEAN_AND_MEAN 1
+ #endif
+ #if !defined( _WINSOCKAPI_ )
+ #define _WINSOCKAPI_
+ #endif
+
#include <windows.h>
+ #include <winsock2.h>
+ #include <ws2tcpip.h>
+
typedef HANDLE MBG_HANDLE;
#define MBG_INVALID_HANDLE INVALID_HANDLE_VALUE
@@ -457,9 +785,15 @@
typedef DWORD DWORD_PTR;
#endif
- #endif
+ // socklen_t support
+ #if ( _MSC_VER < 1500 )
+ // At least VS2008 has a socklen_t type
+ typedef int socklen_t;
+ #endif
- #define _MBG_API WINAPI
+ #define _MBG_API WINAPI
+
+ #endif
#if defined( MBG_LIB_EXPORT )
#define _MBG_API_ATTR __declspec( dllexport )
@@ -467,7 +801,11 @@
#define _MBG_API_ATTR __declspec( dllimport )
#endif
-#elif defined( MBG_TGT_UNIX )
+#elif defined( MBG_TGT_POSIX )
+
+ #if !defined( MBG_TGT_KERNEL )
+ #include <unistd.h>
+ #endif
typedef int MBG_HANDLE;
typedef int MBG_PORT_HANDLE;
@@ -484,6 +822,44 @@
#endif
+/**
+ * @brief A socket file descriptor type
+ */
+#if defined( MBG_TGT_WIN32 )
+ #if !defined( MBG_TGT_KERNEL ) // we don't need this in kernel space
+ // usually evaluates to UINT_PTR, which in turn evaluates
+ // to (unsigned int), or (unsigned __int64).
+ typedef SOCKET MBG_SOCK_FD;
+ #endif
+#elif defined( MBG_TGT_POSIX )
+ typedef int MBG_SOCK_FD; //### TODO
+ //### TODO typedef int SOCKET;
+#endif
+
+
+
+/**
+ * @brief A value to mark an ::MBG_SOCK_FD as invalid
+ */
+#if defined( MBG_TGT_WIN32 )
+ #define MBG_INVALID_SOCK_FD INVALID_SOCKET // usually evaluates to (SOCKET)(~0) since SOCKET is unsigned
+#elif defined( MBG_TGT_POSIX )
+ #define MBG_INVALID_SOCK_FD -1
+#endif
+
+
+
+/**
+ * @brief The return code of socket functions in case of error
+ */
+#if defined( MBG_TGT_WIN32 )
+ #define MBG_SOCKET_ERR_RETVAL SOCKET_ERROR // usually evaluates to -1
+#elif defined( MBG_TGT_POSIX )
+ #define MBG_SOCKET_ERR_RETVAL -1
+#endif
+
+
+
#if !defined( _MBG_API )
#define _MBG_API
#endif
@@ -492,6 +868,10 @@
#define _MBG_API_ATTR
#endif
+#if !defined( _NO_MBG_API )
+ #define _NO_MBG_API
+#endif
+
#if !defined( _NO_MBG_API_ATTR )
#define _NO_MBG_API_ATTR
#endif
@@ -504,6 +884,18 @@
#define MBG_USE_MM_IO_FOR_PCI 0
#endif
+#if defined( MBG_TGT_MISSING_STRUCT_TIMESPEC )
+
+#include <time.h>
+
+ struct timespec
+ {
+ time_t tv_sec;
+ long tv_nsec;
+ };
+
+#endif // defined( MBG_TGT_MISSING_STRUCT_TIMESPEC )
+
// The macros below are defined in order to be able to check if
// certain C language extensions are available on the target system:
diff --git a/mbglib/common/mbgddmsg.h b/mbglib/common/mbgddmsg.h
index 32f174a..ecf9fba 100755
--- a/mbglib/common/mbgddmsg.h
+++ b/mbglib/common/mbgddmsg.h
@@ -1,16 +1,25 @@
/**************************************************************************
*
- * $Id: mbgddmsg.h 1.10 2012/10/02 18:33:21 martin REL_M $
+ * $Id: mbgddmsg.h 1.10.1.6 2015/08/27 16:22:17 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
* Description:
- * Print or remove debug messages by redefinitions.
+ * Definitions and function prototypes to deal with messages
+ * generated by kernel mode drivers. Some type of messages are
+ * always generated, others are only generated ibn DEBUG builds
+ * and are defined void in release builds.
*
* -----------------------------------------------------------------------
* $Log: mbgddmsg.h $
- * Revision 1.10 2012/10/02 18:33:21 martin
+ * Revision 1.10.1.6 2015/08/27 16:22:17 martin
+ * Revision 1.10.1.5 2014/05/27 11:43:23 martin
+ * Revision 1.10.1.4 2014/04/15 13:45:24Z martin
+ * Revision 1.10.1.3 2014/04/11 12:38:39 martin
+ * Revision 1.10.1.2 2014/04/09 15:41:47 martin
+ * Revision 1.10.1.1 2014/04/09 15:10:35Z martin
+ * Revision 1.10 2012/10/02 18:33:21Z martin
* Support for *BSD.
* Also enable debug msgs if MBG_DEBUG is defined.
* Revision 1.8 2009/04/22 09:54:55 martin
@@ -37,103 +46,193 @@
#define _MBGDDMSG_H
+/* Other headers to be included */
+
#include <mbg_tgt.h>
-#if defined( DEBUG ) || ( defined( DBG ) && DBG ) || defined( MBG_DEBUG )
+#if defined( MBG_TGT_NETWARE )
+ #include <conio.h>
+#elif defined( MBG_TGT_OS2 )
+ #include <iprintf.h>
+#elif defined( MBG_TGT_WIN32 )
+ #include <ntddk.h>
+#elif defined( MBG_TGT_LINUX )
+ #include <linux/module.h>
+ #include <linux/version.h>
+#elif defined( MBG_TGT_BSD )
+ // nothing to include
+#else // MBG_TGT_QNX, MBG_TGT_DOS, ...
+ //##+++++++++++++
+ #include <stdio.h>
+#endif
-enum
-{
- MBG_DBG_ERR,
- MBG_DBG_WARN,
- MBG_DBG_INFO,
- MBG_DBG_DETAIL,
- MBG_DBG_INIT_DEV,
- MBG_DEBUG_SEM,
- MBG_DBG_IRQ,
- N_MBG_DBG_LVL
-};
+
+#ifdef _MBGDDMSG
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
-#define _chk_lvl( _lvl ) ( (_lvl) < debug )
+/* Start of header body */
+
+#if defined( _USE_PACK )
+ #pragma pack( 1 ) // set byte alignment
+ #define _USING_BYTE_ALIGNMENT
+#endif
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
#if defined( MBG_TGT_NETWARE )
- #include <conio.h>
#define _printf ConsolePrintf
#define _hd
#define _tl "\n"
#elif defined( MBG_TGT_OS2 )
- #include <iprintf.h>
#define _printf iprintf
#define _hd
#define _tl "\n"
#elif defined( MBG_TGT_WIN32 )
- #include <ntddk.h>
- #define _printf DbgPrint
+ #define _printf mbg_kdd_msg
#define _hd
- #define _tl "\n"
+ #define _tl
+ #define USE_MBG_KDD_MSG 1
#elif defined( MBG_TGT_LINUX )
- // #include <printk.h>
- #define _printf printk
- #define _hd KERN_INFO
- #define _tl "\n"
+ #if ( LINUX_VERSION_CODE < KERNEL_VERSION( 2, 6, 8 ) )
+ // vprintk not supported by the kernel
+ #define _printf printk
+ #define _hd KERN_INFO
+ #define _tl "\n"
+ #else
+ #define _printf mbg_kdd_msg
+ #define _hd KERN_NOTICE
+ #define _tl "\n"
+ #define USE_MBG_KDD_MSG 1
+ #endif
#elif defined( MBG_TGT_BSD )
#define _printf printf
#define _hd
#define _tl "\n"
#else // MBG_TGT_QNX, MBG_TGT_DOS, ...
- #include <stdio.h>
#define _printf printf
#define _hd
#define _tl "\n"
#endif
-#define _mbgddmsg_0( _lvl, _fmt ) \
-do { \
- if ( _chk_lvl( _lvl ) ) \
- { _printf( _hd _fmt _tl ); } \
+#if !defined( USE_MBG_KDD_MSG )
+ #define USE_MBG_KDD_MSG 0
+#endif
+
+
+#define _mbg_kdd_msg_0( _fmt ) \
+do { \
+ _printf( _hd _fmt _tl ); \
+} while ( 0 )
+
+#define _mbg_kdd_msg_1( _fmt, _p1 ) \
+do { \
+ _printf( _hd _fmt _tl, (_p1) ); \
+} while ( 0 )
+
+#define _mbg_kdd_msg_2( _fmt, _p1, _p2 ) \
+do { \
+ _printf( _hd _fmt _tl, (_p1), (_p2) ); \
} while ( 0 )
-#define _mbgddmsg_1( _lvl, _fmt, _p1 ) \
+#define _mbg_kdd_msg_3( _fmt, _p1, _p2, _p3 ) \
+do { \
+ _printf( _hd _fmt _tl, (_p1), (_p2), (_p3) ); \
+} while ( 0 )
+
+#define _mbg_kdd_msg_4( _fmt, _p1, _p2, _p3, _p4 ) \
+do { \
+ _printf( _hd _fmt _tl, (_p1), (_p2), (_p3), (_p4) ); \
+} while ( 0 )
+
+#define _mbg_kdd_msg_5( _fmt, _p1, _p2, _p3, _p4, _p5 ) \
+do { \
+ _printf( _hd _fmt _tl, (_p1), (_p2), (_p3), (_p4), (_p5) ); \
+} while ( 0 )
+
+#define _mbg_kdd_msg_6( _fmt, _p1, _p2, _p3, _p4, _p5, _p6 ) \
+do { \
+ _printf( _hd _fmt _tl, (_p1), (_p2), (_p3), (_p4), (_p5), (_p6) ); \
+} while ( 0 )
+
+#define _mbg_kdd_msg_7( _fmt, _p1, _p2, _p3, _p4, _p5, _p6, _p7 ) \
+do { \
+ _printf( _hd _fmt _tl, (_p1), (_p2), (_p3), (_p4), (_p5), (_p6), (_p7) ); \
+} while ( 0 )
+
+
+
+#if defined( DEBUG ) || ( defined( DBG ) && DBG ) || defined( MBG_DEBUG )
+
+enum
+{
+ MBG_DBG_ERR,
+ MBG_DBG_WARN,
+ MBG_DBG_INFO,
+ MBG_DBG_DETAIL,
+ MBG_DBG_INIT_DEV,
+ MBG_DEBUG_SEM,
+ MBG_DBG_IRQ,
+ N_MBG_DBG_LVL
+};
+
+
+#define _chk_lvl( _lvl ) ( (_lvl) < debug )
+
+#define _mbgddmsg_0( _lvl, _fmt ) \
do { \
if ( _chk_lvl( _lvl ) ) \
- { _printf( _hd _fmt _tl, (_p1) ); } \
+ { _mbg_kdd_msg_0( _fmt ); } \
} while ( 0 )
-#define _mbgddmsg_2( _lvl, _fmt, _p1, _p2 ) \
+#define _mbgddmsg_1( _lvl, _fmt, _p1 ) \
do { \
if ( _chk_lvl( _lvl ) ) \
- { _printf( _hd _fmt _tl, (_p1), (_p2) ); } \
+ { _mbg_kdd_msg_1( _fmt, (_p1) ); } \
} while ( 0 )
-#define _mbgddmsg_3( _lvl, _fmt, _p1, _p2, _p3 ) \
+#define _mbgddmsg_2( _lvl, _fmt, _p1, _p2 ) \
do { \
if ( _chk_lvl( _lvl ) ) \
- { _printf( _hd _fmt _tl, (_p1), (_p2), (_p3) ); } \
+ { _mbg_kdd_msg_2( _fmt, (_p1), (_p2) ); } \
} while ( 0 )
-#define _mbgddmsg_4( _lvl, _fmt, _p1, _p2, _p3, _p4 ) \
+#define _mbgddmsg_3( _lvl, _fmt, _p1, _p2, _p3 ) \
do { \
if ( _chk_lvl( _lvl ) ) \
- { _printf( _hd _fmt _tl, (_p1), (_p2), (_p3), (_p4) ); } \
+ { _mbg_kdd_msg_3( _fmt, (_p1), (_p2), (_p3) ); } \
} while ( 0 )
-#define _mbgddmsg_5( _lvl, _fmt, _p1, _p2, _p3, _p4, _p5 ) \
+#define _mbgddmsg_4( _lvl, _fmt, _p1, _p2, _p3, _p4 ) \
do { \
if ( _chk_lvl( _lvl ) ) \
- { _printf( _hd _fmt _tl, (_p1), (_p2), (_p3), (_p4), (_p5) ); } \
+ { _mbg_kdd_msg_4( _fmt, (_p1), (_p2), (_p3), (_p4) ); } \
} while ( 0 )
-#define _mbgddmsg_6( _lvl, _fmt, _p1, _p2, _p3, _p4, _p5, _p6 ) \
+#define _mbgddmsg_5( _lvl, _fmt, _p1, _p2, _p3, _p4, _p5 ) \
do { \
if ( _chk_lvl( _lvl ) ) \
- { _printf( _hd _fmt _tl, (_p1), (_p2), (_p3), (_p4), (_p5), (_p6) ); } \
+ { _mbg_kdd_msg_5( _fmt, (_p1), (_p2), (_p3), (_p4), (_p5) ); } \
} while ( 0 )
-#define _mbgddmsg_7( _lvl, _fmt, _p1, _p2, _p3, _p4, _p5, _p6, _p7 ) \
+#define _mbgddmsg_6( _lvl, _fmt, _p1, _p2, _p3, _p4, _p5, _p6 ) \
do { \
if ( _chk_lvl( _lvl ) ) \
- { _printf( _hd _fmt _tl, (_p1), (_p2), (_p3), (_p4), (_p5), (_p6), (_p7) ); } \
+ { _mbg_kdd_msg_6( _fmt, (_p1), (_p2), (_p3), (_p4), (_p5), (_p6) ); } \
+} while ( 0 )
+
+#define _mbgddmsg_7( _lvl, _fmt, _p1, _p2, _p3, _p4, _p5, _p6, _p7 ) \
+do { \
+ if ( _chk_lvl( _lvl ) ) \
+ { _mbg_kdd_msg_7( _fmt, (_p1), (_p2), (_p3), (_p4), (_p5), (_p6), (_p7) ); } \
} while ( 0 )
#else
@@ -149,4 +248,32 @@ do {
#endif
+
+/* function prototypes: */
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+ __attribute__( ( format( printf, 1, 2 ) ) ) void mbg_kdd_msg( const char *fmt, ... ) ;
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+
+#if defined( _USING_BYTE_ALIGNMENT )
+ #pragma pack() // set default alignment
+ #undef _USING_BYTE_ALIGNMENT
+#endif
+
+/* End of header body */
+
+
+#undef _ext
+#undef _DO_INIT
+
#endif /* _MBGDDMSG_H */
diff --git a/mbglib/common/mbgdevio.c b/mbglib/common/mbgdevio.c
index 8181e56..93be933 100755
--- a/mbglib/common/mbgdevio.c
+++ b/mbglib/common/mbgdevio.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgdevio.c 1.36 2012/10/02 18:37:09 martin REL_M $
+ * $Id: mbgdevio.c 1.38.1.45.1.11 2017/03/20 17:11:07 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,7 +10,99 @@
*
* -----------------------------------------------------------------------
* $Log: mbgdevio.c $
- * Revision 1.36 2012/10/02 18:37:09 martin
+ * Revision 1.38.1.45.1.11 2017/03/20 17:11:07 martin
+ * Replaced dummy swab...() macro calls by real macros.
+ * Revision 1.38.1.45.1.10 2017/02/22 14:29:17 martin
+ * Fixed a warning from clang compiler.
+ * Revision 1.38.1.45.1.9 2017/02/17 11:48:47 martin
+ * Fixed a potential buffer overflow.
+ * Revision 1.38.1.45.1.8 2017/02/01 16:23:00 martin
+ * PCPS_DEV * parameter for mbg_setup_receiver_info maynow be NULL.
+ * Revision 1.38.1.45.1.7 2016/09/19 14:29:00 martin
+ * Fixed build for direct access targets.
+ * Revision 1.38.1.45.1.6 2016/09/16 09:56:47 martin
+ * *** empty log message ***
+ * Revision 1.38.1.45.1.5 2016/09/16 07:19:58 martin
+ * Revision 1.38.1.45.1.4 2016/09/13 11:10:17Z martin
+ * Modified some macros to avoid compiler warnings.
+ * Renamed some macros.
+ * Revision 1.38.1.45.1.3 2016/08/09 16:00:15Z martin
+ * Fixed build for QNX Neutrino.
+ * Revision 1.38.1.45.1.2 2016/05/30 15:07:22 martin
+ * *** empty log message ***
+ * Revision 1.38.1.45.1.1 2015/12/17 14:18:32 martin
+ * Tmp. saved preliminary changes.
+ * Revision 1.38.1.45 2015/12/02 17:05:00 martin
+ * *** empty log message ***
+ * Revision 1.38.1.44 2015/12/02 16:36:16 martin
+ * *** empty log message ***
+ * Revision 1.38.1.43 2015/12/01 17:01:01 martin
+ * *** empty log message ***
+ * Revision 1.38.1.42 2015/12/01 15:24:33 martin
+ * Marked some functions deprecated.
+ * Revision 1.38.1.41 2015/12/01 13:58:31 martin
+ * *** empty log message ***
+ * Revision 1.38.1.40 2015/10/27 16:22:22 martin
+ * Older defines N_SUPP_DEV, PCPS_MAX_DDEVS, and MBG_MAX_DEVICES
+ * have been obsoleted by new defines N_SUPP_DEV_BUS, N_SUPP_DEV_EXT,
+ * and N_SUPP_DEV_TOTAL.
+ * Revision 1.38.1.39 2015/10/26 14:45:06 martin
+ * *** empty log message ***
+ * Revision 1.38.1.38 2015/10/21 11:21:51 martin
+ * *** empty log message ***
+ * Revision 1.38.1.37 2015/10/20 16:02:01 martin
+ * *** empty log message ***
+ * Revision 1.38.1.36 2015/10/20 15:19:25 martin
+ * *** empty log message ***
+ * Revision 1.38.1.35 2015/10/19 16:42:16 martin
+ * *** empty log message ***
+ * Revision 1.38.1.34 2015/10/05 15:07:19 marvin
+ * Unicode support.
+ * Revision 1.38.1.33 2015/08/31 10:20:28Z martin
+ * Revision 1.38.1.32 2015/04/07 15:41:21Z martin
+ * Revision 1.38.1.31 2014/11/19 16:33:30 martin
+ * Revision 1.38.1.30 2014/11/19 16:15:43 martin
+ * Revision 1.38.1.29 2014/11/19 16:03:07 martin
+ * Revision 1.38.1.28 2014/11/19 14:41:45 martin
+ * Revision 1.38.1.27 2014/11/19 12:33:36 martin
+ * Cleaned up doxygen comments for mbg_dev_has...() functions.
+ * Revision 1.38.1.26 2014/10/27 10:44:02 martin
+ * Revision 1.38.1.25 2014/10/23 11:04:29 martin
+ * Doxygen stuff.
+ * Revision 1.38.1.24 2014/07/22 13:03:58 martin
+ * Revision 1.38.1.23 2014/07/18 11:01:39Z martin
+ * Revision 1.38.1.22 2014/07/16 15:19:56 martin
+ * Revision 1.38.1.21 2014/07/14 15:42:47 martin
+ * Revision 1.38.1.20 2014/07/02 15:34:55 martin
+ * Revision 1.38.1.19 2014/06/26 09:45:23 martin
+ * Revision 1.38.1.18 2014/05/27 11:34:29 martin
+ * Revision 1.38.1.17 2014/05/27 08:22:17 martin
+ * Revision 1.38.1.16 2014/05/26 16:02:12 martin
+ * Revision 1.38.1.15 2014/05/26 07:42:30 martin
+ * Revision 1.38.1.14 2014/05/23 12:30:50Z martin
+ * Revision 1.38.1.13 2014/05/23 09:53:03 martin
+ * Revision 1.38.1.12 2014/05/23 09:49:44 martin
+ * Revision 1.38.1.11 2014/05/23 09:24:06Z martin
+ * gpio and xmr functions.
+ * Revision 1.38.1.10 2014/05/22 16:16:26 martin
+ * Revision 1.38.1.9 2014/04/28 13:54:17 martin
+ * Revision 1.38.1.8 2014/04/23 15:42:57 martin
+ * Revision 1.38.1.7 2014/04/22 13:27:37 martin
+ * Revision 1.38.1.6 2014/04/17 13:16:46 martin
+ * Fixed a bug where XYZ and LLA were not written properly
+ * under target systems not using a kernel driver.
+ * Revision 1.38.1.4 2014/03/28 09:52:10Z martin
+ * Revision 1.38.1.3 2014/03/13 09:46:44 martin
+ * Revision 1.38.1.2 2014/01/31 14:45:34Z martin
+ * Revision 1.38.1.1 2013/12/05 16:35:59 martin
+ * Doxygen changes.
+ * Revision 1.38 2013/11/08 15:04:54 martin
+ * Fixes for big endian targets.
+ * Revision 1.37 2013/09/26 08:54:22 martin
+ * Support GNSS API.
+ * Support mbg_open_device_by_name() on Unix.
+ * Updated doxygen comments.
+ * Revision 1.36 2012/10/02 18:37:09Z martin
* There are some g++ versions which fail to compile source code using
* the macros provided by Linux to define IOCTL codes. If only the API
* functions are called by an application then the IOCTL codes aren't
@@ -52,7 +144,7 @@
* Modifications to support FreeBSD.
* Moved definition of MBG_HW_NAME to the header file.
* Compute PC cycles frequency under Linux if cpu_tick is not set by the kernel.
- * Fixed a bug that kept the function mbg_open_device_by_name in a loop under certain conditions.
+ * Fixed a bug that kept the function mbg_open_device_by_name in a loop under certain conditions.
* Made xhrt leap second check an inline function.
* Revision 1.35 2010/01/12 13:40:25 martin
* Fixed a typo in mbg_dev_has_raw_irig_data().
@@ -241,7 +333,7 @@
* Revision 1.4 2003/04/09 16:07:16Z martin
* New API functions mostly complete.
* Use renamed IOCTL codes from mbgioctl.h.
- * Added DllEntry function foe Win32.
+ * Added DllEntry function for Win32.
* Made MBG_Device_count and MBG_Device_Path local.
* Revision 1.3 2003/01/24 13:44:40Z martin
* Fixed get_ref_time_from_driver_at_sec_change() to be used
@@ -260,11 +352,10 @@
#include <mbgdevio.h>
#undef _MBGDEVIO
-#include <parmpcps.h>
-#include <parmgps.h>
#include <gpsutils.h>
#include <mbgerror.h>
#include <cfg_hlp.h>
+#include <str_util.h>
#if defined( MBG_TGT_DOS_PM )
#include <mbg_dpmi.h>
@@ -286,18 +377,6 @@
-#define MAX_INFO_LEN 260
-
-typedef struct
-{
- MBG_HW_NAME hw_name;
- char model_name[PCPS_CLOCK_NAME_SZ];
- PCPS_SN_STR serial_number;
- char hardware_id[MAX_INFO_LEN]; // OS dependent hardware_id to identify and open the device
-} MBG_DEVICE_INFO;
-
-
-
// target specific code for different environments
#if defined( MBG_TGT_WIN32 )
@@ -305,20 +384,22 @@ typedef struct
#include <mbgsvctl.h>
#include <mbgnames.h>
#include <pci_asic.h>
- #include <mbgutil.h> //##++
+ #include <mbgutil.h>
#include <timecnv.h>
#include <pcpsutil.h>
#include <tchar.h>
#include <stdio.h>
-#elif defined( MBG_TGT_UNIX )
+#elif defined( MBG_TGT_POSIX ) && !defined( MBG_TGT_QNX_NTO )
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
- #include <stdio.h> // sprintf()
- #include <sys/mman.h>
+
+ #if defined( DEBUG )
+ #include <stdio.h> // printf() debug output
+ #endif
#else // other target OSs which access the hardware directly
@@ -342,12 +423,6 @@ typedef struct
#define _pcps_write_gps_var_safe _pcps_write_gps_var
#endif
- #define _mbgdevio_chk_cond( _cond ) \
- { \
- if ( !(_cond) ) \
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV ); \
- }
-
#endif // end of target specific code
@@ -370,139 +445,2585 @@ typedef struct
#define _mbgdevio_read_chk( _dh, _cmd, _ioctl, _p, _sz, _cond ) \
+do \
{ \
_mbgdevio_chk_cond( _cond ); \
rc = _do_mbgdevio_read( _dh, _cmd, _ioctl, _p, _sz ); \
-}
+} while ( 0 )
#define _mbgdevio_read_var_chk( _dh, _cmd, _ioctl, _p, _cond ) \
+do \
{ \
_mbgdevio_chk_cond( _cond ); \
rc = _mbgdevio_read_var( _dh, _cmd, _ioctl, _p ); \
-}
+} while ( 0 )
#define _mbgdevio_write_var_chk( _dh, _cmd, _ioctl, _p, _cond ) \
+do \
{ \
_mbgdevio_chk_cond( _cond ); \
rc = _mbgdevio_write_var( _dh, _cmd, _ioctl, _p ); \
-}
+} while ( 0 )
#define _mbgdevio_write_cmd_chk( _dh, _cmd, _ioctl, _cond ) \
+do \
{ \
_mbgdevio_chk_cond( _cond ); \
rc = _mbgdevio_write_cmd( _dh, _cmd, _ioctl ); \
-}
+} while ( 0 )
#define _mbgdevio_read_gps_chk( _dh, _cmd, _ioctl, _p, _sz, _cond ) \
+do \
{ \
_mbgdevio_chk_cond( _cond ); \
rc = _do_mbgdevio_read_gps( _dh, _cmd, _ioctl, _p, _sz ); \
-}
+} while ( 0 )
#define _mbgdevio_read_gps_var_chk( _dh, _cmd, _ioctl, _p, _cond ) \
+do \
{ \
_mbgdevio_chk_cond( _cond ); \
rc = _mbgdevio_read_gps_var( _dh, _cmd, _ioctl, _p ); \
-}
+} while ( 0 )
#define _mbgdevio_write_gps_var_chk( _dh, _cmd, _ioctl, _p, _cond ) \
+do \
{ \
_mbgdevio_chk_cond( _cond ); \
rc = _mbgdevio_write_gps_var( _dh, _cmd, _ioctl, _p ); \
-}
+} while ( 0 )
#if defined( _MBGIOCTL_H )
- #define _mbgdevio_query_cond( _dh, _cond, _ioctl, _p ) \
- { \
- _mbgdevio_vars(); \
- rc = _mbgdevio_read_var( _dh, -1, _ioctl, _p ); \
- return _mbgdevio_ret_val; \
- }
- #define _mbgdevio_query_ri_cond _mbgdevio_query_cond
+ #define _mbgdevio_old_query_cond( _dh, _cond, _ioctl, _p ) \
+ _mbgdevio_vars(); \
+ rc = _mbgdevio_read_var( _dh, -1, _ioctl, _p ); \
+ return _mbgdevio_ret_val
+
+ #define _mbgdevio_old_query_ri_cond _mbgdevio_old_query_cond
+
#else
- #define _mbgdevio_query_cond( _dh, _cond, _ioctl, _p ) \
- { \
- *p = _cond( _dh ); \
- return MBG_SUCCESS; \
- }
- #define _mbgdevio_query_ri_cond( _dh, _cond, _ioctl, _p ) \
- { \
- *p = _cond( &(_dh)->ri ); \
- return MBG_SUCCESS; \
+ #define _mbgdevio_old_query_cond( _dh, _cond, _ioctl, _p ) \
+ *p = _cond( _dh ); \
+ return MBG_SUCCESS
+
+ #define _mbgdevio_old_query_ri_cond( _dh, _cond, _ioctl, _p ) \
+ *p = _cond( _ri_addr( _dh ) ); \
+ return MBG_SUCCESS
+
+#endif
+
+
+
+#if defined( _MBGIOCTL_H )
+
+ #define _mbgdevio_new_query_cond( _dh, _cond, _ioctl ) \
+ { \
+ int _flag = 0; \
+ _mbgdevio_vars(); \
+ rc = _mbgdevio_read_var( _dh, -1, _ioctl, &_flag ); \
+ \
+ if ( rc == MBG_SUCCESS ) /* no IOCTL error */ \
+ if ( _flag == 0 ) /* if returned value is 0 */ \
+ rc = MBG_ERR_NOT_SUPP_BY_DEV; /* not supp. */ \
+ \
+ /* success or IOCTL error */ \
+ return _mbgdevio_ret_val; \
}
+
+ #define _mbgdevio_new_query_ri_cond _mbgdevio_new_query_cond
+
+#else
+
+ #define _mbgdevio_new_query_cond( _dh, _cond, _ioctl ) \
+ return _cond( _dh ) ? MBG_SUCCESS : MBG_ERR_NOT_SUPP_BY_DEV
+
+ #define _mbgdevio_new_query_ri_cond( _dh, _cond, _ioctl ) \
+ return _cond( _ri_addr( _dh ) ) ? MBG_SUCCESS : MBG_ERR_NOT_SUPP_BY_DEV
+
#endif
+
+#define MAX_INFO_LEN 260
+
+typedef struct
+{
+ MBG_HW_NAME hw_name;
+ char model_name[PCPS_CLOCK_NAME_SZ];
+ PCPS_SN_STR serial_number;
+ char hardware_id[MAX_INFO_LEN]; ///< OS dependent hardware ID string to identify a unique device
+
+} MBG_DEVICE_INFO;
+
+
+
static MBG_PC_CYCLES_FREQUENCY pc_cycles_frequency;
-static MBG_DEVICE_INFO device_info_list[MBG_MAX_DEVICES];
/*HDR*/
/**
- Get the version number of the precompiled DLL/shared object library.
+ * @brief Get the version number of the precompiled DLL/shared object library
+ *
+ * If this library is used as a DLL/shared object library then the version
+ * number can be checked to see if the header files which are actually used
+ * to build an application are compatible with the header files which have
+ * been used to build the library, and thus the API function are called
+ * in the correct way.
+ *
+ * @return the version number
+ *
+ * @see ::mbgdevio_check_version
+ * @see ::MBGDEVIO_VERSION defined in mbgdevio.h
+ */
+_MBG_API_ATTR int _MBG_API mbgdevio_get_version( void )
+{
+ return MBGDEVIO_VERSION;
- If this library is used as a DLL/shared object library then the version
- number can be checked to see if the header files which are actually used
- to build an application are compatible with the header files which have
- been used to build the library, and thus the API function are called
- in the correct way.
+} // mbgdevio_get_version
- @return the version number
- @see mbgdevio_check_version()
- @see ::MBGDEVIO_VERSION defined in mbgdevio.h
- */
-_MBG_API_ATTR int _MBG_API mbgdevio_get_version( void )
+
+/*HDR*/
+/**
+ * @brief Check if the DLL/shared library is compatible with a given version
+ *
+ * If this library is used as a DLL/shared object library then the version
+ * number can be checked to see if the header files which are actually used
+ * to build an application are compatible with the header files which have
+ * been used to build the library, and thus the API functions are called
+ * in the correct way.
+ *
+ * @param[in] header_version Version number to be checked, should be ::MBGDEVIO_VERSION
+ * from the mbgdevio.h file version used to build the application
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgdevio_get_version
+ * @see ::MBGDEVIO_VERSION defined in mbgdevio.h
+ */
+_MBG_API_ATTR int _MBG_API mbgdevio_check_version( int header_version )
{
+ if ( header_version >= MBGDEVIO_COMPAT_VERSION )
+ return MBG_SUCCESS;
- return MBGDEVIO_VERSION;
+ return MBG_ERR_LIB_NOT_COMPATIBLE;
-} // mbgdevio_get_version
+} // mbgdevio_check_version
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::RECEIVER_INFO structure and related calls.
+ *
+ * Very old devices may not provide a ::RECEIVER_INFO structure.
+ * The ::mbg_setup_receiver_info call should be used preferably to set up
+ * a ::RECEIVER_INFO for a device. The function uses this call to determine
+ * whether a ::RECEIVER_INFO can be read directly from a device, or sets up
+ * a default structure using default values depending on the device type.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_receiver_info,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_setup_receiver_info
+ * @see ::mbg_get_gps_receiver_info
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_receiver_info( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_receiver_info, IOCTL_DEV_HAS_RECEIVER_INFO );
+
+} // mbg_chk_dev_has_receiver_info
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_receiver_info;
/*HDR*/
/**
- @brief Check if the DLL/shared library is compatible with a given version.
+ * @brief Check if a device supports large configuration data structures.
+ *
+ * Such structures have been introduced with the first Meinberg GPS receivers.
+ * Mostly all configuration structures are large data structures, and mostly all
+ * current devices support this, but some very old devices may not.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_gps_data,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_gps_data( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_gps_data, IOCTL_DEV_HAS_GPS_DATA );
- If this library is used as a DLL/shared object library then the version
- number can be checked to see if the header files which are actually used
- to build an application are compatible with the header files which have
- been used to build the library, and thus the API function are called
- in the correct way.
+} // mbg_chk_dev_has_gps_data
- @param header_version Version number to be checked, should be ::MBGDEVIO_VERSION
- from the mbgdevio.h file used to build the application
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_gps_data;
- @return ::MBG_SUCCESS if compatible, ::MBG_ERR_LIB_NOT_COMPATIBLE if not.
- @see mbgdevio_get_version()
- @see ::MBGDEVIO_VERSION defined in mbgdevio.h
- */
-_MBG_API_ATTR int _MBG_API mbgdevio_check_version( int header_version )
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_generic_io API call.
+ *
+ * <b>Warning</b>: This call is for debugging purposes and internal use only!
+ *
+ * @note This function should be preferred over ::mbg_dev_has_generic_io,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_generic_io
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_generic_io( MBG_DEV_HANDLE dh )
{
- if ( header_version >= MBGDEVIO_COMPAT_VERSION )
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_generic_io, IOCTL_DEV_HAS_GENERIC_IO );
+
+} // mbg_chk_dev_has_generic_io
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_generic_io;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_asic_version API call.
+ *
+ * It depends on the bus interface chip assembled on the device
+ * if ::mbg_get_asic_version is supported, or not.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_asic_version,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_asic_version
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_asic_version( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_asic_version, IOCTL_DEV_HAS_PCI_ASIC_VERSION );
+
+} // mbg_chk_dev_has_asic_version
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_asic_version;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_asic_features call.
+ *
+ * It depends on the bus interface chip assembled on the device
+ * if ::mbg_get_asic_features is supported, or not.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_asic_features,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_asic_features
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_asic_features( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_asic_features, IOCTL_DEV_HAS_PCI_ASIC_FEATURES );
+
+} // mbg_chk_dev_has_asic_features
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_asic_features;
+
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides eXtended Multi Ref (XMR) inputs.
+ *
+ * Devices providing XMR inputs can receive or decode different timing
+ * signals in parallel, and the supported sources can be prioritized.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_xmr,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_set_gps_xmr_settings_idx
+ * @see ::mbg_get_xmr_holdover_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_xmr( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_ri_cond( dh, _pcps_has_ri_xmr, IOCTL_DEV_HAS_XMR );
+
+} // mbg_chk_dev_supp_xmr
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_supp_xmr;
+
+
+
+static /*HDR*/
+/**
+ * @brief ::TODO
+ */
+int chk_bus_flags( MBG_DEV_HANDLE dh, int bus_flag_mask )
+{
+ PCPS_DEV dev_info;
+
+ int rc = mbg_get_device_info( dh, &dev_info );
+
+ if ( mbg_rc_is_error( rc ) )
+ return rc;
+
+ return ( dev_info.type.bus_flags & bus_flag_mask ) ? MBG_SUCCESS : MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // chk_bus_flags
+
+
+
+/*HDR*/
+/**
+ * @brief Check if the device is connected to the ISA bus.
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to ISA, ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_isa( MBG_DEV_HANDLE dh )
+{
+ return chk_bus_flags( dh, PCPS_BUS_ISA );
+
+} // mbg_chk_dev_is_isa
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_isa;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if the device is connected to the MCA bus.
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to MCA, ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_mca( MBG_DEV_HANDLE dh )
+{
+ return chk_bus_flags( dh, PCPS_BUS_MCA );
+
+} // mbg_chk_dev_is_mca
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_mca;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if the device is connected to the PCI bus and if one of the PCI interface chips is used
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to PCI and one of the PCI interface chips is used,
+ * ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_pci( MBG_DEV_HANDLE dh )
+{
+ return chk_bus_flags( dh, PCPS_BUS_PCI );
+} // mbg_chk_dev_is_pci
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_pci;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if the device is connected to the PCI Express bus and if one of the PCI Express interface chips is used
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to PCI Express and one of the PCI Express interface chips is used,
+ * ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_pci_express( MBG_DEV_HANDLE dh )
+{
+ PCPS_DEV dev_info;
+
+ int rc = mbg_get_device_info( dh, &dev_info );
+
+ if ( mbg_rc_is_error( rc ) )
+ return rc;
+
+ if ( ( dev_info.type.bus_flags == PCPS_BUS_PCI_MBGPEX ) ||
+ ( dev_info.type.bus_flags == PCPS_BUS_PCI_PEX8311 ) )
return MBG_SUCCESS;
- return _mbg_err_to_os( MBG_ERR_LIB_NOT_COMPATIBLE );
+ return MBG_ERR_NOT_SUPP_BY_DEV;
-} // mbgdevio_check_version
+} // mbg_chk_dev_is_pci_express
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_pci_express;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if the device is connected to the USB bus
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to USB, ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_usb( MBG_DEV_HANDLE dh )
+{
+ return chk_bus_flags( dh, PCPS_BUS_USB );
+
+} // mbg_chk_dev_is_usb
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_usb;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports GNSS configuration.
+ *
+ * This is usually the case if a device supports reception of
+ * several different satellite systems, e.g. GPS, Glonass, etc.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_gnss,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_gnss_mode_info
+ * @see ::mbg_set_gps_gnss_mode_settings
+ * @see ::mbg_get_gps_all_gnss_sat_info
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_gnss( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_is_gnss, IOCTL_DEV_IS_GNSS );
+
+} // mbg_chk_dev_is_gnss
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_gnss;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a GPS receiver.
+ *
+ * The function also returns ::MBG_SUCCESS for GNSS receivers
+ * which can track GPS satellites beside other GNSS systems.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_gps,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_gps( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_is_gps, IOCTL_DEV_IS_GPS );
+
+} // mbg_chk_dev_is_gps
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_gps;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a DCF77 receiver.
+ *
+ * Beside standard DCF77 receivers which receive the legacy AM signal
+ * there are also PZF receivers which can decode the pseudo-random phase
+ * modulation and thus yield a higher accuracy. See ::mbg_chk_dev_has_pzf.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_dcf,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pzf
+ * @see ::mbg_chk_dev_is_lwr
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_dcf( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_is_dcf, IOCTL_DEV_IS_DCF );
+
+} // mbg_chk_dev_is_dcf
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_dcf;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports demodulation of the DCF77 PZF code
+ *
+ * Beside the enhanced PZF correlation receivers which decode the DCF77's
+ * pseudo-random phase modulation to yield a better accuracy there are also
+ * legacy DCF77 receivers which just decode the standard AM signal.
+ * See ::mbg_chk_dev_is_dcf.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_pzf,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_corr_info
+ * @see ::mbg_chk_dev_supp_tr_distance
+ * @see ::mbg_chk_dev_is_dcf
+ * @see ::mbg_chk_dev_is_lwr
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_pzf( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_pzf, IOCTL_DEV_HAS_PZF );
+
+} // mbg_chk_dev_has_pzf
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_pzf;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a MSF receiver.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_msf,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_lwr
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_msf( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_is_msf, IOCTL_DEV_IS_MSF );
+
+} // mbg_chk_dev_is_msf
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_msf;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a WWVB receiver.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_wwvb,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_lwr
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_wwvb( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_is_wwvb, IOCTL_DEV_IS_WWVB );
+
+} // _pcps_ddev_is_wwvb
+
+MBG_CHK_SUPP_FNC _pcps_ddev_is_wwvb;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is any long wave signal receiver.
+ *
+ * Long wave receivers include e.g. DCF77, MSF, WWVB, or JJY.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_lwr,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_dcf
+ * @see ::mbg_chk_dev_is_msf
+ * @see ::mbg_chk_dev_is_wwvb
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_lwr( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_is_lwr, IOCTL_DEV_IS_LWR );
+
+} // mbg_chk_dev_is_lwr
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_lwr;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a configurable IRIG input.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_irig_rx,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_irig_rx_info
+ * @see ::mbg_set_irig_rx_settings
+ * @see ::mbg_chk_dev_has_irig_tx
+ * @see ::mbg_chk_dev_has_irig
+*/
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_is_irig_rx( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_is_irig_rx, IOCTL_DEV_IS_IRIG_RX );
+
+} // mbg_chk_dev_is_irig_rx
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_is_irig_rx;
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides simple LAN interface API calls.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_lan_intf,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_state
+ * @see ::mbg_get_ip4_settings
+ * @see ::mbg_set_ip4_settings
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_lan_intf( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_lan_intf, IOCTL_DEV_HAS_LAN_INTF );
+
+} // mbg_chk_dev_has_lan_intf
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_lan_intf;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides PTP configuration/status calls.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_ptp,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_state
+ * @see ::mbg_get_ptp_cfg_info
+ * @see ::mbg_set_ptp_cfg_settings
+ * @see ::mbg_chk_dev_has_ptp_unicast
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_ptp( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_ptp, IOCTL_DEV_HAS_PTP );
+
+} // mbg_chk_dev_has_ptp
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_ptp;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides PTP unicast feature/configuration.
+ *
+ * Not all devices which support PTP do also support PTP Unicast. This API
+ * call checks if PTP Unicast is supported in addition to the standard
+ * PTP multicast.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_ptp_unicast,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_uc_master_cfg_limits
+ * @see ::mbg_get_all_ptp_uc_master_info
+ * @see ::mbg_set_ptp_uc_master_settings_idx
+ * @see ::mbg_get_ptp_state
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_ptp_unicast( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_ri_cond( dh, _pcps_has_ri_ptp_unicast, IOCTL_DEV_HAS_PTP_UNICAST );
+
+} // mbg_chk_dev_has_ptp_unicast
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_ptp_unicast;
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the mbg_get_hr_time... functions.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_hr_time,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_hr_time_cycles
+ * @see ::mbg_get_hr_time_comp
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_hr_time( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_hr_time, IOCTL_DEV_HAS_HR_TIME );
+
+} // mbg_chk_dev_has_hr_time
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_hr_time;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the mbg_get_fast_hr_timestamp... calls.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_fast_hr_timestamp,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_fast_hr_timestamp_cycles
+ * @see ::mbg_get_fast_hr_timestamp_comp
+ * @see ::mbg_get_fast_hr_timestamp
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_fast_hr_timestamp( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_fast_hr_timestamp, IOCTL_DEV_HAS_FAST_HR_TIMESTAMP );
+
+} // mbg_chk_dev_has_fast_hr_timestamp
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_fast_hr_timestamp;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports configurable time scales.
+ *
+ * By default the cards return %UTC and/or local time. However, some cards
+ * can be configured to return raw GPS time or TAI instead.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_time_scale,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_time_scale_info
+ * @see ::mbg_set_time_scale_settings
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_time_scale( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_time_scale, IOCTL_DEV_HAS_GPS_TIME_SCALE );
+
+} // mbg_chk_dev_has_time_scale
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_time_scale;
+
+
+
+/*HDR*/
+/** (Intentionally excluded from Doxygen)
+ * @brief Check if a device supports setting an event time
+ *
+ * This feature is only supported by some special custom firmware
+ * to preset a %UTC time at which the clock is to generate an output signal.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_event_time,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_set_event_time
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_event_time( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_event_time, IOCTL_DEV_HAS_EVENT_TIME );
+
+} // mbg_chk_dev_has_event_time
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_event_time;
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_ucap_entries and ::mbg_get_ucap_event calls.
+ *
+ * If the device doesn't support this but is a GPS card then the card provides
+ * a time capture FIFO buffer and the obsolete ::mbg_get_gps_ucap call can be used
+ * to retrieve entries from the FIFO buffer.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_ucap,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_get_ucap_event
+ * @see ::mbg_clr_ucap_buff
+ * @see ::mbg_get_gps_ucap
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_ucap( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_ucap, IOCTL_DEV_HAS_UCAP );
+
+} // mbg_chk_dev_has_ucap
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_ucap;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_clr_ucap_buff call.
+ *
+ * The ::mbg_clr_ucap_buff call can be used to clear a device's on-board
+ * time capture FIFO buffer, but the call may not be supported by some
+ * older GPS devices.
+ *
+ * @note This function should be preferred over ::mbg_dev_can_clr_ucap_buff,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_clr_ucap_buff
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_can_clr_ucap_buff( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_can_clr_ucap_buff, IOCTL_DEV_CAN_CLR_UCAP_BUFF );
+
+} // mbg_chk_dev_can_clr_ucap_buff
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_can_clr_ucap_buff;
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports timezone configuration using the ::TZDL structure.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_tzdl,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_tzdl
+ * @see ::mbg_set_gps_tzdl
+ * @see ::mbg_chk_dev_has_tz
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_tzdl( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_tzdl, IOCTL_DEV_HAS_TZDL );
+
+} // mbg_chk_dev_has_tzdl
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_tzdl;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports timezone configuration using the ::PCPS_TZDL structure.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_pcps_tzdl,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_pcps_tzdl
+ * @see ::mbg_set_pcps_tzdl
+ * @see ::mbg_chk_dev_has_tz
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_pcps_tzdl( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_pcps_tzdl, IOCTL_DEV_HAS_PCPS_TZDL );
+
+} // mbg_chk_dev_has_pcps_tzdl
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_pcps_tzdl;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports timezone configuration using the ::PCPS_TZCODE type.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_tzcode,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_tzcode
+ * @see ::mbg_set_tzcode
+ * @see ::mbg_chk_dev_has_tz
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_tzcode( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_tzcode, IOCTL_DEV_HAS_TZCODE );
+
+} // mbg_chk_dev_has_tzcode
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_tzcode;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports any kind of timezone configuration.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_tz,
+ * which has been deprecated.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_tzdl
+ * @see ::mbg_chk_dev_has_pcps_tzdl
+ * @see ::mbg_chk_dev_has_tzcode
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_tz( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_tz, IOCTL_DEV_HAS_TZ );
+
+} // mbg_chk_dev_has_tz
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_tz;
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides either an IRIG input or output.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_irig,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_irig_rx
+ * @see ::mbg_chk_dev_has_irig_tx
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_irig( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_irig, IOCTL_DEV_HAS_IRIG );
+
+} // mbg_chk_dev_has_irig
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_irig;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a configurable IRIG output.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_irig,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_irig_tx_info
+ * @see ::mbg_set_irig_tx_settings
+ * @see ::mbg_chk_dev_is_irig_rx
+ * @see ::mbg_chk_dev_has_irig
+ * @see @ref group_icode
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_irig_tx( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_irig_tx, IOCTL_DEV_HAS_IRIG_TX );
+
+} // mbg_chk_dev_has_irig_tx
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_irig_tx;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_irig_ctrl_bits call
+ *
+ * @note This function should be preferred over ::mbg_dev_has_irig_ctrl_bits,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_irig_ctrl_bits
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_irig_ctrl_bits( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_irig_ctrl_bits, IOCTL_DEV_HAS_IRIG_CTRL_BITS );
+
+} // mbg_chk_dev_has_irig_ctrl_bits
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_irig_ctrl_bits;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_raw_irig_data call.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_raw_irig_data,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_raw_irig_data
+ * @see ::mbg_get_raw_irig_data_on_sec_change
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_raw_irig_data( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_raw_irig_data, IOCTL_DEV_HAS_RAW_IRIG_DATA );
+
+} // mbg_chk_dev_has_raw_irig_data
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_raw_irig_data;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_irig_time call.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_irig_time,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_irig_time
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_irig_time( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_irig_time, IOCTL_DEV_HAS_IRIG_TIME );
+
+} // mbg_chk_dev_has_irig_time
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_irig_time;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides the level of its inputs signal.
+ *
+ * This is useful to display the signal level of e.g. an IRIG or similar
+ * time code, or a long wave signal.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_signal,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_signal( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_signal, IOCTL_DEV_HAS_SIGNAL );
+
+} // mbg_chk_dev_has_signal
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_signal;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a modulation signal.
+ *
+ * Modulation signals are e.g. the second marks provided by a long wave receiver.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_mod,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_mod( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_mod, IOCTL_DEV_HAS_MOD );
+
+} // mbg_chk_dev_has_mod
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_mod;
+
+
+
+/*HDR*/
+/** (Intentionally excluded from Doxygen)
+ * Check if a device provides a serial output supporting
+ * higher baud rates than older cards, i.e. ::DEFAULT_BAUD_RATES_DCF_HS
+ * rather than ::DEFAULT_BAUD_RATES_DCF.
+ *
+ * The call ::mbg_get_serial_settings takes care of this, so applications
+ * which use that call as suggested don't need to use this call directly.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_serial_hs,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_serial_settings
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_serial_hs( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_serial_hs, IOCTL_DEV_HAS_SERIAL_HS );
+
+} // mbg_chk_dev_has_serial_hs
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_serial_hs;
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a programmable frequency synthesizer.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_synth,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_synth
+ * @see ::mbg_set_synth
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_synth( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_synth, IOCTL_DEV_HAS_SYNTH );
+
+} // mbg_chk_dev_has_synth
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_synth;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides GPIO signal inputs and/or outputs.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_gpio,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ * @see ::mbg_get_gps_all_gpio_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_gpio( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_ri_cond( dh, _pcps_has_ri_gpio, IOCTL_DEV_HAS_GPIO );
+
+} // mbg_chk_dev_supp_gpio
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_supp_gpio;
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports configuration of antenna cable length.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_cab_len,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_ant_cable_len
+ * @see ::mbg_set_gps_ant_cable_len
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_cab_len( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_cab_len, IOCTL_DEV_HAS_CAB_LEN );
+
+} // mbg_chk_dev_has_cab_len
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_cab_len;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a configurable ref time offset.
+ *
+ * This may be required to convert the received time to %UTC, if the input
+ * signal doesn't specify this (e.g. with most IRIG code formats). //###
+ *
+ * @note This function should be preferred over ::mbg_dev_has_ref_offs,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_ref_offs
+ * @see ::mbg_set_ref_offs
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_ref_offs( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_ref_offs, IOCTL_DEV_HAS_REF_OFFS );
+
+} // mbg_chk_dev_has_ref_offs
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_ref_offs;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::MBG_OPT_INFO/::MBG_OPT_SETTINGS.
+ *
+ * These structures contain optional settings, controlled by flags.
+ * See ::MBG_OPT_SETTINGS and related definitions.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_opt_flags,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_opt_info
+ * @see ::mbg_set_opt_settings
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_opt_flags( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_opt_flags, IOCTL_DEV_HAS_OPT_FLAGS );
+
+} // mbg_chk_dev_has_opt_flags
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_opt_flags;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device support reading/writing of UTC parameters.
+ *
+ * This API call checks if a device supports reading/writing a GPS %UTC
+ * parameter set via the PC bus. Reading/writing these parameters via the
+ * serial port using the Meinberg binary data protocol is supported by all
+ * Meinberg GPS devices.
+ *
+ * The %UTC parameter set is usually received from the satellites' broadcasts
+ * and contains the current time offset between GPS time and UTC, plus information
+ * on a pending leap second event.
+ *
+ * It may be useful to overwrite them to do some tests, or for applications
+ * where a card is freewheeling.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_utc_parm,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_utc_parm
+ * @see ::mbg_set_utc_parm
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_utc_parm( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_utc_parm, IOCTL_DEV_HAS_GPS_UTC_PARM );
+
+} // mbg_chk_dev_has_utc_parm
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_utc_parm;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports reading correlation info
+ *
+ * @note This function should be preferred over ::mbg_dev_has_corr_info,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pzf
+ * @see ::mbg_get_corr_info
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_has_corr_info( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_corr_info, IOCTL_DEV_HAS_CORR_INFO );
+
+} // mbg_chk_dev_has_corr_info
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_has_corr_info;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports configurable distance from transmitter
+ *
+ * The distance from transmitter parameter is used to compensate
+ * the RF propagation delay, mostly with long wave receivers.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_tr_distance,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pzf
+ * @see ::mbg_get_tr_distance
+ * @see ::mbg_set_tr_distance
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_tr_distance( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_tr_distance, IOCTL_DEV_HAS_TR_DISTANCE );
+
+} // mbg_chk_dev_supp_tr_distance
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_supp_tr_distance;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a debug status word to be read
+ *
+ * @note This function should be preferred over ::mbg_dev_has_debug_status,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_debug_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_debug_status( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_debug_status, IOCTL_DEV_HAS_DEBUG_STATUS );
+
+} // mbg_chk_dev_supp_debug_status
+
+MBG_CHK_SUPP_FNC mbg_chk_dev_supp_debug_status;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides an on-board event log.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_evt_log,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_clr_evt_log
+ * @see ::mbg_get_num_evt_log_entries
+ * @see ::mbg_get_first_evt_log_entry
+ * @see ::mbg_get_next_evt_log_entry
+ */
+_MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_evt_log( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_new_query_cond( dh, _pcps_ddev_has_evt_log, IOCTL_DEV_HAS_EVT_LOG );
+
+} // mbg_chk_dev_supp_evt_log
+MBG_CHK_SUPP_FNC mbg_chk_dev_supp_evt_log;
-static /*HDR*/ //##++ make this public ?
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::RECEIVER_INFO structure and related calls.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_receiver_info preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_receiver_info
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_receiver_info" ) _MBG_API mbg_dev_has_receiver_info( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_receiver_info, IOCTL_DEV_HAS_RECEIVER_INFO, p );
+
+} // mbg_dev_has_receiver_info
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports large configuration data structures.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_gps_data preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_gps_data
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_gps_data" ) _MBG_API mbg_dev_has_gps_data( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_gps_data, IOCTL_DEV_HAS_GPS_DATA, p );
+
+} // mbg_dev_has_gps_data
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_generic_io API call.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_generic_io preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_generic_io
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_generic_io" ) _MBG_API mbg_dev_has_generic_io( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_generic_io, IOCTL_DEV_HAS_GENERIC_IO, p );
+
+} // mbg_dev_has_generic_io
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_asic_version call.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_asic_version preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_asic_version
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_asic_version" ) _MBG_API mbg_dev_has_asic_version( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_asic_version, IOCTL_DEV_HAS_PCI_ASIC_VERSION, p );
+
+} // mbg_dev_has_asic_version
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_asic_features call.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_asic_features preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_asic_features
+ * @see ::mbg_get_asic_features
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_asic_features" ) _MBG_API mbg_dev_has_asic_features( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_asic_features, IOCTL_DEV_HAS_PCI_ASIC_FEATURES, p );
+
+} // mbg_chk_dev_has_asic_features
+
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides extended multi ref (XMR) inputs.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_xmr preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_xmr
+ * @see @ref group_multi_ref_ext
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_xmr" ) _MBG_API mbg_dev_has_xmr( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_ri_cond( dh, _pcps_has_ri_xmr, IOCTL_DEV_HAS_XMR, p );
+
+} // mbg_dev_has_xmr
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports GNSS configuration.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_gnss preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_gnss
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_gnss" ) _MBG_API mbg_dev_is_gnss( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_is_gnss, IOCTL_DEV_IS_GNSS, p );
+
+} // mbg_dev_is_gnss
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a GPS receiver.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_is_gps preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_gps
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_gps" ) _MBG_API mbg_dev_is_gps( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_is_gps, IOCTL_DEV_IS_GPS, p );
+
+} // mbg_dev_is_gps
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a DCF77 receiver.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_dcf preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_dcf
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_dcf" ) _MBG_API mbg_dev_is_dcf( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_is_dcf, IOCTL_DEV_IS_DCF, p );
+
+} // mbg_dev_is_dcf
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports demodulation of the DCF77 PZF code
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_pzf preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pzf
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_pzf" ) _MBG_API mbg_dev_has_pzf( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_pzf, IOCTL_DEV_HAS_PZF, p );
+
+} // mbg_dev_has_pzf
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a MSF receiver.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_msf preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_msf
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_msf" ) _MBG_API mbg_dev_is_msf( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_is_msf, IOCTL_DEV_IS_MSF, p );
+
+} // mbg_dev_is_msf
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a WWVB receiver.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_wwvb preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_wwvb
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_wwvb" ) _MBG_API mbg_dev_is_wwvb( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_is_wwvb, IOCTL_DEV_IS_WWVB, p );
+
+} // mbg_dev_is_wwvb
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is any long wave signal receiver.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_lwr preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_lwr
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_lwr" ) _MBG_API mbg_dev_is_lwr( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_is_lwr, IOCTL_DEV_IS_LWR, p );
+
+} // mbg_dev_is_lwr
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a configurable IRIG input.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_irig_rx preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_irig_rx
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_irig_rx" ) _MBG_API mbg_dev_is_irig_rx( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_is_irig_rx, IOCTL_DEV_IS_IRIG_RX, p );
+
+} // mbg_dev_is_irig_rx
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides simple LAN interface API calls.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_lan_intf preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_lan_intf
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_lan_intf" ) _MBG_API mbg_dev_has_lan_intf( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_lan_intf, IOCTL_DEV_HAS_LAN_INTF, p );
+
+} // mbg_dev_has_lan_intf
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides PTP configuration/status calls.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_ptp preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ptp
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_ptp" ) _MBG_API mbg_dev_has_ptp( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_ptp, IOCTL_DEV_HAS_PTP, p );
+
+} // mbg_dev_has_ptp
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides PTP unicast feature/configuration.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_ptp_unicast preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ptp_unicast
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_ptp_unicast" ) _MBG_API mbg_dev_has_ptp_unicast( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_ri_cond( dh, _pcps_has_ri_ptp_unicast, IOCTL_DEV_HAS_PTP_UNICAST, p );
+
+} // mbg_dev_has_ptp_unicast
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the HR_TIME functions.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_hr_time preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_hr_time
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_hr_time" ) _MBG_API mbg_dev_has_hr_time( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_hr_time, IOCTL_DEV_HAS_HR_TIME, p );
+
+} // mbg_dev_has_hr_time
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the mbg_get_fast_hr_timestamp_...() calls.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_fast_hr_timestamp preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_fast_hr_timestamp
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_fast_hr_timestamp" ) _MBG_API mbg_dev_has_fast_hr_timestamp( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_fast_hr_timestamp, IOCTL_DEV_HAS_FAST_HR_TIMESTAMP, p );
+
+} // mbg_dev_has_fast_hr_timestamp
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports configurable time scales.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_time_scale preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_time_scale
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_time_scale" ) _MBG_API mbg_dev_has_time_scale( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_time_scale, IOCTL_DEV_HAS_GPS_TIME_SCALE, p );
+
+} // mbg_dev_has_time_scale
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports setting an event time
+ *
+ * @note This is only supported by some customized devices
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_event_time preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_event_time
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_event_time" ) _MBG_API mbg_dev_has_event_time( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_event_time, IOCTL_DEV_HAS_EVENT_TIME, p );
+
+} // mbg_dev_has_event_time
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_ucap_entries and ::mbg_get_ucap_event calls.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_ucap preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ucap
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_ucap" ) _MBG_API mbg_dev_has_ucap( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_ucap, IOCTL_DEV_HAS_UCAP, p );
+
+} // mbg_dev_has_ucap
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_clr_ucap_buff call.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_can_clr_ucap_buff preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_can_clr_ucap_buff
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_can_clr_ucap_buff" ) _MBG_API mbg_dev_can_clr_ucap_buff( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_can_clr_ucap_buff, IOCTL_DEV_CAN_CLR_UCAP_BUFF, p );
+
+} // mbg_dev_can_clr_ucap_buff
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports timezone configuration using the ::TZDL structure.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_tzdl preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_tzdl
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_tzdl" ) _MBG_API mbg_dev_has_tzdl( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_tzdl, IOCTL_DEV_HAS_TZDL, p );
+
+} // mbg_dev_has_tzdl
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports timezone configuration using the ::PCPS_TZDL structure.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_pcps_tzdl preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pcps_tzdl
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_pcps_tzdl" ) _MBG_API mbg_dev_has_pcps_tzdl( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_pcps_tzdl, IOCTL_DEV_HAS_PCPS_TZDL, p );
+
+} // mbg_dev_has_pcps_tzdl
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports timezone configuration using the ::PCPS_TZCODE type.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_tzcode preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_tzcode
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_tzcode" ) _MBG_API mbg_dev_has_tzcode( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_tzcode, IOCTL_DEV_HAS_TZCODE, p );
+
+} // mbg_dev_has_tzcode
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports any kind of timezone configuration.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_tz preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_tz
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_tz" ) _MBG_API mbg_dev_has_tz( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_tz, IOCTL_DEV_HAS_TZ, p );
+
+} // mbg_dev_has_tz
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides either an IRIG input or output.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_irig preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_irig
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_irig" ) _MBG_API mbg_dev_has_irig( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_irig, IOCTL_DEV_HAS_IRIG, p );
+
+} // mbg_dev_has_irig
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a configurable IRIG output.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_irig_tx preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_irig_tx
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_irig_tx" ) _MBG_API mbg_dev_has_irig_tx( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_irig_tx, IOCTL_DEV_HAS_IRIG_TX, p );
+
+} // mbg_dev_has_irig_tx
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_irig_ctrl_bits call
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_irig_ctrl_bits preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_irig_ctrl_bits
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_irig_ctrl_bits" ) _MBG_API mbg_dev_has_irig_ctrl_bits( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_irig_ctrl_bits, IOCTL_DEV_HAS_IRIG_CTRL_BITS, p );
+
+} // mbg_dev_has_irig_ctrl_bits
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_raw_irig_data call.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_raw_irig_data preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_raw_irig_data
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_raw_irig_data" ) _MBG_API mbg_dev_has_raw_irig_data( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_raw_irig_data, IOCTL_DEV_HAS_RAW_IRIG_DATA, p );
+
+} // mbg_dev_has_raw_irig_data
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::mbg_get_irig_time call.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_irig_time preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_irig_time
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_irig_time" ) _MBG_API mbg_dev_has_irig_time( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_irig_time, IOCTL_DEV_HAS_IRIG_TIME, p );
+
+} // mbg_dev_has_irig_time
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides the level of its inputs signal.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_signal preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_signal
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_signal" ) _MBG_API mbg_dev_has_signal( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_signal, IOCTL_DEV_HAS_SIGNAL, p );
+
+} // mbg_dev_has_signal
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a modulation signal.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_mod preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_mod
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_mod" ) _MBG_API mbg_dev_has_mod( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_mod, IOCTL_DEV_HAS_MOD, p );
+
+} // mbg_dev_has_mod
+
+
+
+/*HDR*/
+/* (Intentionally excluded from Doxygen)
+ * Check if a device provides a serial output supporting
+ * higher baud rates than older cards, i.e. ::DEFAULT_BAUD_RATES_DCF_HS
+ * rather than ::DEFAULT_BAUD_RATES_DCF.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_serial_hs preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_serial_hs
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_serial_hs" ) _MBG_API mbg_dev_has_serial_hs( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_serial_hs, IOCTL_DEV_HAS_SERIAL_HS, p );
+
+} // mbg_dev_has_serial_hs
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a programmable frequency synthesizer.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_synth preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_synth
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_synth" ) _MBG_API mbg_dev_has_synth( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_synth, IOCTL_DEV_HAS_SYNTH, p );
+
+} // mbg_dev_has_synth
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides GPIO signal inputs and/or outputs.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_gpio preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_gpio
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_gpio" ) _MBG_API mbg_dev_has_gpio( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_ri_cond( dh, _pcps_has_ri_gpio, IOCTL_DEV_HAS_GPIO, p );
+
+} // mbg_dev_has_gpio
+
+
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports configuration of antenna cable length.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_cab_len preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_cab_len
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_cab_len" ) _MBG_API mbg_dev_has_cab_len( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_cab_len, IOCTL_DEV_HAS_CAB_LEN, p );
+
+} // mbg_dev_has_cab_len
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a configurable ref time offset.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_ref_offs preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ref_offs
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_ref_offs" ) _MBG_API mbg_dev_has_ref_offs( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_ref_offs, IOCTL_DEV_HAS_REF_OFFS, p );
+
+} // mbg_dev_has_ref_offs
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::MBG_OPT_INFO/::MBG_OPT_SETTINGS.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_opt_flags preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_opt_flags
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_opt_flags" ) _MBG_API mbg_dev_has_opt_flags( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_opt_flags, IOCTL_DEV_HAS_OPT_FLAGS, p );
+
+} // mbg_dev_has_opt_flags
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device support reading/writing of ::UTC parameters.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_utc_parm preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_utc_parm
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_utc_parm" ) _MBG_API mbg_dev_has_utc_parm( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_utc_parm, IOCTL_DEV_HAS_GPS_UTC_PARM, p );
+
+} // mbg_dev_has_utc_parm
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports reading correlation info
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_corr_info preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_corr_info
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_corr_info" ) _MBG_API mbg_dev_has_corr_info( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_corr_info, IOCTL_DEV_HAS_CORR_INFO, p );
+
+} // mbg_dev_has_corr_info
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports configurable distance from transmitter
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_tr_distance preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_tr_distance
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_tr_distance" ) _MBG_API mbg_dev_has_tr_distance( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_tr_distance, IOCTL_DEV_HAS_TR_DISTANCE, p );
+
+} // mbg_dev_has_tr_distance
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides a debug status word to be read
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_debug_status preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_debug_status
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_debug_status" ) _MBG_API mbg_dev_has_debug_status( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_debug_status, IOCTL_DEV_HAS_DEBUG_STATUS, p );
+
+} // mbg_dev_has_debug_status
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device provides an on-board event log.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_evt_log preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_evt_log
+ */
+_MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_evt_log" ) _MBG_API mbg_dev_has_evt_log( MBG_DEV_HANDLE dh, int *p )
+{
+ _mbgdevio_old_query_cond( dh, _pcps_ddev_has_evt_log, IOCTL_DEV_HAS_EVT_LOG, p );
+
+} // mbg_dev_has_evt_log
+
+
+
+static /*HDR*/
+/**
+ * @brief Update a ::PCPS_TIME_STAMP to compensate the latency of an API call
+ *
+ * @param[in,out] ts The timestamp to be updated
+ * @param[in] p_cyc_ts Cycles value taken when the function was called
+ * @param[in] p_cyc_ontime Cycles value taken when access to the device was made
+ * @param[in] p_cyc_freq Cycles frequency determined by the application, depending on the type of cycles counter
+ * @param[out] hns_latency Optional pointer to a variable to receive the computed latency, or NULL
+ *
+ * @return ::MBG_SUCCESS on success, or one of the @ref MBG_ERROR_CODES
+ */
int mbg_comp_hr_latency( PCPS_TIME_STAMP *ts,
const MBG_PC_CYCLES *p_cyc_ts,
const MBG_PC_CYCLES *p_cyc_ontime,
const MBG_PC_CYCLES_FREQUENCY *p_cyc_freq,
int32_t *hns_latency )
{
- #if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_UNIX )
+ #if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX )
int64_t cyc_latency;
int64_t frac_latency;
@@ -521,10 +3042,10 @@ int mbg_comp_hr_latency( PCPS_TIME_STAMP *ts,
);
#endif
- // Account for cycles counter overflow. This is
- // supposed to happen once every 2^^63 units of the
- // cycles counter frequency, i.e. about every
- // 97 years on a system with 3 GHz clock.
+ // Account for cycles counter overflow. If the CPU's TSC is used
+ // this is supposed to happen once every 2^^63 units of the
+ // cycles counter frequency, i.e. about every 97 years on a system
+ // with 3 GHz clock.
if ( cyc_latency < 0 )
{
cyc_latency += ( (uint64_t) -1 ) >> 1;
@@ -537,12 +3058,12 @@ int mbg_comp_hr_latency( PCPS_TIME_STAMP *ts,
#endif
}
- // convert latency to binary fractions of seconds,
+ // Convert latency to binary fractions of seconds,
// i.e. units of 2^^-32.
frac_latency = (*p_cyc_freq) ? ( cyc_latency * ( ( (int64_t) 1 ) << 32 ) / *p_cyc_freq ) : 0;
- // compute the compensated fractional part of the HR time stamp
- // and account for borrows from the sec field
+ // Compute the compensated fractional part of the HR time stamp
+ // and account for borrows from the sec field.
comp_frac = ts->frac - frac_latency;
ts->frac = (uint32_t) comp_frac; // yields 32 LSBs
ts->sec += (uint32_t) ( comp_frac >> 32 ); // yields 32 MSBs
@@ -584,7 +3105,7 @@ int mbg_comp_hr_latency( PCPS_TIME_STAMP *ts,
#else
// This is currently not supported by the target environment.
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_ON_OS );
+ return MBG_ERR_NOT_SUPP_ON_OS;
#endif
@@ -594,15 +3115,16 @@ int mbg_comp_hr_latency( PCPS_TIME_STAMP *ts,
/*HDR*/
/**
- @brief Open a device by index, starting from 0.
-
- This function is <b>out of date</b>, mbg_open_device_by_name()
- should be used instead.
-
- See the <b>note</b> for mbg_find_device() for details.
-
- @param device_index index of the device, use 0 for the first device.
- */
+ * @brief Open a device by index, starting from 0
+ *
+ * @deprecated This function is deprecated, use ::mbg_open_device_by_name preferably.
+ *
+ * @note See comments for ::mbg_find_devices for details.
+ *
+ * @param[in] device_index Index of the device, use 0 for the first device
+ *
+ * @return A valid device handle on success, else ::MBG_INVALID_DEV_HANDLE
+ */
_MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device( unsigned int device_index )
{
#if defined( MBG_TGT_WIN32 )
@@ -616,7 +3138,7 @@ _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device( unsigned int device_index
goto fail;
- dh = CreateFile(
+ dh = CreateFileA(
device_path, // file name
GENERIC_READ | GENERIC_WRITE, // access mode
0, // share mode
@@ -640,15 +3162,15 @@ _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device( unsigned int device_index
fail:
return MBG_INVALID_DEV_HANDLE;
-#elif defined( MBG_TGT_UNIX )
+#elif defined( MBG_TGT_POSIX ) && !defined( MBG_TGT_QNX_NTO )
MBG_DEV_HANDLE dh;
char dev_fn[50];
- if ( device_index > MBG_MAX_DEVICES )
- device_index = MBG_MAX_DEVICES;
+ if ( device_index > N_SUPP_DEV_BUS )
+ device_index = N_SUPP_DEV_BUS;
- sprintf( dev_fn, "/dev/mbgclock%d", device_index ); //##++
+ snprintf_safe( dev_fn, sizeof( dev_fn ), "/dev/mbgclock%d", device_index );
dh = open( dev_fn, O_RDWR );
@@ -666,14 +3188,18 @@ fail:
static /*HDR*/
/* (Intentionally excluded from Doxygen)
- @brief Return a handle to a device specified by a given hardware_id.
-
- The format the hardware_id depends on the operating system, so
- this function is used only internally to detect devices for
- which a unique name of the format MBG_HW_NAME is generated,
- which is in turn used with the public API functions.
- */
-MBG_DEV_HANDLE _MBG_API mbg_open_device_by_hw_id( const char* hw_id )
+ * @brief Return a handle to a device specified by a given hardware_id.
+ *
+ * The format the hardware_id depends on the operating system, so
+ * this function is used only internally to detect devices for
+ * which a unique name of the format MBG_HW_NAME is generated,
+ * which is in turn used with the public API functions.
+ *
+ * @param[in] hw_id The hardware ID string
+ *
+ * @return A valid device handle on success, else ::MBG_INVALID_DEV_HANDLE
+ */
+MBG_DEV_HANDLE _MBG_API mbg_open_device_by_hw_id( const char *hw_id )
{
#if defined( MBG_TGT_WIN32 )
@@ -684,7 +3210,7 @@ MBG_DEV_HANDLE _MBG_API mbg_open_device_by_hw_id( const char* hw_id )
if ( hw_id == NULL )
goto fail;
- dh = CreateFile(
+ dh = CreateFileA(
hw_id, // file name
GENERIC_READ | GENERIC_WRITE, // access mode
0, // share mode
@@ -702,7 +3228,7 @@ MBG_DEV_HANDLE _MBG_API mbg_open_device_by_hw_id( const char* hw_id )
fail:
return MBG_INVALID_DEV_HANDLE;
-#elif defined ( MBG_TGT_UNIX )
+#elif defined( MBG_TGT_POSIX ) && !defined( MBG_TGT_QNX_NTO )
MBG_DEV_HANDLE dh = -1;
@@ -723,22 +3249,22 @@ fail:
/*HDR*/
/**
- @brief Get the number of supported devices installed on the computer.
-
- This function is <b>out of date</b>, mbg_find_devices_with_names()
- should be used instead.
-
- <b>Note:</b> This function is out of date since it may not work
- correctly for Meinberg devices which are disconnected and reconnected
- while the system is running (e.g. USB devices). However, the function
- will be kept for compatibility reasons and works correctly if all
- Meinberg devices are connected at system boot and are not disconnected
- and reconnected during operation
-
- @return The number of devices found
-
- @see mbg_find_devices_with_names()
- */
+ * @brief Get the number of supported devices installed on the computer.
+ *
+ * @deprecated This function is deprecated, ::mbg_find_devices_with_names
+ * should be used instead.
+ *
+ * @note This function is out of date since it may not work
+ * correctly for Meinberg devices which are disconnected and reconnected
+ * while the system is running (e.g. USB devices). However, the function
+ * will be kept for compatibility reasons and works correctly if all
+ * Meinberg devices are connected at system boot and are not disconnected
+ * and reconnected during operation
+ *
+ * @return The number of devices found
+ *
+ * @see ::mbg_find_devices_with_names
+ */
_MBG_API_ATTR int _MBG_API mbg_find_devices( void )
{
#if defined( _PCPSDRVR_H )
@@ -772,13 +3298,13 @@ _MBG_API_ATTR int _MBG_API mbg_find_devices( void )
return mbg_svc_find_devices();
-#elif defined ( MBG_TGT_UNIX )
+#elif defined( MBG_TGT_POSIX )
MBG_DEV_HANDLE dh;
int i = 0;
int n = 0;
- while( i < MBG_MAX_DEVICES )
+ while( i < N_SUPP_DEV_BUS )
{
dh = mbg_open_device( i );
@@ -799,16 +3325,17 @@ _MBG_API_ATTR int _MBG_API mbg_find_devices( void )
-#if defined( MBG_TGT_WIN32 ) || defined ( MBG_TGT_UNIX )
+#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX )
+//### TODO: document this function
static /*HDR*/
int mbg_find_devices_with_hw_id( MBG_DEVICE_LIST ** list, int max_devs )
{
- #if defined ( MBG_TGT_WIN32 )
+ #if defined( MBG_TGT_WIN32 )
return mbg_svc_find_devices_with_hw_id( list, max_devs );
- #elif defined ( MBG_TGT_UNIX )
+ #elif defined( MBG_TGT_POSIX )
MBG_DEVICE_LIST *ListBegin;
int n = 0;
@@ -824,11 +3351,11 @@ int mbg_find_devices_with_hw_id( MBG_DEVICE_LIST ** list, int max_devs )
char dev_name[100];
MBG_DEV_HANDLE dh;
- sprintf( dev_name, "/dev/mbgclock%d", i );
+ snprintf_safe( dev_name, sizeof( dev_name ), "/dev/mbgclock%d", i );
dh = mbg_open_device_by_hw_id( dev_name );
- if ( dh != MBG_INVALID_HANDLE )
+ if ( dh != MBG_INVALID_DEV_HANDLE )
{
mbg_close_device( &dh );
@@ -842,7 +3369,7 @@ int mbg_find_devices_with_hw_id( MBG_DEVICE_LIST ** list, int max_devs )
n++;
}
- if ( ++i >= MBG_MAX_DEVICES )
+ if ( ++i >= N_SUPP_DEV_BUS )
break;
}
@@ -867,19 +3394,20 @@ int mbg_find_devices_with_hw_id( MBG_DEVICE_LIST ** list, int max_devs )
-#if defined ( MBG_TGT_WIN32 ) || defined ( MBG_TGT_UNIX )
+#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX )
+//### TODO: document this function
static /*HDR*/
void _MBG_API mbg_free_device_list( MBG_DEVICE_LIST *devices )
{
- #if defined ( MBG_TGT_WIN32 )
+ #if defined( MBG_TGT_WIN32 )
mbg_svc_free_device_list( devices );
#else
int i = 0;
MBG_DEVICE_LIST *Next = NULL;
- while ( i < MBG_MAX_DEVICES)
+ while ( i < N_SUPP_DEV_BUS)
{
if ( devices )
{
@@ -918,31 +3446,33 @@ void _MBG_API mbg_free_device_list( MBG_DEVICE_LIST *devices )
-#if ( defined( MBG_TGT_WIN32 ) || defined ( MBG_TGT_UNIX ) )
+#if ( defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX ) )
+//### TODO: document this function
static /*HDR*/
void get_hw_name_from_hw_id( MBG_DEVICE_INFO *dev_info )
{
MBG_DEV_HANDLE dh;
PCPS_DEV pdev;
- dh = MBG_INVALID_HANDLE;
+ dh = MBG_INVALID_DEV_HANDLE;
memset( &pdev, 0, sizeof( pdev ) );
// Default initializers
- strcpy( dev_info->model_name, "N/A" );
- strcpy( dev_info->serial_number, "N/A" );
- strcpy( dev_info->hw_name, "N/A" );
+ strcpy( dev_info->model_name, str_not_avail );
+ strcpy( dev_info->serial_number, str_not_avail );
+ strcpy( dev_info->hw_name, str_not_avail );
dh = mbg_open_device_by_hw_id( dev_info->hardware_id );
- if ( dh != MBG_INVALID_HANDLE )
+ if ( dh != MBG_INVALID_DEV_HANDLE )
{
- if ( mbg_get_device_info( dh, &pdev ) == MBG_SUCCESS )
+ if ( mbg_rc_is_success( mbg_get_device_info( dh, &pdev ) ) )
{
strcpy( dev_info->model_name, _pcps_type_name( &pdev ) );
strcpy( dev_info->serial_number, _pcps_sernum( &pdev ) );
- sprintf( dev_info->hw_name, "%s_%s", _pcps_type_name( &pdev ), _pcps_sernum( &pdev ) );
+ snprintf_safe( dev_info->hw_name, sizeof( dev_info->hw_name ), "%s_%s",
+ _pcps_type_name( &pdev ), _pcps_sernum( &pdev ) );
}
mbg_close_device( &dh );
@@ -956,27 +3486,27 @@ void get_hw_name_from_hw_id( MBG_DEVICE_INFO *dev_info )
/*HDR*/
/**
- @brief Allocate memory and set up a list of installed and supported devices.
-
- This function should be used preferably instead of mbg_find_devices().
-
- @param device_list Pointer to a linked list of type ::MBG_DEVICENAME_LIST
- with device names. The list will be allocated by this
- function and has to be freed after usage by calling
- mbg_free_device_name_list().
- @param max_devices Maximum number of devices the function should look for
- (can not exceed ::MBG_MAX_DEVICES).
-
- @return number of present devices
-
- @see ::MBG_HW_NAME for the format of the unique names
- @see mbg_free_device_name_list()
- @see mbg_find_devices()
- */
+ * @brief Allocate memory and set up a list of installed and supported devices.
+ *
+ * This function should be used preferably instead of ::mbg_find_devices.
+ *
+ * @param[in] device_list Pointer to a linked list of type ::MBG_DEVICENAME_LIST
+ * with device names. The list will be allocated by this
+ * function and has to be freed after usage by calling
+ * ::mbg_free_device_name_list.
+ * @param[in] max_devices Maximum number of devices the function should look for
+ * (must not exceed ::N_SUPP_DEV_BUS).
+ *
+ * @return number of present devices
+ *
+ * @see ::MBG_HW_NAME for the format of the unique names
+ * @see ::mbg_free_device_name_list
+ * @see ::mbg_find_devices
+ */
_MBG_API_ATTR int _MBG_API mbg_find_devices_with_names( MBG_DEVICENAME_LIST **device_list,
int max_devices )
{
-#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_UNIX )
+#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX )
MBG_DEVICE_LIST *hardware_list = NULL;
MBG_DEVICE_LIST *hardware_list_begin = NULL;
@@ -1001,7 +3531,7 @@ _MBG_API_ATTR int _MBG_API mbg_find_devices_with_names( MBG_DEVICENAME_LIST **de
// Loop through the list of hardware_ids and get their readable names
for (;;)
{
- if ( hardware_list->device_path && i++ < MBG_MAX_DEVICES )
+ if ( hardware_list->device_path && i++ < N_SUPP_DEV_BUS )
{
strcpy( dev_info.hardware_id, hardware_list->device_path );
@@ -1043,24 +3573,24 @@ _MBG_API_ATTR int _MBG_API mbg_find_devices_with_names( MBG_DEVICENAME_LIST **de
/*HDR*/
/**
- @brief Free the memory allocated for a ::MBG_DEVICENAME_LIST.
-
- The list may have been set up and allocated before
- by mbg_find_devices_with_names().
-
- @param *list Linked list of type ::MBG_DEVICENAME_LIST
-
- @see mbg_find_devices_with_names()
- */
+ * @brief Free the memory allocated for a ::MBG_DEVICENAME_LIST.
+ *
+ * The list may have been set up and allocated before
+ * by ::mbg_find_devices_with_names.
+ *
+ * @param[in,out] list Linked list of type ::MBG_DEVICENAME_LIST
+ *
+ * @see ::mbg_find_devices_with_names
+ */
_MBG_API_ATTR void _MBG_API mbg_free_device_name_list( MBG_DEVICENAME_LIST *list)
{
-#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_UNIX )
+#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX )
MBG_DEVICENAME_LIST *Next = NULL;
int i = 0;
// Deallocate members of linked list
- while ( i < MBG_MAX_DEVICES )
+ while ( i < N_SUPP_DEV_BUS )
{
if ( list )
{
@@ -1079,7 +3609,8 @@ _MBG_API_ATTR void _MBG_API mbg_free_device_name_list( MBG_DEVICENAME_LIST *list
i++;
}
-
+#else
+ // TODO: This needs to be handled
#endif
} // mbg_free_device_list
@@ -1088,62 +3619,68 @@ _MBG_API_ATTR void _MBG_API mbg_free_device_name_list( MBG_DEVICENAME_LIST *list
/*HDR*/
/**
- @brief Return a handle to a device with a certain unique name.
-
- The names of the devices that are installed on the system can be retrieved by
- the function mbg_find_devices_with_names().
-
- This function should be used preferably instead of mbg_open_device().
-
- @param hw_name String with the unique name of the device to be opened
- @param selection_mode One of the enum values of ::MBG_MATCH_MODE
-
- @return On success, the function returns a handle to the device, otherwise ::MBG_INVALID_DEV_HANDLE
-
- @see ::MBG_HW_NAME for the format of the unique names.
- @see ::MBG_MATCH_MODE
- @see mbg_find_devices_with_names()
- */
-_MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device_by_name( const char* hw_name, int selection_mode ) //##++++
+ * @brief Return a handle to a device with a certain unique name.
+ *
+ * The names of the devices that are installed on the system can be retrieved by
+ * the function ::mbg_find_devices_with_names.
+ *
+ * This function should be used preferably instead of ::mbg_open_device.
+ *
+ * @param[in] srch_name String with the unique name of the device to be opened
+ * @param[in] selection_mode One of the enum values of ::MBG_MATCH_MODE
+ *
+ * @return On success, the function returns a handle to the device, otherwise ::MBG_INVALID_DEV_HANDLE
+ *
+ * @see ::MBG_HW_NAME for the format of the unique names
+ * @see ::MBG_MATCH_MODE
+ * @see ::mbg_find_devices_with_names
+ */
+_MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device_by_name( const char *srch_name, int selection_mode ) //##++++
{
+ //### TODO: FIXME for MBG_TGT_QNX_NTO
+
+#if ( ( defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX ) ) ) && ! defined( MBG_TGT_QNX_NTO )
-#if ( defined( MBG_TGT_WIN32 ) || defined ( MBG_TGT_UNIX ) )
+ static MBG_DEVICE_INFO device_info_list[N_SUPP_DEV_BUS];
MBG_DEV_HANDLE dh;
MBG_DEVICE_LIST *devices = NULL;
MBG_DEVICE_LIST *ListBegin = NULL;
char hw_id[MAX_INFO_LEN];
- char tmp_model_name[PCPS_CLOCK_NAME_SZ];
- PCPS_SN_STR tmp_sn;
+ char tmp_model_name[PCPS_CLOCK_NAME_SZ] = { 0 };
+ PCPS_SN_STR tmp_sn; // = { 0 }; //##++++ TODO check what this should be used for
int n_devices = 0;
- int i = 0;
- int j = 0;
-
+ size_t srch_name_len = srch_name ? strlen( srch_name ) : 0;
+ size_t i = 0;
+ size_t j = 0;
hw_id[0] = '\0';
- memset( tmp_model_name, 0, sizeof( tmp_model_name) );
memset( device_info_list, 0, sizeof( device_info_list ) );
memset( tmp_sn, 0, sizeof( tmp_sn ) );
// separate hw_name into clock model and serial number
- if ( hw_name && ( strlen( hw_name ) > 0 ) )
+ if ( srch_name && ( srch_name_len > 0 ) )
{
// clock model
- for ( i = 0; ( i < PCPS_CLOCK_NAME_SZ ) && ( hw_name[i] != '_' ) && ( i < (int) strlen( hw_name ) ); i++ )
- tmp_model_name[i] = hw_name[i];
+ for ( i = 0; ( i < PCPS_CLOCK_NAME_SZ ) && ( srch_name[i] != '_' ) && ( i < srch_name_len ); i++ )
+ {
+ char c = srch_name[i];
+ // convert ASCII lower case characters to upper case
+ tmp_model_name[i] = ( c >= 'a' && c <= 'z' ) ? ( c - 0x20 ) : c;
+ }
- tmp_model_name[i] = 0;
+ tmp_model_name[sizeof( tmp_model_name ) - 1] = 0;
i++;
// serial number
- if ( i < (int) strlen( hw_name ) )
+ if ( i < srch_name_len )
{
j = 0;
- while ( ( i < (int) strlen( hw_name ) ) && ( j < PCPS_SN_SIZE ) )
+ while ( ( i < srch_name_len ) && ( j < PCPS_SN_SIZE ) )
{
- tmp_sn[j] = hw_name[i];
+ tmp_sn[j] = srch_name[i];
j++;
i++;
}
@@ -1156,7 +3693,7 @@ _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device_by_name( const char* hw_na
i = 0;
// get OS-dependent hardware_id strings for devices that are present on the system
- n_devices = mbg_find_devices_with_hw_id( &devices, MBG_MAX_DEVICES );
+ n_devices = mbg_find_devices_with_hw_id( &devices, N_SUPP_DEV_BUS );
ListBegin = devices;
@@ -1164,14 +3701,14 @@ _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device_by_name( const char* hw_na
{
for (;;)
{
- if ( devices->device_path && i < MBG_MAX_DEVICES )
+ if ( devices->device_path && i < N_SUPP_DEV_BUS )
{
strncpy( device_info_list[i].hardware_id, devices->device_path, MAX_INFO_LEN );
// get readable hw_name for the device
get_hw_name_from_hw_id( &device_info_list[i] );
- if ( hw_name && device_info_list[i].hw_name && strcmp( device_info_list[i].hw_name, hw_name ) == 0 ) //##+++++
+ if ( srch_name && strcmp( device_info_list[i].hw_name, srch_name ) == 0 )
{
// The requested device was found
strcpy( hw_id, device_info_list[i].hardware_id );
@@ -1212,12 +3749,12 @@ _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device_by_name( const char* hw_na
#endif
-#if defined ( MBG_TGT_WIN32 )
+#if defined( MBG_TGT_WIN32 )
if ( hw_id[0] == '\0' )
goto fail;
- dh = CreateFile(
+ dh = CreateFileA(
hw_id, // file name
GENERIC_READ | GENERIC_WRITE, // access mode
0, // share mode
@@ -1235,7 +3772,7 @@ _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device_by_name( const char* hw_na
fail:
return MBG_INVALID_DEV_HANDLE;
-#elif defined ( MBG_TGT_UNIX )
+#elif defined( MBG_TGT_POSIX ) && !defined( MBG_TGT_QNX_NTO )
if ( hw_id[0] != '\0' )
dh = open( hw_id, O_RDWR );
@@ -1260,17 +3797,17 @@ fail:
/*HDR*/
/**
- @brief Close a handle to a device and set the handle value to ::MBG_INVALID_DEV_HANDLE.
-
- @param dev_handle Handle to a Meinberg device.
- */
+ * @brief Close a handle to a device and set the handle value to ::MBG_INVALID_DEV_HANDLE.
+ *
+ * @param[in,out] dev_handle Pointer to a Meinberg device handle
+ */
_MBG_API_ATTR void _MBG_API mbg_close_device( MBG_DEV_HANDLE *dev_handle )
{
if ( *dev_handle != MBG_INVALID_DEV_HANDLE && *dev_handle != 0 ) //##++++ dev_handle NULL/0 ???
{
#if defined( MBG_TGT_WIN32 )
CloseHandle( *dev_handle );
- #elif defined( MBG_TGT_UNIX )
+ #elif defined( MBG_TGT_POSIX ) && !defined( MBG_TGT_QNX_NTO )
close( *dev_handle );
#endif
}
@@ -1283,13 +3820,13 @@ _MBG_API_ATTR void _MBG_API mbg_close_device( MBG_DEV_HANDLE *dev_handle )
/*HDR*/
/**
- @brief Read information about the driver handling a given device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_DRVR_INFO structure which is filled up.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function
- */
+ * @brief Read information about the driver handling a given device
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] *p A ::PCPS_DRVR_INFO structure to be filled up.
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_get_drvr_info( MBG_DEV_HANDLE dh, PCPS_DRVR_INFO *p )
{
#if defined( _MBGIOCTL_H )
@@ -1311,13 +3848,13 @@ _MBG_API_ATTR int _MBG_API mbg_get_drvr_info( MBG_DEV_HANDLE dh, PCPS_DRVR_INFO
/*HDR*/
/**
- @brief Read detailed device information.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_DEV structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function
- */
+ * @brief Read detailed device information
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] *p A ::PCPS_DEV structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_get_device_info( MBG_DEV_HANDLE dh, PCPS_DEV *p )
{
#if defined( _MBGIOCTL_H )
@@ -1336,15 +3873,19 @@ _MBG_API_ATTR int _MBG_API mbg_get_device_info( MBG_DEV_HANDLE dh, PCPS_DEV *p )
/*HDR*/
/**
- @brief Read the current state of the on-board ::PCPS_STATUS_PORT.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_STATUS_PORT value to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function
-
- @see \ref group_status_port "bitmask"
- */
+ * @brief Read the current state of the on-board ::PCPS_STATUS_PORT
+ *
+ * This function is useful to read the device's status port which
+ * also includes the ::PCPS_ST_MOD bit reflecting the time code
+ * modulation of long wave receivers.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] *p A ::PCPS_STATUS_PORT value to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see @ref group_status_port "bitmask" //### TODO check syntax
+ */
_MBG_API_ATTR int _MBG_API mbg_get_status_port( MBG_DEV_HANDLE dh, PCPS_STATUS_PORT *p )
{
#if defined( _MBGIOCTL_H )
@@ -1364,31 +3905,31 @@ _MBG_API_ATTR int _MBG_API mbg_get_status_port( MBG_DEV_HANDLE dh, PCPS_STATUS_P
/*HDR*/
/* (Intentionally excluded from Doxygen)
- Generic read function which writes a command code to a device
- and reads a number of replied data to a generic buffer.
-
- <b>Warning</b>: This is for debugging purposes only!
- The specialized API calls should be used preferably.
- A specific device may not support any command code.
-
- @param dh Valid handle to a Meinberg device
- @param cmd Can be any \ref group_cmd_bytes "command byte" supported by the device
- @param *p Pointer to a buffer to be filled up
- @param size Size of the buffer *p
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_generic_write()
- @see mbg_generic_read_gps()
- @see mbg_generic_write_gps()
- @see mbg_generic_io()
- */
+ * Generic read function which writes a command code to a device
+ * and reads a number of replied data to a generic buffer.
+ *
+ * <b>Warning</b>: This is for debugging purposes only!
+ * The specialized API calls should be used preferably.
+ * Not all devices support each of the ::PC_GPS_COMMANDS.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] cmd Can be any @ref PCPS_CMD_CODES "command code" supported by the device
+ * @param[out] p Pointer to a buffer to be filled up
+ * @param[in] size Size of the output buffer
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_generic_write
+ * @see ::mbg_generic_read_gps
+ * @see ::mbg_generic_write_gps
+ * @see ::mbg_generic_io
+ */
_MBG_API_ATTR int _MBG_API mbg_generic_read( MBG_DEV_HANDLE dh, int cmd,
void *p, int size )
{
_mbgdevio_vars();
rc = _mbgdevio_gen_read( dh, cmd, p, size );
- // No type information available, so endianess must be
+ // No type information available, so endianess has to be
// converted by the caller, if required.
return _mbgdevio_ret_val;
@@ -1398,34 +3939,34 @@ _MBG_API_ATTR int _MBG_API mbg_generic_read( MBG_DEV_HANDLE dh, int cmd,
/*HDR*/
/* (Intentionally excluded from Doxygen)
- Generic read function which writes a GPS command code to a device
- and reads a number of replied data to a generic buffer.
- The macro _pcps_has_gps_data() or the API call mbg_dev_has_gps_data()
- check whether this call is supported by a device.
-
- <b>Warning</b>: This is for debugging purposes only!
- The specialized API calls should be used preferably.
- A specific device may not support any GPS command code.
-
- @param dh Valid handle to a Meinberg device
- @param cmd Can be any \ref group_cmd_bytes "command byte" supported by the device.
- @param *p Pointer to a buffer to be filled up
- @param size Size of the buffer *p
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_gps_data()
- @see mbg_generic_write_gps()
- @see mbg_generic_read()
- @see mbg_generic_write()
- @see mbg_generic_io()
- */
+ * Generic read function which writes a GPS command code to a device
+ * and reads a number of data bytes back into a generic buffer.
+ * The function ::mbg_chk_dev_has_gps_data can be used to check
+ * whether this call is supported by a device.
+ *
+ * <b>Warning</b>: This is for debugging purposes only!
+ * The specialized API calls should be used preferably.
+ * Not all devices support each of the ::PC_GPS_COMMANDS.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] cmd One of the ::PCPS_CMD_CODES supported by the device.
+ * @param[out] p Pointer to a buffer to be filled up
+ * @param[in] size Size of the buffer, has to match the expected data size associated with cmd
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_gps_data
+ * @see ::mbg_generic_write_gps
+ * @see ::mbg_generic_read
+ * @see ::mbg_generic_write
+ * @see ::mbg_generic_io
+ */
_MBG_API_ATTR int _MBG_API mbg_generic_read_gps( MBG_DEV_HANDLE dh, int cmd,
void *p, int size )
{
_mbgdevio_vars();
rc = _mbgdevio_gen_read_gps( dh, cmd, p, size );
- // No type information available, so endianess must be
+ // No type information available, so endianess has to be
// converted by the caller, if required.
return _mbgdevio_ret_val;
@@ -1435,30 +3976,30 @@ _MBG_API_ATTR int _MBG_API mbg_generic_read_gps( MBG_DEV_HANDLE dh, int cmd,
/*HDR*/
/* (Intentionally excluded from Doxygen)
- Generic write function which writes a command code plus an
- associated number of data bytes to a device.
-
- <b>Warning</b>: This is for debugging purposes only!
- The specialized API calls should be used preferably.
- A specific device may not support any command code.
-
- @param dh Valid handle to a Meinberg device
- @param cmd Can be any \ref group_cmd_bytes "command byte" supported by the device.
- @param *p Pointer to a buffer to be written
- @param size Size of the buffer *p
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_generic_read()
- @see mbg_generic_read_gps()
- @see mbg_generic_write_gps()
- @see mbg_generic_io()
- */
+ * Generic write function which writes a command code plus an
+ * associated number of data bytes to a device.
+ *
+ * <b>Warning</b>: This is for debugging purposes only!
+ * The specialized API calls should be used preferably.
+ * Not all devices support each of the ::PC_GPS_COMMANDS.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] cmd One of the ::PCPS_CMD_CODES supported by the device.
+ * @param[in] p Pointer to a buffer of data to be written
+ * @param[in] size Size of the buffer, has to match the expected data size associated with cmd
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_generic_read
+ * @see ::mbg_generic_read_gps
+ * @see ::mbg_generic_write_gps
+ * @see ::mbg_generic_io
+ */
_MBG_API_ATTR int _MBG_API mbg_generic_write( MBG_DEV_HANDLE dh, int cmd,
const void *p, int size )
{
_mbgdevio_vars();
- // No type information available, so endianess must be
+ // No type information available, so endianess has to be
// converted by the caller, if required.
rc = _mbgdevio_gen_write( dh, cmd, p, size );
return _mbgdevio_ret_val;
@@ -1469,33 +4010,33 @@ _MBG_API_ATTR int _MBG_API mbg_generic_write( MBG_DEV_HANDLE dh, int cmd,
/*HDR*/
/* (Intentionally excluded from Doxygen)
- Generic write function which writes a GPS command code plus an
- associated number of data bytes to a device.
- The macro _pcps_has_gps_data() or the API call mbg_dev_has_gps_data()
- check whether this call is supported by a device.
-
- <b>Warning</b>: This is for debugging purposes only!
- The specialized API calls should be used preferably.
- A specific device may not support any GPS command code.
-
- @param dh Valid handle to a Meinberg device
- @param cmd Can be any \ref group_cmd_bytes "command byte" supported by the device.
- @param *p Pointer to a buffer to be written
- @param size Size of the buffer *p
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_gps_data()
- @see mbg_generic_read_gps()
- @see mbg_generic_read()
- @see mbg_generic_write()
- @see mbg_generic_io()
- */
+ * Generic write function which writes a GPS command code plus an
+ * associated number of data bytes to a device.
+ * The function ::mbg_chk_dev_has_gps_data can be used to check
+ * whether this call is supported by a device.
+ *
+ * <b>Warning</b>: This is for debugging purposes only!
+ * The specialized API calls should be used preferably.
+ * Not all devices support each of the ::PC_GPS_COMMANDS.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] cmd One of the ::PCPS_CMD_CODES supported by the device.
+ * @param[in] p Pointer to a buffer of data to be written
+ * @param[in] size Size of the buffer, has to match the expected data size associated with cmd
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_gps_data
+ * @see ::mbg_generic_read_gps
+ * @see ::mbg_generic_read
+ * @see ::mbg_generic_write
+ * @see ::mbg_generic_io
+ */
_MBG_API_ATTR int _MBG_API mbg_generic_write_gps( MBG_DEV_HANDLE dh, int cmd,
const void *p, int size )
{
_mbgdevio_vars();
- // No type information available, so endianess must be
+ // No type information available, so endianess has to be
// converted by the caller, if required.
rc = _mbgdevio_gen_write_gps( dh, cmd, p, size );
return _mbgdevio_ret_val;
@@ -1506,20 +4047,20 @@ _MBG_API_ATTR int _MBG_API mbg_generic_write_gps( MBG_DEV_HANDLE dh, int cmd,
/*HDR*/
/* (Intentionally excluded from Doxygen)
- Write and/or read generic data to/from a device.
- The macro _pcps_has_generic_io() or the API call mbg_dev_has_generic_io()
- check whether this call is supported by a device.
-
- <b>Warning</b>: This call is for debugging purposes and internal use only!
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_generic_io()
- @see mbg_generic_read()
- @see mbg_generic_write()
- @see mbg_generic_read_gps()
- @see mbg_generic_write_gps()
- */
+ * Write and/or read generic data to/from a device.
+ * The function ::mbg_chk_dev_has_generic_io checks
+ * whether this call is supported by a device.
+ *
+ * <b>Warning</b>: This call is for debugging purposes and internal use only!
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_generic_io
+ * @see ::mbg_generic_read
+ * @see ::mbg_generic_write
+ * @see ::mbg_generic_read_gps
+ * @see ::mbg_generic_write_gps
+ */
_MBG_API_ATTR int _MBG_API mbg_generic_io( MBG_DEV_HANDLE dh, int type,
const void *in_p, int in_sz,
void *out_p, int out_sz )
@@ -1543,25 +4084,25 @@ _MBG_API_ATTR int _MBG_API mbg_generic_io( MBG_DEV_HANDLE dh, int type,
/*HDR*/
/**
- @brief Read a ::PCPS_TIME structure returning the current date/time/status.
-
- The returned time is local time according to the card's time zone setting,
- with a resolution of 10 ms (i.e. 10ths of seconds).
-
- This call is supported by any device manufactured by Meinberg.
- However, for higher accuracy and resolution the mbg_get_hr_time..() or
- mbg_get_fast_hr_timestamp..() group of calls should be used preferably
- if supported by the device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_TIME structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_hr_time()
- @see mbg_set_time()
- @see mbg_get_sync_time()
- */
+ * @brief Read a ::PCPS_TIME structure returning the current date/time/status.
+ *
+ * The returned time is local time according to the card's time zone setting,
+ * with a resolution of 10 ms (i.e. 10ths of seconds).
+ *
+ * This call is supported by any device manufactured by Meinberg.
+ * However, for higher accuracy and resolution the @ref pcps_hr_time_fncs or
+ * the @ref pcps_fast_timestamp_fncs group of calls should be used preferably,
+ * if supported by the device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_TIME structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_set_time
+ * @see ::mbg_get_sync_time
+ */
_MBG_API_ATTR int _MBG_API mbg_get_time( MBG_DEV_HANDLE dh, PCPS_TIME *p )
{
_mbgdevio_vars();
@@ -1575,18 +4116,20 @@ _MBG_API_ATTR int _MBG_API mbg_get_time( MBG_DEV_HANDLE dh, PCPS_TIME *p )
/*HDR*/
/**
- @brief Set the device's on-board clock to a given date and time.
-
- The macro _pcps_can_set_time() checks whether this call
- is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_STIME structure to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @brief Set the device's on-board clock to a given date and time.
+ *
+ * The macro ::_pcps_can_set_time checks whether this call
+ * is supported by a device.
+ *
+ * @todo Provide an API function replacing ::_pcps_can_set_time.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] p Pointer to a ::PCPS_STIME structure to be written
- @see mbg_get_time()
- */
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_time
+ */
_MBG_API_ATTR int _MBG_API mbg_set_time( MBG_DEV_HANDLE dh, const PCPS_STIME *p )
{
_mbgdevio_vars();
@@ -1601,29 +4144,29 @@ _MBG_API_ATTR int _MBG_API mbg_set_time( MBG_DEV_HANDLE dh, const PCPS_STIME *p
/*HDR*/
/**
- @brief Read the time when the device has last recently synchronized.
-
- Fills a ::PCPS_TIME structure with the date/time/status reporting
- when the device was synchronized the last time to its time source,
- e.g. the DCF77 signal, the GPS satellites, or similar.
- The macro _pcps_has_sync_time() or the API call mbg_dev_has_sync_time()
- check whether this call is supported by a device.
-
- The macro _pcps_has_sync_time() checks whether this call
- is supported by a device.
-
- <b>Note:</b> If that information is not available on the board then
- the value of the returned ::PCPS_TIME::sec field is set to 0xFF.
- The macro _pcps_time_is_read() can be used to check whether the
- returned information is valid, or not available.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_TIME structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_time()
- */
+ * @brief Read the time when the device has last recently synchronized.
+ *
+ * Fills a ::PCPS_TIME structure with the date/time/status reporting
+ * when the device was synchronized the last time to its time source,
+ * e.g. the DCF77 signal, the GPS satellites, or similar.
+ *
+ * The macro ::_pcps_has_sync_time checks whether this call
+ * is supported by a device.
+ *
+ * <b>Note:</b> If that information is not available on the board then
+ * the value of the returned ::PCPS_TIME::sec field is set to 0xFF.
+ * The macro ::_pcps_time_is_read can be used to check whether the
+ * returned information is valid, or "not set".
+ *
+ * @todo Provide an API function replacing ::_pcps_has_sync_time.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_TIME structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_time
+ */
_MBG_API_ATTR int _MBG_API mbg_get_sync_time( MBG_DEV_HANDLE dh, PCPS_TIME *p )
{
_mbgdevio_vars();
@@ -1638,21 +4181,22 @@ _MBG_API_ATTR int _MBG_API mbg_get_sync_time( MBG_DEV_HANDLE dh, PCPS_TIME *p )
/*HDR*/
/**
- @brief Wait until the next second change, then return current time.
-
- Returns time in a ::PCPS_TIME structure similar to mbg_get_time().
-
- <b>Note:</b> This API call is supported under Windows only.
- The call blocks until the kernel driver detects a second change
- reported by the device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_TIME structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_time()
- */
+ * @brief Wait until the next second change, then return current time.
+ *
+ * Returns time in a ::PCPS_TIME structure similar to ::mbg_get_time.
+ *
+ * <b>Note:</b> This API call is supported under Windows only.
+ * The call blocks until the kernel driver detects a second change
+ * reported by the device. The accuracy of this call is limited
+ * to a few milliseconds.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_TIME structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_time
+ */
_MBG_API_ATTR int _MBG_API mbg_get_time_sec_change( MBG_DEV_HANDLE dh, PCPS_TIME *p )
{
#if defined( MBG_TGT_WIN32 )
@@ -1664,7 +4208,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_time_sec_change( MBG_DEV_HANDLE dh, PCPS_TIME
#if defined( __BORLANDC__ )
dh; p; // avoid warnings "never used"
#endif
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_ON_OS );
+ return MBG_ERR_NOT_SUPP_ON_OS;
#endif
} // mbg_get_time_sec_change
@@ -1673,29 +4217,26 @@ _MBG_API_ATTR int _MBG_API mbg_get_time_sec_change( MBG_DEV_HANDLE dh, PCPS_TIME
/*HDR*/
/**
- @brief Read the card's current time with high resolution, plus status.
-
- Fills up a ::PCPS_HR_TIME (High Resolution time) structure containing
- the current %UTC time (seconds since 1970), %UTC offset, and status.
- The macro _pcps_has_hr_time() or the API call mbg_dev_has_hr_time()
- check whether this call is supported by a device.
-
- <b>Note:</b> This API call provides a higher accuracy and resolution
- than mbg_get_time(). However, it does not account for the latency
- which is introduced when accessing the board.
- The mbg_get_hr_time_cycles() and mbg_get_hr_time_comp() calls
- provide ways to account for and/or compensate the latency.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_HR_TIME structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_hr_time()
- @see mbg_get_time()
- @see mbg_get_hr_time_cycles()
- @see mbg_get_hr_time_comp()
- */
+ * @brief Read the card's current time with high resolution, plus status.
+ *
+ * Fills up a ::PCPS_HR_TIME (High Resolution time) structure containing
+ * the current %UTC time (seconds since 1970), %UTC offset, and status.
+ *
+ * The API call ::mbg_chk_dev_has_hr_time checks whether this call
+ * is supported by the device.
+ *
+ * For details see @ref ::pcps_hr_time_fncs
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_HR_TIME structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_hr_time_fncs
+ * @see @ref pcps_hr_time_fncs
+ * @see @ref pcps_fast_timestamp_fncs
+ * @see @ref pcps_std_time_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_hr_time( MBG_DEV_HANDLE dh, PCPS_HR_TIME *p )
{
_mbgdevio_vars();
@@ -1717,13 +4258,13 @@ _MBG_API_ATTR int _MBG_API mbg_get_hr_time( MBG_DEV_HANDLE dh, PCPS_HR_TIME *p )
<b>Note:</b> This is only supported by some special firmware.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TIME_STAMP structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_event_time()
- */
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_event_time
+ */
_MBG_API_ATTR int _MBG_API mbg_set_event_time( MBG_DEV_HANDLE dh, const PCPS_TIME_STAMP *p )
{
_mbgdevio_vars();
@@ -1742,24 +4283,22 @@ _MBG_API_ATTR int _MBG_API mbg_set_event_time( MBG_DEV_HANDLE dh, const PCPS_TIM
/*HDR*/
/**
- @brief Read the serial port configuration from an old type of device.
-
- <b>Note:</b> Direct usage of this function is obsolete.
-
- The generic API function mbg_get_serial_settings() should be used instead
- which fully supports the capabilities of current devices.
-
- The macro _pcps_has_serial() checks whether this call
- is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_SERIAL structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see \ref group_cmd_bytes
- @see mbg_get_serial_settings()
- */
+ * @brief Read the serial port configuration from an old type of device
+ *
+ * @deprecated Direct usage of this function is deprecated. The generic
+ * API function ::mbg_get_serial_settings should be used instead
+ * which fully supports the capabilities of current devices.
+ *
+ * The macro ::_pcps_has_serial checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] p Pointer to a ::PCPS_SERIAL structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_serial_settings
+ */
_MBG_API_ATTR int _MBG_API mbg_get_serial( MBG_DEV_HANDLE dh, PCPS_SERIAL *p )
{
_mbgdevio_vars();
@@ -1773,24 +4312,22 @@ _MBG_API_ATTR int _MBG_API mbg_get_serial( MBG_DEV_HANDLE dh, PCPS_SERIAL *p )
/*HDR*/
/**
- @brief Write the serial port configuration to an old type of device.
-
- <b>Note:</b> Direct usage of this function is obsolete.
-
- The generic API function mbg_save_serial_settings() should be used instead
- which fully supports the capabilities of current devices.
-
- The macro _pcps_has_serial() checks whether this call
- is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_SERIAL structure to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see \ref group_cmd_bytes
- @see mbg_save_serial_settings()
- */
+ * @brief Write the serial port configuration to an old type of device
+ *
+ * @deprecated Direct usage of this function is deprecated. The generic
+ * API function ::mbg_save_serial_settings should be used instead
+ * which fully supports the capabilities of current devices.
+ *
+ * The macro ::_pcps_has_serial checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[in] p Pointer to a ::PCPS_SERIAL structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_save_serial_settings
+ */
_MBG_API_ATTR int _MBG_API mbg_set_serial( MBG_DEV_HANDLE dh, const PCPS_SERIAL *p )
{
_mbgdevio_vars();
@@ -1804,7 +4341,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_serial( MBG_DEV_HANDLE dh, const PCPS_SERIAL
/*HDR*/
/**
- @brief Read time zone/daylight saving configuration code from a device.
+ * @brief Read time zone/daylight saving configuration code from a device.
The APIs using TZCODE are only supported by some simpler cards
and allow just a very basic configuration.
@@ -1816,17 +4353,16 @@ _MBG_API_ATTR int _MBG_API mbg_set_serial( MBG_DEV_HANDLE dh, const PCPS_SERIAL
calls instead which allow for a more detailed configuration of the
time zone and daylight saving settings.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TZCODE structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_tzcode()
- @see mbg_set_tzcode()
- @see mbg_get_pcps_tzdl()
- @see mbg_get_gps_tzdl()
- @see \ref group_cmd_bytes
- */
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_tzcode
+ * @see ::mbg_set_tzcode
+ * @see ::mbg_get_pcps_tzdl
+ * @see ::mbg_get_gps_tzdl
+ */
_MBG_API_ATTR int _MBG_API mbg_get_tzcode( MBG_DEV_HANDLE dh, PCPS_TZCODE *p )
{
_mbgdevio_vars();
@@ -1841,7 +4377,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_tzcode( MBG_DEV_HANDLE dh, PCPS_TZCODE *p )
/*HDR*/
/**
- @brief Write time zone/daylight saving configuration code to a device.
+ * @brief Write time zone/daylight saving configuration code to a device.
The APIs using TZCODE are only supported by some simpler cards
and allow just a very basic configuration.
@@ -1853,17 +4389,16 @@ _MBG_API_ATTR int _MBG_API mbg_get_tzcode( MBG_DEV_HANDLE dh, PCPS_TZCODE *p )
calls instead which allow for a more detailed configuration of the
time zone and daylight saving settings.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TZCODE structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_tzcode()
- @see mbg_get_tzcode()
- @see mbg_set_pcps_tzdl()
- @see mbg_set_gps_tzdl()
- @see \ref group_cmd_bytes
- */
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_tzcode
+ * @see ::mbg_get_tzcode
+ * @see ::mbg_set_pcps_tzdl
+ * @see ::mbg_set_gps_tzdl
+ */
_MBG_API_ATTR int _MBG_API mbg_set_tzcode( MBG_DEV_HANDLE dh, const PCPS_TZCODE *p )
{
_mbgdevio_vars();
@@ -1878,7 +4413,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_tzcode( MBG_DEV_HANDLE dh, const PCPS_TZCODE
/*HDR*/
/**
- @brief Read time zone/daylight saving parameters from a device.
+ * @brief Read time zone/daylight saving parameters from a device.
This function fills up a ::PCPS_TZDL structure which supports a more
detailed configuration of time zone and daylight saving than the TZCODE
@@ -1890,16 +4425,15 @@ _MBG_API_ATTR int _MBG_API mbg_set_tzcode( MBG_DEV_HANDLE dh, const PCPS_TZCODE
Other cards may support the mbg_get_tzcode() or mbg_get_gps_tzdl()
calls instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TZDL structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_pcps_tzdl()
- @see mbg_set_pcps_tzdl()
- @see mbg_get_tzcode()
- @see mbg_get_gps_tzdl()
- @see \ref group_cmd_bytes
+ * @see ::mbg_dev_has_pcps_tzdl
+ * @see ::mbg_set_pcps_tzdl
+ * @see ::mbg_get_tzcode
+ * @see ::mbg_get_gps_tzdl
*/
_MBG_API_ATTR int _MBG_API mbg_get_pcps_tzdl( MBG_DEV_HANDLE dh, PCPS_TZDL *p )
{
@@ -1915,7 +4449,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_pcps_tzdl( MBG_DEV_HANDLE dh, PCPS_TZDL *p )
/*HDR*/
/**
- @brief Write time zone/daylight saving parameters to a device.
+ * @brief Write time zone/daylight saving parameters to a device.
This function passes a ::PCPS_TZDL structure to a device which supports
a more detailed configuration of time zone and daylight saving than the
@@ -1926,16 +4460,15 @@ _MBG_API_ATTR int _MBG_API mbg_get_pcps_tzdl( MBG_DEV_HANDLE dh, PCPS_TZDL *p )
Other cards may support the mbg_set_tzcode() or mbg_set_gps_tzdl()
calls instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TZDL structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_pcps_tzdl()
- @see mbg_get_pcps_tzdl()
- @see mbg_set_tzcode()
- @see mbg_set_gps_tzdl()
- @see \ref group_cmd_bytes
+ * @see ::mbg_dev_has_pcps_tzdl
+ * @see ::mbg_get_pcps_tzdl
+ * @see ::mbg_set_tzcode
+ * @see ::mbg_set_gps_tzdl
*/
_MBG_API_ATTR int _MBG_API mbg_set_pcps_tzdl( MBG_DEV_HANDLE dh, const PCPS_TZDL *p )
{
@@ -1955,7 +4488,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_pcps_tzdl( MBG_DEV_HANDLE dh, const PCPS_TZDL
/*HDR*/
/**
- @brief Read the %UTC offset configuration of the reference time from a device.
+ * @brief Read the %UTC offset configuration of the reference time from a device.
This parameter is used to specify the %UTC offset of an incoming
reference time signal if a kind of time signal e.g. an IRIG input
@@ -1964,14 +4497,13 @@ _MBG_API_ATTR int _MBG_API mbg_set_pcps_tzdl( MBG_DEV_HANDLE dh, const PCPS_TZDL
The macro _pcps_has_ref_offs() or the API call mbg_dev_has_ref_offs()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_REF_OFFS value to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ref_offs()
- @see mbg_set_ref_offs()
- @see ::PCPS_GET_REF_OFFS
+ * @see ::mbg_dev_has_ref_offs
+ * @see ::mbg_set_ref_offs
*/
_MBG_API_ATTR int _MBG_API mbg_get_ref_offs( MBG_DEV_HANDLE dh, MBG_REF_OFFS *p )
{
@@ -1987,7 +4519,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_ref_offs( MBG_DEV_HANDLE dh, MBG_REF_OFFS *p
/*HDR*/
/**
- @brief Write the %UTC offset configuration of the reference time to a device.
+ * @brief Write the %UTC offset configuration of the reference time to a device.
This parameter is used to specify the %UTC offset of an incoming
reference time signal if a kind of time signal e.g. an IRIG input
@@ -1996,14 +4528,13 @@ _MBG_API_ATTR int _MBG_API mbg_get_ref_offs( MBG_DEV_HANDLE dh, MBG_REF_OFFS *p
The macro _pcps_has_ref_offs() or the API call mbg_dev_has_ref_offs()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_REF_OFFS value to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ref_offs()
- @see mbg_get_ref_offs()
- @see ::PCPS_SET_REF_OFFS
+ * @see ::mbg_dev_has_ref_offs
+ * @see ::mbg_get_ref_offs
*/
_MBG_API_ATTR int _MBG_API mbg_set_ref_offs( MBG_DEV_HANDLE dh, const MBG_REF_OFFS *p )
{
@@ -2023,20 +4554,20 @@ _MBG_API_ATTR int _MBG_API mbg_set_ref_offs( MBG_DEV_HANDLE dh, const MBG_REF_OF
/*HDR*/
/**
- @brief Read a ::MBG_OPT_INFO structure containing optional settings, controlled by flags.
+ * @brief Read a ::MBG_OPT_INFO structure containing optional settings, controlled by flags.
The ::MBG_OPT_INFO structure contains a mask of supported flags plus the current
settings of those flags.
The macro _pcps_has_opt_flags() or the API call mbg_dev_has_opt_flags()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_OPT_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_opt_flags()
- @see mbg_set_opt_settings()
+ * @see ::mbg_dev_has_opt_flags
+ * @see ::mbg_set_opt_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_opt_info( MBG_DEV_HANDLE dh, MBG_OPT_INFO *p )
{
@@ -2052,20 +4583,20 @@ _MBG_API_ATTR int _MBG_API mbg_get_opt_info( MBG_DEV_HANDLE dh, MBG_OPT_INFO *p
/*HDR*/
/**
- @brief Write a ::MBG_OPT_SETTINGS structure containing optional device settings.
+ * @brief Write a ::MBG_OPT_SETTINGS structure containing optional device settings.
The macro _pcps_has_opt_flags() or the API call mbg_dev_has_opt_flags()
check whether this call is supported by a device.
The ::MBG_OPT_INFO structure should be read first to check which of the specified
flag is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_OPT_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_opt_flags()
- @see mbg_get_opt_info()
+ * @see ::mbg_dev_has_opt_flags
+ * @see ::mbg_get_opt_info
*/
_MBG_API_ATTR int _MBG_API mbg_set_opt_settings( MBG_DEV_HANDLE dh, const MBG_OPT_SETTINGS *p )
{
@@ -2086,27 +4617,27 @@ _MBG_API_ATTR int _MBG_API mbg_set_opt_settings( MBG_DEV_HANDLE dh, const MBG_OP
/*HDR*/
/**
- @brief Read the current IRIG input settings plus the supported settings.
-
- Calling this function directly is usually obsolete. The function
- mbg_get_all_irig_rx_info() should be used instead which also reads some
- other associated parameters affecting the behaviour of the IRIG input.
-
- The macro _pcps_is_irig_rx() or the API call mbg_dev_is_irig_rx()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an ::IRIG_INFO structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_all_irig_rx_info()
- @see mbg_set_irig_rx_settings()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
- */
+ * @brief Read the current IRIG input settings plus capabilities
+ *
+ * @deprecated Calling this function directly is deprecated. The function
+ * ::mbg_get_all_irig_rx_info should be used instead which also reads some
+ * other associated parameters affecting the behaviour of the IRIG input.
+ *
+ * The API call ::mbg_dev_is_irig_rx checks whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] *p An ::IRIG_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_all_irig_rx_info
+ * @see ::mbg_set_irig_rx_settings
+ * @see ::mbg_dev_is_irig_rx
+ * @see ::mbg_dev_has_irig_tx
+ * @see ::mbg_dev_has_irig
+ * @see @ref group_icode
+ */
_MBG_API_ATTR int _MBG_API mbg_get_irig_rx_info( MBG_DEV_HANDLE dh, IRIG_INFO *p )
{
_mbgdevio_vars();
@@ -2121,29 +4652,28 @@ _MBG_API_ATTR int _MBG_API mbg_get_irig_rx_info( MBG_DEV_HANDLE dh, IRIG_INFO *p
/*HDR*/
/**
- @brief Write an ::IRIG_SETTINGS structure to a device to configure an IRIG input.
-
- Calling this function directly is usually obsolete. The function
- mbg_set_all_irig_rx_info() should be used instead which also writes some
- other associated parameters affecting the behaviour of the IRIG input.
-
- The macro _pcps_is_irig_rx() or the API call mbg_dev_is_irig_rx()
- check whether this call is supported by a device.
- The ::IRIG_INFO structure should be read first to determine the possible
- settings supported by this card's IRIG input.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::IRIG_SETTINGS structure to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_set_all_irig_rx_info()
- @see mbg_get_irig_rx_info()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
- */
+ * @brief Write an ::IRIG_SETTINGS structure to a device to configure an IRIG input.
+ *
+ * @deprecated Calling this function directly is deprecated. The function
+ * ::mbg_save_all_irig_rx_settings should be used instead which also writes some
+ * other associated parameters affecting the behaviour of the IRIG input.
+ *
+ * The API call ::mbg_dev_is_irig_rx checks whether this call is supported
+ * by a device. The ::IRIG_INFO structure should be read first to determine
+ * the possible settings supported by the device's IRIG input.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] p Pointer to a ::IRIG_SETTINGS structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_save_all_irig_rx_settings
+ * @see ::mbg_get_irig_rx_info
+ * @see ::mbg_dev_is_irig_rx
+ * @see ::mbg_dev_has_irig_tx
+ * @see ::mbg_dev_has_irig
+ * @see @ref group_icode
+ */
_MBG_API_ATTR int _MBG_API mbg_set_irig_rx_settings( MBG_DEV_HANDLE dh, const IRIG_SETTINGS *p )
{
_mbgdevio_vars();
@@ -2163,20 +4693,20 @@ _MBG_API_ATTR int _MBG_API mbg_set_irig_rx_settings( MBG_DEV_HANDLE dh, const IR
/*HDR*/
/**
- @brief Read all IRIG input configuration information from a device.
+ * @brief Read all IRIG input configuration information from a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pdev Pointer to the device's ::PCPS_DEV structure
@param p_irig_info Pointer to a ::IRIG_SETTINGS structure to be written
@param p_ref_offs Pointer to a ::MBG_REF_OFFS structure to be written
@param p_opt_info Pointer to a ::MBG_OPT_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_save_all_irig_rx_settings()
- @see mbg_set_irig_rx_settings()
- @see mbg_set_ref_offs()
- @see mbg_set_opt_settings()
+ * @see ::mbg_save_all_irig_rx_settings
+ * @see ::mbg_set_irig_rx_settings
+ * @see ::mbg_set_ref_offs
+ * @see ::mbg_set_opt_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_all_irig_rx_info( MBG_DEV_HANDLE dh,
const PCPS_DEV *pdev,
@@ -2187,14 +4717,14 @@ _MBG_API_ATTR int _MBG_API mbg_get_all_irig_rx_info( MBG_DEV_HANDLE dh,
int rc;
if ( !_pcps_is_irig_rx( pdev ) )
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV );
+ return MBG_ERR_NOT_SUPP_BY_DEV;
rc = mbg_get_irig_rx_info( dh, p_irig_info );
- if ( rc == MBG_SUCCESS && _pcps_has_ref_offs( pdev ) )
+ if ( mbg_rc_is_success( rc ) && _pcps_has_ref_offs( pdev ) )
rc = mbg_get_ref_offs( dh, p_ref_offs );
- if ( rc == MBG_SUCCESS && _pcps_has_opt_flags( pdev ) )
+ if ( mbg_rc_is_success( rc ) && _pcps_has_opt_flags( pdev ) )
rc = mbg_get_opt_info( dh, p_opt_info );
return rc;
@@ -2205,25 +4735,25 @@ _MBG_API_ATTR int _MBG_API mbg_get_all_irig_rx_info( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Write all IRIG input configuration settings to a device.
+ * @brief Write all IRIG input configuration settings to a device.
The macro _pcps_is_irig_rx() or the API call mbg_dev_is_irig_rx()
check whether this call is supported by a device.
The ::IRIG_INFO structure should be read first to determine the possible
settings supported by this card's IRIG input.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pdev Pointer to the device's ::PCPS_DEV structure
@param p_irig_settings Pointer to a ::IRIG_SETTINGS structure to be written
@param p_ref_offs Pointer to a ::MBG_REF_OFFS structure to be written
@param p_opt_settings Pointer to a ::MBG_OPT_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_all_irig_rx_info()
- @see mbg_set_irig_rx_settings()
- @see mbg_set_ref_offs()
- @see mbg_set_opt_settings()
+ * @see ::mbg_get_all_irig_rx_info
+ * @see ::mbg_set_irig_rx_settings
+ * @see ::mbg_set_ref_offs
+ * @see ::mbg_set_opt_settings
*/
_MBG_API_ATTR int _MBG_API mbg_save_all_irig_rx_settings( MBG_DEV_HANDLE dh,
const PCPS_DEV *pdev,
@@ -2234,14 +4764,14 @@ _MBG_API_ATTR int _MBG_API mbg_save_all_irig_rx_settings( MBG_DEV_HANDLE dh,
int rc;
if ( !_pcps_is_irig_rx( pdev ) )
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV );
+ return MBG_ERR_NOT_SUPP_BY_DEV;
rc = mbg_set_irig_rx_settings( dh, p_irig_settings );
- if ( rc == MBG_SUCCESS && _pcps_has_ref_offs( pdev ) )
+ if ( mbg_rc_is_success( rc ) && _pcps_has_ref_offs( pdev ) )
rc = mbg_set_ref_offs( dh, p_ref_offs );
- if ( rc == MBG_SUCCESS && _pcps_has_opt_flags( pdev ) )
+ if ( mbg_rc_is_success( rc ) && _pcps_has_opt_flags( pdev ) )
rc = mbg_set_opt_settings( dh, p_opt_settings );
return rc;
@@ -2252,26 +4782,7 @@ _MBG_API_ATTR int _MBG_API mbg_save_all_irig_rx_settings( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Check if a device supports the mbg_get_irig_ctrl_bits() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_irig_ctrl_bits()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_irig_ctrl_bits( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_irig_ctrl_bits, IOCTL_DEV_HAS_IRIG_CTRL_BITS, p );
-
-} // mbg_dev_has_irig_ctrl_bits
-
-
-
-/*HDR*/
-/**
- @brief Read the control function bits received from an incoming IRIG signal.
+ * @brief Read the control function bits received from an incoming IRIG signal.
This function fills a ::MBG_IRIG_CTRL_BITS structure with the control function
bits decoded from the incoming IRIG signal.
@@ -2293,13 +4804,13 @@ _MBG_API_ATTR int _MBG_API mbg_dev_has_irig_ctrl_bits( MBG_DEV_HANDLE dh, int *p
The macro _pcps_has_irig_ctrl_bits() or the API call mbg_dev_has_irig_ctrl_bits()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_IRIG_CTRL_BITS type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_irig_ctrl_bits()
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_irig_ctrl_bits
+ */
_MBG_API_ATTR int _MBG_API mbg_get_irig_ctrl_bits( MBG_DEV_HANDLE dh,
MBG_IRIG_CTRL_BITS *p )
{
@@ -2314,27 +4825,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_irig_ctrl_bits( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Check if a device supports the mbg_get_raw_irig_data() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_raw_irig_data()
- @see mbg_get_raw_irig_data_on_sec_change()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_raw_irig_data( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_raw_irig_data, IOCTL_DEV_HAS_RAW_IRIG_DATA, p );
-
-} // mbg_dev_has_raw_irig_data
-
-
-
-/*HDR*/
-/**
- @brief Read raw IRIG data from an IRIG receiver.
+ * @brief Read raw IRIG data from an IRIG receiver.
This function fills a ::MBG_RAW_IRIG_DATA structure with the raw data bits received
from the incoming IRIG signal. This enables an application itself to decode the
@@ -2343,14 +4834,14 @@ _MBG_API_ATTR int _MBG_API mbg_dev_has_raw_irig_data( MBG_DEV_HANDLE dh, int *p
The macro _pcps_has_raw_irig_data() or the API call mbg_dev_has_raw_irig_data()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_RAW_IRIG_DATA type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_raw_irig_data()
- @see mbg_get_raw_irig_data_on_sec_change()
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_raw_irig_data
+ * @see ::mbg_get_raw_irig_data_on_sec_change
+ */
_MBG_API_ATTR int _MBG_API mbg_get_raw_irig_data( MBG_DEV_HANDLE dh,
MBG_RAW_IRIG_DATA *p )
{
@@ -2365,7 +4856,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_raw_irig_data( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Wait for second changeover then read raw IRIG data from an IRIG receiver.
+ * @brief Wait for second changeover then read raw IRIG data from an IRIG receiver.
This function waits until the second of the device's on-board time rolls over, and
then reads the last recent raw IRIG data from the device.
@@ -2376,14 +4867,14 @@ _MBG_API_ATTR int _MBG_API mbg_get_raw_irig_data( MBG_DEV_HANDLE dh,
<b>Note:</b> The mbg_get_time_sec_change() function called by this function is
supported under Windows only, so this function can also only be used under Windows.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_RAW_IRIG_DATA type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_raw_irig_data()
- @see mbg_get_raw_irig_data()
- @see mbg_get_time_sec_change()
+ * @see ::mbg_dev_has_raw_irig_data
+ * @see ::mbg_get_raw_irig_data
+ * @see ::mbg_get_time_sec_change
*/
_MBG_API_ATTR int _MBG_API mbg_get_raw_irig_data_on_sec_change( MBG_DEV_HANDLE dh,
MBG_RAW_IRIG_DATA *p )
@@ -2393,7 +4884,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_raw_irig_data_on_sec_change( MBG_DEV_HANDLE d
rc = mbg_get_time_sec_change( dh, &t );
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
rc = mbg_get_raw_irig_data( dh, p );
return _mbgdevio_ret_val;
@@ -2404,26 +4895,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_raw_irig_data_on_sec_change( MBG_DEV_HANDLE d
/*HDR*/
/**
- @brief Check if a device supports the mbg_get_irig_time() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_irig_time()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_irig_time( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_irig_time, IOCTL_DEV_HAS_IRIG_TIME, p );
-
-} // mbg_dev_has_irig_time
-
-
-
-/*HDR*/
-/**
- @brief Read the IRIG time and day-of-year number from an IRIG receiver.
+ * @brief Read the IRIG time and day-of-year number from an IRIG receiver.
Fills up a ::PCPS_IRIG_TIME structure with the raw IRIG day-of-year number
and time decoded from the latest IRIG input frame. If the configured IRIG code
@@ -2433,12 +4905,12 @@ _MBG_API_ATTR int _MBG_API mbg_dev_has_irig_time( MBG_DEV_HANDLE dh, int *p )
The macro _pcps_has_irig_time() or the API call mbg_dev_has_irig_time()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_IRIG_TIME type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_irig_time()
+ * @see ::mbg_dev_has_irig_time
*/
_MBG_API_ATTR int _MBG_API mbg_get_irig_time( MBG_DEV_HANDLE dh,
PCPS_IRIG_TIME *p )
@@ -2454,18 +4926,18 @@ _MBG_API_ATTR int _MBG_API mbg_get_irig_time( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Clear a device's on-board time capture FIFO buffer.
+ * @brief Clear a device's on-board time capture FIFO buffer.
The macro _pcps_can_clr_ucap_buff() or the API call mbg_dev_can_clr_ucap_buff()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_can_clr_ucap_buff()
- @see mbg_get_ucap_entries()
- @see mbg_get_ucap_event()
+ * @see ::mbg_dev_can_clr_ucap_buff
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_get_ucap_event
*/
_MBG_API_ATTR int _MBG_API mbg_clr_ucap_buff( MBG_DEV_HANDLE dh )
{
@@ -2480,7 +4952,7 @@ _MBG_API_ATTR int _MBG_API mbg_clr_ucap_buff( MBG_DEV_HANDLE dh )
/*HDR*/
/**
- @brief Read information on a device's event capture buffer.
+ * @brief Read information on a device's event capture buffer.
Fills a ::PCPS_UCAP_ENTRIES structure with the number of user capture
events actually stored in the FIFO buffer, and the maximum number of
@@ -2489,14 +4961,14 @@ _MBG_API_ATTR int _MBG_API mbg_clr_ucap_buff( MBG_DEV_HANDLE dh )
The macro _pcps_has_ucap() or the API call mbg_dev_has_ucap()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_UCAP_ENTRIES structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ucap()
- @see mbg_get_ucap_entries()
- @see mbg_get_ucap_event()
+ * @see ::mbg_dev_has_ucap
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_get_ucap_event
*/
_MBG_API_ATTR int _MBG_API mbg_get_ucap_entries( MBG_DEV_HANDLE dh, PCPS_UCAP_ENTRIES *p )
{
@@ -2513,7 +4985,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_ucap_entries( MBG_DEV_HANDLE dh, PCPS_UCAP_EN
/*HDR*/
/**
- @brief Retrieve a single time capture event from the on-board FIFO buffer.
+ * @brief Retrieve a single time capture event from the on-board FIFO buffer.
The capture event is returned in a ::PCPS_HR_TIME structure. The oldest entry
in the FIFO is retrieved and then removed from the FIFO.
@@ -2528,14 +5000,14 @@ _MBG_API_ATTR int _MBG_API mbg_get_ucap_entries( MBG_DEV_HANDLE dh, PCPS_UCAP_EN
call which is obsolete but still supported for compatibility with
older cards.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_HR_TIME structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ucap()
- @see mbg_get_ucap_entries()
- @see mbg_clr_ucap_buff()
+ * @see ::mbg_dev_has_ucap
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_clr_ucap_buff
*/
_MBG_API_ATTR int _MBG_API mbg_get_ucap_event( MBG_DEV_HANDLE dh, PCPS_HR_TIME *p )
{
@@ -2552,7 +5024,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_ucap_event( MBG_DEV_HANDLE dh, PCPS_HR_TIME *
/*HDR*/
/**
- @brief Read the card's time zone/daylight saving parameters.
+ * @brief Read the card's time zone/daylight saving parameters.
This function returns the time zone/daylight saving parameters
in a ::TZDL structure.
@@ -2564,16 +5036,16 @@ _MBG_API_ATTR int _MBG_API mbg_get_ucap_event( MBG_DEV_HANDLE dh, PCPS_HR_TIME *
supported by non-GPS cards. Other cards may support the mbg_get_tzcode()
or mbg_get_pcps_tzdl() calls instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TZDL structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_tzdl()
- @see mbg_set_gps_tzdl()
- @see mbg_get_tzcode()
- @see mbg_get_pcps_tzdl()
- @see \ref group_tzdl
+ * @see ::mbg_dev_has_tzdl
+ * @see ::mbg_set_gps_tzdl
+ * @see ::mbg_get_tzcode
+ * @see ::mbg_get_pcps_tzdl
+ * @see @ref group_tzdl
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_tzdl( MBG_DEV_HANDLE dh, TZDL *p )
{
@@ -2588,7 +5060,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_tzdl( MBG_DEV_HANDLE dh, TZDL *p )
/*HDR*/
/**
- @brief Write the card's time zone/daylight saving parameters.
+ * @brief Write the card's time zone/daylight saving parameters.
This function writes the time zone/daylight saving parameters
in a ::TZDL structure to a device.
@@ -2600,16 +5072,16 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_tzdl( MBG_DEV_HANDLE dh, TZDL *p )
supported by non-GPS cards. Other cards may support the mbg_set_tzcode()
or mbg_set_pcps_tzdl() calls instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TZDL structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_tzdl()
- @see mbg_get_gps_tzdl()
- @see mbg_set_tzcode()
- @see mbg_set_pcps_tzdl()
- @see \ref group_tzdl
+ * @see ::mbg_dev_has_tzdl
+ * @see ::mbg_get_gps_tzdl
+ * @see ::mbg_set_tzcode
+ * @see ::mbg_set_pcps_tzdl
+ * @see @ref group_tzdl
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_tzdl( MBG_DEV_HANDLE dh, const TZDL *p )
{
@@ -2628,7 +5100,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_tzdl( MBG_DEV_HANDLE dh, const TZDL *p )
/*HDR*/
/**
- @brief Retrieve the software revision of a GPS receiver.
+ * @brief Retrieve the software revision of a GPS receiver.
This call is obsolete but still supported for compatibility
with older GPS cards.
@@ -2639,13 +5111,13 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_tzdl( MBG_DEV_HANDLE dh, const TZDL *p )
<b>Note:</b> The function mbg_get_gps_receiver_info() should
be used instead, if supported by the card.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::SW_REV structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_is_gps()
- @see mbg_get_gps_receiver_info()
+ * @see ::mbg_dev_is_gps
+ * @see ::mbg_get_gps_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_sw_rev( MBG_DEV_HANDLE dh, SW_REV *p )
{
@@ -2660,7 +5132,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_sw_rev( MBG_DEV_HANDLE dh, SW_REV *p )
/*HDR*/
/**
- @brief Retrieve the status of the battery buffered GPS variables.
+ * @brief Retrieve the status of the battery buffered GPS variables.
These GPS variables hold some parameters sent by the GPS satellites
which are required for proper operation. If the saved set of parameters
@@ -2670,11 +5142,11 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_sw_rev( MBG_DEV_HANDLE dh, SW_REV *p )
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::BVAR_STAT structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_bvar_stat( MBG_DEV_HANDLE dh, BVAR_STAT *p )
{
_mbgdevio_vars();
@@ -2688,7 +5160,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_bvar_stat( MBG_DEV_HANDLE dh, BVAR_STAT *
/*HDR*/
/**
- @brief Read the current board time using a ::TTM structure.
+ * @brief Read the current board time using a ::TTM structure.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -2696,13 +5168,13 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_bvar_stat( MBG_DEV_HANDLE dh, BVAR_STAT *
<b>Note:</b> This API call is pretty slow, so the mbg_get_hr_time_..()
or mbg_get_fast_hr_timestamp...() group of calls should be used preferably.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TTM structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_hr_time()
- @see mbg_get_fast_hr_timestamp()
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_fast_hr_timestamp
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_time( MBG_DEV_HANDLE dh, TTM *p )
{
@@ -2717,7 +5189,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_time( MBG_DEV_HANDLE dh, TTM *p )
/*HDR*/
/**
- @brief Set the time on a GPS receiver device.
+ * @brief Set the time on a GPS receiver device.
Write a ::TTM structure to a GPS receiver in order to set the
on-board date and time.
@@ -2725,11 +5197,11 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_time( MBG_DEV_HANDLE dh, TTM *p )
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TTM structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_set_gps_time( MBG_DEV_HANDLE dh, const TTM *p )
{
_mbgdevio_vars();
@@ -2747,7 +5219,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_time( MBG_DEV_HANDLE dh, const TTM *p )
/*HDR*/
/**
- @brief Read a ::PORT_PARM structure with a device's serial port configuration.
+ * @brief Read a ::PORT_PARM structure with a device's serial port configuration.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -2757,13 +5229,13 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_time( MBG_DEV_HANDLE dh, const TTM *p )
up to 2 ports. The generic function mbg_get_serial_settings()
should be used instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PORT_PARM structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_serial_settings()
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_serial_settings
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_port_parm( MBG_DEV_HANDLE dh, PORT_PARM *p )
{
_mbgdevio_vars();
@@ -2777,7 +5249,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_port_parm( MBG_DEV_HANDLE dh, PORT_PARM *
/*HDR*/
/**
- @brief Write a ::PORT_PARM structure to configure the on-board serial ports.
+ * @brief Write a ::PORT_PARM structure to configure the on-board serial ports.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -2787,13 +5259,13 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_port_parm( MBG_DEV_HANDLE dh, PORT_PARM *
up to 2 ports. The generic function mbg_save_serial_settings()
should be used instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PORT_PARM structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_save_serial_settings()
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_save_serial_settings
+ */
_MBG_API_ATTR int _MBG_API mbg_set_gps_port_parm( MBG_DEV_HANDLE dh, const PORT_PARM *p )
{
_mbgdevio_vars();
@@ -2811,7 +5283,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_port_parm( MBG_DEV_HANDLE dh, const PORT_
/*HDR*/
/**
- @brief Read an ::ANT_INFO structure to retrieve an extended GPS antenna status.
+ * @brief Read an ::ANT_INFO structure to retrieve an extended GPS antenna status.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -2822,11 +5294,11 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_port_parm( MBG_DEV_HANDLE dh, const PORT_
the antenna has been reconnected <b>and</b> the receiver has synchronized
to the GPS satellites again.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ANT_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_ant_info( MBG_DEV_HANDLE dh, ANT_INFO *p )
{
_mbgdevio_vars();
@@ -2840,7 +5312,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_ant_info( MBG_DEV_HANDLE dh, ANT_INFO *p
/*HDR*/
/**
- @brief Read a time capture event from the on-board FIFO buffer using a ::TTM structure.
+ * @brief Read a time capture event from the on-board FIFO buffer using a ::TTM structure.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -2850,14 +5322,14 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_ant_info( MBG_DEV_HANDLE dh, ANT_INFO *p
by the device. Anyway, this call is still supported for compatibility
with older devices.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TTM structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_ucap_entries()
- @see mbg_get_ucap_event()
- @see mbg_clr_ucap_buff()
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_get_ucap_event
+ * @see ::mbg_clr_ucap_buff
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_ucap( MBG_DEV_HANDLE dh, TTM *p )
{
@@ -2872,25 +5344,25 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_ucap( MBG_DEV_HANDLE dh, TTM *p )
/*HDR*/
/**
- @brief Read the ::ENABLE_FLAGS structure controlling when outputs are to be enabled.
+ * @brief Read the ::ENABLE_FLAGS structure controlling when outputs are to be enabled.
The ::ENABLE_FLAGS structure controls whether certain outputs
shall be enabled immediately after the card's power-up, or only
after the card has synchronized to its input signal.
- The macro _pcps_has_gps_data() or the API call mbg_dev_has_gps_data()
- check whether this call is supported by a device.
+ * The function ::mbg_chk_dev_has_gps_data can be used to check
+ * whether this call is supported by a device.
<b>Note:</b> Not all of the input signals specified for the
::ENABLE_FLAGS structure can be modified individually.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::ENABLE_FLAGS structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see ::ENABLE_FLAGS
- @see mbg_set_gps_enable_flags()
+ * @see ::ENABLE_FLAGS
+ * @see ::mbg_set_gps_enable_flags
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_enable_flags( MBG_DEV_HANDLE dh, ENABLE_FLAGS *p )
{
@@ -2906,25 +5378,25 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_enable_flags( MBG_DEV_HANDLE dh, ENABLE_F
/*HDR*/
/**
- @brief Write an ENABLE_FLAGS structure to configure when outputs shall be enabled.
+ * @brief Write an ENABLE_FLAGS structure to configure when outputs shall be enabled.
The ::ENABLE_FLAGS structure controls whether certain outputs
shall be enabled immediately after the card's power-up, or only
after the card has synchronized to its input signal.
- The macro _pcps_has_gps_data() or the API call mbg_dev_has_gps_data()
- check whether this call is supported by a device.
+ * The function ::mbg_chk_dev_has_gps_data can be used to check
+ * whether this call is supported by a device.
<b>Note:</b> Not all of the input signals specified for the
ENABLE_FLAGS structure can be modified individually.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ENABLE_FLAGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see ENABLE_FLAGS
- @see mbg_get_gps_enable_flags()
+ * @see ::ENABLE_FLAGS
+ * @see ::mbg_get_gps_enable_flags
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_enable_flags( MBG_DEV_HANDLE dh,
const ENABLE_FLAGS *p )
@@ -2945,21 +5417,21 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_enable_flags( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Read the extended GPS receiver status from a device.
-
- The ::STAT_INFO structure reports the status of the GPS receiver,
- including mode of operation and number of visible/usable satellites.
-
- The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::STAT_INFO structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see ::STAT_INFO
-*/
+ * @brief Read the extended GPS receiver status from a device.
+ *
+ * The ::STAT_INFO structure reports the status of the GPS receiver,
+ * including mode of operation and number of visible/usable satellites.
+ *
+ * The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::STAT_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::STAT_INFO
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_stat_info( MBG_DEV_HANDLE dh, STAT_INFO *p )
{
_mbgdevio_vars();
@@ -2973,17 +5445,17 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_stat_info( MBG_DEV_HANDLE dh, STAT_INFO *
/*HDR*/
/**
- @brief Send a ::GPS_CMD to a GPS receiver device.
+ * @brief Send a ::GPS_CMD to a GPS receiver device.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::GPS_CMD
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see ::PC_GPS_CMD_BOOT, ::PC_GPS_CMD_INIT_SYS, ::PC_GPS_CMD_INIT_USER, ::PC_GPS_CMD_INIT_DAC
+ * @see ::PC_GPS_CMD_BOOT, ::PC_GPS_CMD_INIT_SYS, ::PC_GPS_CMD_INIT_USER, ::PC_GPS_CMD_INIT_DAC
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_cmd( MBG_DEV_HANDLE dh, const GPS_CMD *p )
{
@@ -3001,7 +5473,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_cmd( MBG_DEV_HANDLE dh, const GPS_CMD *p
/*HDR*/
/**
- @brief Read the current geographic position from a GPS device.
+ * @brief Read the current geographic position from a GPS device.
The returned ::POS structure contains the current position in
ECEF (Earth Centered, Earth Fixed) kartesian coordinates, and in
@@ -3011,13 +5483,13 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_cmd( MBG_DEV_HANDLE dh, const GPS_CMD *p
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::POS structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_gps_pos_xyz()
- @see mbg_set_gps_pos_lla()
+ * @see ::mbg_set_gps_pos_xyz
+ * @see ::mbg_set_gps_pos_lla
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_pos( MBG_DEV_HANDLE dh, POS *p )
{
@@ -3033,7 +5505,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_pos( MBG_DEV_HANDLE dh, POS *p )
/*HDR*/
/**
- @brief Set the GPS receiver position using ::XYZ coordinates.
+ * @brief Set the GPS receiver position using ::XYZ coordinates.
The structure ::XYZ must specify the new position in ECEF
(Earth Centered, Earth Fixed) kartesian coordinates.
@@ -3041,13 +5513,13 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_pos( MBG_DEV_HANDLE dh, POS *p )
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param p Position in ::XYZ format to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_gps_pos_lla()
- @see mbg_get_gps_pos()
+ * @see ::mbg_set_gps_pos_lla
+ * @see ::mbg_get_gps_pos
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_pos_xyz( MBG_DEV_HANDLE dh, const XYZ p )
{
@@ -3062,7 +5534,10 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_pos_xyz( MBG_DEV_HANDLE dh, const XYZ p )
_mbg_swab_double( &xyz[i] );
}
- rc = _mbgdevio_write_gps_var( dh, PC_GPS_POS_XYZ, IOCTL_SET_GPS_POS_XYZ, xyz );
+ // _mbgdevio_write_gps_var() would fail here since
+ // XYZ is an array, not a structure.
+ rc = _mbgdevio_write_gps( dh, PC_GPS_POS_XYZ, IOCTL_SET_GPS_POS_XYZ,
+ xyz, sizeof( XYZ ) );
return _mbgdevio_ret_val;
} // mbg_set_gps_pos_xyz
@@ -3071,22 +5546,22 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_pos_xyz( MBG_DEV_HANDLE dh, const XYZ p )
/*HDR*/
/**
- @brief Set the GPS receiver position using ::LLA coordinates.
-
- The structure LLA must specify the new position as longitude, latitude,
- and altitude, using the WGS84 geographic datum.
-
- The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device.
- @param p Position in ::LLA format to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_set_gps_pos_xyz()
- @see mbg_get_gps_pos()
-*/
+ * @brief Set the GPS receiver position using ::LLA coordinates
+ *
+ * The structure ::LLA must specify the new position as longitude,
+ * latitude, and altitude, using the WGS84 geographic datum.
+ *
+ * The macro ::_pcps_is_gps or the API call ::mbg_dev_is_gps
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param p Position in ::LLA format to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_set_gps_pos_xyz
+ * @see ::mbg_get_gps_pos
+ */
_MBG_API_ATTR int _MBG_API mbg_set_gps_pos_lla( MBG_DEV_HANDLE dh, const LLA p )
{
_mbgdevio_vars();
@@ -3100,7 +5575,10 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_pos_lla( MBG_DEV_HANDLE dh, const LLA p )
_mbg_swab_double( &lla[i] );
}
- rc = _mbgdevio_write_gps_var( dh, PC_GPS_POS_LLA, IOCTL_SET_GPS_POS_LLA, lla );
+ // _mbgdevio_write_gps_var() would fail here since
+ // LLA is an array, not a structure.
+ rc = _mbgdevio_write_gps( dh, PC_GPS_POS_LLA, IOCTL_SET_GPS_POS_LLA, lla, sizeof( LLA ) );
+
return _mbgdevio_ret_val;
} // mbg_set_gps_pos_lla
@@ -3109,22 +5587,23 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_pos_lla( MBG_DEV_HANDLE dh, const LLA p )
/*HDR*/
/**
- @brief Read the configured GPS antenna cable length from a device.
-
- The antenna cable length parameter is used to compensate the propagation
- delay of the RF signal over the antenna cable, which is about 5 ns/m.
-
- The macro _pcps_has_cab_len() or the API call mbg_dev_has_cab_len()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device.
- @param *p ::ANT_CABLE_LEN structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_cab_len()
- @see mbg_set_gps_ant_cable_len()
-*/
+ * @brief Read the configured GPS antenna cable length from a device.
+ *
+ * The antenna cable length parameter is used by GPS/GNSS receivers
+ * to compensate the propagation delay of the RF signal over the antenna
+ * cable, which is about 5 ns/m.
+ *
+ * The macro ::_pcps_has_cab_len or the API call ::mbg_dev_has_cab_len
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p ::ANT_CABLE_LEN structure to be filled up
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_cab_len
+ * @see ::mbg_set_gps_ant_cable_len
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_ant_cable_len( MBG_DEV_HANDLE dh, ANT_CABLE_LEN *p )
{
_mbgdevio_vars();
@@ -3140,21 +5619,26 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_ant_cable_len( MBG_DEV_HANDLE dh, ANT_CAB
/*HDR*/
/**
- @brief Write the GPS antenna cable length configuration to a device.
-
- The antenna cable length parameter is used to compensate the propagation
- delay of the RF signal over the antenna cable, which is about 5 ns/m.
-
- The macro _pcps_has_cab_len() or the API call mbg_dev_has_cab_len()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device.
- @param *p ::ANT_CABLE_LEN structure to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_cab_len()
- @see mbg_get_gps_ant_cable_len()
+ * @brief Write the GPS antenna cable length configuration to a device.
+ *
+ * The antenna cable length parameter is used by GPS/GNSS receivers
+ * to compensate the propagation delay of the RF signal over the antenna
+ * cable, which is about 5 ns/m.
+ *
+ * The macro ::_pcps_has_cab_len or the API call ::mbg_dev_has_cab_len
+ * check whether this call is supported by a device.
+ *
+ * @note Different devices may accept different maximum values, so the
+ * written value should be re-read using ::mbg_get_gps_ant_cable_len
+ * to check if the parameter has been accepted.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p ::ANT_CABLE_LEN structure to be written
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_cab_len
+ * @see ::mbg_get_gps_ant_cable_len
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_ant_cable_len( MBG_DEV_HANDLE dh,
const ANT_CABLE_LEN *p )
@@ -3176,7 +5660,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_ant_cable_len( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Read the ::RECEIVER_INFO structure from a device.
+ * @brief Read the ::RECEIVER_INFO structure from a device.
The macro _pcps_has_receiver_info() or the API call mbg_dev_has_receiver_info()
check whether this call is supported by a device.
@@ -3185,12 +5669,12 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_ant_cable_len( MBG_DEV_HANDLE dh,
preferably, which also sets up a basic ::RECEIVER_INFO structure
for devices which don't provide that structure by themselves.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::RECEIVER_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_setup_receiver_info()
+ * @see ::mbg_setup_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_receiver_info( MBG_DEV_HANDLE dh, RECEIVER_INFO *p )
{
@@ -3210,7 +5694,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_receiver_info( MBG_DEV_HANDLE dh, RECEIVE
/*HDR*/
/**
- @brief Read a ::STR_TYPE_INFO_IDX array of supported string types.
+ * @brief Read a ::STR_TYPE_INFO_IDX array of supported string types.
The function mbg_setup_receiver_info() must have been called before,
and the returned ::RECEIVER_INFO structure passed to this function.
@@ -3218,15 +5702,15 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_receiver_info( MBG_DEV_HANDLE dh, RECEIVE
<b>Note:</b> The function mbg_get_serial_settings() should be used preferably
to get retrieve the current port settings and configuration options.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param stii Pointer to a an array of string type information to be filled up
@param *p_ri Pointer to a ::RECEIVER_INFO structure returned by mbg_setup_receiver_info()
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_setup_receiver_info()
- @see mbg_get_gps_all_port_info()
- @see mbg_get_serial_settings()
+ * @see ::mbg_setup_receiver_info
+ * @see ::mbg_get_gps_all_port_info
+ * @see ::mbg_get_serial_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_all_str_type_info( MBG_DEV_HANDLE dh,
STR_TYPE_INFO_IDX stii[],
@@ -3247,11 +5731,11 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_str_type_info( MBG_DEV_HANDLE dh,
rc = _mbgdevio_gen_read_gps( dh, PC_GPS_ALL_STR_TYPE_INFO, stii,
p_ri->n_str_type * sizeof( stii[0] ) );
else
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV );
+ return MBG_ERR_NOT_SUPP_BY_DEV;
#endif
#if defined( MBG_ARCH_BIG_ENDIAN )
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
{
int i;
for ( i = 0; i < p_ri->n_str_type; i++ )
@@ -3270,7 +5754,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_str_type_info( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Read a ::PORT_INFO_IDX array of supported serial port configurations.
+ * @brief Read a ::PORT_INFO_IDX array of supported serial port configurations.
The function mbg_setup_receiver_info() must have been called before,
and the returned ::RECEIVER_INFO structure passed to this function.
@@ -3278,15 +5762,15 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_str_type_info( MBG_DEV_HANDLE dh,
<b>Note:</b> The function mbg_get_serial_settings() should be used preferably
to get retrieve the current port settings and configuration options.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pii Pointer to a an array of port configuration information to be filled up
@param *p_ri Pointer to a ::RECEIVER_INFO structure returned by mbg_setup_receiver_info()
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_setup_receiver_info()
- @see mbg_get_gps_all_str_type_info()
- @see mbg_get_serial_settings()
+ * @see ::mbg_setup_receiver_info
+ * @see ::mbg_get_gps_all_str_type_info
+ * @see ::mbg_get_serial_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_all_port_info( MBG_DEV_HANDLE dh,
PORT_INFO_IDX pii[],
@@ -3307,11 +5791,11 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_port_info( MBG_DEV_HANDLE dh,
rc = _mbgdevio_gen_read_gps( dh, PC_GPS_ALL_PORT_INFO, pii,
p_ri->n_com_ports * sizeof( pii[0] ) );
else
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV );
+ return MBG_ERR_NOT_SUPP_BY_DEV;
#endif
#if defined( MBG_ARCH_BIG_ENDIAN )
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
{
int i;
for ( i = 0; i < p_ri->n_com_ports; i++ )
@@ -3330,7 +5814,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_port_info( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Write the configuration for a single serial port to a device.
+ * @brief Write the configuration for a single serial port to a device.
The ::PORT_SETTINGS_IDX structure contains both the ::PORT_SETTINGS
and the port index value. Except for the parameter types this call is
@@ -3342,14 +5826,14 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_port_info( MBG_DEV_HANDLE dh,
<b>Note:</b> The function mbg_save_serial_settings() should be used preferably
to write new port configuration to the board.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PORT_SETTINGS_IDX structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_save_serial_settings()
- @see mbg_set_gps_port_settings()
- @see mbg_dev_has_receiver_info()
+ * @see ::mbg_save_serial_settings
+ * @see ::mbg_set_gps_port_settings
+ * @see ::mbg_dev_has_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_port_settings_idx( MBG_DEV_HANDLE dh,
const PORT_SETTINGS_IDX *p )
@@ -3371,7 +5855,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_port_settings_idx( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Write the configuration for a single serial port to a device.
+ * @brief Write the configuration for a single serial port to a device.
The ::PORT_SETTINGS structure does not contain the port index, so the
the port index must be given separately. Except for the parameter types
@@ -3383,15 +5867,15 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_port_settings_idx( MBG_DEV_HANDLE dh,
<b>Note:</b> The function mbg_save_serial_settings() should be used preferably
to write new port configuration to the board.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PORT_SETTINGS structure to be filled up
@param idx Index of the serial port to be configured (starting from 0 ).
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_save_serial_settings()
- @see mbg_set_gps_port_settings_idx()
- @see mbg_dev_has_receiver_info()
+ * @see ::mbg_save_serial_settings
+ * @see ::mbg_set_gps_port_settings_idx
+ * @see ::mbg_dev_has_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_port_settings( MBG_DEV_HANDLE dh,
const PORT_SETTINGS *p, int idx )
@@ -3412,55 +5896,71 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_port_settings( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Set up a ::RECEIVER_INFO structure for a device.
+ * @brief Set up a ::RECEIVER_INFO structure for a device.
+ *
+ * If the device supports the ::RECEIVER_INFO structure then the structure
+ * is read from the device, otherwise a structure is set up using
+ * default values depending on the device type.
+ * Optionally, the function mbg_get_device_info() may have been called
+ * before, and the returned ::PCPS_DEV structure can be passed to this
+ * function.
+ * If a NULL pointer is passed instead, the device info is retrieved
+ * directly from the device, using the device handle.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] p_dev Optional pointer to a ::PCPS_DEV structure, may be NULL
+ * @param[out] p Pointer to a ::RECEIVER_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_device_info
+ * @see ::mbg_dev_has_receiver_info
+ */
+_MBG_API_ATTR int _MBG_API mbg_setup_receiver_info( MBG_DEV_HANDLE dh,
+ const PCPS_DEV *p_dev,
+ RECEIVER_INFO *p )
+{
+ PCPS_DEV dev = { { 0 } };
+ int rc;
- If the device supports the ::RECEIVER_INFO structure then the structure
- is read from the device, otherwise a structure is set up using
- default values depending on the device type.
- The function mbg_get_device_info() must have been called before,
- and the returned PCPS_DEV structure passed to this function.
+ if ( p_dev == NULL )
+ {
+ rc = mbg_get_device_info( dh, &dev );
- @param dh Valid handle to a Meinberg device.
- @param *pdev Pointer to a ::PCPS_DEV structure returned by mbg_get_device_info()
- @param *p Pointer to a ::RECEIVER_INFO structure to be filled up
+ if ( mbg_rc_is_error( rc ) )
+ return rc;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ p_dev = &dev;
+ }
- @see mbg_get_device_info()
- @see mbg_dev_has_receiver_info()
-*/
-_MBG_API_ATTR int _MBG_API mbg_setup_receiver_info( MBG_DEV_HANDLE dh,
- const PCPS_DEV *pdev,
- RECEIVER_INFO *p )
-{
// If the clock supports the receiver_info structure then
// read it from the clock, otherwise set up some default
// values depending on the clock type.
- if ( _pcps_has_receiver_info( pdev ) )
+ if ( _pcps_has_receiver_info( p_dev ) )
{
- int rc = mbg_get_gps_receiver_info( dh, p );
+ rc = mbg_get_gps_receiver_info( dh, p );
- if ( rc != MBG_SUCCESS )
+ if ( mbg_rc_is_error( rc ) )
return rc;
goto check;
}
- if ( _pcps_is_gps( pdev ) )
+ if ( _pcps_is_gps( p_dev ) )
_setup_default_receiver_info_gps( p );
else
- _setup_default_receiver_info_dcf( p, pdev );
+ _setup_default_receiver_info_dcf( p, p_dev );
check:
// Make sure this program supports at least as many ports as
// the current clock device.
if ( p->n_com_ports > MAX_PARM_PORT )
- return _mbg_err_to_os( MBG_ERR_N_COM_EXCEEDS_SUPP );
+ return MBG_ERR_N_COM_EXCEEDS_SUPP;
// Make sure this program supports at least as many string types
// as the current clock device.
if ( p->n_str_type > MAX_PARM_STR_TYPE )
- return _mbg_err_to_os( MBG_ERR_N_STR_EXCEEDS_SUPP );
+ return MBG_ERR_N_STR_EXCEEDS_SUPP;
return MBG_SUCCESS;
@@ -3471,28 +5971,27 @@ check:
/*HDR*/
/**
- @brief Read the version code of the on-board PCI/PCIe interface ASIC.
+ * @brief Read the version code of the on-board PCI/PCIe interface ASIC.
The macro _pcps_has_asic_version() or the API call mbg_dev_has_asic_version()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCI_ASIC_VERSION type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_asic_version()
+ * @see ::mbg_dev_has_asic_version
*/
_MBG_API_ATTR int _MBG_API mbg_get_asic_version( MBG_DEV_HANDLE dh, PCI_ASIC_VERSION *p )
{
-
#if defined( _MBGIOCTL_H )
_mbgdevio_vars();
rc = _mbgdevio_read_var( dh, -1, IOCTL_GET_PCI_ASIC_VERSION, p );
return _mbgdevio_ret_val;
#else
if ( !_pcps_ddev_has_asic_version( dh ) )
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV );
+ return MBG_ERR_NOT_SUPP_BY_DEV;
*p = _mbg_inp32_to_cpu( dh, 0, _pcps_ddev_io_base_mapped( dh, 0 )
+ offsetof( PCI_ASIC, raw_version ) );
@@ -3506,17 +6005,17 @@ _MBG_API_ATTR int _MBG_API mbg_get_asic_version( MBG_DEV_HANDLE dh, PCI_ASIC_VER
/*HDR*/
/**
- @brief Read the features of the on-board PCI/PCIe interface ASIC.
+ * @brief Read the features of the on-board PCI/PCIe interface ASIC.
The macro _pcps_has_asic_features() or the API call mbg_dev_has_asic_features()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCI_ASIC_FEATURES type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_asic_features()
+ * @see ::mbg_dev_has_asic_features
*/
_MBG_API_ATTR int _MBG_API mbg_get_asic_features( MBG_DEV_HANDLE dh,
PCI_ASIC_FEATURES *p )
@@ -3530,7 +6029,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_asic_features( MBG_DEV_HANDLE dh,
if ( !_pcps_ddev_has_asic_features( dh ) )
{
*p = 0;
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV );
+ return MBG_ERR_NOT_SUPP_BY_DEV;
}
*p = _mbg_inp32_to_cpu( dh, 0, _pcps_ddev_io_base_mapped( dh, 0 )
@@ -3545,30 +6044,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_asic_features( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Check if a device supports configurable time scales.
-
- By default the cards return UTC and/or local time. However, some cards
- can be configured to return raw GPS time or TAI instead.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_time_scale_info()
- @see mbg_set_time_scale_settings()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_time_scale( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_time_scale, IOCTL_DEV_HAS_GPS_TIME_SCALE, p );
-
-} // mbg_dev_has_time_scale
-
-
-
-/*HDR*/
-/**
- @brief Read the current time scale settings and which time scales are supported.
+ * @brief Read the current time scale settings and which time scales are supported.
The ::MBG_TIME_SCALE_INFO structure tells which time scale settings are supported
by a device, and which time scale is currently configured.
@@ -3577,13 +6053,13 @@ _MBG_API_ATTR int _MBG_API mbg_dev_has_time_scale( MBG_DEV_HANDLE dh, int *p )
check whether this call is supported by a device.
See also the notes for mbg_dev_has_time_scale().
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_TIME_SCALE_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_time_scale_settings()
- @see mbg_dev_has_time_scale()
+ * @see ::mbg_set_time_scale_settings
+ * @see ::mbg_dev_has_time_scale
*/
_MBG_API_ATTR int _MBG_API mbg_get_time_scale_info( MBG_DEV_HANDLE dh, MBG_TIME_SCALE_INFO *p )
{
@@ -3600,7 +6076,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_time_scale_info( MBG_DEV_HANDLE dh, MBG_TIME_
/*HDR*/
/**
- @brief Write the time scale configuration to a device.
+ * @brief Write the time scale configuration to a device.
The ::MBG_TIME_SCALE_SETTINGS structure determines which time scale
is to be used for the time stamps which can be read from a device.
@@ -3612,15 +6088,15 @@ _MBG_API_ATTR int _MBG_API mbg_get_time_scale_info( MBG_DEV_HANDLE dh, MBG_TIME_
The function mbg_get_time_scale_info() should have been called before
in order to determine which time scales are supported by the card.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_TIME_SCALE_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_time_scale_info()
- @see mbg_dev_has_time_scale()
+ * @see ::mbg_get_time_scale_info
+ * @see ::mbg_dev_has_time_scale
*/
-_MBG_API_ATTR int _MBG_API mbg_set_time_scale_settings( MBG_DEV_HANDLE dh, MBG_TIME_SCALE_SETTINGS *p )
+_MBG_API_ATTR int _MBG_API mbg_set_time_scale_settings( MBG_DEV_HANDLE dh, const MBG_TIME_SCALE_SETTINGS *p )
{
_mbgdevio_vars();
#if defined( MBG_ARCH_BIG_ENDIAN )
@@ -3639,51 +6115,19 @@ _MBG_API_ATTR int _MBG_API mbg_set_time_scale_settings( MBG_DEV_HANDLE dh, MBG_T
/*HDR*/
/**
- @brief Check if a device support reading/writing of UTC parameters.
-
- This API call checks if a device supports reading/writing a GPS UTC
- parameter set via the PC bus. Reading/writing these parameters via the
- serial port using the Meinberg binary data protocol is supported by all
- Meinberg GPS devices.
-
- The UTC parameter set is usually received from the satellites' broadcasts
- and contains the current time offset between GPS time and UTC, plus information
- on a pending leap second event.
-
- It may be useful to overwrite them to do some tests, or for applications
- where a card is freewheeling.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_utc_parm()
- @see mbg_set_utc_parm()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_utc_parm( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_utc_parm, IOCTL_DEV_HAS_GPS_UTC_PARM, p );
-
-} // mbg_dev_has_utc_parm
-
-
-
-/*HDR*/
-/**
- @brief Read a ::UTC parameter structure from a device.
+ * @brief Read a ::UTC parameter structure from a device.
The macro _pcps_has_utc_parm() or the API call mbg_dev_has_utc_parm()
check whether this call is supported by a device.
See also the notes for mbg_dev_has_utc_parm().
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::UTC structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_utc_parm()
- @see mbg_set_utc_parm()
+ * @see ::mbg_dev_has_utc_parm
+ * @see ::mbg_set_utc_parm
*/
_MBG_API_ATTR int _MBG_API mbg_get_utc_parm( MBG_DEV_HANDLE dh, UTC *p )
{
@@ -3702,7 +6146,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_utc_parm( MBG_DEV_HANDLE dh, UTC *p )
/*HDR*/
/**
- @brief Write a ::UTC parameter structure to a device.
+ * @brief Write a ::UTC parameter structure to a device.
This should only be done for testing, or if a card is operated in
freewheeling mode. If the receiver is tracking any satellites then the settings
@@ -3713,26 +6157,30 @@ _MBG_API_ATTR int _MBG_API mbg_get_utc_parm( MBG_DEV_HANDLE dh, UTC *p )
check whether this call is supported by a device.
See also the notes for mbg_dev_has_utc_parm().
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a valid ::UTC structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_utc_parm()
- @see mbg_get_utc_parm()
+ * @see ::mbg_dev_has_utc_parm
+ * @see ::mbg_get_utc_parm
*/
-_MBG_API_ATTR int _MBG_API mbg_set_utc_parm( MBG_DEV_HANDLE dh, UTC *p )
+_MBG_API_ATTR int _MBG_API mbg_set_utc_parm( MBG_DEV_HANDLE dh, const UTC *p )
{
_mbgdevio_vars();
+
+ // the original parameters need to be modified anyway, so always use a copy
+ UTC tmp = *p;
+
#if defined( MBG_ARCH_BIG_ENDIAN )
- UTC tmp = *p;
_mbg_swab_utc_parm( &tmp );
- p = &tmp;
#endif
- swap_double( &p->A0 );
- swap_double( &p->A1 );
+
+ swap_double( &tmp.A0 );
+ swap_double( &tmp.A1 );
+
_mbgdevio_write_gps_var_chk( dh, PC_GPS_UTC,
- IOCTL_SET_GPS_UTC_PARM, p,
+ IOCTL_SET_GPS_UTC_PARM, &tmp,
_pcps_ddev_has_utc_parm( dh ) );
return _mbgdevio_ret_val;
@@ -3742,7 +6190,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_utc_parm( MBG_DEV_HANDLE dh, UTC *p )
/*HDR*/
/**
- @brief Read the current time plus the associated PC cycles from a device.
+ * @brief Read the current time plus the associated PC cycles from a device.
The ::PCPS_TIME_CYCLES structure contains a ::PCPS_TIME structure
and a PC cycle counter value which can be used to compensate the latency
@@ -3762,15 +6210,15 @@ _MBG_API_ATTR int _MBG_API mbg_set_utc_parm( MBG_DEV_HANDLE dh, UTC *p )
latency of the call in units of the cycle counter clock frequency, e.g as reported
by QueryPerformanceFrequency() under Windows.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TIME_CYCLES structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_hr_time_cycles()
- @see mbg_get_hr_time_comp()
- @see mbg_get_hr_time()
- @see mbg_get_time()
+ * @see ::mbg_get_hr_time_cycles
+ * @see ::mbg_get_hr_time_comp
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_time
*/
_MBG_API_ATTR int _MBG_API mbg_get_time_cycles( MBG_DEV_HANDLE dh, PCPS_TIME_CYCLES *p )
{
@@ -3790,35 +6238,41 @@ _MBG_API_ATTR int _MBG_API mbg_get_time_cycles( MBG_DEV_HANDLE dh, PCPS_TIME_CYC
/*HDR*/
/**
- @brief Read the current high resolution time plus the associated PC cycles from a device.
-
- The ::PCPS_HR_TIME_CYCLES structure contains a ::PCPS_HR_TIME structure
- and a PC cycle counter value which can be used to compensate the latency
- of the call, i.e. the program execution time until the time stamp has actually
- been read from the board.
-
- The macro _pcps_has_hr_time() or the API call mbg_dev_has_hr_time()
- check whether this call is supported by a device.
-
- The cycle counter value corresponds to a value returned by QueryPerformanceCounter()
- under Windows, and get_cycles() under Linux. On operating systems or targets which don't
- provide a cycles counter the returned cycles value is always 0.
-
- Applications should first pick up their own cycle counter value and then call
- this function. The difference of the cycle counter values corresponds to the
- latency of the call in units of the cycle counter clock frequency, e.g as reported
- by QueryPerformanceFrequency() under Windows.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_HR_TIME_CYCLES structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_hr_time_comp()
- @see mbg_get_hr_time()
- @see mbg_get_time_cycles()
- @see mbg_get_time()
-*/
+ * @brief Read the current high resolution time plus the associated PC cycles from a device.
+ *
+ * The returned ::PCPS_HR_TIME_CYCLES structure contains a ::PCPS_HR_TIME
+ * structure and a PC cycle counter value which can be used to compensate
+ * the latency of the call, i.e. the program execution time until the time stamp
+ * has actually been read from the board.
+ *
+ * The API call ::mbg_chk_dev_has_hr_time checks whether this call
+ * is supported by the device.
+ *
+ * For details see @ref ::pcps_hr_time_fncs
+ *
+ * The cycle counter value corresponds to a value returned by QueryPerformanceCounter()
+ * under Windows, and get_cycles() under Linux. On operating systems or targets which don't
+ * provide a cycles counter the returned cycles value is always 0.
+ *
+ * Applications should first pick up their own cycle counter value and then call
+ * this function. The difference of the cycle counter values corresponds to the
+ * latency of the call in units of the cycle counter clock frequency, e.g as reported
+ * by QueryPerformanceFrequency() under Windows.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_HR_TIME_CYCLES structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_hr_time_fncs
+ * @see ::mbg_chk_dev_has_hr_time
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_hr_time_cycles
+ * @see ::mbg_get_hr_time_comp
+ * @see @ref pcps_hr_time_fncs
+ * @see @ref pcps_fast_timestamp_fncs
+ * @see @ref pcps_std_time_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_hr_time_cycles( MBG_DEV_HANDLE dh,
PCPS_HR_TIME_CYCLES *p )
{
@@ -3840,36 +6294,42 @@ _MBG_API_ATTR int _MBG_API mbg_get_hr_time_cycles( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Read the current high resolution time, and compensate the call's latency.
-
- Read a ::PCPS_HR_TIME structure plus cycle counter value, and correct the
- time stamp for the latency of the call as described for mbg_get_hr_time_cycles(),
- then return the compensated time stamp and optionally the latency.
-
- The macro _pcps_has_hr_time() or the API call mbg_dev_has_hr_time()
- check whether this call is supported by a device.
-
- The cycle counter value corresponds to a value returned by QueryPerformanceCounter()
- under Windows, and get_cycles() under Linux. On operating systems or targets which don't
- provide a cycles counter the returned cycles value is always 0.
-
- Applications should first pick up their own cycle counter value and then call
- this function. The difference of the cycle counter values corresponds to the
- latency of the call in units of the cycle counter clock frequency, e.g as reported
- by QueryPerformanceFrequency() under Windows.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_HR_TIME structure to be filled up
- @param *hns_latency Optional pointer to an int32_t value to return
- the latency in 100ns units. Pass NULL if not used.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_hr_time_comp()
- @see mbg_get_hr_time()
- @see mbg_get_time_cycles()
- @see mbg_get_time()
-*/
+ * @brief Read the current high resolution time, and compensate the call's latency.
+ *
+ * Read a ::PCPS_HR_TIME structure plus cycle counter value, and correct the
+ * time stamp for the latency of the call as described for ::mbg_get_hr_time_cycles,
+ * then return the compensated time stamp and optionally the latency.
+ *
+ * The API call ::mbg_chk_dev_has_hr_time checks whether this call
+ * is supported by the device.
+ *
+ * For details see @ref ::pcps_hr_time_fncs
+ *
+ * The cycle counter value corresponds to a value returned by QueryPerformanceCounter()
+ * under Windows, and get_cycles() under Linux. On operating systems or targets which don't
+ * provide a cycles counter the returned cycles value is always 0.
+ *
+ * Applications should first pick up their own cycle counter value and then call
+ * this function. The difference of the cycle counter values corresponds to the
+ * latency of the call in units of the cycle counter clock frequency, e.g as reported
+ * by QueryPerformanceFrequency() under Windows.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_HR_TIME structure to be filled up
+ * @param[out] hns_latency Optional pointer to an int32_t value to return
+ * the latency in 100ns units, or NULL, if not used.
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_hr_time_fncs
+ * @see ::mbg_chk_dev_has_hr_time
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_hr_time_cycles
+ * @see ::mbg_get_hr_time_comp
+ * @see @ref pcps_hr_time_fncs
+ * @see @ref pcps_fast_timestamp_fncs
+ * @see @ref pcps_std_time_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_hr_time_comp( MBG_DEV_HANDLE dh, PCPS_HR_TIME *p,
int32_t *hns_latency )
{
@@ -3884,7 +6344,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_hr_time_comp( MBG_DEV_HANDLE dh, PCPS_HR_TIME
rc = mbg_get_hr_time_cycles( dh, &htc );
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
{
mbg_init_pc_cycles_frequency( dh, &pc_cycles_frequency );
rc = mbg_comp_hr_latency( &htc.t.tstamp, &htc.cycles, &cyc_now, &pc_cycles_frequency, hns_latency );
@@ -3899,7 +6359,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_hr_time_comp( MBG_DEV_HANDLE dh, PCPS_HR_TIME
/*HDR*/
/**
- @brief Read the current IRIG output settings plus the supported settings.
+ * @brief Read the current IRIG output settings plus the supported settings.
The returned ::IRIG_INFO structure contains the configuration of an IRIG output
plus the possible settings supported by that output.
@@ -3907,16 +6367,16 @@ _MBG_API_ATTR int _MBG_API mbg_get_hr_time_comp( MBG_DEV_HANDLE dh, PCPS_HR_TIME
The macro _pcps_has_irig_tx() or the API call mbg_dev_has_irig_tx()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to an ::IRIG_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_irig_tx_settings()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
+ * @see ::mbg_set_irig_tx_settings
+ * @see ::mbg_dev_has_irig_tx
+ * @see ::mbg_dev_is_irig_rx
+ * @see ::mbg_dev_has_irig
+ * @see @ref group_icode
*/
_MBG_API_ATTR int _MBG_API mbg_get_irig_tx_info( MBG_DEV_HANDLE dh, IRIG_INFO *p )
{
@@ -3948,21 +6408,21 @@ _MBG_API_ATTR int _MBG_API mbg_get_irig_tx_info( MBG_DEV_HANDLE dh, IRIG_INFO *p
/*HDR*/
/**
- @brief Write an ::IRIG_SETTINGS structure to a device to configure the IRIG output.
+ * @brief Write an ::IRIG_SETTINGS structure to a device to configure the IRIG output.
The macro _pcps_has_irig_tx() or the API call mbg_dev_has_irig_tx()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to an ::IRIG_INFO structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_irig_tx_info()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
+ * @see ::mbg_get_irig_tx_info
+ * @see ::mbg_dev_has_irig_tx
+ * @see ::mbg_dev_is_irig_rx
+ * @see ::mbg_dev_has_irig
+ * @see @ref group_icode
*/
_MBG_API_ATTR int _MBG_API mbg_set_irig_tx_settings( MBG_DEV_HANDLE dh, const IRIG_SETTINGS *p )
{
@@ -4002,24 +6462,24 @@ _MBG_API_ATTR int _MBG_API mbg_set_irig_tx_settings( MBG_DEV_HANDLE dh, const IR
/*HDR*/
/**
- @brief Read the current frequency synthesizer settings from a device.
-
- Read a ::SYNTH structure containing the configuration of an optional
- on-board programmable frequency synthesizer.
-
- The macro _pcps_has_synth() or the API call mbg_dev_has_synth()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::SYNTH structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_synth()
- @see mbg_set_synth()
- @see mbg_get_synth_state()
- @see \ref group_synth
-*/
+ * @brief Read the current frequency synthesizer settings from a device.
+ *
+ * Read a ::SYNTH structure containing the configuration of an optional
+ * on-board programmable frequency synthesizer.
+ *
+ * The macro ::_pcps_has_synth or the API call ::mbg_dev_has_synth
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::SYNTH structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_synth
+ * @see ::mbg_set_synth
+ * @see ::mbg_get_synth_state
+ * @see @ref group_synth
+ */
_MBG_API_ATTR int _MBG_API mbg_get_synth( MBG_DEV_HANDLE dh, SYNTH *p )
{
_mbgdevio_vars();
@@ -4034,24 +6494,24 @@ _MBG_API_ATTR int _MBG_API mbg_get_synth( MBG_DEV_HANDLE dh, SYNTH *p )
/*HDR*/
/**
- @brief Write some frequency synthesizer settings to a device.
-
- Write a ::SYNTH structure containing the configuration of an optional
- on-board programmable frequency synthesizer.
-
- The macro _pcps_has_synth() or the API call mbg_dev_has_synth()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::SYNTH structure to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_synth()
- @see mbg_get_synth()
- @see mbg_get_synth_state()
- @see \ref group_synth
-*/
+ * @brief Write some frequency synthesizer settings to a device.
+ *
+ * Write a ::SYNTH structure containing the configuration of an optional
+ * on-board programmable frequency synthesizer.
+ *
+ * The macro _pcps_has_synth() or the API call mbg_dev_has_synth()
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::SYNTH structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_synth
+ * @see ::mbg_get_synth
+ * @see ::mbg_get_synth_state
+ * @see @::\ref group_synth
+ */
_MBG_API_ATTR int _MBG_API mbg_set_synth( MBG_DEV_HANDLE dh, const SYNTH *p )
{
_mbgdevio_vars();
@@ -4070,20 +6530,20 @@ _MBG_API_ATTR int _MBG_API mbg_set_synth( MBG_DEV_HANDLE dh, const SYNTH *p )
/*HDR*/
/**
- @brief Read the current status of the on-board frequency synthesizer.
+ * @brief Read the current status of the on-board frequency synthesizer.
The macro _pcps_has_synth() or the API call mbg_dev_has_synth()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::SYNTH_STATE structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_synth()
- @see mbg_get_synth()
- @see mbg_set_synth()
- @see \ref group_synth
+ * @see ::mbg_dev_has_synth
+ * @see ::mbg_get_synth
+ * @see ::mbg_set_synth
+ * @see @ref group_synth
*/
_MBG_API_ATTR int _MBG_API mbg_get_synth_state( MBG_DEV_HANDLE dh, SYNTH_STATE *p )
{
@@ -4099,38 +6559,19 @@ _MBG_API_ATTR int _MBG_API mbg_get_synth_state( MBG_DEV_HANDLE dh, SYNTH_STATE *
/*HDR*/
/**
- @brief Check if a device supports the mbg_get_fast_hr_timestamp_...() calls.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_fast_hr_timestamp_cycles()
- @see mbg_get_fast_hr_timestamp_comp()
- @see mbg_get_fast_hr_timestamp()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_fast_hr_timestamp( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_fast_hr_timestamp, IOCTL_DEV_HAS_FAST_HR_TIMESTAMP, p );
-
-} // mbg_dev_has_fast_hr_timestamp
-
-
-
-/*HDR*/
-/**
- @brief Read a high resolution ::PCPS_TIME_STAMP_CYCLES structure via memory mapped access.
+ * @brief Read a high resolution ::PCPS_TIME_STAMP_CYCLES structure via memory mapped access.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TIME_STAMP_CYCLES structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_fast_hr_timestamp()
- @see mbg_get_fast_hr_timestamp_comp()
- @see mbg_get_fast_hr_timestamp()
-*/
+ * @ingroup pcps_fast_timestamp_fncs
+ * @see ::mbg_dev_has_fast_hr_timestamp
+ * @see ::mbg_get_fast_hr_timestamp_comp
+ * @see ::mbg_get_fast_hr_timestamp
+ * @see @ref pcps_fast_timestamp_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp_cycles( MBG_DEV_HANDLE dh,
PCPS_TIME_STAMP_CYCLES *p )
{
@@ -4141,29 +6582,32 @@ _MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp_cycles( MBG_DEV_HANDLE dh,
return _mbgdevio_ret_val;
#else
// This is currently not supported by the target environment.
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_ON_OS );
+ return MBG_ERR_NOT_SUPP_ON_OS;
#endif
+
} // mbg_get_fast_hr_timestamp_cycles
/*HDR*/
/**
- @brief Read a high resolution timestamp and compensate the latency of the call.
+ * @brief Read a high resolution timestamp and compensate the latency of the call.
The retrieved ::PCPS_TIME_STAMP is read from memory mapped registers,
and timestamp is compensated for the call's latency before it is returned.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TIME_STAMP structure to be filled up
@param *hns_latency Optionally receive the latency in hectonanoseconds
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_fast_hr_timestamp()
- @see mbg_get_fast_hr_timestamp_cycles()
- @see mbg_get_fast_hr_timestamp()
-*/
+ * @ingroup pcps_fast_timestamp_fncs
+ * @see ::mbg_dev_has_fast_hr_timestamp
+ * @see ::mbg_get_fast_hr_timestamp_cycles
+ * @see ::mbg_get_fast_hr_timestamp
+ * @see @ref pcps_fast_timestamp_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp_comp( MBG_DEV_HANDLE dh,
PCPS_TIME_STAMP *p,
int32_t *hns_latency )
@@ -4179,7 +6623,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp_comp( MBG_DEV_HANDLE dh,
rc = mbg_get_fast_hr_timestamp_cycles( dh, &tc );
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
{
mbg_init_pc_cycles_frequency( dh, &pc_cycles_frequency );
rc = mbg_comp_hr_latency( &tc.tstamp, &tc.cycles, &cyc_now, &pc_cycles_frequency, hns_latency );
@@ -4194,7 +6638,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp_comp( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Read a high resolution ::PCPS_TIME_STAMP structure via memory mapped access.
+ * @brief Read a high resolution ::PCPS_TIME_STAMP structure via memory mapped access.
This function does not return or evaluate a cycles count, so the latency
of the call can not be determined. However, depending on the timer hardware
@@ -4202,15 +6646,17 @@ _MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp_comp( MBG_DEV_HANDLE dh,
on some hardware architectures, so this call can be used to yield lower
latencies, under the restriction to be unable to determine the exact latency.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TIME_STAMP structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_fast_hr_timestamp()
- @see mbg_get_fast_hr_timestamp_comp()
- @see mbg_get_fast_hr_timestamp_cycles()
-*/
+ * @ingroup pcps_fast_timestamp_fncs
+ * @see ::mbg_dev_has_fast_hr_timestamp
+ * @see ::mbg_get_fast_hr_timestamp_comp
+ * @see ::mbg_get_fast_hr_timestamp_cycles
+ * @see @ref pcps_fast_timestamp_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp( MBG_DEV_HANDLE dh,
PCPS_TIME_STAMP *p )
{
@@ -4221,597 +6667,16 @@ _MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp( MBG_DEV_HANDLE dh,
return _mbgdevio_ret_val;
#else
// This is currently not supported by the target environment.
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_ON_OS );
+ return MBG_ERR_NOT_SUPP_ON_OS;
#endif
-} // mbg_get_fast_hr_timestamp
-
-
-
-/*HDR*/
-/**
- @brief Check if a device is a GPS receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_is_gps( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_is_gps, IOCTL_DEV_IS_GPS, p );
-
-} // mbg_dev_is_gps
-
-
-/*HDR*/
-/**
- @brief Check if a device is a DCF77 receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_is_dcf( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_is_dcf, IOCTL_DEV_IS_DCF, p );
-
-} // mbg_dev_is_dcf
-
-
-
-/*HDR*/
-/**
- @brief Check if a device is a MSF receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_is_msf( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_is_msf, IOCTL_DEV_IS_MSF, p );
-
-} // mbg_dev_is_msf
-
-
-
-/*HDR*/
-/**
- @brief Check if a device is a WWVB receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_is_wwvb( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_is_wwvb, IOCTL_DEV_IS_WWVB, p );
-
-} // mbg_dev_is_msf
-
-
-
-/*HDR*/
-/**
- @brief Check if a device is any long wave signal receiver.
-
- Long wave receivers include e.g. DCF77, MSF, WWVB, or JJY.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_is_lwr( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_is_lwr, IOCTL_DEV_IS_LWR, p );
-
-} // mbg_dev_is_lwr
-
-
-
-/*HDR*/
-/**
- @brief Check if a device provides a configurable IRIG input.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_irig_rx_info()
- @see mbg_set_irig_rx_settings()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_has_irig()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_is_irig_rx( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_is_irig_rx, IOCTL_DEV_IS_IRIG_RX, p );
-
-} // mbg_dev_is_irig_rx
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports the HR_TIME functions.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_hr_time()
- @see mbg_get_hr_time_cycles()
- @see mbg_get_hr_time_comp()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_hr_time( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_hr_time, IOCTL_DEV_HAS_HR_TIME, p );
-
-} // mbg_dev_has_hr_time
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports configuration of antenna cable length.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_gps_ant_cable_len()
- @see mbg_set_gps_ant_cable_len()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_cab_len( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_cab_len, IOCTL_DEV_HAS_CAB_LEN, p );
-
-} // mbg_dev_has_cab_len
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports timezone configuration using the ::TZDL structure.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_gps_tzdl()
- @see mbg_set_gps_tzdl()
- @see mbg_dev_has_tz()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_tzdl( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_tzdl, IOCTL_DEV_HAS_TZDL, p );
-
-} // mbg_dev_has_tzdl
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports timezone configuration using the ::PCPS_TZDL structure.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_pcps_tzdl()
- @see mbg_set_pcps_tzdl()
- @see mbg_dev_has_tz()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_pcps_tzdl( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_pcps_tzdl, IOCTL_DEV_HAS_PCPS_TZDL, p );
-
-} // mbg_dev_has_pcps_tzdl
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports timezone configuration using the ::PCPS_TZCODE type.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_tzcode()
- @see mbg_set_tzcode()
- @see mbg_dev_has_tz()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_tzcode( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_tzcode, IOCTL_DEV_HAS_TZCODE, p );
-
-} // mbg_dev_has_tzcode
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports any kind of timezone configuration.
-
- This can be used e.g. to check if a specifig dialog or menu has to
- be displayed.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_tzdl()
- @see mbg_dev_has_pcps_tzdl()
- @see mbg_dev_has_tzcode()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_tz( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_tz, IOCTL_DEV_HAS_TZ, p );
-
-} // mbg_dev_has_tz
-
-
-
-/*HDR*/
-/* (Intentionally excluded from Doxygen)
- Check if a device supports setting an event time, i.e.
- configure a %UTC time when the clock shall generate an event.
-
- <b>Note:</b> This is only supported by some special firmware.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_set_event_time()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_event_time( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_event_time, IOCTL_DEV_HAS_EVENT_TIME, p );
-
-} // mbg_dev_has_event_time
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports the ::RECEIVER_INFO structure and related calls.
-
- @note Older GPS devices may not support that structure.
-
- The mbg_get_gps_receiver_info() call uses this call to decide whether a
- ::RECEIVER_INFO can be read directly from a device, or whether a default
- structure has to be set up using default values depending on the device type.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_gps_receiver_info()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_receiver_info( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_receiver_info, IOCTL_DEV_HAS_RECEIVER_INFO, p );
-
-} // mbg_dev_has_receiver_info
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports the mbg_clr_ucap_buff() call.
-
- The mbg_clr_ucap_buff() call can be used to clear a card's on-board
- time capture FIFO buffer.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_clr_ucap_buff()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_can_clr_ucap_buff( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_can_clr_ucap_buff, IOCTL_DEV_CAN_CLR_UCAP_BUFF, p );
-
-} // mbg_dev_can_clr_ucap_buff
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports the mbg_get_ucap_entries() and mbg_get_ucap_event() calls.
-
- If the card does not but it is a GPS card then the card provides
- a time capture FIFO buffer and the obsolete mbg_get_gps_ucap()
- call can be used to retrieve entries from the FIFO buffer.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_ucap_entries()
- @see mbg_get_ucap_event()
- @see mbg_clr_ucap_buff()
- @see mbg_get_gps_ucap()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_ucap( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_ucap, IOCTL_DEV_HAS_UCAP, p );
-
-} // mbg_dev_has_ucap
-
-
-
-/*HDR*/
-/**
- @brief Check if a device provides a configurable IRIG output.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_irig_tx_info()
- @see mbg_set_irig_tx_settings()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
-
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_irig_tx( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_irig_tx, IOCTL_DEV_HAS_IRIG_TX, p );
-
-} // mbg_dev_has_irig_tx
-
-
-
-/*HDR*/
-/* (Intentionally excluded from Doxygen)
- Check if a device provides a serial output supporting
- higher baud rates than older cards, i.e. ::DEFAULT_BAUD_RATES_DCF_HS
- rather than ::DEFAULT_BAUD_RATES_DCF.
-
- The mbg_get_serial_settings() takes care of this, so applications
- which use that call as suggested won't need to use this call directly.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_serial_settings()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_serial_hs( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_serial_hs, IOCTL_DEV_HAS_SERIAL_HS, p );
-
-} // mbg_dev_has_serial_hs
-
-
-
-/*HDR*/
-/**
- @brief Check if a device provides the level of its inputs signal.
-
- This is useful to display the signal level of e.g. an IRIG or longwave signal.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_signal( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_signal, IOCTL_DEV_HAS_SIGNAL, p );
-
-} // mbg_dev_has_signal
-
-
-
-/*HDR*/
-/**
- @brief Check if a device provides a modulation signal.
-
- Modulation signals are e.g. the second marks of a DCF77 AM receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_mod( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_mod, IOCTL_DEV_HAS_MOD, p );
-
-} // mbg_dev_has_mod
-
-
-
-/*HDR*/
-/**
- @brief Check if a device provides either an IRIG input or output.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig_tx()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_irig( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_irig, IOCTL_DEV_HAS_IRIG, p );
-
-} // mbg_dev_has_irig
-
-
-
-/*HDR*/
-/**
- @brief Check if a device provides a configurable ref time offset.
-
- This may be required to convert the received time to %UTC, if the input
- signal doesn't specify this (e.g. most IRIG code formats).
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_ref_offs()
- @see mbg_set_ref_offs()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_ref_offs( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_ref_offs, IOCTL_DEV_HAS_REF_OFFS, p );
-
-} // mbg_dev_has_ref_offs
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports the ::MBG_OPT_INFO/::MBG_OPT_SETTINGS.
-
- These structures containing optional settings, controlled by flags.
- See ::MBG_OPT_SETTINGS and related definitions.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_opt_info()
- @see mbg_set_opt_settings()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_opt_flags( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_opt_flags, IOCTL_DEV_HAS_OPT_FLAGS, p );
-
-} // mbg_dev_has_opt_flags
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports large configuration data structures.
-
- Such structures have been introduced with the first Meinberg GPS receivers.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_gps_data( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_gps_data, IOCTL_DEV_HAS_GPS_DATA, p );
-
-} // mbg_dev_has_gps_data
-
-
-
-/*HDR*/
-/**
- @brief Check if a device provides a programmable frequency synthesizer.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_synth()
- @see mbg_set_synth()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_synth( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_synth, IOCTL_DEV_HAS_SYNTH, p );
-
-} // mbg_dev_has_synth
-
-
-
-/*HDR*/
-/* (Intentionally excluded from Doxygen)
- @brief Check if a device supports the mbg_generic_io() call.
-
- <b>Warning</b>: That call is for debugging purposes and internal use only!
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_generic_io()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_generic_io( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_generic_io, IOCTL_DEV_HAS_GENERIC_IO, p );
-
-} // mbg_dev_has_generic_io
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports the mbg_get_asic_version() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_asic_version()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_asic_version( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_asic_version, IOCTL_DEV_HAS_PCI_ASIC_VERSION, p );
-
-} // mbg_dev_has_asic_version
-
-
-
-/*HDR*/
-/**
- @brief Check if a device supports the mbg_get_asic_features() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_asic_features()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_asic_features( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_asic_features, IOCTL_DEV_HAS_PCI_ASIC_FEATURES, p );
-
-} // mbg_dev_has_asic_features
+} // mbg_get_fast_hr_timestamp
/*HDR*/
/**
- @brief Read current configuraton and features provided by the programmable pulse outputs.
+ * @brief Read current configuraton and features provided by the programmable pulse outputs.
Reads a ::POUT_INFO_IDX array of current settings and configuration
options of the device's programmable pulse outputs.
@@ -4824,15 +6689,15 @@ _MBG_API_ATTR int _MBG_API mbg_dev_has_asic_features( MBG_DEV_HANDLE dh, int *p
The array passed to this function to receive the returned data
must be able to hold at least ::RECEIVER_INFO::n_prg_out elements.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pii Pointer to a an array of ::POUT_INFO_IDX structures to be filled up
@param *p_ri Pointer to a ::RECEIVER_INFO structure returned by mbg_setup_receiver_info()
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_gps_pout_settings_idx()
- @see mbg_set_gps_pout_settings()
- @see mbg_setup_receiver_info()
+ * @see ::mbg_set_gps_pout_settings_idx
+ * @see ::mbg_set_gps_pout_settings
+ * @see ::mbg_setup_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_all_pout_info( MBG_DEV_HANDLE dh,
POUT_INFO_IDX pii[],
@@ -4853,11 +6718,11 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_pout_info( MBG_DEV_HANDLE dh,
rc = _mbgdevio_gen_read_gps( dh, PC_GPS_ALL_POUT_INFO, pii,
p_ri->n_prg_out * sizeof( pii[0] ) );
else
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV );
+ return MBG_ERR_NOT_SUPP_BY_DEV;
#endif
#if defined( MBG_ARCH_BIG_ENDIAN )
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
{
int i;
for ( i = 0; i < p_ri->n_prg_out; i++ )
@@ -4876,7 +6741,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_pout_info( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Write the configuration for a single programmable pulse output
+ * @brief Write the configuration for a single programmable pulse output
The ::POUT_SETTINGS_IDX structure contains both the ::POUT_SETTINGS
and the output index value. Except for the parameter types this call
@@ -4886,13 +6751,13 @@ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_pout_info( MBG_DEV_HANDLE dh,
(i.e. the number of programmable outputs on the board) is not 0, and the
output index value must be in the range 0..::RECEIVER_INFO::n_prg_out.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::POUT_SETTINGS_IDX structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_gps_all_pout_info()
- @see mbg_set_gps_pout_settings()
+ * @see ::mbg_get_gps_all_pout_info
+ * @see ::mbg_set_gps_pout_settings
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_pout_settings_idx( MBG_DEV_HANDLE dh,
const POUT_SETTINGS_IDX *p )
@@ -4914,7 +6779,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_pout_settings_idx( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Write the configuration for a single programmable pulse output
+ * @brief Write the configuration for a single programmable pulse output
The ::POUT_SETTINGS structure does not contain the index of the
programmable output to be configured, so the index must explicitely
@@ -4925,14 +6790,14 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_pout_settings_idx( MBG_DEV_HANDLE dh,
(i.e. the number of programmable outputs on the board) is not 0, and the
output index value must be in the range 0..::RECEIVER_INFO::n_prg_out.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::POUT_SETTINGS structure to be written
@param idx Index of the programmable pulse output to be configured (starting from 0 ).
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_gps_all_pout_info()
- @see mbg_set_gps_pout_settings_idx()
+ * @see ::mbg_get_gps_all_pout_info
+ * @see ::mbg_set_gps_pout_settings_idx
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_pout_settings( MBG_DEV_HANDLE dh,
const POUT_SETTINGS *p, int idx )
@@ -4950,17 +6815,17 @@ _MBG_API_ATTR int _MBG_API mbg_set_gps_pout_settings( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Read a device's IRQ status information.
+ * @brief Read a device's IRQ status information.
IRQ status information includes flags indicating whether IRQs are
actually enabled, and whether IRQ support by a card is possibly
unsafe due to the firmware and interface chip version.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_IRQ_STAT_INFO variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- */
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_get_irq_stat_info( MBG_DEV_HANDLE dh, PCPS_IRQ_STAT_INFO *p )
{
#if defined( _MBGIOCTL_H )
@@ -4979,42 +6844,20 @@ _MBG_API_ATTR int _MBG_API mbg_get_irq_stat_info( MBG_DEV_HANDLE dh, PCPS_IRQ_ST
/*HDR*/
/**
- @brief Check if a device provides simple LAN interface API calls.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_lan_if_info()
- @see mbg_get_ip4_state()
- @see mbg_get_ip4_settings()
- @see mbg_set_ip4_settings()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_lan_intf( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_lan_intf, IOCTL_DEV_HAS_LAN_INTF, p );
-
-} // mbg_dev_has_lan_intf
-
-
-
-/*HDR*/
-/**
- @brief Read LAN interface information from a device.
+ * @brief Read LAN interface information from a device.
The macro _pcps_has_lan_intf() or the API call mbg_dev_has_lan_intf()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::LAN_IF_INFO variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_lan_intf()
- @see mbg_get_ip4_state()
- @see mbg_get_ip4_settings()
- @see mbg_set_ip4_settings()
+ * @see ::mbg_dev_has_lan_intf
+ * @see ::mbg_get_ip4_state
+ * @see ::mbg_get_ip4_settings
+ * @see ::mbg_set_ip4_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_lan_if_info( MBG_DEV_HANDLE dh, LAN_IF_INFO *p )
{
@@ -5031,20 +6874,20 @@ _MBG_API_ATTR int _MBG_API mbg_get_lan_if_info( MBG_DEV_HANDLE dh, LAN_IF_INFO *
/*HDR*/
/**
- @brief Read LAN IPv4 state from a device.
+ * @brief Read LAN IPv4 state from a device.
The macro _pcps_has_lan_intf() or the API call mbg_dev_has_lan_intf()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::IP4_SETTINGS variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_lan_intf()
- @see mbg_get_lan_if_info()
- @see mbg_get_ip4_settings()
- @see mbg_set_ip4_settings()
+ * @see ::mbg_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_settings
+ * @see ::mbg_set_ip4_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_ip4_state( MBG_DEV_HANDLE dh, IP4_SETTINGS *p )
{
@@ -5061,20 +6904,20 @@ _MBG_API_ATTR int _MBG_API mbg_get_ip4_state( MBG_DEV_HANDLE dh, IP4_SETTINGS *p
/*HDR*/
/**
- @brief Read LAN IPv4 settings from a device.
+ * @brief Read LAN IPv4 settings from a device.
The macro _pcps_has_lan_intf() or the API call mbg_dev_has_lan_intf()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::IP4_SETTINGS variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_lan_intf()
- @see mbg_get_lan_if_info()
- @see mbg_get_ip4_state()
- @see mbg_set_ip4_settings()
+ * @see ::mbg_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_state
+ * @see ::mbg_set_ip4_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_ip4_settings( MBG_DEV_HANDLE dh, IP4_SETTINGS *p )
{
@@ -5091,19 +6934,19 @@ _MBG_API_ATTR int _MBG_API mbg_get_ip4_settings( MBG_DEV_HANDLE dh, IP4_SETTINGS
/*HDR*/
/**
- @brief Write LAN IPv4 settings to a device.
+ * @brief Write LAN IPv4 settings to a device.
The macro _pcps_has_lan_intf() or the API call mbg_dev_has_lan_intf()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p ::IP4_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_lan_intf()
- @see mbg_get_lan_if_info()
- @see mbg_get_ip4_settings()
+ * @see ::mbg_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_settings
*/
_MBG_API_ATTR int _MBG_API mbg_set_ip4_settings( MBG_DEV_HANDLE dh,
const IP4_SETTINGS *p )
@@ -5125,67 +6968,21 @@ _MBG_API_ATTR int _MBG_API mbg_set_ip4_settings( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Check if a device provides PTP configuration/status calls.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_state
- @see mbg_get_ptp_cfg_info
- @see mbg_set_ptp_cfg_settings
- @see mbg_dev_has_ptp_unicast
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_ptp( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_ptp, IOCTL_DEV_HAS_PTP, p );
-
-} // mbg_dev_has_ptp
-
-
-
-/*HDR*/
-/**
- @brief Check if a device provides PTP unicast feature/configuration.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_uc_master_cfg_limits
- @see mbg_get_all_ptp_uc_master_info
- @see mbg_set_ptp_uc_master_settings_idx
- @see mbg_get_ptp_state
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_ptp_unicast( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_ri_cond( dh, _pcps_has_ri_ptp_unicast, IOCTL_DEV_HAS_PTP_UNICAST, p );
-
-} // mbg_dev_has_ptp_unicast
-
-
-
-/*HDR*/
-/**
- @brief Read PTP/IEEE1588 status from a device.
+ * @brief Read PTP/IEEE1588 status from a device.
The macro _pcps_has_ptp() or the API call mbg_dev_has_ptp()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PTP_STATE variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_cfg_info
- @see mbg_set_ptp_cfg_settings
- @see mbg_dev_has_ptp_unicast
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_cfg_info
+ * @see ::mbg_set_ptp_cfg_settings
+ * @see ::mbg_dev_has_ptp_unicast
*/
_MBG_API_ATTR int _MBG_API mbg_get_ptp_state( MBG_DEV_HANDLE dh, PTP_STATE *p )
{
@@ -5202,21 +6999,21 @@ _MBG_API_ATTR int _MBG_API mbg_get_ptp_state( MBG_DEV_HANDLE dh, PTP_STATE *p )
/*HDR*/
/**
- @brief Read PTP/IEEE1588 config info and current settings from a device.
+ * @brief Read PTP/IEEE1588 config info and current settings from a device.
The macro _pcps_has_ptp() or the API call mbg_dev_has_ptp()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PTP_CFG_INFO variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_state
- @see mbg_set_ptp_cfg_settings
- @see mbg_dev_has_ptp_unicast
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_state
+ * @see ::mbg_set_ptp_cfg_settings
+ * @see ::mbg_dev_has_ptp_unicast
*/
_MBG_API_ATTR int _MBG_API mbg_get_ptp_cfg_info( MBG_DEV_HANDLE dh, PTP_CFG_INFO *p )
{
@@ -5233,21 +7030,21 @@ _MBG_API_ATTR int _MBG_API mbg_get_ptp_cfg_info( MBG_DEV_HANDLE dh, PTP_CFG_INFO
/*HDR*/
/**
- @brief Write PTP/IEEE1588 configuration settings to a device.
+ * @brief Write PTP/IEEE1588 configuration settings to a device.
The macro _pcps_has_ptp() or the API call mbg_dev_has_ptp()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p ::PTP_CFG_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_state
- @see mbg_get_ptp_cfg_info
- @see mbg_dev_has_ptp_unicast
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_state
+ * @see ::mbg_get_ptp_cfg_info
+ * @see ::mbg_dev_has_ptp_unicast
*/
_MBG_API_ATTR int _MBG_API mbg_set_ptp_cfg_settings( MBG_DEV_HANDLE dh,
const PTP_CFG_SETTINGS *p )
@@ -5269,28 +7066,29 @@ _MBG_API_ATTR int _MBG_API mbg_set_ptp_cfg_settings( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Read PTP/IEEE1588 unicast master configuration limits from a device.
+ * @brief Read PTP/IEEE1588 unicast master configuration limits from a device.
The macro _pcps_has_ri_ptp_unicast() or the API call mbg_dev_has_ptp_unicast()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PTP_UC_MASTER_CFG_LIMITS variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp_unicast
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_all_ptp_uc_master_info
- @see mbg_set_ptp_uc_master_settings_idx
- @see mbg_get_ptp_state
+ * @see ::mbg_dev_has_ptp_unicast
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_all_ptp_uc_master_info
+ * @see ::mbg_set_ptp_uc_master_settings_idx
+ * @see ::mbg_get_ptp_state
*/
_MBG_API_ATTR int _MBG_API mbg_get_ptp_uc_master_cfg_limits( MBG_DEV_HANDLE dh, PTP_UC_MASTER_CFG_LIMITS *p )
{
_mbgdevio_vars();
_mbgdevio_read_gps_var_chk( dh, PC_GPS_PTP_UC_MASTER_CFG_LIMITS,
IOCTL_PTP_UC_MASTER_CFG_LIMITS, p,
- _pcps_has_ri_ptp_unicast( &dh->ri ) );
+ _pcps_has_ri_ptp_unicast( _ri_addr( dh ) ) );
+
_mbg_swab_ptp_uc_master_cfg_limits( p );
return _mbgdevio_ret_val;
@@ -5300,7 +7098,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_ptp_uc_master_cfg_limits( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Read PTP Unicast master settings and configuration options.
+ * @brief Read PTP Unicast master settings and configuration options.
The function mbg_setup_receiver_info() must have been called before,
and the returned ::RECEIVER_INFO structure passed to this function.
@@ -5310,17 +7108,17 @@ _MBG_API_ATTR int _MBG_API mbg_get_ptp_uc_master_cfg_limits( MBG_DEV_HANDLE dh,
The array passed to this function to receive the returned data
must be able to hold at least ::RECEIVER_INFO::n_prg_out elements.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pii Pointer to a an array of ::PTP_UC_MASTER_INFO_IDX structures to be filled up
@param p_umsl Pointer to a ::PTP_UC_MASTER_CFG_LIMITS structure returned by mbg_get_ptp_uc_master_cfg_limits()
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp_unicast
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_uc_master_cfg_limits
- @see mbg_set_ptp_uc_master_settings_idx
- @see mbg_get_ptp_state
+ * @see ::mbg_dev_has_ptp_unicast
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_uc_master_cfg_limits
+ * @see ::mbg_set_ptp_uc_master_settings_idx
+ * @see ::mbg_get_ptp_state
*/
_MBG_API_ATTR int _MBG_API mbg_get_all_ptp_uc_master_info( MBG_DEV_HANDLE dh,
PTP_UC_MASTER_INFO_IDX pii[],
@@ -5338,11 +7136,11 @@ _MBG_API_ATTR int _MBG_API mbg_get_all_ptp_uc_master_info( MBG_DEV_HANDLE dh,
rc = _mbgdevio_gen_read_gps( dh, PC_GPS_ALL_PTP_UC_MASTER_INFO, pii,
p_umsl->n_supp_master * sizeof( pii[0] ) );
else
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV );
+ return MBG_ERR_NOT_SUPP_BY_DEV;
#endif
#if defined( MBG_ARCH_BIG_ENDIAN )
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
{
int i;
for ( i = 0; i < p_umsl->n_supp_master; i++ )
@@ -5361,21 +7159,21 @@ _MBG_API_ATTR int _MBG_API mbg_get_all_ptp_uc_master_info( MBG_DEV_HANDLE dh,
/*HDR*/
/**
- @brief Write PTP/IEEE1588 unicast configuration settings to a device.
+ * @brief Write PTP/IEEE1588 unicast configuration settings to a device.
The macro _pcps_has_ri_ptp_unicast() or the API call mbg_dev_has_ptp_unicast()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p ::PTP_UC_MASTER_SETTINGS_IDX structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp_unicast
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_uc_master_cfg_limits
- @see mbg_get_all_ptp_uc_master_info
- @see mbg_get_ptp_state
+ * @see ::mbg_dev_has_ptp_unicast
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_uc_master_cfg_limits
+ * @see ::mbg_get_all_ptp_uc_master_info
+ * @see ::mbg_get_ptp_state
*/
_MBG_API_ATTR int _MBG_API mbg_set_ptp_uc_master_settings_idx( MBG_DEV_HANDLE dh,
const PTP_UC_MASTER_SETTINGS_IDX *p )
@@ -5397,30 +7195,30 @@ _MBG_API_ATTR int _MBG_API mbg_set_ptp_uc_master_settings_idx( MBG_DEV_HANDLE dh
/*HDR*/
/**
- @brief Read both system time and associated device time from the kernel driver.
-
- The kernel driver reads the current system time plus a HR time structure
- from a card immediately after each other. The returned info structure also
- contains some cycles counts to be able to determine the execution times
- required to read those time stamps.
-
- The advantage of this call compared to mbg_get_time_info_tstamp() is
- that this call also returns the card's status. On the other hand, reading
- the HR time from the card may block e.g. if another application accesses
- the board.
-
- This call makes a mbg_get_hr_time_cycles() call internally so the macro
- _pcps_has_hr_time() or the API call mbg_dev_has_hr_time() can be
- used to check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_TIME_INFO_HRT variable to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_hr_time()
- @see mbg_get_time_info_tstamp()
- */
+ * @brief Read both system time and associated device time from the kernel driver
+ *
+ * The kernel driver reads the current system time plus a HR time structure
+ * from a card immediately after each other. The returned info structure also
+ * contains some cycles counts to be able to determine the execution times
+ * required to read those time stamps.
+ *
+ * The advantage of this call compared to ::mbg_get_time_info_tstamp is
+ * that this call also returns the card's status. On the other hand, reading
+ * the HR time from the card may block e.g. if another application accesses
+ * the board.
+ *
+ * This call makes a ::mbg_get_hr_time_cycles call internally so the API call
+ * ::mbg_dev_has_hr_time can be used to check whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_TIME_INFO_HRT structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_hr_time
+ * @see ::mbg_get_time_info_tstamp
+ */
_MBG_API_ATTR int _MBG_API mbg_get_time_info_hrt( MBG_DEV_HANDLE dh, MBG_TIME_INFO_HRT *p )
{
#if defined( _MBGIOCTL_H )
@@ -5430,7 +7228,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_time_info_hrt( MBG_DEV_HANDLE dh, MBG_TIME_IN
_mbg_swab_mbg_time_info_hrt( p );
return _mbgdevio_ret_val;
#else
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_ON_OS );
+ return MBG_ERR_NOT_SUPP_ON_OS;
#endif
} // mbg_get_time_info_hrt
@@ -5439,21 +7237,21 @@ _MBG_API_ATTR int _MBG_API mbg_get_time_info_hrt( MBG_DEV_HANDLE dh, MBG_TIME_IN
/*HDR*/
/**
- @brief Read both system time and associated device timestamp from the kernel driver.
-
- This call is similar to mbg_get_time_info_hrt() except that a
- mbg_get_fast_hr_timestamp_cycles() call is made internally, so the macro
- _pcps_has_fast_hr_timestamp() or the API call mbg_dev_has_fast_hr_timestamp()
- can be used to check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_TIME_INFO_TSTAMP variable to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_fast_hr_timestamp()
- @see mbg_get_time_info_hrt()
- */
+ * @brief Read both system time and associated device timestamp from the kernel driver.
+ *
+ * This call is similar to ::mbg_get_time_info_hrt except that a
+ * ::mbg_get_fast_hr_timestamp_cycles call is made internally, so the
+ * API call ::mbg_dev_has_fast_hr_timestamp can be used to check
+ * whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_TIME_INFO_TSTAMP structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_fast_hr_timestamp
+ * @see ::mbg_get_time_info_hrt
+ */
_MBG_API_ATTR int _MBG_API mbg_get_time_info_tstamp( MBG_DEV_HANDLE dh, MBG_TIME_INFO_TSTAMP *p )
{
#if defined( _MBGIOCTL_H )
@@ -5463,7 +7261,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_time_info_tstamp( MBG_DEV_HANDLE dh, MBG_TIME
_mbg_swab_mbg_time_info_tstamp( p );
return _mbgdevio_ret_val;
#else
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_ON_OS );
+ return MBG_ERR_NOT_SUPP_ON_OS;
#endif
} // mbg_get_time_info_tstamp
@@ -5472,388 +7270,805 @@ _MBG_API_ATTR int _MBG_API mbg_get_time_info_tstamp( MBG_DEV_HANDLE dh, MBG_TIME
/*HDR*/
/**
- @brief Check if a device supports demodulation of the DCF77 PZF code.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_corr_info()
- @see mbg_dev_has_tr_distance()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_pzf( MBG_DEV_HANDLE dh, int *p )
+ * @brief Read PZF correlation info from a device
+ *
+ * The the API call ::mbg_dev_has_corr_info checks
+ * whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::CORR_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_pzf
+ * @see ::mbg_dev_has_corr_info
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_corr_info( MBG_DEV_HANDLE dh, CORR_INFO *p )
{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_pzf, IOCTL_DEV_HAS_PZF, p );
+ _mbgdevio_vars();
+ _mbgdevio_read_var_chk( dh, PCPS_GET_CORR_INFO,
+ IOCTL_GET_CORR_INFO, p,
+ _pcps_ddev_has_corr_info( dh ) );
+ _mbg_swab_corr_info( p );
+ return _mbgdevio_ret_val;
-} // mbg_dev_has_pzf
+} // mbg_get_corr_info
/*HDR*/
/**
- @brief Check if a device supports reading correlation info.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_pzf()
- @see mbg_get_corr_info()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_corr_info( MBG_DEV_HANDLE dh, int *p )
+ * @brief Read configurable "distance from transmitter" parameter from a device.
+ *
+ * The distance from transmitter parameter is used to compensate
+ * the RF propagation delay, mostly with long wave receivers.
+ *
+ * The API call ::mbg_dev_has_tr_distance checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::TR_DISTANCE variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_pzf
+ * @see ::mbg_dev_has_tr_distance
+ * @see ::mbg_set_tr_distance
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_tr_distance( MBG_DEV_HANDLE dh, TR_DISTANCE *p )
{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_corr_info, IOCTL_DEV_HAS_CORR_INFO, p );
+ _mbgdevio_vars();
+ _mbgdevio_read_var_chk( dh, PCPS_GET_TR_DISTANCE,
+ IOCTL_GET_TR_DISTANCE, p,
+ _pcps_ddev_has_tr_distance( dh ) );
+ _mbg_swab_tr_distance( p );
+ return _mbgdevio_ret_val;
-} // mbg_dev_has_corr_info
+} // mbg_get_tr_distance
/*HDR*/
/**
- @brief Check if a device supports configurable distance from transmitter.
+ * @brief Write configurable "distance from transmitter" parameter to a device.
+ *
+ * The distance from transmitter parameter is used to compensate
+ * the RF propagation delay, mostly with long wave receivers.
+ *
+ * The API call ::mbg_dev_has_tr_distance checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] p Pointer to a ::TR_DISTANCE variable to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_pzf
+ * @see ::mbg_dev_has_tr_distance
+ * @see ::mbg_get_tr_distance
+ */
+_MBG_API_ATTR int _MBG_API mbg_set_tr_distance( MBG_DEV_HANDLE dh, const TR_DISTANCE *p )
+{
+ _mbgdevio_vars();
+ #if defined( MBG_ARCH_BIG_ENDIAN )
+ TR_DISTANCE tmp = *p;
+ _mbg_swab_tr_distance( &tmp );
+ p = &tmp;
+ #endif
+ _mbgdevio_write_var_chk( dh, PCPS_SET_TR_DISTANCE, IOCTL_SET_TR_DISTANCE,
+ p, _pcps_ddev_has_tr_distance( dh ) );
+ return _mbgdevio_ret_val;
- The distance from transmitter parameter is used to compensate
- the RF propagation delay, mostly with long wave receivers.
+} // mbg_set_tr_distance
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- @see mbg_dev_has_pzf()
- @see mbg_get_tr_distance()
- @see mbg_set_tr_distance()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_tr_distance( MBG_DEV_HANDLE dh, int *p )
+/*HDR*/
+/**
+ * @brief Read a debug status word from a device
+ *
+ * This is mainly supported by IRIG timecode receiver cards, and the status
+ * word is intended to provide more detailed information why a card might not
+ * synchronize to the incoming timecode signal.
+ *
+ * See ::MBG_DEBUG_STATUS and related definitions for details.
+ *
+ * The API call ::mbg_dev_has_debug_status checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_DEBUG_STATUS variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_debug_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_debug_status( MBG_DEV_HANDLE dh, MBG_DEBUG_STATUS *p )
{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_tr_distance, IOCTL_DEV_HAS_TR_DISTANCE, p );
+ _mbgdevio_vars();
+ _mbgdevio_read_var_chk( dh, PCPS_GET_DEBUG_STATUS,
+ IOCTL_GET_DEBUG_STATUS, p,
+ _pcps_ddev_has_debug_status( dh ) );
+ _mbg_swab_debug_status( p );
+ return _mbgdevio_ret_val;
-} // mbg_dev_has_tr_distance
+} // mbg_get_debug_status
/*HDR*/
/**
- @brief Read PZF correlation info from a device.
+ * @brief Clear the device's on-board event log.
+ *
+ * The API call ::mbg_dev_has_evt_log checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_evt_log
+ * @see ::mbg_get_num_evt_log_entries
+ * @see ::mbg_get_first_evt_log_entry
+ * @see ::mbg_get_next_evt_log_entry
+ */
+_MBG_API_ATTR int _MBG_API mbg_clr_evt_log( MBG_DEV_HANDLE dh )
+{
+ _mbgdevio_vars();
+ _mbgdevio_write_cmd_chk( dh, PCPS_CLR_EVT_LOG, IOCTL_CLR_EVT_LOG,
+ _pcps_ddev_has_evt_log( dh ) );
+ return _mbgdevio_ret_val;
- The macro _pcps_has_corr_info() or the API call mbg_dev_has_corr_info()
- check whether this call is supported by a device.
+} // mbg_clr_evt_log
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::CORR_INFO variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- @see mbg_dev_has_pzf()
- @see mbg_dev_has_corr_info()
- */
-_MBG_API_ATTR int _MBG_API mbg_get_corr_info( MBG_DEV_HANDLE dh, CORR_INFO *p )
+/*HDR*/
+/**
+ * @brief Read details about a device's on-board event log buffer.
+ *
+ * The returned ::MBG_NUM_EVT_LOG_ENTRIES structure tells how many event log
+ * entries which can be saved on the board, and how many entries actually
+ * have been saved.
+ *
+ * The API call ::mbg_dev_has_evt_log checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_NUM_EVT_LOG_ENTRIES variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_evt_log
+ * @see ::mbg_clr_evt_log
+ * @see ::mbg_get_first_evt_log_entry
+ * @see ::mbg_get_next_evt_log_entry
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_num_evt_log_entries( MBG_DEV_HANDLE dh, MBG_NUM_EVT_LOG_ENTRIES *p )
{
_mbgdevio_vars();
- _mbgdevio_read_var_chk( dh, PCPS_GET_CORR_INFO,
- IOCTL_GET_CORR_INFO, p,
- _pcps_ddev_has_corr_info( dh ) );
- _mbg_swab_corr_info( p );
+ _mbgdevio_read_var_chk( dh, PCPS_NUM_EVT_LOG_ENTRIES,
+ IOCTL_GET_NUM_EVT_LOG_ENTRIES, p,
+ _pcps_ddev_has_evt_log( dh ) );
+ _mbg_swab_mbg_num_evt_log_entries( p );
return _mbgdevio_ret_val;
-} // mbg_get_corr_info
+} // mbg_get_num_evt_log_entries
/*HDR*/
/**
- @brief Read configurable "distance from transmitter" parameter from a device.
-
- The distance from transmitter parameter is used to compensate
- the RF propagation delay, mostly with long wave receivers.
+ * @brief Read the first (oldest) event log entry from a device.
+ *
+ * @note Subsequent reads should be made using ::mbg_get_next_evt_log_entry.
+ *
+ * The API call ::mbg_dev_has_evt_log checks whether this call
+ * is supported by a device.
+ *
+ * If no (more) event log entry is available on the device then
+ * the returned MBG_EVT_LOG_ENTRY::code is MBG_EVT_ID_NONE.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_EVT_LOG_ENTRY variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_evt_log
+ * @see ::mbg_clr_evt_log
+ * @see ::mbg_get_num_evt_log_entries
+ * @see ::mbg_get_next_evt_log_entry
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_first_evt_log_entry( MBG_DEV_HANDLE dh, MBG_EVT_LOG_ENTRY *p )
+{
+ _mbgdevio_vars();
+ _mbgdevio_read_var_chk( dh, PCPS_FIRST_EVT_LOG_ENTRY,
+ IOCTL_GET_FIRST_EVT_LOG_ENTRY, p,
+ _pcps_ddev_has_evt_log( dh ) );
+ _mbg_swab_mbg_evt_log_entry( p );
+ return _mbgdevio_ret_val;
- The macro _pcps_has_tr_distance() or the API call mbg_dev_has_tr_distance()
- check whether this call is supported by a device.
+} // mbg_get_first_evt_log_entry
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::TR_DISTANCE variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- @see mbg_dev_has_pzf()
- @see mbg_dev_has_tr_distance()
- @see mbg_set_tr_distance()
- */
-_MBG_API_ATTR int _MBG_API mbg_get_tr_distance( MBG_DEV_HANDLE dh, TR_DISTANCE *p )
+/*HDR*/
+/**
+ * @brief Read the next event log entry from a device.
+ *
+ * @note The first read should be made using ::mbg_get_first_evt_log_entry
+ * to set the on-board read index to the oldest entry.
+ *
+ * The API call ::mbg_dev_has_evt_log checks whether this call
+ * is supported by a device.
+ *
+ * If no (more) event log entry is available on the device then
+ * the returned MBG_EVT_LOG_ENTRY::code is MBG_EVT_ID_NONE.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_EVT_LOG_ENTRY variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_evt_log
+ * @see ::mbg_clr_evt_log
+ * @see ::mbg_get_num_evt_log_entries
+ * @see ::mbg_get_first_evt_log_entry
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_next_evt_log_entry( MBG_DEV_HANDLE dh, MBG_EVT_LOG_ENTRY *p )
{
_mbgdevio_vars();
- _mbgdevio_read_var_chk( dh, PCPS_GET_TR_DISTANCE,
- IOCTL_GET_TR_DISTANCE, p,
- _pcps_ddev_has_tr_distance( dh ) );
- _mbg_swab_tr_distance( p );
+ _mbgdevio_read_var_chk( dh, PCPS_NEXT_EVT_LOG_ENTRY,
+ IOCTL_GET_NEXT_EVT_LOG_ENTRY, p,
+ _pcps_ddev_has_evt_log( dh ) );
+ _mbg_swab_mbg_evt_log_entry( p );
return _mbgdevio_ret_val;
-} // mbg_get_tr_distance
+} // mbg_get_next_evt_log_entry
/*HDR*/
/**
- @brief Write configurable "distance from transmitter" parameter to a device.
-
- The distance from transmitter parameter is used to compensate
- the RF propagation delay, mostly with long wave receivers.
+ * @brief Read the current GNSS mode info including current settings.
+ *
+ * The ::MBG_GNSS_MODE_INFO structure tells which GNSS systems are supported
+ * by a device, and also includes the settings currently in effect.
+ *
+ * The API call mbg_dev_is_gnss() can be used to check whether this call
+ * is supported by a device. See also the notes for mbg_dev_is_gnss().
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p_mi Pointer to a ::MBG_GNSS_MODE_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_set_gps_gnss_mode_settings
+ * @see ::mbg_get_gps_all_gnss_sat_info
+ * @see ::mbg_dev_is_gnss
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_gps_gnss_mode_info( MBG_DEV_HANDLE dh, MBG_GNSS_MODE_INFO *p_mi )
+{
+ _mbgdevio_vars();
+ _mbgdevio_read_gps_var_chk( dh, PC_GPS_GNSS_MODE,
+ IOCTL_GET_GNSS_MODE_INFO, p_mi,
+ _pcps_ddev_is_gnss( dh ) );
+ _mbg_swab_mbg_gnss_mode_info( p_mi );
+ return _mbgdevio_ret_val;
- The macro _pcps_has_tr_distance() or the API call mbg_dev_has_tr_distance()
- check whether this call is supported by a device.
+} // mbg_get_gps_gnss_mode_info
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::TR_DISTANCE variable to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- @see mbg_dev_has_pzf()
- @see mbg_dev_has_tr_distance()
- @see mbg_get_tr_distance()
- */
-_MBG_API_ATTR int _MBG_API mbg_set_tr_distance( MBG_DEV_HANDLE dh, const TR_DISTANCE *p )
+/*HDR*/
+/**
+ * @brief Write the GNSS mode configuration to a device.
+ *
+ * The ::MBG_GNSS_MODE_SETTINGS structure determines to configure the
+ * GNSS settings for a device, i.e. which satellite systems have to be used.
+ *
+ * The function mbg_get_gps_gnss_mode_info() should have been called before
+ * to determine which GNSS settings are supported by the device.
+ *
+ * The API call mbg_dev_is_gnss() can be used to check whether these API calls
+ * are supported by a device. See also the notes for mbg_dev_is_gnss().
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p_ms Pointer to a ::MBG_GNSS_MODE_SETTINGS structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_gnss_mode_info
+ * @see ::mbg_get_gps_all_gnss_sat_info
+ * @see ::mbg_dev_is_gnss
+ */
+_MBG_API_ATTR int _MBG_API mbg_set_gps_gnss_mode_settings( MBG_DEV_HANDLE dh,
+ const MBG_GNSS_MODE_SETTINGS *p_ms )
{
_mbgdevio_vars();
#if defined( MBG_ARCH_BIG_ENDIAN )
- TR_DISTANCE tmp = *p;
- _mbg_swab_tr_distance( &tmp );
- p = &tmp;
+ MBG_GNSS_MODE_SETTINGS tmp = *p_ms;
+ _mbg_swab_mbg_gnss_mode_settings( &tmp );
+ p_ms = &tmp;
#endif
- _mbgdevio_write_var_chk( dh, PCPS_SET_TR_DISTANCE, IOCTL_SET_TR_DISTANCE,
- p, _pcps_ddev_has_tr_distance( dh ) );
+ _mbgdevio_write_gps_var_chk( dh, PC_GPS_GNSS_MODE,
+ IOCTL_SET_GNSS_MODE_SETTINGS, p_ms,
+ _pcps_ddev_is_gnss( dh ) );
return _mbgdevio_ret_val;
-} // mbg_set_tr_distance
+} // mbg_set_gps_gnss_mode_settings
/*HDR*/
/**
- @brief Check if a device provides a debug status word to be read.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_debug_status()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_debug_status( MBG_DEV_HANDLE dh, int *p )
+ * @brief Read a ::GNSS_SAT_INFO_IDX array of satellite status information.
+ *
+ * The function ::mbg_get_gps_gnss_mode_info must have been called before,
+ * and the returned ::MBG_GNSS_MODE_INFO structure be passed to this function.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] gsii Pointer to a an array of satellite info structures to be filled up
+ * @param[in] p_mi Pointer to a ::MBG_GNSS_MODE_INFO structure returned by ::mbg_get_gps_gnss_mode_info
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_gnss_mode_info
+ * @see ::mbg_set_gps_gnss_mode_settings
+ * @see ::mbg_dev_is_gnss
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_gps_all_gnss_sat_info( MBG_DEV_HANDLE dh,
+ GNSS_SAT_INFO_IDX gsii[],
+ const MBG_GNSS_MODE_INFO *p_mi )
{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_debug_status, IOCTL_DEV_HAS_DEBUG_STATUS, p );
-
-} // mbg_dev_has_debug_status
-
+ _mbgdevio_vars();
+ int n_supp = num_bits_set( p_mi->supp_gnss_types );
-/*HDR*/
-/**
- @brief Read a debug status word from a device.
+ #if _MBG_SUPP_VAR_ACC_SIZE
+ _mbgdevio_read_gps_chk( dh, PC_GPS_ALL_GNSS_SAT_INFO,
+ IOCTL_GET_ALL_GNSS_SAT_INFO, gsii,
+ n_supp * sizeof( gsii[0] ),
+ _pcps_ddev_is_gnss( dh ) );
+ #else
+ rc = _mbgdevio_gen_read_gps( dh, PC_GPS_ALL_GNSS_SAT_INFO, gsii,
+ n_supp * sizeof( gsii[0] ) );
+ #endif
- This is mainly supported by IRIG timecode receiver cards, and the status
- word is intended to provide more detailed information why a card might not
- synchronize to the incoming timecode signal.
+ #if defined( MBG_ARCH_BIG_ENDIAN )
+ if ( mbg_rc_is_success( rc ) )
+ {
+ int i;
+ for ( i = 0; i < n_supp; i++ )
+ {
+ GNSS_SAT_INFO_IDX *p = &gsii[i];
+ _mbg_swab_gnss_sat_info_idx( p );
+ }
+ }
+ #endif
- See ::MBG_DEBUG_STATUS and related definitions for details.
+ return _mbgdevio_ret_val;
- The macro _pcps_has_debug_status() or the API call mbg_dev_has_debug_status()
- check whether this call is supported by a device.
+} // mbg_get_gps_all_gnss_sat_info
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_DEBUG_STATUS variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- @see mbg_dev_has_debug_status()
- */
-_MBG_API_ATTR int _MBG_API mbg_get_debug_status( MBG_DEV_HANDLE dh, MBG_DEBUG_STATUS *p )
+/*HDR*/
+/**
+ * @brief Read common GPIO configuration limits
+ *
+ * The API call ::mbg_dev_has_gpio checks whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] p A ::MBG_GPIO_CFG_LIMITS structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_gpio
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ * @see ::mbg_get_gps_all_gpio_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_gpio_cfg_limits( MBG_DEV_HANDLE dh, MBG_GPIO_CFG_LIMITS *p )
{
_mbgdevio_vars();
- _mbgdevio_read_var_chk( dh, PCPS_GET_DEBUG_STATUS,
- IOCTL_GET_DEBUG_STATUS, p,
- _pcps_ddev_has_debug_status( dh ) );
- _mbg_swab_debug_status( p );
+ _mbgdevio_read_gps_var_chk( dh, PC_GPS_GPIO_CFG_LIMITS,
+ IOCTL_GET_GPIO_CFG_LIMITS, p,
+ _pcps_ddev_has_gpio( dh ) );
+ _mbg_swab_mbg_gpio_cfg_limits( p );
+
return _mbgdevio_ret_val;
-} // mbg_get_debug_status
+} // mbg_get_gpio_cfg_limits
/*HDR*/
/**
- @brief Check if a device provides an on-board event log.
+ * @brief Get all GPIO settings and capabilities.
+ *
+ * The API call ::mbg_dev_has_gpio checks whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] gii An array of ::MBG_GPIO_STATUS_IDX structures to be filled up
+ * @param[in] p_gcl Pointer to a ::MBG_GPIO_CFG_LIMITS structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_gpio
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ * @see ::mbg_get_gps_all_gpio_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_gps_all_gpio_info( MBG_DEV_HANDLE dh,
+ MBG_GPIO_INFO_IDX gii[],
+ const MBG_GPIO_CFG_LIMITS *p_gcl )
+{
+ _mbgdevio_vars();
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
+ uint32_t n_supp = p_gcl->num_io;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ #if _MBG_SUPP_VAR_ACC_SIZE
+ _mbgdevio_read_gps_chk( dh, PC_GPS_ALL_GPIO_INFO,
+ IOCTL_GET_ALL_GPIO_INFO, gii,
+ n_supp * sizeof( gii[0] ),
+ _pcps_ddev_has_gpio( dh ) );
+ #else
+ rc = _mbgdevio_gen_read_gps( dh, PC_GPS_ALL_GPIO_INFO, gii,
+ n_supp * sizeof( gii[0] ) );
+ #endif
- @see mbg_clr_evt_log()
- @see mbg_get_num_evt_log_entries()
- @see mbg_get_first_evt_log_entry()
- @see mbg_get_next_evt_log_entry()
-*/
-_MBG_API_ATTR int _MBG_API mbg_dev_has_evt_log( MBG_DEV_HANDLE dh, int *p )
-{
- _mbgdevio_query_cond( dh, _pcps_ddev_has_evt_log, IOCTL_DEV_HAS_EVT_LOG, p );
+ #if defined( MBG_ARCH_BIG_ENDIAN )
+ if ( mbg_rc_is_success( rc ) )
+ {
+ int i;
+ for ( i = 0; i < n_supp; i++ )
+ {
+ MBG_GPIO_INFO_IDX *p = &gii[i];
+ _mbg_swab_mbg_gpio_info_idx( p );
+ }
+ }
+ #endif
-} // mbg_dev_has_evt_log
+ return _mbgdevio_ret_val;
+
+} // mbg_get_gps_all_gpio_info
/*HDR*/
/**
- @brief Clear the card's on-board event log.
+ * @brief Write the configuration for a single GPIO port to a device
+ *
+ * The ::MBG_GPIO_SETTINGS_IDX structure contains both the ::MBG_GPIO_SETTINGS
+ * and the port index value.
+ *
+ * The API call ::mbg_dev_has_gpio checks whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] p Pointer to a ::MBG_GPIO_SETTINGS_IDX structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_gpio
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ * @see ::mbg_get_gps_all_gpio_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_set_gps_gpio_settings_idx( MBG_DEV_HANDLE dh,
+ const MBG_GPIO_SETTINGS_IDX *p )
+{
+ _mbgdevio_vars();
+ #if defined( MBG_ARCH_BIG_ENDIAN )
+ MBG_GPIO_SETTINGS_IDX tmp = *p;
+ _mbg_swab_mbg_gpio_settings_idx( &tmp );
+ p = &tmp;
+ #endif
+ _mbgdevio_write_gps_var_chk( dh, PC_GPS_GPIO_SETTINGS_IDX,
+ IOCTL_SET_GPIO_SETTINGS_IDX, p,
+ _pcps_ddev_has_gpio( dh ) );
+ return _mbgdevio_ret_val;
- The macro _pcps_has_evt_log() or the API call mbg_dev_has_evt_log()
- check whether this call is supported by a device.
+} // mbg_set_gps_gpio_settings_idx
- @param dh Valid handle to a Meinberg device
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- @see mbg_dev_has_evt_log()
- @see mbg_get_num_evt_log_entries()
- @see mbg_get_first_evt_log_entry()
- @see mbg_get_next_evt_log_entry()
- */
-_MBG_API_ATTR int _MBG_API mbg_clr_evt_log( MBG_DEV_HANDLE dh )
+/*HDR*/
+/**
+ * @brief Read the status of all GPIO signal ports
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] gsi An array of ::MBG_GPIO_STATUS_IDX structures to be filled up
+ * @param[in] p_gcl Pointer to a ::MBG_GPIO_CFG_LIMITS structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_gpio
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_gps_all_gpio_status( MBG_DEV_HANDLE dh,
+ MBG_GPIO_STATUS_IDX gsi[],
+ const MBG_GPIO_CFG_LIMITS *p_gcl )
{
_mbgdevio_vars();
- _mbgdevio_write_cmd_chk( dh, PCPS_CLR_EVT_LOG, IOCTL_CLR_EVT_LOG,
- _pcps_ddev_has_evt_log( dh ) );
- return _mbgdevio_ret_val;
-} // mbg_clr_evt_log
+ uint32_t n_supp;
+ if ( !( p_gcl->flags & MBG_GPIO_CFG_LIMIT_FLAG_MASK_STATUS_SUPP ) )
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+ n_supp = p_gcl->num_io;
-/*HDR*/
-/**
- @brief Read details about a device's on-board event log buffer.
+ #if _MBG_SUPP_VAR_ACC_SIZE
+ _mbgdevio_read_gps_chk( dh, PC_GPS_ALL_GPIO_STATUS,
+ IOCTL_GET_ALL_GPIO_STATUS, gsi,
+ n_supp * sizeof( gsi[0] ),
+ _pcps_ddev_has_gpio( dh ) );
+ #else
+ rc = _mbgdevio_gen_read_gps( dh, PC_GPS_ALL_GPIO_STATUS, gsi,
+ n_supp * sizeof( gsi[0] ) );
+ #endif
- The returned ::MBG_NUM_EVT_LOG_ENTRIES structure tells how many event log
- entries which can be saved on the board, and how many entries actually
- have been saved.
+ #if defined( MBG_ARCH_BIG_ENDIAN )
+ if ( mbg_rc_is_success( rc ) )
+ {
+ int i;
+ for ( i = 0; i < n_supp; i++ )
+ {
+ MBG_GPIO_STATUS_IDX *p = &gsi[i];
+ _mbg_swab_mbg_gpio_status_idx( p );
+ }
+ }
+ #endif
- The macro _pcps_has_evt_log() or the API call mbg_dev_has_evt_log()
- check whether this call is supported by a device.
+ return _mbgdevio_ret_val;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_NUM_EVT_LOG_ENTRIES variable to be filled up
+} // mbg_get_gps_all_gpio_status
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- @see mbg_dev_has_evt_log()
- @see mbg_clr_evt_log()
- @see mbg_get_first_evt_log_entry()
- @see mbg_get_next_evt_log_entry()
- */
-_MBG_API_ATTR int _MBG_API mbg_get_num_evt_log_entries( MBG_DEV_HANDLE dh, MBG_NUM_EVT_LOG_ENTRIES *p )
+
+/*HDR*/
+/**
+ * @brief
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] *p A ::XMULTI_REF_INSTANCES structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_set_gps_xmr_settings_idx
+ * @see ::mbg_get_xmr_holdover_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_xmr_instances( MBG_DEV_HANDLE dh, XMULTI_REF_INSTANCES *p )
{
_mbgdevio_vars();
- _mbgdevio_read_var_chk( dh, PCPS_NUM_EVT_LOG_ENTRIES,
- IOCTL_GET_NUM_EVT_LOG_ENTRIES, p,
- _pcps_ddev_has_evt_log( dh ) );
- _mbg_swab_mbg_num_evt_log_entries( p );
+ _mbgdevio_read_gps_var_chk( dh, PC_GPS_XMR_INSTANCES,
+ IOCTL_GET_XMR_INSTANCES, p,
+ _pcps_ddev_has_xmr( dh ) );
+ _mbg_swab_xmulti_ref_instances( p );
return _mbgdevio_ret_val;
-} // mbg_get_num_evt_log_entries
+} // mbg_get_xmr_instances
/*HDR*/
/**
- @brief Read the first (oldest) event log entry from a device.
-
- @note Subsequent reads should be made using mbg_get_next_evt_log_entry().
-
- The macro _pcps_has_evt_log() or the API call mbg_dev_has_evt_log()
- check whether this call is supported by a device.
+ * @brief Read the status of all XMR sources
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] xmrsi An array of ::XMULTI_REF_STATUS_IDX structures to be filled up
+ * @param[in] p_xmri Pointer to a ::XMULTI_REF_INSTANCES structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_set_gps_xmr_settings_idx
+ * @see ::mbg_get_xmr_holdover_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_gps_all_xmr_status( MBG_DEV_HANDLE dh,
+ XMULTI_REF_STATUS_IDX xmrsi[],
+ const XMULTI_REF_INSTANCES *p_xmri )
+{
+ _mbgdevio_vars();
- If no (more) event log entry is available on the device then
- the returned MBG_EVT_LOG_ENTRY::code is MBG_EVT_ID_NONE.
+ int n_supp = p_xmri->n_xmr_settings;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_EVT_LOG_ENTRY variable to be filled up
+ #if _MBG_SUPP_VAR_ACC_SIZE
+ _mbgdevio_read_gps_chk( dh, PC_GPS_ALL_XMR_STATUS,
+ IOCTL_GET_ALL_XMR_STATUS, xmrsi,
+ n_supp * sizeof( xmrsi[0] ),
+ _pcps_ddev_has_xmr( dh ) );
+ #else
+ rc = _mbgdevio_gen_read_gps( dh, PC_GPS_ALL_XMR_STATUS, xmrsi,
+ n_supp * sizeof( xmrsi[0] ) );
+ #endif
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ #if defined( MBG_ARCH_BIG_ENDIAN )
+ if ( mbg_rc_is_success( rc ) )
+ {
+ int i;
+ for ( i = 0; i < n_supp; i++ )
+ {
+ XMULTI_REF_STATUS_IDX *p = &xmrsi[i];
+ _mbg_swab_xmulti_ref_status_idx( p );
+ }
+ }
+ #endif
- @see mbg_dev_has_evt_log()
- @see mbg_clr_evt_log()
- @see mbg_get_num_evt_log_entries()
- @see mbg_get_next_evt_log_entry()
- */
-_MBG_API_ATTR int _MBG_API mbg_get_first_evt_log_entry( MBG_DEV_HANDLE dh, MBG_EVT_LOG_ENTRY *p )
-{
- _mbgdevio_vars();
- _mbgdevio_read_var_chk( dh, PCPS_FIRST_EVT_LOG_ENTRY,
- IOCTL_GET_FIRST_EVT_LOG_ENTRY, p,
- _pcps_ddev_has_evt_log( dh ) );
- _mbg_swab_mbg_evt_log_entry( p );
return _mbgdevio_ret_val;
-} // mbg_get_first_evt_log_entry
+} // mbg_get_gps_all_xmr_status
/*HDR*/
/**
- @brief Read the next event log entry from a device.
+ * @brief Read all XMR settings and capabilities
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] xmrii An array of ::XMULTI_REF_INFO_IDX structures to be filled up
+ * @param[in] p_xmri Pointer to a ::XMULTI_REF_INSTANCES structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_set_gps_xmr_settings_idx
+ * @see ::mbg_get_xmr_holdover_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_gps_all_xmr_info( MBG_DEV_HANDLE dh,
+ XMULTI_REF_INFO_IDX xmrii[],
+ const XMULTI_REF_INSTANCES *p_xmri )
+{
+ _mbgdevio_vars();
- @note The first read should be made using mbg_get_first_evt_log_entry()
- to set the on-board read index to the oldest entry.
+ int n_supp = p_xmri->n_xmr_settings;
- The macro _pcps_has_evt_log() or the API call mbg_dev_has_evt_log()
- check whether this call is supported by a device.
+ #if _MBG_SUPP_VAR_ACC_SIZE
+ _mbgdevio_read_gps_chk( dh, PC_GPS_ALL_XMR_INFO,
+ IOCTL_GET_ALL_XMR_INFO, xmrii,
+ n_supp * sizeof( xmrii[0] ),
+ _pcps_ddev_has_xmr( dh ) );
+ #else
+ rc = _mbgdevio_gen_read_gps( dh, PC_GPS_ALL_XMR_INFO, xmrii,
+ n_supp * sizeof( xmrii[0] ) );
+ #endif
+
+ #if defined( MBG_ARCH_BIG_ENDIAN )
+ if ( mbg_rc_is_success( rc ) )
+ {
+ int i;
+ for ( i = 0; i < n_supp; i++ )
+ {
+ XMULTI_REF_INFO_IDX *p = &xmrii[i];
+ _mbg_swab_xmulti_ref_info_idx( p );
+ }
+ }
+ #endif
- If no (more) event log entry is available on the device then
- the returned MBG_EVT_LOG_ENTRY::code is MBG_EVT_ID_NONE.
+ return _mbgdevio_ret_val;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_EVT_LOG_ENTRY variable to be filled up
+} // mbg_get_gps_all_xmr_info
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- @see mbg_dev_has_evt_log()
- @see mbg_clr_evt_log()
- @see mbg_get_num_evt_log_entries()
- @see mbg_get_first_evt_log_entry()
- */
-_MBG_API_ATTR int _MBG_API mbg_get_next_evt_log_entry( MBG_DEV_HANDLE dh, MBG_EVT_LOG_ENTRY *p )
+
+/*HDR*/
+/**
+ * @brief Write a single XMR setting to a device
+ *
+ * The ::XMULTI_REF_SETTINGS_IDX structure contains both the ::XMULTI_REF_SETTINGS
+ * and the index value.
+ *
+ * The macro ::_pcps_has_ri_xmr or the API call ::mbg_dev_has_xmr
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::XMULTI_REF_SETTINGS_IDX structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_get_xmr_holdover_status
+ */
+_MBG_API_ATTR int _MBG_API mbg_set_gps_xmr_settings_idx( MBG_DEV_HANDLE dh,
+ const XMULTI_REF_SETTINGS_IDX *p )
{
_mbgdevio_vars();
- _mbgdevio_read_var_chk( dh, PCPS_NEXT_EVT_LOG_ENTRY,
- IOCTL_GET_NEXT_EVT_LOG_ENTRY, p,
- _pcps_ddev_has_evt_log( dh ) );
- _mbg_swab_mbg_evt_log_entry( p );
+ #if defined( MBG_ARCH_BIG_ENDIAN )
+ XMULTI_REF_SETTINGS_IDX tmp = *p;
+ _mbg_swab_xmr_settings_idx( &tmp );
+ p = &tmp;
+ #endif
+ _mbgdevio_write_gps_var_chk( dh, PC_GPS_XMR_SETTINGS_IDX,
+ IOCTL_SET_XMR_SETTINGS_IDX, p,
+ _pcps_ddev_has_xmr( dh ) );
return _mbgdevio_ret_val;
-} // mbg_get_next_evt_log_entry
+} // mbg_set_gps_xmr_settings_idx
/*HDR*/
/**
- @brief Read the CPU affinity of a process.
+ * @brief Read the current XMR holdover interval from a device
+ *
+ * Read a ::SYNTH structure containing the configuration of an optional
+ * on-board programmable frequency synthesizer.
+ *
+ * The macro ::_pcps_has_ri_xmr or the API call ::mbg_dev_has_xmr
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::XMR_HOLDOVER_INTV structure to be filled up
+ * @param[in] p_xmri Pointer to a ::XMULTI_REF_INSTANCES structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_set_gps_xmr_settings_idx
+ */
+_MBG_API_ATTR int _MBG_API mbg_get_xmr_holdover_status( MBG_DEV_HANDLE dh, XMR_HOLDOVER_STATUS *p,
+ const XMULTI_REF_INSTANCES *p_xmri )
+{
+ _mbgdevio_vars();
- This means on which of the available CPUs or CPU cores the process can be executed.
+ if ( !( p_xmri->flags & XMRIF_MSK_HOLDOVER_STATUS_SUPP ) )
+ return MBG_ERR_NOT_SUPP_BY_DEV;
- @param pid The process ID.
- @param *p Pointer to a ::MBG_CPU_SET variable which contains a mask of CPUs.
+ _mbgdevio_read_gps_var_chk( dh, PC_GPS_XMR_HOLDOVER_STATUS,
+ IOCTL_GET_XMR_HOLDOVER_STATUS, p,
+ _pcps_ddev_has_xmr( dh ) );
+ _mbg_swab_xmr_holdover_status( p );
- @return ::MBG_SUCCESS or error code returned by the system call.
+ return _mbgdevio_ret_val;
- @see mbg_set_process_affinity()
- @see mbg_set_current_process_affinity_to_cpu()
- */
+} // mbg_get_xmr_holdover_status
+
+
+
+/*HDR*/
+/**
+ * @brief Read the CPU affinity of a process.
+ *
+ * This means on which of the available CPUs or CPU cores the process can be executed.
+ *
+ * @param pid The process ID.
+ * @param *p Pointer to a ::MBG_CPU_SET variable which contains a mask of CPUs.
+ *
+ * @return ::MBG_SUCCESS or error code returned by the system call.
+ *
+ * @see ::mbg_set_process_affinity
+ * @see ::mbg_set_current_process_affinity_to_cpu
+ */
_MBG_API_ATTR int _MBG_API mbg_get_process_affinity( MBG_PROCESS_ID pid, MBG_CPU_SET *p )
{
#if defined( MBG_TGT_LINUX )
- return sched_getaffinity( pid, sizeof( *p ), p );
+ if ( sched_getaffinity( pid, sizeof( *p ), p ) == 0 ) // success
+ return MBG_SUCCESS;
+
+ return mbg_get_last_error( NULL );
#elif defined( MBG_TGT_WIN32 )
@@ -5863,7 +8078,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_process_affinity( MBG_PROCESS_ID pid, MBG_CPU
#else
- return -1;
+ return MBG_ERR_NOT_SUPP_ON_OS;
#endif
@@ -5873,7 +8088,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_process_affinity( MBG_PROCESS_ID pid, MBG_CPU
/*HDR*/
/**
- @brief Set the CPU affinity of a process.
+ * @brief Set the CPU affinity of a process.
This determines on which of the available CPUs
the process is allowed to be executed.
@@ -5881,10 +8096,10 @@ _MBG_API_ATTR int _MBG_API mbg_get_process_affinity( MBG_PROCESS_ID pid, MBG_CPU
@param pid The process ID.
@param *p Pointer to a ::MBG_CPU_SET variable which contains a mask of CPUs.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_get_process_affinity()
- @see mbg_set_current_process_affinity_to_cpu()
+ * @see ::mbg_get_process_affinity
+ * @see ::mbg_set_current_process_affinity_to_cpu
*/
_MBG_API_ATTR int _MBG_API mbg_set_process_affinity( MBG_PROCESS_ID pid, MBG_CPU_SET *p )
{
@@ -5898,7 +8113,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_process_affinity( MBG_PROCESS_ID pid, MBG_CPU
#else
- return -1;
+ return MBG_ERR_NOT_SUPP_ON_OS;
#endif
@@ -5908,16 +8123,16 @@ _MBG_API_ATTR int _MBG_API mbg_set_process_affinity( MBG_PROCESS_ID pid, MBG_CPU
/*HDR*/
/**
- @brief Set the CPU affinity of a process for a single CPU only.
+ * @brief Set the CPU affinity of a process for a single CPU only.
This means the process may only be executed on that single CPU.
@param cpu_num The number of the CPU.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_get_process_affinity()
- @see mbg_set_process_affinity()
+ * @see ::mbg_get_process_affinity
+ * @see ::mbg_set_process_affinity
*/
_MBG_API_ATTR int _MBG_API mbg_set_current_process_affinity_to_cpu( int cpu_num )
{
@@ -5936,7 +8151,7 @@ _MBG_API_ATTR int _MBG_API mbg_set_current_process_affinity_to_cpu( int cpu_num
/*HDR*/
/**
- @brief Create a new execution thread for the current process.
+ * @brief Create a new execution thread for the current process.
This function is only implemented for targets which support threads.
@@ -5944,14 +8159,14 @@ _MBG_API_ATTR int _MBG_API mbg_set_current_process_affinity_to_cpu( int cpu_num
@param fnc The name of the thread function to be started.
@param arg A generic argument passed to the thread function.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_thread_stop()
- @see mbg_thread_sleep_interruptible()
- @see mbg_thread_set_affinity()
+ * @see ::mbg_thread_stop
+ * @see ::mbg_thread_sleep_interruptible
+ * @see ::mbg_thread_set_affinity
*/
_MBG_API_ATTR int _MBG_API mbg_thread_create( MBG_THREAD_INFO *p_ti,
- MBG_THREAD_FNC_RET_VAL (MBG_THREAD_FNC_ATTR *fnc)(void *), void *arg )
+ MBG_THREAD_FNC fnc, void *arg )
{
#if defined( MBG_TGT_LINUX )
@@ -5994,18 +8209,18 @@ fail:
/*HDR*/
/**
- @brief Stop a thread which has been created by mbg_thread_create().
+ * @brief Stop a thread which has been created by mbg_thread_create().
Wait until the thread has finished and release all resources.
This function is only implemented for targets which support threads.
@param p_ti Pointer to a ::MBG_THREAD_INFO structure associated with the thread.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_thread_create()
- @see mbg_thread_sleep_interruptible()
- @see mbg_thread_set_affinity()
+ * @see ::mbg_thread_create
+ * @see ::mbg_thread_sleep_interruptible
+ * @see ::mbg_thread_set_affinity
*/
_MBG_API_ATTR int _MBG_API mbg_thread_stop( MBG_THREAD_INFO *p_ti )
{
@@ -6043,7 +8258,7 @@ _MBG_API_ATTR int _MBG_API mbg_thread_stop( MBG_THREAD_INFO *p_ti )
/*HDR*/
/**
- @brief Let the current thread sleep for a certain interval.
+ * @brief Let the current thread sleep for a certain interval.
The sleep is interrupted if a signal is received indicating
the thread should terminate.
@@ -6052,13 +8267,13 @@ _MBG_API_ATTR int _MBG_API mbg_thread_stop( MBG_THREAD_INFO *p_ti )
@param p_ti Pointer to a ::MBG_THREAD_INFO structure associated with the thread.
@param sleep_ms The number of milliseconds to sleep
- @return 0 if the sleep interval has expired normally
+ * @return 0 if the sleep interval has expired normally
1 if a signal to terminate has been received
<0 if an error has occurred
- @see mbg_thread_create()
- @see mbg_thread_stop()
- @see mbg_thread_set_affinity()
+ * @see ::mbg_thread_create
+ * @see ::mbg_thread_stop
+ * @see ::mbg_thread_set_affinity
*/
_MBG_API_ATTR int _MBG_API mbg_thread_sleep_interruptible( MBG_THREAD_INFO *p_ti, ulong sleep_ms )
{
@@ -6096,7 +8311,7 @@ _MBG_API_ATTR int _MBG_API mbg_thread_sleep_interruptible( MBG_THREAD_INFO *p_ti
/*HDR*/
/**
- @brief Set the CPU affinity of a single thread.
+ * @brief Set the CPU affinity of a single thread.
This determines on which of the available CPUs the thread
is allowed to be executed.
@@ -6106,11 +8321,11 @@ _MBG_API_ATTR int _MBG_API mbg_thread_sleep_interruptible( MBG_THREAD_INFO *p_ti
@param p_ti Pointer to a ::MBG_THREAD_INFO structure associated with the thread.
@param *p Pointer to a ::MBG_CPU_SET variable which contains a mask of CPUs.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_thread_create()
- @see mbg_thread_stop()
- @see mbg_thread_sleep_interruptible()
+ * @see ::mbg_thread_create
+ * @see ::mbg_thread_stop
+ * @see ::mbg_thread_sleep_interruptible
*/
_MBG_API_ATTR int _MBG_API mbg_thread_set_affinity( MBG_THREAD_INFO *p_ti, MBG_CPU_SET *p )
{
@@ -6138,7 +8353,7 @@ _MBG_API_ATTR int _MBG_API mbg_thread_set_affinity( MBG_THREAD_INFO *p_ti, MBG_C
static /*HDR*/
/**
- @brief A thread function implementing polling of a device at regular intervals.
+ * @brief A thread function implementing polling of a device at regular intervals.
At each polling a high resolution time stamp and an associated cycles count
are saved which can be used to retrieve extrapolated time stamps using the
@@ -6156,13 +8371,13 @@ static /*HDR*/
@param *p_void Pointer to a ::MBG_POLL_THREAD_INFO structure.
- @return ::MBG_SUCCESS or nothing, depending on the taget system.
+ * @return ::MBG_SUCCESS or nothing, depending on the taget system.
- @see mbg_xhrt_poll_thread_create()
- @see mbg_xhrt_poll_thread_stop()
- @see mbg_get_xhrt_time_as_pcps_hr_time()
- @see mbg_get_xhrt_time_as_filetime()
- @see mbg_get_xhrt_cycles_frequency()
+ * @see ::mbg_xhrt_poll_thread_create
+ * @see ::mbg_xhrt_poll_thread_stop
+ * @see ::mbg_get_xhrt_time_as_pcps_hr_time
+ * @see ::mbg_get_xhrt_time_as_filetime
+ * @see ::mbg_get_xhrt_cycles_frequency
*/
MBG_THREAD_FNC_RET_VAL MBG_THREAD_FNC_ATTR mbg_xhrt_poll_thread_fnc( void *p_void )
{
@@ -6181,7 +8396,7 @@ MBG_THREAD_FNC_RET_VAL MBG_THREAD_FNC_ATTR mbg_xhrt_poll_thread_fnc( void *p_voi
int rc = mbg_get_hr_time_cycles( p->dh, &xhrt_vars.htc );
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
{
xhrt_vars.pcps_hr_tstamp64 = pcps_time_stamp_to_uint64( &xhrt_vars.htc.t.tstamp );
@@ -6193,7 +8408,7 @@ MBG_THREAD_FNC_RET_VAL MBG_THREAD_FNC_ATTR mbg_xhrt_poll_thread_fnc( void *p_voi
_mbg_crit_sect_enter( &p->crit_sect );
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
{
p->vars = xhrt_vars;
p->prv_vars = prv_xhrt_vars;
@@ -6209,7 +8424,7 @@ MBG_THREAD_FNC_RET_VAL MBG_THREAD_FNC_ATTR mbg_xhrt_poll_thread_fnc( void *p_voi
_mbg_crit_sect_leave( &p->crit_sect );
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
prv_xhrt_vars = xhrt_vars;
if ( mbg_thread_sleep_interruptible( &p_pti->ti, sleep_ms ) )
@@ -6224,7 +8439,7 @@ MBG_THREAD_FNC_RET_VAL MBG_THREAD_FNC_ATTR mbg_xhrt_poll_thread_fnc( void *p_voi
/*HDR*/
/**
- @brief Set up a ::MBG_POLL_THREAD_INFO structure and start a new thread.
+ * @brief Set up a ::MBG_POLL_THREAD_INFO structure and start a new thread.
The new thread runs the mbg_xhrt_poll_thread_fnc() function.
@@ -6236,24 +8451,22 @@ MBG_THREAD_FNC_RET_VAL MBG_THREAD_FNC_ATTR mbg_xhrt_poll_thread_fnc( void *p_voi
@param sleep_ms the sleep interval for the poll thread function in ms.
If this parameter is 0 then the default sleep interval is used.
- @return ::MBG_SUCCESS on success,
+ * @return ::MBG_SUCCESS on success,
::MBG_ERR_NOT_SUPP_BY_DEV if the device to poll does not support HR time
else the result of mbg_thread_create()
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_stop()
- @see mbg_get_xhrt_time_as_pcps_hr_time()
- @see mbg_get_xhrt_time_as_filetime()
- @see mbg_get_xhrt_cycles_frequency()
+ * @see ::mbg_xhrt_poll_thread_stop
+ * @see ::mbg_get_xhrt_time_as_pcps_hr_time
+ * @see ::mbg_get_xhrt_time_as_filetime
+ * @see ::mbg_get_xhrt_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_xhrt_poll_thread_create( MBG_POLL_THREAD_INFO *p_pti, MBG_DEV_HANDLE dh,
MBG_PC_CYCLES_FREQUENCY freq_hz, int sleep_ms )
{
- int has_hr_time;
- int rc = mbg_dev_has_hr_time( dh, &has_hr_time );
+ int rc = mbg_chk_dev_has_hr_time( dh );
- if ( ( rc != MBG_SUCCESS ) || !has_hr_time )
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV );
+ if ( mbg_rc_is_error( rc ) )
+ return rc;
memset( p_pti, 0, sizeof( *p_pti ) );
@@ -6272,25 +8485,24 @@ _MBG_API_ATTR int _MBG_API mbg_xhrt_poll_thread_create( MBG_POLL_THREAD_INFO *p_
/*HDR*/
/**
- @brief Stop a polling thread started by mbg_xhrt_poll_thread_create().
+ * @brief Stop a polling thread started by mbg_xhrt_poll_thread_create().
This call also releases all associated resources.
@param *p_pti Pointer to a ::MBG_POLL_THREAD_INFO structure.
- @return the result of mbg_thread_stop()
+ * @return the result of mbg_thread_stop()
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_create()
- @see mbg_get_xhrt_time_as_pcps_hr_time()
- @see mbg_get_xhrt_time_as_filetime()
- @see mbg_get_xhrt_cycles_frequency()
+ * @see ::mbg_xhrt_poll_thread_create
+ * @see ::mbg_get_xhrt_time_as_pcps_hr_time
+ * @see ::mbg_get_xhrt_time_as_filetime
+ * @see ::mbg_get_xhrt_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_xhrt_poll_thread_stop( MBG_POLL_THREAD_INFO *p_pti )
{
int rc = mbg_thread_stop( &p_pti->ti );
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
_mbg_crit_sect_destroy( &p_pti->xhrt_info.crit_sect );
return rc;
@@ -6337,7 +8549,7 @@ int mbg_get_xhrt_data( MBG_XHRT_INFO *p, uint64_t *tstamp, MBG_XHRT_VARS *vars )
/*HDR*/
/**
- @brief Retrieve an extrapolated time stamp in PCPS_HR_TIME format.
+ * @brief Retrieve an extrapolated time stamp in PCPS_HR_TIME format.
The time stamp is extrapolated using the system's current cycles counter value
and a time stamp plus associated cycles counter value saved by the polling thread.
@@ -6348,13 +8560,12 @@ int mbg_get_xhrt_data( MBG_XHRT_INFO *p, uint64_t *tstamp, MBG_XHRT_VARS *vars )
@param *p Pointer to a ::MBG_XHRT_INFO structure used to retrieve data from the polling thread.
@param *p_hrt Pointer to a ::PCPS_HR_TIME structure to be filled up.
- @return MBG_SUCCESS or another return value from the polling thread's IOCTL call.
+ * @return MBG_SUCCESS or another return value from the polling thread's IOCTL call.
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_create()
- @see mbg_xhrt_poll_thread_stop()
- @see mbg_get_xhrt_time_as_filetime()
- @see mbg_get_xhrt_cycles_frequency()
+ * @see ::mbg_xhrt_poll_thread_create
+ * @see ::mbg_xhrt_poll_thread_stop
+ * @see ::mbg_get_xhrt_time_as_filetime
+ * @see ::mbg_get_xhrt_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_get_xhrt_time_as_pcps_hr_time( MBG_XHRT_INFO *p, PCPS_HR_TIME *p_hrt )
{
@@ -6384,7 +8595,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_xhrt_time_as_pcps_hr_time( MBG_XHRT_INFO *p,
/*HDR*/
/**
- @brief Retrieve an extrapolated time stamp in FILETIME format.
+ * @brief Retrieve an extrapolated time stamp in FILETIME format.
The time stamp is extrapolated using the system's current cycles counter value
and a time stamp plus associated cycles counter value saved by the polling thread.
@@ -6394,15 +8605,14 @@ _MBG_API_ATTR int _MBG_API mbg_get_xhrt_time_as_pcps_hr_time( MBG_XHRT_INFO *p,
implemented under Windows.
@param *p Pointer to a ::MBG_XHRT_INFO structure used to retrieve data from the polling thread.
- @param *p_ft Pointer to a ::FILETIME structure to be filled up.
+ @param *p_ft Pointer to a FILETIME structure to be filled up.
- @return MBG_SUCCESS or another return value from the polling thread's IOCTL call.
+ * @return MBG_SUCCESS or another return value from the polling thread's IOCTL call.
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_create()
- @see mbg_xhrt_poll_thread_stop()
- @see mbg_get_xhrt_time_as_pcps_hr_time()
- @see mbg_get_xhrt_cycles_frequency()
+ * @see ::mbg_xhrt_poll_thread_create
+ * @see ::mbg_xhrt_poll_thread_stop
+ * @see ::mbg_get_xhrt_time_as_pcps_hr_time
+ * @see ::mbg_get_xhrt_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_get_xhrt_time_as_filetime( MBG_XHRT_INFO *p, FILETIME *p_ft )
{
@@ -6426,7 +8636,7 @@ _MBG_API_ATTR int _MBG_API mbg_get_xhrt_time_as_filetime( MBG_XHRT_INFO *p, FILE
/*HDR*/
/**
- @brief Retrieve the frequency of the system's cycles counter.
+ * @brief Retrieve the frequency of the system's cycles counter.
The frequency is determined by the device polling thread.
See mbg_xhrt_poll_thread_fnc() for details and limitations.
@@ -6435,13 +8645,12 @@ _MBG_API_ATTR int _MBG_API mbg_get_xhrt_time_as_filetime( MBG_XHRT_INFO *p, FILE
@param *p Pointer to a ::MBG_XHRT_INFO structure used to retrieve data from the polling thread.
@param *p_freq_hz Pointer to a ::MBG_PC_CYCLES_FREQUENCY variable in which the frequency is returned.
- @return a status code from the polling thread: MBG_SUCCESS or an IOCTL error code.
+ * @return a status code from the polling thread: MBG_SUCCESS or an IOCTL error code.
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_create()
- @see mbg_xhrt_poll_thread_stop()
- @see mbg_get_xhrt_time_as_pcps_hr_time()
- @see mbg_get_xhrt_time_as_filetime()
+ * @see ::mbg_xhrt_poll_thread_create
+ * @see ::mbg_xhrt_poll_thread_stop
+ * @see ::mbg_get_xhrt_time_as_pcps_hr_time
+ * @see ::mbg_get_xhrt_time_as_filetime
*/
_MBG_API_ATTR int _MBG_API mbg_get_xhrt_cycles_frequency( MBG_XHRT_INFO *p, MBG_PC_CYCLES_FREQUENCY *p_freq_hz )
{
@@ -6466,16 +8675,16 @@ _MBG_API_ATTR int _MBG_API mbg_get_xhrt_cycles_frequency( MBG_XHRT_INFO *p, MBG_
/*HDR*/
/**
- @brief Retrieve the default system's cycles counter frequency from the kernel driver.
+ * @brief Retrieve the default system's cycles counter frequency from the kernel driver.
This API call can be used on systems which don't provide this information in user space.
@param dh handle of the device to which the IOCTL call is sent.
@param *p Pointer of a ::MBG_PC_CYCLES_FREQUENCY variable to be filled up.
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_default_cycles_frequency()
+ * @see ::mbg_get_default_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_get_default_cycles_frequency_from_dev( MBG_DEV_HANDLE dh, MBG_PC_CYCLES_FREQUENCY *p )
{
@@ -6483,20 +8692,15 @@ _MBG_API_ATTR int _MBG_API mbg_get_default_cycles_frequency_from_dev( MBG_DEV_HA
_mbgdevio_vars();
rc = _mbgdevio_read_var( dh, -1, IOCTL_GET_CYCLES_FREQUENCY, p );
// native endianess, no need to swap bytes
- if ( rc != MBG_SUCCESS )
+ if ( mbg_rc_is_error( rc ) )
*p = 0;
#if defined( MBG_TGT_LINUX )
if ( *p == 0 )
{
- int has_hr_time = 0;
-
- rc = mbg_dev_has_hr_time( dh, &has_hr_time );
-
- if ( rc != MBG_SUCCESS )
- goto done;
+ rc = mbg_chk_dev_has_hr_time( dh );
- if ( has_hr_time )
+ if ( mbg_rc_is_success( rc ) )
{
PCPS_HR_TIME_CYCLES htc1;
PCPS_HR_TIME_CYCLES htc2;
@@ -6505,14 +8709,14 @@ _MBG_API_ATTR int _MBG_API mbg_get_default_cycles_frequency_from_dev( MBG_DEV_HA
rc = mbg_get_hr_time_cycles( dh, &htc1 );
- if ( rc != MBG_SUCCESS )
+ if ( mbg_rc_is_error( rc ) )
goto done;
sleep( 1 );
rc = mbg_get_hr_time_cycles( dh, &htc2 );
- if ( rc != MBG_SUCCESS )
+ if ( mbg_rc_is_error( rc ) )
goto done;
// compute cycles frequency from delta htc
@@ -6530,7 +8734,7 @@ done:
*p = 0;
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_ON_OS );
+ return MBG_ERR_NOT_SUPP_ON_OS;
#endif
@@ -6548,7 +8752,7 @@ done:
@return the default cycles counter frequency in Hz, or 0 if the value is not available.
- @see mbg_get_default_cycles_frequency_from_dev()
+ * @see ::mbg_get_default_cycles_frequency_from_dev
*/
_MBG_API_ATTR MBG_PC_CYCLES_FREQUENCY _MBG_API mbg_get_default_cycles_frequency( void )
{
diff --git a/mbglib/common/mbgdevio.h b/mbglib/common/mbgdevio.h
index 8455bd8..70f5ef5 100755
--- a/mbglib/common/mbgdevio.h
+++ b/mbglib/common/mbgdevio.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgdevio.h 1.40 2012/10/02 18:40:30 martin REL_M $
+ * $Id: mbgdevio.h 1.41.1.30.1.11 2017/03/17 12:00:39 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,7 +10,76 @@
*
* -----------------------------------------------------------------------
* $Log: mbgdevio.h $
- * Revision 1.40 2012/10/02 18:40:30 martin
+ * Revision 1.41.1.30.1.11 2017/03/17 12:00:39 martin
+ * Include cfg_hlp.h due to moved definitions.
+ * Revision 1.41.1.30.1.10 2017/02/01 16:23:19 martin
+ * Updated function prototypes.
+ * Revision 1.41.1.30.1.9 2016/10/20 11:25:21 martin
+ * Improved handling of ioctl error codes for POSIX.
+ * Revision 1.41.1.30.1.8 2016/10/17 17:12:44 martin
+ * Account for MBG_ERROR_CODES returned by the ioctl function under Linux.
+ * Revision 1.41.1.30.1.7 2016/09/23 08:54:21 martin
+ * Exclude mbg_chk_tstamp64_leap_sec() for BC builds for now.
+ * Revision 1.41.1.30.1.6 2016/09/22 08:30:40Z martin
+ * Fixed compiler warning under Windows x64.
+ * Revision 1.41.1.30.1.5 2016/08/11 07:48:12Z martin
+ * Fixed a compiler warning.
+ * Revision 1.41.1.30.1.4 2016/08/10 12:27:03Z martin
+ * Check for MBG_TGT_POSIX instead of MBG_TGT_UNIX.
+ * Revision 1.41.1.30.1.3 2016/07/22 09:57:11 martin
+ * Quieted some compiler warninges.
+ * Revision 1.41.1.30.1.2 2016/07/15 14:09:48 martin
+ * Use functions from new module timeutil.
+ * Revision 1.41.1.30.1.1 2016/05/30 15:07:32 martin
+ * *** empty log message ***
+ * Revision 1.41.1.30 2015/12/02 17:05:03 martin
+ * *** empty log message ***
+ * Revision 1.41.1.29 2015/12/02 16:36:19 martin
+ * *** empty log message ***
+ * Revision 1.41.1.28 2015/12/01 17:01:03 martin
+ * *** empty log message ***
+ * Revision 1.41.1.27 2015/12/01 13:58:33 martin
+ * *** empty log message ***
+ * Revision 1.41.1.26 2015/10/27 16:22:24 martin
+ * Older defines N_SUPP_DEV, PCPS_MAX_DDEVS, and MBG_MAX_DEVICES
+ * have been obsoleted by new defines N_SUPP_DEV_BUS, N_SUPP_DEV_EXT,
+ * and N_SUPP_DEV_TOTAL.
+ * Revision 1.41.1.25 2015/10/21 11:21:54 martin
+ * *** empty log message ***
+ * Revision 1.41.1.24 2015/10/20 16:02:04 martin
+ * *** empty log message ***
+ * Revision 1.41.1.23 2015/10/20 15:19:27 martin
+ * *** empty log message ***
+ * Revision 1.41.1.22 2015/10/19 16:42:18 martin
+ * *** empty log message ***
+ * Revision 1.41.1.21 2015/08/27 16:24:16 martin
+ * Revision 1.41.1.20 2014/11/19 16:33:31 martin
+ * Revision 1.41.1.19 2014/11/19 16:15:45 martin
+ * Revision 1.41.1.18 2014/11/19 16:03:09 martin
+ * Revision 1.41.1.17 2014/10/29 16:27:16 martin
+ * Revision 1.41.1.16 2014/07/18 11:01:41 martin
+ * Revision 1.41.1.15 2014/07/16 15:19:57 martin
+ * Revision 1.41.1.14 2014/07/16 13:06:39 martin
+ * Revision 1.41.1.13 2014/07/14 15:42:49 martin
+ * Revision 1.41.1.12 2014/06/26 12:24:22 martin
+ * Revision 1.41.1.11 2014/05/27 08:22:20Z martin
+ * Revision 1.41.1.10 2014/05/26 16:02:13 martin
+ * Revision 1.41.1.9 2014/05/23 12:40:19 martin
+ * Revision 1.41.1.8 2014/05/23 09:24:08 martin
+ * gpio and xmr functions.
+ * Revision 1.41.1.7 2014/04/23 15:42:59 martin
+ * Revision 1.41.1.6 2014/04/22 15:27:47 martin
+ * Revision 1.41.1.5 2014/04/22 13:29:18 martin
+ * Revision 1.41.1.4 2014/03/28 10:23:24 martin
+ * Revision 1.41.1.3 2014/03/05 10:38:29 martin
+ * Windows.h is now included in mbg_tgt.h.
+ * Revision 1.41.1.2 2014/01/31 14:45:35Z martin
+ * Revision 1.41.1.1 2013/12/12 11:24:16 martin
+ * Revision 1.41 2013/09/26 08:54:54 martin
+ * Defined thread function type MBG_THREAD_FNC.
+ * Defined check-if-supported function type MBG_CHK_SUPP_FNC.
+ * Updated function prototypes.
+ * Revision 1.40 2012/10/02 18:40:30Z martin
* There are some g++ versions which fail to compile source code using
* the macros provided by Linux to define IOCTL codes. If only the API
* functions are called by an application then the IOCTL codes aren't
@@ -33,7 +102,7 @@
* Made xhrt leap second check an inline function.
* Fixed macro to avoid compiler warning.
* Revision 1.39 2009/12/15 15:34:59Z daniel
- * Support reading the raw IRIG data bits for firmware versions
+ * Support reading the raw IRIG data bits for firmware versions
* which support this feature.
* Revision 1.38.1.2 2009/12/10 09:58:53Z daniel
* Revision 1.38.1.1 2009/12/10 09:45:29Z daniel
@@ -129,11 +198,11 @@
* PC high resolution timer cycles.
* Updated function prototypes.
* Revision 1.9 2003/06/19 08:50:05Z martin
- * Definition of MBGDEVIO_VERSION number to allow DLL
+ * Definition of MBGDEVIO_VERSION number to allow DLL
* API version checking.
* Replaced some defines by typedefs.
* Renamed USE_DOS_TSR to MBG_USE_DOS_TSR.
- * New preprocessor symbol MBG_USE_KERNEL_DRIVER which
+ * New preprocessor symbol MBG_USE_KERNEL_DRIVER which
* is defined only for targets which use IOCTLs.
* Don't include pcps_dos.h here.
* Updated function prototypes.
@@ -171,12 +240,15 @@
#include <mbg_tgt.h>
#include <mbg_arch.h>
+#include <cfg_hlp.h>
+#include <timeutil.h>
#include <mbgmutex.h>
#include <mbgerror.h>
#include <mbggeo.h>
#include <pcpsdev.h>
#include <pci_asic.h>
#include <use_pack.h>
+
#include <time.h>
@@ -184,7 +256,6 @@
#define MBGDEVIO_COMPAT_VERSION 0x0210
-#define MBG_MAX_DEVICES 8
#if defined( MBG_TGT_WIN32 )
@@ -201,7 +272,6 @@
#endif
#define MBG_USE_KERNEL_DRIVER 1
- #include <windows.h>
#define MBGDEVIO_RET_VAL DWORD
#define _mbgdevio_cnv_ret_val( _v ) (_v)
@@ -269,6 +339,13 @@
#endif
+#if defined( MBG_TGT_POSIX )
+ #include <stdio.h>
+ #include <errno.h>
+
+ #define MBG_HAS_POSIX_IOCTL 1
+#endif
+
#if !defined( MBGDEVIO_XHRT_API )
#define MBGDEVIO_XHRT_API 0
#endif
@@ -296,9 +373,84 @@
#endif
+//### TODO More detailed information for the function groups below.
+
+/**
+ * @defgroup pcps_hr_time_fncs API functions reading high resolution time, plus status
+ *
+ * These functions return a high resolution time, including status flags and
+ * local time offset according to the time zone configuration on the device.
+ *
+ * The API call ::mbg_chk_dev_has_hr_time checks if these functions are supported
+ * by a device.
+ *
+ * Due to the extended information returned to the caller these function
+ * require interaction with the on-board microcontroller, and thus take
+ * longer to execute.
+ *
+ * <b>Note:</b> These API calls provides better accuracy and higher resolution
+ * than the the standard functions in @ref pcps_std_time_fncs.
+ *
+ * The ::mbg_get_hr_time function doesn't account for the latency
+ * which is introduced when accessing the board.
+ * The ::mbg_get_hr_time_cycles and ::mbg_get_hr_time_comp calls
+ * provide ways to account for and/or compensate the latency.
+ *
+ * @see ::mbg_chk_dev_has_hr_time
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_hr_time_cycles
+ * @see ::mbg_get_hr_time_comp
+ * @see @ref pcps_hr_time_fncs
+ * @see @ref pcps_fast_timestamp_fncs
+ * @see @ref pcps_std_time_fncs
+ */
+
+/**
+ * @defgroup pcps_fast_timestamp_fncs API functions reading high resolution timestamps, without status
+ *
+ * These functions are fast, but return only the UTC time. No status flags,
+ * no time zone offset. The time stamps are read from a latched counter chain
+ * in the PCI chip set, so this is only supported by cards whose chi set supports this.
+ */
+
+/**
+ * @defgroup pcps_std_time_fncs Legacy API functions to read or set the time
+ *
+ * These functions are supported by all devices, but return time only
+ * as a ::PCPS_TIME structure whose resolution is limited to 10 ms.
+ */
+
+/**
+ * @defgroup pcps_chk_feat_fncs Functions used to check if a particular feature is supported
+ *
+ * Each of these functions can be used to check if a device supports a particular feature.
+ * ::MBG_SUCCESS is returned if the requested feature is supported, otherwise one of the
+ * @ref MBG_ERROR_CODES is returned, as appropriate.
+ */
+
+/**
+ * @defgroup pcps_chk_feat_fncs_deprecated Deprecated functions used to check if a particular feature is supported
+ *
+ * @deprecated These function are deprecated. Use the @ref pcps_chk_feat_fncs preferably.
+ *
+ * These deprecated functions can still be used to check if a device supports
+ * a particular feature, and will be kept for compatibility.
+ *
+ * However, they return an error code if the call itself failed, and only if the
+ * call succeeded a flag variable is set up telling if the requested feature
+ * is supported, or not. So it's not very handy for an application to check both
+ * of these condition for every single call.
+ *
+ * There are newer replacement functions available which can be used in a
+ * much easier way.
+ *
+ * @see @ref pcps_chk_feat_fncs
+ */
+
+
// If MBGDEVIO_SIMPLE != 0 then some complex configuration
// API calls are excluded from build, which would otherwise
-// require some additional mbglib modules to be linked
+// require some additional mbglib modules to be linked
// to the application.
#if !defined( MBGDEVIO_SIMPLE )
#define MBGDEVIO_SIMPLE 0
@@ -340,13 +492,16 @@
/**
- The type below is used to store a unique ID for a device which
- is made up of the device model name and its serial number, i.e.:
- Format: [model_name]_[serial_number], e.g. "GPS170PCI_028210040670"
- */
+ * @brief A string buffer for a unique device ID
+ *
+ * The unique ID is made up of the device model name
+ * and its serial number, i.e. [model_name]_[serial_number]
+ * E.g.: "GPS170PCI_028210040670"
+ */
typedef char MBG_HW_NAME[PCPS_CLOCK_NAME_SZ + PCPS_SN_SIZE + 1];
+// Definitions specific to the target OS
#if defined( MBG_TGT_LINUX )
@@ -388,7 +543,7 @@ typedef char MBG_HW_NAME[PCPS_CLOCK_NAME_SZ + PCPS_SN_SIZE + 1];
#if !defined( MBG_TGT_WIN32 )
- #define FILETIME int // just a dummy to avoid build errors
+ #define FILETIME int // just a dummy to avoid build errors
#endif
@@ -414,7 +569,7 @@ typedef char MBG_HW_NAME[PCPS_CLOCK_NAME_SZ + PCPS_SN_SIZE + 1];
#endif
#if !defined( _mbg_cpu_set )
- #define _mbg_cpu_set( _i, _ps ) ( *(_ps) |= ( 1UL << (_i) ) )
+ #define _mbg_cpu_set( _i, _ps ) ( *(_ps) |= ( (MBG_CPU_SET) 1UL << (_i) ) )
#endif
#if !defined( _mbg_cpu_isset )
@@ -451,6 +606,7 @@ typedef struct
#endif
} MBG_THREAD_INFO;
+typedef MBG_THREAD_FNC_RET_VAL (MBG_THREAD_FNC_ATTR *MBG_THREAD_FNC)(void *);
typedef struct
@@ -481,15 +637,17 @@ typedef struct
/**
- Match modes to decide how to proceed if a certain
- model type with certain serial number can not be found
+ * @brief Device matching modes
+ *
+ * Match modes to determine how to proceed if a device with
+ * particular model type and serial number has not been detected.
*/
enum MBG_MATCH_MODE
{
- MBG_MATCH_ANY, /**< open the next available device on the system */
- MBG_MATCH_MODEL, /**< open the next available device on the system with the same clock type */
- MBG_MATCH_EXACTLY, /**< force opening exactly the requested device otherwise exit with failure */
- N_MBG_MATCH_MODE /**< number of known modes */
+ MBG_MATCH_ANY, ///< use the next device available on the system
+ MBG_MATCH_MODEL, ///< use the next available device of the same type
+ MBG_MATCH_EXACTLY, ///< use only exactly the excat matching device, otherwise fail
+ N_MBG_MATCH_MODE ///< number of known modes
};
@@ -511,6 +669,11 @@ typedef struct _MBG_DEVICENAME_LIST
} MBG_DEVICENAME_LIST;
+/**
+ * @brief Type of functions to check if a feature is supported
+ */
+typedef int _MBG_API MBG_CHK_SUPP_FNC( MBG_DEV_HANDLE dh );
+
/* function prototypes: */
@@ -524,441 +687,2002 @@ extern "C" {
/* by MAKEHDR, do not remove the comments. */
/**
- Get the version number of the precompiled DLL/shared object library.
+ * @brief Get the version number of the precompiled DLL/shared object library
+ *
+ * If this library is used as a DLL/shared object library then the version
+ * number can be checked to see if the header files which are actually used
+ * to build an application are compatible with the header files which have
+ * been used to build the library, and thus the API function are called
+ * in the correct way.
+ *
+ * @return the version number
+ *
+ * @see ::mbgdevio_check_version
+ * @see ::MBGDEVIO_VERSION defined in mbgdevio.h
+ */
+ _MBG_API_ATTR int _MBG_API mbgdevio_get_version( void ) ;
- If this library is used as a DLL/shared object library then the version
- number can be checked to see if the header files which are actually used
- to build an application are compatible with the header files which have
- been used to build the library, and thus the API function are called
- in the correct way.
+ /**
+ * @brief Check if the DLL/shared library is compatible with a given version
+ *
+ * If this library is used as a DLL/shared object library then the version
+ * number can be checked to see if the header files which are actually used
+ * to build an application are compatible with the header files which have
+ * been used to build the library, and thus the API functions are called
+ * in the correct way.
+ *
+ * @param[in] header_version Version number to be checked, should be ::MBGDEVIO_VERSION
+ * from the mbgdevio.h file version used to build the application
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbgdevio_get_version
+ * @see ::MBGDEVIO_VERSION defined in mbgdevio.h
+ */
+ _MBG_API_ATTR int _MBG_API mbgdevio_check_version( int header_version ) ;
- @return the version number
+ /**
+ * @brief Check if a device supports the ::RECEIVER_INFO structure and related calls.
+ *
+ * Very old devices may not provide a ::RECEIVER_INFO structure.
+ * The ::mbg_setup_receiver_info call should be used preferably to set up
+ * a ::RECEIVER_INFO for a device. The function uses this call to determine
+ * whether a ::RECEIVER_INFO can be read directly from a device, or sets up
+ * a default structure using default values depending on the device type.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_receiver_info,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_setup_receiver_info
+ * @see ::mbg_get_gps_receiver_info
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_receiver_info( MBG_DEV_HANDLE dh ) ;
- @see mbgdevio_check_version()
- @see ::MBGDEVIO_VERSION defined in mbgdevio.h
- */
- _MBG_API_ATTR int _MBG_API mbgdevio_get_version( void ) ;
+ /**
+ * @brief Check if a device supports large configuration data structures.
+ *
+ * Such structures have been introduced with the first Meinberg GPS receivers.
+ * Mostly all configuration structures are large data structures, and mostly all
+ * current devices support this, but some very old devices may not.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_gps_data,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_gps_data( MBG_DEV_HANDLE dh ) ;
/**
- @brief Check if the DLL/shared library is compatible with a given version.
+ * @brief Check if a device supports the ::mbg_generic_io API call.
+ *
+ * <b>Warning</b>: This call is for debugging purposes and internal use only!
+ *
+ * @note This function should be preferred over ::mbg_dev_has_generic_io,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_generic_io
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_generic_io( MBG_DEV_HANDLE dh ) ;
- If this library is used as a DLL/shared object library then the version
- number can be checked to see if the header files which are actually used
- to build an application are compatible with the header files which have
- been used to build the library, and thus the API function are called
- in the correct way.
+ /**
+ * @brief Check if a device supports the ::mbg_get_asic_version API call.
+ *
+ * It depends on the bus interface chip assembled on the device
+ * if ::mbg_get_asic_version is supported, or not.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_asic_version,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_asic_version
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_asic_version( MBG_DEV_HANDLE dh ) ;
- @param header_version Version number to be checked, should be ::MBGDEVIO_VERSION
- from the mbgdevio.h file used to build the application
+ /**
+ * @brief Check if a device supports the ::mbg_get_asic_features call.
+ *
+ * It depends on the bus interface chip assembled on the device
+ * if ::mbg_get_asic_features is supported, or not.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_asic_features,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_asic_features
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_asic_features( MBG_DEV_HANDLE dh ) ;
- @return ::MBG_SUCCESS if compatible, ::MBG_ERR_LIB_NOT_COMPATIBLE if not.
+ /**
+ * @brief Check if a device provides eXtended Multi Ref (XMR) inputs.
+ *
+ * Devices providing XMR inputs can receive or decode different timing
+ * signals in parallel, and the supported sources can be prioritized.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_xmr,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_set_gps_xmr_settings_idx
+ * @see ::mbg_get_xmr_holdover_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_xmr( MBG_DEV_HANDLE dh ) ;
- @see mbgdevio_get_version()
- @see ::MBGDEVIO_VERSION defined in mbgdevio.h
- */
- _MBG_API_ATTR int _MBG_API mbgdevio_check_version( int header_version ) ;
+ /**
+ * @brief Check if the device is connected to the ISA bus.
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to ISA, ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_isa( MBG_DEV_HANDLE dh ) ;
/**
- @brief Open a device by index, starting from 0.
+ * @brief Check if the device is connected to the MCA bus.
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to MCA, ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_mca( MBG_DEV_HANDLE dh ) ;
- This function is <b>out of date</b>, mbg_open_device_by_name()
- should be used instead.
+ /**
+ * @brief Check if the device is connected to the PCI bus and if one of the PCI interface chips is used
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to PCI and one of the PCI interface chips is used,
+ * ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_pci( MBG_DEV_HANDLE dh ) ;
- See the <b>note</b> for mbg_find_device() for details.
+ /**
+ * @brief Check if the device is connected to the PCI Express bus and if one of the PCI Express interface chips is used
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to PCI Express and one of the PCI Express interface chips is used,
+ * ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_pci_express( MBG_DEV_HANDLE dh ) ;
- @param device_index index of the device, use 0 for the first device.
- */
- _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device( unsigned int device_index ) ;
+ /**
+ * @brief Check if the device is connected to the USB bus
+ *
+ * @note This function should be used instead of checking the bus_flags manually
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the device is connected to USB, ::MBG_ERR_NOT_SUPP_BY_DEV otherwise
+ *
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_usb( MBG_DEV_HANDLE dh ) ;
/**
- @brief Get the number of supported devices installed on the computer.
+ * @brief Check if a device supports GNSS configuration.
+ *
+ * This is usually the case if a device supports reception of
+ * several different satellite systems, e.g. GPS, Glonass, etc.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_gnss,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_gnss_mode_info
+ * @see ::mbg_set_gps_gnss_mode_settings
+ * @see ::mbg_get_gps_all_gnss_sat_info
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_gnss( MBG_DEV_HANDLE dh ) ;
- This function is <b>out of date</b>, mbg_find_devices_with_names()
- should be used instead.
+ /**
+ * @brief Check if a device is a GPS receiver.
+ *
+ * The function also returns ::MBG_SUCCESS for GNSS receivers
+ * which can track GPS satellites beside other GNSS systems.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_gps,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_gps( MBG_DEV_HANDLE dh ) ;
- <b>Note:</b> This function is out of date since it may not work
- correctly for Meinberg devices which are disconnected and reconnected
- while the system is running (e.g. USB devices). However, the function
- will be kept for compatibility reasons and works correctly if all
- Meinberg devices are connected at system boot and are not disconnected
- and reconnected during operation
+ /**
+ * @brief Check if a device is a DCF77 receiver.
+ *
+ * Beside standard DCF77 receivers which receive the legacy AM signal
+ * there are also PZF receivers which can decode the pseudo-random phase
+ * modulation and thus yield a higher accuracy. See ::mbg_chk_dev_has_pzf.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_dcf,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pzf
+ * @see ::mbg_chk_dev_is_lwr
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_dcf( MBG_DEV_HANDLE dh ) ;
- @return The number of devices found
+ /**
+ * @brief Check if a device supports demodulation of the DCF77 PZF code
+ *
+ * Beside the enhanced PZF correlation receivers which decode the DCF77's
+ * pseudo-random phase modulation to yield a better accuracy there are also
+ * legacy DCF77 receivers which just decode the standard AM signal.
+ * See ::mbg_chk_dev_is_dcf.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_pzf,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_corr_info
+ * @see ::mbg_chk_dev_supp_tr_distance
+ * @see ::mbg_chk_dev_is_dcf
+ * @see ::mbg_chk_dev_is_lwr
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_pzf( MBG_DEV_HANDLE dh ) ;
- @see mbg_find_devices_with_names()
- */
- _MBG_API_ATTR int _MBG_API mbg_find_devices( void ) ;
+ /**
+ * @brief Check if a device is a MSF receiver.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_msf,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_lwr
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_msf( MBG_DEV_HANDLE dh ) ;
/**
- @brief Allocate memory and set up a list of installed and supported devices.
+ * @brief Check if a device is a WWVB receiver.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_wwvb,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_lwr
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_wwvb( MBG_DEV_HANDLE dh ) ;
- This function should be used preferably instead of mbg_find_devices().
+ /**
+ * @brief Check if a device is any long wave signal receiver.
+ *
+ * Long wave receivers include e.g. DCF77, MSF, WWVB, or JJY.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_lwr,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_dcf
+ * @see ::mbg_chk_dev_is_msf
+ * @see ::mbg_chk_dev_is_wwvb
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_lwr( MBG_DEV_HANDLE dh ) ;
- @param device_list Pointer to a linked list of type ::MBG_DEVICENAME_LIST
- with device names. The list will be allocated by this
- function and has to be freed after usage by calling
- mbg_free_device_name_list().
- @param max_devices Maximum number of devices the function should look for
- (can not exceed ::MBG_MAX_DEVICES).
+ /**
+ * @brief Check if a device provides a configurable IRIG input.
+ *
+ * @note This function should be preferred over ::mbg_dev_is_irig_rx,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_irig_rx_info
+ * @see ::mbg_set_irig_rx_settings
+ * @see ::mbg_chk_dev_has_irig_tx
+ * @see ::mbg_chk_dev_has_irig
+*/
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_is_irig_rx( MBG_DEV_HANDLE dh ) ;
- @return number of present devices
+ /**
+ * @brief Check if a device provides simple LAN interface API calls.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_lan_intf,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_state
+ * @see ::mbg_get_ip4_settings
+ * @see ::mbg_set_ip4_settings
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_lan_intf( MBG_DEV_HANDLE dh ) ;
- @see ::MBG_HW_NAME for the format of the unique names
- @see mbg_free_device_name_list()
- @see mbg_find_devices()
- */
- _MBG_API_ATTR int _MBG_API mbg_find_devices_with_names( MBG_DEVICENAME_LIST **device_list, int max_devices ) ;
+ /**
+ * @brief Check if a device provides PTP configuration/status calls.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_ptp,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_state
+ * @see ::mbg_get_ptp_cfg_info
+ * @see ::mbg_set_ptp_cfg_settings
+ * @see ::mbg_chk_dev_has_ptp_unicast
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_ptp( MBG_DEV_HANDLE dh ) ;
/**
- @brief Free the memory allocated for a ::MBG_DEVICENAME_LIST.
+ * @brief Check if a device provides PTP unicast feature/configuration.
+ *
+ * Not all devices which support PTP do also support PTP Unicast. This API
+ * call checks if PTP Unicast is supported in addition to the standard
+ * PTP multicast.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_ptp_unicast,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_uc_master_cfg_limits
+ * @see ::mbg_get_all_ptp_uc_master_info
+ * @see ::mbg_set_ptp_uc_master_settings_idx
+ * @see ::mbg_get_ptp_state
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_ptp_unicast( MBG_DEV_HANDLE dh ) ;
- The list may have been set up and allocated before
- by mbg_find_devices_with_names().
+ /**
+ * @brief Check if a device supports the mbg_get_hr_time... functions.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_hr_time,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_hr_time_cycles
+ * @see ::mbg_get_hr_time_comp
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_hr_time( MBG_DEV_HANDLE dh ) ;
- @param *list Linked list of type ::MBG_DEVICENAME_LIST
+ /**
+ * @brief Check if a device supports the mbg_get_fast_hr_timestamp... calls.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_fast_hr_timestamp,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_fast_hr_timestamp_cycles
+ * @see ::mbg_get_fast_hr_timestamp_comp
+ * @see ::mbg_get_fast_hr_timestamp
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_fast_hr_timestamp( MBG_DEV_HANDLE dh ) ;
- @see mbg_find_devices_with_names()
- */
- _MBG_API_ATTR void _MBG_API mbg_free_device_name_list( MBG_DEVICENAME_LIST *list) ;
+ /**
+ * @brief Check if a device supports configurable time scales.
+ *
+ * By default the cards return %UTC and/or local time. However, some cards
+ * can be configured to return raw GPS time or TAI instead.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_time_scale,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_time_scale_info
+ * @see ::mbg_set_time_scale_settings
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_time_scale( MBG_DEV_HANDLE dh ) ;
+
+ /** (Intentionally excluded from Doxygen)
+ * @brief Check if a device supports setting an event time
+ *
+ * This feature is only supported by some special custom firmware
+ * to preset a %UTC time at which the clock is to generate an output signal.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_event_time,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_set_event_time
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_event_time( MBG_DEV_HANDLE dh ) ;
/**
- @brief Return a handle to a device with a certain unique name.
+ * @brief Check if a device supports the ::mbg_get_ucap_entries and ::mbg_get_ucap_event calls.
+ *
+ * If the device doesn't support this but is a GPS card then the card provides
+ * a time capture FIFO buffer and the obsolete ::mbg_get_gps_ucap call can be used
+ * to retrieve entries from the FIFO buffer.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_ucap,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_get_ucap_event
+ * @see ::mbg_clr_ucap_buff
+ * @see ::mbg_get_gps_ucap
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_ucap( MBG_DEV_HANDLE dh ) ;
- The names of the devices that are installed on the system can be retrieved by
- the function mbg_find_devices_with_names().
+ /**
+ * @brief Check if a device supports the ::mbg_clr_ucap_buff call.
+ *
+ * The ::mbg_clr_ucap_buff call can be used to clear a device's on-board
+ * time capture FIFO buffer, but the call may not be supported by some
+ * older GPS devices.
+ *
+ * @note This function should be preferred over ::mbg_dev_can_clr_ucap_buff,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_clr_ucap_buff
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_can_clr_ucap_buff( MBG_DEV_HANDLE dh ) ;
- This function should be used preferably instead of mbg_open_device().
+ /**
+ * @brief Check if a device supports timezone configuration using the ::TZDL structure.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_tzdl,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_tzdl
+ * @see ::mbg_set_gps_tzdl
+ * @see ::mbg_chk_dev_has_tz
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_tzdl( MBG_DEV_HANDLE dh ) ;
- @param hw_name String with the unique name of the device to be opened
- @param selection_mode One of the enum values of ::MBG_MATCH_MODE
+ /**
+ * @brief Check if a device supports timezone configuration using the ::PCPS_TZDL structure.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_pcps_tzdl,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_pcps_tzdl
+ * @see ::mbg_set_pcps_tzdl
+ * @see ::mbg_chk_dev_has_tz
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_pcps_tzdl( MBG_DEV_HANDLE dh ) ;
- @return On success, the function returns a handle to the device, otherwise ::MBG_INVALID_DEV_HANDLE
+ /**
+ * @brief Check if a device supports timezone configuration using the ::PCPS_TZCODE type.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_tzcode,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_tzcode
+ * @see ::mbg_set_tzcode
+ * @see ::mbg_chk_dev_has_tz
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_tzcode( MBG_DEV_HANDLE dh ) ;
- @see ::MBG_HW_NAME for the format of the unique names.
- @see ::MBG_MATCH_MODE
- @see mbg_find_devices_with_names()
- */
- _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device_by_name( const char* hw_name, int selection_mode ) //##++++
-;
+ /**
+ * @brief Check if a device supports any kind of timezone configuration.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_tz,
+ * which has been deprecated.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_tzdl
+ * @see ::mbg_chk_dev_has_pcps_tzdl
+ * @see ::mbg_chk_dev_has_tzcode
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_tz( MBG_DEV_HANDLE dh ) ;
/**
- @brief Close a handle to a device and set the handle value to ::MBG_INVALID_DEV_HANDLE.
+ * @brief Check if a device provides either an IRIG input or output.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_irig,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_irig_rx
+ * @see ::mbg_chk_dev_has_irig_tx
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_irig( MBG_DEV_HANDLE dh ) ;
- @param dev_handle Handle to a Meinberg device.
- */
- _MBG_API_ATTR void _MBG_API mbg_close_device( MBG_DEV_HANDLE *dev_handle ) ;
+ /**
+ * @brief Check if a device provides a configurable IRIG output.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_irig,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_irig_tx_info
+ * @see ::mbg_set_irig_tx_settings
+ * @see ::mbg_chk_dev_is_irig_rx
+ * @see ::mbg_chk_dev_has_irig
+ * @see @ref group_icode
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_irig_tx( MBG_DEV_HANDLE dh ) ;
/**
- @brief Read information about the driver handling a given device.
+ * @brief Check if a device supports the ::mbg_get_irig_ctrl_bits call
+ *
+ * @note This function should be preferred over ::mbg_dev_has_irig_ctrl_bits,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_irig_ctrl_bits
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_irig_ctrl_bits( MBG_DEV_HANDLE dh ) ;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_DRVR_INFO structure which is filled up.
+ /**
+ * @brief Check if a device supports the ::mbg_get_raw_irig_data call.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_raw_irig_data,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_raw_irig_data
+ * @see ::mbg_get_raw_irig_data_on_sec_change
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_raw_irig_data( MBG_DEV_HANDLE dh ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function
- */
- _MBG_API_ATTR int _MBG_API mbg_get_drvr_info( MBG_DEV_HANDLE dh, PCPS_DRVR_INFO *p ) ;
+ /**
+ * @brief Check if a device supports the ::mbg_get_irig_time call.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_irig_time,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_irig_time
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_irig_time( MBG_DEV_HANDLE dh ) ;
/**
- @brief Read detailed device information.
+ * @brief Check if a device provides the level of its inputs signal.
+ *
+ * This is useful to display the signal level of e.g. an IRIG or similar
+ * time code, or a long wave signal.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_signal,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_signal( MBG_DEV_HANDLE dh ) ;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_DEV structure to be filled up
+ /**
+ * @brief Check if a device provides a modulation signal.
+ *
+ * Modulation signals are e.g. the second marks provided by a long wave receiver.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_mod,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_mod( MBG_DEV_HANDLE dh ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function
- */
- _MBG_API_ATTR int _MBG_API mbg_get_device_info( MBG_DEV_HANDLE dh, PCPS_DEV *p ) ;
+ /** (Intentionally excluded from Doxygen)
+ * Check if a device provides a serial output supporting
+ * higher baud rates than older cards, i.e. ::DEFAULT_BAUD_RATES_DCF_HS
+ * rather than ::DEFAULT_BAUD_RATES_DCF.
+ *
+ * The call ::mbg_get_serial_settings takes care of this, so applications
+ * which use that call as suggested don't need to use this call directly.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_serial_hs,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_serial_settings
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_serial_hs( MBG_DEV_HANDLE dh ) ;
/**
- @brief Read the current state of the on-board ::PCPS_STATUS_PORT.
+ * @brief Check if a device provides a programmable frequency synthesizer.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_synth,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_synth
+ * @see ::mbg_set_synth
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_synth( MBG_DEV_HANDLE dh ) ;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_STATUS_PORT value to be filled up
+ /**
+ * @brief Check if a device provides GPIO signal inputs and/or outputs.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_gpio,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ * @see ::mbg_get_gps_all_gpio_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_gpio( MBG_DEV_HANDLE dh ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function
+ /**
+ * @brief Check if a device supports configuration of antenna cable length.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_cab_len,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_ant_cable_len
+ * @see ::mbg_set_gps_ant_cable_len
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_cab_len( MBG_DEV_HANDLE dh ) ;
- @see \ref group_status_port "bitmask"
- */
- _MBG_API_ATTR int _MBG_API mbg_get_status_port( MBG_DEV_HANDLE dh, PCPS_STATUS_PORT *p ) ;
+ /**
+ * @brief Check if a device provides a configurable ref time offset.
+ *
+ * This may be required to convert the received time to %UTC, if the input
+ * signal doesn't specify this (e.g. with most IRIG code formats). //###
+ *
+ * @note This function should be preferred over ::mbg_dev_has_ref_offs,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_ref_offs
+ * @see ::mbg_set_ref_offs
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_ref_offs( MBG_DEV_HANDLE dh ) ;
- /* (Intentionally excluded from Doxygen)
- Generic read function which writes a command code to a device
- and reads a number of replied data to a generic buffer.
+ /**
+ * @brief Check if a device supports the ::MBG_OPT_INFO/::MBG_OPT_SETTINGS.
+ *
+ * These structures contain optional settings, controlled by flags.
+ * See ::MBG_OPT_SETTINGS and related definitions.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_opt_flags,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_opt_info
+ * @see ::mbg_set_opt_settings
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_opt_flags( MBG_DEV_HANDLE dh ) ;
- <b>Warning</b>: This is for debugging purposes only!
- The specialized API calls should be used preferably.
- A specific device may not support any command code.
+ /**
+ * @brief Check if a device support reading/writing of UTC parameters.
+ *
+ * This API call checks if a device supports reading/writing a GPS %UTC
+ * parameter set via the PC bus. Reading/writing these parameters via the
+ * serial port using the Meinberg binary data protocol is supported by all
+ * Meinberg GPS devices.
+ *
+ * The %UTC parameter set is usually received from the satellites' broadcasts
+ * and contains the current time offset between GPS time and UTC, plus information
+ * on a pending leap second event.
+ *
+ * It may be useful to overwrite them to do some tests, or for applications
+ * where a card is freewheeling.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_utc_parm,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_utc_parm
+ * @see ::mbg_set_utc_parm
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_utc_parm( MBG_DEV_HANDLE dh ) ;
- @param dh Valid handle to a Meinberg device
- @param cmd Can be any \ref group_cmd_bytes "command byte" supported by the device
- @param *p Pointer to a buffer to be filled up
- @param size Size of the buffer *p
+ /**
+ * @brief Check if a device supports reading correlation info
+ *
+ * @note This function should be preferred over ::mbg_dev_has_corr_info,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pzf
+ * @see ::mbg_get_corr_info
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_has_corr_info( MBG_DEV_HANDLE dh ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Check if a device supports configurable distance from transmitter
+ *
+ * The distance from transmitter parameter is used to compensate
+ * the RF propagation delay, mostly with long wave receivers.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_tr_distance,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pzf
+ * @see ::mbg_get_tr_distance
+ * @see ::mbg_set_tr_distance
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_tr_distance( MBG_DEV_HANDLE dh ) ;
- @see mbg_generic_write()
- @see mbg_generic_read_gps()
- @see mbg_generic_write_gps()
- @see mbg_generic_io()
- */
- _MBG_API_ATTR int _MBG_API mbg_generic_read( MBG_DEV_HANDLE dh, int cmd, void *p, int size ) ;
+ /**
+ * @brief Check if a device provides a debug status word to be read
+ *
+ * @note This function should be preferred over ::mbg_dev_has_debug_status,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_debug_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_debug_status( MBG_DEV_HANDLE dh ) ;
- /* (Intentionally excluded from Doxygen)
- Generic read function which writes a GPS command code to a device
- and reads a number of replied data to a generic buffer.
- The macro _pcps_has_gps_data() or the API call mbg_dev_has_gps_data()
- check whether this call is supported by a device.
+ /**
+ * @brief Check if a device provides an on-board event log.
+ *
+ * @note This function should be preferred over ::mbg_dev_has_evt_log,
+ * which has been deprecated.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS if the requested feature is supported, ::MBG_ERR_NOT_SUPP_BY_DEV
+ * if not supported, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_clr_evt_log
+ * @see ::mbg_get_num_evt_log_entries
+ * @see ::mbg_get_first_evt_log_entry
+ * @see ::mbg_get_next_evt_log_entry
+ */
+ _MBG_API_ATTR int _MBG_API mbg_chk_dev_supp_evt_log( MBG_DEV_HANDLE dh ) ;
- <b>Warning</b>: This is for debugging purposes only!
- The specialized API calls should be used preferably.
- A specific device may not support any GPS command code.
+ /**
+ * @brief Check if a device supports the ::RECEIVER_INFO structure and related calls.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_receiver_info preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_receiver_info
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_receiver_info" ) _MBG_API mbg_dev_has_receiver_info( MBG_DEV_HANDLE dh, int *p ) ;
- @param dh Valid handle to a Meinberg device
- @param cmd Can be any \ref group_cmd_bytes "command byte" supported by the device.
- @param *p Pointer to a buffer to be filled up
- @param size Size of the buffer *p
+ /**
+ * @brief Check if a device supports large configuration data structures.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_gps_data preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_gps_data
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_gps_data" ) _MBG_API mbg_dev_has_gps_data( MBG_DEV_HANDLE dh, int *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Check if a device supports the ::mbg_generic_io API call.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_generic_io preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_generic_io
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_generic_io" ) _MBG_API mbg_dev_has_generic_io( MBG_DEV_HANDLE dh, int *p ) ;
- @see mbg_dev_has_gps_data()
- @see mbg_generic_write_gps()
- @see mbg_generic_read()
- @see mbg_generic_write()
- @see mbg_generic_io()
- */
- _MBG_API_ATTR int _MBG_API mbg_generic_read_gps( MBG_DEV_HANDLE dh, int cmd, void *p, int size ) ;
+ /**
+ * @brief Check if a device supports the ::mbg_get_asic_version call.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_asic_version preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_asic_version
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_asic_version" ) _MBG_API mbg_dev_has_asic_version( MBG_DEV_HANDLE dh, int *p ) ;
- /* (Intentionally excluded from Doxygen)
- Generic write function which writes a command code plus an
- associated number of data bytes to a device.
+ /**
+ * @brief Check if a device supports the ::mbg_get_asic_features call.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_asic_features preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_asic_features
+ * @see ::mbg_get_asic_features
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_asic_features" ) _MBG_API mbg_dev_has_asic_features( MBG_DEV_HANDLE dh, int *p ) ;
- <b>Warning</b>: This is for debugging purposes only!
- The specialized API calls should be used preferably.
- A specific device may not support any command code.
+ /**
+ * @brief Check if a device provides extended multi ref (XMR) inputs.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_xmr preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_xmr
+ * @see @ref group_multi_ref_ext
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_xmr" ) _MBG_API mbg_dev_has_xmr( MBG_DEV_HANDLE dh, int *p ) ;
- @param dh Valid handle to a Meinberg device
- @param cmd Can be any \ref group_cmd_bytes "command byte" supported by the device.
- @param *p Pointer to a buffer to be written
- @param size Size of the buffer *p
+ /**
+ * @brief Check if a device supports GNSS configuration.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_gnss preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_gnss
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_gnss" ) _MBG_API mbg_dev_is_gnss( MBG_DEV_HANDLE dh, int *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Check if a device is a GPS receiver.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_is_gps preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_gps
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_gps" ) _MBG_API mbg_dev_is_gps( MBG_DEV_HANDLE dh, int *p ) ;
- @see mbg_generic_read()
- @see mbg_generic_read_gps()
- @see mbg_generic_write_gps()
- @see mbg_generic_io()
- */
- _MBG_API_ATTR int _MBG_API mbg_generic_write( MBG_DEV_HANDLE dh, int cmd, const void *p, int size ) ;
+ /**
+ * @brief Check if a device is a DCF77 receiver.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_dcf preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_dcf
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_dcf" ) _MBG_API mbg_dev_is_dcf( MBG_DEV_HANDLE dh, int *p ) ;
- /* (Intentionally excluded from Doxygen)
- Generic write function which writes a GPS command code plus an
- associated number of data bytes to a device.
- The macro _pcps_has_gps_data() or the API call mbg_dev_has_gps_data()
- check whether this call is supported by a device.
+ /**
+ * @brief Check if a device supports demodulation of the DCF77 PZF code
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_pzf preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pzf
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_pzf" ) _MBG_API mbg_dev_has_pzf( MBG_DEV_HANDLE dh, int *p ) ;
- <b>Warning</b>: This is for debugging purposes only!
- The specialized API calls should be used preferably.
- A specific device may not support any GPS command code.
+ /**
+ * @brief Check if a device is a MSF receiver.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_msf preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_msf
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_msf" ) _MBG_API mbg_dev_is_msf( MBG_DEV_HANDLE dh, int *p ) ;
- @param dh Valid handle to a Meinberg device
- @param cmd Can be any \ref group_cmd_bytes "command byte" supported by the device.
- @param *p Pointer to a buffer to be written
- @param size Size of the buffer *p
+ /**
+ * @brief Check if a device is a WWVB receiver.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_wwvb preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_wwvb
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_wwvb" ) _MBG_API mbg_dev_is_wwvb( MBG_DEV_HANDLE dh, int *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Check if a device is any long wave signal receiver.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_lwr preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_lwr
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_lwr" ) _MBG_API mbg_dev_is_lwr( MBG_DEV_HANDLE dh, int *p ) ;
- @see mbg_dev_has_gps_data()
- @see mbg_generic_read_gps()
- @see mbg_generic_read()
- @see mbg_generic_write()
- @see mbg_generic_io()
- */
- _MBG_API_ATTR int _MBG_API mbg_generic_write_gps( MBG_DEV_HANDLE dh, int cmd, const void *p, int size ) ;
+ /**
+ * @brief Check if a device provides a configurable IRIG input.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_is_irig_rx preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_is_irig_rx
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_is_irig_rx" ) _MBG_API mbg_dev_is_irig_rx( MBG_DEV_HANDLE dh, int *p ) ;
- /* (Intentionally excluded from Doxygen)
- Write and/or read generic data to/from a device.
- The macro _pcps_has_generic_io() or the API call mbg_dev_has_generic_io()
- check whether this call is supported by a device.
+ /**
+ * @brief Check if a device provides simple LAN interface API calls.
+ *
+ * @deprecated This function is deprecated, use ::mbg_chk_dev_has_lan_intf preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_lan_intf
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_lan_intf" ) _MBG_API mbg_dev_has_lan_intf( MBG_DEV_HANDLE dh, int *p ) ;
- <b>Warning</b>: This call is for debugging purposes and internal use only!
+ /**
+ * @brief Check if a device provides PTP configuration/status calls.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_ptp preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ptp
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_ptp" ) _MBG_API mbg_dev_has_ptp( MBG_DEV_HANDLE dh, int *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Check if a device provides PTP unicast feature/configuration.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_ptp_unicast preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ptp_unicast
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_ptp_unicast" ) _MBG_API mbg_dev_has_ptp_unicast( MBG_DEV_HANDLE dh, int *p ) ;
- @see mbg_dev_has_generic_io()
- @see mbg_generic_read()
- @see mbg_generic_write()
- @see mbg_generic_read_gps()
- @see mbg_generic_write_gps()
- */
- _MBG_API_ATTR int _MBG_API mbg_generic_io( MBG_DEV_HANDLE dh, int type, const void *in_p, int in_sz, void *out_p, int out_sz ) ;
+ /**
+ * @brief Check if a device supports the HR_TIME functions.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_hr_time preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_hr_time
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_hr_time" ) _MBG_API mbg_dev_has_hr_time( MBG_DEV_HANDLE dh, int *p ) ;
/**
- @brief Read a ::PCPS_TIME structure returning the current date/time/status.
+ * @brief Check if a device supports the mbg_get_fast_hr_timestamp_...() calls.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_fast_hr_timestamp preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_fast_hr_timestamp
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_fast_hr_timestamp" ) _MBG_API mbg_dev_has_fast_hr_timestamp( MBG_DEV_HANDLE dh, int *p ) ;
- The returned time is local time according to the card's time zone setting,
- with a resolution of 10 ms (i.e. 10ths of seconds).
+ /**
+ * @brief Check if a device supports configurable time scales.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_time_scale preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_time_scale
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_time_scale" ) _MBG_API mbg_dev_has_time_scale( MBG_DEV_HANDLE dh, int *p ) ;
- This call is supported by any device manufactured by Meinberg.
- However, for higher accuracy and resolution the mbg_get_hr_time..() or
- mbg_get_fast_hr_timestamp..() group of calls should be used preferably
- if supported by the device.
+ /**
+ * @brief Check if a device supports setting an event time
+ *
+ * @note This is only supported by some customized devices
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_event_time preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_event_time
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_event_time" ) _MBG_API mbg_dev_has_event_time( MBG_DEV_HANDLE dh, int *p ) ;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_TIME structure to be filled up
+ /**
+ * @brief Check if a device supports the ::mbg_get_ucap_entries and ::mbg_get_ucap_event calls.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_ucap preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ucap
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_ucap" ) _MBG_API mbg_dev_has_ucap( MBG_DEV_HANDLE dh, int *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Check if a device supports the ::mbg_clr_ucap_buff call.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_can_clr_ucap_buff preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_can_clr_ucap_buff
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_can_clr_ucap_buff" ) _MBG_API mbg_dev_can_clr_ucap_buff( MBG_DEV_HANDLE dh, int *p ) ;
- @see mbg_get_hr_time()
- @see mbg_set_time()
- @see mbg_get_sync_time()
- */
- _MBG_API_ATTR int _MBG_API mbg_get_time( MBG_DEV_HANDLE dh, PCPS_TIME *p ) ;
+ /**
+ * @brief Check if a device supports timezone configuration using the ::TZDL structure.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_tzdl preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_tzdl
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_tzdl" ) _MBG_API mbg_dev_has_tzdl( MBG_DEV_HANDLE dh, int *p ) ;
/**
- @brief Set the device's on-board clock to a given date and time.
+ * @brief Check if a device supports timezone configuration using the ::PCPS_TZDL structure.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_pcps_tzdl preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_pcps_tzdl
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_pcps_tzdl" ) _MBG_API mbg_dev_has_pcps_tzdl( MBG_DEV_HANDLE dh, int *p ) ;
- The macro _pcps_can_set_time() checks whether this call
- is supported by a device.
+ /**
+ * @brief Check if a device supports timezone configuration using the ::PCPS_TZCODE type.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_tzcode preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_tzcode
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_tzcode" ) _MBG_API mbg_dev_has_tzcode( MBG_DEV_HANDLE dh, int *p ) ;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_STIME structure to be written
+ /**
+ * @brief Check if a device supports any kind of timezone configuration.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_tz preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_tz
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_tz" ) _MBG_API mbg_dev_has_tz( MBG_DEV_HANDLE dh, int *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Check if a device provides either an IRIG input or output.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_irig preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_irig
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_irig" ) _MBG_API mbg_dev_has_irig( MBG_DEV_HANDLE dh, int *p ) ;
- @see mbg_get_time()
- */
- _MBG_API_ATTR int _MBG_API mbg_set_time( MBG_DEV_HANDLE dh, const PCPS_STIME *p ) ;
+ /**
+ * @brief Check if a device provides a configurable IRIG output.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_irig_tx preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_irig_tx
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_irig_tx" ) _MBG_API mbg_dev_has_irig_tx( MBG_DEV_HANDLE dh, int *p ) ;
/**
- @brief Read the time when the device has last recently synchronized.
+ * @brief Check if a device supports the ::mbg_get_irig_ctrl_bits call
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_irig_ctrl_bits preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_irig_ctrl_bits
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_irig_ctrl_bits" ) _MBG_API mbg_dev_has_irig_ctrl_bits( MBG_DEV_HANDLE dh, int *p ) ;
- Fills a ::PCPS_TIME structure with the date/time/status reporting
- when the device was synchronized the last time to its time source,
- e.g. the DCF77 signal, the GPS satellites, or similar.
- The macro _pcps_has_sync_time() or the API call mbg_dev_has_sync_time()
- check whether this call is supported by a device.
+ /**
+ * @brief Check if a device supports the ::mbg_get_raw_irig_data call.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_raw_irig_data preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_raw_irig_data
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_raw_irig_data" ) _MBG_API mbg_dev_has_raw_irig_data( MBG_DEV_HANDLE dh, int *p ) ;
- The macro _pcps_has_sync_time() checks whether this call
- is supported by a device.
+ /**
+ * @brief Check if a device supports the ::mbg_get_irig_time call.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_irig_time preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_irig_time
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_irig_time" ) _MBG_API mbg_dev_has_irig_time( MBG_DEV_HANDLE dh, int *p ) ;
- <b>Note:</b> If that information is not available on the board then
- the value of the returned ::PCPS_TIME::sec field is set to 0xFF.
- The macro _pcps_time_is_read() can be used to check whether the
- returned information is valid, or not available.
+ /**
+ * @brief Check if a device provides the level of its inputs signal.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_signal preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_signal
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_signal" ) _MBG_API mbg_dev_has_signal( MBG_DEV_HANDLE dh, int *p ) ;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_TIME structure to be filled up
+ /**
+ * @brief Check if a device provides a modulation signal.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_mod preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_mod
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_mod" ) _MBG_API mbg_dev_has_mod( MBG_DEV_HANDLE dh, int *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /* (Intentionally excluded from Doxygen)
+ * Check if a device provides a serial output supporting
+ * higher baud rates than older cards, i.e. ::DEFAULT_BAUD_RATES_DCF_HS
+ * rather than ::DEFAULT_BAUD_RATES_DCF.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_serial_hs preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_serial_hs
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_serial_hs" ) _MBG_API mbg_dev_has_serial_hs( MBG_DEV_HANDLE dh, int *p ) ;
- @see mbg_get_time()
- */
- _MBG_API_ATTR int _MBG_API mbg_get_sync_time( MBG_DEV_HANDLE dh, PCPS_TIME *p ) ;
+ /**
+ * @brief Check if a device provides a programmable frequency synthesizer.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_synth preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_synth
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_synth" ) _MBG_API mbg_dev_has_synth( MBG_DEV_HANDLE dh, int *p ) ;
/**
- @brief Wait until the next second change, then return current time.
+ * @brief Check if a device provides GPIO signal inputs and/or outputs.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_gpio preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_gpio
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_gpio" ) _MBG_API mbg_dev_has_gpio( MBG_DEV_HANDLE dh, int *p ) ;
- Returns time in a ::PCPS_TIME structure similar to mbg_get_time().
+ /**
+ * @brief Check if a device supports configuration of antenna cable length.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_cab_len preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_cab_len
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_cab_len" ) _MBG_API mbg_dev_has_cab_len( MBG_DEV_HANDLE dh, int *p ) ;
- <b>Note:</b> This API call is supported under Windows only.
- The call blocks until the kernel driver detects a second change
- reported by the device.
+ /**
+ * @brief Check if a device provides a configurable ref time offset.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_ref_offs preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_ref_offs
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_ref_offs" ) _MBG_API mbg_dev_has_ref_offs( MBG_DEV_HANDLE dh, int *p ) ;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_TIME structure to be filled up
+ /**
+ * @brief Check if a device supports the ::MBG_OPT_INFO/::MBG_OPT_SETTINGS.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_opt_flags preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_opt_flags
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_opt_flags" ) _MBG_API mbg_dev_has_opt_flags( MBG_DEV_HANDLE dh, int *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Check if a device support reading/writing of ::UTC parameters.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_utc_parm preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_utc_parm
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_utc_parm" ) _MBG_API mbg_dev_has_utc_parm( MBG_DEV_HANDLE dh, int *p ) ;
- @see mbg_get_time()
- */
- _MBG_API_ATTR int _MBG_API mbg_get_time_sec_change( MBG_DEV_HANDLE dh, PCPS_TIME *p ) ;
+ /**
+ * @brief Check if a device supports reading correlation info
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_has_corr_info preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_corr_info
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_has_corr_info" ) _MBG_API mbg_dev_has_corr_info( MBG_DEV_HANDLE dh, int *p ) ;
/**
- @brief Read the card's current time with high resolution, plus status.
+ * @brief Check if a device supports configurable distance from transmitter
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_tr_distance preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_tr_distance
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_tr_distance" ) _MBG_API mbg_dev_has_tr_distance( MBG_DEV_HANDLE dh, int *p ) ;
- Fills up a ::PCPS_HR_TIME (High Resolution time) structure containing
- the current %UTC time (seconds since 1970), %UTC offset, and status.
- The macro _pcps_has_hr_time() or the API call mbg_dev_has_hr_time()
- check whether this call is supported by a device.
+ /**
+ * @brief Check if a device provides a debug status word to be read
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_debug_status preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_debug_status
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_debug_status" ) _MBG_API mbg_dev_has_debug_status( MBG_DEV_HANDLE dh, int *p ) ;
- <b>Note:</b> This API call provides a higher accuracy and resolution
- than mbg_get_time(). However, it does not account for the latency
- which is introduced when accessing the board.
- The mbg_get_hr_time_cycles() and mbg_get_hr_time_comp() calls
- provide ways to account for and/or compensate the latency.
+ /**
+ * @brief Check if a device provides an on-board event log.
+ *
+ * @deprecated This function is deprecated. Use ::mbg_chk_dev_supp_evt_log preferably.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to an int which is updated if the API call succeeds.
+ * The flag is set != 0 if the requested feature is supported, else 0.
+ *
+ * @return ::MBG_SUCCESS on success, if *p has been updated, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_supp_evt_log
+ */
+ _MBG_API_ATTR int _DEPRECATED_BY( "mbg_chk_dev_supp_evt_log" ) _MBG_API mbg_dev_has_evt_log( MBG_DEV_HANDLE dh, int *p ) ;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_HR_TIME structure to be filled up
+ /**
+ * @brief Open a device by index, starting from 0
+ *
+ * @deprecated This function is deprecated, use ::mbg_open_device_by_name preferably.
+ *
+ * @note See comments for ::mbg_find_devices for details.
+ *
+ * @param[in] device_index Index of the device, use 0 for the first device
+ *
+ * @return A valid device handle on success, else ::MBG_INVALID_DEV_HANDLE
+ */
+ _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device( unsigned int device_index ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Get the number of supported devices installed on the computer.
+ *
+ * @deprecated This function is deprecated, ::mbg_find_devices_with_names
+ * should be used instead.
+ *
+ * @note This function is out of date since it may not work
+ * correctly for Meinberg devices which are disconnected and reconnected
+ * while the system is running (e.g. USB devices). However, the function
+ * will be kept for compatibility reasons and works correctly if all
+ * Meinberg devices are connected at system boot and are not disconnected
+ * and reconnected during operation
+ *
+ * @return The number of devices found
+ *
+ * @see ::mbg_find_devices_with_names
+ */
+ _MBG_API_ATTR int _MBG_API mbg_find_devices( void ) ;
- @see mbg_dev_has_hr_time()
- @see mbg_get_time()
- @see mbg_get_hr_time_cycles()
- @see mbg_get_hr_time_comp()
- */
- _MBG_API_ATTR int _MBG_API mbg_get_hr_time( MBG_DEV_HANDLE dh, PCPS_HR_TIME *p ) ;
+ /**
+ * @brief Allocate memory and set up a list of installed and supported devices.
+ *
+ * This function should be used preferably instead of ::mbg_find_devices.
+ *
+ * @param[in] device_list Pointer to a linked list of type ::MBG_DEVICENAME_LIST
+ * with device names. The list will be allocated by this
+ * function and has to be freed after usage by calling
+ * ::mbg_free_device_name_list.
+ * @param[in] max_devices Maximum number of devices the function should look for
+ * (must not exceed ::N_SUPP_DEV_BUS).
+ *
+ * @return number of present devices
+ *
+ * @see ::MBG_HW_NAME for the format of the unique names
+ * @see ::mbg_free_device_name_list
+ * @see ::mbg_find_devices
+ */
+ _MBG_API_ATTR int _MBG_API mbg_find_devices_with_names( MBG_DEVICENAME_LIST **device_list, int max_devices ) ;
- /* (Intentionally excluded from Doxygen )
- Write a high resolution time stamp ::PCPS_TIME_STAMP to a device
- to configure a %UTC time when the clock shall generate an event.
- The macro _pcps_has_event_time() or the API call mbg_dev_has_event_time()
- check whether this call is supported by a device.
+ /**
+ * @brief Free the memory allocated for a ::MBG_DEVICENAME_LIST.
+ *
+ * The list may have been set up and allocated before
+ * by ::mbg_find_devices_with_names.
+ *
+ * @param[in,out] list Linked list of type ::MBG_DEVICENAME_LIST
+ *
+ * @see ::mbg_find_devices_with_names
+ */
+ _MBG_API_ATTR void _MBG_API mbg_free_device_name_list( MBG_DEVICENAME_LIST *list) ;
- <b>Note:</b> This is only supported by some special firmware.
+ /**
+ * @brief Return a handle to a device with a certain unique name.
+ *
+ * The names of the devices that are installed on the system can be retrieved by
+ * the function ::mbg_find_devices_with_names.
+ *
+ * This function should be used preferably instead of ::mbg_open_device.
+ *
+ * @param[in] srch_name String with the unique name of the device to be opened
+ * @param[in] selection_mode One of the enum values of ::MBG_MATCH_MODE
+ *
+ * @return On success, the function returns a handle to the device, otherwise ::MBG_INVALID_DEV_HANDLE
+ *
+ * @see ::MBG_HW_NAME for the format of the unique names
+ * @see ::MBG_MATCH_MODE
+ * @see ::mbg_find_devices_with_names
+ */
+ _MBG_API_ATTR MBG_DEV_HANDLE _MBG_API mbg_open_device_by_name( const char *srch_name, int selection_mode ) //##++++
+;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_TIME_STAMP structure to be written
+ /**
+ * @brief Close a handle to a device and set the handle value to ::MBG_INVALID_DEV_HANDLE.
+ *
+ * @param[in,out] dev_handle Pointer to a Meinberg device handle
+ */
+ _MBG_API_ATTR void _MBG_API mbg_close_device( MBG_DEV_HANDLE *dev_handle ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Read information about the driver handling a given device
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] *p A ::PCPS_DRVR_INFO structure to be filled up.
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_drvr_info( MBG_DEV_HANDLE dh, PCPS_DRVR_INFO *p ) ;
- @see mbg_dev_has_event_time()
- */
- _MBG_API_ATTR int _MBG_API mbg_set_event_time( MBG_DEV_HANDLE dh, const PCPS_TIME_STAMP *p ) ;
+ /**
+ * @brief Read detailed device information
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] *p A ::PCPS_DEV structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_device_info( MBG_DEV_HANDLE dh, PCPS_DEV *p ) ;
/**
- @brief Read the serial port configuration from an old type of device.
+ * @brief Read the current state of the on-board ::PCPS_STATUS_PORT
+ *
+ * This function is useful to read the device's status port which
+ * also includes the ::PCPS_ST_MOD bit reflecting the time code
+ * modulation of long wave receivers.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] *p A ::PCPS_STATUS_PORT value to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see @ref group_status_port "bitmask" //### TODO check syntax
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_status_port( MBG_DEV_HANDLE dh, PCPS_STATUS_PORT *p ) ;
+
+ /* (Intentionally excluded from Doxygen)
+ * Generic read function which writes a command code to a device
+ * and reads a number of replied data to a generic buffer.
+ *
+ * <b>Warning</b>: This is for debugging purposes only!
+ * The specialized API calls should be used preferably.
+ * Not all devices support each of the ::PC_GPS_COMMANDS.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] cmd Can be any @ref PCPS_CMD_CODES "command code" supported by the device
+ * @param[out] p Pointer to a buffer to be filled up
+ * @param[in] size Size of the output buffer
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_generic_write
+ * @see ::mbg_generic_read_gps
+ * @see ::mbg_generic_write_gps
+ * @see ::mbg_generic_io
+ */
+ _MBG_API_ATTR int _MBG_API mbg_generic_read( MBG_DEV_HANDLE dh, int cmd, void *p, int size ) ;
+
+ /* (Intentionally excluded from Doxygen)
+ * Generic read function which writes a GPS command code to a device
+ * and reads a number of data bytes back into a generic buffer.
+ * The function ::mbg_chk_dev_has_gps_data can be used to check
+ * whether this call is supported by a device.
+ *
+ * <b>Warning</b>: This is for debugging purposes only!
+ * The specialized API calls should be used preferably.
+ * Not all devices support each of the ::PC_GPS_COMMANDS.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] cmd One of the ::PCPS_CMD_CODES supported by the device.
+ * @param[out] p Pointer to a buffer to be filled up
+ * @param[in] size Size of the buffer, has to match the expected data size associated with cmd
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_gps_data
+ * @see ::mbg_generic_write_gps
+ * @see ::mbg_generic_read
+ * @see ::mbg_generic_write
+ * @see ::mbg_generic_io
+ */
+ _MBG_API_ATTR int _MBG_API mbg_generic_read_gps( MBG_DEV_HANDLE dh, int cmd, void *p, int size ) ;
+
+ /* (Intentionally excluded from Doxygen)
+ * Generic write function which writes a command code plus an
+ * associated number of data bytes to a device.
+ *
+ * <b>Warning</b>: This is for debugging purposes only!
+ * The specialized API calls should be used preferably.
+ * Not all devices support each of the ::PC_GPS_COMMANDS.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] cmd One of the ::PCPS_CMD_CODES supported by the device.
+ * @param[in] p Pointer to a buffer of data to be written
+ * @param[in] size Size of the buffer, has to match the expected data size associated with cmd
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_generic_read
+ * @see ::mbg_generic_read_gps
+ * @see ::mbg_generic_write_gps
+ * @see ::mbg_generic_io
+ */
+ _MBG_API_ATTR int _MBG_API mbg_generic_write( MBG_DEV_HANDLE dh, int cmd, const void *p, int size ) ;
+
+ /* (Intentionally excluded from Doxygen)
+ * Generic write function which writes a GPS command code plus an
+ * associated number of data bytes to a device.
+ * The function ::mbg_chk_dev_has_gps_data can be used to check
+ * whether this call is supported by a device.
+ *
+ * <b>Warning</b>: This is for debugging purposes only!
+ * The specialized API calls should be used preferably.
+ * Not all devices support each of the ::PC_GPS_COMMANDS.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] cmd One of the ::PCPS_CMD_CODES supported by the device.
+ * @param[in] p Pointer to a buffer of data to be written
+ * @param[in] size Size of the buffer, has to match the expected data size associated with cmd
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_chk_dev_has_gps_data
+ * @see ::mbg_generic_read_gps
+ * @see ::mbg_generic_read
+ * @see ::mbg_generic_write
+ * @see ::mbg_generic_io
+ */
+ _MBG_API_ATTR int _MBG_API mbg_generic_write_gps( MBG_DEV_HANDLE dh, int cmd, const void *p, int size ) ;
- <b>Note:</b> Direct usage of this function is obsolete.
+ /* (Intentionally excluded from Doxygen)
+ * Write and/or read generic data to/from a device.
+ * The function ::mbg_chk_dev_has_generic_io checks
+ * whether this call is supported by a device.
+ *
+ * <b>Warning</b>: This call is for debugging purposes and internal use only!
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_generic_io
+ * @see ::mbg_generic_read
+ * @see ::mbg_generic_write
+ * @see ::mbg_generic_read_gps
+ * @see ::mbg_generic_write_gps
+ */
+ _MBG_API_ATTR int _MBG_API mbg_generic_io( MBG_DEV_HANDLE dh, int type, const void *in_p, int in_sz, void *out_p, int out_sz ) ;
- The generic API function mbg_get_serial_settings() should be used instead
- which fully supports the capabilities of current devices.
+ /**
+ * @brief Read a ::PCPS_TIME structure returning the current date/time/status.
+ *
+ * The returned time is local time according to the card's time zone setting,
+ * with a resolution of 10 ms (i.e. 10ths of seconds).
+ *
+ * This call is supported by any device manufactured by Meinberg.
+ * However, for higher accuracy and resolution the @ref pcps_hr_time_fncs or
+ * the @ref pcps_fast_timestamp_fncs group of calls should be used preferably,
+ * if supported by the device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_TIME structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_set_time
+ * @see ::mbg_get_sync_time
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_time( MBG_DEV_HANDLE dh, PCPS_TIME *p ) ;
- The macro _pcps_has_serial() checks whether this call
- is supported by a device.
+ /**
+ * @brief Set the device's on-board clock to a given date and time.
+ *
+ * The macro ::_pcps_can_set_time checks whether this call
+ * is supported by a device.
+ *
+ * @todo Provide an API function replacing ::_pcps_can_set_time.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] p Pointer to a ::PCPS_STIME structure to be written
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_SERIAL structure to be filled up
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_time
+ */
+ _MBG_API_ATTR int _MBG_API mbg_set_time( MBG_DEV_HANDLE dh, const PCPS_STIME *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Read the time when the device has last recently synchronized.
+ *
+ * Fills a ::PCPS_TIME structure with the date/time/status reporting
+ * when the device was synchronized the last time to its time source,
+ * e.g. the DCF77 signal, the GPS satellites, or similar.
+ *
+ * The macro ::_pcps_has_sync_time checks whether this call
+ * is supported by a device.
+ *
+ * <b>Note:</b> If that information is not available on the board then
+ * the value of the returned ::PCPS_TIME::sec field is set to 0xFF.
+ * The macro ::_pcps_time_is_read can be used to check whether the
+ * returned information is valid, or "not set".
+ *
+ * @todo Provide an API function replacing ::_pcps_has_sync_time.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_TIME structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_time
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_sync_time( MBG_DEV_HANDLE dh, PCPS_TIME *p ) ;
- @see \ref group_cmd_bytes
- @see mbg_get_serial_settings()
- */
- _MBG_API_ATTR int _MBG_API mbg_get_serial( MBG_DEV_HANDLE dh, PCPS_SERIAL *p ) ;
+ /**
+ * @brief Wait until the next second change, then return current time.
+ *
+ * Returns time in a ::PCPS_TIME structure similar to ::mbg_get_time.
+ *
+ * <b>Note:</b> This API call is supported under Windows only.
+ * The call blocks until the kernel driver detects a second change
+ * reported by the device. The accuracy of this call is limited
+ * to a few milliseconds.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_TIME structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_time
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_time_sec_change( MBG_DEV_HANDLE dh, PCPS_TIME *p ) ;
/**
- @brief Write the serial port configuration to an old type of device.
+ * @brief Read the card's current time with high resolution, plus status.
+ *
+ * Fills up a ::PCPS_HR_TIME (High Resolution time) structure containing
+ * the current %UTC time (seconds since 1970), %UTC offset, and status.
+ *
+ * The API call ::mbg_chk_dev_has_hr_time checks whether this call
+ * is supported by the device.
+ *
+ * For details see @ref ::pcps_hr_time_fncs
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_HR_TIME structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_hr_time_fncs
+ * @see @ref pcps_hr_time_fncs
+ * @see @ref pcps_fast_timestamp_fncs
+ * @see @ref pcps_std_time_fncs
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_hr_time( MBG_DEV_HANDLE dh, PCPS_HR_TIME *p ) ;
- <b>Note:</b> Direct usage of this function is obsolete.
+ /* (Intentionally excluded from Doxygen )
+ Write a high resolution time stamp ::PCPS_TIME_STAMP to a device
+ to configure a %UTC time when the clock shall generate an event.
+ The macro _pcps_has_event_time() or the API call mbg_dev_has_event_time()
+ check whether this call is supported by a device.
- The generic API function mbg_save_serial_settings() should be used instead
- which fully supports the capabilities of current devices.
+ <b>Note:</b> This is only supported by some special firmware.
- The macro _pcps_has_serial() checks whether this call
- is supported by a device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ @param *p Pointer to a ::PCPS_TIME_STAMP structure to be written
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_SERIAL structure to be written
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_event_time
+ */
+ _MBG_API_ATTR int _MBG_API mbg_set_event_time( MBG_DEV_HANDLE dh, const PCPS_TIME_STAMP *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Read the serial port configuration from an old type of device
+ *
+ * @deprecated Direct usage of this function is deprecated. The generic
+ * API function ::mbg_get_serial_settings should be used instead
+ * which fully supports the capabilities of current devices.
+ *
+ * The macro ::_pcps_has_serial checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] p Pointer to a ::PCPS_SERIAL structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_serial_settings
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_serial( MBG_DEV_HANDLE dh, PCPS_SERIAL *p ) ;
- @see \ref group_cmd_bytes
- @see mbg_save_serial_settings()
- */
+ /**
+ * @brief Write the serial port configuration to an old type of device
+ *
+ * @deprecated Direct usage of this function is deprecated. The generic
+ * API function ::mbg_save_serial_settings should be used instead
+ * which fully supports the capabilities of current devices.
+ *
+ * The macro ::_pcps_has_serial checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[in] p Pointer to a ::PCPS_SERIAL structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_save_serial_settings
+ */
_MBG_API_ATTR int _MBG_API mbg_set_serial( MBG_DEV_HANDLE dh, const PCPS_SERIAL *p ) ;
/**
- @brief Read time zone/daylight saving configuration code from a device.
+ * @brief Read time zone/daylight saving configuration code from a device.
The APIs using TZCODE are only supported by some simpler cards
and allow just a very basic configuration.
@@ -970,21 +2694,20 @@ extern "C" {
calls instead which allow for a more detailed configuration of the
time zone and daylight saving settings.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TZCODE structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_tzcode()
- @see mbg_set_tzcode()
- @see mbg_get_pcps_tzdl()
- @see mbg_get_gps_tzdl()
- @see \ref group_cmd_bytes
- */
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_tzcode
+ * @see ::mbg_set_tzcode
+ * @see ::mbg_get_pcps_tzdl
+ * @see ::mbg_get_gps_tzdl
+ */
_MBG_API_ATTR int _MBG_API mbg_get_tzcode( MBG_DEV_HANDLE dh, PCPS_TZCODE *p ) ;
/**
- @brief Write time zone/daylight saving configuration code to a device.
+ * @brief Write time zone/daylight saving configuration code to a device.
The APIs using TZCODE are only supported by some simpler cards
and allow just a very basic configuration.
@@ -996,21 +2719,20 @@ extern "C" {
calls instead which allow for a more detailed configuration of the
time zone and daylight saving settings.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TZCODE structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_tzcode()
- @see mbg_get_tzcode()
- @see mbg_set_pcps_tzdl()
- @see mbg_set_gps_tzdl()
- @see \ref group_cmd_bytes
- */
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_tzcode
+ * @see ::mbg_get_tzcode
+ * @see ::mbg_set_pcps_tzdl
+ * @see ::mbg_set_gps_tzdl
+ */
_MBG_API_ATTR int _MBG_API mbg_set_tzcode( MBG_DEV_HANDLE dh, const PCPS_TZCODE *p ) ;
/**
- @brief Read time zone/daylight saving parameters from a device.
+ * @brief Read time zone/daylight saving parameters from a device.
This function fills up a ::PCPS_TZDL structure which supports a more
detailed configuration of time zone and daylight saving than the TZCODE
@@ -1022,21 +2744,20 @@ extern "C" {
Other cards may support the mbg_get_tzcode() or mbg_get_gps_tzdl()
calls instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TZDL structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_pcps_tzdl()
- @see mbg_set_pcps_tzdl()
- @see mbg_get_tzcode()
- @see mbg_get_gps_tzdl()
- @see \ref group_cmd_bytes
+ * @see ::mbg_dev_has_pcps_tzdl
+ * @see ::mbg_set_pcps_tzdl
+ * @see ::mbg_get_tzcode
+ * @see ::mbg_get_gps_tzdl
*/
_MBG_API_ATTR int _MBG_API mbg_get_pcps_tzdl( MBG_DEV_HANDLE dh, PCPS_TZDL *p ) ;
/**
- @brief Write time zone/daylight saving parameters to a device.
+ * @brief Write time zone/daylight saving parameters to a device.
This function passes a ::PCPS_TZDL structure to a device which supports
a more detailed configuration of time zone and daylight saving than the
@@ -1047,21 +2768,20 @@ extern "C" {
Other cards may support the mbg_set_tzcode() or mbg_set_gps_tzdl()
calls instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TZDL structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_pcps_tzdl()
- @see mbg_get_pcps_tzdl()
- @see mbg_set_tzcode()
- @see mbg_set_gps_tzdl()
- @see \ref group_cmd_bytes
+ * @see ::mbg_dev_has_pcps_tzdl
+ * @see ::mbg_get_pcps_tzdl
+ * @see ::mbg_set_tzcode
+ * @see ::mbg_set_gps_tzdl
*/
_MBG_API_ATTR int _MBG_API mbg_set_pcps_tzdl( MBG_DEV_HANDLE dh, const PCPS_TZDL *p ) ;
/**
- @brief Read the %UTC offset configuration of the reference time from a device.
+ * @brief Read the %UTC offset configuration of the reference time from a device.
This parameter is used to specify the %UTC offset of an incoming
reference time signal if a kind of time signal e.g. an IRIG input
@@ -1070,19 +2790,18 @@ extern "C" {
The macro _pcps_has_ref_offs() or the API call mbg_dev_has_ref_offs()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_REF_OFFS value to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ref_offs()
- @see mbg_set_ref_offs()
- @see ::PCPS_GET_REF_OFFS
+ * @see ::mbg_dev_has_ref_offs
+ * @see ::mbg_set_ref_offs
*/
_MBG_API_ATTR int _MBG_API mbg_get_ref_offs( MBG_DEV_HANDLE dh, MBG_REF_OFFS *p ) ;
/**
- @brief Write the %UTC offset configuration of the reference time to a device.
+ * @brief Write the %UTC offset configuration of the reference time to a device.
This parameter is used to specify the %UTC offset of an incoming
reference time signal if a kind of time signal e.g. an IRIG input
@@ -1091,158 +2810,144 @@ extern "C" {
The macro _pcps_has_ref_offs() or the API call mbg_dev_has_ref_offs()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_REF_OFFS value to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ref_offs()
- @see mbg_get_ref_offs()
- @see ::PCPS_SET_REF_OFFS
+ * @see ::mbg_dev_has_ref_offs
+ * @see ::mbg_get_ref_offs
*/
_MBG_API_ATTR int _MBG_API mbg_set_ref_offs( MBG_DEV_HANDLE dh, const MBG_REF_OFFS *p ) ;
/**
- @brief Read a ::MBG_OPT_INFO structure containing optional settings, controlled by flags.
+ * @brief Read a ::MBG_OPT_INFO structure containing optional settings, controlled by flags.
The ::MBG_OPT_INFO structure contains a mask of supported flags plus the current
settings of those flags.
The macro _pcps_has_opt_flags() or the API call mbg_dev_has_opt_flags()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_OPT_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_opt_flags()
- @see mbg_set_opt_settings()
+ * @see ::mbg_dev_has_opt_flags
+ * @see ::mbg_set_opt_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_opt_info( MBG_DEV_HANDLE dh, MBG_OPT_INFO *p ) ;
/**
- @brief Write a ::MBG_OPT_SETTINGS structure containing optional device settings.
+ * @brief Write a ::MBG_OPT_SETTINGS structure containing optional device settings.
The macro _pcps_has_opt_flags() or the API call mbg_dev_has_opt_flags()
check whether this call is supported by a device.
The ::MBG_OPT_INFO structure should be read first to check which of the specified
flag is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_OPT_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_opt_flags()
- @see mbg_get_opt_info()
+ * @see ::mbg_dev_has_opt_flags
+ * @see ::mbg_get_opt_info
*/
_MBG_API_ATTR int _MBG_API mbg_set_opt_settings( MBG_DEV_HANDLE dh, const MBG_OPT_SETTINGS *p ) ;
/**
- @brief Read the current IRIG input settings plus the supported settings.
-
- Calling this function directly is usually obsolete. The function
- mbg_get_all_irig_rx_info() should be used instead which also reads some
- other associated parameters affecting the behaviour of the IRIG input.
-
- The macro _pcps_is_irig_rx() or the API call mbg_dev_is_irig_rx()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an ::IRIG_INFO structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_all_irig_rx_info()
- @see mbg_set_irig_rx_settings()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
- */
+ * @brief Read the current IRIG input settings plus capabilities
+ *
+ * @deprecated Calling this function directly is deprecated. The function
+ * ::mbg_get_all_irig_rx_info should be used instead which also reads some
+ * other associated parameters affecting the behaviour of the IRIG input.
+ *
+ * The API call ::mbg_dev_is_irig_rx checks whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] *p An ::IRIG_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_all_irig_rx_info
+ * @see ::mbg_set_irig_rx_settings
+ * @see ::mbg_dev_is_irig_rx
+ * @see ::mbg_dev_has_irig_tx
+ * @see ::mbg_dev_has_irig
+ * @see @ref group_icode
+ */
_MBG_API_ATTR int _MBG_API mbg_get_irig_rx_info( MBG_DEV_HANDLE dh, IRIG_INFO *p ) ;
/**
- @brief Write an ::IRIG_SETTINGS structure to a device to configure an IRIG input.
-
- Calling this function directly is usually obsolete. The function
- mbg_set_all_irig_rx_info() should be used instead which also writes some
- other associated parameters affecting the behaviour of the IRIG input.
-
- The macro _pcps_is_irig_rx() or the API call mbg_dev_is_irig_rx()
- check whether this call is supported by a device.
- The ::IRIG_INFO structure should be read first to determine the possible
- settings supported by this card's IRIG input.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::IRIG_SETTINGS structure to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_set_all_irig_rx_info()
- @see mbg_get_irig_rx_info()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
- */
+ * @brief Write an ::IRIG_SETTINGS structure to a device to configure an IRIG input.
+ *
+ * @deprecated Calling this function directly is deprecated. The function
+ * ::mbg_save_all_irig_rx_settings should be used instead which also writes some
+ * other associated parameters affecting the behaviour of the IRIG input.
+ *
+ * The API call ::mbg_dev_is_irig_rx checks whether this call is supported
+ * by a device. The ::IRIG_INFO structure should be read first to determine
+ * the possible settings supported by the device's IRIG input.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] p Pointer to a ::IRIG_SETTINGS structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_save_all_irig_rx_settings
+ * @see ::mbg_get_irig_rx_info
+ * @see ::mbg_dev_is_irig_rx
+ * @see ::mbg_dev_has_irig_tx
+ * @see ::mbg_dev_has_irig
+ * @see @ref group_icode
+ */
_MBG_API_ATTR int _MBG_API mbg_set_irig_rx_settings( MBG_DEV_HANDLE dh, const IRIG_SETTINGS *p ) ;
/**
- @brief Read all IRIG input configuration information from a device.
+ * @brief Read all IRIG input configuration information from a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pdev Pointer to the device's ::PCPS_DEV structure
@param p_irig_info Pointer to a ::IRIG_SETTINGS structure to be written
@param p_ref_offs Pointer to a ::MBG_REF_OFFS structure to be written
@param p_opt_info Pointer to a ::MBG_OPT_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_save_all_irig_rx_settings()
- @see mbg_set_irig_rx_settings()
- @see mbg_set_ref_offs()
- @see mbg_set_opt_settings()
+ * @see ::mbg_save_all_irig_rx_settings
+ * @see ::mbg_set_irig_rx_settings
+ * @see ::mbg_set_ref_offs
+ * @see ::mbg_set_opt_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_all_irig_rx_info( MBG_DEV_HANDLE dh, const PCPS_DEV *pdev, IRIG_INFO *p_irig_info, MBG_REF_OFFS *p_ref_offs, MBG_OPT_INFO *p_opt_info ) ;
/**
- @brief Write all IRIG input configuration settings to a device.
+ * @brief Write all IRIG input configuration settings to a device.
The macro _pcps_is_irig_rx() or the API call mbg_dev_is_irig_rx()
check whether this call is supported by a device.
The ::IRIG_INFO structure should be read first to determine the possible
settings supported by this card's IRIG input.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pdev Pointer to the device's ::PCPS_DEV structure
@param p_irig_settings Pointer to a ::IRIG_SETTINGS structure to be written
@param p_ref_offs Pointer to a ::MBG_REF_OFFS structure to be written
@param p_opt_settings Pointer to a ::MBG_OPT_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_all_irig_rx_info()
- @see mbg_set_irig_rx_settings()
- @see mbg_set_ref_offs()
- @see mbg_set_opt_settings()
+ * @see ::mbg_get_all_irig_rx_info
+ * @see ::mbg_set_irig_rx_settings
+ * @see ::mbg_set_ref_offs
+ * @see ::mbg_set_opt_settings
*/
_MBG_API_ATTR int _MBG_API mbg_save_all_irig_rx_settings( MBG_DEV_HANDLE dh, const PCPS_DEV *pdev, const IRIG_SETTINGS *p_irig_settings, const MBG_REF_OFFS *p_ref_offs, const MBG_OPT_SETTINGS *p_opt_settings ) ;
/**
- @brief Check if a device supports the mbg_get_irig_ctrl_bits() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_irig_ctrl_bits()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_irig_ctrl_bits( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read the control function bits received from an incoming IRIG signal.
+ * @brief Read the control function bits received from an incoming IRIG signal.
This function fills a ::MBG_IRIG_CTRL_BITS structure with the control function
bits decoded from the incoming IRIG signal.
@@ -1264,30 +2969,17 @@ extern "C" {
The macro _pcps_has_irig_ctrl_bits() or the API call mbg_dev_has_irig_ctrl_bits()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_IRIG_CTRL_BITS type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_irig_ctrl_bits()
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_irig_ctrl_bits
+ */
_MBG_API_ATTR int _MBG_API mbg_get_irig_ctrl_bits( MBG_DEV_HANDLE dh, MBG_IRIG_CTRL_BITS *p ) ;
/**
- @brief Check if a device supports the mbg_get_raw_irig_data() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_raw_irig_data()
- @see mbg_get_raw_irig_data_on_sec_change()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_raw_irig_data( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read raw IRIG data from an IRIG receiver.
+ * @brief Read raw IRIG data from an IRIG receiver.
This function fills a ::MBG_RAW_IRIG_DATA structure with the raw data bits received
from the incoming IRIG signal. This enables an application itself to decode the
@@ -1296,18 +2988,18 @@ extern "C" {
The macro _pcps_has_raw_irig_data() or the API call mbg_dev_has_raw_irig_data()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_RAW_IRIG_DATA type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_raw_irig_data()
- @see mbg_get_raw_irig_data_on_sec_change()
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_raw_irig_data
+ * @see ::mbg_get_raw_irig_data_on_sec_change
+ */
_MBG_API_ATTR int _MBG_API mbg_get_raw_irig_data( MBG_DEV_HANDLE dh, MBG_RAW_IRIG_DATA *p ) ;
/**
- @brief Wait for second changeover then read raw IRIG data from an IRIG receiver.
+ * @brief Wait for second changeover then read raw IRIG data from an IRIG receiver.
This function waits until the second of the device's on-board time rolls over, and
then reads the last recent raw IRIG data from the device.
@@ -1318,31 +3010,19 @@ extern "C" {
<b>Note:</b> The mbg_get_time_sec_change() function called by this function is
supported under Windows only, so this function can also only be used under Windows.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_RAW_IRIG_DATA type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_raw_irig_data()
- @see mbg_get_raw_irig_data()
- @see mbg_get_time_sec_change()
+ * @see ::mbg_dev_has_raw_irig_data
+ * @see ::mbg_get_raw_irig_data
+ * @see ::mbg_get_time_sec_change
*/
_MBG_API_ATTR int _MBG_API mbg_get_raw_irig_data_on_sec_change( MBG_DEV_HANDLE dh, MBG_RAW_IRIG_DATA *p ) ;
/**
- @brief Check if a device supports the mbg_get_irig_time() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_irig_time()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_irig_time( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read the IRIG time and day-of-year number from an IRIG receiver.
+ * @brief Read the IRIG time and day-of-year number from an IRIG receiver.
Fills up a ::PCPS_IRIG_TIME structure with the raw IRIG day-of-year number
and time decoded from the latest IRIG input frame. If the configured IRIG code
@@ -1352,33 +3032,33 @@ extern "C" {
The macro _pcps_has_irig_time() or the API call mbg_dev_has_irig_time()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_IRIG_TIME type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_irig_time()
+ * @see ::mbg_dev_has_irig_time
*/
_MBG_API_ATTR int _MBG_API mbg_get_irig_time( MBG_DEV_HANDLE dh, PCPS_IRIG_TIME *p ) ;
/**
- @brief Clear a device's on-board time capture FIFO buffer.
+ * @brief Clear a device's on-board time capture FIFO buffer.
The macro _pcps_can_clr_ucap_buff() or the API call mbg_dev_can_clr_ucap_buff()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_can_clr_ucap_buff()
- @see mbg_get_ucap_entries()
- @see mbg_get_ucap_event()
+ * @see ::mbg_dev_can_clr_ucap_buff
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_get_ucap_event
*/
_MBG_API_ATTR int _MBG_API mbg_clr_ucap_buff( MBG_DEV_HANDLE dh ) ;
/**
- @brief Read information on a device's event capture buffer.
+ * @brief Read information on a device's event capture buffer.
Fills a ::PCPS_UCAP_ENTRIES structure with the number of user capture
events actually stored in the FIFO buffer, and the maximum number of
@@ -1387,19 +3067,19 @@ extern "C" {
The macro _pcps_has_ucap() or the API call mbg_dev_has_ucap()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_UCAP_ENTRIES structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ucap()
- @see mbg_get_ucap_entries()
- @see mbg_get_ucap_event()
+ * @see ::mbg_dev_has_ucap
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_get_ucap_event
*/
_MBG_API_ATTR int _MBG_API mbg_get_ucap_entries( MBG_DEV_HANDLE dh, PCPS_UCAP_ENTRIES *p ) ;
/**
- @brief Retrieve a single time capture event from the on-board FIFO buffer.
+ * @brief Retrieve a single time capture event from the on-board FIFO buffer.
The capture event is returned in a ::PCPS_HR_TIME structure. The oldest entry
in the FIFO is retrieved and then removed from the FIFO.
@@ -1414,19 +3094,19 @@ extern "C" {
call which is obsolete but still supported for compatibility with
older cards.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_HR_TIME structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ucap()
- @see mbg_get_ucap_entries()
- @see mbg_clr_ucap_buff()
+ * @see ::mbg_dev_has_ucap
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_clr_ucap_buff
*/
_MBG_API_ATTR int _MBG_API mbg_get_ucap_event( MBG_DEV_HANDLE dh, PCPS_HR_TIME *p ) ;
/**
- @brief Read the card's time zone/daylight saving parameters.
+ * @brief Read the card's time zone/daylight saving parameters.
This function returns the time zone/daylight saving parameters
in a ::TZDL structure.
@@ -1438,21 +3118,21 @@ extern "C" {
supported by non-GPS cards. Other cards may support the mbg_get_tzcode()
or mbg_get_pcps_tzdl() calls instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TZDL structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_tzdl()
- @see mbg_set_gps_tzdl()
- @see mbg_get_tzcode()
- @see mbg_get_pcps_tzdl()
- @see \ref group_tzdl
+ * @see ::mbg_dev_has_tzdl
+ * @see ::mbg_set_gps_tzdl
+ * @see ::mbg_get_tzcode
+ * @see ::mbg_get_pcps_tzdl
+ * @see @ref group_tzdl
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_tzdl( MBG_DEV_HANDLE dh, TZDL *p ) ;
/**
- @brief Write the card's time zone/daylight saving parameters.
+ * @brief Write the card's time zone/daylight saving parameters.
This function writes the time zone/daylight saving parameters
in a ::TZDL structure to a device.
@@ -1464,21 +3144,21 @@ extern "C" {
supported by non-GPS cards. Other cards may support the mbg_set_tzcode()
or mbg_set_pcps_tzdl() calls instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TZDL structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_tzdl()
- @see mbg_get_gps_tzdl()
- @see mbg_set_tzcode()
- @see mbg_set_pcps_tzdl()
- @see \ref group_tzdl
+ * @see ::mbg_dev_has_tzdl
+ * @see ::mbg_get_gps_tzdl
+ * @see ::mbg_set_tzcode
+ * @see ::mbg_set_pcps_tzdl
+ * @see @ref group_tzdl
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_tzdl( MBG_DEV_HANDLE dh, const TZDL *p ) ;
/**
- @brief Retrieve the software revision of a GPS receiver.
+ * @brief Retrieve the software revision of a GPS receiver.
This call is obsolete but still supported for compatibility
with older GPS cards.
@@ -1489,18 +3169,18 @@ extern "C" {
<b>Note:</b> The function mbg_get_gps_receiver_info() should
be used instead, if supported by the card.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::SW_REV structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_is_gps()
- @see mbg_get_gps_receiver_info()
+ * @see ::mbg_dev_is_gps
+ * @see ::mbg_get_gps_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_sw_rev( MBG_DEV_HANDLE dh, SW_REV *p ) ;
/**
- @brief Retrieve the status of the battery buffered GPS variables.
+ * @brief Retrieve the status of the battery buffered GPS variables.
These GPS variables hold some parameters sent by the GPS satellites
which are required for proper operation. If the saved set of parameters
@@ -1510,15 +3190,15 @@ extern "C" {
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::BVAR_STAT structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_bvar_stat( MBG_DEV_HANDLE dh, BVAR_STAT *p ) ;
/**
- @brief Read the current board time using a ::TTM structure.
+ * @brief Read the current board time using a ::TTM structure.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -1526,18 +3206,18 @@ extern "C" {
<b>Note:</b> This API call is pretty slow, so the mbg_get_hr_time_..()
or mbg_get_fast_hr_timestamp...() group of calls should be used preferably.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TTM structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_hr_time()
- @see mbg_get_fast_hr_timestamp()
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_fast_hr_timestamp
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_time( MBG_DEV_HANDLE dh, TTM *p ) ;
/**
- @brief Set the time on a GPS receiver device.
+ * @brief Set the time on a GPS receiver device.
Write a ::TTM structure to a GPS receiver in order to set the
on-board date and time.
@@ -1545,15 +3225,15 @@ extern "C" {
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TTM structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_set_gps_time( MBG_DEV_HANDLE dh, const TTM *p ) ;
/**
- @brief Read a ::PORT_PARM structure with a device's serial port configuration.
+ * @brief Read a ::PORT_PARM structure with a device's serial port configuration.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -1563,17 +3243,17 @@ extern "C" {
up to 2 ports. The generic function mbg_get_serial_settings()
should be used instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PORT_PARM structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_serial_settings()
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_serial_settings
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_port_parm( MBG_DEV_HANDLE dh, PORT_PARM *p ) ;
/**
- @brief Write a ::PORT_PARM structure to configure the on-board serial ports.
+ * @brief Write a ::PORT_PARM structure to configure the on-board serial ports.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -1583,17 +3263,17 @@ extern "C" {
up to 2 ports. The generic function mbg_save_serial_settings()
should be used instead.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PORT_PARM structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_save_serial_settings()
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_save_serial_settings
+ */
_MBG_API_ATTR int _MBG_API mbg_set_gps_port_parm( MBG_DEV_HANDLE dh, const PORT_PARM *p ) ;
/**
- @brief Read an ::ANT_INFO structure to retrieve an extended GPS antenna status.
+ * @brief Read an ::ANT_INFO structure to retrieve an extended GPS antenna status.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -1604,15 +3284,15 @@ extern "C" {
the antenna has been reconnected <b>and</b> the receiver has synchronized
to the GPS satellites again.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ANT_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_ant_info( MBG_DEV_HANDLE dh, ANT_INFO *p ) ;
/**
- @brief Read a time capture event from the on-board FIFO buffer using a ::TTM structure.
+ * @brief Read a time capture event from the on-board FIFO buffer using a ::TTM structure.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
@@ -1622,98 +3302,98 @@ extern "C" {
by the device. Anyway, this call is still supported for compatibility
with older devices.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::TTM structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_ucap_entries()
- @see mbg_get_ucap_event()
- @see mbg_clr_ucap_buff()
+ * @see ::mbg_get_ucap_entries
+ * @see ::mbg_get_ucap_event
+ * @see ::mbg_clr_ucap_buff
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_ucap( MBG_DEV_HANDLE dh, TTM *p ) ;
/**
- @brief Read the ::ENABLE_FLAGS structure controlling when outputs are to be enabled.
+ * @brief Read the ::ENABLE_FLAGS structure controlling when outputs are to be enabled.
The ::ENABLE_FLAGS structure controls whether certain outputs
shall be enabled immediately after the card's power-up, or only
after the card has synchronized to its input signal.
- The macro _pcps_has_gps_data() or the API call mbg_dev_has_gps_data()
- check whether this call is supported by a device.
+ * The function ::mbg_chk_dev_has_gps_data can be used to check
+ * whether this call is supported by a device.
<b>Note:</b> Not all of the input signals specified for the
::ENABLE_FLAGS structure can be modified individually.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::ENABLE_FLAGS structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see ::ENABLE_FLAGS
- @see mbg_set_gps_enable_flags()
+ * @see ::ENABLE_FLAGS
+ * @see ::mbg_set_gps_enable_flags
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_enable_flags( MBG_DEV_HANDLE dh, ENABLE_FLAGS *p ) ;
/**
- @brief Write an ENABLE_FLAGS structure to configure when outputs shall be enabled.
+ * @brief Write an ENABLE_FLAGS structure to configure when outputs shall be enabled.
The ::ENABLE_FLAGS structure controls whether certain outputs
shall be enabled immediately after the card's power-up, or only
after the card has synchronized to its input signal.
- The macro _pcps_has_gps_data() or the API call mbg_dev_has_gps_data()
- check whether this call is supported by a device.
+ * The function ::mbg_chk_dev_has_gps_data can be used to check
+ * whether this call is supported by a device.
<b>Note:</b> Not all of the input signals specified for the
ENABLE_FLAGS structure can be modified individually.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ENABLE_FLAGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see ENABLE_FLAGS
- @see mbg_get_gps_enable_flags()
+ * @see ::ENABLE_FLAGS
+ * @see ::mbg_get_gps_enable_flags
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_enable_flags( MBG_DEV_HANDLE dh, const ENABLE_FLAGS *p ) ;
/**
- @brief Read the extended GPS receiver status from a device.
-
- The ::STAT_INFO structure reports the status of the GPS receiver,
- including mode of operation and number of visible/usable satellites.
-
- The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::STAT_INFO structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see ::STAT_INFO
-*/
+ * @brief Read the extended GPS receiver status from a device.
+ *
+ * The ::STAT_INFO structure reports the status of the GPS receiver,
+ * including mode of operation and number of visible/usable satellites.
+ *
+ * The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::STAT_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::STAT_INFO
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_stat_info( MBG_DEV_HANDLE dh, STAT_INFO *p ) ;
/**
- @brief Send a ::GPS_CMD to a GPS receiver device.
+ * @brief Send a ::GPS_CMD to a GPS receiver device.
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::GPS_CMD
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see ::PC_GPS_CMD_BOOT, ::PC_GPS_CMD_INIT_SYS, ::PC_GPS_CMD_INIT_USER, ::PC_GPS_CMD_INIT_DAC
+ * @see ::PC_GPS_CMD_BOOT, ::PC_GPS_CMD_INIT_SYS, ::PC_GPS_CMD_INIT_USER, ::PC_GPS_CMD_INIT_DAC
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_cmd( MBG_DEV_HANDLE dh, const GPS_CMD *p ) ;
/**
- @brief Read the current geographic position from a GPS device.
+ * @brief Read the current geographic position from a GPS device.
The returned ::POS structure contains the current position in
ECEF (Earth Centered, Earth Fixed) kartesian coordinates, and in
@@ -1723,18 +3403,18 @@ extern "C" {
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::POS structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_gps_pos_xyz()
- @see mbg_set_gps_pos_lla()
+ * @see ::mbg_set_gps_pos_xyz
+ * @see ::mbg_set_gps_pos_lla
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_pos( MBG_DEV_HANDLE dh, POS *p ) ;
/**
- @brief Set the GPS receiver position using ::XYZ coordinates.
+ * @brief Set the GPS receiver position using ::XYZ coordinates.
The structure ::XYZ must specify the new position in ECEF
(Earth Centered, Earth Fixed) kartesian coordinates.
@@ -1742,75 +3422,81 @@ extern "C" {
The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param p Position in ::XYZ format to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_gps_pos_lla()
- @see mbg_get_gps_pos()
+ * @see ::mbg_set_gps_pos_lla
+ * @see ::mbg_get_gps_pos
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_pos_xyz( MBG_DEV_HANDLE dh, const XYZ p ) ;
/**
- @brief Set the GPS receiver position using ::LLA coordinates.
-
- The structure LLA must specify the new position as longitude, latitude,
- and altitude, using the WGS84 geographic datum.
-
- The macro _pcps_is_gps() or the API call mbg_dev_is_gps()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device.
- @param p Position in ::LLA format to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_set_gps_pos_xyz()
- @see mbg_get_gps_pos()
-*/
+ * @brief Set the GPS receiver position using ::LLA coordinates
+ *
+ * The structure ::LLA must specify the new position as longitude,
+ * latitude, and altitude, using the WGS84 geographic datum.
+ *
+ * The macro ::_pcps_is_gps or the API call ::mbg_dev_is_gps
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param p Position in ::LLA format to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_set_gps_pos_xyz
+ * @see ::mbg_get_gps_pos
+ */
_MBG_API_ATTR int _MBG_API mbg_set_gps_pos_lla( MBG_DEV_HANDLE dh, const LLA p ) ;
/**
- @brief Read the configured GPS antenna cable length from a device.
-
- The antenna cable length parameter is used to compensate the propagation
- delay of the RF signal over the antenna cable, which is about 5 ns/m.
-
- The macro _pcps_has_cab_len() or the API call mbg_dev_has_cab_len()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device.
- @param *p ::ANT_CABLE_LEN structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_cab_len()
- @see mbg_set_gps_ant_cable_len()
-*/
+ * @brief Read the configured GPS antenna cable length from a device.
+ *
+ * The antenna cable length parameter is used by GPS/GNSS receivers
+ * to compensate the propagation delay of the RF signal over the antenna
+ * cable, which is about 5 ns/m.
+ *
+ * The macro ::_pcps_has_cab_len or the API call ::mbg_dev_has_cab_len
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p ::ANT_CABLE_LEN structure to be filled up
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_cab_len
+ * @see ::mbg_set_gps_ant_cable_len
+ */
_MBG_API_ATTR int _MBG_API mbg_get_gps_ant_cable_len( MBG_DEV_HANDLE dh, ANT_CABLE_LEN *p ) ;
/**
- @brief Write the GPS antenna cable length configuration to a device.
-
- The antenna cable length parameter is used to compensate the propagation
- delay of the RF signal over the antenna cable, which is about 5 ns/m.
-
- The macro _pcps_has_cab_len() or the API call mbg_dev_has_cab_len()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device.
- @param *p ::ANT_CABLE_LEN structure to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_cab_len()
- @see mbg_get_gps_ant_cable_len()
+ * @brief Write the GPS antenna cable length configuration to a device.
+ *
+ * The antenna cable length parameter is used by GPS/GNSS receivers
+ * to compensate the propagation delay of the RF signal over the antenna
+ * cable, which is about 5 ns/m.
+ *
+ * The macro ::_pcps_has_cab_len or the API call ::mbg_dev_has_cab_len
+ * check whether this call is supported by a device.
+ *
+ * @note Different devices may accept different maximum values, so the
+ * written value should be re-read using ::mbg_get_gps_ant_cable_len
+ * to check if the parameter has been accepted.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p ::ANT_CABLE_LEN structure to be written
+ *
+ * @return One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_cab_len
+ * @see ::mbg_get_gps_ant_cable_len
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_ant_cable_len( MBG_DEV_HANDLE dh, const ANT_CABLE_LEN *p ) ;
/**
- @brief Read the ::RECEIVER_INFO structure from a device.
+ * @brief Read the ::RECEIVER_INFO structure from a device.
The macro _pcps_has_receiver_info() or the API call mbg_dev_has_receiver_info()
check whether this call is supported by a device.
@@ -1819,17 +3505,17 @@ extern "C" {
preferably, which also sets up a basic ::RECEIVER_INFO structure
for devices which don't provide that structure by themselves.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::RECEIVER_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_setup_receiver_info()
+ * @see ::mbg_setup_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_receiver_info( MBG_DEV_HANDLE dh, RECEIVER_INFO *p ) ;
/**
- @brief Read a ::STR_TYPE_INFO_IDX array of supported string types.
+ * @brief Read a ::STR_TYPE_INFO_IDX array of supported string types.
The function mbg_setup_receiver_info() must have been called before,
and the returned ::RECEIVER_INFO structure passed to this function.
@@ -1837,20 +3523,20 @@ extern "C" {
<b>Note:</b> The function mbg_get_serial_settings() should be used preferably
to get retrieve the current port settings and configuration options.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param stii Pointer to a an array of string type information to be filled up
@param *p_ri Pointer to a ::RECEIVER_INFO structure returned by mbg_setup_receiver_info()
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_setup_receiver_info()
- @see mbg_get_gps_all_port_info()
- @see mbg_get_serial_settings()
+ * @see ::mbg_setup_receiver_info
+ * @see ::mbg_get_gps_all_port_info
+ * @see ::mbg_get_serial_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_all_str_type_info( MBG_DEV_HANDLE dh, STR_TYPE_INFO_IDX stii[], const RECEIVER_INFO *p_ri ) ;
/**
- @brief Read a ::PORT_INFO_IDX array of supported serial port configurations.
+ * @brief Read a ::PORT_INFO_IDX array of supported serial port configurations.
The function mbg_setup_receiver_info() must have been called before,
and the returned ::RECEIVER_INFO structure passed to this function.
@@ -1858,20 +3544,20 @@ extern "C" {
<b>Note:</b> The function mbg_get_serial_settings() should be used preferably
to get retrieve the current port settings and configuration options.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pii Pointer to a an array of port configuration information to be filled up
@param *p_ri Pointer to a ::RECEIVER_INFO structure returned by mbg_setup_receiver_info()
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_setup_receiver_info()
- @see mbg_get_gps_all_str_type_info()
- @see mbg_get_serial_settings()
+ * @see ::mbg_setup_receiver_info
+ * @see ::mbg_get_gps_all_str_type_info
+ * @see ::mbg_get_serial_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_all_port_info( MBG_DEV_HANDLE dh, PORT_INFO_IDX pii[], const RECEIVER_INFO *p_ri ) ;
/**
- @brief Write the configuration for a single serial port to a device.
+ * @brief Write the configuration for a single serial port to a device.
The ::PORT_SETTINGS_IDX structure contains both the ::PORT_SETTINGS
and the port index value. Except for the parameter types this call is
@@ -1883,19 +3569,19 @@ extern "C" {
<b>Note:</b> The function mbg_save_serial_settings() should be used preferably
to write new port configuration to the board.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PORT_SETTINGS_IDX structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_save_serial_settings()
- @see mbg_set_gps_port_settings()
- @see mbg_dev_has_receiver_info()
+ * @see ::mbg_save_serial_settings
+ * @see ::mbg_set_gps_port_settings
+ * @see ::mbg_dev_has_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_port_settings_idx( MBG_DEV_HANDLE dh, const PORT_SETTINGS_IDX *p ) ;
/**
- @brief Write the configuration for a single serial port to a device.
+ * @brief Write the configuration for a single serial port to a device.
The ::PORT_SETTINGS structure does not contain the port index, so the
the port index must be given separately. Except for the parameter types
@@ -1907,86 +3593,73 @@ extern "C" {
<b>Note:</b> The function mbg_save_serial_settings() should be used preferably
to write new port configuration to the board.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PORT_SETTINGS structure to be filled up
@param idx Index of the serial port to be configured (starting from 0 ).
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_save_serial_settings()
- @see mbg_set_gps_port_settings_idx()
- @see mbg_dev_has_receiver_info()
+ * @see ::mbg_save_serial_settings
+ * @see ::mbg_set_gps_port_settings_idx
+ * @see ::mbg_dev_has_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_port_settings( MBG_DEV_HANDLE dh, const PORT_SETTINGS *p, int idx ) ;
/**
- @brief Set up a ::RECEIVER_INFO structure for a device.
-
- If the device supports the ::RECEIVER_INFO structure then the structure
- is read from the device, otherwise a structure is set up using
- default values depending on the device type.
- The function mbg_get_device_info() must have been called before,
- and the returned PCPS_DEV structure passed to this function.
-
- @param dh Valid handle to a Meinberg device.
- @param *pdev Pointer to a ::PCPS_DEV structure returned by mbg_get_device_info()
- @param *p Pointer to a ::RECEIVER_INFO structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_device_info()
- @see mbg_dev_has_receiver_info()
-*/
- _MBG_API_ATTR int _MBG_API mbg_setup_receiver_info( MBG_DEV_HANDLE dh, const PCPS_DEV *pdev, RECEIVER_INFO *p ) ;
+ * @brief Set up a ::RECEIVER_INFO structure for a device.
+ *
+ * If the device supports the ::RECEIVER_INFO structure then the structure
+ * is read from the device, otherwise a structure is set up using
+ * default values depending on the device type.
+ * Optionally, the function mbg_get_device_info() may have been called
+ * before, and the returned ::PCPS_DEV structure can be passed to this
+ * function.
+ * If a NULL pointer is passed instead, the device info is retrieved
+ * directly from the device, using the device handle.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] p_dev Optional pointer to a ::PCPS_DEV structure, may be NULL
+ * @param[out] p Pointer to a ::RECEIVER_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_device_info
+ * @see ::mbg_dev_has_receiver_info
+ */
+ _MBG_API_ATTR int _MBG_API mbg_setup_receiver_info( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, RECEIVER_INFO *p ) ;
/**
- @brief Read the version code of the on-board PCI/PCIe interface ASIC.
+ * @brief Read the version code of the on-board PCI/PCIe interface ASIC.
The macro _pcps_has_asic_version() or the API call mbg_dev_has_asic_version()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCI_ASIC_VERSION type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_asic_version()
+ * @see ::mbg_dev_has_asic_version
*/
_MBG_API_ATTR int _MBG_API mbg_get_asic_version( MBG_DEV_HANDLE dh, PCI_ASIC_VERSION *p ) ;
/**
- @brief Read the features of the on-board PCI/PCIe interface ASIC.
+ * @brief Read the features of the on-board PCI/PCIe interface ASIC.
The macro _pcps_has_asic_features() or the API call mbg_dev_has_asic_features()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCI_ASIC_FEATURES type to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_asic_features()
+ * @see ::mbg_dev_has_asic_features
*/
_MBG_API_ATTR int _MBG_API mbg_get_asic_features( MBG_DEV_HANDLE dh, PCI_ASIC_FEATURES *p ) ;
/**
- @brief Check if a device supports configurable time scales.
-
- By default the cards return UTC and/or local time. However, some cards
- can be configured to return raw GPS time or TAI instead.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_time_scale_info()
- @see mbg_set_time_scale_settings()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_time_scale( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read the current time scale settings and which time scales are supported.
+ * @brief Read the current time scale settings and which time scales are supported.
The ::MBG_TIME_SCALE_INFO structure tells which time scale settings are supported
by a device, and which time scale is currently configured.
@@ -1995,18 +3668,18 @@ extern "C" {
check whether this call is supported by a device.
See also the notes for mbg_dev_has_time_scale().
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_TIME_SCALE_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_time_scale_settings()
- @see mbg_dev_has_time_scale()
+ * @see ::mbg_set_time_scale_settings
+ * @see ::mbg_dev_has_time_scale
*/
_MBG_API_ATTR int _MBG_API mbg_get_time_scale_info( MBG_DEV_HANDLE dh, MBG_TIME_SCALE_INFO *p ) ;
/**
- @brief Write the time scale configuration to a device.
+ * @brief Write the time scale configuration to a device.
The ::MBG_TIME_SCALE_SETTINGS structure determines which time scale
is to be used for the time stamps which can be read from a device.
@@ -2018,60 +3691,35 @@ extern "C" {
The function mbg_get_time_scale_info() should have been called before
in order to determine which time scales are supported by the card.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::MBG_TIME_SCALE_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_time_scale_info()
- @see mbg_dev_has_time_scale()
+ * @see ::mbg_get_time_scale_info
+ * @see ::mbg_dev_has_time_scale
*/
- _MBG_API_ATTR int _MBG_API mbg_set_time_scale_settings( MBG_DEV_HANDLE dh, MBG_TIME_SCALE_SETTINGS *p ) ;
+ _MBG_API_ATTR int _MBG_API mbg_set_time_scale_settings( MBG_DEV_HANDLE dh, const MBG_TIME_SCALE_SETTINGS *p ) ;
/**
- @brief Check if a device support reading/writing of UTC parameters.
-
- This API call checks if a device supports reading/writing a GPS UTC
- parameter set via the PC bus. Reading/writing these parameters via the
- serial port using the Meinberg binary data protocol is supported by all
- Meinberg GPS devices.
-
- The UTC parameter set is usually received from the satellites' broadcasts
- and contains the current time offset between GPS time and UTC, plus information
- on a pending leap second event.
-
- It may be useful to overwrite them to do some tests, or for applications
- where a card is freewheeling.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_utc_parm()
- @see mbg_set_utc_parm()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_utc_parm( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read a ::UTC parameter structure from a device.
+ * @brief Read a ::UTC parameter structure from a device.
The macro _pcps_has_utc_parm() or the API call mbg_dev_has_utc_parm()
check whether this call is supported by a device.
See also the notes for mbg_dev_has_utc_parm().
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::UTC structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_utc_parm()
- @see mbg_set_utc_parm()
+ * @see ::mbg_dev_has_utc_parm
+ * @see ::mbg_set_utc_parm
*/
_MBG_API_ATTR int _MBG_API mbg_get_utc_parm( MBG_DEV_HANDLE dh, UTC *p ) ;
/**
- @brief Write a ::UTC parameter structure to a device.
+ * @brief Write a ::UTC parameter structure to a device.
This should only be done for testing, or if a card is operated in
freewheeling mode. If the receiver is tracking any satellites then the settings
@@ -2082,18 +3730,18 @@ extern "C" {
check whether this call is supported by a device.
See also the notes for mbg_dev_has_utc_parm().
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a valid ::UTC structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_utc_parm()
- @see mbg_get_utc_parm()
+ * @see ::mbg_dev_has_utc_parm
+ * @see ::mbg_get_utc_parm
*/
- _MBG_API_ATTR int _MBG_API mbg_set_utc_parm( MBG_DEV_HANDLE dh, UTC *p ) ;
+ _MBG_API_ATTR int _MBG_API mbg_set_utc_parm( MBG_DEV_HANDLE dh, const UTC *p ) ;
/**
- @brief Read the current time plus the associated PC cycles from a device.
+ * @brief Read the current time plus the associated PC cycles from a device.
The ::PCPS_TIME_CYCLES structure contains a ::PCPS_TIME structure
and a PC cycle counter value which can be used to compensate the latency
@@ -2113,85 +3761,97 @@ extern "C" {
latency of the call in units of the cycle counter clock frequency, e.g as reported
by QueryPerformanceFrequency() under Windows.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TIME_CYCLES structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_hr_time_cycles()
- @see mbg_get_hr_time_comp()
- @see mbg_get_hr_time()
- @see mbg_get_time()
+ * @see ::mbg_get_hr_time_cycles
+ * @see ::mbg_get_hr_time_comp
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_time
*/
_MBG_API_ATTR int _MBG_API mbg_get_time_cycles( MBG_DEV_HANDLE dh, PCPS_TIME_CYCLES *p ) ;
/**
- @brief Read the current high resolution time plus the associated PC cycles from a device.
-
- The ::PCPS_HR_TIME_CYCLES structure contains a ::PCPS_HR_TIME structure
- and a PC cycle counter value which can be used to compensate the latency
- of the call, i.e. the program execution time until the time stamp has actually
- been read from the board.
-
- The macro _pcps_has_hr_time() or the API call mbg_dev_has_hr_time()
- check whether this call is supported by a device.
-
- The cycle counter value corresponds to a value returned by QueryPerformanceCounter()
- under Windows, and get_cycles() under Linux. On operating systems or targets which don't
- provide a cycles counter the returned cycles value is always 0.
-
- Applications should first pick up their own cycle counter value and then call
- this function. The difference of the cycle counter values corresponds to the
- latency of the call in units of the cycle counter clock frequency, e.g as reported
- by QueryPerformanceFrequency() under Windows.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_HR_TIME_CYCLES structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_hr_time_comp()
- @see mbg_get_hr_time()
- @see mbg_get_time_cycles()
- @see mbg_get_time()
-*/
+ * @brief Read the current high resolution time plus the associated PC cycles from a device.
+ *
+ * The returned ::PCPS_HR_TIME_CYCLES structure contains a ::PCPS_HR_TIME
+ * structure and a PC cycle counter value which can be used to compensate
+ * the latency of the call, i.e. the program execution time until the time stamp
+ * has actually been read from the board.
+ *
+ * The API call ::mbg_chk_dev_has_hr_time checks whether this call
+ * is supported by the device.
+ *
+ * For details see @ref ::pcps_hr_time_fncs
+ *
+ * The cycle counter value corresponds to a value returned by QueryPerformanceCounter()
+ * under Windows, and get_cycles() under Linux. On operating systems or targets which don't
+ * provide a cycles counter the returned cycles value is always 0.
+ *
+ * Applications should first pick up their own cycle counter value and then call
+ * this function. The difference of the cycle counter values corresponds to the
+ * latency of the call in units of the cycle counter clock frequency, e.g as reported
+ * by QueryPerformanceFrequency() under Windows.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_HR_TIME_CYCLES structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_hr_time_fncs
+ * @see ::mbg_chk_dev_has_hr_time
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_hr_time_cycles
+ * @see ::mbg_get_hr_time_comp
+ * @see @ref pcps_hr_time_fncs
+ * @see @ref pcps_fast_timestamp_fncs
+ * @see @ref pcps_std_time_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_hr_time_cycles( MBG_DEV_HANDLE dh, PCPS_HR_TIME_CYCLES *p ) ;
/**
- @brief Read the current high resolution time, and compensate the call's latency.
-
- Read a ::PCPS_HR_TIME structure plus cycle counter value, and correct the
- time stamp for the latency of the call as described for mbg_get_hr_time_cycles(),
- then return the compensated time stamp and optionally the latency.
-
- The macro _pcps_has_hr_time() or the API call mbg_dev_has_hr_time()
- check whether this call is supported by a device.
-
- The cycle counter value corresponds to a value returned by QueryPerformanceCounter()
- under Windows, and get_cycles() under Linux. On operating systems or targets which don't
- provide a cycles counter the returned cycles value is always 0.
-
- Applications should first pick up their own cycle counter value and then call
- this function. The difference of the cycle counter values corresponds to the
- latency of the call in units of the cycle counter clock frequency, e.g as reported
- by QueryPerformanceFrequency() under Windows.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::PCPS_HR_TIME structure to be filled up
- @param *hns_latency Optional pointer to an int32_t value to return
- the latency in 100ns units. Pass NULL if not used.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_hr_time_comp()
- @see mbg_get_hr_time()
- @see mbg_get_time_cycles()
- @see mbg_get_time()
-*/
+ * @brief Read the current high resolution time, and compensate the call's latency.
+ *
+ * Read a ::PCPS_HR_TIME structure plus cycle counter value, and correct the
+ * time stamp for the latency of the call as described for ::mbg_get_hr_time_cycles,
+ * then return the compensated time stamp and optionally the latency.
+ *
+ * The API call ::mbg_chk_dev_has_hr_time checks whether this call
+ * is supported by the device.
+ *
+ * For details see @ref ::pcps_hr_time_fncs
+ *
+ * The cycle counter value corresponds to a value returned by QueryPerformanceCounter()
+ * under Windows, and get_cycles() under Linux. On operating systems or targets which don't
+ * provide a cycles counter the returned cycles value is always 0.
+ *
+ * Applications should first pick up their own cycle counter value and then call
+ * this function. The difference of the cycle counter values corresponds to the
+ * latency of the call in units of the cycle counter clock frequency, e.g as reported
+ * by QueryPerformanceFrequency() under Windows.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::PCPS_HR_TIME structure to be filled up
+ * @param[out] hns_latency Optional pointer to an int32_t value to return
+ * the latency in 100ns units, or NULL, if not used.
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_hr_time_fncs
+ * @see ::mbg_chk_dev_has_hr_time
+ * @see ::mbg_get_hr_time
+ * @see ::mbg_get_hr_time_cycles
+ * @see ::mbg_get_hr_time_comp
+ * @see @ref pcps_hr_time_fncs
+ * @see @ref pcps_fast_timestamp_fncs
+ * @see @ref pcps_std_time_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_hr_time_comp( MBG_DEV_HANDLE dh, PCPS_HR_TIME *p, int32_t *hns_latency ) ;
/**
- @brief Read the current IRIG output settings plus the supported settings.
+ * @brief Read the current IRIG output settings plus the supported settings.
The returned ::IRIG_INFO structure contains the configuration of an IRIG output
plus the possible settings supported by that output.
@@ -2199,146 +3859,136 @@ extern "C" {
The macro _pcps_has_irig_tx() or the API call mbg_dev_has_irig_tx()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to an ::IRIG_INFO structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_irig_tx_settings()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
+ * @see ::mbg_set_irig_tx_settings
+ * @see ::mbg_dev_has_irig_tx
+ * @see ::mbg_dev_is_irig_rx
+ * @see ::mbg_dev_has_irig
+ * @see @ref group_icode
*/
_MBG_API_ATTR int _MBG_API mbg_get_irig_tx_info( MBG_DEV_HANDLE dh, IRIG_INFO *p ) ;
/**
- @brief Write an ::IRIG_SETTINGS structure to a device to configure the IRIG output.
+ * @brief Write an ::IRIG_SETTINGS structure to a device to configure the IRIG output.
The macro _pcps_has_irig_tx() or the API call mbg_dev_has_irig_tx()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to an ::IRIG_INFO structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_irig_tx_info()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
+ * @see ::mbg_get_irig_tx_info
+ * @see ::mbg_dev_has_irig_tx
+ * @see ::mbg_dev_is_irig_rx
+ * @see ::mbg_dev_has_irig
+ * @see @ref group_icode
*/
_MBG_API_ATTR int _MBG_API mbg_set_irig_tx_settings( MBG_DEV_HANDLE dh, const IRIG_SETTINGS *p ) ;
/**
- @brief Read the current frequency synthesizer settings from a device.
-
- Read a ::SYNTH structure containing the configuration of an optional
- on-board programmable frequency synthesizer.
-
- The macro _pcps_has_synth() or the API call mbg_dev_has_synth()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::SYNTH structure to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_synth()
- @see mbg_set_synth()
- @see mbg_get_synth_state()
- @see \ref group_synth
-*/
+ * @brief Read the current frequency synthesizer settings from a device.
+ *
+ * Read a ::SYNTH structure containing the configuration of an optional
+ * on-board programmable frequency synthesizer.
+ *
+ * The macro ::_pcps_has_synth or the API call ::mbg_dev_has_synth
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::SYNTH structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_synth
+ * @see ::mbg_set_synth
+ * @see ::mbg_get_synth_state
+ * @see @ref group_synth
+ */
_MBG_API_ATTR int _MBG_API mbg_get_synth( MBG_DEV_HANDLE dh, SYNTH *p ) ;
/**
- @brief Write some frequency synthesizer settings to a device.
-
- Write a ::SYNTH structure containing the configuration of an optional
- on-board programmable frequency synthesizer.
-
- The macro _pcps_has_synth() or the API call mbg_dev_has_synth()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::SYNTH structure to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_synth()
- @see mbg_get_synth()
- @see mbg_get_synth_state()
- @see \ref group_synth
-*/
+ * @brief Write some frequency synthesizer settings to a device.
+ *
+ * Write a ::SYNTH structure containing the configuration of an optional
+ * on-board programmable frequency synthesizer.
+ *
+ * The macro _pcps_has_synth() or the API call mbg_dev_has_synth()
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::SYNTH structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_synth
+ * @see ::mbg_get_synth
+ * @see ::mbg_get_synth_state
+ * @see @::\ref group_synth
+ */
_MBG_API_ATTR int _MBG_API mbg_set_synth( MBG_DEV_HANDLE dh, const SYNTH *p ) ;
/**
- @brief Read the current status of the on-board frequency synthesizer.
+ * @brief Read the current status of the on-board frequency synthesizer.
The macro _pcps_has_synth() or the API call mbg_dev_has_synth()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::SYNTH_STATE structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_synth()
- @see mbg_get_synth()
- @see mbg_set_synth()
- @see \ref group_synth
+ * @see ::mbg_dev_has_synth
+ * @see ::mbg_get_synth
+ * @see ::mbg_set_synth
+ * @see @ref group_synth
*/
_MBG_API_ATTR int _MBG_API mbg_get_synth_state( MBG_DEV_HANDLE dh, SYNTH_STATE *p ) ;
/**
- @brief Check if a device supports the mbg_get_fast_hr_timestamp_...() calls.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_fast_hr_timestamp_cycles()
- @see mbg_get_fast_hr_timestamp_comp()
- @see mbg_get_fast_hr_timestamp()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_fast_hr_timestamp( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read a high resolution ::PCPS_TIME_STAMP_CYCLES structure via memory mapped access.
+ * @brief Read a high resolution ::PCPS_TIME_STAMP_CYCLES structure via memory mapped access.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TIME_STAMP_CYCLES structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_fast_hr_timestamp()
- @see mbg_get_fast_hr_timestamp_comp()
- @see mbg_get_fast_hr_timestamp()
-*/
+ * @ingroup pcps_fast_timestamp_fncs
+ * @see ::mbg_dev_has_fast_hr_timestamp
+ * @see ::mbg_get_fast_hr_timestamp_comp
+ * @see ::mbg_get_fast_hr_timestamp
+ * @see @ref pcps_fast_timestamp_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp_cycles( MBG_DEV_HANDLE dh, PCPS_TIME_STAMP_CYCLES *p ) ;
/**
- @brief Read a high resolution timestamp and compensate the latency of the call.
+ * @brief Read a high resolution timestamp and compensate the latency of the call.
The retrieved ::PCPS_TIME_STAMP is read from memory mapped registers,
and timestamp is compensated for the call's latency before it is returned.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TIME_STAMP structure to be filled up
@param *hns_latency Optionally receive the latency in hectonanoseconds
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_fast_hr_timestamp()
- @see mbg_get_fast_hr_timestamp_cycles()
- @see mbg_get_fast_hr_timestamp()
-*/
+ * @ingroup pcps_fast_timestamp_fncs
+ * @see ::mbg_dev_has_fast_hr_timestamp
+ * @see ::mbg_get_fast_hr_timestamp_cycles
+ * @see ::mbg_get_fast_hr_timestamp
+ * @see @ref pcps_fast_timestamp_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp_comp( MBG_DEV_HANDLE dh, PCPS_TIME_STAMP *p, int32_t *hns_latency ) ;
/**
- @brief Read a high resolution ::PCPS_TIME_STAMP structure via memory mapped access.
+ * @brief Read a high resolution ::PCPS_TIME_STAMP structure via memory mapped access.
This function does not return or evaluate a cycles count, so the latency
of the call can not be determined. However, depending on the timer hardware
@@ -2346,405 +3996,21 @@ extern "C" {
on some hardware architectures, so this call can be used to yield lower
latencies, under the restriction to be unable to determine the exact latency.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_TIME_STAMP structure to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_fast_hr_timestamp()
- @see mbg_get_fast_hr_timestamp_comp()
- @see mbg_get_fast_hr_timestamp_cycles()
-*/
+ * @ingroup pcps_fast_timestamp_fncs
+ * @see ::mbg_dev_has_fast_hr_timestamp
+ * @see ::mbg_get_fast_hr_timestamp_comp
+ * @see ::mbg_get_fast_hr_timestamp_cycles
+ * @see @ref pcps_fast_timestamp_fncs
+ */
_MBG_API_ATTR int _MBG_API mbg_get_fast_hr_timestamp( MBG_DEV_HANDLE dh, PCPS_TIME_STAMP *p ) ;
/**
- @brief Check if a device is a GPS receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_is_gps( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device is a DCF77 receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_is_dcf( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device is a MSF receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_is_msf( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device is a WWVB receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_is_wwvb( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device is any long wave signal receiver.
-
- Long wave receivers include e.g. DCF77, MSF, WWVB, or JJY.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_is_lwr( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device provides a configurable IRIG input.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_irig_rx_info()
- @see mbg_set_irig_rx_settings()
- @see mbg_dev_has_irig_tx()
- @see mbg_dev_has_irig()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_is_irig_rx( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports the HR_TIME functions.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_hr_time()
- @see mbg_get_hr_time_cycles()
- @see mbg_get_hr_time_comp()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_hr_time( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports configuration of antenna cable length.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_gps_ant_cable_len()
- @see mbg_set_gps_ant_cable_len()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_cab_len( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports timezone configuration using the ::TZDL structure.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_gps_tzdl()
- @see mbg_set_gps_tzdl()
- @see mbg_dev_has_tz()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_tzdl( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports timezone configuration using the ::PCPS_TZDL structure.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_pcps_tzdl()
- @see mbg_set_pcps_tzdl()
- @see mbg_dev_has_tz()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_pcps_tzdl( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports timezone configuration using the ::PCPS_TZCODE type.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_tzcode()
- @see mbg_set_tzcode()
- @see mbg_dev_has_tz()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_tzcode( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports any kind of timezone configuration.
-
- This can be used e.g. to check if a specifig dialog or menu has to
- be displayed.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_tzdl()
- @see mbg_dev_has_pcps_tzdl()
- @see mbg_dev_has_tzcode()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_tz( MBG_DEV_HANDLE dh, int *p ) ;
-
- /* (Intentionally excluded from Doxygen)
- Check if a device supports setting an event time, i.e.
- configure a %UTC time when the clock shall generate an event.
-
- <b>Note:</b> This is only supported by some special firmware.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_set_event_time()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_event_time( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports the ::RECEIVER_INFO structure and related calls.
-
- @note Older GPS devices may not support that structure.
-
- The mbg_get_gps_receiver_info() call uses this call to decide whether a
- ::RECEIVER_INFO can be read directly from a device, or whether a default
- structure has to be set up using default values depending on the device type.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_gps_receiver_info()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_receiver_info( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports the mbg_clr_ucap_buff() call.
-
- The mbg_clr_ucap_buff() call can be used to clear a card's on-board
- time capture FIFO buffer.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_clr_ucap_buff()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_can_clr_ucap_buff( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports the mbg_get_ucap_entries() and mbg_get_ucap_event() calls.
-
- If the card does not but it is a GPS card then the card provides
- a time capture FIFO buffer and the obsolete mbg_get_gps_ucap()
- call can be used to retrieve entries from the FIFO buffer.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_ucap_entries()
- @see mbg_get_ucap_event()
- @see mbg_clr_ucap_buff()
- @see mbg_get_gps_ucap()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_ucap( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device provides a configurable IRIG output.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_irig_tx_info()
- @see mbg_set_irig_tx_settings()
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig()
- @see \ref group_icode
-
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_irig_tx( MBG_DEV_HANDLE dh, int *p ) ;
-
- /* (Intentionally excluded from Doxygen)
- Check if a device provides a serial output supporting
- higher baud rates than older cards, i.e. ::DEFAULT_BAUD_RATES_DCF_HS
- rather than ::DEFAULT_BAUD_RATES_DCF.
-
- The mbg_get_serial_settings() takes care of this, so applications
- which use that call as suggested won't need to use this call directly.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_serial_settings()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_serial_hs( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device provides the level of its inputs signal.
-
- This is useful to display the signal level of e.g. an IRIG or longwave signal.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_signal( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device provides a modulation signal.
-
- Modulation signals are e.g. the second marks of a DCF77 AM receiver.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_mod( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device provides either an IRIG input or output.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_is_irig_rx()
- @see mbg_dev_has_irig_tx()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_irig( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device provides a configurable ref time offset.
-
- This may be required to convert the received time to %UTC, if the input
- signal doesn't specify this (e.g. most IRIG code formats).
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_ref_offs()
- @see mbg_set_ref_offs()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_ref_offs( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports the ::MBG_OPT_INFO/::MBG_OPT_SETTINGS.
-
- These structures containing optional settings, controlled by flags.
- See ::MBG_OPT_SETTINGS and related definitions.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_opt_info()
- @see mbg_set_opt_settings()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_opt_flags( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports large configuration data structures.
-
- Such structures have been introduced with the first Meinberg GPS receivers.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_gps_data( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device provides a programmable frequency synthesizer.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_synth()
- @see mbg_set_synth()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_synth( MBG_DEV_HANDLE dh, int *p ) ;
-
- /* (Intentionally excluded from Doxygen)
- @brief Check if a device supports the mbg_generic_io() call.
-
- <b>Warning</b>: That call is for debugging purposes and internal use only!
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_generic_io()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_generic_io( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports the mbg_get_asic_version() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_asic_version()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_asic_version( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports the mbg_get_asic_features() call.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_asic_features()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_asic_features( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read current configuraton and features provided by the programmable pulse outputs.
+ * @brief Read current configuraton and features provided by the programmable pulse outputs.
Reads a ::POUT_INFO_IDX array of current settings and configuration
options of the device's programmable pulse outputs.
@@ -2757,20 +4023,20 @@ extern "C" {
The array passed to this function to receive the returned data
must be able to hold at least ::RECEIVER_INFO::n_prg_out elements.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pii Pointer to a an array of ::POUT_INFO_IDX structures to be filled up
@param *p_ri Pointer to a ::RECEIVER_INFO structure returned by mbg_setup_receiver_info()
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_set_gps_pout_settings_idx()
- @see mbg_set_gps_pout_settings()
- @see mbg_setup_receiver_info()
+ * @see ::mbg_set_gps_pout_settings_idx
+ * @see ::mbg_set_gps_pout_settings
+ * @see ::mbg_setup_receiver_info
*/
_MBG_API_ATTR int _MBG_API mbg_get_gps_all_pout_info( MBG_DEV_HANDLE dh, POUT_INFO_IDX pii[], const RECEIVER_INFO *p_ri ) ;
/**
- @brief Write the configuration for a single programmable pulse output
+ * @brief Write the configuration for a single programmable pulse output
The ::POUT_SETTINGS_IDX structure contains both the ::POUT_SETTINGS
and the output index value. Except for the parameter types this call
@@ -2780,18 +4046,18 @@ extern "C" {
(i.e. the number of programmable outputs on the board) is not 0, and the
output index value must be in the range 0..::RECEIVER_INFO::n_prg_out.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::POUT_SETTINGS_IDX structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_gps_all_pout_info()
- @see mbg_set_gps_pout_settings()
+ * @see ::mbg_get_gps_all_pout_info
+ * @see ::mbg_set_gps_pout_settings
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_pout_settings_idx( MBG_DEV_HANDLE dh, const POUT_SETTINGS_IDX *p ) ;
/**
- @brief Write the configuration for a single programmable pulse output
+ * @brief Write the configuration for a single programmable pulse output
The ::POUT_SETTINGS structure does not contain the index of the
programmable output to be configured, so the index must explicitely
@@ -2802,227 +4068,180 @@ extern "C" {
(i.e. the number of programmable outputs on the board) is not 0, and the
output index value must be in the range 0..::RECEIVER_INFO::n_prg_out.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::POUT_SETTINGS structure to be written
@param idx Index of the programmable pulse output to be configured (starting from 0 ).
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_gps_all_pout_info()
- @see mbg_set_gps_pout_settings_idx()
+ * @see ::mbg_get_gps_all_pout_info
+ * @see ::mbg_set_gps_pout_settings_idx
*/
_MBG_API_ATTR int _MBG_API mbg_set_gps_pout_settings( MBG_DEV_HANDLE dh, const POUT_SETTINGS *p, int idx ) ;
/**
- @brief Read a device's IRQ status information.
+ * @brief Read a device's IRQ status information.
IRQ status information includes flags indicating whether IRQs are
actually enabled, and whether IRQ support by a card is possibly
unsafe due to the firmware and interface chip version.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PCPS_IRQ_STAT_INFO variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
- */
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ */
_MBG_API_ATTR int _MBG_API mbg_get_irq_stat_info( MBG_DEV_HANDLE dh, PCPS_IRQ_STAT_INFO *p ) ;
/**
- @brief Check if a device provides simple LAN interface API calls.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_lan_if_info()
- @see mbg_get_ip4_state()
- @see mbg_get_ip4_settings()
- @see mbg_set_ip4_settings()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_lan_intf( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read LAN interface information from a device.
+ * @brief Read LAN interface information from a device.
The macro _pcps_has_lan_intf() or the API call mbg_dev_has_lan_intf()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::LAN_IF_INFO variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_lan_intf()
- @see mbg_get_ip4_state()
- @see mbg_get_ip4_settings()
- @see mbg_set_ip4_settings()
+ * @see ::mbg_dev_has_lan_intf
+ * @see ::mbg_get_ip4_state
+ * @see ::mbg_get_ip4_settings
+ * @see ::mbg_set_ip4_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_lan_if_info( MBG_DEV_HANDLE dh, LAN_IF_INFO *p ) ;
/**
- @brief Read LAN IPv4 state from a device.
+ * @brief Read LAN IPv4 state from a device.
The macro _pcps_has_lan_intf() or the API call mbg_dev_has_lan_intf()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::IP4_SETTINGS variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_lan_intf()
- @see mbg_get_lan_if_info()
- @see mbg_get_ip4_settings()
- @see mbg_set_ip4_settings()
+ * @see ::mbg_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_settings
+ * @see ::mbg_set_ip4_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_ip4_state( MBG_DEV_HANDLE dh, IP4_SETTINGS *p ) ;
/**
- @brief Read LAN IPv4 settings from a device.
+ * @brief Read LAN IPv4 settings from a device.
The macro _pcps_has_lan_intf() or the API call mbg_dev_has_lan_intf()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::IP4_SETTINGS variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_lan_intf()
- @see mbg_get_lan_if_info()
- @see mbg_get_ip4_state()
- @see mbg_set_ip4_settings()
+ * @see ::mbg_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_state
+ * @see ::mbg_set_ip4_settings
*/
_MBG_API_ATTR int _MBG_API mbg_get_ip4_settings( MBG_DEV_HANDLE dh, IP4_SETTINGS *p ) ;
/**
- @brief Write LAN IPv4 settings to a device.
+ * @brief Write LAN IPv4 settings to a device.
The macro _pcps_has_lan_intf() or the API call mbg_dev_has_lan_intf()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p ::IP4_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_lan_intf()
- @see mbg_get_lan_if_info()
- @see mbg_get_ip4_settings()
+ * @see ::mbg_dev_has_lan_intf
+ * @see ::mbg_get_lan_if_info
+ * @see ::mbg_get_ip4_settings
*/
_MBG_API_ATTR int _MBG_API mbg_set_ip4_settings( MBG_DEV_HANDLE dh, const IP4_SETTINGS *p ) ;
/**
- @brief Check if a device provides PTP configuration/status calls.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_state
- @see mbg_get_ptp_cfg_info
- @see mbg_set_ptp_cfg_settings
- @see mbg_dev_has_ptp_unicast
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_ptp( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device provides PTP unicast feature/configuration.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_uc_master_cfg_limits
- @see mbg_get_all_ptp_uc_master_info
- @see mbg_set_ptp_uc_master_settings_idx
- @see mbg_get_ptp_state
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_ptp_unicast( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read PTP/IEEE1588 status from a device.
+ * @brief Read PTP/IEEE1588 status from a device.
The macro _pcps_has_ptp() or the API call mbg_dev_has_ptp()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PTP_STATE variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_cfg_info
- @see mbg_set_ptp_cfg_settings
- @see mbg_dev_has_ptp_unicast
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_cfg_info
+ * @see ::mbg_set_ptp_cfg_settings
+ * @see ::mbg_dev_has_ptp_unicast
*/
_MBG_API_ATTR int _MBG_API mbg_get_ptp_state( MBG_DEV_HANDLE dh, PTP_STATE *p ) ;
/**
- @brief Read PTP/IEEE1588 config info and current settings from a device.
+ * @brief Read PTP/IEEE1588 config info and current settings from a device.
The macro _pcps_has_ptp() or the API call mbg_dev_has_ptp()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PTP_CFG_INFO variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_state
- @see mbg_set_ptp_cfg_settings
- @see mbg_dev_has_ptp_unicast
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_state
+ * @see ::mbg_set_ptp_cfg_settings
+ * @see ::mbg_dev_has_ptp_unicast
*/
_MBG_API_ATTR int _MBG_API mbg_get_ptp_cfg_info( MBG_DEV_HANDLE dh, PTP_CFG_INFO *p ) ;
/**
- @brief Write PTP/IEEE1588 configuration settings to a device.
+ * @brief Write PTP/IEEE1588 configuration settings to a device.
The macro _pcps_has_ptp() or the API call mbg_dev_has_ptp()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p ::PTP_CFG_SETTINGS structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_state
- @see mbg_get_ptp_cfg_info
- @see mbg_dev_has_ptp_unicast
+ * @see ::mbg_dev_has_ptp
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_state
+ * @see ::mbg_get_ptp_cfg_info
+ * @see ::mbg_dev_has_ptp_unicast
*/
_MBG_API_ATTR int _MBG_API mbg_set_ptp_cfg_settings( MBG_DEV_HANDLE dh, const PTP_CFG_SETTINGS *p ) ;
/**
- @brief Read PTP/IEEE1588 unicast master configuration limits from a device.
+ * @brief Read PTP/IEEE1588 unicast master configuration limits from a device.
The macro _pcps_has_ri_ptp_unicast() or the API call mbg_dev_has_ptp_unicast()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p Pointer to a ::PTP_UC_MASTER_CFG_LIMITS variable to be filled up
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp_unicast
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_all_ptp_uc_master_info
- @see mbg_set_ptp_uc_master_settings_idx
- @see mbg_get_ptp_state
+ * @see ::mbg_dev_has_ptp_unicast
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_all_ptp_uc_master_info
+ * @see ::mbg_set_ptp_uc_master_settings_idx
+ * @see ::mbg_get_ptp_state
*/
_MBG_API_ATTR int _MBG_API mbg_get_ptp_uc_master_cfg_limits( MBG_DEV_HANDLE dh, PTP_UC_MASTER_CFG_LIMITS *p ) ;
/**
- @brief Read PTP Unicast master settings and configuration options.
+ * @brief Read PTP Unicast master settings and configuration options.
The function mbg_setup_receiver_info() must have been called before,
and the returned ::RECEIVER_INFO structure passed to this function.
@@ -3032,334 +4251,497 @@ extern "C" {
The array passed to this function to receive the returned data
must be able to hold at least ::RECEIVER_INFO::n_prg_out elements.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param pii Pointer to a an array of ::PTP_UC_MASTER_INFO_IDX structures to be filled up
@param p_umsl Pointer to a ::PTP_UC_MASTER_CFG_LIMITS structure returned by mbg_get_ptp_uc_master_cfg_limits()
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp_unicast
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_uc_master_cfg_limits
- @see mbg_set_ptp_uc_master_settings_idx
- @see mbg_get_ptp_state
+ * @see ::mbg_dev_has_ptp_unicast
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_uc_master_cfg_limits
+ * @see ::mbg_set_ptp_uc_master_settings_idx
+ * @see ::mbg_get_ptp_state
*/
_MBG_API_ATTR int _MBG_API mbg_get_all_ptp_uc_master_info( MBG_DEV_HANDLE dh, PTP_UC_MASTER_INFO_IDX pii[], const PTP_UC_MASTER_CFG_LIMITS *p_umsl ) ;
/**
- @brief Write PTP/IEEE1588 unicast configuration settings to a device.
+ * @brief Write PTP/IEEE1588 unicast configuration settings to a device.
The macro _pcps_has_ri_ptp_unicast() or the API call mbg_dev_has_ptp_unicast()
check whether this call is supported by a device.
- @param dh Valid handle to a Meinberg device.
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
@param *p ::PTP_UC_MASTER_SETTINGS_IDX structure to be written
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_dev_has_ptp_unicast
- @see mbg_get_all_ptp_cfg_info
- @see mbg_get_ptp_uc_master_cfg_limits
- @see mbg_get_all_ptp_uc_master_info
- @see mbg_get_ptp_state
+ * @see ::mbg_dev_has_ptp_unicast
+ * @see ::mbg_get_all_ptp_cfg_info
+ * @see ::mbg_get_ptp_uc_master_cfg_limits
+ * @see ::mbg_get_all_ptp_uc_master_info
+ * @see ::mbg_get_ptp_state
*/
_MBG_API_ATTR int _MBG_API mbg_set_ptp_uc_master_settings_idx( MBG_DEV_HANDLE dh, const PTP_UC_MASTER_SETTINGS_IDX *p ) ;
/**
- @brief Read both system time and associated device time from the kernel driver.
-
- The kernel driver reads the current system time plus a HR time structure
- from a card immediately after each other. The returned info structure also
- contains some cycles counts to be able to determine the execution times
- required to read those time stamps.
-
- The advantage of this call compared to mbg_get_time_info_tstamp() is
- that this call also returns the card's status. On the other hand, reading
- the HR time from the card may block e.g. if another application accesses
- the board.
-
- This call makes a mbg_get_hr_time_cycles() call internally so the macro
- _pcps_has_hr_time() or the API call mbg_dev_has_hr_time() can be
- used to check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_TIME_INFO_HRT variable to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_hr_time()
- @see mbg_get_time_info_tstamp()
- */
+ * @brief Read both system time and associated device time from the kernel driver
+ *
+ * The kernel driver reads the current system time plus a HR time structure
+ * from a card immediately after each other. The returned info structure also
+ * contains some cycles counts to be able to determine the execution times
+ * required to read those time stamps.
+ *
+ * The advantage of this call compared to ::mbg_get_time_info_tstamp is
+ * that this call also returns the card's status. On the other hand, reading
+ * the HR time from the card may block e.g. if another application accesses
+ * the board.
+ *
+ * This call makes a ::mbg_get_hr_time_cycles call internally so the API call
+ * ::mbg_dev_has_hr_time can be used to check whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_TIME_INFO_HRT structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_hr_time
+ * @see ::mbg_get_time_info_tstamp
+ */
_MBG_API_ATTR int _MBG_API mbg_get_time_info_hrt( MBG_DEV_HANDLE dh, MBG_TIME_INFO_HRT *p ) ;
/**
- @brief Read both system time and associated device timestamp from the kernel driver.
-
- This call is similar to mbg_get_time_info_hrt() except that a
- mbg_get_fast_hr_timestamp_cycles() call is made internally, so the macro
- _pcps_has_fast_hr_timestamp() or the API call mbg_dev_has_fast_hr_timestamp()
- can be used to check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_TIME_INFO_TSTAMP variable to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_fast_hr_timestamp()
- @see mbg_get_time_info_hrt()
- */
+ * @brief Read both system time and associated device timestamp from the kernel driver.
+ *
+ * This call is similar to ::mbg_get_time_info_hrt except that a
+ * ::mbg_get_fast_hr_timestamp_cycles call is made internally, so the
+ * API call ::mbg_dev_has_fast_hr_timestamp can be used to check
+ * whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_TIME_INFO_TSTAMP structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_fast_hr_timestamp
+ * @see ::mbg_get_time_info_hrt
+ */
_MBG_API_ATTR int _MBG_API mbg_get_time_info_tstamp( MBG_DEV_HANDLE dh, MBG_TIME_INFO_TSTAMP *p ) ;
/**
- @brief Check if a device supports demodulation of the DCF77 PZF code.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_corr_info()
- @see mbg_dev_has_tr_distance()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_pzf( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports reading correlation info.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_pzf()
- @see mbg_get_corr_info()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_corr_info( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Check if a device supports configurable distance from transmitter.
-
- The distance from transmitter parameter is used to compensate
- the RF propagation delay, mostly with long wave receivers.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_pzf()
- @see mbg_get_tr_distance()
- @see mbg_set_tr_distance()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_tr_distance( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read PZF correlation info from a device.
-
- The macro _pcps_has_corr_info() or the API call mbg_dev_has_corr_info()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::CORR_INFO variable to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_pzf()
- @see mbg_dev_has_corr_info()
- */
+ * @brief Read PZF correlation info from a device
+ *
+ * The the API call ::mbg_dev_has_corr_info checks
+ * whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::CORR_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_pzf
+ * @see ::mbg_dev_has_corr_info
+ */
_MBG_API_ATTR int _MBG_API mbg_get_corr_info( MBG_DEV_HANDLE dh, CORR_INFO *p ) ;
/**
- @brief Read configurable "distance from transmitter" parameter from a device.
-
- The distance from transmitter parameter is used to compensate
- the RF propagation delay, mostly with long wave receivers.
-
- The macro _pcps_has_tr_distance() or the API call mbg_dev_has_tr_distance()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::TR_DISTANCE variable to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_pzf()
- @see mbg_dev_has_tr_distance()
- @see mbg_set_tr_distance()
- */
+ * @brief Read configurable "distance from transmitter" parameter from a device.
+ *
+ * The distance from transmitter parameter is used to compensate
+ * the RF propagation delay, mostly with long wave receivers.
+ *
+ * The API call ::mbg_dev_has_tr_distance checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::TR_DISTANCE variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_pzf
+ * @see ::mbg_dev_has_tr_distance
+ * @see ::mbg_set_tr_distance
+ */
_MBG_API_ATTR int _MBG_API mbg_get_tr_distance( MBG_DEV_HANDLE dh, TR_DISTANCE *p ) ;
/**
- @brief Write configurable "distance from transmitter" parameter to a device.
-
- The distance from transmitter parameter is used to compensate
- the RF propagation delay, mostly with long wave receivers.
-
- The macro _pcps_has_tr_distance() or the API call mbg_dev_has_tr_distance()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::TR_DISTANCE variable to be written
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_pzf()
- @see mbg_dev_has_tr_distance()
- @see mbg_get_tr_distance()
- */
+ * @brief Write configurable "distance from transmitter" parameter to a device.
+ *
+ * The distance from transmitter parameter is used to compensate
+ * the RF propagation delay, mostly with long wave receivers.
+ *
+ * The API call ::mbg_dev_has_tr_distance checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[in] p Pointer to a ::TR_DISTANCE variable to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_pzf
+ * @see ::mbg_dev_has_tr_distance
+ * @see ::mbg_get_tr_distance
+ */
_MBG_API_ATTR int _MBG_API mbg_set_tr_distance( MBG_DEV_HANDLE dh, const TR_DISTANCE *p ) ;
/**
- @brief Check if a device provides a debug status word to be read.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_get_debug_status()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_debug_status( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Read a debug status word from a device.
-
- This is mainly supported by IRIG timecode receiver cards, and the status
- word is intended to provide more detailed information why a card might not
- synchronize to the incoming timecode signal.
-
- See ::MBG_DEBUG_STATUS and related definitions for details.
-
- The macro _pcps_has_debug_status() or the API call mbg_dev_has_debug_status()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_DEBUG_STATUS variable to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_debug_status()
- */
+ * @brief Read a debug status word from a device
+ *
+ * This is mainly supported by IRIG timecode receiver cards, and the status
+ * word is intended to provide more detailed information why a card might not
+ * synchronize to the incoming timecode signal.
+ *
+ * See ::MBG_DEBUG_STATUS and related definitions for details.
+ *
+ * The API call ::mbg_dev_has_debug_status checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_DEBUG_STATUS variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_debug_status
+ */
_MBG_API_ATTR int _MBG_API mbg_get_debug_status( MBG_DEV_HANDLE dh, MBG_DEBUG_STATUS *p ) ;
/**
- @brief Check if a device provides an on-board event log.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_clr_evt_log()
- @see mbg_get_num_evt_log_entries()
- @see mbg_get_first_evt_log_entry()
- @see mbg_get_next_evt_log_entry()
-*/
- _MBG_API_ATTR int _MBG_API mbg_dev_has_evt_log( MBG_DEV_HANDLE dh, int *p ) ;
-
- /**
- @brief Clear the card's on-board event log.
-
- The macro _pcps_has_evt_log() or the API call mbg_dev_has_evt_log()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_evt_log()
- @see mbg_get_num_evt_log_entries()
- @see mbg_get_first_evt_log_entry()
- @see mbg_get_next_evt_log_entry()
- */
+ * @brief Clear the device's on-board event log.
+ *
+ * The API call ::mbg_dev_has_evt_log checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_evt_log
+ * @see ::mbg_get_num_evt_log_entries
+ * @see ::mbg_get_first_evt_log_entry
+ * @see ::mbg_get_next_evt_log_entry
+ */
_MBG_API_ATTR int _MBG_API mbg_clr_evt_log( MBG_DEV_HANDLE dh ) ;
/**
- @brief Read details about a device's on-board event log buffer.
-
- The returned ::MBG_NUM_EVT_LOG_ENTRIES structure tells how many event log
- entries which can be saved on the board, and how many entries actually
- have been saved.
-
- The macro _pcps_has_evt_log() or the API call mbg_dev_has_evt_log()
- check whether this call is supported by a device.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_NUM_EVT_LOG_ENTRIES variable to be filled up
-
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
-
- @see mbg_dev_has_evt_log()
- @see mbg_clr_evt_log()
- @see mbg_get_first_evt_log_entry()
- @see mbg_get_next_evt_log_entry()
- */
+ * @brief Read details about a device's on-board event log buffer.
+ *
+ * The returned ::MBG_NUM_EVT_LOG_ENTRIES structure tells how many event log
+ * entries which can be saved on the board, and how many entries actually
+ * have been saved.
+ *
+ * The API call ::mbg_dev_has_evt_log checks whether this call
+ * is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_NUM_EVT_LOG_ENTRIES variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_evt_log
+ * @see ::mbg_clr_evt_log
+ * @see ::mbg_get_first_evt_log_entry
+ * @see ::mbg_get_next_evt_log_entry
+ */
_MBG_API_ATTR int _MBG_API mbg_get_num_evt_log_entries( MBG_DEV_HANDLE dh, MBG_NUM_EVT_LOG_ENTRIES *p ) ;
/**
- @brief Read the first (oldest) event log entry from a device.
-
- @note Subsequent reads should be made using mbg_get_next_evt_log_entry().
-
- The macro _pcps_has_evt_log() or the API call mbg_dev_has_evt_log()
- check whether this call is supported by a device.
-
- If no (more) event log entry is available on the device then
- the returned MBG_EVT_LOG_ENTRY::code is MBG_EVT_ID_NONE.
-
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_EVT_LOG_ENTRY variable to be filled up
+ * @brief Read the first (oldest) event log entry from a device.
+ *
+ * @note Subsequent reads should be made using ::mbg_get_next_evt_log_entry.
+ *
+ * The API call ::mbg_dev_has_evt_log checks whether this call
+ * is supported by a device.
+ *
+ * If no (more) event log entry is available on the device then
+ * the returned MBG_EVT_LOG_ENTRY::code is MBG_EVT_ID_NONE.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_EVT_LOG_ENTRY variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_evt_log
+ * @see ::mbg_clr_evt_log
+ * @see ::mbg_get_num_evt_log_entries
+ * @see ::mbg_get_next_evt_log_entry
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_first_evt_log_entry( MBG_DEV_HANDLE dh, MBG_EVT_LOG_ENTRY *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Read the next event log entry from a device.
+ *
+ * @note The first read should be made using ::mbg_get_first_evt_log_entry
+ * to set the on-board read index to the oldest entry.
+ *
+ * The API call ::mbg_dev_has_evt_log checks whether this call
+ * is supported by a device.
+ *
+ * If no (more) event log entry is available on the device then
+ * the returned MBG_EVT_LOG_ENTRY::code is MBG_EVT_ID_NONE.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] p Pointer to a ::MBG_EVT_LOG_ENTRY variable to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_evt_log
+ * @see ::mbg_clr_evt_log
+ * @see ::mbg_get_num_evt_log_entries
+ * @see ::mbg_get_first_evt_log_entry
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_next_evt_log_entry( MBG_DEV_HANDLE dh, MBG_EVT_LOG_ENTRY *p ) ;
- @see mbg_dev_has_evt_log()
- @see mbg_clr_evt_log()
- @see mbg_get_num_evt_log_entries()
- @see mbg_get_next_evt_log_entry()
- */
- _MBG_API_ATTR int _MBG_API mbg_get_first_evt_log_entry( MBG_DEV_HANDLE dh, MBG_EVT_LOG_ENTRY *p ) ;
+ /**
+ * @brief Read the current GNSS mode info including current settings.
+ *
+ * The ::MBG_GNSS_MODE_INFO structure tells which GNSS systems are supported
+ * by a device, and also includes the settings currently in effect.
+ *
+ * The API call mbg_dev_is_gnss() can be used to check whether this call
+ * is supported by a device. See also the notes for mbg_dev_is_gnss().
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p_mi Pointer to a ::MBG_GNSS_MODE_INFO structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_set_gps_gnss_mode_settings
+ * @see ::mbg_get_gps_all_gnss_sat_info
+ * @see ::mbg_dev_is_gnss
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_gps_gnss_mode_info( MBG_DEV_HANDLE dh, MBG_GNSS_MODE_INFO *p_mi ) ;
/**
- @brief Read the next event log entry from a device.
+ * @brief Write the GNSS mode configuration to a device.
+ *
+ * The ::MBG_GNSS_MODE_SETTINGS structure determines to configure the
+ * GNSS settings for a device, i.e. which satellite systems have to be used.
+ *
+ * The function mbg_get_gps_gnss_mode_info() should have been called before
+ * to determine which GNSS settings are supported by the device.
+ *
+ * The API call mbg_dev_is_gnss() can be used to check whether these API calls
+ * are supported by a device. See also the notes for mbg_dev_is_gnss().
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p_ms Pointer to a ::MBG_GNSS_MODE_SETTINGS structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_gnss_mode_info
+ * @see ::mbg_get_gps_all_gnss_sat_info
+ * @see ::mbg_dev_is_gnss
+ */
+ _MBG_API_ATTR int _MBG_API mbg_set_gps_gnss_mode_settings( MBG_DEV_HANDLE dh, const MBG_GNSS_MODE_SETTINGS *p_ms ) ;
- @note The first read should be made using mbg_get_first_evt_log_entry()
- to set the on-board read index to the oldest entry.
+ /**
+ * @brief Read a ::GNSS_SAT_INFO_IDX array of satellite status information.
+ *
+ * The function ::mbg_get_gps_gnss_mode_info must have been called before,
+ * and the returned ::MBG_GNSS_MODE_INFO structure be passed to this function.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] gsii Pointer to a an array of satellite info structures to be filled up
+ * @param[in] p_mi Pointer to a ::MBG_GNSS_MODE_INFO structure returned by ::mbg_get_gps_gnss_mode_info
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_get_gps_gnss_mode_info
+ * @see ::mbg_set_gps_gnss_mode_settings
+ * @see ::mbg_dev_is_gnss
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_gnss_sat_info( MBG_DEV_HANDLE dh, GNSS_SAT_INFO_IDX gsii[], const MBG_GNSS_MODE_INFO *p_mi ) ;
- The macro _pcps_has_evt_log() or the API call mbg_dev_has_evt_log()
- check whether this call is supported by a device.
+ /**
+ * @brief Read common GPIO configuration limits
+ *
+ * The API call ::mbg_dev_has_gpio checks whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] p A ::MBG_GPIO_CFG_LIMITS structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_gpio
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ * @see ::mbg_get_gps_all_gpio_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_gpio_cfg_limits( MBG_DEV_HANDLE dh, MBG_GPIO_CFG_LIMITS *p ) ;
- If no (more) event log entry is available on the device then
- the returned MBG_EVT_LOG_ENTRY::code is MBG_EVT_ID_NONE.
+ /**
+ * @brief Get all GPIO settings and capabilities.
+ *
+ * The API call ::mbg_dev_has_gpio checks whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] gii An array of ::MBG_GPIO_STATUS_IDX structures to be filled up
+ * @param[in] p_gcl Pointer to a ::MBG_GPIO_CFG_LIMITS structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_gpio
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ * @see ::mbg_get_gps_all_gpio_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_gpio_info( MBG_DEV_HANDLE dh, MBG_GPIO_INFO_IDX gii[], const MBG_GPIO_CFG_LIMITS *p_gcl ) ;
- @param dh Valid handle to a Meinberg device
- @param *p Pointer to a ::MBG_EVT_LOG_ENTRY variable to be filled up
+ /**
+ * @brief Write the configuration for a single GPIO port to a device
+ *
+ * The ::MBG_GPIO_SETTINGS_IDX structure contains both the ::MBG_GPIO_SETTINGS
+ * and the port index value.
+ *
+ * The API call ::mbg_dev_has_gpio checks whether this call is supported
+ * by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] p Pointer to a ::MBG_GPIO_SETTINGS_IDX structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_gpio
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ * @see ::mbg_get_gps_all_gpio_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_set_gps_gpio_settings_idx( MBG_DEV_HANDLE dh, const MBG_GPIO_SETTINGS_IDX *p ) ;
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ /**
+ * @brief Read the status of all GPIO signal ports
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] gsi An array of ::MBG_GPIO_STATUS_IDX structures to be filled up
+ * @param[in] p_gcl Pointer to a ::MBG_GPIO_CFG_LIMITS structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_gpio
+ * @see ::mbg_get_gpio_cfg_limits
+ * @see ::mbg_get_gps_all_gpio_info
+ * @see ::mbg_set_gps_gpio_settings_idx
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_gpio_status( MBG_DEV_HANDLE dh, MBG_GPIO_STATUS_IDX gsi[], const MBG_GPIO_CFG_LIMITS *p_gcl ) ;
- @see mbg_dev_has_evt_log()
- @see mbg_clr_evt_log()
- @see mbg_get_num_evt_log_entries()
- @see mbg_get_first_evt_log_entry()
- */
- _MBG_API_ATTR int _MBG_API mbg_get_next_evt_log_entry( MBG_DEV_HANDLE dh, MBG_EVT_LOG_ENTRY *p ) ;
+ /**
+ * @brief
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param[out] *p A ::XMULTI_REF_INSTANCES structure to be filled up
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_set_gps_xmr_settings_idx
+ * @see ::mbg_get_xmr_holdover_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_xmr_instances( MBG_DEV_HANDLE dh, XMULTI_REF_INSTANCES *p ) ;
/**
- @brief Read the CPU affinity of a process.
+ * @brief Read the status of all XMR sources
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] xmrsi An array of ::XMULTI_REF_STATUS_IDX structures to be filled up
+ * @param[in] p_xmri Pointer to a ::XMULTI_REF_INSTANCES structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_set_gps_xmr_settings_idx
+ * @see ::mbg_get_xmr_holdover_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_xmr_status( MBG_DEV_HANDLE dh, XMULTI_REF_STATUS_IDX xmrsi[], const XMULTI_REF_INSTANCES *p_xmri ) ;
- This means on which of the available CPUs or CPU cores the process can be executed.
+ /**
+ * @brief Read all XMR settings and capabilities
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device
+ * @param[out] xmrii An array of ::XMULTI_REF_INFO_IDX structures to be filled up
+ * @param[in] p_xmri Pointer to a ::XMULTI_REF_INSTANCES structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_set_gps_xmr_settings_idx
+ * @see ::mbg_get_xmr_holdover_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_gps_all_xmr_info( MBG_DEV_HANDLE dh, XMULTI_REF_INFO_IDX xmrii[], const XMULTI_REF_INSTANCES *p_xmri ) ;
- @param pid The process ID.
- @param *p Pointer to a ::MBG_CPU_SET variable which contains a mask of CPUs.
+ /**
+ * @brief Write a single XMR setting to a device
+ *
+ * The ::XMULTI_REF_SETTINGS_IDX structure contains both the ::XMULTI_REF_SETTINGS
+ * and the index value.
+ *
+ * The macro ::_pcps_has_ri_xmr or the API call ::mbg_dev_has_xmr
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::XMULTI_REF_SETTINGS_IDX structure to be written
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_get_xmr_holdover_status
+ */
+ _MBG_API_ATTR int _MBG_API mbg_set_gps_xmr_settings_idx( MBG_DEV_HANDLE dh, const XMULTI_REF_SETTINGS_IDX *p ) ;
- @return ::MBG_SUCCESS or error code returned by the system call.
+ /**
+ * @brief Read the current XMR holdover interval from a device
+ *
+ * Read a ::SYNTH structure containing the configuration of an optional
+ * on-board programmable frequency synthesizer.
+ *
+ * The macro ::_pcps_has_ri_xmr or the API call ::mbg_dev_has_xmr
+ * check whether this call is supported by a device.
+ *
+ * @param[in] dh Valid ::MBG_DEV_HANDLE handle to a Meinberg device.
+ * @param *p Pointer to a ::XMR_HOLDOVER_INTV structure to be filled up
+ * @param[in] p_xmri Pointer to a ::XMULTI_REF_INSTANCES structure read before
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_dev_has_xmr
+ * @see ::mbg_get_xmr_instances
+ * @see ::mbg_get_gps_all_xmr_status
+ * @see ::mbg_get_gps_all_xmr_info
+ * @see ::mbg_set_gps_xmr_settings_idx
+ */
+ _MBG_API_ATTR int _MBG_API mbg_get_xmr_holdover_status( MBG_DEV_HANDLE dh, XMR_HOLDOVER_STATUS *p, const XMULTI_REF_INSTANCES *p_xmri ) ;
- @see mbg_set_process_affinity()
- @see mbg_set_current_process_affinity_to_cpu()
- */
+ /**
+ * @brief Read the CPU affinity of a process.
+ *
+ * This means on which of the available CPUs or CPU cores the process can be executed.
+ *
+ * @param pid The process ID.
+ * @param *p Pointer to a ::MBG_CPU_SET variable which contains a mask of CPUs.
+ *
+ * @return ::MBG_SUCCESS or error code returned by the system call.
+ *
+ * @see ::mbg_set_process_affinity
+ * @see ::mbg_set_current_process_affinity_to_cpu
+ */
_MBG_API_ATTR int _MBG_API mbg_get_process_affinity( MBG_PROCESS_ID pid, MBG_CPU_SET *p ) ;
/**
- @brief Set the CPU affinity of a process.
+ * @brief Set the CPU affinity of a process.
This determines on which of the available CPUs
the process is allowed to be executed.
@@ -3367,29 +4749,29 @@ extern "C" {
@param pid The process ID.
@param *p Pointer to a ::MBG_CPU_SET variable which contains a mask of CPUs.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_get_process_affinity()
- @see mbg_set_current_process_affinity_to_cpu()
+ * @see ::mbg_get_process_affinity
+ * @see ::mbg_set_current_process_affinity_to_cpu
*/
_MBG_API_ATTR int _MBG_API mbg_set_process_affinity( MBG_PROCESS_ID pid, MBG_CPU_SET *p ) ;
/**
- @brief Set the CPU affinity of a process for a single CPU only.
+ * @brief Set the CPU affinity of a process for a single CPU only.
This means the process may only be executed on that single CPU.
@param cpu_num The number of the CPU.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_get_process_affinity()
- @see mbg_set_process_affinity()
+ * @see ::mbg_get_process_affinity
+ * @see ::mbg_set_process_affinity
*/
_MBG_API_ATTR int _MBG_API mbg_set_current_process_affinity_to_cpu( int cpu_num ) ;
/**
- @brief Create a new execution thread for the current process.
+ * @brief Create a new execution thread for the current process.
This function is only implemented for targets which support threads.
@@ -3397,32 +4779,32 @@ extern "C" {
@param fnc The name of the thread function to be started.
@param arg A generic argument passed to the thread function.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_thread_stop()
- @see mbg_thread_sleep_interruptible()
- @see mbg_thread_set_affinity()
+ * @see ::mbg_thread_stop
+ * @see ::mbg_thread_sleep_interruptible
+ * @see ::mbg_thread_set_affinity
*/
- _MBG_API_ATTR int _MBG_API mbg_thread_create( MBG_THREAD_INFO *p_ti, MBG_THREAD_FNC_RET_VAL (MBG_THREAD_FNC_ATTR *fnc)(void *), void *arg ) ;
+ _MBG_API_ATTR int _MBG_API mbg_thread_create( MBG_THREAD_INFO *p_ti, MBG_THREAD_FNC fnc, void *arg ) ;
/**
- @brief Stop a thread which has been created by mbg_thread_create().
+ * @brief Stop a thread which has been created by mbg_thread_create().
Wait until the thread has finished and release all resources.
This function is only implemented for targets which support threads.
@param p_ti Pointer to a ::MBG_THREAD_INFO structure associated with the thread.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_thread_create()
- @see mbg_thread_sleep_interruptible()
- @see mbg_thread_set_affinity()
+ * @see ::mbg_thread_create
+ * @see ::mbg_thread_sleep_interruptible
+ * @see ::mbg_thread_set_affinity
*/
_MBG_API_ATTR int _MBG_API mbg_thread_stop( MBG_THREAD_INFO *p_ti ) ;
/**
- @brief Let the current thread sleep for a certain interval.
+ * @brief Let the current thread sleep for a certain interval.
The sleep is interrupted if a signal is received indicating
the thread should terminate.
@@ -3431,18 +4813,18 @@ extern "C" {
@param p_ti Pointer to a ::MBG_THREAD_INFO structure associated with the thread.
@param sleep_ms The number of milliseconds to sleep
- @return 0 if the sleep interval has expired normally
+ * @return 0 if the sleep interval has expired normally
1 if a signal to terminate has been received
<0 if an error has occurred
- @see mbg_thread_create()
- @see mbg_thread_stop()
- @see mbg_thread_set_affinity()
+ * @see ::mbg_thread_create
+ * @see ::mbg_thread_stop
+ * @see ::mbg_thread_set_affinity
*/
_MBG_API_ATTR int _MBG_API mbg_thread_sleep_interruptible( MBG_THREAD_INFO *p_ti, ulong sleep_ms ) ;
/**
- @brief Set the CPU affinity of a single thread.
+ * @brief Set the CPU affinity of a single thread.
This determines on which of the available CPUs the thread
is allowed to be executed.
@@ -3452,16 +4834,16 @@ extern "C" {
@param p_ti Pointer to a ::MBG_THREAD_INFO structure associated with the thread.
@param *p Pointer to a ::MBG_CPU_SET variable which contains a mask of CPUs.
- @return ::MBG_SUCCESS or error code returned by the system call.
+ * @return ::MBG_SUCCESS or error code returned by the system call.
- @see mbg_thread_create()
- @see mbg_thread_stop()
- @see mbg_thread_sleep_interruptible()
+ * @see ::mbg_thread_create
+ * @see ::mbg_thread_stop
+ * @see ::mbg_thread_sleep_interruptible
*/
_MBG_API_ATTR int _MBG_API mbg_thread_set_affinity( MBG_THREAD_INFO *p_ti, MBG_CPU_SET *p ) ;
/**
- @brief Set up a ::MBG_POLL_THREAD_INFO structure and start a new thread.
+ * @brief Set up a ::MBG_POLL_THREAD_INFO structure and start a new thread.
The new thread runs the mbg_xhrt_poll_thread_fnc() function.
@@ -3473,37 +4855,35 @@ extern "C" {
@param sleep_ms the sleep interval for the poll thread function in ms.
If this parameter is 0 then the default sleep interval is used.
- @return ::MBG_SUCCESS on success,
+ * @return ::MBG_SUCCESS on success,
::MBG_ERR_NOT_SUPP_BY_DEV if the device to poll does not support HR time
else the result of mbg_thread_create()
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_stop()
- @see mbg_get_xhrt_time_as_pcps_hr_time()
- @see mbg_get_xhrt_time_as_filetime()
- @see mbg_get_xhrt_cycles_frequency()
+ * @see ::mbg_xhrt_poll_thread_stop
+ * @see ::mbg_get_xhrt_time_as_pcps_hr_time
+ * @see ::mbg_get_xhrt_time_as_filetime
+ * @see ::mbg_get_xhrt_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_xhrt_poll_thread_create( MBG_POLL_THREAD_INFO *p_pti, MBG_DEV_HANDLE dh, MBG_PC_CYCLES_FREQUENCY freq_hz, int sleep_ms ) ;
/**
- @brief Stop a polling thread started by mbg_xhrt_poll_thread_create().
+ * @brief Stop a polling thread started by mbg_xhrt_poll_thread_create().
This call also releases all associated resources.
@param *p_pti Pointer to a ::MBG_POLL_THREAD_INFO structure.
- @return the result of mbg_thread_stop()
+ * @return the result of mbg_thread_stop()
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_create()
- @see mbg_get_xhrt_time_as_pcps_hr_time()
- @see mbg_get_xhrt_time_as_filetime()
- @see mbg_get_xhrt_cycles_frequency()
+ * @see ::mbg_xhrt_poll_thread_create
+ * @see ::mbg_get_xhrt_time_as_pcps_hr_time
+ * @see ::mbg_get_xhrt_time_as_filetime
+ * @see ::mbg_get_xhrt_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_xhrt_poll_thread_stop( MBG_POLL_THREAD_INFO *p_pti ) ;
/**
- @brief Retrieve an extrapolated time stamp in PCPS_HR_TIME format.
+ * @brief Retrieve an extrapolated time stamp in PCPS_HR_TIME format.
The time stamp is extrapolated using the system's current cycles counter value
and a time stamp plus associated cycles counter value saved by the polling thread.
@@ -3514,18 +4894,17 @@ extern "C" {
@param *p Pointer to a ::MBG_XHRT_INFO structure used to retrieve data from the polling thread.
@param *p_hrt Pointer to a ::PCPS_HR_TIME structure to be filled up.
- @return MBG_SUCCESS or another return value from the polling thread's IOCTL call.
+ * @return MBG_SUCCESS or another return value from the polling thread's IOCTL call.
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_create()
- @see mbg_xhrt_poll_thread_stop()
- @see mbg_get_xhrt_time_as_filetime()
- @see mbg_get_xhrt_cycles_frequency()
+ * @see ::mbg_xhrt_poll_thread_create
+ * @see ::mbg_xhrt_poll_thread_stop
+ * @see ::mbg_get_xhrt_time_as_filetime
+ * @see ::mbg_get_xhrt_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_get_xhrt_time_as_pcps_hr_time( MBG_XHRT_INFO *p, PCPS_HR_TIME *p_hrt ) ;
/**
- @brief Retrieve an extrapolated time stamp in FILETIME format.
+ * @brief Retrieve an extrapolated time stamp in FILETIME format.
The time stamp is extrapolated using the system's current cycles counter value
and a time stamp plus associated cycles counter value saved by the polling thread.
@@ -3535,20 +4914,19 @@ extern "C" {
implemented under Windows.
@param *p Pointer to a ::MBG_XHRT_INFO structure used to retrieve data from the polling thread.
- @param *p_ft Pointer to a ::FILETIME structure to be filled up.
+ @param *p_ft Pointer to a FILETIME structure to be filled up.
- @return MBG_SUCCESS or another return value from the polling thread's IOCTL call.
+ * @return MBG_SUCCESS or another return value from the polling thread's IOCTL call.
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_create()
- @see mbg_xhrt_poll_thread_stop()
- @see mbg_get_xhrt_time_as_pcps_hr_time()
- @see mbg_get_xhrt_cycles_frequency()
+ * @see ::mbg_xhrt_poll_thread_create
+ * @see ::mbg_xhrt_poll_thread_stop
+ * @see ::mbg_get_xhrt_time_as_pcps_hr_time
+ * @see ::mbg_get_xhrt_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_get_xhrt_time_as_filetime( MBG_XHRT_INFO *p, FILETIME *p_ft ) ;
/**
- @brief Retrieve the frequency of the system's cycles counter.
+ * @brief Retrieve the frequency of the system's cycles counter.
The frequency is determined by the device polling thread.
See mbg_xhrt_poll_thread_fnc() for details and limitations.
@@ -3557,27 +4935,26 @@ extern "C" {
@param *p Pointer to a ::MBG_XHRT_INFO structure used to retrieve data from the polling thread.
@param *p_freq_hz Pointer to a ::MBG_PC_CYCLES_FREQUENCY variable in which the frequency is returned.
- @return a status code from the polling thread: MBG_SUCCESS or an IOCTL error code.
+ * @return a status code from the polling thread: MBG_SUCCESS or an IOCTL error code.
- @see mbg_xhrt_poll_thread_fnc()
- @see mbg_xhrt_poll_thread_create()
- @see mbg_xhrt_poll_thread_stop()
- @see mbg_get_xhrt_time_as_pcps_hr_time()
- @see mbg_get_xhrt_time_as_filetime()
+ * @see ::mbg_xhrt_poll_thread_create
+ * @see ::mbg_xhrt_poll_thread_stop
+ * @see ::mbg_get_xhrt_time_as_pcps_hr_time
+ * @see ::mbg_get_xhrt_time_as_filetime
*/
_MBG_API_ATTR int _MBG_API mbg_get_xhrt_cycles_frequency( MBG_XHRT_INFO *p, MBG_PC_CYCLES_FREQUENCY *p_freq_hz ) ;
/**
- @brief Retrieve the default system's cycles counter frequency from the kernel driver.
+ * @brief Retrieve the default system's cycles counter frequency from the kernel driver.
This API call can be used on systems which don't provide this information in user space.
@param dh handle of the device to which the IOCTL call is sent.
@param *p Pointer of a ::MBG_PC_CYCLES_FREQUENCY variable to be filled up.
- @return ::MBG_SUCCESS or error code returned by device I/O control function.
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
- @see mbg_get_default_cycles_frequency()
+ * @see ::mbg_get_default_cycles_frequency
*/
_MBG_API_ATTR int _MBG_API mbg_get_default_cycles_frequency_from_dev( MBG_DEV_HANDLE dh, MBG_PC_CYCLES_FREQUENCY *p ) ;
@@ -3590,7 +4967,7 @@ extern "C" {
@return the default cycles counter frequency in Hz, or 0 if the value is not available.
- @see mbg_get_default_cycles_frequency_from_dev()
+ * @see ::mbg_get_default_cycles_frequency_from_dev
*/
_MBG_API_ATTR MBG_PC_CYCLES_FREQUENCY _MBG_API mbg_get_default_cycles_frequency( void ) ;
@@ -3605,7 +4982,7 @@ extern "C" {
#if defined( MBG_TGT_WIN32 )
static __mbg_inline
-MBGDEVIO_RET_VAL do_mbg_ioctl( MBG_DEV_HANDLE dh, int ioctl_code,
+MBGDEVIO_RET_VAL do_mbg_ioctl( MBG_DEV_HANDLE dh, int ioctl_code,
const void *in_p, int in_sz, void *out_p, int out_sz )
{
DWORD ReturnedLength;
@@ -3618,16 +4995,16 @@ MBGDEVIO_RET_VAL do_mbg_ioctl( MBG_DEV_HANDLE dh, int ioctl_code,
{
DWORD rc = GetLastError();
-#if 0 //##++++++++++++++++++++++++
-// We can't call mbgsvctl_log_mbgdevio_error() here (for now).
-// Is is defined in mbgsvctl.h, and including mbgsvc.h here,
-// or copying the prototype here results in DLL import/export
-// mismatch errors.
+ #if 0 //### TODO
+ // We can't call mbgsvctl_log_mbgdevio_error() here (for now).
+ // Is is defined in mbgsvctl.h, and including mbgsvctl.h here,
+ // or copying the prototype here results in DLL import/export
+ // mismatch errors.
// do not report a USB device timeout error
- if ( rc != _mbg_err_to_os( MBG_ERR_USB_ACCESS ) )
+ if ( rc != MBG_ERR_USB_ACCESS )
mbgsvctl_log_mbgdevio_error( ioctl_code, rc );
-#endif
+ #endif
return rc;
}
@@ -3639,10 +5016,14 @@ MBGDEVIO_RET_VAL do_mbg_ioctl( MBG_DEV_HANDLE dh, int ioctl_code,
#define _do_mbg_ioctl( _dh, _ioctl, _p, _in_sz, _out_sz ) \
do_mbg_ioctl( _dh, _ioctl, (LPVOID) _p, _in_sz, (LPVOID) _p, _out_sz )
-#elif defined( MBG_TGT_UNIX )
+#elif defined( MBG_HAS_POSIX_IOCTL )
+
+ // In case of an error ioctl returns -1, and errno has been set to a *positive*
+ // error number according to negative Meinberg error codes, so we need to return
+ // -errno in case of an error to pass the original negative Meinberg error code.
#define _do_mbg_ioctl( _dh, _ioctl, _p, _in_sz, _out_sz ) \
- ioctl( _dh, _ioctl, _p )
+ ( ( ( rc = ioctl( _dh, _ioctl, _p ) ) >= 0 ) ? rc : -errno )
#endif
@@ -3656,16 +5037,19 @@ MBGDEVIO_RET_VAL do_mbg_ioctl( MBG_DEV_HANDLE dh, int ioctl_code,
/**
@brief Send a generic IOCTL command to the driver.
- @param dh Valid handle to a Meinberg device
- @param info Additional information for the kernel driver depending on
- the IOCTL code, i.e. the low level function to be called: <br>
- one of the PCPS_... commands with IOCTL_PCPS_GENERIC_{READ|WRITE}<br>
- one of the PC_GPS_... commands with IOCTL_PCPS_GENERIC_{READ|WRITE}_GPS<br>
- one of the PCPS_GEN_IO_... enumeration codes with IOCTL_PCPS_GENERIC_IO
- @param ioctl One of the IOCTL_GENERIC_... codes telling the kernel driver
- which low level function to use, e.g. normal read or write,
- large (GPS) data read or write, or generic I/O.
- @param *p Pointer to an int which is set 0 or != 0 unless the call fails.
+ @param dh Valid handle to a Meinberg device
+ @param info Additional information for the kernel driver depending on
+ the IOCTL code, i.e. the low level function to be called: <br>
+ one of the PCPS_... commands with IOCTL_PCPS_GENERIC_{READ|WRITE}<br>
+ one of the PC_GPS_... commands with IOCTL_PCPS_GENERIC_{READ|WRITE}_GPS<br>
+ one of the PCPS_GEN_IO_... enumeration codes with IOCTL_PCPS_GENERIC_IO
+ @param ioctl_code One of the IOCTL_GENERIC_... codes telling the kernel driver
+ which low level function to use, e.g. normal read or write,
+ large (GPS) data read or write, or generic I/O.
+ @param in_p Pointer to an input buffer passed to the driver, can be NULL
+ @param in_sz Size of the input buffer, can be 0 if no buffer is used
+ @param out_p Pointer to an output buffer passed to the driver, can be NULL
+ @param out_sz Size of the output buffer, can be 0 if no buffer is used
@return ::MBG_SUCCESS or error code returned by device I/O control function.
*/
@@ -3704,7 +5088,7 @@ MBGDEVIO_RET_VAL do_mbg_ioctl( MBG_DEV_HANDLE dh, int ioctl_code,
p_buff = (IOCTL_GENERIC_BUFFER *) malloc( buff_size );
if ( p_buff == NULL )
- return _mbg_err_to_os( MBG_ERR_NO_MEM );
+ return MBG_ERR_NO_MEM;
p_buff->ctl.info = info;
p_buff->ctl.data_size_in = in_sz;
@@ -3751,8 +5135,10 @@ MBGDEVIO_RET_VAL do_mbg_ioctl( MBG_DEV_HANDLE dh, int ioctl_code,
#define _mbgdevio_write_cmd( _dh, _cmd, _ioctl ) \
_do_mbgdevio_write( _dh, _cmd, _ioctl, NULL, 0 )
+ #define _mbgdevio_read_gps _do_mbgdevio_read
#define _mbgdevio_read_gps_var _mbgdevio_read_var
+ #define _mbgdevio_write_gps _do_mbgdevio_write
#define _mbgdevio_write_gps_var _mbgdevio_write_var
@@ -3774,10 +5160,10 @@ MBGDEVIO_RET_VAL do_mbg_ioctl( MBG_DEV_HANDLE dh, int ioctl_code,
#else // accessing hardware device directly
- #define _mbgdevio_chk_cond( _cond ) \
- { \
- if ( !(_cond) ) \
- return _mbg_err_to_os( MBG_ERR_NOT_SUPP_BY_DEV ); \
+ #define _mbgdevio_chk_cond( _cond ) \
+ { \
+ if ( !(_cond) ) \
+ return MBG_ERR_NOT_SUPP_BY_DEV; \
}
#define _mbgdevio_read( _dh, _cmd, _ioctl, _p, _sz ) \
@@ -3858,38 +5244,51 @@ MBGDEVIO_RET_VAL do_mbg_ioctl( MBG_DEV_HANDLE dh, int ioctl_code,
-#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_UNIX )
+#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX )
+
+// ### TODO
+// For some reason the code below causes an internal compiler error
+// with Borland C++Builder 5.0 release builds. Since we don't need
+// this function in the BC5 projects anyway we exclude it brom build.
+
+#if !defined( __BORLANDC__ )
static __mbg_inline
void mbg_chk_tstamp64_leap_sec( uint64_t *tstamp64, PCPS_TIME_STATUS_X *status )
{
if ( *status & ( PCPS_LS_ANN | PCPS_LS_ENB ) )
{
- time_t t = (uint32_t) ( *tstamp64 >> 32 );
- struct tm tm = *gmtime( &t );
+ struct tm tm = { 0 };
+ time_t t = cvt_to_time_t( (uint32_t) ( (*tstamp64) >> 32 ) );
+ int rc = mbg_gmtime( &tm, &t );
- // Handle leap second and status
- if ( tm.tm_hour == 0 && tm.tm_min == 0 && tm.tm_sec == 0 )
+ if ( mbg_rc_is_success( rc ) )
{
- if ( *status & PCPS_LS_ANN )
+ // Handle leap second and status
+ if ( tm.tm_hour == 0 && tm.tm_min == 0 && tm.tm_sec == 0 )
{
- // Set leap second enabled flag on rollover to the leap second and clear announce flag
- *status &= ~PCPS_LS_ANN;
- *status |= PCPS_LS_ENB;
-
- // Decrement interpolated second to avoid automated overflow during the leap second.
- // Second 59 appears for the second time.
- *tstamp64 -= PCPS_HRT_BIN_FRAC_SCALE;
+ if ( *status & PCPS_LS_ANN )
+ {
+ // Set leap second enabled flag on rollover to the leap second and clear announce flag
+ *status &= ~PCPS_LS_ANN;
+ *status |= PCPS_LS_ENB;
+
+ // Decrement interpolated second to avoid automated overflow during the leap second.
+ // Second 59 appears for the second time.
+ *tstamp64 -= PCPS_HRT_BIN_FRAC_SCALE;
+ }
+ else
+ if ( *status & PCPS_LS_ENB ) // Clear bits when leap second expires and 0:00:00 UTC is reached
+ *status &= ~( PCPS_LS_ANN | PCPS_LS_ENB );
}
- else
- if ( *status & PCPS_LS_ENB ) // Clear bits when leap second expires and 0:00:00 UTC is reached
- *status &= ~( PCPS_LS_ANN | PCPS_LS_ENB );
}
}
} // mbg_chk_tstamp64_leap_sec
-#endif // defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_UNIX )
+#endif // !defined( __BORLANDC__ )
+
+#endif // defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX )
diff --git a/mbglib/common/mbgerror.c b/mbglib/common/mbgerror.c
new file mode 100755
index 0000000..60eee81
--- /dev/null
+++ b/mbglib/common/mbgerror.c
@@ -0,0 +1,733 @@
+
+/**************************************************************************
+ *
+ * $Id: mbgerror.c 1.2.1.5 2017/02/22 11:53:24 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Meinberg Library to communicate with USB devices from user space
+ *
+ * -----------------------------------------------------------------------
+ * $Log: mbgerror.c $
+ * Revision 1.2.1.5 2017/02/22 11:53:24 martin
+ * Removed type cast.which is now obsolete
+ * due to changed library type.
+ * Revision 1.2.1.4 2016/12/16 12:40:25Z thomas-b
+ * Added table entry for posix errors for ENOSPC (MBG_ERR_NO_SPACE)
+ * Revision 1.2.1.3 2016/09/13 10:24:02 martin
+ * Fixed some compiler warnings.
+ * Revision 1.2.1.2 2016/08/16 12:48:30Z gregoire.diehl
+ * CVI fixes
+ * Revision 1.2.1.1 2016/08/11 07:58:15 martin
+ * Fixed a compiler warning.
+ * Revision 1.2 2016/08/05 12:25:44Z martin
+ * Added some functions.
+ * Revision 1.1 2014/03/07 12:08:14 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#define _MBGERROR
+ #include <mbgerror.h>
+#undef _MBGERROR
+
+#include <mbg_tgt.h>
+
+#include <stdio.h>
+#include <string.h>
+
+#if defined( MBG_TGT_POSIX ) || \
+ defined( MBG_TGT_WIN32 ) || \
+ defined( MBG_TGT_DOS )
+ #define _MBG_TGT_HAS_POSIX_ERRNO 1
+#else
+ #define _MBG_TGT_HAS_POSIX_ERRNO 0
+#endif
+
+#if _MBG_TGT_HAS_POSIX_ERRNO
+ #include <errno.h>
+#endif
+
+#if defined( MBG_TGT_DOS )
+ #include <stddef.h>
+#endif
+
+#if defined( MBG_TGT_POSIX )
+ #include <netdb.h>
+#endif
+
+#if defined(USE_MBG_ZLIB)
+ #include <zlib.h>
+#endif
+
+
+typedef struct
+{
+ int orig_errno;
+ int mbg_errno;
+
+} ERRNO_CNV_ENTRY;
+
+
+
+#if _MBG_TGT_HAS_POSIX_ERRNO
+
+static ERRNO_CNV_ENTRY posix_errno_table[] =
+{
+ // POSIX codes taken from Linux asm-generic/errno.h
+ { EPERM, MBG_ERR_PERM }, // 1, Operation not permitted
+ { ENOENT, MBG_ERR_NO_ENTITY }, // 2, No such file or directory
+ // { ESRCH, }, // 3, No such process
+ { EINTR, MBG_ERR_INTR }, // 4, Interrupted system call
+ { EIO, MBG_ERR_IO }, // 5, I/O error
+ { ENXIO, MBG_ERR_NOT_FOUND }, // 6, No such device or address
+ // { E2BIG, }, // 7, Argument list too long
+ // { ENOEXEC, }, // 8, Exec format error
+ // { EBADF, }, // 9, Bad file number
+ // { ECHILD, }, // 10, No child processes
+ // { EAGAIN, }, // 11, Try again
+ { ENOMEM, MBG_ERR_NO_MEM }, // 12, Out of memory
+ { EACCES, MBG_ERR_ACCESS }, // 13, Permission denied
+ // { EFAULT, }, // 14, Bad address
+ // { ENOTBLK, }, // 15, Block device required
+ { EBUSY, MBG_ERR_BUSY }, // 16, Device or resource busy
+ { EEXIST, MBG_ERR_EXIST }, // 17, File exists
+ { EXDEV, MBG_ERR_NO_DEV }, // 18, Cross-device link
+ // { ENODEV, }, // 19, No such device
+ // { ENOTDIR, }, // 20, Not a directory
+ // { EISDIR, }, // 21, Is a directory
+ { EINVAL, MBG_ERR_INV_PARM }, // 22, Invalid argument
+ // { ENFILE, }, // 23, File table overflow
+ // { EMFILE, }, // 24, Too many open files
+ // { ENOTTY, }, // 25, Not a typewriter
+ // { ETXTBSY, }, // 26, Text file busy
+ // { EFBIG, }, // 27, File too large
+ { ENOSPC, MBG_ERR_NO_SPACE }, // 28, No space left on device
+ { ESPIPE, MBG_ERR_PIPE }, // 29, Illegal seek
+ // { EROFS, }, // 30, Read-only file system
+ // { EMLINK, }, // 31, Too many links
+ // { EPIPE, }, // 32, Broken pipe
+ // { EDOM, }, // 33, Math argument out of domain of func
+ { ERANGE, MBG_ERR_RANGE }, // 34, Math result not representable
+#if defined( EOVERFLOW )
+ { EOVERFLOW, MBG_ERR_OVERFLOW }, // 75, Value too large for defined data type
+#endif
+#if defined( ENOTSOCK )
+ { ENOTSOCK, MBG_ERR_NOT_A_SOCKET }, // 88, Socket operation on non-socket
+#endif
+#if defined( ECONNRESET )
+ { ECONNRESET, MBG_ERR_CONN_RESET }, // 104, Connection reset by peer
+#endif
+ { 0, 0 } // end-of-table identifier
+
+}; // posix_errno_table
+
+#endif // _MBG_TGT_HAS_POSIX_ERRNO
+
+
+
+#if defined( MBG_TGT_POSIX )
+
+static ERRNO_CNV_ENTRY posix_h_errno_table[] =
+{
+ // POSIX codes taken from Linux netdb.h
+ { HOST_NOT_FOUND, MBG_ERR_HOST_NOT_FOUND }, // The specified host is unknown
+ // { NO_ADDRESS, }, // Usually same numeric value as NO_DATA
+ // { NO_DATA, }, // The requested name is valid but does not have an IP address
+ // { NO_RECOVERY, }, // A nonrecoverable name server error occurred
+ // { TRY_AGAIN, }, // A temporary error occurred on an authoritative name server. Try again later.
+ { 0, 0 } // end-of-table identifier
+
+}; // posix_h_errno_table
+
+#endif // defined( MBG_TGT_POSIX )
+
+
+
+#if defined( MBG_TGT_CVI )
+
+static ERRNO_CNV_ENTRY cvi_rs232_error_table[] =
+{
+ // { kRS_UnknownSysError, }, // Unknown system error.
+ // { kRS_InvalidPortNum, }, // In valid port number.
+ // { kRS_PortNotOpen, }, // Port is not open.
+ // { kRS_UnknownIOError, }, // Unknown I/O error.
+ // { kRS_InternalError, }, // Unexpected internal error.
+ // { kRS_NoPortFound, }, // No serial port found.
+ // { kRS_CanNotOpenPort, }, // Cannot open port.
+ // { kRS_NullPointerPassed, }, // A NULL pointer was passed when a non-NULL pointer was expected.
+ // { kRS_OutOfMemory, }, // Out of memory.
+ // { kRS_OutOfSystemResources, }, // Unable to allocate system resources.
+ // { kRS_InvalidParameter, }, // Invalid parameter.
+ // { kRS_InvalidBaudRate, }, // Invalid baud rate.
+ // { kRS_InvalidParity, }, // Invalid parity.
+ // { kRS_InvalidDataBits, }, // Invalid number of data bits.
+ // { kRS_InvalidStopBits, }, // Invalid number of stop bits.
+ // { kRS_BadFileHandle, }, // Bad file handle.
+ // { kRS_FileIOError, }, // File I/O error.
+ // { kRS_InvalidCount, }, // Invalid count; must be greater than or equal to 0.
+ // { kRS_InvalidIntLevel, }, // Invalid interrupt level.
+ // { kRS_IOTimeOut, }, // I/O operation timed out.
+ // { kRS_InvalidBreakTime, }, // Break time must be a positive value.
+ // { kRS_InvalidInQSize, }, // Requested input queue size must be 0 or greater.
+ // { kRS_InvalidOutQSize, }, // Requested output queue size must be 0 or greater.
+ // { kRS_GeneralIOFailure, }, // General I/O error.
+ // { kRS_InvalidBufferPointer, }, // Buffer parameter is NULL.
+ // { kRS_VISALibrariesMissing, }, // A necessary run-time library could not be found or loaded.
+ // { kRS_NoAckReceived, }, // Packet was sent, but no acknowledgment was received.
+ // { kRS_MaxRetriesBeforeSend, }, // Packet was not sent within retry limit.
+ // { kRS_MaxRetriesBeforeReceived, }, // Packet was not received within retry limit.
+ // { kRS_UnexpectedEOT, }, // End of transmission character encountered when start of data character expected.
+ // { kRS_CanNotReadPackNum, }, // Unable to read packet number.
+ // { kRS_InconsistentPackNum, }, // Inconsistent packet number.
+ // { kRS_CanNotReadPackData, }, // Unable to read packet data.
+ // { kRS_CanNotReadCheckSum, }, // Unable to read checksum.
+ // { kRS_CheckSumError, }, // Checksum received did not match computed checksum.
+ // { kRS_PackSizeGTInQ, }, // Packet size exceeds input queue size.
+ // { kRS_OpenFileError, }, // Error opening file.
+ // { kRS_ReadFileError, }, // Error reading file.
+ // { kRS_NoInitNegAck, }, // Did not receive initial negative acknowledgment character.
+ // { kRS_NoAckAfterEOT, }, // Did not receive acknowledgment after end of transmission character was sent.
+ // { kRS_WriteFileError, }, // Error writing to file.
+ // { kRS_NoSOHorEOT, }, // Did not receive either a start of data or end of transmission character when expected.
+ // { kRS_TransferCancelled, }, // Transfer was canceled because CAN ASCII character was received.
+ // { kRS_InvalidStartDelay, }, // Invalid start delay.
+ // { kRS_InvalidMaxTries, }, // Invalid maximum number of retries.
+ // { kRS_InvalidWaitPeriod, }, // Invalid wait period.
+ // { kRS_InvalidPacketSize, }, // Invalid packet size.
+ // { kRS_CanNotReadCRC, }, // Unable to read Cyclical Redundancy Check.
+ // { kRS_CRCError, }, // Cyclical Redundancy Check error.
+ { 0, 0 } // end-of-table identifier
+
+}; // cvi_rs232_error_table
+
+#endif // defined( MBG_TGT_CVI )
+
+
+
+#if defined( MBG_TGT_WIN32 )
+
+static ERRNO_CNV_ENTRY win32_error_table[] =
+{
+ // System Error Codes (1300-1699)
+ { ERROR_ACCESS_DENIED, MBG_ERR_ACCESS }, //
+ { ERROR_PRIVILEGE_NOT_HELD, MBG_ERR_PERM }, //
+ { ERROR_INVALID_HANDLE, MBG_ERR_INV_HANDLE }, //
+ { ERROR_NOT_ENOUGH_MEMORY, MBG_ERR_NO_MEM }, //
+ { ERROR_OUTOFMEMORY, MBG_ERR_NO_MEM }, //
+ // { ERROR_WRITE_PROTECT, }, //
+ // { ERROR_BAD_UNIT, }, //
+ // { ERROR_NOT_READY, }, //
+ // { ERROR_WRITE_FAULT, }, //
+ // { ERROR_READ_FAULT, }, //
+ // { ERROR_GEN_FAILURE, }, //
+ // { ERROR_SHARING_VIOLATION, }, //
+ // { ERROR_LOCK_VIOLATION, }, //
+ // { ERROR_NOT_SUPPORTED, }, //
+ // { ERROR_DUP_NAME, }, //
+ // { ERROR_BAD_DEV_TYPE, }, //
+ // { ERROR_BUFFER_OVERFLOW, }, //
+ { ERROR_BUSY, MBG_ERR_BUSY }, //
+ // { ERROR_NOACCESS, }, //
+ { 0, 0 } // end-of-table identifier
+
+}; // win32_error_table
+
+
+
+static ERRNO_CNV_ENTRY win32_wsa_err_table[] =
+{
+ { WSAEINTR, MBG_ERR_INTR }, // 10004L A blocking operation was interrupted by a call to WSACancelBlockingCall.
+ // { WSAEBADF // 10009L The file handle supplied is not valid.
+ // { WSAEACCES // 10013L An attempt was made to access a socket in a way forbidden by its access permissions.
+ // { WSAEFAULT // 10014L The system detected an invalid pointer address in attempting to use a pointer argument in a call.
+ // { WSAEINVAL // 10022L An invalid argument was supplied.
+ // { WSAEMFILE // 10024L Too many open sockets.
+ // { WSAEWOULDBLOCK // 10035L A non-blocking socket operation could not be completed immediately.
+ // { WSAEINPROGRESS // 10036L A blocking operation is currently executing.
+ // { WSAEALREADY // 10037L An operation was attempted on a non-blocking socket that already had an operation in progress.
+ { WSAENOTSOCK, MBG_ERR_NOT_A_SOCKET }, // 10038L An operation was attempted on something that is not a socket.
+ // { WSAEDESTADDRREQ // 10039L A required address was omitted from an operation on a socket.
+ // { WSAEMSGSIZE // 10040L A message sent on a datagram socket was larger than the internal message buffer or some other network limit, or the buffer used to receive a datagram into was smaller than the datagram itself.
+ // { WSAEPROTOTYPE // 10041L A protocol was specified in the socket function call that does not support the semantics of the socket type requested.
+ // { WSAENOPROTOOPT // 10042L An unknown, invalid, or unsupported option or level was specified in a getsockopt or setsockopt call.
+ // { WSAEPROTONOSUPPORT // 10043L The requested protocol has not been configured into the system, or no implementation for it exists.
+ // { WSAESOCKTNOSUPPORT // 10044L The support for the specified socket type does not exist in this address family.
+ // { WSAEOPNOTSUPP // 10045L The attempted operation is not supported for the type of object referenced.
+ // { WSAEPFNOSUPPORT // 10046L The protocol family has not been configured into the system or no implementation for it exists.
+ // { WSAEAFNOSUPPORT // 10047L An address incompatible with the requested protocol was used.
+ // { WSAEADDRINUSE // 10048L Only one usage of each socket address (protocol/network address/port) is normally permitted.
+ // { WSAEADDRNOTAVAIL // 10049L The requested address is not valid in its context.
+ // { WSAENETDOWN // 10050L A socket operation encountered a dead network.
+ // { WSAENETUNREACH // 10051L A socket operation was attempted to an unreachable network.
+ // { WSAENETRESET // 10052L The connection has been broken due to keep-alive activity detecting a failure while the operation was in progress.
+ // { WSAECONNABORTED // 10053L An established connection was aborted by the software in your host machine.
+ { WSAECONNRESET, MBG_ERR_CONN_RESET }, // 10054L An existing connection was forcibly closed by the remote host.
+ // { WSAENOBUFS // 10055L An operation on a socket could not be performed because the system lacked sufficient buffer space or because a queue was full.
+ // { WSAEISCONN // 10056L A connect request was made on an already connected socket.
+ // { WSAENOTCONN // 10057L A request to send or receive data was disallowed because the socket is not connected and (when sending on a datagram socket using a sendto call) no address was supplied.
+ // { WSAESHUTDOWN // 10058L A request to send or receive data was disallowed because the socket had already been shut down in that direction with a previous shutdown call.
+ // { WSAETOOMANYREFS // 10059L Too many references to some kernel object.
+ // { WSAETIMEDOUT // 10060L A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond.
+ // { WSAECONNREFUSED // 10061L No connection could be made because the target machine actively refused it.
+ // { WSAELOOP // 10062L Cannot translate name.
+ // { WSAENAMETOOLONG // 10063L Name component or name was too long.
+ // { WSAEHOSTDOWN // 10064L A socket operation failed because the destination host was down.
+ // { WSAEHOSTUNREACH // 10065L A socket operation was attempted to an unreachable host.
+ // { WSAENOTEMPTY // 10066L Cannot remove a directory that is not empty.
+ // { WSAEPROCLIM // 10067L A Windows Sockets implementation may have a limit on the number of applications that may use it simultaneously.
+ // { WSAEUSERS // 10068L Ran out of quota.
+ // { WSAEDQUOT // 10069L Ran out of disk quota.
+ // { WSAESTALE // 10070L File handle reference is no longer available.
+ // { WSAEREMOTE // 10071L Item is not available locally.
+ // { WSASYSNOTREADY // 10091L WSAStartup cannot function at this time because the underlying system it uses to provide network services is currently unavailable.
+ // { WSAVERNOTSUPPORTED // 10092L The Windows Sockets version requested is not supported.
+ { WSANOTINITIALISED, MBG_ERR_SOCK_INIT }, // 10093L Either the application has not called WSAStartup, or WSAStartup failed.
+ // { WSAEDISCON // 10101L Returned by WSARecv or WSARecvFrom to indicate the remote party has initiated a graceful shutdown sequence.
+ // { WSAENOMORE // 10102L No more results can be returned by WSALookupServiceNext.
+ // { WSAECANCELLED // 10103L A call to WSALookupServiceEnd was made while this call was still processing. The call has been canceled.
+ // { WSAEINVALIDPROCTABLE // 10104L The procedure call table is invalid.
+ // { WSAEINVALIDPROVIDER // 10105L The requested service provider is invalid.
+ // { WSAEPROVIDERFAILEDINIT // 10106L The requested service provider could not be loaded or initialized.
+ // { WSASYSCALLFAILURE // 10107L A system call that should never fail has failed.
+ // { WSASERVICE_NOT_FOUND // 10108L No such service is known. The service cannot be found in the specified name space.
+ // { WSATYPE_NOT_FOUND // 10109L The specified class was not found.
+ // { WSA_E_NO_MORE // 10110L No more results can be returned by WSALookupServiceNext.
+ // { WSA_E_CANCELLED // 10111L A call to WSALookupServiceEnd was made while this call was still processing. The call has been canceled.
+ // { WSAEREFUSED // 10112L A database query failed because it was actively refused.
+ { WSAHOST_NOT_FOUND, MBG_ERR_HOST_NOT_FOUND }, // 11001L No such host is known.
+ // { WSATRY_AGAIN // 11002L This is usually a temporary error during hostname resolution and means that the local server did not receive a response from an authoritative server.
+ // { WSANO_RECOVERY // 11003L A non-recoverable error occurred during a database lookup.
+ // { WSANO_DATA // 11004L The requested name is valid, but no data of the requested type was found.
+ { 0, 0 } // end-of-table identifier
+
+}; // win32_wsa_err_table
+
+#endif // defined( MBG_TGT_WIN32 )
+
+
+
+/**
+ * @brief Lookup some error code in a conversion table
+ *
+ * @param[in] orig_errno
+ * @param[in] tbl
+ *
+ * @return @ref MBG_ERROR_CODES associated with the original error code,
+ * or ::MBG_ERR_UNSPEC if origianl code not found in table.
+ */
+static /*HDR*/
+int lookup_mbg_errno( int orig_errno, const ERRNO_CNV_ENTRY tbl[] )
+{
+ const ERRNO_CNV_ENTRY *p;
+
+ for ( p = tbl; p->orig_errno || p->mbg_errno; p++ )
+ if ( p->orig_errno == orig_errno )
+ return p->mbg_errno;
+
+ return MBG_ERR_UNSPEC;
+
+} // lookup_mbg_errno
+
+
+
+/*HDR*/
+/**
+ * @brief Return an error string associated with the @ref MBG_ERROR_CODES
+ *
+ * @param[in] mbg_errno One of the @ref MBG_ERROR_CODES
+ *
+ * @return A constant string describing the error, or NULL for unknown error codes
+ */
+const char *mbg_strerror( int mbg_errno )
+{
+ static const MBG_CODE_NAME_TABLE_ENTRY tbl[] = MBG_ERR_NAMES_ENG;
+
+ const MBG_CODE_NAME_TABLE_ENTRY *p;
+
+ for ( p = tbl; p->name; p++ )
+ {
+ if ( mbg_errno == p->code )
+ return p->name;
+ }
+
+
+ return "Unknown error";
+
+} // mbg_strerror
+
+
+
+// test if ioctl error and print msg if true
+//### TODO check if this should be renamed
+/*HDR*/
+int mbg_ioctl_err( int rc, const char *descr )
+{
+ if ( mbg_rc_is_error( rc ) )
+ {
+ fprintf( stderr, "** %s: %s (rc: %i)\n", descr, mbg_strerror( rc ), rc );
+ return -1;
+ }
+
+ return 0;
+
+} // mbg_ioctl_err
+
+
+
+#if defined( MBG_TGT_CVI )
+
+/*HDR*/
+/**
+ * @brief Translate an error code from the Labwindows/CVI RS-232 library to one of the @ref MBG_ERROR_CODES
+ *
+ * @param[in] cvi_rc An error code returned by a CVI RS-232 library function
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ *
+ * @see http://zone.ni.com/reference/en-XX/help/370051V-01/cvi/libref/cvirs232_error_conditions/
+ */
+int mbg_cvi_rs232_error_to_mbg( int cvi_rc, const char *info )
+{
+ #if DEBUG
+ if ( info )
+ fprintf( stderr, "%s, CVI RS-232 rc: %i\n", info, cvi_rc );
+ #else
+ (void) info; // avoid compiler warning
+ #endif
+
+ return ( cvi_rc < 0 ) ? lookup_mbg_errno( cvi_rc, cvi_rs232_error_table ) : MBG_SUCCESS;
+
+} // mbg_cvi_rs232_error_to_mbg
+
+#endif
+
+
+
+#if defined( MBG_TGT_WIN32 )
+
+/*HDR*/
+/**
+ * @brief Translate a Windows non-socket API error code to one of the @ref MBG_ERROR_CODES
+ *
+ * @param[in] last_err A Windows non-socket API error code as returned by GetLastError()
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+int mbg_win32_last_err_to_mbg( DWORD last_err, const char *info )
+{
+ #if DEBUG
+ if ( info )
+ fprintf( stderr, "%s, wsa_err: 0x%08lX\n", info, (long) last_err );
+ #else
+ (void) info; // avoid compiler warning
+ #endif
+
+ return ( last_err == ERROR_SUCCESS ) ? MBG_SUCCESS : lookup_mbg_errno( last_err, win32_error_table );
+
+} // mbg_win32_last_err_to_mbg
+
+
+
+/*HDR*/
+/**
+ * @brief Translate a Windows socket API error code to one of the @ref MBG_ERROR_CODES
+ *
+ * @param[in] wsa_err A Windows socket API error code as returned by WSAGetLastError()
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+int mbg_win32_wsa_err_to_mbg( DWORD wsa_err, const char *info )
+{
+ #if DEBUG
+ if ( info )
+ fprintf( stderr, "%s, wsa_err: 0x%08lX\n", info, (long) wsa_err );
+ #else
+ (void) info; // avoid compiler warning
+ #endif
+
+ // The WSA error code is only retrieved after an error has occurred, so
+ // we don't need care for the success case here.
+ return lookup_mbg_errno( wsa_err, win32_wsa_err_table );
+
+} // mbg_win32_wsa_err_to_mbg
+
+#endif // defined( MBG_TGT_WIN32 )
+
+
+
+#if _MBG_TGT_HAS_POSIX_ERRNO
+
+/*HDR*/
+/**
+ * @brief Translate a POSIX errno error code to one of the @ref MBG_ERROR_CODES
+ *
+ * @param[in] posix_errno A POSIX error code as usually defined in errno.h
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+int mbg_posix_errno_to_mbg( int posix_errno, const char *info )
+{
+ #if DEBUG
+ if ( info )
+ fprintf( stderr, "%s: %s (errno: %i)\n", info,
+ strerror( posix_errno ), posix_errno );
+ #else
+ (void) info; // avoid compiler warning
+ #endif
+
+ return lookup_mbg_errno( posix_errno, posix_errno_table );
+
+} // mbg_posix_errno_to_mbg
+
+#endif // _MBG_TGT_HAS_POSIX_ERRNO
+
+
+
+#if defined( MBG_TGT_POSIX )
+
+/*HDR*/
+/**
+ * @brief Translate a POSIX h_errno error code to one of the @ref MBG_ERROR_CODES
+ *
+ * This function is specific to translate error codes returned by
+ * gethostbyname() and gethostbyaddr(). In case of error these functions
+ * don't set errno but h_errno to a specific value.
+ *
+ * The functions gethostbyname() and gethostbyaddr() are obsolete,
+ * and getaddressinfo() should be used preferably.
+ *
+ * @param[in] posix_h_errno An error code as usually defined in netdb.h
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+int mbg_posix_h_errno_to_mbg( int posix_h_errno, const char *info )
+{
+ #if DEBUG
+ if ( info )
+ fprintf( stderr, "%s: %s (h_errno: %i)\n", info,
+ hstrerror( posix_h_errno ), posix_h_errno );
+ #else
+ (void) info; // avoid compiler warning
+ #endif
+
+ return lookup_mbg_errno( posix_h_errno, posix_h_errno_table );
+
+} // mbg_posix_h_errno_to_mbg
+
+#endif // defined( MBG_TGT_POSIX )
+
+
+
+/*HDR*/
+/**
+ * @brief Get and translate last error after non-socket function call
+ *
+ * Retrieve the "last error" code after a non-socket function has been called
+ * and translate to one of the @ref MBG_ERROR_CODES.
+ *
+ * On POSIX systems the "last error" code is always stored in errno, but
+ * e.g. under Windows the "last error" code after a socket function
+ * has to be retrieved by calling WSAGetLastError(), whereas the "last error"
+ * code from non-socket POSIX-like functions has to be retrieved
+ * by calling GetLastError().
+ *
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+int mbg_get_last_error( const char *info )
+{
+ #if defined( MBG_TGT_WIN32 )
+
+ // Under Windows the "last error" code after a non-socket function
+ // has to be retrieved by calling GetLastError(), whereas
+ // the "last error" code from POSIX-like socket functions
+ // is retrieved by calling WSAGetLastError().
+ return mbg_win32_last_err_to_mbg( GetLastError(), info );
+
+ #elif defined( MBG_TGT_POSIX )
+
+ // On POSIX systems the "last error" code is always stored in errno.
+ return mbg_posix_errno_to_mbg( errno, info );
+
+ #else
+
+ // ### TODO #error This function is not supported for this target.
+ return mbg_posix_errno_to_mbg( errno, info );
+
+ #endif
+
+} // mbg_get_last_error
+
+
+
+#if !defined( MBG_TGT_DOS )
+
+/*HDR*/
+/**
+ * @brief Get and translate last error after socket function call
+ *
+ * Retrieve the "last error" code after a socket function has been called
+ * and translate to one of the @ref MBG_ERROR_CODES.
+ *
+ * On POSIX systems the "last error" code is always stored in errno, but
+ * e.g. under Windows the "last error" code after a socket function
+ * has to be retrieved by calling WSAGetLastError, whereas the "last error"
+ * code from non-socket POSIX-like functions is stored in errno as usual.
+ *
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+int mbg_get_last_socket_error( const char *info )
+{
+ #if defined( MBG_TGT_CVI )
+
+ #warning This needs to be implemented for CVI
+ return MBG_ERR_UNSPEC;
+
+ #elif defined( MBG_TGT_WIN32 )
+
+ // Under Windows the "last error" code after a socket function
+ // has to be retrieved by calling WSAGetLastError, whereas
+ // the "last error" code from non-socket POSIX-like functions
+ // is stored in errno as usual.
+ return mbg_win32_wsa_err_to_mbg( WSAGetLastError(), info );
+
+ #elif defined( MBG_TGT_POSIX )
+
+ // On POSIX systems the "last error" code is always stored in errno.
+ return mbg_posix_errno_to_mbg( errno, info );
+
+ #else
+
+ #error This function is not supported for this target.
+
+ #endif
+
+} // mbg_get_last_socket_error
+
+
+
+/*HDR*/
+/**
+ * @brief Retrieve and convert last error after gethostbyname()
+ *
+ * This function is specific to retrieve and translate error codes
+ * returned by gethostbyname() and gethostbyaddr(). In case of error
+ * these functions don't set errno but h_errno on POSIX systems, but
+ * under Windows the error code can be retrieved by WSAGetLastError()
+ * as usual.
+ *
+ * The functions gethostbyname() and gethostbyaddr() are obsolete,
+ * and getaddressinfo() should be used preferably.
+ *
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+int mbg_get_gethostbyname_error( const char *info )
+{
+ #if defined( MBG_TGT_CVI )
+
+ #warning This needs to be implemented for CVI
+ return MBG_ERR_UNSPEC;
+
+ #elif defined( MBG_TGT_WIN32 )
+
+ return mbg_win32_wsa_err_to_mbg( WSAGetLastError(), info );
+
+ #elif defined( MBG_TGT_POSIX )
+
+ return mbg_posix_h_errno_to_mbg( h_errno, info );
+
+ #else
+
+ #error This function is not supported for this target.
+
+ #endif
+
+} // mbg_get_gethostbyname_error
+
+#endif // !defined( MBG_TGT_DOS )
+
+
+
+#if 0 // not yet finished
+// error handler for getaddressinfo()
+/*
+ * Handle specific error returned by getaddressinfo()
+ */
+ /*HDR*/
+int mbg_gai_error( int rc, const char *info )
+{
+ #if defined( MBG_TGT_CVI )
+
+ #warning This needs to be implemented for CVI
+ return MBG_ERR_UNSPEC;
+
+ #elif defined( MBG_TGT_WIN32 )
+
+ return mbg_win32_wsa_err_to_mbg( WSAGetLastError(), info );
+
+ #elif defined( MBG_TGT_POSIX )
+
+ return mbg_posix_h_errno_to_mbg( h_errno, info );
+
+ #else
+
+ return MBG_ERR_UNSPEC;
+
+ #endif
+
+} // mbg_get_gai_error
+
+#endif
+
+
+
+#if defined( USE_MBG_ZLIB )
+
+/*HDR*/
+/**
+ * @brief Retrieve and convert last zlib internal error code
+ *
+ * @param[in] zlib_error zlib internal error code
+ * @param[in] info An optional informational text string, or NULL
+ * @param[in] msg An optional zlib specific error msg, or NULL.
+ * Struct z_stream contains member msg.
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+int mbg_zlib_error_to_mbg( int zlib_error, const char *info, const char *msg )
+{
+ #if DEBUG
+ if ( info && msg )
+ fprintf( stderr, "%s: %s (zlib_error: %d)\n", info,
+ msg, zlib_error );
+ #endif
+
+ switch ( zlib_error )
+ {
+ case Z_ERRNO: return mbg_get_last_error( info );
+ case Z_MEM_ERROR: return MBG_ERR_NO_MEM;
+ /*
+ * All other zlib error codes are not specified any further.
+ * So, it's hard to guess what they mean and we return MBG_UNSPEC so far.
+ */
+ default:
+ return MBG_ERR_UNSPEC;
+ }
+
+} // mbg_zlib_error_to_mbg
+
+#endif // defined(USE_MBG_ZLIB)
+
+
diff --git a/mbglib/common/mbgerror.h b/mbglib/common/mbgerror.h
index bd9cb4a..817baac 100755
--- a/mbglib/common/mbgerror.h
+++ b/mbglib/common/mbgerror.h
@@ -1,8 +1,7 @@
/**************************************************************************
*
- * $Id: mbgerror.h 1.6 2012/10/02 18:42:26 martin REL_M $
- * $Name: $
+ * $Id: mbgerror.h 1.13 2017/02/28 15:23:14 gregoire TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -12,7 +11,27 @@
*
* -----------------------------------------------------------------------
* $Log: mbgerror.h $
- * Revision 1.6 2012/10/02 18:42:26 martin
+ * Revision 1.13 2017/02/28 15:23:14 gregoire
+ * error code MBG_ERR_INV_IDX added
+ * Revision 1.12 2017/01/10 15:54:56 philipp
+ * Fixed syntax error
+ * Revision 1.11 2017/01/10 14:26:31 philipp
+ * Added error MBG_ERR_NOT_CONFIGURED
+ * Revision 1.10 2016/12/16 12:40:33 thomas-b
+ * Added MBG_ERR_NO_SPACE
+ * Revision 1.9 2016/10/31 17:41:55 martin
+ * New error code MBG_ERR_DATA_FMT.
+ * Revision 1.8 2016/08/05 12:29:20 martin
+ * Re-enabled some symbols which have been commented out.
+ * Added new codes, and initializers for code/string conversion tables.
+ * Updated doxygen comments.
+ * Updated function prorotypes.
+ * Revision 1.7 2014/05/27 13:32:47Z martin
+ * Defined additional common error codes which can be
+ * translated from OS specific codes.
+ * Function prototypes from new module mbgerror.c.
+ * Comments in doxygen style.
+ * Revision 1.6 2012/10/02 18:42:26Z martin
* New codes MBG_ERR_N_POUT_EXCEEDS_SUPP and
* MBG_ERR_N_UC_MSTR_EXCEEDS_SUPP.
* Modified comments for doxygen.
@@ -39,6 +58,7 @@
/* Other headers to be included */
#include <mbg_tgt.h>
+#include <words.h>
#ifdef _MBGERROR
#define _ext
@@ -50,96 +70,301 @@
/* Start of header body */
+#if !defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_KERNEL )
+ //### TODO Surprisingly we need this also for Windows
+ // in kernel mode. This should be fixed.
+ #define DWORD uint32_t // just to avoid compiler errors
+#endif
+
+
+
/**
- @defgroup group_error_codes Error codes
-
- Error codes used with Meinberg devices and drivers.
- The codes will be translated into an OS dependent error code,
- when they are returned to the calling function.
-
- For Windows, these codes are made positive and or'ed with 0xE0000000 afterwards.
-
- Example: Code -19 (#MBG_ERR_GENERIC) will be converted to 0xE0000013 under Windows.
-
- @note Attention:
- These error codes below must match exactly the corresponding codes that are evaluated in user space.
- For Windows, they are located in messages.mc/.h in mbgsvctl.dll
-
- @{
-*/
-
-
-#define MBG_SUCCESS PCPS_SUCCESS /**< 0, no error */
-
-// The codes below are defined in pcpsdefs.h and returned by the firmware:
-#define MBG_ERR_STIME PCPS_ERR_STIME /**< -1, invalid date/time/status passed */
-#define MBG_ERR_CFG PCPS_ERR_CFG /**< -2, invalid parms with a PCPS_CFG_GROUP cmd */
-
-// Codes returned by the driver's low level functions:
-#define MBG_ERR_GENERIC -19 /**< Generic error */
-#define MBG_ERR_TIMEOUT -20 /**< Timeout accessing the board */
-#define MBG_ERR_FW_ID -21 /**< Invalid firmware ID */
-#define MBG_ERR_NBYTES -22 /**< The number of parameter bytes
- passed to the board did not match
- the number of bytes expected. */
-#define MBG_ERR_INV_TIME -23 /**< The device's time is not valid */
-#define MBG_ERR_FIFO -24 /**< The device's FIFO is empty, though
- it shouldn't be */
-#define MBG_ERR_NOT_READY -25 /**< Board is temporary unable to respond
- (during initialization after RESET) */
-#define MBG_ERR_INV_TYPE -26 /**< Board did not recognize data type */
-
-
-// Codes returned by the driver's high level functions:
-#define MBG_ERR_NO_MEM -27 /**< Failed to allocate memory */
-#define MBG_ERR_CLAIM_RSRC -28 /**< Failed to claim port or mem resource */
-#define MBG_ERR_DEV_NOT_SUPP -29 /**< Specified device type not supported by driver */
-#define MBG_ERR_INV_DEV_REQUEST -30 /**< IOCTL call not supported by driver */
-#define MBG_ERR_NOT_SUPP_BY_DEV -31 /**< Cmd or feature not supported by device */
-#define MBG_ERR_USB_ACCESS -32 /**< USB access failed */
-#define MBG_ERR_CYCLIC_TIMEOUT -33 /**< Cyclic event (IRQ, etc.) didn't occur */
-#define MBG_ERR_NOT_SUPP_ON_OS -34 /**< The function is not supported on this operating system */
-#define MBG_ERR_LIB_NOT_COMPATIBLE -35 /**< The installed version of the DLL/shared object is not
- compatible with version used to build the application */
-#define MBG_ERR_N_COM_EXCEEDS_SUPP -36 /**< The number of COM ports provided by the device
- exceeds the maximum supported by the driver */
-#define MBG_ERR_N_STR_EXCEEDS_SUPP -37 /**< The number of string formats supported by the device
- exceeds the maximum supported by the driver */
-#define MBG_ERR_IRQ_UNSAFE -38 /**< The enabled IRQs are unsafe with this firmware/ASIC version */
-#define MBG_ERR_N_POUT_EXCEEDS_SUPP -39 /**< The number of programmable outputs provided by the device
- exceeds the maximum supported by the driver */
+ * @brief Error codes used with Meinberg devices and drivers
+ *
+ * Appropriate error strings can be retrieved via the ::mbg_strerror function.
+ *
+ * Under Windows, some message strings are provided as resources appended
+ * to the mbgctrl DLL, but the codes specified here have to be translated
+ * to Windows-specific error codes before the appropriate resource string
+ * can be retrieved. Actually this is done by taking the absolute number
+ * of an error code and have it or'ed with 0xE0000000 afterwards, e.g.
+ * ::MBG_ERR_GENERIC (-19) will yield Windows code 0xE0000013.
+ * * See ::_mbg_err_to_os
+ *
+ * @see ::MBG_ERR_NAMES_ENG
+ *
+ * @anchor MBG_RETURN_CODES @{ */
+
+// NOTE: Some of these codes have to match codes which are defined in pcpsdefs.h
+// and returned by the firmware of bus-level devices, so the definitions
+// must *not* be renumbered.
+
+#define MBG_SUCCESS 0 ///< no error, has to match ::PCPS_SUCCESS
+
+ /** @anchor MBG_ERROR_CODES @{ */
+
+// Other codes which have to match codes defined in pcpsdefs.h returned by bus-level devices
+#define MBG_ERR_STIME -1 ///< tried to write invalid date/time/status to device, has to match ::PCPS_ERR_STIME
+#define MBG_ERR_CFG -2 ///< tried to write invalid configuration parameters to device, has to match ::PCPS_ERR_CFG (see also ::MBG_ERR_INV_CFG)
+
+
+// Codes returned by low level functions of the bus-level device driver
+#define MBG_ERR_GENERIC -19 ///< generic error
+#define MBG_ERR_TIMEOUT -20 ///< timeout accessing the device
+#define MBG_ERR_FW_ID -21 ///< invalid firmware ID
+#define MBG_ERR_NBYTES -22 ///< the number of parameter bytes passed to the device did not
+ ///< match the number of bytes expected by the device
+
+#define MBG_ERR_INV_TIME -23 ///< the device doesn't have valid time
+#define MBG_ERR_FIFO -24 ///< the data FIFO of a bus-level device is empty, though it shouldn't be
+#define MBG_ERR_NOT_READY -25 ///< bus-level device is temp. unable to respond e.g. during init. after RESET
+#define MBG_ERR_INV_TYPE -26 ///< bus-level device didn't recognize data type
+
+
+// Codes returned by the high level API functions
+#define MBG_ERR_NO_MEM -27 ///< failed to allocate memory
+#define MBG_ERR_CLAIM_RSRC -28 ///< failed to claim port or mem resource
+#define MBG_ERR_DEV_NOT_SUPP -29 ///< specified device type not supported by driver
+#define MBG_ERR_INV_DEV_REQUEST -30 ///< IOCTL call not supported by driver
+#define MBG_ERR_NOT_SUPP_BY_DEV -31 ///< cmd or feature not supported by device
+#define MBG_ERR_USB_ACCESS -32 ///< USB access failed
+#define MBG_ERR_CYCLIC_TIMEOUT -33 ///< cyclic event (IRQ, etc.) didn't occur
+#define MBG_ERR_NOT_SUPP_ON_OS -34 ///< function is not supported under this operating system
+#define MBG_ERR_LIB_NOT_COMPATIBLE -35 ///< installed shared lib. version not compat. with version used at build time
+#define MBG_ERR_N_COM_EXCEEDS_SUPP -36 ///< num. COM ports of the device exceeds max. supp. by driver
+#define MBG_ERR_N_STR_EXCEEDS_SUPP -37 ///< num. string formats of the device exceeds max. supp. by driver
+#define MBG_ERR_IRQ_UNSAFE -38 ///< enabled IRQ of bus-level device is unsafe with this firmware/ASIC version
+#define MBG_ERR_N_POUT_EXCEEDS_SUPP -39 ///< num. prog. outputs of the device exceeds max. supp. by driver
// Legacy codes used with DOS TSRs only:
-#define MBG_ERR_INV_INTNO -40 /**< Invalid interrupt number */
-#define MBG_ERR_NO_DRIVER -41 /**< A driver could not be found */
-#define MBG_ERR_DRV_VERSION -42 /**< The driver is too old */
+#define MBG_ERR_INV_INTNO -40 ///< invalid interrupt number
+#define MBG_ERR_NO_DRIVER -41 ///< a driver could not be found
+#define MBG_ERR_DRV_VERSION -42 ///< the driver is too old
-#define MBG_ERR_COPY_TO_USER -43 /**< kernel driver failed to copy data from kernel to user space */
-#define MBG_ERR_COPY_FROM_USER -44 /**< kernel driver failed to copy data from use to kernel space */
+#define MBG_ERR_COPY_TO_USER -43 ///< kernel driver failed to copy data from kernel to user space
+#define MBG_ERR_COPY_FROM_USER -44 ///< kernel driver failed to copy data from use to kernel space
+
// More codes returned by the driver's high level functions:
+#define MBG_ERR_N_UC_MSTR_EXCEEDS_SUPP -45 ///< num. PTP unicast masters of the device exceeds max. supp. by driver
+#define MBG_ERR_N_GNSS_EXCEEDS_SUPP -46 ///< num. of GNSS systems supp. by device exceeds max. supp. by driver
+#define MBG_ERR_N_GPIO_EXCEEDS_SUPP -47 ///< num. of GPIO ports supp. by device exceeds max. supp. by driver
+#define MBG_ERR_N_XMR_EXCEEDS_SUPP -48 ///< num. of XMR sources supp. by device exceeds max. supp. by driver
+
+#define MBG_ERR_UNSPEC -60 ///< unspecified error
+
+#define MBG_ERR_HDR_CSUM -61 ///< binary protocol header checksum error
+#define MBG_ERR_DATA_CSUM -62 ///< binary protocol data checksum error
+#define MBG_ERR_RCVD_NACK -63 ///< binary protocol received reply msg with a NACK code
+#define MBG_ERR_RCVD_NO_ACK -64 ///< binary protocol received reply msg without expected ACK code //### TODO
+#define MBG_ERR_CONN_TYPE -65 ///< binary protocol no valid/supported connection type specified
+#define MBG_ERR_BYTES_WRITTEN -66 ///< binary protocol failed to write all bytes
+#define MBG_ERR_AUTH -67 ///< binary protocol failed authentication
+
+#define MBG_ERR_SOCK_INIT -68 ///< socket interface not initialized, or failed to initialize
+#define MBG_ERR_INV_SOCK_FD -69 ///< invalid socket when tried to open network socket
+#define MBG_ERR_NOT_A_SOCKET -70 ///< socket descriptor is not a socket
+#define MBG_ERR_NBLOCK_WAIT_SLCT -71 ///< select timed out when waiting for non-blocking network port to become ready
+#define MBG_ERR_NBLOCK_WAIT_WR_FD -72 ///< write fd not set after select when waiting for non-blocking network port to become ready
+
+#define MBG_ERR_IO -73 ///< generic I/O error
+#define MBG_ERR_INV_PARM -74 ///< invalid parameter
+#define MBG_ERR_NO_DEV -75 ///< specified device not found
+#define MBG_ERR_NOT_FOUND -76 ///< specified item not found
+
+#define MBG_ERR_OVERFLOW -77 ///< range or buffer overflow
+#define MBG_ERR_PIPE -78 ///< pipe error
+#define MBG_ERR_INTR -79 ///< interrupted system call
+#define MBG_ERR_ACCESS -80 ///< access denied, e.g. when trying to access a device
+#define MBG_ERR_PERM -81 ///< operation not permitted, e.g. when trying to set the system time
+#define MBG_ERR_BUSY -82 ///< device busy
+#define MBG_ERR_INV_HANDLE -83 ///< invalid file/device handle specified
+
+#define MBG_ERR_XBP_CASC_LVL -84 ///< too many XBP cascading levels
+#define MBG_ERR_ENCRYPT -85 ///< encryption failed
+#define MBG_ERR_DECRYPT -86 ///< decryption failed
+
+#define MBG_ERR_DISCONN -87 ///< connection closed by remote site / host
+#define MBG_ERR_INV_CFG -88 ///< invalid/inconsistent configuration parameters read from device, see also ::MBG_ERR_CFG
+#define MBG_ERR_RANGE -89 ///< input parameter was out of range
+
+#define MBG_ERR_INV_TLV_ANN_BYTES -90 ///< number of announced TLV bytes doesn't match number of transferred bytes
+#define MBG_ERR_INV_TLV_SIZE -91 ///< ### TODO
+#define MBG_ERR_INV_TLV_UID -92 ///< ### TODO
+
+#define MBG_ERR_EXIST -93 ///< file exists
+#define MBG_ERR_DATA_SIZE -94 ///< the received data size toesn't match the expected data size
+#define MBG_ERR_NO_ENTITY -95 ///< no such entity //### TODO or use MBG_ERR_NO_DEV / MBG_ERR_NOT_FOUND ?
+#define MBG_ERR_ALREADY_ALLOC -96 ///< pointer already allocated when trying to allocate memory
+#define MBG_ERR_HOST_NOT_FOUND -97 ///< host not found
+#define MBG_ERR_CONN_RESET -98 ///< connection reset by peer
+#define MBG_ERR_DATA_FMT -99 ///< invalid data format
+
+#define MBG_ERR_NO_SPACE -100 ///< insufficient disk space left on the device
+#define MBG_ERR_NOT_CONFIGURED -101 ///< configuration option is not active/configured
+#define MBG_ERR_INV_IDX -102 ///< invalid index value used
+
+// NOTE: New codes have to be appended to this list, and the sequence of codes must not
+// be changed. Whenever new codes have been defined, appropriate entries have to be added
+// to the ::MBG_ERR_NAMES_ENG table initializer below, and the Windows-specific message
+// texts specified in messages.mc/.h from which the resources appended to mbgsvctl.dll
+// are generated have to be updated accordingly.
+
+/** @} anchor MBG_ERROR_CODES */
+
+/** @} anchor MBG_RETURN_CODES */
+
+
+/**
+ * @brief Strings associated with @ref MBG_RETURN_CODES
+ *
+ * @see @ref MBG_RETURN_CODES
+ */
+#define MBG_ERR_NAMES_ENG \
+{ \
+ { MBG_SUCCESS, "Success, no error" }, \
+ { MBG_ERR_STIME, "Invalid date/time for device" }, \
+ { MBG_ERR_CFG, "Invalid configuration parameters for device" }, \
+ { MBG_ERR_GENERIC, "Generic error" }, \
+ { MBG_ERR_TIMEOUT, "Timeout" }, \
+ { MBG_ERR_FW_ID, "Invalid firmware ID" }, \
+ { MBG_ERR_NBYTES, "Unexpected number of data bytes for this API" }, \
+ { MBG_ERR_INV_TIME, "Invalid time passed to device" }, \
+ { MBG_ERR_FIFO, "FIFO unexpectedly empty" }, \
+ { MBG_ERR_NOT_READY, "Device not ready" }, \
+ { MBG_ERR_INV_TYPE, "Unsupported data type" }, \
+ { MBG_ERR_NO_MEM, "Memory allocation error" }, \
+ { MBG_ERR_CLAIM_RSRC, "Faild to claim resources" }, \
+ { MBG_ERR_DEV_NOT_SUPP, "Device not supported" }, \
+ { MBG_ERR_INV_DEV_REQUEST, "Request not supported" }, \
+ { MBG_ERR_NOT_SUPP_BY_DEV, "Not supported by device" }, \
+ { MBG_ERR_USB_ACCESS, "USB access failed" }, \
+ { MBG_ERR_CYCLIC_TIMEOUT, "Cyclic message timeout" }, \
+ { MBG_ERR_NOT_SUPP_ON_OS, "Not supported by OS" }, \
+ { MBG_ERR_LIB_NOT_COMPATIBLE, "Shared lib not compatible" }, \
+ { MBG_ERR_N_COM_EXCEEDS_SUPP, "Num. COM ports exceeds supported" }, \
+ { MBG_ERR_N_STR_EXCEEDS_SUPP, "Num. string formats exceeds supported" }, \
+ { MBG_ERR_IRQ_UNSAFE, "Unsafe IRQ support" }, \
+ { MBG_ERR_N_POUT_EXCEEDS_SUPP, "Num prog. outputs exceeds supported" }, \
+ { MBG_ERR_INV_INTNO, "Invalid interrupt number" }, \
+ { MBG_ERR_NO_DRIVER, "Driver not found" }, \
+ { MBG_ERR_DRV_VERSION, "Driver too old" }, \
+ { MBG_ERR_COPY_TO_USER, "Error copying to user space" }, \
+ { MBG_ERR_COPY_FROM_USER, "Error copying from user space" }, \
+ { MBG_ERR_N_UC_MSTR_EXCEEDS_SUPP, "Num. PTP Unicast masters exceeds supported" }, \
+ { MBG_ERR_N_GNSS_EXCEEDS_SUPP, "Num. GNSS systems exceeds supported" }, \
+ { MBG_ERR_N_GPIO_EXCEEDS_SUPP, "Num. GPIO ports exceeds supported" }, \
+ { MBG_ERR_N_XMR_EXCEEDS_SUPP, "Num. XMR sources exceeds supported" }, \
+ { MBG_ERR_UNSPEC, "Unspecified error" }, \
+ { MBG_ERR_HDR_CSUM, "Header checksum error" }, \
+ { MBG_ERR_DATA_CSUM, "Data checksum error" }, \
+ { MBG_ERR_RCVD_NACK, "Received NACK message" }, \
+ { MBG_ERR_RCVD_NO_ACK, "Didn't receive ACK message" }, \
+ { MBG_ERR_CONN_TYPE, "Invalid I/O connection type" }, \
+ { MBG_ERR_BYTES_WRITTEN, "Failed to write all bytes" }, \
+ { MBG_ERR_AUTH, "Authentication failed" }, \
+ { MBG_ERR_SOCK_INIT, "Failed to initialize socket" }, \
+ { MBG_ERR_INV_SOCK_FD, "Invalid socket descriptor" }, \
+ { MBG_ERR_NOT_A_SOCKET, "Not a socket descriptor" }, \
+ { MBG_ERR_NBLOCK_WAIT_SLCT, "Select timed out waiting for port ready" }, \
+ { MBG_ERR_NBLOCK_WAIT_WR_FD, "Write file descriptor not ready after waiting for port ready" }, \
+ { MBG_ERR_IO, "Generic I/O error" }, \
+ { MBG_ERR_INV_PARM, "Invalid parameter" }, \
+ { MBG_ERR_NO_DEV, "Specified device not found" }, \
+ { MBG_ERR_NOT_FOUND, "Specified item not found" }, \
+ { MBG_ERR_OVERFLOW, "Buffer overflow" }, \
+ { MBG_ERR_PIPE, "Pipe error" }, \
+ { MBG_ERR_INTR, "Interrupted system call" }, \
+ { MBG_ERR_ACCESS, "Access denied" }, \
+ { MBG_ERR_PERM, "Operation not permitted" }, \
+ { MBG_ERR_BUSY, "Device busy" }, \
+ { MBG_ERR_INV_HANDLE, "Invalid handle" }, \
+ { MBG_ERR_XBP_CASC_LVL, "Too many XBP cascading levels" }, \
+ { MBG_ERR_ENCRYPT, "Encryption failed" }, \
+ { MBG_ERR_DECRYPT, "Decryption failed" }, \
+ { MBG_ERR_DISCONN, "Connection closed by remote site/host" }, \
+ { MBG_ERR_INV_CFG, "Invalid/inconsistent configuration read from device" }, \
+ { MBG_ERR_RANGE, "Input parameter was out of range" }, \
+ { MBG_ERR_INV_TLV_ANN_BYTES, "TLV num of transferred bytes differs from num of announced bytes" }, \
+ { MBG_ERR_INV_TLV_SIZE, "MBG_ERR_INV_TLV_SIZE" }, /* ### TODO */ \
+ { MBG_ERR_INV_TLV_UID, "MBG_ERR_INV_TLV_UID" }, /* ### TODO */ \
+ { MBG_ERR_EXIST, "File exists" }, \
+ { MBG_ERR_DATA_SIZE, "Received data size mismatch" }, \
+ { MBG_ERR_NO_ENTITY, "No such entity" }, \
+ { MBG_ERR_ALREADY_ALLOC, "Memory already allocated" }, \
+ { MBG_ERR_HOST_NOT_FOUND, "Host not found" }, \
+ { MBG_ERR_CONN_RESET, "Connection reset by peer" }, \
+ { MBG_ERR_DATA_FMT, "Invalid data format" }, \
+ { MBG_ERR_NO_SPACE, "Insufficient disk space" }, \
+ { MBG_ERR_NOT_CONFIGURED, "Configuration is not active and/or configured" }, \
+ { MBG_ERR_INV_IDX, "Invalid or unsupported index value used"}, \
+ { 0, NULL } /* end of table */ \
+}
+
+
+
+#if defined( __mbg_inline )
+
+static __mbg_inline
+/**
+ * @brief Check if the code returned by a function indicates an error
+ *
+ * @param[in] rc One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_rc_is_success
+ * @see @ref MBG_RETURN_CODES
+ */
+bool mbg_rc_is_error( int rc )
+{
+ // Meinberg error codes are all < 0.
+ return rc < MBG_SUCCESS;
+
+} // mbg_rc_is_error
+
+
+static __mbg_inline
+/**
+ * @brief Check if the code returned by a function indicates success
+ *
+ * @param[in] rc One of the @ref MBG_RETURN_CODES
+ *
+ * @see ::mbg_rc_is_error
+ * @see @ref MBG_RETURN_CODES
+ */
+bool mbg_rc_is_success( int rc )
+{
+ // There are functions which don't only return MBG_SUCCESS
+ // on success but some arbitrary positive number, e.g. the
+ // number of bytes sent. So success just means "not an error".
+ return !mbg_rc_is_error( rc );
+
+} // mbg_rc_is_success
+
+#else
+
+ #define mbg_rc_is_error( _rc ) ( (_rc) < MBG_SUCCESS )
+ #define mbg_rc_is_success( _rc ) ( !mbg_rc_is_error( _rc ) )
+
+#endif
+
-#define MBG_ERR_N_UC_MSTR_EXCEEDS_SUPP -39 /**< The number of PTP unicast masters supported by the device
- exceeds the maximum supported by the driver */
-/** @} group_error_codes */
-// Depending on the operating system, the codes above have to be converted before
-// they are sent up to user space
#if defined( MBG_TGT_WIN32 )
+
+ // Windows-specific codes and code conversion
+
#if !defined( STATUS_SUCCESS ) // not in kernel mode
#define STATUS_SUCCESS 0
#endif
#define _mbg_err_to_os( _c ) \
- ( ( _c == MBG_SUCCESS ) ? STATUS_SUCCESS : ( abs( _c ) | 0xE0000000 ) )
-#endif
+ ( ( (_c) == MBG_SUCCESS ) ? STATUS_SUCCESS : ( abs( _c ) | 0xE0000000 ) )
+
+#else
+ #define _mbg_err_to_os( _c ) (_c ) //### TODO remove this
-// If no specific conversion has been defined
-// then use the original codes.
-#if !defined( _mbg_err_to_os )
- #define _mbg_err_to_os( _c ) ( _c )
#endif
@@ -155,7 +380,140 @@ extern "C" {
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
-/* (no header definitions found) */
+ /**
+ * @brief Return an error string associated with the @ref MBG_ERROR_CODES
+ *
+ * @param[in] mbg_errno One of the @ref MBG_ERROR_CODES
+ *
+ * @return A constant string describing the error, or NULL for unknown error codes
+ */
+ const char *mbg_strerror( int mbg_errno ) ;
+
+ int mbg_ioctl_err( int rc, const char *descr ) ;
+ /**
+ * @brief Translate an error code from the Labwindows/CVI RS-232 library to one of the @ref MBG_ERROR_CODES
+ *
+ * @param[in] cvi_rc An error code returned by a CVI RS-232 library function
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ *
+ * @see http://zone.ni.com/reference/en-XX/help/370051V-01/cvi/libref/cvirs232_error_conditions/
+ */
+ int mbg_cvi_rs232_error_to_mbg( int cvi_rc, const char *info ) ;
+
+ /**
+ * @brief Translate a Windows non-socket API error code to one of the @ref MBG_ERROR_CODES
+ *
+ * @param[in] last_err A Windows non-socket API error code as returned by GetLastError()
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+ int mbg_win32_last_err_to_mbg( DWORD last_err, const char *info ) ;
+
+ /**
+ * @brief Translate a Windows socket API error code to one of the @ref MBG_ERROR_CODES
+ *
+ * @param[in] wsa_err A Windows socket API error code as returned by WSAGetLastError()
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+ int mbg_win32_wsa_err_to_mbg( DWORD wsa_err, const char *info ) ;
+
+ /**
+ * @brief Translate a POSIX errno error code to one of the @ref MBG_ERROR_CODES
+ *
+ * @param[in] posix_errno A POSIX error code as usually defined in errno.h
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+ int mbg_posix_errno_to_mbg( int posix_errno, const char *info ) ;
+
+ /**
+ * @brief Translate a POSIX h_errno error code to one of the @ref MBG_ERROR_CODES
+ *
+ * This function is specific to translate error codes returned by
+ * gethostbyname() and gethostbyaddr(). In case of error these functions
+ * don't set errno but h_errno to a specific value.
+ *
+ * The functions gethostbyname() and gethostbyaddr() are obsolete,
+ * and getaddressinfo() should be used preferably.
+ *
+ * @param[in] posix_h_errno An error code as usually defined in netdb.h
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+ int mbg_posix_h_errno_to_mbg( int posix_h_errno, const char *info ) ;
+
+ /**
+ * @brief Get and translate last error after non-socket function call
+ *
+ * Retrieve the "last error" code after a non-socket function has been called
+ * and translate to one of the @ref MBG_ERROR_CODES.
+ *
+ * On POSIX systems the "last error" code is always stored in errno, but
+ * e.g. under Windows the "last error" code after a socket function
+ * has to be retrieved by calling WSAGetLastError(), whereas the "last error"
+ * code from non-socket POSIX-like functions has to be retrieved
+ * by calling GetLastError().
+ *
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+ int mbg_get_last_error( const char *info ) ;
+
+ /**
+ * @brief Get and translate last error after socket function call
+ *
+ * Retrieve the "last error" code after a socket function has been called
+ * and translate to one of the @ref MBG_ERROR_CODES.
+ *
+ * On POSIX systems the "last error" code is always stored in errno, but
+ * e.g. under Windows the "last error" code after a socket function
+ * has to be retrieved by calling WSAGetLastError, whereas the "last error"
+ * code from non-socket POSIX-like functions is stored in errno as usual.
+ *
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+ int mbg_get_last_socket_error( const char *info ) ;
+
+ /**
+ * @brief Retrieve and convert last error after gethostbyname()
+ *
+ * This function is specific to retrieve and translate error codes
+ * returned by gethostbyname() and gethostbyaddr(). In case of error
+ * these functions don't set errno but h_errno on POSIX systems, but
+ * under Windows the error code can be retrieved by WSAGetLastError()
+ * as usual.
+ *
+ * The functions gethostbyname() and gethostbyaddr() are obsolete,
+ * and getaddressinfo() should be used preferably.
+ *
+ * @param[in] info An optional informational text string, or NULL
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+ int mbg_get_gethostbyname_error( const char *info ) ;
+
+ /**
+ * @brief Retrieve and convert last zlib internal error code
+ *
+ * @param[in] zlib_error zlib internal error code
+ * @param[in] info An optional informational text string, or NULL
+ * @param[in] msg An optional zlib specific error msg, or NULL.
+ * Struct z_stream contains member msg.
+ *
+ * @return One of the @ref MBG_ERROR_CODES
+ */
+ int mbg_zlib_error_to_mbg( int zlib_error, const char *info, const char *msg ) ;
+
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/mbggeo.h b/mbglib/common/mbggeo.h
index 415064a..57468d0 100755
--- a/mbglib/common/mbggeo.h
+++ b/mbglib/common/mbggeo.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbggeo.h 1.11 2011/06/22 10:18:10 martin REL_M $
+ * $Id: mbggeo.h 1.13 2017/01/27 08:57:58 martin REL_M $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,7 +10,7 @@
*
* Terms used:
*
- * WGS84 world geodetic system of 1984
+ * WGS84 World Geodetic System of 1984
*
* XYZ WGS84 earth centered, earth fixed (ECEF) kartesian
* coordinates
@@ -22,6 +22,11 @@
*
* -----------------------------------------------------------------------
* $Log: mbggeo.h $
+ * Revision 1.13 2017/01/27 08:57:58 martin
+ * Fixed macro syntax.
+ * Revision 1.12 2016/10/31 16:50:56 martin
+ * Fixed a typo.
+ * Updated doxygen comments.
* Revision 1.11 2011/06/22 10:18:10 martin
* Cleaned up handling of pragma pack().
* Revision 1.10 2008/09/03 14:54:28 martin
@@ -34,7 +39,7 @@
* Revision 1.7 2003/02/14 13:23:04Z martin
* Omit inclusion of mystd.h.
* Revision 1.6 2003/01/13 15:17:15 martin
- * Structures were defined with default alignment which
+ * Structures were defined with default alignment which
* could result in different data sizes on different platforms.
* Revision 1.5 2002/12/18 14:46:41Z martin
* Removed variable USER_POS meinberg.
@@ -71,104 +76,130 @@
/**
- Geographic longitude or latitude in [degrees, minutes, seconds]
- longitude East latitude North and positve, South or West angles negative
+ * @brief Geographic longitude or latitude in [degrees, minutes, seconds]
+ *
+ * Longitude East and latitude North are positive angles, South or West
+ * angles are negative.
*/
typedef struct
{
- uint16_t prefix; /**< 'N', 'E', 'S' or 'W' */
- uint16_t deg; /**< [0...90 (lat) or 0...180 (lon)] */
- uint16_t min; /**< [0...59] */
- double sec; /**< [0...59.999] */
+ uint16_t prefix; ///< 'N', 'E', 'S' or 'W'
+ uint16_t deg; ///< [0...90 (lat) or 0...180 (lon)]
+ uint16_t min; ///< [0...59]
+ double sec; ///< [0...59.99999...]
+
} DMS;
-// The corresponding macro _mbg_swab_dms() is defined in gpsdefs.h.
#define _mbg_swab_dms( _p ) \
+do \
{ \
_mbg_swab16( &(_p)->prefix ); \
_mbg_swab16( &(_p)->deg ); \
_mbg_swab16( &(_p)->min ); \
_mbg_swab_double( &(_p)->sec ); \
-}
+} while ( 0 )
+/**
+ * @brief A geographic position represented in different formats
+ */
typedef struct
{
- XYZ xyz; /**< always WGS84 ECEF coordinates */
- LLA lla; /**< depending on the ellipsoid used for reference */
- DMS longitude; /**< longitude in degrees, minutes, seconds */
- DMS latitude; /**< latitude in degrees, minutes, seconds */
- int16_t ellipsoid; /**< ellipsoid used for reference */
+ XYZ xyz; ///< Always WGS84 ECEF coordinates
+ LLA lla; ///< Longitude, latitude and altitude, depending on the ellipsoid used for reference
+ DMS longitude; ///< Longitude broken down to degrees, minutes, seconds
+ DMS latitude; ///< Latitude broken down to degrees, minutes, seconds
+ int16_t ellipsoid; ///< Ellipsoid used for reference, see ::ELLIPSOIDS
+
} POS;
#define _mbg_swab_pos( _p ) \
+do \
{ \
_mbg_swab_xyz( (_p)->xyz ); \
_mbg_swab_lla( (_p)->lla ); \
_mbg_swab_dms( &(_p)->longitude ); \
_mbg_swab_dms( &(_p)->latitude ); \
_mbg_swab16( &(_p)->ellipsoid ); \
-}
+} while ( 0 )
+/**
+ * @brief A structure used internally to compute a geographic position
+ *
+ * Also contains intermediate results useful for the computation.
+ */
typedef struct
{
- CSUM csum; /* checksum of the remaining bytes */
- int16_t valid; /* flag data are valid */
+ CSUM csum; ///< Checksum of the remaining bytes
+ int16_t valid; ///< Indicator if data is valid
- char name[40];
- POS pos; /* the position in WGS84 ECEF coords and LLA */
+ char name[40]; ///< Informational string
+ POS pos; ///< The position in WGS84 ECEF coords and ::LLA
double det;
-/* The components below hold the results of intermediate terms */
-/* computed in complete_user_pos(). */
+ // The components below hold the results of intermediate terms
+ // computed in complete_user_pos().
-/* The sin.., cos.., nt.. and ut.. variables are used to compute the */
-/* enu_dcos[] parameters of a SV structure in xyz_to_ead(). */
+ // The sin.., cos.., nt.. and ut.. variables are used to compute the
+ // enu_dcos[] parameters of a SV structure in xyz_to_ead().
-/* The e_radius.. variables are used to compute the latitude, longitude */
-/* and altitude from ECEF coordinates in lla_to_xyz(). */
+ // The e_radius.. variables are used to compute the latitude, longitude
+ // and altitude from ECEF coordinates in lla_to_xyz().
- double sin_lat; /* sin( latitude ) */
- double cos_lat; /* cos( latitude ) */
- double sin_lon; /* sin( longitude ) */
- double cos_lon; /* cos( longitude ) */
+ double sin_lat; ///< sin( latitude )
+ double cos_lat; ///< cos( latitude )
+ double sin_lon; ///< sin( longitude )
+ double cos_lon; ///< cos( longitude )
- double nt1; /* -sin_lat * cos_lon */
- double nt2; /* -sin_lat * sin_lon */
- double utx; /* cos_lat * cos_lon */
- double uty; /* cos_lat * sin_lon */
+ double nt1; ///< -sin_lat * cos_lon
+ double nt2; ///< -sin_lat * sin_lon
+ double utx; ///< cos_lat * cos_lon
+ double uty; ///< cos_lat * sin_lon
- double e_radius; /* N */
- double e_radius_alt; /* N + h */
+ double e_radius; ///< N
+ double e_radius_alt; ///< N + h
} USER_POS;
+/**
+ * @brief Characteristics of a geographic reference ellipsoid
+ */
typedef struct
{
- CSUM csum; /* checksum of the remaining bytes */
- int16_t valid; /* flag data are valid */
+ CSUM csum; ///< Checksum of the remaining bytes
+ int16_t valid; ///< Indicator if data is valid
char name[40];
- XYZ dxyz; /* offset from the WGS84 ECEF coords */
- double a; /* semi major axis */
- double rcp_f; /* reciproke of flatness */
+ XYZ dxyz; ///< Offset from the WGS84 ECEF coords
+ double a; ///< Semi major axis
+ double rcp_f; ///< Reciproke of flatness
+
+ // The variables below are computed in the init_mbggeo() function:
-/* the variables below will be computed in the init_mbggeo() function: */
+ double f; ///< Flatness
+ double b; ///< Semi minor axis
+ double sqr_e; ///< Square of numerical eccentricity
- double f; /* flatness */
- double b; /* semi minor axis */
- double sqr_e; /* square of numerical eccentricity */
} ELLIPSOID;
-enum { WGS84, BESSEL, N_ELLIPSOIDS };
+/**
+ * @brief An enumeration of known ellipsoids
+ */
+enum ELLIPSOIDS
+{
+ WGS84,
+ BESSEL,
+ N_ELLIPSOIDS
+};
+
_ext ELLIPSOID ellipsoid[N_ELLIPSOIDS]
#ifdef _DO_INIT
@@ -191,15 +222,15 @@ _ext ELLIPSOID ellipsoid[N_ELLIPSOIDS]
;
-/* WGS84 constants used */
+// WGS84 constants used
-_ext double OMEGADOTe /* earth's rotation rate [rad/sec] */
+_ext double OMEGADOTe // Earth's rotation rate [rad/sec]
#ifdef _DO_INIT
= 7.2921151467e-5
#endif
;
-_ext double mue /* earth's gravitational constant [m^3/sec^2] */
+_ext double mue // Earth's gravitational constant [m^3/sec^2]
#ifdef _DO_INIT
= 3.986005e14
#endif
@@ -249,10 +280,10 @@ _ext double d2r
;
-/* variables for simplifying computations */
+// Variables for simplifying computations
_ext double gps_two_pi;
-_ext double sqrt_mue; /* sqrt( mue ) */
+_ext double sqrt_mue; // sqrt( mue )
diff --git a/mbglib/common/mbgioctl.h b/mbglib/common/mbgioctl.h
index f127652..56d9355 100755
--- a/mbglib/common/mbgioctl.h
+++ b/mbglib/common/mbgioctl.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgioctl.h 1.25 2012/10/02 18:45:55 martin REL_M $
+ * $Id: mbgioctl.h 1.26.1.10 2017/02/22 15:23:45 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,24 @@
*
* -----------------------------------------------------------------------
* $Log: mbgioctl.h $
+ * Revision 1.26.1.10 2017/02/22 15:23:45 martin
+ * Fixed macro definition syntax to avoid clang compiler warnings.
+ * Revision 1.26.1.9 2014/10/17 13:28:28 martin
+ * Revision 1.26.1.8 2014/10/17 11:37:24 martin
+ * Doxygen changes.
+ * Revision 1.26.1.7 2014/06/26 09:44:03 martin
+ * Revision 1.26.1.6 2014/05/23 12:30:51 martin
+ * Revision 1.26.1.5 2014/05/22 16:16:52 martin
+ * Revision 1.26.1.4 2014/05/22 14:55:27 martin
+ * Added IOCTL codes for XMR support.
+ * Revision 1.26.1.3 2014/04/15 15:39:00 martin
+ * Support GPIO ports.
+ * Revision 1.26.1.2 2014/04/11 13:58:10 martin
+ * Simplified declaration of code/name tables.
+ * Revision 1.26.1.1 2014/03/05 10:37:58 martin
+ * Windows.h is now included in mbg_tgt.h.
+ * Revision 1.26 2013/09/26 08:27:04Z martin
+ * Support GNSS API.
* Revision 1.25 2012/10/02 18:45:55 martin
* There are some g++ versions which fail to compile source code using
* the macros provided by Linux to define IOCTL codes. If only the API
@@ -35,7 +53,7 @@
* Use MBG_TGT_KERNEL instead of _KDD_.
* Use IOTYPE 'Z' under *BSD since this means passthrough on NetBSD.
* Revision 1.24 2009/12/15 15:34:59Z daniel
- * Support reading the raw IRIG data bits for firmware versions
+ * Support reading the raw IRIG data bits for firmware versions
* which support this feature.
* Revision 1.23 2009/09/29 15:08:41Z martin
* Support retrieving time discipline info.
@@ -75,23 +93,23 @@
* Added support for programmable pulse outputs.
* Revision 1.12 2005/06/02 10:22:05Z martin
* Added IOCTL code IOCTL_GET_SYNTH_STATE.
- * Added IOCTL codes IOCTL_DEV_HAS_GENERIC_IO,
+ * Added IOCTL codes IOCTL_DEV_HAS_GENERIC_IO,
* IOCTL_PCPS_GENERIC_IO, and IOCTL_GET_SYNTH_STATE.
* Revision 1.11 2005/01/14 10:21:11Z martin
* Added IOCTLs which query device features.
* Revision 1.10 2004/12/09 11:03:36Z martin
* Support configuration of on-board frequency synthesizer.
* Revision 1.9 2004/11/09 12:49:41Z martin
- * Modifications were required in order to be able to configure IRIG
+ * Modifications were required in order to be able to configure IRIG
* settings of cards which provide both IRIG input and output.
- * The existing codes have been renamed with .._RX.. and are used to
- * configure the IRIG receiver (input). New codes have been defined
+ * The existing codes have been renamed with .._RX.. and are used to
+ * configure the IRIG receiver (input). New codes have been defined
* used to configure the IRIG transmitter.
* Renamed IOCTL_GET_GPS_STAT to IOCTL_GET_GPS_BVAR_STAT.
* Use more specific data types than generic types.
* Modified IOCTL codes used for hardware debugging.
* Revision 1.8 2004/09/06 15:46:04Z martin
- * Changed definition of IOCTL codes to support syntax used
+ * Changed definition of IOCTL codes to support syntax used
* with Linux kernel 2.6.x.
* Account for renamed symbols.
* Revision 1.7 2004/04/07 10:08:11 martin
@@ -130,7 +148,11 @@
#include <pci_asic.h>
-#define USE_DEBUG_PORT defined( MBG_ARCH_X86 )
+#if defined( MBG_ARCH_X86 )
+ #define USE_DEBUG_PORT 1
+#else
+ #define USE_DEBUG_PORT 0
+#endif
#if defined( MBG_TGT_LINUX )
@@ -168,7 +190,6 @@
#endif
#if !defined( MBG_TGT_KERNEL )
- #include <windows.h>
#include <winioctl.h>
#endif
@@ -230,6 +251,14 @@
// We must use native alignment here!
+/**
+ * @defgroup group_ioctl_codes IOCTL codes used by Meinberg drivers
+ *
+ * @see ::IOCTL_CODES_TABLE
+ *
+ * @anchor IOCTL_CODES
+ *
+ * @{ */
// read general driver info, device info, and status port
#define IOCTL_GET_PCPS_DRVR_INFO _MBG_IOR( IOTYPE, 0x00, PCPS_DRVR_INFO )
@@ -434,6 +463,25 @@
#define IOCTL_GET_FIRST_EVT_LOG_ENTRY _MBG_IOR( IOTYPE, 0x93, MBG_EVT_LOG_ENTRY )
#define IOCTL_GET_NEXT_EVT_LOG_ENTRY _MBG_IOR( IOTYPE, 0x94, MBG_EVT_LOG_ENTRY )
+#define IOCTL_DEV_IS_GNSS _MBG_IOR( IOTYPE, 0x95, int )
+#define IOCTL_GET_GNSS_MODE_INFO _MBG_IOR( IOTYPE, 0x96, MBG_GNSS_MODE_INFO )
+#define IOCTL_SET_GNSS_MODE_SETTINGS _MBG_IOW( IOTYPE, 0x97, MBG_GNSS_MODE_SETTINGS )
+#define IOCTL_GET_ALL_GNSS_SAT_INFO _MBG_IOG( IOTYPE, 0x98, IOCTL_GENERIC_REQ ) // variable size
+
+#define IOCTL_DEV_HAS_GPIO _MBG_IOR( IOTYPE, 0x99, int )
+#define IOCTL_GET_GPIO_CFG_LIMITS _MBG_IOR( IOTYPE, 0x9A, MBG_GPIO_CFG_LIMITS )
+#define IOCTL_GET_ALL_GPIO_INFO _MBG_IOG( IOTYPE, 0x9B, IOCTL_GENERIC_REQ ) // variable size
+#define IOCTL_SET_GPIO_SETTINGS_IDX _MBG_IOW( IOTYPE, 0x9C, MBG_GPIO_SETTINGS_IDX )
+
+#define IOCTL_DEV_HAS_XMR _MBG_IOR( IOTYPE, 0x9D, int )
+#define IOCTL_GET_XMR_INSTANCES _MBG_IOR( IOTYPE, 0x9E, XMULTI_REF_INSTANCES )
+#define IOCTL_GET_ALL_XMR_INFO _MBG_IOG( IOTYPE, 0x9F, IOCTL_GENERIC_REQ ) // variable size
+#define IOCTL_SET_XMR_SETTINGS_IDX _MBG_IOW( IOTYPE, 0xA0, XMULTI_REF_SETTINGS_IDX )
+#define IOCTL_GET_ALL_XMR_STATUS _MBG_IOG( IOTYPE, 0xA1, IOCTL_GENERIC_REQ ) // variable size
+#define IOCTL_GET_XMR_HOLDOVER_STATUS _MBG_IOR( IOTYPE, 0xA2, XMR_HOLDOVER_STATUS )
+
+#define IOCTL_GET_ALL_GPIO_STATUS _MBG_IOG( IOTYPE, 0xA3, IOCTL_GENERIC_REQ ) // variable size
+
// The codes below are subject to changes without notice. They may be supported
// by some kernel drivers, but usage is restricted to Meinberg software development.
@@ -444,162 +492,181 @@
#define IOCTL_MBG_DBG_CLR_BIT _MBG_IOW( IOTYPE, 0xF3, uint8_t )
#define IOCTL_MBG_DBG_CLR_ALL _MBG_IO( IOTYPE, 0xF4 )
+/** @} defgroup group_ioctl_codes */
+
/**
* @brief An initializer for a table of IOCTL codes and associated names.
*
- * This can e.g. be assigned to an array of MBG_CODE_NAME_TABLE_ENTRY elements
+ * This can e.g. initialize an array of ::MBG_CODE_NAME_TABLE_ENTRY elements
* and may be helpful when debugging.
+ *
+ * @see @ref IOCTL_CODES
*/
-#define MBG_IOCTL_CODE_TABLE \
-{ \
- { IOCTL_GET_PCPS_DRVR_INFO, "IOCTL_GET_PCPS_DRVR_INFO" }, \
- { IOCTL_GET_PCPS_DEV, "IOCTL_GET_PCPS_DEV" }, \
- { IOCTL_GET_PCPS_STATUS_PORT, "IOCTL_GET_PCPS_STATUS_PORT" }, \
- { IOCTL_PCPS_GENERIC_READ, "IOCTL_PCPS_GENERIC_READ" }, \
- { IOCTL_PCPS_GENERIC_WRITE, "IOCTL_PCPS_GENERIC_WRITE" }, \
- { IOCTL_PCPS_GENERIC_READ_GPS, "IOCTL_PCPS_GENERIC_READ_GPS" }, \
- { IOCTL_PCPS_GENERIC_WRITE_GPS, "IOCTL_PCPS_GENERIC_WRITE_GPS" }, \
- { IOCTL_GET_PCPS_TIME, "IOCTL_GET_PCPS_TIME" }, \
- { IOCTL_SET_PCPS_TIME, "IOCTL_SET_PCPS_TIME" }, \
- { IOCTL_GET_PCPS_SYNC_TIME, "IOCTL_GET_PCPS_SYNC_TIME" }, \
- { IOCTL_GET_PCPS_TIME_SEC_CHANGE, "IOCTL_GET_PCPS_TIME_SEC_CHANGE" }, \
- { IOCTL_GET_PCPS_HR_TIME, "IOCTL_GET_PCPS_HR_TIME" }, \
- { IOCTL_SET_PCPS_EVENT_TIME, "IOCTL_SET_PCPS_EVENT_TIME" }, \
- { IOCTL_GET_PCPS_SERIAL, "IOCTL_GET_PCPS_SERIAL" }, \
- { IOCTL_SET_PCPS_SERIAL, "IOCTL_SET_PCPS_SERIAL" }, \
- { IOCTL_GET_PCPS_TZCODE, "IOCTL_GET_PCPS_TZCODE" }, \
- { IOCTL_SET_PCPS_TZCODE, "IOCTL_SET_PCPS_TZCODE" }, \
- { IOCTL_GET_PCPS_TZDL, "IOCTL_GET_PCPS_TZDL" }, \
- { IOCTL_SET_PCPS_TZDL, "IOCTL_SET_PCPS_TZDL" }, \
- { IOCTL_GET_REF_OFFS, "IOCTL_GET_REF_OFFS" }, \
- { IOCTL_SET_REF_OFFS, "IOCTL_SET_REF_OFFS" }, \
- { IOCTL_GET_MBG_OPT_INFO, "IOCTL_GET_MBG_OPT_INFO" }, \
- { IOCTL_SET_MBG_OPT_SETTINGS, "IOCTL_SET_MBG_OPT_SETTINGS" }, \
- { IOCTL_GET_PCPS_IRIG_RX_INFO, "IOCTL_GET_PCPS_IRIG_RX_INFO" }, \
- { IOCTL_SET_PCPS_IRIG_RX_SETTINGS, "IOCTL_SET_PCPS_IRIG_RX_SETTINGS" }, \
- { IOCTL_PCPS_CLR_UCAP_BUFF, "IOCTL_PCPS_CLR_UCAP_BUFF" }, \
- { IOCTL_GET_PCPS_UCAP_ENTRIES, "IOCTL_GET_PCPS_UCAP_ENTRIES" }, \
- { IOCTL_GET_PCPS_UCAP_EVENT, "IOCTL_GET_PCPS_UCAP_EVENT" }, \
- { IOCTL_GET_GPS_TZDL, "IOCTL_GET_GPS_TZDL" }, \
- { IOCTL_SET_GPS_TZDL, "IOCTL_SET_GPS_TZDL" }, \
- { IOCTL_GET_GPS_SW_REV, "IOCTL_GET_GPS_SW_REV" }, \
- { IOCTL_GET_GPS_BVAR_STAT, "IOCTL_GET_GPS_BVAR_STAT" }, \
- { IOCTL_GET_GPS_TIME, "IOCTL_GET_GPS_TIME" }, \
- { IOCTL_SET_GPS_TIME, "IOCTL_SET_GPS_TIME" }, \
- { IOCTL_GET_GPS_PORT_PARM, "IOCTL_GET_GPS_PORT_PARM" }, \
- { IOCTL_SET_GPS_PORT_PARM, "IOCTL_SET_GPS_PORT_PARM" }, \
- { IOCTL_GET_GPS_ANT_INFO, "IOCTL_GET_GPS_ANT_INFO" }, \
- { IOCTL_GET_GPS_UCAP, "IOCTL_GET_GPS_UCAP" }, \
- { IOCTL_GET_GPS_ENABLE_FLAGS, "IOCTL_GET_GPS_ENABLE_FLAGS" }, \
- { IOCTL_SET_GPS_ENABLE_FLAGS, "IOCTL_SET_GPS_ENABLE_FLAGS" }, \
- { IOCTL_GET_GPS_STAT_INFO, "IOCTL_GET_GPS_STAT_INFO" }, \
- { IOCTL_SET_GPS_CMD, "IOCTL_SET_GPS_CMD" }, \
- { IOCTL_GET_GPS_IDENT, "IOCTL_GET_GPS_IDENT" }, \
- { IOCTL_GET_GPS_POS, "IOCTL_GET_GPS_POS" }, \
- { IOCTL_SET_GPS_POS_XYZ, "IOCTL_SET_GPS_POS_XYZ" }, \
- { IOCTL_SET_GPS_POS_LLA, "IOCTL_SET_GPS_POS_LLA" }, \
- { IOCTL_GET_GPS_ANT_CABLE_LEN, "IOCTL_GET_GPS_ANT_CABLE_LEN" }, \
- { IOCTL_SET_GPS_ANT_CABLE_LEN, "IOCTL_SET_GPS_ANT_CABLE_LEN" }, \
- { IOCTL_GET_GPS_RECEIVER_INFO, "IOCTL_GET_GPS_RECEIVER_INFO" }, \
- { IOCTL_GET_GPS_ALL_STR_TYPE_INFO, "IOCTL_GET_GPS_ALL_STR_TYPE_INFO" }, \
- { IOCTL_GET_GPS_ALL_PORT_INFO, "IOCTL_GET_GPS_ALL_PORT_INFO" }, \
- { IOCTL_SET_GPS_PORT_SETTINGS_IDX, "IOCTL_SET_GPS_PORT_SETTINGS_IDX" }, \
- { IOCTL_GET_PCI_ASIC_VERSION, "IOCTL_GET_PCI_ASIC_VERSION" }, \
- { IOCTL_GET_PCPS_TIME_CYCLES, "IOCTL_GET_PCPS_TIME_CYCLES" }, \
- { IOCTL_GET_PCPS_HR_TIME_CYCLES, "IOCTL_GET_PCPS_HR_TIME_CYCLES" }, \
- { IOCTL_GET_PCPS_IRIG_TX_INFO, "IOCTL_GET_PCPS_IRIG_TX_INFO" }, \
- { IOCTL_SET_PCPS_IRIG_TX_SETTINGS, "IOCTL_SET_PCPS_IRIG_TX_SETTINGS" }, \
- { IOCTL_GET_SYNTH, "IOCTL_GET_SYNTH" }, \
- { IOCTL_SET_SYNTH, "IOCTL_SET_SYNTH" }, \
- { IOCTL_DEV_IS_GPS, "IOCTL_DEV_IS_GPS" }, \
- { IOCTL_DEV_IS_DCF, "IOCTL_DEV_IS_DCF" }, \
- { IOCTL_DEV_IS_IRIG_RX, "IOCTL_DEV_IS_IRIG_RX" }, \
- { IOCTL_DEV_HAS_HR_TIME, "IOCTL_DEV_HAS_HR_TIME" }, \
- { IOCTL_DEV_HAS_CAB_LEN, "IOCTL_DEV_HAS_CAB_LEN" }, \
- { IOCTL_DEV_HAS_TZDL, "IOCTL_DEV_HAS_TZDL" }, \
- { IOCTL_DEV_HAS_PCPS_TZDL, "IOCTL_DEV_HAS_PCPS_TZDL" }, \
- { IOCTL_DEV_HAS_TZCODE, "IOCTL_DEV_HAS_TZCODE" }, \
- { IOCTL_DEV_HAS_TZ, "IOCTL_DEV_HAS_TZ" }, \
- { IOCTL_DEV_HAS_EVENT_TIME, "IOCTL_DEV_HAS_EVENT_TIME" }, \
- { IOCTL_DEV_HAS_RECEIVER_INFO, "IOCTL_DEV_HAS_RECEIVER_INFO" }, \
- { IOCTL_DEV_CAN_CLR_UCAP_BUFF, "IOCTL_DEV_CAN_CLR_UCAP_BUFF" }, \
- { IOCTL_DEV_HAS_UCAP, "IOCTL_DEV_HAS_UCAP" }, \
- { IOCTL_DEV_HAS_IRIG_TX, "IOCTL_DEV_HAS_IRIG_TX" }, \
- { IOCTL_DEV_HAS_SERIAL_HS, "IOCTL_DEV_HAS_SERIAL_HS" }, \
- { IOCTL_DEV_HAS_SIGNAL, "IOCTL_DEV_HAS_SIGNAL" }, \
- { IOCTL_DEV_HAS_MOD, "IOCTL_DEV_HAS_MOD" }, \
- { IOCTL_DEV_HAS_IRIG, "IOCTL_DEV_HAS_IRIG" }, \
- { IOCTL_DEV_HAS_REF_OFFS, "IOCTL_DEV_HAS_REF_OFFS" }, \
- { IOCTL_DEV_HAS_OPT_FLAGS, "IOCTL_DEV_HAS_OPT_FLAGS" }, \
- { IOCTL_DEV_HAS_GPS_DATA, "IOCTL_DEV_HAS_GPS_DATA" }, \
- { IOCTL_DEV_HAS_SYNTH, "IOCTL_DEV_HAS_SYNTH" }, \
- { IOCTL_DEV_HAS_GENERIC_IO, "IOCTL_DEV_HAS_GENERIC_IO" }, \
- { IOCTL_PCPS_GENERIC_IO, "IOCTL_PCPS_GENERIC_IO" }, \
- { IOCTL_GET_SYNTH_STATE, "IOCTL_GET_SYNTH_STATE" }, \
- { IOCTL_GET_GPS_ALL_POUT_INFO, "IOCTL_GET_GPS_ALL_POUT_INFO" }, \
- { IOCTL_SET_GPS_POUT_SETTINGS_IDX, "IOCTL_SET_GPS_POUT_SETTINGS_IDX" }, \
- { IOCTL_GET_MAPPED_MEM_ADDR, "IOCTL_GET_MAPPED_MEM_ADDR" }, \
- { IOCTL_UNMAP_MAPPED_MEM, "IOCTL_UNMAP_MAPPED_MEM" }, \
- { IOCTL_GET_PCI_ASIC_FEATURES, "IOCTL_GET_PCI_ASIC_FEATURES" }, \
- { IOCTL_DEV_HAS_PCI_ASIC_FEATURES, "IOCTL_DEV_HAS_PCI_ASIC_FEATURES" }, \
- { IOCTL_DEV_HAS_PCI_ASIC_VERSION, "IOCTL_DEV_HAS_PCI_ASIC_VERSION" }, \
- { IOCTL_DEV_IS_MSF, "IOCTL_DEV_IS_MSF" }, \
- { IOCTL_DEV_IS_LWR, "IOCTL_DEV_IS_LWR" }, \
- { IOCTL_DEV_IS_WWVB, "IOCTL_DEV_IS_WWVB" }, \
- { IOCTL_GET_IRQ_STAT_INFO, "IOCTL_GET_IRQ_STAT_INFO" }, \
- { IOCTL_GET_CYCLES_FREQUENCY, "IOCTL_GET_CYCLES_FREQUENCY" }, \
- { IOCTL_DEV_HAS_FAST_HR_TIMESTAMP, "IOCTL_DEV_HAS_FAST_HR_TIMESTAMP" }, \
- { IOCTL_GET_FAST_HR_TIMESTAMP_CYCLES, "IOCTL_GET_FAST_HR_TIMESTAMP_CYCLES" }, \
- { IOCTL_GET_FAST_HR_TIMESTAMP, "IOCTL_GET_FAST_HR_TIMESTAMP" }, \
- { IOCTL_DEV_HAS_GPS_TIME_SCALE, "IOCTL_DEV_HAS_GPS_TIME_SCALE" }, \
- { IOCTL_GET_GPS_TIME_SCALE_INFO, "IOCTL_GET_GPS_TIME_SCALE_INFO" }, \
- { IOCTL_SET_GPS_TIME_SCALE_SETTINGS, "IOCTL_SET_GPS_TIME_SCALE_SETTINGS" }, \
- { IOCTL_DEV_HAS_GPS_UTC_PARM, "IOCTL_DEV_HAS_GPS_UTC_PARM" }, \
- { IOCTL_GET_GPS_UTC_PARM, "IOCTL_GET_GPS_UTC_PARM" }, \
- { IOCTL_SET_GPS_UTC_PARM, "IOCTL_SET_GPS_UTC_PARM" }, \
- { IOCTL_DEV_HAS_IRIG_CTRL_BITS, "IOCTL_DEV_HAS_IRIG_CTRL_BITS" }, \
- { IOCTL_GET_IRIG_CTRL_BITS, "IOCTL_GET_IRIG_CTRL_BITS" }, \
- { IOCTL_DEV_HAS_LAN_INTF, "IOCTL_DEV_HAS_LAN_INTF" }, \
- { IOCTL_GET_LAN_IF_INFO, "IOCTL_GET_LAN_IF_INFO" }, \
- { IOCTL_GET_IP4_STATE, "IOCTL_GET_IP4_STATE" }, \
- { IOCTL_GET_IP4_SETTINGS, "IOCTL_GET_IP4_SETTINGS" }, \
- { IOCTL_SET_IP4_SETTINGS, "IOCTL_SET_IP4_SETTINGS" }, \
- { IOCTL_DEV_IS_PTP, "IOCTL_DEV_IS_PTP" }, \
- { IOCTL_DEV_HAS_PTP, "IOCTL_DEV_HAS_PTP" }, \
- { IOCTL_GET_PTP_STATE, "IOCTL_GET_PTP_STATE" }, \
- { IOCTL_GET_PTP_CFG_INFO, "IOCTL_GET_PTP_CFG_INFO" }, \
- { IOCTL_SET_PTP_CFG_SETTINGS, "IOCTL_SET_PTP_CFG_SETTINGS" }, \
- { IOCTL_DEV_HAS_IRIG_TIME, "IOCTL_DEV_HAS_IRIG_TIME" }, \
- { IOCTL_GET_IRIG_TIME, "IOCTL_GET_IRIG_TIME" }, \
- { IOCTL_GET_TIME_INFO_HRT, "IOCTL_GET_TIME_INFO_HRT" }, \
- { IOCTL_GET_TIME_INFO_TSTAMP, "IOCTL_GET_TIME_INFO_TSTAMP" }, \
- { IOCTL_DEV_HAS_RAW_IRIG_DATA, "IOCTL_DEV_HAS_RAW_IRIG_DATA" }, \
- { IOCTL_GET_RAW_IRIG_DATA, "IOCTL_GET_RAW_IRIG_DATA" }, \
- { IOCTL_DEV_HAS_PTP_UNICAST, "IOCTL_DEV_HAS_PTP_UNICAST" }, \
- { IOCTL_PTP_UC_MASTER_CFG_LIMITS, "IOCTL_PTP_UC_MASTER_CFG_LIMITS" }, \
- { IOCTL_GET_ALL_PTP_UC_MASTER_INFO, "IOCTL_GET_ALL_PTP_UC_MASTER_INFO" }, \
- { IOCTL_SET_PTP_UC_MASTER_SETTINGS_IDX, "IOCTL_SET_PTP_UC_MASTER_SETTINGS_IDX" }, \
- { IOCTL_DEV_HAS_PZF, "IOCTL_DEV_HAS_PZF" }, \
- { IOCTL_DEV_HAS_CORR_INFO, "IOCTL_DEV_HAS_CORR_INFO" }, \
- { IOCTL_DEV_HAS_TR_DISTANCE, "IOCTL_DEV_HAS_TR_DISTANCE" }, \
- { IOCTL_GET_CORR_INFO, "IOCTL_GET_CORR_INFO" }, \
- { IOCTL_GET_TR_DISTANCE, "IOCTL_GET_TR_DISTANCE" }, \
- { IOCTL_SET_TR_DISTANCE, "IOCTL_SET_TR_DISTANCE" }, \
- { IOCTL_DEV_HAS_DEBUG_STATUS, "IOCTL_DEV_HAS_DEBUG_STATUS" }, \
- { IOCTL_GET_DEBUG_STATUS, "IOCTL_GET_DEBUG_STATUS" }, \
- { IOCTL_DEV_HAS_EVT_LOG, "IOCTL_DEV_HAS_EVT_LOG" }, \
- { IOCTL_CLR_EVT_LOG, "IOCTL_CLR_EVT_LOG" }, \
- { IOCTL_GET_NUM_EVT_LOG_ENTRIES, "IOCTL_GET_NUM_EVT_LOG_ENTRIES" }, \
- { IOCTL_GET_FIRST_EVT_LOG_ENTRY, "IOCTL_GET_FIRST_EVT_LOG_ENTRY" }, \
- { IOCTL_GET_NEXT_EVT_LOG_ENTRY, "IOCTL_GET_NEXT_EVT_LOG_ENTRY" }, \
- \
- { IOCTL_MBG_DBG_GET_PORT_ADDR, "IOCTL_MBG_DBG_GET_PORT_ADDR" }, \
- { IOCTL_MBG_DBG_SET_PORT_ADDR, "IOCTL_MBG_DBG_SET_PORT_ADDR" }, \
- { IOCTL_MBG_DBG_SET_BIT, "IOCTL_MBG_DBG_SET_BIT" }, \
- { IOCTL_MBG_DBG_CLR_BIT, "IOCTL_MBG_DBG_CLR_BIT" }, \
- { 0, NULL } \
+#define IOCTL_CODES_TABLE \
+{ \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_DRVR_INFO ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_DEV ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_STATUS_PORT ), \
+ _mbg_cn_table_entry( IOCTL_PCPS_GENERIC_READ ), \
+ _mbg_cn_table_entry( IOCTL_PCPS_GENERIC_WRITE ), \
+ _mbg_cn_table_entry( IOCTL_PCPS_GENERIC_READ_GPS ), \
+ _mbg_cn_table_entry( IOCTL_PCPS_GENERIC_WRITE_GPS ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_TIME ), \
+ _mbg_cn_table_entry( IOCTL_SET_PCPS_TIME ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_SYNC_TIME ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_TIME_SEC_CHANGE ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_HR_TIME ), \
+ _mbg_cn_table_entry( IOCTL_SET_PCPS_EVENT_TIME ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_SERIAL ), \
+ _mbg_cn_table_entry( IOCTL_SET_PCPS_SERIAL ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_TZCODE ), \
+ _mbg_cn_table_entry( IOCTL_SET_PCPS_TZCODE ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_TZDL ), \
+ _mbg_cn_table_entry( IOCTL_SET_PCPS_TZDL ), \
+ _mbg_cn_table_entry( IOCTL_GET_REF_OFFS ), \
+ _mbg_cn_table_entry( IOCTL_SET_REF_OFFS ), \
+ _mbg_cn_table_entry( IOCTL_GET_MBG_OPT_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_MBG_OPT_SETTINGS ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_IRIG_RX_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_PCPS_IRIG_RX_SETTINGS ), \
+ _mbg_cn_table_entry( IOCTL_PCPS_CLR_UCAP_BUFF ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_UCAP_ENTRIES ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_UCAP_EVENT ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_TZDL ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_TZDL ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_SW_REV ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_BVAR_STAT ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_TIME ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_TIME ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_PORT_PARM ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_PORT_PARM ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_ANT_INFO ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_UCAP ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_ENABLE_FLAGS ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_ENABLE_FLAGS ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_STAT_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_CMD ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_IDENT ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_POS ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_POS_XYZ ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_POS_LLA ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_ANT_CABLE_LEN ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_ANT_CABLE_LEN ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_RECEIVER_INFO ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_ALL_STR_TYPE_INFO ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_ALL_PORT_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_PORT_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCI_ASIC_VERSION ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_TIME_CYCLES ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_HR_TIME_CYCLES ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCPS_IRIG_TX_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_PCPS_IRIG_TX_SETTINGS ), \
+ _mbg_cn_table_entry( IOCTL_GET_SYNTH ), \
+ _mbg_cn_table_entry( IOCTL_SET_SYNTH ), \
+ _mbg_cn_table_entry( IOCTL_DEV_IS_GPS ), \
+ _mbg_cn_table_entry( IOCTL_DEV_IS_DCF ), \
+ _mbg_cn_table_entry( IOCTL_DEV_IS_IRIG_RX ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_HR_TIME ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_CAB_LEN ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_TZDL ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_PCPS_TZDL ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_TZCODE ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_TZ ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_EVENT_TIME ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_RECEIVER_INFO ), \
+ _mbg_cn_table_entry( IOCTL_DEV_CAN_CLR_UCAP_BUFF ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_UCAP ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_IRIG_TX ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_SERIAL_HS ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_SIGNAL ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_MOD ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_IRIG ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_REF_OFFS ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_OPT_FLAGS ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_GPS_DATA ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_SYNTH ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_GENERIC_IO ), \
+ _mbg_cn_table_entry( IOCTL_PCPS_GENERIC_IO ), \
+ _mbg_cn_table_entry( IOCTL_GET_SYNTH_STATE ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_ALL_POUT_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_POUT_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( IOCTL_GET_MAPPED_MEM_ADDR ), \
+ _mbg_cn_table_entry( IOCTL_UNMAP_MAPPED_MEM ), \
+ _mbg_cn_table_entry( IOCTL_GET_PCI_ASIC_FEATURES ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_PCI_ASIC_FEATURES ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_PCI_ASIC_VERSION ), \
+ _mbg_cn_table_entry( IOCTL_DEV_IS_MSF ), \
+ _mbg_cn_table_entry( IOCTL_DEV_IS_LWR ), \
+ _mbg_cn_table_entry( IOCTL_DEV_IS_WWVB ), \
+ _mbg_cn_table_entry( IOCTL_GET_IRQ_STAT_INFO ), \
+ _mbg_cn_table_entry( IOCTL_GET_CYCLES_FREQUENCY ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_FAST_HR_TIMESTAMP ), \
+ _mbg_cn_table_entry( IOCTL_GET_FAST_HR_TIMESTAMP_CYCLES ), \
+ _mbg_cn_table_entry( IOCTL_GET_FAST_HR_TIMESTAMP ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_GPS_TIME_SCALE ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_TIME_SCALE_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_TIME_SCALE_SETTINGS ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_GPS_UTC_PARM ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPS_UTC_PARM ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPS_UTC_PARM ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_IRIG_CTRL_BITS ), \
+ _mbg_cn_table_entry( IOCTL_GET_IRIG_CTRL_BITS ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_LAN_INTF ), \
+ _mbg_cn_table_entry( IOCTL_GET_LAN_IF_INFO ), \
+ _mbg_cn_table_entry( IOCTL_GET_IP4_STATE ), \
+ _mbg_cn_table_entry( IOCTL_GET_IP4_SETTINGS ), \
+ _mbg_cn_table_entry( IOCTL_SET_IP4_SETTINGS ), \
+ _mbg_cn_table_entry( IOCTL_DEV_IS_PTP ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_PTP ), \
+ _mbg_cn_table_entry( IOCTL_GET_PTP_STATE ), \
+ _mbg_cn_table_entry( IOCTL_GET_PTP_CFG_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_PTP_CFG_SETTINGS ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_IRIG_TIME ), \
+ _mbg_cn_table_entry( IOCTL_GET_IRIG_TIME ), \
+ _mbg_cn_table_entry( IOCTL_GET_TIME_INFO_HRT ), \
+ _mbg_cn_table_entry( IOCTL_GET_TIME_INFO_TSTAMP ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_RAW_IRIG_DATA ), \
+ _mbg_cn_table_entry( IOCTL_GET_RAW_IRIG_DATA ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_PTP_UNICAST ), \
+ _mbg_cn_table_entry( IOCTL_PTP_UC_MASTER_CFG_LIMITS ), \
+ _mbg_cn_table_entry( IOCTL_GET_ALL_PTP_UC_MASTER_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_PTP_UC_MASTER_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_PZF ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_CORR_INFO ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_TR_DISTANCE ), \
+ _mbg_cn_table_entry( IOCTL_GET_CORR_INFO ), \
+ _mbg_cn_table_entry( IOCTL_GET_TR_DISTANCE ), \
+ _mbg_cn_table_entry( IOCTL_SET_TR_DISTANCE ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_DEBUG_STATUS ), \
+ _mbg_cn_table_entry( IOCTL_GET_DEBUG_STATUS ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_EVT_LOG ), \
+ _mbg_cn_table_entry( IOCTL_CLR_EVT_LOG ), \
+ _mbg_cn_table_entry( IOCTL_GET_NUM_EVT_LOG_ENTRIES ), \
+ _mbg_cn_table_entry( IOCTL_GET_FIRST_EVT_LOG_ENTRY ), \
+ _mbg_cn_table_entry( IOCTL_GET_NEXT_EVT_LOG_ENTRY ), \
+ _mbg_cn_table_entry( IOCTL_DEV_IS_GNSS ), \
+ _mbg_cn_table_entry( IOCTL_GET_GNSS_MODE_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_GNSS_MODE_SETTINGS ), \
+ _mbg_cn_table_entry( IOCTL_GET_ALL_GNSS_SAT_INFO ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_GPIO ), \
+ _mbg_cn_table_entry( IOCTL_GET_GPIO_CFG_LIMITS ), \
+ _mbg_cn_table_entry( IOCTL_GET_ALL_GPIO_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_GPIO_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( IOCTL_DEV_HAS_XMR ), \
+ _mbg_cn_table_entry( IOCTL_GET_XMR_INSTANCES ), \
+ _mbg_cn_table_entry( IOCTL_GET_ALL_XMR_INFO ), \
+ _mbg_cn_table_entry( IOCTL_SET_XMR_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( IOCTL_GET_ALL_XMR_STATUS ), \
+ _mbg_cn_table_entry( IOCTL_GET_XMR_HOLDOVER_STATUS ), \
+ _mbg_cn_table_entry( IOCTL_GET_ALL_GPIO_STATUS ), \
+ \
+ _mbg_cn_table_entry( IOCTL_MBG_DBG_GET_PORT_ADDR ), \
+ _mbg_cn_table_entry( IOCTL_MBG_DBG_SET_PORT_ADDR ), \
+ _mbg_cn_table_entry( IOCTL_MBG_DBG_SET_BIT ), \
+ _mbg_cn_table_entry( IOCTL_MBG_DBG_CLR_BIT ), \
+ _mbg_cn_table_end() \
}
@@ -703,6 +770,9 @@ int ioctl_get_required_privilege( ulong ioctl_code )
case IOCTL_GET_NUM_EVT_LOG_ENTRIES:
case IOCTL_GET_FIRST_EVT_LOG_ENTRY:
case IOCTL_GET_NEXT_EVT_LOG_ENTRY:
+ #if _MBG_SUPP_VAR_ACC_SIZE
+ case IOCTL_GET_ALL_GNSS_SAT_INFO:
+ #endif
return MBG_REQ_PRIVL_NONE;
// Commands returning device capabilities and features:
@@ -711,6 +781,7 @@ int ioctl_get_required_privilege( ulong ioctl_code )
case IOCTL_DEV_IS_MSF:
case IOCTL_DEV_IS_WWVB:
case IOCTL_DEV_IS_LWR:
+ case IOCTL_DEV_IS_GNSS:
case IOCTL_DEV_IS_IRIG_RX:
case IOCTL_DEV_HAS_HR_TIME:
case IOCTL_DEV_HAS_CAB_LEN:
@@ -749,6 +820,8 @@ int ioctl_get_required_privilege( ulong ioctl_code )
case IOCTL_DEV_HAS_TR_DISTANCE:
case IOCTL_DEV_HAS_DEBUG_STATUS:
case IOCTL_DEV_HAS_EVT_LOG:
+ case IOCTL_DEV_HAS_GPIO:
+ case IOCTL_DEV_HAS_XMR:
return MBG_REQ_PRIVL_NONE;
// The next codes are somewhat special since they change something
@@ -795,7 +868,15 @@ int ioctl_get_required_privilege( ulong ioctl_code )
case IOCTL_GET_GPS_ALL_PORT_INFO:
case IOCTL_GET_GPS_ALL_POUT_INFO:
case IOCTL_GET_ALL_PTP_UC_MASTER_INFO:
+ case IOCTL_GET_ALL_GPIO_INFO:
+ case IOCTL_GET_ALL_GPIO_STATUS:
+ case IOCTL_GET_ALL_XMR_STATUS:
+ case IOCTL_GET_ALL_XMR_INFO:
#endif
+ case IOCTL_GET_GNSS_MODE_INFO:
+ case IOCTL_GET_GPIO_CFG_LIMITS:
+ case IOCTL_GET_XMR_INSTANCES:
+ case IOCTL_GET_XMR_HOLDOVER_STATUS:
return MBG_REQ_PRIVL_CFG_READ;
// Writing device configuration:
@@ -817,6 +898,8 @@ int ioctl_get_required_privilege( ulong ioctl_code )
case IOCTL_SET_PTP_CFG_SETTINGS:
case IOCTL_SET_PTP_UC_MASTER_SETTINGS_IDX:
case IOCTL_SET_TR_DISTANCE:
+ case IOCTL_SET_GNSS_MODE_SETTINGS:
+ case IOCTL_SET_GPIO_SETTINGS_IDX:
return MBG_REQ_PRIVL_CFG_WRITE;
// Operations which may severely affect system operation:
@@ -827,6 +910,7 @@ int ioctl_get_required_privilege( ulong ioctl_code )
case IOCTL_SET_GPS_TIME_SCALE_SETTINGS:
case IOCTL_SET_GPS_UTC_PARM:
case IOCTL_SET_GPS_CMD:
+ case IOCTL_SET_XMR_SETTINGS_IDX:
// generic write operations can do anything
case IOCTL_PCPS_GENERIC_WRITE:
case IOCTL_PCPS_GENERIC_WRITE_GPS:
diff --git a/mbglib/common/mbgklist.h b/mbglib/common/mbgklist.h
new file mode 100755
index 0000000..19f22a3
--- /dev/null
+++ b/mbglib/common/mbgklist.h
@@ -0,0 +1,304 @@
+
+/**************************************************************************
+ *
+ * $Id: mbgklist.h 1.2.1.4 2017/01/12 15:09:45 philipp TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Userspace implementation of Linux Kernel's list.h
+ *
+ * -----------------------------------------------------------------------
+ * $Log: mbgklist.h $
+ * Revision 1.2.1.4 2017/01/12 15:09:45 philipp
+ * Added more safe loop macros
+ * Revision 1.2.1.3 2017/01/12 12:21:22 philipp
+ * Added safe loop macros
+ * Revision 1.2.1.2 2016/08/11 14:13:22 martin
+ * Revision 1.2.1.1 2016/08/10 14:32:13Z martin
+ * *** empty log message ***
+ * Revision 1.2 2015/10/06 07:08:45 philipp
+ * Added functions to loop containers of list entries
+ * Revision 1.1 2015/09/09 10:42:27 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#ifndef _MBGKLIST_H
+#define _MBGKLIST_H
+
+/* Other headers to be included */
+
+#include <mbg_cof.h>
+
+
+#ifdef _MBGKLIST
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+#define MBG_KLIST_INIT(name) { &(name), &(name) }
+
+#define MBG_KLIST_DECLARE(name) \
+ struct mbg_klist_head name = MBG_KLIST_INIT(name)
+
+#define mbg_klist_for_each(head, pos) \
+ for (pos = (head)->next; pos != (head); pos = pos->next)
+
+#define mbg_klist_for_each_safe(head, pos, n) \
+ for (pos = (head)->next, n = (pos)->next; \
+ pos != (head); \
+ pos = n, n = pos->next)
+
+#define mbg_klist_for_each_rev(head, pos) \
+ for (pos = (head)->prev; pos != (head); pos = pos->prev)
+
+#define mbg_klist_for_each_rev_safe(head, pos, n) \
+ for (pos = (head)->prev, n = (pos)->prev; \
+ pos != (head); \
+ pos = n, n = pos->prev)
+
+#define mbg_klist_entry(ptr, type, member) \
+ mbg_container_of(ptr, type, member)
+
+#define mbg_klist_first_entry(ptr, type, member) \
+ mbg_klist_entry((ptr)->next, type, member)
+
+#define mbg_klist_last_entry(ptr, type, member) \
+ mbg_klist_entry((ptr)->prev, type, member)
+
+
+
+#if defined( __GNUC__ ) || defined( __clang__ ) // "typeof" supported
+
+#define mbg_klist_next_entry(pos, member) \
+ mbg_klist_entry((pos)->member.next, typeof(*pos), member)
+
+#define mbg_klist_prev_entry(pos, member) \
+ mbg_klist_entry((pos)->member.prev, typeof(*pos), member)
+
+#define mbg_klist_for_each_entry(head, pos, member) \
+ for (pos = mbg_klist_first_entry(head, typeof(*pos), member); \
+ &pos->member != (head); \
+ pos = mbg_klist_next_entry(pos, member))
+
+#define mbg_klist_for_each_entry_rev(head, pos, member) \
+ for (pos = mbg_klist_last_entry(head, typeof(*pos), member); \
+ &pos->member != (head); \
+ pos = mbg_klist_prev_entry(pos, member))
+
+#define mbg_klist_for_each_entry_safe(head, pos, n, member) \
+ for (pos = mbg_klist_first_entry(head, typeof(*pos), member), \
+ n = mbg_klist_next_entry(pos, member); \
+ &pos->member != (head); \
+ pos = n, n = mbg_klist_next_entry(pos, member))
+
+#define mbg_klist_for_each_entry_rev_safe(head, pos, n, member) \
+ for (pos = mbg_klist_last_entry(head, typeof(*pos), member), \
+ n = mbg_klist_prev_entry(pos, member); \
+ &pos->member != (head); \
+ pos = n, n = mbg_klist_prev_entry(pos, member))
+
+#endif
+
+
+
+struct mbg_klist_head
+{
+ struct mbg_klist_head *prev;
+ struct mbg_klist_head *next;
+};
+
+
+
+/* function prototypes: */
+
+static __mbg_inline
+void mbg_klist_init( struct mbg_klist_head *head )
+{
+ head->next = head;
+ head->prev = head;
+}
+
+
+static __mbg_inline
+void __mbg_klist_add_item( struct mbg_klist_head *item, struct mbg_klist_head *prev, struct mbg_klist_head *next )
+{
+ next->prev = item;
+ item->next = next;
+ item->prev = prev;
+ prev->next = item;
+}
+
+
+static __mbg_inline
+void mbg_klist_prepend_item( struct mbg_klist_head *head, struct mbg_klist_head *item )
+{
+ __mbg_klist_add_item( item, head, head->next );
+}
+
+
+static __mbg_inline
+void mbg_klist_append_item( struct mbg_klist_head *head, struct mbg_klist_head *item )
+{
+ __mbg_klist_add_item( item, head->prev, head );
+}
+
+
+static __mbg_inline
+void __mbg_klist_delete_item( struct mbg_klist_head *prev, struct mbg_klist_head *next )
+{
+ next->prev = prev;
+ prev->next = next;
+}
+
+
+static __mbg_inline
+void mbg_klist_delete_item( struct mbg_klist_head *item )
+{
+ __mbg_klist_delete_item( item->prev, item->next );
+}
+
+
+static __mbg_inline
+void mbg_klist_delete_item_init( struct mbg_klist_head *item )
+{
+ __mbg_klist_delete_item( item->prev, item->next );
+ mbg_klist_init( item );
+}
+
+
+static __mbg_inline
+void mbg_klist_replace_item( struct mbg_klist_head *old, struct mbg_klist_head *item )
+{
+ item->next = old->next;
+ item->next->prev = item;
+ item->prev = old->prev;
+ item->prev->next = item;
+}
+
+
+static __mbg_inline
+void mbg_klist_replace_item_init( struct mbg_klist_head *old, struct mbg_klist_head *item )
+{
+ mbg_klist_replace_item( old, item );
+ mbg_klist_init( item );
+}
+
+
+static __mbg_inline
+void mbg_klist_move_prepend_item( struct mbg_klist_head *head, struct mbg_klist_head *item )
+{
+ mbg_klist_delete_item( item );
+ mbg_klist_prepend_item( head, item );
+}
+
+
+static __mbg_inline
+void mbg_klist_move_append_item( struct mbg_klist_head *head, struct mbg_klist_head *item )
+{
+ mbg_klist_delete_item( item );
+ mbg_klist_append_item( head, item );
+}
+
+
+static __mbg_inline
+int mbg_klist_is_first( const struct mbg_klist_head *head, const struct mbg_klist_head *item )
+{
+ return ( ( item->prev == head ) ? 1 : 0 );
+}
+
+
+static __mbg_inline
+int mbg_klist_is_last( const struct mbg_klist_head *head, const struct mbg_klist_head *item )
+{
+ return ( ( item->next == head ) ? 1 : 0 );
+}
+
+
+static __mbg_inline
+int mbg_klist_is_empty( const struct mbg_klist_head *head )
+{
+ return ( ( head->next == head ) ? 1 : 0 );
+}
+
+
+static __mbg_inline
+void __mbg_klist_add_list( const struct mbg_klist_head *list, struct mbg_klist_head *prev, struct mbg_klist_head *next )
+{
+ struct mbg_klist_head *first = list->next;
+ struct mbg_klist_head *last = list->prev;
+
+ first->prev = prev;
+ prev->next = first;
+
+ last->next = next;
+ next->prev = last;
+}
+
+
+static __mbg_inline
+void mbg_klist_prepend_list( struct mbg_klist_head *head, const struct mbg_klist_head *list )
+{
+ if ( !mbg_klist_is_empty( list ) )
+ __mbg_klist_add_list( list, head, head->next );
+}
+
+
+static __mbg_inline
+void mbg_klist_append_list( struct mbg_klist_head *head, const struct mbg_klist_head *list )
+{
+ if ( !mbg_klist_is_empty( list ) )
+ __mbg_klist_add_list( list, head->prev, head );
+}
+
+
+static __mbg_inline
+void mbg_klist_prepend_list_init( struct mbg_klist_head *head, struct mbg_klist_head *list )
+{
+ if ( !mbg_klist_is_empty( list ) )
+ {
+ __mbg_klist_add_list( list, head, head->next );
+ mbg_klist_init( list );
+ }
+}
+
+
+static __mbg_inline
+void mbg_klist_append_list_init( struct mbg_klist_head *head, struct mbg_klist_head *list )
+{
+ if ( !mbg_klist_is_empty( list ) )
+ {
+ __mbg_klist_add_list( list, head->prev, head );
+ mbg_klist_init( list );
+ }
+}
+
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+/* End of header body */
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _MBGKLIST_H */
diff --git a/mbglib/common/mbgmktm.c b/mbglib/common/mbgmktm.c
index 3285b73..b8ada79 100755
--- a/mbglib/common/mbgmktm.c
+++ b/mbglib/common/mbgmktm.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgmktm.c 1.1 2006/08/22 08:57:15 martin REL_M $
+ * $Id: mbgmktm.c 1.1.1.3 2014/10/20 14:35:38 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,10 @@
*
* -----------------------------------------------------------------------
* $Log: mbgmktm.c $
+ * Revision 1.1.1.3 2014/10/20 14:35:38 martin
+ * Allow 0 as valid return value for mbg_mktime().
+ * Revision 1.1.1.2 2014/10/14 13:52:28Z martin
+ * Revision 1.1.1.1 2014/10/14 08:59:02 martin
* Revision 1.1 2006/08/22 08:57:15 martin
* Former function totalsec() moved here from pcpsmktm.c.
*
@@ -19,7 +23,7 @@
#include <mbgmktm.h>
#undef _MBGMKTM
-#include <sys/types.h>
+#include <assert.h>
static const char Days[12] =
@@ -33,41 +37,56 @@ static int YDays[12] =
};
-/*--------------------------------------------------------------
- * Name: mbg_mktime()
- *
- * Purpose: This function works like the standard mktime()
- * function but does not account for a timezone
- * setting configured for the standard C library.
- * Also, it does not take a structure but a set
- * of variables which makes it more versatile.
- * The accepted variables are in the same ranges
- * as the struct tm members used by mktime().
+
+/*HDR*/
+/**
+ * @brief Compute a linear time_t value from broken down date and time
*
- * Input: int year year - 1900
- * int month months since January, 0..11
- * int day days after 1st, 0..30
- * int hour 0..23
- * int min 0..59
- * int sec 0..59, 60 if leap second
+ * This function works like the standard mktime() function but does not
+ * account for a timezone setting configured for the standard C library.
+ * Also, it does not take a structure but a set of variables which makes
+ * it more versatile. The accepted variables are in the same ranges
+ * as the struct tm members used by mktime().
*
- * Output: --
+ * @param[in] year year number - 1900
+ * @param[in] month months since January, 0..11
+ * @param[in] day days after 1st, 0..30
+ * @param[in] hour 0..23
+ * @param[in] min 0..59
+ * @param[in] sec 0..59, 60 if leap second
*
- * Ret value: seconds since 1970 (Unix time_t format)
- * or -1 if range overflow
- *-------------------------------------------------------------*/
-
-/*HDR*/
-long mbg_mktime( int year, int month, int day,
- int hour, int min, int sec )
+ * @return seconds since 1970-01-01 (Unix time_t format) or ((time_t) -1) if range overflow
+ */
+time_t mbg_mktime( int year, int month, int day,
+ int hour, int min, int sec )
{
int leaps;
long days;
- long secs;
+ time_t secs;
+ // time_t should be at least 4 bytes
+ assert( sizeof( time_t ) >= 4 );
- if ( year < 70 || year > 138 )
- return ( -1 );
+ if ( sizeof( time_t ) == 4 )
+ {
+ // 32 bit *signed* time_t will roll over after 2038-01-19 03:14:07
+ // when the number of seconds reaches 0x7FFFFFFF, so we don't try
+ // conversions for 2038 or later, though 32 bit *unsigned* time_t
+ // may still work after year 2100.
+ if ( year < 70 || year > 137 )
+ goto fail;
+ }
+ else
+ if ( sizeof( time_t ) == 8 )
+ {
+ // 64 bit time_t will work for million years. However, it's not
+ // clear what happes for dates before 1970-01-01T00:00:00 if time_t
+ // is *unsigned*.
+ if ( year < 70 )
+ goto fail;
+ }
+ else
+ goto fail;
min += sec / 60;
sec %= 60; /* Seconds are normalized */
@@ -111,7 +130,14 @@ long mbg_mktime( int year, int month, int day,
secs = days * 86400L + hour * 3600L + min * 60L + sec;
- return( secs > 0 ? secs : -1 );
+ if ( secs < 0 ) // == 0 is valid for 1970-01-01 00:00:00
+ goto fail;
+
+ return secs;
+
+
+fail:
+ return (time_t) -1;
} // mbg_mktime
diff --git a/mbglib/common/mbgmktm.h b/mbglib/common/mbgmktm.h
index 2aada2a..ab0d40e 100755
--- a/mbglib/common/mbgmktm.h
+++ b/mbglib/common/mbgmktm.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgmktm.h 1.1 2006/08/22 08:57:15 martin REL_M $
+ * $Id: mbgmktm.h 1.1.1.1 2014/10/14 13:53:50 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,8 @@
*
* -----------------------------------------------------------------------
* $Log: mbgmktm.h $
+ * Revision 1.1.1.1 2014/10/14 13:53:50 martin
+ * Updated function prototypes.
* Revision 1.1 2006/08/22 08:57:15 martin
* Former function totalsec() moved here from pcpsmktm.c.
*
@@ -21,6 +23,9 @@
/* Other headers to be included */
+#include <time.h>
+
+
#ifdef _MBGMKTM
#define _ext
#else
@@ -42,7 +47,26 @@ extern "C" {
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
-long mbg_mktime( int year, int month, int day, int hour, int min, int sec ) ;
+ /**
+ * @brief Compute a linear time_t value from broken down date and time
+ *
+ * This function works like the standard mktime() function but does not
+ * account for a timezone setting configured for the standard C library.
+ * Also, it does not take a structure but a set of variables which makes
+ * it more versatile. The accepted variables are in the same ranges
+ * as the struct tm members used by mktime().
+ *
+ * @param[in] year year number - 1900
+ * @param[in] month months since January, 0..11
+ * @param[in] day days after 1st, 0..30
+ * @param[in] hour 0..23
+ * @param[in] min 0..59
+ * @param[in] sec 0..59, 60 if leap second
+ *
+ * @return seconds since 1970-01-01 (Unix time_t format) or ((time_t) -1) if range overflow
+ */
+ time_t mbg_mktime( int year, int month, int day, int hour, int min, int sec ) ;
+
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/mbgmutex.h b/mbglib/common/mbgmutex.h
index 0948c9c..b8e1ae8 100755
--- a/mbglib/common/mbgmutex.h
+++ b/mbglib/common/mbgmutex.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgmutex.h 1.3 2013/04/11 13:46:58 martin REL_M $
+ * $Id: mbgmutex.h 1.3.1.2 2014/03/04 12:08:12 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -11,6 +11,9 @@
*
* -----------------------------------------------------------------------
* $Log: mbgmutex.h $
+ * Revision 1.3.1.2 2014/03/04 12:08:12 martin
+ * Revision 1.3.1.1 2014/01/08 17:20:57Z martin
+ * MBG_TGT_POSIX
* Revision 1.3 2013/04/11 13:46:58 martin
* Use non-specific spinlock function under Windows.
* Revision 1.2 2012/03/08 12:19:01Z martin
@@ -143,8 +146,6 @@
#if defined( MBG_TGT_WIN32 ) // Windows user space
- #include <windows.h>
-
// definitions used with mutexes
typedef HANDLE MBG_MUTEX;
#define _mbg_mutex_init( _pm ) *(_pm) = CreateMutex( NULL, FALSE, NULL )
@@ -163,7 +164,7 @@
#define _MBG_CRIT_SECT_DEFINED 1
- #elif defined( MBG_TGT_UNIX ) // Unix user space use pthread library
+ #elif defined( MBG_TGT_POSIX ) // Unix user space use pthread library
#include <pthread.h>
diff --git a/mbglib/common/mbgpccyc.h b/mbglib/common/mbgpccyc.h
index d94645c..584348a 100755
--- a/mbglib/common/mbgpccyc.h
+++ b/mbglib/common/mbgpccyc.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgpccyc.h 1.2 2012/03/12 13:45:57 martin REL_M $
+ * $Id: mbgpccyc.h 1.6 2016/08/09 16:01:10 martin REL_M $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,14 @@
*
* -----------------------------------------------------------------------
* $Log: mbgpccyc.h $
+ * Revision 1.6 2016/08/09 16:01:10 martin
+ * Syntax fix.
+ * Revision 1.5 2016/02/17 16:04:18 martin
+ * Include header file missing for FreeBSD.
+ * Revision 1.4 2015/10/19 09:16:45 martin
+ * Fixed some spelling.
+ * Revision 1.3 2014/10/08 13:10:14 martin
+ * Check for MBG_TGT_POSIX instead of MBG_TGT_UNIX.
* Revision 1.2 2012/03/12 13:45:57 martin
* Added cycles support for Linux/IA64, FreeBSD and NetBSD
* in kernel space.
@@ -39,6 +47,7 @@
#if defined( MBG_TGT_FREEBSD )
#if defined( MBG_TGT_KERNEL )
#if defined( MBG_ARCH_X86 )
+ #include <sys/time.h>
#include <machine/clock.h> /* for symbol 'tsc_freq' */
#endif
#endif
@@ -67,7 +76,7 @@
* The cycle counter value is usually derived from the PC CPU's TSC or some other
* timer hardware on the mainboard.
*/
-#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_UNIX )
+#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_POSIX )
typedef int64_t MBG_PC_CYCLES;
typedef uint64_t MBG_PC_CYCLES_FREQUENCY;
@@ -104,7 +113,7 @@
// which would copy the output regs edx:eax as a 64 bit
// number to a variable x.
//
- // The "=A" expression should implicitely tell the compiler
+ // The "=A" expression should implicitly tell the compiler
// the edx and eax registers have been clobbered. However,
// this does not seem to work properly at least with gcc 4.1.2
// shipped with Centos 5.
@@ -116,14 +125,14 @@
// assumes edx is unchanged, which may yield faulty results
// or even lead to segmentation faults.
//
- // A possible workaround could be to mark edx explicitely as
+ // A possible workaround could be to mark edx explicitly as
// being clobbered in the asm inline code, but unfortunately
// other gcc versions report an error if a register which is
- // implicitely (by "=A") known to be clobbered is also listed
- // explicitely to be clobbered.
+ // implicitly (by "=A") known to be clobbered is also listed
+ // explicitly to be clobbered.
//
// So the code below is a workaround which tells the compiler
- // implicitely that the eax ("=a") and edx ("=d") registers
+ // implicitly that the eax ("=a") and edx ("=d") registers
// are being used and thus clobbered.
union
@@ -195,7 +204,7 @@ void mbg_get_pc_cycles( MBG_PC_CYCLES *p )
#define MBG_PC_CYCLES_SUPPORTED 1
- #elif defined( MBG_TGT_NETBSD ) && defined ( MBG_TGT_KERNEL )
+ #elif defined( MBG_TGT_NETBSD ) && defined( MBG_TGT_KERNEL )
*p = cpu_counter(); //##++ or cpu_counter_serializing()
diff --git a/mbglib/common/mbgsystm.c b/mbglib/common/mbgsystm.c
new file mode 100755
index 0000000..4095faf
--- /dev/null
+++ b/mbglib/common/mbgsystm.c
@@ -0,0 +1,60 @@
+
+/**************************************************************************
+ *
+ * $Id: mbgsystm.c 1.1.1.2 2016/08/10 12:27:11 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Generic functions to deal with the computer's system time
+ *
+ * -----------------------------------------------------------------------
+ * $Log: mbgsystm.c $
+ * Revision 1.1.1.2 2016/08/10 12:27:11 martin
+ * *** empty log message ***
+ * Revision 1.1.1.1 2016/08/09 16:04:21 martin
+ * Made mbg_delta_sys_time_ms() an inline function.
+ * Revision 1.1 2015/09/15 13:21:00 martin
+ * Initial revision.
+ * Moved existing code from different modules here.
+ *
+ **************************************************************************/
+
+#define _MBGSYSTM
+ #include <mbgsystm.h>
+#undef _MBGSYSTM
+
+
+#if 0
+
+ /*HDR*/
+/**
+ * @brief Compute delta between two ::MBG_SYS_TIME times, in milliseconds
+ *
+ * @param[in] t2 the time to be subtracted from
+ * @param[in] t1 The time to be subtracted
+ *
+ * @return The time difference in [milliseconds]
+ */
+long mbg_delta_sys_time_ms( const MBG_SYS_TIME *t2, const MBG_SYS_TIME *t1 )
+{
+ #if defined( MBG_TGT_POSIX )
+ long dt = ( t2->secs - t1->secs ) * 1000;
+ #if defined ( MBG_TGT_LINUX ) && defined( MBG_TGT_KERNEL )
+ int64_t tmp64 = t2->nano_secs - t1->nano_secs;
+ do_div( tmp64, 1000000 );
+ dt += tmp64;
+ #else
+ dt += ( t2->nano_secs - t1->nano_secs ) / 1000000;
+ #endif
+ return dt;
+ #elif defined( MBG_TGT_WIN32 )
+ return (long) ( ( t2->QuadPart - t1->QuadPart ) / HNS_PER_MS );
+ #else
+ return 0;
+ #endif
+
+} // mbg_delta_sys_time_ms
+
+#endif
+
diff --git a/mbglib/common/mbgsystm.h b/mbglib/common/mbgsystm.h
new file mode 100755
index 0000000..5b2ff67
--- /dev/null
+++ b/mbglib/common/mbgsystm.h
@@ -0,0 +1,509 @@
+
+/**************************************************************************
+ *
+ * $Id: mbgsystm.h 1.1.1.9.1.5 2017/02/17 11:49:19 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Generic functions and definitions to deal with the computer's
+ * system time, and prototypes for mbgsystm.c.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: mbgsystm.h $
+ * Revision 1.1.1.9.1.5 2017/02/17 11:49:19 martin
+ * Fixed control of inclusion of headers.
+ * Revision 1.1.1.9.1.4 2017/02/09 14:42:51 martin
+ * *** empty log message ***
+ * Revision 1.1.1.9.1.3 2017/02/09 11:03:29 martin
+ * Include ktime.h only for newer kernels.
+ * Revision 1.1.1.9.1.2 2016/09/08 09:54:04 martin
+ * Include mbg_win32.h for Windows kernel mode only.
+ * Revision 1.1.1.9.1.1 2016/08/22 15:05:11 martin
+ * Don't use mbg_win32.h?
+ * Revision 1.1.1.9 2016/08/10 12:28:36Z martin
+ * Updated function prototypes.
+ * Revision 1.1.1.8 2016/08/10 07:11:15 martin
+ * *** empty log message ***
+ * Revision 1.1.1.7 2016/08/09 16:04:48 martin
+ * Made mbg_delta_sys_time_ms() an inline function.
+ * Cleanup.
+ * Revision 1.1.1.6 2015/11/04 09:33:40 martin
+ * Revision 1.1.1.5 2015/10/22 14:29:04Z martin
+ * *** empty log message ***
+ * Revision 1.1.1.4 2015/09/18 14:53:46 martin
+ * Fixes for FreeBSD.
+ * Revision 1.1.1.3 2015/09/18 13:59:29 martin
+ * *** empty log message ***
+ * Revision 1.1.1.2 2015/09/15 16:12:15 martin
+ * Revision 1.1.1.1 2015/09/15 13:52:32Z martin
+ * Fixed build error under DOS.
+ * Revision 1.1 2015/09/15 13:21:00Z martin
+ * Initial revision.
+ * Moved existing code from different modules here.
+ *
+ **************************************************************************/
+
+#ifndef _MBGSYSTM_H
+#define _MBGSYSTM_H
+
+
+/* Other headers to be included */
+
+#include <mbg_tgt.h>
+#include <words.h>
+
+#if defined( MBG_TGT_POSIX )
+
+ #if defined( MBG_TGT_KERNEL )
+
+ #if defined( MBG_TGT_LINUX )
+
+ #define LINUX_KERNEL_HAS_MSLEEP ( LINUX_VERSION_CODE >= KERNEL_VERSION( 2, 6, 16 ) )
+ #define LINUX_KERNEL_HAS_GETNSTIMEOFDAY ( LINUX_VERSION_CODE >= KERNEL_VERSION( 2, 6, 22 ) )
+ #define LINUX_KERNEL_HAS_KTIME_H ( LINUX_VERSION_CODE >= KERNEL_VERSION( 2, 6, 16 ) )
+
+ #if !LINUX_KERNEL_HAS_MSLEEP
+ #include <linux/wait.h>
+ #include <linux/sched.h>
+ #endif
+
+ // We need the prototype for getnstimeofday(). In newer kernels
+ // (e.g. 4.x) this is available via linux/ktime.h, which in turn
+ // includes linux/timekeeping.h, which declares the prototype.
+ #if LINUX_KERNEL_HAS_KTIME_H
+ #include <linux/ktime.h>
+ #endif
+
+ // In older kernel versions the prototype for getnstimeofday()
+ // is declared in linux/time.h, so we include that one anyway.
+ #include <linux/time.h>
+
+ #include <linux/delay.h>
+ #include <linux/jiffies.h>
+
+ #elif defined( MBG_TGT_BSD )
+
+ #include <sys/libkern.h>
+ #include <sys/time.h>
+
+ #endif
+
+ #else // POSIX user space
+
+ #include <time.h>
+
+ #if defined( MBG_TGT_LINUX )
+ #include <sys/sysinfo.h>
+ #endif
+
+ #endif
+
+#elif defined( MBG_TGT_WIN32 )
+
+ #if defined( MBG_TGT_KERNEL )
+ #include <mbg_w32.h>
+ #endif
+
+ #include <mbgtime.h>
+
+#elif defined( MBG_TGT_DOS )
+
+ #include <dos.h>
+
+#endif
+
+
+#ifdef _MBGSYSTM
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ Define generic types to hold PC cycle counter values and system timestamps.
+ The generic types are defined using native types used by the target operating
+ systems.
+
+ The cycle counter value is usually derived from the PC CPU's TSC or some other
+ timer hardware on the mainboard.
+ */
+#if defined( MBG_TGT_POSIX )
+
+ typedef NANO_TIME_64 MBG_SYS_TIME;
+ typedef int64_t MBG_SYS_UPTIME; // [s]
+
+#elif defined( MBG_TGT_WIN32 )
+
+ typedef LARGE_INTEGER MBG_SYS_TIME;
+ typedef int64_t MBG_SYS_UPTIME; // [s]
+
+#elif defined( MBG_TGT_OS2 )
+
+ typedef uint32_t MBG_SYS_TIME; //## dummy
+ typedef long MBG_SYS_UPTIME; //## dummy
+
+#elif defined( MBG_TGT_DOS )
+
+ typedef uint32_t MBG_SYS_TIME; //## dummy
+ typedef long MBG_SYS_UPTIME; //## dummy
+
+#else // other target OSs which access the hardware directly
+
+ typedef uint32_t MBG_SYS_TIME; //## dummy
+ typedef long MBG_SYS_UPTIME; //## dummy
+
+#endif
+
+//### TODO
+// MBG_SYS_TIME is always read in native machine endianess,
+// so no need to convert endianess.
+#define _mbg_swab_mbg_sys_time( _p ) \
+ _nop_macro_fnc()
+
+
+
+static __mbg_inline
+void mbg_get_sys_time( MBG_SYS_TIME *p )
+{
+ #if defined( MBG_TGT_POSIX )
+
+ #if defined( MBG_TGT_KERNEL ) // kernel space functions even differ for POSIX systems
+
+ #if defined( MBG_TGT_LINUX ) // Linux kernel space
+
+ #if ( LINUX_KERNEL_HAS_GETNSTIMEOFDAY )
+ {
+ // getnstimeofday() supported
+ struct timespec ts;
+
+ getnstimeofday( &ts );
+
+ p->secs = ts.tv_sec;
+ p->nano_secs = ts.tv_nsec;
+ }
+ #else
+ {
+ // getnstimeofday() *not* supported
+ struct timeval tv;
+
+ do_gettimeofday( &tv );
+
+ p->secs = tv.tv_sec;
+ p->nano_secs = tv.tv_usec * 1000;
+ }
+ #endif
+
+ #elif defined( MBG_TGT_BSD ) // BSD kernel space
+ {
+ struct timespec ts;
+
+ nanotime( &ts );
+
+ p->secs = ts.tv_sec;
+ p->nano_secs = ts.tv_nsec;
+ }
+ #endif
+
+ #else // POSIX user space
+ {
+ struct timespec ts;
+
+ #if defined( CLOCK_REALTIME_PRECISE ) // at least available in FreeBSD
+ clock_gettime( CLOCK_REALTIME_PRECISE, &ts );
+ #else
+ clock_gettime( CLOCK_REALTIME, &ts );
+ #endif
+
+ p->secs = ts.tv_sec;
+ p->nano_secs = ts.tv_nsec;
+ }
+ #endif
+
+ #elif defined( MBG_TGT_WIN32 )
+
+ #if defined( MBG_TGT_KERNEL ) // Windows kernel space
+ #if defined( MBG_TGT_WIN32_PNP ) && !defined( MBG_TGT_WIN32_PNP_X64 )
+ extern KE_QUERY_SYSTEM_TIME_FNC ke_query_system_time_fnc;
+ ke_query_system_time_fnc( p );
+ #else
+ KeQuerySystemTime( p );
+ #endif
+ #else // Windows user space
+ {
+ FILETIME ft;
+ GetSystemTimeAsFileTime( &ft );
+ p->LowPart = ft.dwLowDateTime;
+ p->HighPart = ft.dwHighDateTime;
+ }
+ #endif
+
+ #else
+
+ *p = 0; // dummy
+
+ #endif
+
+} // mbg_get_sys_time
+
+
+
+static __mbg_inline
+void mbg_get_sys_uptime( MBG_SYS_UPTIME *p )
+{
+ #if defined( MBG_TGT_WIN32 )
+
+ #if defined( MBG_TGT_KERNEL ) // kernel space
+
+ ULONGLONG time_increment = KeQueryTimeIncrement();
+ LARGE_INTEGER tick_count;
+
+ KeQueryTickCount( &tick_count );
+
+ // multiplication by time_increment yields HNS units,
+ // but we need seconds
+ *p = ( tick_count.QuadPart * time_increment ) / HNS_PER_SEC;
+
+ #else // user space
+
+ DWORD tickCount;
+ DWORD timeAdjustment;
+ DWORD timeIncrement;
+ BOOL timeAdjustmentDisabled;
+
+ if ( !GetSystemTimeAdjustment( &timeAdjustment, &timeIncrement, &timeAdjustmentDisabled ) )
+ *p = -1; // failed
+
+ // ATTENTION: This is compatible with older Windows versions, but
+ // the returned tick count wraps around to zero after 49.7 days.
+ // A new GetTickCount64() call is available under Windows Vista and newer,
+ // but the function call had to be imported dynamically since otherwise
+ // programs refused to start under pre-Vista versions due to undefined DLL symbol.
+ tickCount = GetTickCount();
+
+ *p = ( ( (MBG_SYS_UPTIME) tickCount ) * timeIncrement ) / HNS_PER_SEC;
+
+ #endif
+
+ #elif defined( MBG_TGT_LINUX )
+
+ #if defined( MBG_TGT_KERNEL )
+ // getrawmonotonic() can possibly be used for this in newer kernels
+ {
+ // Using a simple 64 bit division may result in a linker error
+ // in kernel mode due to a missing symbol __udivdi3, so we use
+ // a specific inline function do_div().
+ // Also, the jiffies counter is not set to 0 at startup but to
+ // a defined initialization value we need to account for.
+ uint64_t tmp = get_jiffies_64() - INITIAL_JIFFIES;
+ do_div( tmp, HZ );
+ *p = tmp;
+ }
+ #else
+ {
+ struct sysinfo si;
+ int rc = sysinfo( &si );
+ *p = ( rc == 0 ) ? si.uptime : -1;
+ }
+ #endif
+
+ #elif defined( MBG_TGT_BSD )
+
+ #if defined( MBG_TGT_KERNEL )
+ {
+ struct timespec ts;
+ #if 0 //##+++++++
+ {
+ struct bintime bt;
+
+ binuptime( &bt );
+ #if defined( DEBUG )
+ printf( "binuptime: %lli.%09lli\n",
+ (long long) bt.sec,
+ (long long) bt.frac );
+ #endif
+ }
+ #endif
+
+ nanouptime( &ts );
+ #if defined( DEBUG )
+ printf( "nanouptime: %lli.%09lli\n",
+ (long long) ts.tv_sec,
+ (long long) ts.tv_nsec );
+ #endif
+ *p = ts.tv_sec;
+ }
+ #elif defined( MBG_TGT_FREEBSD )
+ {
+ struct timespec ts;
+ // CLOCK_UPTIME_FAST is specific to FreeBSD
+ int rc = clock_gettime( CLOCK_UPTIME_FAST, &ts );
+ *p = ( rc == 0 ) ? ts.tv_sec : -1;
+ }
+ #else // MBG_TGT_NETBSD, ...
+
+ *p = -1; //##++ needs to be implemented
+
+ #endif
+
+ #else
+
+ *p = -1; // not supported
+
+ #endif
+
+} // mbg_get_sys_uptime
+
+
+
+/**
+ * @brief Compute delta between two ::MBG_SYS_TIME times, in milliseconds
+ *
+ * @param[in] t2 the time to be subtracted from
+ * @param[in] t1 The time to be subtracted
+ *
+ * @return The time difference in [milliseconds]
+ */
+static __mbg_inline
+long mbg_delta_sys_time_ms( const MBG_SYS_TIME *t2, const MBG_SYS_TIME *t1 )
+{
+ #if defined( MBG_TGT_POSIX )
+ long dt = ( t2->secs - t1->secs ) * 1000;
+ #if defined ( MBG_TGT_LINUX ) && defined( MBG_TGT_KERNEL )
+ int64_t tmp64 = t2->nano_secs - t1->nano_secs;
+ do_div( tmp64, 1000000 );
+ dt += tmp64;
+ #else
+ dt += ( t2->nano_secs - t1->nano_secs ) / 1000000;
+ #endif
+ return dt;
+ #elif defined( MBG_TGT_WIN32 )
+ return (long) ( ( t2->QuadPart - t1->QuadPart ) / HNS_PER_MS );
+ #else
+ return 0;
+ #endif
+
+} // mbg_delta_sys_time_ms
+
+
+
+static __mbg_inline
+void mbg_sleep_sec( long sec )
+{
+ #if defined( MBG_TGT_POSIX )
+
+ #if defined( MBG_TGT_KERNEL ) // kernel space functions even differ for POSIX systems
+
+ #if defined( MBG_TGT_LINUX ) // Linux kernel space
+
+ // msleep is not defined in older kernels, so we use this
+ // only if it is surely supported.
+ #if LINUX_KERNEL_HAS_MSLEEP
+ msleep( sec * 1000 );
+ #else
+ {
+ DECLARE_WAIT_QUEUE_HEAD( tmp_wait );
+ wait_event_interruptible_timeout( tmp_wait, 0, sec * HZ + 1 );
+ }
+ #endif
+
+ #elif defined( MBG_TGT_FREEBSD )
+
+ struct timeval tv = { 0 };
+ int ticks;
+ tv.tv_sec = sec;
+ ticks = tvtohz( &tv );
+
+ #if defined( DEBUG )
+ printf( "pause: %lli.%06lli (%i ticks)\n",
+ (long long) tv.tv_sec,
+ (long long) tv.tv_usec,
+ ticks );
+ #endif
+
+ pause( "pause", ticks );
+
+ #elif defined( MBG_TGT_NETBSD )
+
+ int timeo = mstohz( sec * 1000 );
+
+ #if defined( DEBUG )
+ printf( "kpause: %i s (%i ticks)\n", sec, timeo );
+ #endif
+
+ kpause( "pause", 1, timeo, NULL );
+
+ #endif
+
+ #else // POSIX user space
+
+ sleep( sec );
+
+ #endif
+
+ #elif defined( MBG_TGT_WIN32 )
+
+ #if defined( MBG_TGT_KERNEL ) // kernel space
+
+ LARGE_INTEGER delay;
+
+ // we need to pass a negative value to KeDelayExecutionThread()
+ // since the given time is a relative time interval, not absolute
+ // time. See the API docs for KeDelayExecutionThread().
+ delay.QuadPart = - ((LONGLONG) sec * HNS_PER_SEC);
+
+ KeDelayExecutionThread( KernelMode, FALSE, &delay );
+
+ #else // user space
+
+ // Sleep() expects milliseconds
+ Sleep( sec * 1000 );
+
+ #endif
+
+ #elif defined( MBG_TGT_DOS )
+
+ delay( (unsigned) ( sec * 1000 ) );
+
+ #else
+
+ // This needs to be implemented for the target OS
+ // and thus will probably yield a linker error.
+ do_sleep_sec( sec );
+
+ #endif
+
+} // mbg_sleep_sec
+
+
+
+/* function prototypes: */
+
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+/* (no header definitions found) */
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+/* End of header body */
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _MBGSYSTM_H */
diff --git a/mbglib/common/mbgtime.h b/mbglib/common/mbgtime.h
index d88bb57..2c5c50e 100755
--- a/mbglib/common/mbgtime.h
+++ b/mbglib/common/mbgtime.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgtime.h 1.19 2013/05/22 16:47:01 martin REL_M $
+ * $Id: mbgtime.h 1.23.1.3 2017/03/17 11:33:05 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,22 @@
*
* -----------------------------------------------------------------------
* $Log: mbgtime.h $
+ * Revision 1.23.1.3 2017/03/17 11:33:05 martin
+ * *** empty log message ***
+ * Revision 1.23.1.2 2017/03/17 10:36:41 martin
+ * *** empty log message ***
+ * Revision 1.23.1.1 2017/03/16 15:24:46 martin
+ * Updated preliminary function prototypes.
+ * Revision 1.23 2017/03/16 12:26:13 martin
+ * Updated function prototypes.
+ * Revision 1.22 2017/01/25 13:10:55 gregoire.diehl
+ * nano_time_64_to_double and double_to_nano_time_64 added
+ * Revision 1.21 2016/12/15 17:44:59Z martin
+ * Changed conditions to include time.h.
+ * Fixed spelling.
+ * Removed trailing spaces.
+ * Revision 1.20 2014/05/27 08:09:19 martin
+ * Added NTP_SEC_BIAS.
* Revision 1.19 2013/05/22 16:47:01 martin
* Added some useful macros.
* Revision 1.18 2012/10/02 18:51:11 martin
@@ -61,10 +77,7 @@
#include <gpsdefs.h>
-#if _IS_MBG_FIRMWARE \
- || defined( MBG_TGT_WIN32 ) \
- || defined( MBG_TGT_DOS ) \
- || defined( MBG_TGT_QNX_NTO )
+#if !defined( MBG_TGT_KERNEL ) || defined( MBG_TGT_WIN32 )
#include <time.h>
#endif
@@ -75,6 +88,7 @@ extern "C" {
#ifdef _MBGTIME
#define _ext
+ #define _DO_INIT
#else
#define _ext extern
#endif
@@ -83,13 +97,30 @@ extern "C" {
/* Start of header body */
-// The Unix time_t epoche is usually 1970-01-01 00:00 whereas
-// the GPS epoche is 1980-01-06 00:00, so the difference is 10 years,
-// plus 2 days due to leap years (1972 and 1976), plus the difference
-// of the day-of-month (6 - 1).
-#define GPS_SEC_BIAS 315964800UL // ( ( ( 10UL * 365UL ) + 2 + 5 ) * SECS_PER_DAY )
+/**
+ * @brief GPS epoch bias from ordinary time_t epoch
+ *
+ * The Unix time_t epoch is usually 1970-01-01 00:00 whereas
+ * the GPS epoch is 1980-01-06 00:00, so the difference is 10 years,
+ * plus 2 days due to leap years (1972 and 1976), plus the difference
+ * of the day-of-month (6 - 1), so:<br>
+ *
+ * time_t t = ( gps_week * ::SECS_PER_WEEK ) + sec_of_week + ::GPS_SEC_BIAS
+ */
+#define GPS_SEC_BIAS 315964800UL // ( ( ( 10UL * 365UL ) + 2 + 5 ) * SECS_PER_DAY )
+
+
+/**
+ * @brief NTP epoch bias from ordinary time_t epoch
+ *
+ * The Unix time_t epoch is usually 1970-01-01 00:00 whereas
+ * the NTP epoch is 1900-01-01 00:00, so the difference is
+ * a constant number of seconds:<br>
+ *
+ * time_t t = ntp_time - ::NTP_SEC_BIAS
+ */
+#define NTP_SEC_BIAS 2208988800UL
-// time_t t = ( gps_week * SECS_PER_WEEK ) + sec_of_week + GPS_SEC_BIAS
// Modified Julian Day (MJD) numbers for some commonly used epochs.
@@ -102,7 +133,7 @@ extern "C" {
// The constant below defines the Windows FILETIME number (100 ns intervals
-// since 1601-01-01) for 1970-01-01, which is usually the epoche for the time_t
+// since 1601-01-01) for 1970-01-01, which is usually the epoch for the time_t
// type used by the standard C library.
#if !defined( FILETIME_1970 )
// FILETIME represents a 64 bit number, so we need to defined the
@@ -171,6 +202,7 @@ typedef struct
clock_t start;
clock_t stop;
short is_set;
+
} TIMEOUT;
@@ -200,7 +232,7 @@ typedef struct
#define MSEC_PER_HOUR ( MSEC_PER_SEC * SECS_PER_HOUR )
#define MSEC_PER_DAY ( MSEC_PER_SEC * SECS_PER_DAY )
-#define NSECS_PER_SEC 1000000000UL
+#define NSECS_PER_SEC 1000000000UL
#if !defined( HNS_PER_SEC )
#define HNS_PER_SEC 10000000UL
@@ -239,56 +271,56 @@ _ext TM_GPS datum;
_ext const char *short_time_fmt
-#ifdef _MBGTIME
+#ifdef _DO_INIT
= "%2i:%02i"
#endif
;
_ext const char *time_fmt
-#ifdef _MBGTIME
+#ifdef _DO_INIT
= "%2i:%02i:%02i"
#endif
;
_ext const char *long_time_fmt
-#ifdef _MBGTIME
+#ifdef _DO_INIT
= "%2i:%02i:%02i.%02i"
#endif
;
_ext const char *date_fmt
-#ifdef _MBGTIME
+#ifdef _DO_INIT
= "%2i.%02i.%04i"
#endif
;
_ext const char *day_date_fmt
-#ifdef _MBGTIME
+#ifdef _DO_INIT
= "%s, %2i.%02i.%04i"
#endif
;
_ext const char *day_name_eng[]
-#ifdef _MBGTIME
+#ifdef _DO_INIT
= { "Su", "Mo", "Tu", "We", "Th", "Fr", "Sa" }
#endif
;
_ext const char *day_name_ger[]
-#ifdef _MBGTIME
+#ifdef _DO_INIT
= { "So", "Mo", "Di", "Mi", "Do", "Fr", "Sa" }
#endif
;
_ext const TM_GPS init_tm
-#ifdef _MBGTIME
+#ifdef _DO_INIT
= { 1980, 1, 1, 0, 0, 0, 0, 0, 0, 0 }
#endif
;
_ext DAYS_OF_MONTH_TABLE days_of_month
-#ifdef _MBGTIME
+#ifdef _DO_INIT
= DAYS_OF_MONTH_TABLE_INIT
#endif
;
@@ -313,29 +345,296 @@ _ext DAYS_OF_MONTH_TABLE days_of_month
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
+ /**
+ * @brief Set a timeout object to specified interval
+ *
+ * @param[out] t The timeout object
+ * @param[in] clk The current time, in clock_t ticks
+ * @param[in] interval The interval until expiration, in clock_t ticks
+ */
void set_timeout( TIMEOUT *t, clock_t clk, clock_t interval ) ;
+
+ /**
+ * @brief Stretch a timeout specified in given timeout object
+ *
+ * @param[in,out] t The timeout object
+ * @param[in] interval The interval until expiration, in clock_t ticks
+ */
void stretch_timeout( TIMEOUT *t, clock_t interval ) ;
+
+ /**
+ * @brief Check if a timeout object has expired
+ *
+ * @param[in] t The timeout object
+ * @param[in] clk The current time, in clock_t ticks
+ *
+ * @return 1 if timeout expired, else 0
+ */
bit check_timeout( TIMEOUT *t, clock_t clk ) ;
- int err_tm( TM_GPS *tm ) ;
+
+ /**
+ * @brief Check if a ::TM_GPS structure contains a valid date and time
+ *
+ * @param[in] tm The date/time structure to be checked
+ *
+ * @return 0 if date/time is valid, else a negative number indicating
+ * which field was found invalid
+ */
+ int err_tm( const TM_GPS *tm ) ;
+
+ /**
+ * @brief Set the time in a ::TM_GPS structure to 00:00:00
+ *
+ * FIXME what about the frac and UTC offset fields?
+ *
+ * @param[in] tm The date/time structure to be set
+ *
+ * @return Pointer to the ::TM_GPS structure that has been passed
+ */
TM_GPS *clear_time( TM_GPS *tm ) ;
+
+ /**
+ * @brief Convert second-of-week to day-of-week and time-of-day
+ *
+ * @param[in] wsec The second-of-week number to be converted
+ * @param[out] tm Address of a ::TM_GPS structure which takes the computed results
+ *
+ * @return Pointer to the ::TM_GPS structure that has been passed
+ *
+ * @see ::tm_to_wsec
+ */
TM_GPS *wsec_to_tm( long wsec, TM_GPS *tm ) ;
- long tm_to_wsec( TM_GPS *tm ) ;
+
+ /**
+ * @brief Compute second-of-week from day-of-week and time-of-day
+ *
+ * @todo Specify input / output ranges
+ *
+ * @param[in] tm Address of a ::TM_GPS structure providing day-of-week and time-of-day
+ *
+ * @return The computed second-of-week number
+ *
+ * @see ::wsec_to_tm
+ */
+ long tm_to_wsec( const TM_GPS *tm ) ;
+
+ /**
+ * @brief Check if a specific year is a leap year
+ *
+ * @param[in] y The full year number
+ *
+ * @return != 0 if the year is a leap year, else 0
+ */
int is_leap_year( int y ) ;
+
+ /**
+ * @brief Compute the day-of-year from a given date
+ *
+ * @param[in] day The day-of-month
+ * @param[in] month The month
+ * @param[in] year The full year number
+ *
+ * @return The computed day-of-year
+ */
int day_of_year( int day, int month, int year ) ;
+
+ /**
+ * @brief Compute a date from a given year and day-of-year
+ *
+ * @param[in] year The full year number
+ * @param[in] day_num Number of days from the beginning of that year, may be negative
+ * @param[out] tm Address of a ::TM_GPS structure which takes the computed results
+ */
void date_of_year ( int year, int day_num, TM_GPS *tm ) ;
+
+ /**
+ * @brief Compute day-of-week from a given date
+ *
+ * @todo Specify range of returned day-of-week. Should we just call n_days()?
+ *
+ * @param[in] day The day-of-month
+ * @param[in] month The month
+ * @param[in] year The full year number
+ *
+ * @return The computed day-of-week
+ *
+ * @see ::n_days
+ */
int day_of_week( int day, int month, int year ) ;
+
+ /**
+ * @brief FIXME Compute yearday-of-week from a given date
+ *
+ * @todo Specify range of returned day-of-week
+ *
+ * @param[in] day The day-of-month
+ * @param[in] month The month
+ * @param[in] year The full year number
+ *
+ * @return The computed day-of-week
+ */
int days_to_years( long *day_num, int year ) ;
+
+ /**
+ * @brief Compute number of days after Jan 1, 0000 for a given date
+ *
+ * @param[in] mday The day-of-month
+ * @param[in] month The month
+ * @param[in] year The full year number
+ *
+ * @return The computed number of days
+ *
+ * @see ::day_of_week
+ */
long n_days( ushort mday, ushort month, ushort year ) ;
+
+ /**
+ * @brief Convert a ::NANO_TIME time to double
+ *
+ * @param[in] p Address of a ::NANO_TIME structure to be converted
+ *
+ * @return The computed number of seconds with fractions, as double
+ *
+ * @see ::double_to_nano_time
+ */
double nano_time_to_double( const NANO_TIME *p ) ;
+
+ /**
+ * @brief Setup a ::NANO_TIME structure from a time provided as double
+ *
+ * @param[out] p Address of a ::NANO_TIME structure to be set up
+ * @param[in] d The time to be converted, in seconds with fractions, as double
+ *
+ * @see ::nano_time_to_double
+ */
void double_to_nano_time( NANO_TIME *p, double d ) ;
+
+ /**
+ * @brief Convert a ::NANO_TIME_64 time to double
+ *
+ * @param[in] p Address of a ::NANO_TIME_64 structure to be converted
+ *
+ * @return The computed number of seconds with fractions, as double
+ *
+ * @see ::double_to_nano_time_64
+ */
+ double nano_time_64_to_double( const NANO_TIME_64 *p ) ;
+
+ /**
+ * @brief Setup a ::NANO_TIME_64 structure from a time as double
+ *
+ * @param[out] p Address of a ::NANO_TIME_64 structure to be set up
+ * @param[in] d The time to be converted, in seconds with fractions, as double
+ *
+ * @see ::nano_time_64_to_double
+ */
+ void double_to_nano_time_64( NANO_TIME_64 *p, double d ) ;
+
+ /**
+ * @brief Set up a ::NANO_TIME_64 structure from a string with a time in seconds and fractions
+ *
+ * @param[in] s A string with a time in seconds, with fractions separated by decimal point
+ * @param[out] p Address of a ::NANO_TIME_64 structure to be set up
+ */
+ void str_s_to_nano_time_64( const char *s, NANO_TIME_64 *p ) ;
+
+ /**
+ * @brief Set up a ::NANO_TIME_64 structure from a string with a time in milliseconds and fractions
+ *
+ * @param[in] s A string with a time in milliseconds, with fractions separated by decimal point
+ * @param[out] p Address of a ::NANO_TIME_64 structure to be set up
+ */
+ void str_ms_to_nano_time_64( const char *s, NANO_TIME_64 *p ) ;
+
+ /**
+ * @brief Convert a ::NTP_TSTAMP structure to a ::NANO_TIME_64 structure
+ *
+ * @param[in] p_nts The ::NTP_TSTAMP structure to be converted
+ * @param[out] p_nt64 The ::NANO_TIME_64 structure to be filled up
+ */
+ void ntp_tstamp_to_nanotime_64( const NTP_TSTAMP *p_nts, NANO_TIME_64 *p_nt64 ) ;
+
+ /**
+ * @brief Set up a ::NTP_TSTAMP structure from a hex string with a time in seconds and binary fractions
+ *
+ * @param[in] s A string with a time in seconds since epoch 1900-01-01,
+ * with binary fractions separated by decimal point,
+ * e.g. 'dc763e43.73bd5a8f' as printed by the ntpq utility
+ * @param[out] p Address of a ::NANO_TIME_64 structure to be set up
+ *
+ * @see ::str_ntp_hex_to_nano_time_64
+ */
+ void str_ntp_hex_to_ntp_tstamp( const char *s, NTP_TSTAMP *p ) ;
+
+ /**
+ * @brief Set up a ::NANO_TIME_64 structure from a hex string with a time in seconds and binary fractions
+ *
+ * @param[in] s A string with a time in seconds since epoch 1900-01-01,
+ * with binary fractions separated by decimal point,
+ * e.g. 'dc763e43.73bd5a8f' as printed by the ntpq utility
+ * @param[out] p Address of a ::NANO_TIME_64 structure to be set up
+ *
+ * @see ::str_ntp_hex_to_ntp_tstamp
+ */
+ void str_ntp_hex_to_nano_time_64( const char *s, NANO_TIME_64 *p ) ;
+
+ /**
+ * @brief Print time with hours, minutes, seconds to a string
+ *
+ * @param[out] s Address of a string buffer to be filled
+ * @param[in] tm Address of a ::TM_GPS structure providing date and time
+ */
int sprint_time( char *s, const TM_GPS *tm ) ;
+
+ /**
+ * @brief Print time with hours, minutes to a string
+ *
+ * @param[out] s Address of a string buffer to be filled
+ * @param[in] tm Address of a ::TM_GPS structure providing date and time
+ */
int sprint_short_time( char *s, TM_GPS *time ) ;
+
+ /**
+ * @brief Print date to a string
+ *
+ * @param[out] s Address of a string buffer to be filled
+ * @param[in] tm Address of a ::TM_GPS structure providing date and time
+ */
int sprint_date( char *s, const TM_GPS *tm ) ;
+
+ /**
+ * @brief Print day-of-week and date to a string
+ *
+ * @param[out] s Address of a string buffer to be filled
+ * @param[in] tm Address of a ::TM_GPS structure providing date and time
+ */
int sprint_day_date( char *s, const TM_GPS *tm ) ;
+
+ /**
+ * @brief Print day-of-week, date and time to a string
+ *
+ * @param[out] s Address of a string buffer to be filled
+ * @param[in] tm Address of a ::TM_GPS structure providing date and time
+ */
int sprint_tm( char *s, const TM_GPS *tm ) ;
- void sscan_time( char *s, TM_GPS *tm ) ;
+
+ /**
+ * @brief Extract a time from a string
+ *
+ * @param[in] s A time string in format hh:mm:ss
+ * @param[out] tm Address of a ::TM_GPS structure which takes the extracted time
+ */
+ void sscan_time( const char *s, TM_GPS *tm ) ;
+
+ /**
+ * @brief Extract a date from a string
+ *
+ * @param[in] s A date string in format dd.mm. or dd.mm.yyyy
+ * @param[out] tm Address of a ::TM_GPS structure which takes the extracted date
+ */
void sscan_date( char *s, TM_GPS *tm ) ;
+
/* ----- function prototypes end ----- */
@@ -343,6 +642,7 @@ _ext DAYS_OF_MONTH_TABLE days_of_month
#undef _ext
+#undef _DO_INIT
#ifdef __cplusplus
}
diff --git a/mbglib/common/mbgutil.c b/mbglib/common/mbgutil.c
index edc41b4..d3cb946 100755
--- a/mbglib/common/mbgutil.c
+++ b/mbglib/common/mbgutil.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgutil.c 1.6 2012/10/15 13:12:17 martin REL_M $
+ * $Id: mbgutil.c 1.6.1.18 2016/07/22 09:57:11 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,30 @@
*
* -----------------------------------------------------------------------
* $Log: mbgutil.c $
+ * Revision 1.6.1.18 2016/07/22 09:57:11 martin
+ * Quieted some compiler warninges.
+ * Revision 1.6.1.17 2016/07/15 14:09:48 martin
+ * Use functions from new module timeutil.
+ * Revision 1.6.1.16 2016/04/26 09:23:36 martin
+ * Revision 1.6.1.15 2016/03/16 11:46:34Z martin
+ * *** empty log message ***
+ * Revision 1.6.1.14 2015/12/01 11:36:25 martin
+ * *** empty log message ***
+ * Revision 1.6.1.13 2015/11/24 15:44:55 martin
+ * Revision 1.6.1.12 2015/11/20 16:30:41Z martin
+ * Revision 1.6.1.11 2015/11/02 10:12:28Z martin
+ * *** empty log message ***
+ * Revision 1.6.1.10 2015/10/30 11:36:54 martin
+ * Revision 1.6.1.9 2015/09/08 10:37:02Z martin
+ * Revision 1.6.1.8 2015/08/27 16:17:27Z martin
+ * Use safe string functions from str_util.c.
+ * Revision 1.6.1.7 2014/05/27 11:32:47 martin
+ * Revision 1.6.1.6 2014/05/27 11:26:24 martin
+ * Revision 1.6.1.5 2014/03/13 16:04:12 martin
+ * Revision 1.6.1.4 2014/03/13 15:45:36 martin
+ * Revision 1.6.1.3 2014/03/13 14:31:52Z martin
+ * Revision 1.6.1.2 2013/10/23 10:40:53Z martin
+ * Revision 1.6.1.1 2013/10/22 10:05:55 martin
* Revision 1.6 2012/10/15 13:12:17 martin
* Fixed build under DOS.
* Fixed format/type mismatch when printing UTC offset.
@@ -35,12 +59,17 @@
#include <mbgutil.h>
#undef _MBGUTIL
+#include <cfg_hlp.h>
+#include <mbgerror.h>
#include <pcpsutil.h>
-#include <pcpslstr.h>
+#include <charcode.h>
#include <pcpsdev.h>
+#include <str_util.h>
+#include <qsdefs.h>
#include <stdio.h>
#include <time.h>
+#include <limits.h>
// required at least for Linux:
#include <stdarg.h>
@@ -60,32 +89,32 @@ static int mbg_date_time_dist = 2;
static int mbg_pos_dist = 2;
static uint16_t mbg_year_lim = 1980;
+static const char str_inv_cnv[] = "(invalid conversion)";
+
+// The size_t type can eventually be larger than an int type.
+// However, some snprintf-like functions expect a size_t value
+// to specify the buffer size, but just return an int value.
+// So we take care that at least the return value is limited
+// to MAXINT.
#if defined( MBG_TGT_WIN32 )
- #define mbg_vsnprintf _vsnprintf
+ #define _int_from_size_t( _n ) \
+ ( ( (_n) > INT_MAX ) ? INT_MAX : (int) (_n) )
#else
- #define mbg_vsnprintf vsnprintf
-#endif
-
-
-#if defined( MBG_TGT_DOS )
-
-static /*HDR*/
-int vsnprintf( char *s, int max_len, const char *fmt, va_list arg_list )
-{
- return vsprintf( s, fmt, arg_list );
-
-} // vsnprintf
-
+ #define _int_from_size_t( _n ) (_n)
#endif
/*HDR*/
+/**
+ * @brief Get the DLL/shared library's version code
+ *
+ * @return The version code at which the library was built
+ */
_MBG_API_ATTR int _MBG_API mbgutil_get_version( void )
{
-
return MBGUTIL_VERSION;
} // mbgutil_get_version
@@ -93,54 +122,58 @@ _MBG_API_ATTR int _MBG_API mbgutil_get_version( void )
/*HDR*/
+/**
+ * @brief Check the DLL/shared library's compatibility
+ *
+ * @param header_version Version code defined in the header file when the application is built
+ *
+ * @return ::MBG_SUCCESS if compatible, else ::MBG_ERR_LIB_NOT_COMPATIBLE
+ */
_MBG_API_ATTR int _MBG_API mbgutil_check_version( int header_version )
{
if ( header_version >= MBGUTIL_COMPAT_VERSION )
- return PCPS_SUCCESS;
+ return MBG_SUCCESS;
- return -1;
+ return MBG_ERR_LIB_NOT_COMPATIBLE;
} // mbgutil_check_version
-// We have our own version of snprintf() since under Windows
-// _snprintf(), returns -1 and does not write a terminating 0
-// if the output exceeds the buffer size.
-//
-// This function terminates the output string properly. However,
-// the maximum return value is (max_len - 1), so the function
-// can not be used to determine the buffer size that would be
-// required for an untruncated string.
-
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_snprintf( char *s, size_t max_len, const char * fmt, ... )
+/**
+ * @brief A portable, safe implementation of snprintf()
+ *
+ * For a detailed description see ::vsnprintf_safe
+ *
+ * @param s pointer to the output buffer
+ * @param max_len size of the output buffer
+ * @param fmt format string according to subsequent parameters
+ * @param ... variable argument list according to the format string
+ *
+ * @return the number of characters written to the output buffer, except the terminating 0
+ *
+ * @see ::vsnprintf_safe
+ * @see ::snprintf_safe
+ */
+_MBG_API_ATTR int __attribute__( ( format( printf, 3, 4 ) ) )
+_MBG_API mbg_snprintf( char *s, size_t max_len, const char * fmt, ... )
{
- int n;
-
+ size_t n;
va_list ap;
- va_start( ap, fmt );
-
- n = mbg_vsnprintf( s, max_len, fmt, ap );
-
- va_end( ap );
-
+ // TODO: size_t can be larger than int, so what happens if
+ // a very long string is written to the buffer and the number
+ // of bytes written exceeds MAXINT, in which case the number
+ // can't be returned?
- #if defined( MBG_TGT_WIN32 )
-
- // Terminate the output string properly under Windows.
- // For other targets assume the POSIX version is available.
- if ( n < 0 || n >= (int) max_len )
- {
- n = max_len - 1;
- s[n] = 0;
- }
+ va_start( ap, fmt );
- #endif
+ n = vsnprintf_safe( s, max_len, fmt, ap );
+ va_end( ap );
- return n;
+ return _int_from_size_t( n );
} // mbg_snprintf
@@ -149,14 +182,26 @@ _MBG_API_ATTR int _MBG_API mbg_snprintf( char *s, size_t max_len, const char * f
/*HDR*/
_MBG_API_ATTR int _MBG_API mbg_strncpy( char *s, size_t max_len, const char *src )
{
- //##++ This could be coded more efficiently
- return mbg_snprintf( s, max_len, "%s", src );
+ size_t n = sn_cpy_str_safe( s, max_len, src );
+ return _int_from_size_t( n );
} // mbg_strncpy
/*HDR*/
+/**
+ * @brief Write a character multiple times to a string buffer
+ *
+ * Append a terminating 0 to the buffer.
+ *
+ * @param s pointer to the output buffer
+ * @param max_len size of the output buffer
+ * @param c the character to write to the output buffer
+ * @param n the number of characters to write to the output buffer
+ *
+ * @return the number of characters written to the output buffer, except the terminating 0
+ */
_MBG_API_ATTR int _MBG_API mbg_strchar( char *s, size_t max_len, char c, size_t n )
{
size_t i;
@@ -168,48 +213,54 @@ _MBG_API_ATTR int _MBG_API mbg_strchar( char *s, size_t max_len, char c, size_t
if ( i >= max_len )
break;
+ if ( i >= ( INT_MAX - 1 ) )
+ break;
+
s[i] = c;
}
s[i] = 0;
- return i;
+ return (int) i;
} // mbg_strchar
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_date_short( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_date_short( char *s, int max_len,
int mday, int month )
{
- return mbg_snprintf( s, max_len, "%02u.%02u.", mday, month );
-
+ size_t n = snprintf_safe( s, max_len, "%02u.%02u.", mday, month );
+ return _int_from_size_t( n );
+
} // mbg_str_date_short
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_date( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_date( char *s, int max_len,
int mday, int month, int year )
{
- int n = mbg_str_date_short( s, max_len, mday, month );
- n += mbg_snprintf( s + n, max_len - n, "%04u",
- ( year < 256 ) ?
- pcps_exp_year( (uint8_t) year, mbg_year_lim ) :
- year
- );
- return n;
+ size_t n = mbg_str_date_short( s, max_len, mday, month );
+
+ n += snprintf_safe( &s[n], max_len - n, "%04u",
+ ( year < 256 ) ?
+ pcps_exp_year( (uint8_t) year, mbg_year_lim ) :
+ year );
+
+ return _int_from_size_t( n );
} // mbg_str_date
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_time_short( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_time_short( char *s, int max_len,
int hour, int min )
{
- return mbg_snprintf( s, max_len, "%2u:%02u", hour, min );
+ size_t n = snprintf_safe( s, max_len, "%2u:%02u", hour, min );
+ return _int_from_size_t( n );
} // mbg_str_time_short
@@ -219,11 +270,11 @@ _MBG_API_ATTR int _MBG_API mbg_str_time_short( char *s, int max_len,
_MBG_API_ATTR int _MBG_API mbg_str_time( char *s, int max_len,
int hour, int min, int sec )
{
- int n = mbg_str_time_short( s, max_len, hour, min );
+ size_t n = mbg_str_time_short( s, max_len, hour, min );
- n += mbg_snprintf( s + n, max_len - n, ":%02u", sec );
+ n += snprintf_safe( &s[n], max_len - n, ":%02u", sec );
- return n;
+ return _int_from_size_t( n );
} // mbg_str_time
@@ -233,11 +284,11 @@ _MBG_API_ATTR int _MBG_API mbg_str_time( char *s, int max_len,
_MBG_API_ATTR int _MBG_API mbg_str_time_long( char *s, int max_len,
int hour, int min, int sec, int sec100 )
{
- int n = mbg_str_time( s, max_len, hour, min, sec );
+ size_t n = mbg_str_time( s, max_len, hour, min, sec );
- n += mbg_snprintf( s + n, max_len - n, ".%02u", sec100 );
+ n += snprintf_safe( &s[n], max_len - n, ".%02u", sec100 );
- return n;
+ return _int_from_size_t( n );
} // mbg_str_time_long
@@ -247,31 +298,33 @@ _MBG_API_ATTR int _MBG_API mbg_str_time_long( char *s, int max_len,
_MBG_API_ATTR int _MBG_API mbg_str_tm_gps_date_time( char *s, int max_len,
const TM_GPS *pt )
{
- int n = mbg_str_date( s, max_len, pt->mday, pt->month, pt->year );
- n += mbg_strchar( s + n, max_len - n, ' ', mbg_date_time_dist );
- n += mbg_str_time( s + n, max_len - n, pt->hour, pt->min, pt->sec );
+ size_t n = mbg_str_date( s, max_len, pt->mday, pt->month, pt->year );
+ n += mbg_strchar( &s[n], max_len - n, ' ', mbg_date_time_dist );
+ n += mbg_str_time( &s[n], max_len - _int_from_size_t( n ), pt->hour, pt->min, pt->sec );
- return n;
+ return _int_from_size_t( n );
} // mbg_str_tm_gps_date_time
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_date_short( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_date_short( char *s, int max_len,
const PCPS_TIME *pt )
{
- return mbg_str_date_short( s, max_len, pt->mday, pt->month );
+ size_t n = mbg_str_date_short( s, max_len, pt->mday, pt->month );
+ return _int_from_size_t( n );
} // mbg_str_pcps_date_short
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_date( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_date( char *s, int max_len,
const PCPS_TIME *pt )
{
- return mbg_str_date( s, max_len, pt->mday, pt->month, pt->year );
+ size_t n = mbg_str_date( s, max_len, pt->mday, pt->month, pt->year );
+ return _int_from_size_t( n );
} // mbg_str_pcps_date
@@ -281,7 +334,8 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_date( char *s, int max_len,
_MBG_API_ATTR int _MBG_API mbg_str_pcps_time_short( char *s, int max_len,
const PCPS_TIME *pt )
{
- return mbg_str_time_short( s, max_len, pt->hour, pt->min );
+ size_t n = mbg_str_time_short( s, max_len, pt->hour, pt->min );
+ return _int_from_size_t( n );
} // mbg_str_pcps_time_short
@@ -291,7 +345,8 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_time_short( char *s, int max_len,
_MBG_API_ATTR int _MBG_API mbg_str_pcps_time( char *s, int max_len,
const PCPS_TIME *pt )
{
- return mbg_str_time( s, max_len, pt->hour, pt->min, pt->sec );
+ size_t n = mbg_str_time( s, max_len, pt->hour, pt->min, pt->sec );
+ return _int_from_size_t( n );
} // mbg_str_pcps_time
@@ -301,60 +356,77 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_time( char *s, int max_len,
_MBG_API_ATTR int _MBG_API mbg_str_pcps_time_long( char *s, int max_len,
const PCPS_TIME *pt )
{
- return mbg_str_time_long( s, max_len, pt->hour, pt->min, pt->sec, pt->sec100 );
+ size_t n = mbg_str_time_long( s, max_len, pt->hour, pt->min, pt->sec, pt->sec100 );
+ return _int_from_size_t( n );
} // mbg_str_pcps_time_long
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_date_time( char *s, int max_len,
- const PCPS_TIME *pt,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_date_time( char *s, int max_len,
+ const PCPS_TIME *pt,
const char *tz_str )
{
- int n = mbg_str_pcps_date( s, max_len, pt );
- n += mbg_strchar( s + n, max_len - n, ' ', mbg_date_time_dist );
- n += mbg_str_pcps_time( s + n, max_len - n, pt );
+ size_t n = mbg_str_pcps_date( s, max_len, pt );
+ n += mbg_strchar( &s[n], max_len - n, ' ', mbg_date_time_dist );
+ n += mbg_str_pcps_time( &s[n], max_len - _int_from_size_t( n ), pt );
+
+ return _int_from_size_t( n );
- return n;
-
} // mbg_str_pcps_date_time
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date( char *s, int max_len,
uint32_t sec )
{
- time_t t = sec;
- struct tm tm = *gmtime( &t );
- return mbg_str_date( s, max_len, tm.tm_mday, tm.tm_mon + 1, tm.tm_year );
+ struct tm tm = { 0 };
+ time_t t = cvt_to_time_t( sec );
+ int rc = mbg_gmtime( &tm, &t );
+
+ return mbg_rc_is_success( rc ) ?
+ mbg_str_date( s, max_len, tm.tm_mday, tm.tm_mon + 1, tm.tm_year ) :
+ sn_cpy_str_safe( s, max_len, str_inv_cnv );
} // mbg_str_pcps_hr_date
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time( char *s, int max_len,
uint32_t sec )
{
- time_t t = sec;
- struct tm tm = *gmtime( &t );
- return mbg_str_time( s, max_len, tm.tm_hour, tm.tm_min, tm.tm_sec );
+ struct tm tm = { 0 };
+ time_t t = cvt_to_time_t( sec );
+ int rc = mbg_gmtime( &tm, &t );
+
+ return mbg_rc_is_success( rc ) ?
+ mbg_str_time( s, max_len, tm.tm_hour, tm.tm_min, tm.tm_sec ) :
+ sn_cpy_str_safe( s, max_len, str_inv_cnv );
} // mbg_str_pcps_hr_time
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_utc( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_utc( char *s, int max_len,
const PCPS_HR_TIME *pt )
{
- time_t t = pt->tstamp.sec;
- struct tm tm = *gmtime( &t );
- int n = mbg_str_date( s, max_len, tm.tm_mday , tm.tm_mon + 1, tm.tm_year );
- n += mbg_strchar( s + n, max_len - n, ' ', mbg_date_time_dist );
- n += mbg_str_time( s + n, max_len - n, tm.tm_hour, tm.tm_min, tm.tm_sec );
+ struct tm tm = { 0 };
+ int n = 0;
+ time_t t = cvt_to_time_t( pt->tstamp.sec );
+ int rc = mbg_gmtime( &tm, &t );
+
+ if ( mbg_rc_is_success( rc ) )
+ {
+ n = mbg_str_date( s, max_len, tm.tm_mday , tm.tm_mon + 1, tm.tm_year );
+ n += mbg_strchar( &s[n], max_len - n, ' ', mbg_date_time_dist );
+ n += mbg_str_time( &s[n], max_len - n, tm.tm_hour, tm.tm_min, tm.tm_sec );
+ }
+ else
+ n = sn_cpy_str_safe( s, max_len, str_inv_cnv );
return n;
@@ -363,14 +435,23 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_utc( char *s, int max_len,
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_loc( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_loc( char *s, int max_len,
const PCPS_HR_TIME *pt )
{
- time_t t = pt->tstamp.sec + pt->utc_offs;
- struct tm tm = *gmtime( &t );
- int n = mbg_str_date( s, max_len, tm.tm_mday , tm.tm_mon + 1, tm.tm_year );
- n += mbg_strchar( s + n, max_len - n, ' ', mbg_date_time_dist );
- n += mbg_str_time( s + n, max_len - n, tm.tm_hour, tm.tm_min, tm.tm_sec );
+ struct tm tm = { 0 };
+ int n = 0;
+ long l = (long) pt->tstamp.sec + pt->utc_offs;
+ time_t t = cvt_to_time_t( l );
+ int rc = mbg_gmtime( &tm, &t );
+
+ if ( mbg_rc_is_success( rc ) )
+ {
+ n = mbg_str_date( s, max_len, tm.tm_mday , tm.tm_mon + 1, tm.tm_year );
+ n += mbg_strchar( &s[n], max_len - n, ' ', mbg_date_time_dist );
+ n += mbg_str_time( &s[n], max_len - n, tm.tm_hour, tm.tm_min, tm.tm_sec );
+ }
+ else
+ n = sn_cpy_str_safe( s, max_len, str_inv_cnv );
return n;
@@ -379,40 +460,41 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_loc( char *s, int max_len,
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_frac( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_frac( char *s, int max_len,
uint32_t frac )
{
- return mbg_snprintf( s, max_len, PCPS_HRT_FRAC_SCALE_FMT,
- frac_sec_from_bin( frac, PCPS_HRT_FRAC_SCALE ) );
+ size_t n = snprintf_safe( s, max_len, PCPS_HRT_FRAC_SCALE_FMT,
+ (ulong) frac_sec_from_bin( frac, PCPS_HRT_FRAC_SCALE ) );
+ return _int_from_size_t( n );
} // mbg_str_pcps_hr_time_frac
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_offs( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_offs( char *s, int max_len,
const PCPS_HR_TIME *pt,
const char *info )
{
- int n = mbg_snprintf( s, max_len, "%s", info );
+ size_t n = snprintf_safe( s, max_len, "%s", info );
if ( pt->utc_offs )
{
ldiv_t ldt = ldiv( labs( pt->utc_offs ) / 60, 60 );
- n += mbg_snprintf( s + n, max_len - n, "%c%02lu:%02luh",
- ( pt->utc_offs < 0 ) ? '-' : '+',
- ldt.quot, ldt.rem );
+ n += snprintf_safe( &s[n], max_len - n, "%c%02lu:%02luh",
+ ( pt->utc_offs < 0 ) ? '-' : '+',
+ ldt.quot, ldt.rem );
}
- return n;
+ return _int_from_size_t( n );
} // mbg_str_pcps_hr_time_offs
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_utc( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_utc( char *s, int max_len,
const PCPS_HR_TIME *pt )
{
int n = mbg_str_pcps_hr_date_time_utc( s, max_len, pt );
@@ -420,7 +502,7 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_utc( char *s, int max_len,
if ( n < ( max_len - 1 ) )
{
s[n++] = '.';
- n += mbg_str_pcps_hr_time_frac( s + n, max_len - n, pt->tstamp.frac );
+ n += mbg_str_pcps_hr_time_frac( &s[n], max_len - n, pt->tstamp.frac );
}
return n;
@@ -430,7 +512,7 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_utc( char *s, int max_len,
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_loc( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_loc( char *s, int max_len,
const PCPS_HR_TIME *pt )
{
int n = mbg_str_pcps_hr_date_time_loc( s, max_len, pt );
@@ -438,7 +520,7 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_loc( char *s, int max_len,
if ( n < ( max_len - 1 ) )
{
s[n++] = '.';
- n += mbg_str_pcps_hr_time_frac( s + n, max_len - n, pt->tstamp.frac );
+ n += mbg_str_pcps_hr_time_frac( &s[n], max_len - n, pt->tstamp.frac );
}
if ( n < ( max_len - 1 ) )
@@ -452,7 +534,7 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_loc( char *s, int max_len,
cp = "GPS";
s[n++] = ' ';
- n += mbg_str_pcps_hr_time_offs( s + n, max_len - n, pt, cp );
+ n += mbg_str_pcps_hr_time_offs( &s[n], max_len - n, pt, cp );
}
return n;
@@ -462,53 +544,51 @@ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_loc( char *s, int max_len,
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_tstamp_raw( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_tstamp_raw( char *s, int max_len,
const PCPS_TIME_STAMP *pt )
{
- return mbg_snprintf( s, max_len, "%08lX.%08lX", pt->sec, pt->frac );
+ size_t n = snprintf_safe( s, max_len, "%08lX.%08lX", (ulong) pt->sec, (ulong) pt->frac );
+ return _int_from_size_t( n );
} // mbg_str_pcps_tstamp_raw
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_raw( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_raw( char *s, int max_len,
const PCPS_HR_TIME *pt )
{
- int n = mbg_str_pcps_tstamp_raw( s, max_len, &pt->tstamp );
- n += mbg_str_pcps_hr_time_offs( s + n, max_len - n, pt, ", Loc: " );
- n += mbg_snprintf( s + n, max_len - n, ", st: 0x%04X", pt->status );
+ size_t n = mbg_str_pcps_tstamp_raw( s, max_len, &pt->tstamp );
+ n += mbg_str_pcps_hr_time_offs( &s[n], max_len - _int_from_size_t( n ), pt, ", Loc: " );
+ n += snprintf_safe( &s[n], max_len - n, ", st: 0x%04X", pt->status );
+
+ return _int_from_size_t( n );
- return n;
-
} // mbg_str_pcps_hr_time_raw
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_ucap( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_ucap( char *s, int max_len,
const PCPS_HR_TIME *pt )
{
- int n = mbg_snprintf( s, max_len, "CAP%u: ", pt->signal );
- n += mbg_str_pcps_hr_tstamp_loc( s + n, max_len - n, pt );
+ size_t n = snprintf_safe( s, max_len, "CAP%u: ", pt->signal );
+ n += mbg_str_pcps_hr_tstamp_loc( &s[n], max_len - _int_from_size_t( n ), pt );
+
+ return _int_from_size_t( n );
- return n;
-
} // mbg_str_ucap
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pos_dms( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pos_dms( char *s, int max_len,
const DMS *pdms, int prec )
{
- return mbg_snprintf( s, max_len, "%c %i" DEG "%02i'%02.*f\"",
- pdms->prefix,
- pdms->deg,
- pdms->min,
- prec,
- pdms->sec
- );
+ size_t n = snprintf_safe( s, max_len, "%c %i" DEG "%02i'%02.*f\"",
+ pdms->prefix, pdms->deg, pdms->min,
+ prec, pdms->sec );
+ return _int_from_size_t( n );
} // mbg_str_pos_dms
@@ -517,14 +597,15 @@ _MBG_API_ATTR int _MBG_API mbg_str_pos_dms( char *s, int max_len,
/*HDR*/
_MBG_API_ATTR int _MBG_API mbg_str_pos_alt( char *s, int max_len, double alt )
{
- return mbg_snprintf( s, max_len, "%.0fm", alt );
+ size_t n = snprintf_safe( s, max_len, "%.0fm", alt );
+ return _int_from_size_t( n );
} // mbg_str_pos_alt
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_pos( char *s, int max_len,
+_MBG_API_ATTR int _MBG_API mbg_str_pos( char *s, int max_len,
const POS *ppos, int prec )
{
int n;
@@ -532,15 +613,15 @@ _MBG_API_ATTR int _MBG_API mbg_str_pos( char *s, int max_len,
if ( ppos->lla[LON] || ppos->lla[LAT] || ppos->lla[ALT] )
{
n = mbg_str_pos_dms( s, max_len, &ppos->latitude, prec );
- n += mbg_strchar( s + n, max_len - n, ',', 1 );
- n += mbg_strchar( s + n, max_len - n, ' ', mbg_pos_dist );
- n += mbg_str_pos_dms( s + n, max_len - n, &ppos->longitude, prec );
- n += mbg_strchar( s + n, max_len - n, ',', 1 );
- n += mbg_strchar( s + n, max_len - n, ' ', mbg_pos_dist );
- n += mbg_str_pos_alt( s + n, max_len - n, ppos->lla[ALT] );
+ n += mbg_strchar( &s[n], max_len - n, ',', 1 );
+ n += mbg_strchar( &s[n], max_len - n, ' ', mbg_pos_dist );
+ n += mbg_str_pos_dms( &s[n], max_len - n, &ppos->longitude, prec );
+ n += mbg_strchar( &s[n], max_len - n, ',', 1 );
+ n += mbg_strchar( &s[n], max_len - n, ' ', mbg_pos_dist );
+ n += mbg_str_pos_alt( &s[n], max_len - n, ppos->lla[ALT] );
}
else
- n = mbg_strncpy( s, max_len, "N/A" );
+ n = mbg_strncpy( s, max_len, str_not_avail );
return n;
@@ -549,53 +630,82 @@ _MBG_API_ATTR int _MBG_API mbg_str_pos( char *s, int max_len,
/*HDR*/
-_MBG_API_ATTR int _MBG_API mbg_str_dev_name( char *s, int max_len, const char *short_name,
+_MBG_API_ATTR int _MBG_API mbg_str_dev_name( char *s, int max_len, const char *short_name,
uint16_t fw_rev_num, PCI_ASIC_VERSION asic_version_num )
{
- #define HW_NAME_SZ PCPS_CLOCK_NAME_SZ+PCPS_SN_SIZE+1
+ #define HW_NAME_SZ ( PCPS_CLOCK_NAME_SZ + PCPS_SN_SIZE + 1 )
- char model_code[HW_NAME_SZ];
- PCPS_SN_STR sernum;
+ char model_code[HW_NAME_SZ] = { 0 };
+ PCPS_SN_STR sernum = { 0 };
unsigned int i = 0;
- int n = 0;
+ size_t n = 0;
+ size_t l = strlen( short_name );
- memset( model_code, 0, sizeof( model_code ) );
- memset( sernum, 0, sizeof( sernum ) );
-
- if ( strlen( short_name ) > 0 )
+ if ( l > 0 )
{
- if ( strstr( short_name, "COM") )
- return mbg_snprintf(s, max_len,"%s", short_name);
+ // For serial port string specifies we just copy
+ // the short_name.
+ if ( device_id_is_serial( short_name ) )
+ {
+ n = sn_cpy_str_safe( s, max_len, short_name );
+ goto out;
+ }
+
+ // If the short_name has more than HW_NAME_SZ characters
+ // then we have to reduce the maximum length.
+ // For bus level device, the short_name usually consists of
+ // the model name, followed by an underscore '_', followed
+ // by the serial number, e.g. "PZF180PEX_046411000030".
+ if ( HW_NAME_SZ < l )
+ l = HW_NAME_SZ;
- for ( i = 0; ( i < HW_NAME_SZ ) && ( i < strlen( short_name ) ); i++ )
+ for ( i = 0; i < l; i++ )
{
if ( short_name[i] == '_' )
{
i++;
break;
}
+
model_code[i] = short_name[i];
}
- strncpy( sernum, &short_name[i], PCPS_SN_SIZE-1 );
- if ( sernum[12] == ' ' )
- sernum[12] = '\0';
+ strncpy_safe( sernum, &short_name[i], sizeof( sernum ) );
+
+ //### TODO
+ // Legal serial numbers have MBG_GRP_SERNUM_LEN characters, which is
+ // less than the maximum length of a PCPS_SN_STR type string.
+ // Do we really have to check and truncate the PCPS_SN_STR sernum?
+ if ( sernum[MBG_GRP_SERNUM_LEN] == ' ' )
+ sernum[MBG_GRP_SERNUM_LEN] = '\0';
}
- n = mbg_snprintf( s, max_len, "%s, S/N %s", model_code, sernum );
+ n = snprintf_safe( s, max_len, "%s, S/N %s", model_code, sernum );
- if ( fw_rev_num > 0 )
- n += mbg_snprintf( &s[n], max_len," (FW v%X.%02X", fw_rev_num>>8, fw_rev_num & 0x00FF );
+ if ( fw_rev_num || asic_version_num )
+ n += sn_cpy_str_safe( &s[n], max_len - n, " (" );
- if ( asic_version_num > 0 )
+ if ( fw_rev_num )
{
- mbg_snprintf( &s[n], max_len," / ASIC v%d.%02d)", _convert_asic_version_number( asic_version_num ) >> 8,
- ( _convert_asic_version_number( asic_version_num ) ) & 0xFF );
+ n += snprintf_safe( &s[n], max_len - n, "FW v%X.%02X",
+ fw_rev_num >> 8, fw_rev_num & 0xFF );
+ // Append a separator if ASIC version will follow.
+ if ( asic_version_num )
+ n += sn_cpy_str_safe( &s[n], max_len - n, " / " );
}
- else
- mbg_snprintf( &s[n], max_len,")" );
- return strlen(s);
+ if ( asic_version_num )
+ {
+ n += snprintf_safe( &s[n], max_len - n, "ASIC v%d.%02d",
+ _convert_asic_version_number( asic_version_num ) >> 8,
+ _convert_asic_version_number( asic_version_num ) & 0xFF );
+ }
+
+ if ( fw_rev_num || asic_version_num )
+ n += sn_cpy_str_safe( &s[n], max_len - n, ")" );
+
+out:
+ return _int_from_size_t( n );
} // mbg_str_dev_name
diff --git a/mbglib/common/mbgutil.h b/mbglib/common/mbgutil.h
index 8d1d748..494f346 100755
--- a/mbglib/common/mbgutil.h
+++ b/mbglib/common/mbgutil.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgutil.h 1.17 2012/10/15 10:08:32 martin REL_M $
+ * $Id: mbgutil.h 1.17.1.10 2016/07/15 14:10:05 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,19 @@
*
* -----------------------------------------------------------------------
* $Log: mbgutil.h $
+ * Revision 1.17.1.10 2016/07/15 14:10:05 martin
+ * Include timeutil.h.
+ * Revision 1.17.1.9 2015/08/27 16:17:53 martin
+ * Updated function prototypes.
+ * Revision 1.17.1.8 2014/05/27 11:32:47 martin
+ * Revision 1.17.1.7 2014/03/13 16:04:12 martin
+ * Revision 1.17.1.6 2014/03/13 15:45:37 martin
+ * Revision 1.17.1.5 2014/03/13 14:58:52Z martin
+ * Revision 1.17.1.4 2014/03/13 14:31:53Z martin
+ * Revision 1.17.1.3 2014/03/05 10:38:30Z martin
+ * Windows.h is now included in mbg_tgt.h.
+ * Revision 1.17.1.2 2013/10/23 10:40:53Z martin
+ * Revision 1.17.1.1 2013/10/22 10:06:01 martin
* Revision 1.17 2012/10/15 10:08:32 martin
* Include stdlib.h.
* Cleaned up handling of pragma pack().
@@ -55,6 +68,7 @@
/* Other headers to be included */
#include <mbg_tgt.h>
+#include <timeutil.h>
#include <use_pack.h>
#include <pcpsdefs.h>
#include <mbggeo.h>
@@ -70,7 +84,6 @@
#if defined( MBG_TGT_WIN32 )
- #include <windows.h>
#elif defined( MBG_TGT_LINUX )
@@ -132,38 +145,81 @@ extern "C" {
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
+ /**
+ * @brief Get the DLL/shared library's version code
+ *
+ * @return The version code at which the library was built
+ */
_MBG_API_ATTR int _MBG_API mbgutil_get_version( void ) ;
+
+ /**
+ * @brief Check the DLL/shared library's compatibility
+ *
+ * @param header_version Version code defined in the header file when the application is built
+ *
+ * @return ::MBG_SUCCESS if compatible, else ::MBG_ERR_LIB_NOT_COMPATIBLE
+ */
_MBG_API_ATTR int _MBG_API mbgutil_check_version( int header_version ) ;
- _MBG_API_ATTR int _MBG_API mbg_snprintf( char *s, size_t max_len, const char * fmt, ... ) ;
+
+ /**
+ * @brief A portable, safe implementation of snprintf()
+ *
+ * For a detailed description see ::vsnprintf_safe
+ *
+ * @param s pointer to the output buffer
+ * @param max_len size of the output buffer
+ * @param fmt format string according to subsequent parameters
+ * @param ... variable argument list according to the format string
+ *
+ * @return the number of characters written to the output buffer, except the terminating 0
+ *
+ * @see ::vsnprintf_safe
+ * @see ::snprintf_safe
+ */
+ _MBG_API_ATTR int __attribute__( ( format( printf, 3, 4 ) ) ) _MBG_API mbg_snprintf( char *s, size_t max_len, const char * fmt, ... ) ;
+
_MBG_API_ATTR int _MBG_API mbg_strncpy( char *s, size_t max_len, const char *src ) ;
+ /**
+ * @brief Write a character multiple times to a string buffer
+ *
+ * Append a terminating 0 to the buffer.
+ *
+ * @param s pointer to the output buffer
+ * @param max_len size of the output buffer
+ * @param c the character to write to the output buffer
+ * @param n the number of characters to write to the output buffer
+ *
+ * @return the number of characters written to the output buffer, except the terminating 0
+ */
_MBG_API_ATTR int _MBG_API mbg_strchar( char *s, size_t max_len, char c, size_t n ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_date_short( char *s, int max_len, int mday, int month ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_date( char *s, int max_len, int mday, int month, int year ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_time_short( char *s, int max_len, int hour, int min ) ;
+
+ _MBG_API_ATTR int _MBG_API mbg_str_date_short( char *s, int max_len, int mday, int month ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_date( char *s, int max_len, int mday, int month, int year ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_time_short( char *s, int max_len, int hour, int min ) ;
_MBG_API_ATTR int _MBG_API mbg_str_time( char *s, int max_len, int hour, int min, int sec ) ;
_MBG_API_ATTR int _MBG_API mbg_str_time_long( char *s, int max_len, int hour, int min, int sec, int sec100 ) ;
_MBG_API_ATTR int _MBG_API mbg_str_tm_gps_date_time( char *s, int max_len, const TM_GPS *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_date_short( char *s, int max_len, const PCPS_TIME *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_date( char *s, int max_len, const PCPS_TIME *pt ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_date_short( char *s, int max_len, const PCPS_TIME *pt ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_date( char *s, int max_len, const PCPS_TIME *pt ) ;
_MBG_API_ATTR int _MBG_API mbg_str_pcps_time_short( char *s, int max_len, const PCPS_TIME *pt ) ;
_MBG_API_ATTR int _MBG_API mbg_str_pcps_time( char *s, int max_len, const PCPS_TIME *pt ) ;
_MBG_API_ATTR int _MBG_API mbg_str_pcps_time_long( char *s, int max_len, const PCPS_TIME *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_date_time( char *s, int max_len, const PCPS_TIME *pt, const char *tz_str ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date( char *s, int max_len, uint32_t sec ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time( char *s, int max_len, uint32_t sec ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_utc( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_loc( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_frac( char *s, int max_len, uint32_t frac ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_offs( char *s, int max_len, const PCPS_HR_TIME *pt, const char *info ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_utc( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_loc( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_tstamp_raw( char *s, int max_len, const PCPS_TIME_STAMP *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_raw( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_ucap( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pos_dms( char *s, int max_len, const DMS *pdms, int prec ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_date_time( char *s, int max_len, const PCPS_TIME *pt, const char *tz_str ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date( char *s, int max_len, uint32_t sec ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time( char *s, int max_len, uint32_t sec ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_utc( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_date_time_loc( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_frac( char *s, int max_len, uint32_t frac ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_offs( char *s, int max_len, const PCPS_HR_TIME *pt, const char *info ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_utc( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_tstamp_loc( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_tstamp_raw( char *s, int max_len, const PCPS_TIME_STAMP *pt ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pcps_hr_time_raw( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_ucap( char *s, int max_len, const PCPS_HR_TIME *pt ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pos_dms( char *s, int max_len, const DMS *pdms, int prec ) ;
_MBG_API_ATTR int _MBG_API mbg_str_pos_alt( char *s, int max_len, double alt ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_pos( char *s, int max_len, const POS *ppos, int prec ) ;
- _MBG_API_ATTR int _MBG_API mbg_str_dev_name( char *s, int max_len, const char *short_name, uint16_t fw_rev_num, PCI_ASIC_VERSION asic_version_num ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_pos( char *s, int max_len, const POS *ppos, int prec ) ;
+ _MBG_API_ATTR int _MBG_API mbg_str_dev_name( char *s, int max_len, const char *short_name, uint16_t fw_rev_num, PCI_ASIC_VERSION asic_version_num ) ;
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/myutil.h b/mbglib/common/myutil.h
index f24dafe..0f0d817 100755
--- a/mbglib/common/myutil.h
+++ b/mbglib/common/myutil.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: myutil.h 1.15 2012/10/02 18:51:52 martin REL_M $
+ * $Id: myutil.h 1.20 2017/03/22 15:09:03 andre.hartmann TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,16 @@
*
* -----------------------------------------------------------------------
* $Log: myutil.h $
+ * Revision 1.20 2017/03/22 15:09:03 andre.hartmann
+ * added macros for lin. interpolation
+ * Revision 1.19 2017/01/27 12:24:08Z martin
+ * Moved STRINGIFY() macro to words.h.
+ * Revision 1.18 2014/10/20 12:30:38 martin
+ * Moved macro _isdigit() to words.h.
+ * Revision 1.17 2014/07/15 06:19:48Z andre
+ * added function _sgn( _x ), returns sign of _x
+ * Revision 1.16 2013/12/16 13:32:57Z martin
+ * Don't redefine MIN and MAX.
* Revision 1.15 2012/10/02 18:51:52 martin
* Updated handling of pragma pack().
* Revision 1.14 2011/02/16 14:02:35 martin
@@ -74,21 +84,6 @@
#endif
-// The two macros below can be used to define a constant string on the
-// compiler's command line, e.g. like -DVERSION_STRING="v1.0 BETA".
-// Source code like
-// const char version_string[] = VERSION_STRING;
-// may not work for every compiler since the double quotes
-// in VERSION_STRING may be removed when the definition is evaluated.
-// A proper solution is to use the STRINGIFY() macro below:
-// const char version_string[] = STRINGIFY( VERSION_STRING );
-// The XSTRINGIFY() macro is simply a helper macro which should not
-// be used alone.
-#define STRINGIFY(x) XSTRINGIFY(x)
-#define XSTRINGIFY(x) #x
-
-
-
#if MBG_TGT_HAS_64BIT_TYPES
#define _frac( _x ) ( ( (_x) == 0.0 ) ? 0.0 : ( (_x) - (double) ( (int64_t) (_x) ) ) )
#else
@@ -96,12 +91,16 @@
#endif
-#define _isdigit( _c ) ( (_c) >= '0' && (_c) <= '9' )
-
#define _eos( _s ) ( &(_s)[strlen( _s )] )
-#define MIN( _x, _y ) ( ( (_x) < (_y) ) ? (_x) : (_y) )
-#define MAX( _x, _y ) ( ( (_x) > (_y) ) ? (_x) : (_y) )
+#if !defined( MIN )
+ #define MIN( _x, _y ) ( ( (_x) < (_y) ) ? (_x) : (_y) )
+#endif
+
+#if !defined( MAX )
+ #define MAX( _x, _y ) ( ( (_x) > (_y) ) ? (_x) : (_y) )
+#endif
+
#define SWAP( _x, _y ) { temp = (_x); (_x) = (_y); (_y) = temp; }
#define SQR( _x ) ( (_x) * (_x) )
@@ -160,6 +159,14 @@ typedef union
#define _is_supported( _i, _msk ) \
( ( (_msk) & _idx_bit( _i ) ) != 0 )
+// return the sign of a number
+#define _sgn( _x ) ( ( ( _x ) < 0 ) ? -1 : 1 )
+
+
+// macro for linear interpolation y = _m * x + _b between two points ( X1; Y1 ), ( X2; Y2 )
+#define _m( _Y1, _X1, _Y2, _X2 ) ( ( _Y2 -_Y1 ) / ( _X2 -_X1 ) )
+#define _b( _Y1, _X1, _Y2, _X2 ) ( ( ( _Y1 * _X2 ) - ( _Y2 * _X1 ) ) / ( _X2 -_X1 ) )
+
/*
* The macro below copies a string, taking care not to
diff --git a/mbglib/common/ntp_shm.c b/mbglib/common/ntp_shm.c
index 42d836a..1fe9779 100755
--- a/mbglib/common/ntp_shm.c
+++ b/mbglib/common/ntp_shm.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: ntp_shm.c 1.1 2012/05/29 09:54:15 martin REL_M $
+ * $Id: ntp_shm.c 1.1.1.1 2013/07/23 16:10:35 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,7 @@
*
* -----------------------------------------------------------------------
* $Log: ntp_shm.c $
+ * Revision 1.1.1.1 2013/07/23 16:10:35 martin
* Revision 1.1 2012/05/29 09:54:15 martin
* Initial revision.
*
@@ -24,9 +25,6 @@
#include <string.h>
-//##+++++++++++
-extern void mbg_log( int lvl, const char *fmt, ... );
-
/*HDR*/
struct shmTime *getShmTime( int unit )
@@ -38,7 +36,7 @@ struct shmTime *getShmTime( int unit )
if ( shmid == -1 )
{
- mbg_log( LOG_ERR, "shmget %i failed: %s", unit, strerror( errno ) );
+ syslog( LOG_ERR, "shmget %i failed: %s", unit, strerror( errno ) );
return NULL;
}
@@ -47,7 +45,7 @@ struct shmTime *getShmTime( int unit )
if ( (long) p == -1L )
{
- mbg_log( LOG_ERR, "shmat %i failed: %s", unit, strerror( errno ) );
+ syslog( LOG_ERR, "shmat %i failed: %s", unit, strerror( errno ) );
return NULL;
}
@@ -70,7 +68,7 @@ int ntpshm_init( struct shmTime **shmTime, int n_units )
if ( p == NULL )
{
- mbg_log( LOG_WARNING, "** Failed to initialize NTP SHM unit %i", i );
+ syslog( LOG_WARNING, "** Failed to initialize NTP SHM unit %i", i );
ret_val = -1;
continue;
}
@@ -81,7 +79,7 @@ int ntpshm_init( struct shmTime **shmTime, int n_units )
p->precision = -5; /* initially 0.5 sec */
p->nsamples = 3; /* stages of median filter */
- mbg_log( LOG_INFO, "NTP SHM unit %i initialized successfully", i );
+ syslog( LOG_INFO, "NTP SHM unit %i initialized successfully", i );
}
return ret_val;
diff --git a/mbglib/common/ntp_shm.h b/mbglib/common/ntp_shm.h
index 270d71e..0589cfe 100755
--- a/mbglib/common/ntp_shm.h
+++ b/mbglib/common/ntp_shm.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: ntp_shm.h 1.2 2013/01/02 10:23:41 daniel REL_M $
+ * $Id: ntp_shm.h 1.2.2.2 2014/07/30 10:20:38 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,8 +10,10 @@
*
* -----------------------------------------------------------------------
* $Log: ntp_shm.h $
- * Revision 1.2 2013/01/02 10:23:41 daniel
- * Added nsec support.
+ * Revision 1.2.2.2 2014/07/30 10:20:38 martin
+ * Doxygen fixes.
+ * Revision 1.2.2.1 2013/12/12 11:28:35 martin
+ * Doxygen stuff.
* Revision 1.2 2013/01/02 10:23:41 daniel
* Added nsec support
* Revision 1.1 2012/05/29 09:54:15 martin
@@ -51,12 +53,15 @@ extern "C" {
/**
* @defgroup group_ntp_defs NTP interface definitions
*
- * @Note These definitions have been copied from the NTP source code (http://www.ntp.org)
+ * @note These definitions have been copied from the NTP source code (http://www.ntp.org)
*
* @{ */
-/** @brief Structure of NTP's shared memory segment */
-struct shmTime {
+/**
+ * @brief Structure of NTP's shared memory segment
+ */
+struct shmTime
+{
int mode; /* 0 - if valid set
* use values,
* clear valid
@@ -71,7 +76,7 @@ struct shmTime {
int clockTimeStampUSec; /* external clock */
time_t receiveTimeStampSec; /* internal clock, when external value was received */
int receiveTimeStampUSec; /* internal clock, when external value was received */
- int leap;
+ int leap; ///< see @ref NTP_LEAP_BITS
int precision;
int nsamples;
int valid;
@@ -80,18 +85,33 @@ struct shmTime {
int dummy[8];
};
-/** @brief codes used with struct shmTime::leap */
+/**
+ * @defgroup NTP_LEAP_BITS NTP Leap Bits
+ *
+ * @note This describes NTP leap bits
+ *
+ * @{ */
+
#define LEAP_NOWARNING 0x0 /**< normal, no leap second warning */
#define LEAP_ADDSECOND 0x1 /**< last minute of day has 61 seconds */
#define LEAP_DELSECOND 0x2 /**< last minute of day has 59 seconds */
#define LEAP_NOTINSYNC 0x3 /**< overload, clock is free running */
-#define NTPD_BASE 0x4e545030 /* "NTP0" */
+/** @} defgroup NTP_LEAP_BITS */
+
-#define MAX_SHM_REFCLOCKS 4
+/**
+ * @brief Number of units (refclocks) supported by the SMH segment
+ */
+#define MAX_SHM_REFCLOCKS 4
-/** @} group_ntp_defs */
+/**
+ * @brief Basic SHM unit identifier (unit 0)
+ */
+#define NTPD_BASE 0x4e545030 ///< "NTP0"
+
+/** @} defgroup group_ntp_defs */
diff --git a/mbglib/common/parmgps.c b/mbglib/common/parmgps.c
deleted file mode 100755
index 44e620b..0000000
--- a/mbglib/common/parmgps.c
+++ /dev/null
@@ -1,242 +0,0 @@
-
-/**************************************************************************
- *
- * $Id: parmgps.c 1.5 2008/10/21 10:47:26 martin REL_M $
- *
- * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
- *
- * Description:
- * Functions to handle/convert Meinberg GPS specific parameters.
- *
- * -----------------------------------------------------------------------
- * $Log: parmgps.c $
- * Revision 1.5 2008/10/21 10:47:26 martin
- * Renamed check_port_info() to check_valid_port_info()
- * to avoid naming conflicts.
- * Revision 1.4 2008/09/15 14:11:25 martin
- * New function check_port_info() which returns a bit mask indicating
- * which fields of a PORT_SETTINGS structure are not valid.
- * This is based on code taken from valid_port_info(), which now calls
- * check_port_info() and returns a value compatible to the earlier version.
- * Revision 1.3 2004/11/09 14:21:36 martin
- * Redefined some data types using C99 fixed-size definitions.
- * Revision 1.2 2002/02/19 13:30:23Z MARTIN
- * Bug fix in port_settings_from_port_parm_mode().
- * Revision 1.1 2002/01/30 10:30:26 MARTIN
- * Initial revision
- *
- **************************************************************************/
-
-#define _PARMGPS
- #include <parmgps.h>
-#undef _PARMGPS
-
-#include <myutil.h>
-#include <string.h>
-
-
-
-/*HDR*/
-int get_str_idx( const char *search,
- const char *str_table[],
- int n_entries )
-{
- int i;
-
- for ( i = 0; i < n_entries; i++ )
- if ( strcmp( search, str_table[i] ) == 0 )
- return i;
-
- return -1;
-
-} // get_str_idx
-
-
-
-/*HDR*/
-int get_baud_rate_idx( BAUD_RATE baud_rate )
-{
- int i;
-
- for ( i = 0; i < N_MBG_BAUD_RATES; i++ )
- if ( baud_rate == mbg_baud_rate[i] )
- return i;
-
- return -1;
-
-} // get_baud_rate_idx
-
-
-
-/*HDR*/
-int get_framing_idx( const char *framing )
-{
- return get_str_idx( framing, mbg_framing_str, N_MBG_FRAMINGS );
-
-} // get_framing_idx
-
-
-
-/*HDR*/
-void port_settings_from_port_parm_mode(
- PORT_SETTINGS *p_ps,
- uint8_t pp_mode,
- int str_type_cap
- )
-{
- if ( pp_mode >= STR_UCAP )
- {
- p_ps->str_type = str_type_cap;
- p_ps->mode = ( pp_mode == STR_UCAP ) ? STR_AUTO : STR_ON_REQ;
- }
- else
- {
- p_ps->str_type = 0;
- p_ps->mode = pp_mode;
- }
-
-} // port_settings_from_port_parm_mode
-
-
-
-/*HDR*/
-void port_parm_mode_from_port_settings(
- uint8_t *pp_mode,
- const PORT_SETTINGS *p_ps,
- int str_type_cap
- )
-{
- if ( p_ps->str_type == str_type_cap )
- *pp_mode = ( p_ps->mode == STR_ON_REQ ) ? STR_UCAP_REQ : STR_UCAP;
- else
- *pp_mode = p_ps->mode;
-
-} // port_parm_mode_from_port_settings
-
-
-
-/*HDR*/
-void port_settings_from_port_parm(
- PORT_SETTINGS *p_ps,
- int port_num,
- const PORT_PARM *p_pp,
- int cap_str_idx
-)
-{
- p_ps->parm = p_pp->com[port_num];
-
- port_settings_from_port_parm_mode( p_ps, p_pp->mode[port_num],
- cap_str_idx );
-
-} // port_info_from_port_parm
-
-
-
-/*HDR*/
-void port_parm_from_port_settings(
- PORT_PARM *p_pp,
- int port_num,
- const PORT_SETTINGS *p_ps,
- int cap_str_idx
-)
-{
- p_pp->com[port_num] = p_ps->parm;
-
- port_parm_mode_from_port_settings( &p_pp->mode[port_num],
- p_ps, cap_str_idx );
-
-} // port_parm_from_port_settings
-
-
-
-/*HDR*/
-int check_valid_port_info( const PORT_INFO *p_pi,
- const STR_TYPE_INFO_IDX str_type_info_idx[],
- int n_str_type )
-
-{
- const PORT_SETTINGS *p_ps = &p_pi->port_settings;
- int idx;
- int flags = 0;
-
-
- if ( p_pi->supp_baud_rates & ~_mask( N_MBG_BAUD_RATES ) )
- flags |= MBG_PS_MSK_BAUD_RATE_OVR_SW; // dev. supports more baud rates than driver
-
- idx = get_baud_rate_idx( p_ps->parm.baud_rate );
-
- if ( !_inrange( idx, 0, N_MBG_BAUD_RATES ) ||
- !_is_supported( idx, p_pi->supp_baud_rates ) )
- flags |= MBG_PS_MSK_BAUD_RATE;
-
-
- if ( p_pi->supp_framings & ~_mask( N_MBG_FRAMINGS ) )
- flags |= MBG_PS_MSK_FRAMING_OVR_SW; // dev. supports more framings than driver
-
- idx = get_framing_idx( p_ps->parm.framing );
-
- if ( !_inrange( idx, 0, N_MBG_FRAMINGS ) ||
- !_is_supported( idx, p_pi->supp_framings ) )
- flags |= MBG_PS_MSK_FRAMING;
-
-
- if ( p_ps->parm.handshake >= N_COM_HS )
- flags |= MBG_PS_MSK_HS_OVR_SW; // handshake index exceeds max.
-
- if ( p_ps->parm.handshake != HS_NONE ) // currently no device supports any handshake
- flags |= MBG_PS_MSK_HS; // handshake mode not supp. by dev.
-
-
- if ( p_pi->supp_str_types & ~_mask( n_str_type ) )
- flags |= MBG_PS_MSK_STR_TYPE_OVR_SW; // firmware error: more string types supported than reported
-
- idx = p_ps->str_type;
-
- if ( idx >= n_str_type )
- flags |= MBG_PS_MSK_STR_TYPE_OVR_DEV; // string type index exceeds max.
- else
- {
- if ( !_is_supported( idx, p_pi->supp_str_types ) )
- flags |= MBG_PS_MSK_STR_TYPE; // string type not supported by this port
- else
- {
- // Use the str_type index to get the supported output mode mask
- // from the string type info table. This is required to check
- // whether the selected mode is supported by the selected
- // string type.
- ulong supp_modes = str_type_info_idx[idx].str_type_info.supp_modes;
-
- if ( supp_modes & ~_mask( N_STR_MODE ) )
- flags |= MBG_PS_MSK_STR_MODE_OVR_SW; // dev. supports more string modes than driver
-
- idx = p_ps->mode;
-
- if ( idx >= N_STR_MODE ) // mode is always >= 0
- flags |= MBG_PS_MSK_STR_MODE_OVR_SW; // string mode index exceeds max.
- else
- if ( !_is_supported( idx, supp_modes ) )
- flags |= MBG_PS_MSK_STR_MODE; // string mode not supp. by this string type and port
- }
- }
-
-
- if ( p_ps->flags != 0 ) /* currently always 0 */
- flags |= MBG_PS_MSK_FLAGS_OVR_SW | MBG_PS_MSK_FLAGS;
-
-
- return flags;
-
-} // check_valid_port_info
-
-
-
-/*HDR*/
-int valid_port_info( const PORT_INFO *p_pi,
- const STR_TYPE_INFO_IDX str_type_info_idx[],
- int n_str_type )
-{
- return check_valid_port_info( p_pi, str_type_info_idx, n_str_type ) == 0;
-
-} // valid_port_info
-
-
diff --git a/mbglib/common/parmgps.h b/mbglib/common/parmgps.h
deleted file mode 100755
index 5ff32c8..0000000
--- a/mbglib/common/parmgps.h
+++ /dev/null
@@ -1,142 +0,0 @@
-
-/**************************************************************************
- *
- * $Id: parmgps.h 1.8 2012/10/15 10:06:37 martin REL_M $
- *
- * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
- *
- * Description:
- * Definitions and prototypes for parmgps.c.
- *
- * -----------------------------------------------------------------------
- * $Log: parmgps.h $
- * Revision 1.8 2012/10/15 10:06:37 martin
- * Cleaned up handling of pragma pack().
- * Revision 1.7 2011/02/16 10:12:13 martin
- * Fixed macro syntax for _setup_default_receiver_info_gps().
- * Revision 1.6 2008/10/21 10:41:09Z martin
- * Renamed check_port_info() to check_valid_port_info()
- * to avoid naming conflicts.
- * Revision 1.5 2008/09/10 16:22:32 martin
- * Updated function prototypes.
- * Revision 1.4 2004/11/09 14:22:34 martin
- * Updated function prototypes.
- * Revision 1.3 2004/05/19 07:50:16Z martin
- * Use symbolic constant as initializer.
- * Revision 1.2 2004/04/14 09:21:23Z martin
- * Pack structures 1 byte aligned.
- * Revision 1.1 2002/01/30 10:33:38Z MARTIN
- * Initial revision
- *
- **************************************************************************/
-
-#ifndef _PARMGPS_H
-#define _PARMGPS_H
-
-
-/* Other headers to be included */
-
-#include <gpsdefs.h>
-#include <use_pack.h>
-
-
-#ifdef _PARMGPS
- #define _ext
- #define _DO_INIT
-#else
- #define _ext extern
-#endif
-
-
-/* Start of header body */
-
-#if defined( _USE_PACK )
- #pragma pack( 1 ) // set byte alignment
- #define _USING_BYTE_ALIGNMENT
-#endif
-
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-
-#define DEFAULT_N_STR_TYPE_GPS 2
-
-#define DEFAULT_SUPP_STR_TYPES_GPS \
- ( ( 1UL << DEFAULT_N_STR_TYPE_GPS ) - 1 )
-
-
-/*
- * The macro below can be used to initialize a
- * RECEIVER_INFO structure for old GPS receiver models
- * which don't supply that structure.
- *
- * Parameters: (RECEIVER_INFO *) _p
- */
-#define _setup_default_receiver_info_gps( _p ) \
-do \
-{ \
- memset( (_p), 0, sizeof( *(_p) ) ); \
- \
- (_p)->ticks_per_sec = DEFAULT_GPS_TICKS_PER_SEC; \
- (_p)->n_ucaps = 2; \
- (_p)->n_com_ports = DEFAULT_N_COM; \
- (_p)->n_str_type = DEFAULT_N_STR_TYPE_GPS; \
-} while ( 0 )
-
-
-_ext BAUD_RATE mbg_baud_rate[N_MBG_BAUD_RATES]
-#ifdef _DO_INIT
- = MBG_BAUD_RATES
-#endif
-;
-
-_ext const char *mbg_baud_str[N_MBG_BAUD_RATES]
-#ifdef _DO_INIT
- = MBG_BAUD_STRS
-#endif
-;
-
-_ext const char *mbg_framing_str[N_MBG_FRAMINGS]
-#ifdef _DO_INIT
- = MBG_FRAMING_STRS
-#endif
-;
-
-
-/* ----- function prototypes begin ----- */
-
-/* This section was generated automatically */
-/* by MAKEHDR, do not remove the comments. */
-
- int get_str_idx( const char *search, const char *str_table[], int n_entries ) ;
- int get_baud_rate_idx( BAUD_RATE baud_rate ) ;
- int get_framing_idx( const char *framing ) ;
- void port_settings_from_port_parm_mode( PORT_SETTINGS *p_ps, uint8_t pp_mode, int str_type_cap ) ;
- void port_parm_mode_from_port_settings( uint8_t *pp_mode, const PORT_SETTINGS *p_ps, int str_type_cap ) ;
- void port_settings_from_port_parm( PORT_SETTINGS *p_ps, int port_num, const PORT_PARM *p_pp, int cap_str_idx ) ;
- void port_parm_from_port_settings( PORT_PARM *p_pp, int port_num, const PORT_SETTINGS *p_ps, int cap_str_idx ) ;
- int check_valid_port_info( const PORT_INFO *p, const STR_TYPE_INFO_IDX str_type_info_idx[], int n_str_type ) ;
- int valid_port_info( const PORT_INFO *p, const STR_TYPE_INFO_IDX str_type_info_idx[], int n_str_type ) ;
-
-/* ----- function prototypes end ----- */
-
-
-#ifdef __cplusplus
-}
-#endif
-
-
-#if defined( _USING_BYTE_ALIGNMENT )
- #pragma pack() // set default alignment
- #undef _USING_BYTE_ALIGNMENT
-#endif
-
-/* End of header body */
-
-#undef _ext
-#undef _DO_INIT
-
-#endif /* _PARMGPS_H */
-
diff --git a/mbglib/common/parmpcps.c b/mbglib/common/parmpcps.c
deleted file mode 100755
index cd02754..0000000
--- a/mbglib/common/parmpcps.c
+++ /dev/null
@@ -1,115 +0,0 @@
-
-/**************************************************************************
- *
- * $Id: parmpcps.c 1.4 2004/11/09 14:24:15 martin REL_M $
- *
- * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
- *
- * Description:
- * Functions to handle/convert parameters used by Meinberg plug-in
- * radio clocks.
- *
- * -----------------------------------------------------------------------
- * $Log: parmpcps.c $
- * Revision 1.4 2004/11/09 14:24:15 martin
- * Redefined interface data types using C99 fixed-size definitions.
- * Revision 1.3 2003/04/17 10:43:35Z martin
- * Moved some definitions to parmpcps.h.
- * Removed some functions which are now in mbgdevio.c.
- * Revision 1.2 2002/03/25 09:03:43Z MARTIN
- * Fixed a bug where the wrong framing was configured for DCF77 clocks.
- * Revision 1.1 2002/02/19 14:00:19 MARTIN
- * Initial revision
- *
- **************************************************************************/
-
-#define _PARMPCPS
- #include <parmpcps.h>
-#undef _PARMPCPS
-
-#include <parmgps.h>
-#include <pcpsutil.h>
-#include <myutil.h>
-
-#include <string.h>
-
-
-static const int pcps_to_mbg_framing_tbl[N_PCPS_FR_DCF] =
-{
- MBG_FRAMING_8N1,
- MBG_FRAMING_7E2,
- MBG_FRAMING_8N2,
- MBG_FRAMING_8E1
-};
-
-
-
-/*HDR*/
-void port_info_from_pcps_serial(
- PORT_INFO_IDX *p_pii,
- PCPS_SERIAL pcps_serial,
- uint32_t supp_baud_rates
-)
-{
- PCPS_SER_PACK ser_pack;
- PORT_INFO *p_pi;
- PORT_SETTINGS *p_ps;
-
- ser_pack.pack = pcps_serial;
- pcps_unpack_serial( &ser_pack );
-
- p_pi = &p_pii[0].port_info;
- p_ps = &p_pi->port_settings;
-
- p_ps->parm.baud_rate = mbg_baud_rate[ser_pack.baud];
-
- _strncpy_0( p_ps->parm.framing,
- mbg_framing_str[pcps_to_mbg_framing_tbl[ser_pack.frame]] );
-
- p_ps->parm.handshake = HS_NONE;
-
- p_ps->str_type = 0;
- p_ps->mode = ser_pack.mode;
-
- p_pi->supp_baud_rates = supp_baud_rates;
- p_pi->supp_framings = DEFAULT_FRAMINGS_DCF;
- p_pi->supp_str_types = DEFAULT_SUPP_STR_TYPES_DCF;
-
-} // port_info_from_pcps_serial
-
-
-/*HDR*/
-void pcps_serial_from_port_info(
- PCPS_SERIAL *p,
- const PORT_INFO_IDX *p_pii
-)
-{
- PCPS_SER_PACK ser_pack;
- const PORT_INFO *p_pi = &p_pii[0].port_info;
- const PORT_SETTINGS *p_ps = &p_pi->port_settings;
- int framing_idx = get_framing_idx( p_ps->parm.framing );
- int i;
-
-
- ser_pack.baud = get_baud_rate_idx( p_ps->parm.baud_rate );
-
- // Translate the common framing index to the corresponding
- // number used with the old PCPS_SERIAL parameter.
- // This should always return a valid result since the
- // framing index is expected to be selected from
- // supported framings.
- for ( i = 0; i < N_PCPS_FR_DCF; i++ )
- if ( pcps_to_mbg_framing_tbl[i] == framing_idx )
- break;
-
- ser_pack.frame = i;
-
- ser_pack.mode = p_ps->mode;
-
- pcps_pack_serial( &ser_pack );
-
- *p = ser_pack.pack;
-
-} // pcps_serial_from_port_info
-
-
diff --git a/mbglib/common/parmpcps.h b/mbglib/common/parmpcps.h
deleted file mode 100755
index bc2f2bf..0000000
--- a/mbglib/common/parmpcps.h
+++ /dev/null
@@ -1,163 +0,0 @@
-
-/**************************************************************************
- *
- * $Id: parmpcps.h 1.8 2012/10/15 10:05:38 martin REL_M $
- *
- * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
- *
- * Description:
- * Definitions and prototypes for parmpcps.c.
- *
- * -----------------------------------------------------------------------
- * $Log: parmpcps.h $
- * Revision 1.8 2012/10/15 10:05:38 martin
- * Cleaned up handling of pragma pack().
- * Revision 1.7 2011/04/01 10:30:51 martin
- * Fixed macro syntax for _setup_default_receiver_info_dcf().
- * Revision 1.6 2011/02/16 10:13:12 martin
- * Fixed macro syntax for _setup_default_receiver_info_pcps().
- * Revision 1.5 2004/11/09 14:24:58Z martin
- * Updated function prototypes.
- * Revision 1.4 2004/05/19 07:52:25Z martin
- * Fixed macro setting default number of string types.
- * Revision 1.3 2004/04/14 09:21:44Z martin
- * Pack structures 1 byte aligned.
- * Revision 1.2 2003/04/17 10:42:46Z martin
- * Moved typedef RECEIVER_PORT_CFG to pcpsdev.h.
- * Moved some definitions from parmpcps.c here.
- * Removed some global variables.
- * Updated function prototypes.
- * Revision 1.1 2002/02/19 14:00:19Z MARTIN
- * Initial revision
- *
- **************************************************************************/
-
-#ifndef _PARMPCPS_H
-#define _PARMPCPS_H
-
-/* Other headers to be included */
-
-#include <pcpsdev.h>
-#include <use_pack.h>
-
-
-#ifdef _PARMPCPS
- #define _ext
- #define _DO_INIT
-#else
- #define _ext extern
-#endif
-
-
-/* Start of header body */
-
-#if defined( _USE_PACK )
- #pragma pack( 1 ) // set byte alignment
- #define _USING_BYTE_ALIGNMENT
-#endif
-
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-
-#define DEFAULT_BAUD_RATES_DCF \
-( \
- MBG_PORT_HAS_300 | \
- MBG_PORT_HAS_600 | \
- MBG_PORT_HAS_1200 | \
- MBG_PORT_HAS_2400 | \
- MBG_PORT_HAS_4800 | \
- MBG_PORT_HAS_9600 \
-)
-
-#define DEFAULT_BAUD_RATES_DCF_HS \
-( \
- MBG_PORT_HAS_300 | \
- MBG_PORT_HAS_600 | \
- MBG_PORT_HAS_1200 | \
- MBG_PORT_HAS_2400 | \
- MBG_PORT_HAS_4800 | \
- MBG_PORT_HAS_9600 | \
- MBG_PORT_HAS_19200 | \
- MBG_PORT_HAS_38400 \
-)
-
-
-#define DEFAULT_FRAMINGS_DCF \
-( \
- MBG_PORT_HAS_7E2 | \
- MBG_PORT_HAS_8N1 | \
- MBG_PORT_HAS_8N2 | \
- MBG_PORT_HAS_8E1 \
-)
-
-
-#define DEFAULT_N_STR_TYPE_DCF 1
-
-#define DEFAULT_SUPP_STR_TYPES_DCF \
- ( ( 1UL << DEFAULT_N_STR_TYPE_DCF ) - 1 )
-
-
-/*
- * The macro below can be used to initialize a
- * RECEIVER_INFO structure for DCF77 receivers
- * which don't supply that structure.
- *
- * Parameters: (RECEIVER_INFO *) _p
- */
-#define _setup_default_receiver_info_dcf( _p, _pdev ) \
-do \
-{ \
- memset( (_p), 0, sizeof( *(_p) ) ); \
- \
- (_p)->ticks_per_sec = DEFAULT_GPS_TICKS_PER_SEC; \
- (_p)->n_ucaps = 0; \
- (_p)->n_com_ports = _pcps_has_serial( _pdev ) ? 1 : 0; \
- (_p)->n_str_type = ( (_p)->n_com_ports != 0 ) ? \
- DEFAULT_N_STR_TYPE_DCF : 0; \
-} while ( 0 )
-
-
-#define DEFAULT_MAX_STR_TYPE 2 //##++ DEFAULT_N_STR_TYPE_GPS
-
-_ext STR_TYPE_INFO default_str_type_info[DEFAULT_MAX_STR_TYPE]
-#ifdef _DO_INIT
- = {
- { DEFAULT_STR_MODES, "Default Time String", "Time", 0 },
- { DEFAULT_STR_MODES_UCAP, "Capture String", "Cap", 0 }
- }
-#endif
-;
-
-
-
-/* ----- function prototypes begin ----- */
-
-/* This section was generated automatically */
-/* by MAKEHDR, do not remove the comments. */
-
- void port_info_from_pcps_serial( PORT_INFO_IDX *p_pii, PCPS_SERIAL pcps_serial, uint32_t supp_baud_rates ) ;
- void pcps_serial_from_port_info( PCPS_SERIAL *p, const PORT_INFO_IDX *p_pii ) ;
-
-/* ----- function prototypes end ----- */
-
-
-#ifdef __cplusplus
-}
-#endif
-
-
-#if defined( _USING_BYTE_ALIGNMENT )
- #pragma pack() // set default alignment
- #undef _USING_BYTE_ALIGNMENT
-#endif
-
-/* End of header body */
-
-
-#undef _ext
-#undef _DO_INIT
-
-#endif /* _PARMPCPS_H */
diff --git a/mbglib/common/pci_asic.h b/mbglib/common/pci_asic.h
index bf104f2..36f04af 100755
--- a/mbglib/common/pci_asic.h
+++ b/mbglib/common/pci_asic.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pci_asic.h 1.23 2013/06/26 15:57:07 martin TRASH $
+ * $Id: pci_asic.h 1.27 2017/04/25 11:36:30 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,7 +10,16 @@
*
* -----------------------------------------------------------------------
* $Log: pci_asic.h $
- * Revision 1.23 2013/06/26 15:57:07 martin
+ * Revision 1.27 2017/04/25 11:36:30 martin
+ * Renamed GRC181PEX to GNS181PEX.
+ * Revision 1.26 2016/09/15 14:55:02 martin
+ * Support GRC181PEX.
+ * Added doxgen comments.
+ * Revision 1.25 2014/10/17 11:38:39 martin
+ * Updated version info for GPS180PEX.
+ * Revision 1.24 2013/10/01 15:29:39 martin
+ * Updated version info for PTP270PEX.
+ * Revision 1.23 2013/06/26 15:57:07Z martin
* Support GLN180PEX.
* Revision 1.22 2011/10/05 09:46:12 martin
* Updated version info for GPS180PEX.
@@ -38,7 +47,7 @@
* Modified syntax of macro _convert_asic_version_number().
* Added macros to deal with the ASIC version number.
* Added definition PCI_ASIC_HAS_PGMB_IRQ.
- * Added ASIC revision numbers for PEX511, TCR511PEX, and GPS170PEX
+ * Added ASIC revision numbers for PEX511, TCR511PEX, and GPS170PEX
* which fix an IRQ bug with these cards.
* Added definitions for PTP270PEX, FRC511PEX, and TCR170PEX.
* Revision 1.12 2008/07/21 10:30:00Z martin
@@ -64,7 +73,7 @@
* Revision 1.4 2004/10/14 15:01:23 martin
* Added support for TCR167PCI.
* Revision 1.3 2003/05/13 14:38:55Z MARTIN
- * Added ushort fields to unions PCI_ASIC_REG and
+ * Added ushort fields to unions PCI_ASIC_REG and
* PCI_ASIC_ADDON_DATA.
* Revision 1.2 2003/04/03 10:56:38 martin
* Use unions for registers.
@@ -98,77 +107,140 @@
#define _USING_BYTE_ALIGNMENT
#endif
-
+/**
+ * @brief Set of PCI ASIC registers which are writeable once after power-up
+ **/
typedef struct
{
uint32_t cfg_class_rev_id;
uint16_t cfg_badr_0;
uint16_t cfg_dev_id;
+
} PCI_ASIC_CFG;
+/**
+ * @brief A PCI ASIC register as 32, 16, or 8 bit accessible union
+ */
typedef union
{
uint32_t ul;
uint16_t us[2];
uint8_t b[4];
+
} PCI_ASIC_REG;
+
+/**
+ * @brief A data type to hold the PCI ASIC version code
+ */
typedef uint32_t PCI_ASIC_VERSION;
+
#define _mbg_swab_asic_version( _p ) _mbg_swab32( _p )
+
+
+/**
+ * @brief A data type to hold the PCI ASIC feature flags mask
+ *
+ * @see @ref PCI_ASIC_FEATURE_MASKS
+ */
typedef uint32_t PCI_ASIC_FEATURES;
+
#define _mbg_swab_asic_features( _p ) _mbg_swab32( _p )
-#define PCI_ASIC_HAS_MM_IO 0x0001
-#define PCI_ASIC_HAS_PGMB_IRQ 0x0002
+/**
+ * @brief Bit masks used with ::PCI_ASIC_FEATURES
+ *
+ * @see ::PCI_ASIC_FEATURES
+ *
+ * @anchor PCI_ASIC_FEATURE_MASKS @{ */
+
+#define PCI_ASIC_HAS_MM_IO 0x0001 ///< The device supports memory mapped I/O
+#define PCI_ASIC_HAS_PGMB_IRQ 0x0002 ///< The device supports programmable interrupts (yet not used)
+
+/** @} anchor PCI_ASIC_FEATURE_MASKS */
+
+
+
+/**
+ * @brief The addon-data part of a PCI ASIC
+ */
typedef union
{
uint32_t ul[4];
uint16_t us[8];
uint8_t b[16];
+
} PCI_ASIC_ADDON_DATA;
+
+/**
+ * @brief Register layout of a PCI ASIC
+ */
typedef struct
{
- PCI_ASIC_CFG cfg; // writeable from add-on once after power-up
- PCI_ASIC_VERSION raw_version;
- PCI_ASIC_FEATURES features;
- PCI_ASIC_REG status_port;
- PCI_ASIC_REG control_status; // codes defined below
- PCI_ASIC_REG pci_data; // pass byte from PCI bus to add-on
- PCI_ASIC_REG reserved_1;
-
- PCI_ASIC_ADDON_DATA addon_data; // returns data from add-on to PCI bus
- PCI_ASIC_ADDON_DATA reserved_2; // currently not implemented
+ PCI_ASIC_CFG cfg; ///< Registers which are writeable from add-on once after power-up
+ PCI_ASIC_VERSION raw_version; ///< Raw version code
+ PCI_ASIC_FEATURES features; ///< PCI ASIC feature mask, see @ref PCI_ASIC_FEATURE_MASKS
+ PCI_ASIC_REG status_port; ///< The status port register
+ PCI_ASIC_REG control_status; ///< See @ref PCI_ASIC_CONTROL_STATUS_MASKS
+ PCI_ASIC_REG pci_data; ///< Register used to pass byte from PCI bus to add-on side
+ PCI_ASIC_REG reserved_1; ///< Currently not implemented / used
+
+ PCI_ASIC_ADDON_DATA addon_data; ///< Register set used to return data from add-on to PCI bus
+ PCI_ASIC_ADDON_DATA reserved_2; ///< Currently not implemented / used
+
} PCI_ASIC;
-// The following bits are used with the control_status register.
-// All other bits are reserved for future use.
-// The IRQ flag for the add-on side is set whenever data is
-// written to the cmd register. It is cleared if the add-on
-// microcontroller writes this bit back to the control_status
-// register. If the bit is set, the add-on signals /ADD_ON_IRQ
-// and ADD_ON_BUSY are asserted.
+/**
+ * @brief Bit masks used with ::PCI_ASIC::control_status
+ *
+ * @see ::PCI_ASIC
+ *
+ * @anchor PCI_ASIC_CONTROL_STATUS_MASKS @{ */
+
+/**
+ * @brief Add-on IRQ flag
+ *
+ * The IRQ flag for the add-on side is set whenever data is
+ * written to the cmd register. It is cleared if the add-on
+ * microcontroller writes this bit back to the control_status
+ * register. If the bit is set, the add-on signals /ADD_ON_IRQ
+ * and ADD_ON_BUSY are asserted.
+ */
#define PCI_ASIC_ADD_ON_IRQF 0x00000001UL
-// The IRQ flag for the PCI bus is set whenever the add-on
-// microcontroller asserts the ASIC's /PCI_IRQ line, or the
-// add-on microcontroller sets this bit to 1. It is cleared
-// if this bit is written back from the PCI side. If the bit
-// is set, an IRQ is asserted on the PCI bus.
+/**
+ * @brief PCI IRQ flag
+ *
+ * The IRQ flag for the PCI bus is set whenever the add-on
+ * microcontroller asserts the ASIC's /PCI_IRQ line, or the
+ * add-on microcontroller sets this bit to 1. It is cleared
+ * if this bit is written back from the PCI side. If the bit
+ * is set, an IRQ is asserted on the PCI bus.
+ */
#define PCI_ASIC_PCI_IRQF 0x00010000UL
+// NOTE All other bits are reserved for future use.
+
+/** @} anchor PCI_ASIC_CONTROL_STATUS_MASKS */
-// The ASIC's address decoder always decodes 8 bits, so
-// each device must request at least that number of
-// addresses from the PCI BIOS:
+
+
+/**
+ * @brief PCI address range
+ *
+ * The ASIC's address decoder always decodes 8 bits, so
+ * each device must request at least this number of
+ * addresses from the PCI BIOS.
+ */
#define PCI_ASIC_ADDR_RANGE 0x100U
@@ -227,34 +299,42 @@ typedef struct
_hilo_16( PCI_DEV_TCR511PCI ) \
}
-/*
- Handling of the version numbers of the PCI interface
- chips has changed between the ASICs used for standard PCI
- and the EPLDs used to configure the PEX8311 chip
- for a specific device.
- The macro below can be used to convert both types
- of version number into the same format so that the
- version numbers can be handled in the same way:
-*/
+
+/**
+ * @brief Version number conversion macro
+ *
+ * Handling of the version numbers of the PCI interface
+ * chips has changed between the ASICs used for standard PCI
+ * and the EPLDs used to configure the PEX8311 chip
+ * for a specific device.
+ *
+ * This macro can be used to convert both types of
+ * version number into the same format so that the
+ * version numbers can be handled in the same way
+ */
#define _convert_asic_version_number( _n ) \
( ( (_n) < 0x100 ) ? ( (_n) << 8 ) : (_n) )
-/*
- * Macros to extract the major and minor part of an ASIC version number */
-
+/**
+ * @brief Extract the major part of an ASIC version number
+ */
#define _pcps_asic_version_major( _v ) \
( ( (_v) >> 8 ) & 0xFF )
+
+/**
+ * @brief Extract the minor part of an ASIC version number
+ */
#define _pcps_asic_version_minor( _v ) \
( (_v) & 0xFF )
-/*
- * Macros to check whether a version number is correct
- * and matches a required minimum version
+
+/**
+ * @brief Check whether a version number is correct and matches a required minimum version
*/
#define _pcps_asic_version_greater_equal( _v, _v_major, _v_minor ) \
( \
@@ -263,35 +343,44 @@ typedef struct
)
-/*
- The low byte of the converted version number is handled
- as a minor version, whereas the remaining upper bytes are
- interpreted as a major number which may be specific
- for a device.
-*/
-enum
+
+/**
+ * @brief ASIC major version numbers
+ *
+ * @see @ref PCI_ASIC_MINOR_VERSION_NUMBERS
+ */
+enum PCI_ASIC_MAJOR_VERSION_NUMBERS
{
- PCI_ASIC_MAJOR_PCI_0, // PCI ASIC with CRC bug
- PCI_ASIC_MAJOR_PCI_1, // fixed version of PCI ASIC
- PCI_ASIC_MAJOR_PEX511, // PEX EPLD for PEX511
- PCI_ASIC_MAJOR_GPS170PEX, // PEX EPLD for GPS170PEX
- PCI_ASIC_MAJOR_TCR511PEX, // PEX EPLD for TCR511PEX
- PCI_ASIC_MAJOR_PTP270PEX, // PEX EPLD for PTP270PEX
- PCI_ASIC_MAJOR_FRC511PEX, // PEX EPLD for FRC511PEX
- PCI_ASIC_MAJOR_TCR170PEX, // PEX EPLD for TCR170PEX
- PCI_ASIC_MAJOR_GPS180PEX, // PEX EPLD for GPS180PEX
- PCI_ASIC_MAJOR_TCR180PEX, // PEX EPLD for TCR180PEX
- PCI_ASIC_MAJOR_PZF180PEX, // PEX EPLD for PZF180PEX
- PCI_ASIC_MAJOR_GLN180PEX, // PEX EPLD for GLN180PEX
- N_PCI_ASIC_MAJOR // the number of known codes
+ PCI_ASIC_MAJOR_PCI_0, ///< PCI ASIC with CRC bug
+ PCI_ASIC_MAJOR_PCI_1, ///< fixed version of PCI ASIC
+ PCI_ASIC_MAJOR_PEX511, ///< PEX EPLD for PEX511
+ PCI_ASIC_MAJOR_GPS170PEX, ///< PEX EPLD for GPS170PEX
+ PCI_ASIC_MAJOR_TCR511PEX, ///< PEX EPLD for TCR511PEX
+ PCI_ASIC_MAJOR_PTP270PEX, ///< PEX EPLD for PTP270PEX
+ PCI_ASIC_MAJOR_FRC511PEX, ///< PEX EPLD for FRC511PEX
+ PCI_ASIC_MAJOR_TCR170PEX, ///< PEX EPLD for TCR170PEX
+ PCI_ASIC_MAJOR_GPS180PEX, ///< PEX EPLD for GPS180PEX/GPS180AMC
+ PCI_ASIC_MAJOR_TCR180PEX, ///< PEX EPLD for TCR180PEX
+ PCI_ASIC_MAJOR_PZF180PEX, ///< PEX EPLD for PZF180PEX
+ PCI_ASIC_MAJOR_GLN180PEX, ///< PEX EPLD for GLN180PEX
+ PCI_ASIC_MAJOR_GNS181PEX, ///< PEX EPLD for GNS181PEX
+ N_PCI_ASIC_MAJOR ///< the number of known codes
};
-/*
- The minor number increases when a new EPLD image is released.
- At least EPLD images with the following "required minor" numbers
- should be installed for proper operation. The "current minor"
- numbers can be used to check if a newer EPLD image is available:
-*/
+
+
+/**
+ * @brief ASIC minor version definitions
+ *
+ * The minor number increases when a new EPLD image is released.
+ * At least EPLD images with the defined "required minor" numbers
+ * should be installed for proper operation. The "current minor"
+ * numbers can be used to check if a newer EPLD image is available.
+ *
+ * @see ::PCI_ASIC_MAJOR_VERSION_NUMBERS
+ *
+ * @anchor PCI_ASIC_MINOR_VERSION_NUMBERS @{ */
+
#define PCI_ASIC_CURRENT_MINOR_PEX511 0x04
#define PCI_ASIC_REQUIRED_MINOR_PEX511 0x03
#define PCI_ASIC_FIX_HRT_MINOR_PEX511 0x04 // increases HRT accuracy
@@ -309,8 +398,11 @@ enum
// 0x04 // EPLD sources shared with PEX511 0x04
#define PCI_ASIC_FIX_IRQ_MINOR_TCR511PEX 0x03 // fixes IRQ problem, increases HRT accuracy
-#define PCI_ASIC_CURRENT_MINOR_PTP270PEX 0x02
+#define PCI_ASIC_CURRENT_MINOR_PTP270PEX 0x05
#define PCI_ASIC_REQUIRED_MINOR_PTP270PEX 0x01
+// 0x05 // ...
+// 0x04 // ...
+// 0x03 // ...
// 0x02 // increased accuracy of IRIG DCLS slopes
// 0x01 // supports inversion of ucap slopes
@@ -322,13 +414,14 @@ enum
#define PCI_ASIC_FIX_EE_ACCESS_TCR170PEX 0x02 // fixes EE access problem after reset
#define PCI_ASIC_FIX_FO_IN_LEVEL_TCR170PEX 0x03 // correct polarity for fiber optic input
-#define PCI_ASIC_CURRENT_MINOR_GPS180PEX 0x05
+#define PCI_ASIC_CURRENT_MINOR_GPS180PEX 0x06
#define PCI_ASIC_REQUIRED_MINOR_GPS180PEX 0x01
// 0x01 // updated VHDL compiler and associated PCI primitives
// 0x02 // I/O using 3.3V LVTTL
// 0x03 // GPS TIC pulse len now 1 sample clock
// 0x04 // Enabled PCI IRQ line which had unintentionally been disabled earlier
// 0x05 // Increased accuracy of synthesizer output
+// 0x06 // T0 AUX Capture used by firmware v2.0x
#define PCI_ASIC_CURRENT_MINOR_TCR180PEX 0x00
#define PCI_ASIC_REQUIRED_MINOR_TCR180PEX 0x00
@@ -339,14 +432,35 @@ enum
#define PCI_ASIC_CURRENT_MINOR_GLN180PEX 0x00
#define PCI_ASIC_REQUIRED_MINOR_GLN180PEX 0x00
+#define PCI_ASIC_CURRENT_MINOR_GNS181PEX 0x00
+#define PCI_ASIC_REQUIRED_MINOR_GNS181PEX 0x00
+
+/** @} anchor PCI_ASIC_MINOR_VERSION_NUMBERS */
+
+
+
+/**
+ * @brief A structure holding version information for a specific device
+ *
+ * @see ::DEFAULT_PCI_ASIC_VERSION_INFO_TABLE
+ */
typedef struct
{
unsigned int dev_type_num;
unsigned int major;
unsigned int current_minor;
unsigned int required_minor;
+
} PCI_ASIC_VERSION_INFO;
+
+/**
+ * @brief An initializer for a table of ASIC version information for all known devices
+ *
+ * @note GPS180AMC uses the same ASIC as GPS180PEX
+ *
+ * @see ::PCI_ASIC_VERSION_INFO
+ */
#define DEFAULT_PCI_ASIC_VERSION_INFO_TABLE \
{ \
{ PCPS_TYPE_PEX511, PCI_ASIC_MAJOR_PEX511, PCI_ASIC_CURRENT_MINOR_PEX511, PCI_ASIC_REQUIRED_MINOR_PEX511 }, \
@@ -359,6 +473,8 @@ typedef struct
{ PCPS_TYPE_TCR180PEX, PCI_ASIC_MAJOR_TCR180PEX, PCI_ASIC_CURRENT_MINOR_TCR180PEX, PCI_ASIC_REQUIRED_MINOR_TCR180PEX }, \
{ PCPS_TYPE_PZF180PEX, PCI_ASIC_MAJOR_PZF180PEX, PCI_ASIC_CURRENT_MINOR_PZF180PEX, PCI_ASIC_REQUIRED_MINOR_PZF180PEX }, \
{ PCPS_TYPE_GLN180PEX, PCI_ASIC_MAJOR_GLN180PEX, PCI_ASIC_CURRENT_MINOR_GLN180PEX, PCI_ASIC_REQUIRED_MINOR_GLN180PEX }, \
+ { PCPS_TYPE_GPS180AMC, PCI_ASIC_MAJOR_GPS180PEX, PCI_ASIC_CURRENT_MINOR_GPS180PEX, PCI_ASIC_REQUIRED_MINOR_GPS180PEX }, \
+ { PCPS_TYPE_GNS181PEX, PCI_ASIC_MAJOR_GNS181PEX, PCI_ASIC_CURRENT_MINOR_GNS181PEX, PCI_ASIC_REQUIRED_MINOR_GNS181PEX }, \
{ 0 } \
}
diff --git a/mbglib/common/pcidefs.h b/mbglib/common/pcidefs.h
index ed365d2..4a3baed 100755
--- a/mbglib/common/pcidefs.h
+++ b/mbglib/common/pcidefs.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcidefs.h 1.7 2008/06/09 10:43:09 martin REL_M $
+ * $Id: pcidefs.h 1.8 2013/09/26 09:26:34 martin REL_M $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,7 +10,11 @@
*
* -----------------------------------------------------------------------
* $Log: pcidefs.h $
- * Revision 1.7 2008/06/09 10:43:09 martin
+ * Revision 1.8 2013/09/26 09:26:34 martin
+ * Added num of addr regs for PCI CFG header type 0x01.
+ * Re-ordered definition of PCI vendor IDs based on numerical code.
+ * Added some PCI vendor IDs.
+ * Revision 1.7 2008/06/09 10:43:09Z martin
* Added PCI_CMD_ENB_MEM_ACC code.
* Revision 1.6 2005/09/19 13:06:15Z martin
* Added definition for number of base address registers.
@@ -170,7 +174,8 @@ typedef struct
#define PCI_CS_MIN_GNT 0x3E
#define PCI_CS_MAX_LAT 0x3F
-#define PCI_CS_N_BASE_ADDRESS 6 /* max number of address spaces */
+#define PCI_CS_N_BASE_ADDRESS 6 /* num of badr regs for header type 0x00 */
+#define PCI_CS_N_BASE_ADDRESS_01 2 /* num of badr regs for header type 0x01 */
#define PCI_CMD_ENB_IO_ACC 0x01
@@ -213,20 +218,26 @@ typedef struct
-// some known vendor IDs, in alphabetical order:
+// some known vendor IDs, in numerical order:
-#define PCI_VENDOR_3COM 0x10B7
-#define PCI_VENDOR_ADAPTEC_1 0x9004
-#define PCI_VENDOR_ADAPTEC_2 0x9005
-#define PCI_VENDOR_AMCC 0x10E8
-#define PCI_VENDOR_AMD 0x1022
#define PCI_VENDOR_ASUS 0x1000
+#define PCI_VENDOR_ATI 0x1002
#define PCI_VENDOR_CIRRUS_LOGIC 0x1013
-#define PCI_VENDOR_ELSA 0x5333
#define PCI_VENDOR_IBM 0x1014
-#define PCI_VENDOR_INTEL 0x8086
+#define PCI_VENDOR_AMD 0x1022
#define PCI_VENDOR_MATROX 0x102B
+#define PCI_VENDOR_NEC 0x1033
+#define PCI_VENDOR_TEXAS_INSTR 0x104C
+#define PCI_VENDOR_PLX 0x10B5
+#define PCI_VENDOR_3COM 0x10B7
+#define PCI_VENDOR_AMCC 0x10E8
+#define PCI_VENDOR_REALTEK 0x10EC
#define PCI_VENDOR_MEINBERG 0x1360
+#define PCI_VENDOR_JMICRON 0x197B
+#define PCI_VENDOR_ELSA 0x5333
+#define PCI_VENDOR_INTEL 0x8086
+#define PCI_VENDOR_ADAPTEC_1 0x9004
+#define PCI_VENDOR_ADAPTEC_2 0x9005
/* End of header body */
diff --git a/mbglib/common/pcpsdefs.h b/mbglib/common/pcpsdefs.h
index e301697..a0fa80e 100755
--- a/mbglib/common/pcpsdefs.h
+++ b/mbglib/common/pcpsdefs.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcpsdefs.h 1.51 2013/06/25 09:51:39 martin TRASH $
+ * $Id: pcpsdefs.h 1.61 2017/04/25 11:38:38 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,37 @@
*
* -----------------------------------------------------------------------
* $Log: pcpsdefs.h $
+ * Revision 1.61 2017/04/25 11:38:38 martin
+ * Renamed GRC181PEX to GNS181PEX.
+ * Revision 1.60 2017/03/17 12:00:05 martin
+ * Moved definitions of PCPS_HRT_FRAC_CONVERSION_TYPE,
+ * PCPS_HRT_BIN_FRAC_SCALE, and PCPS_HRT_FRAC_SCALE_FMT
+ * to cfg_hlp.h.
+ * Revision 1.59 2017/01/27 08:11:19 martin
+ * Fixed macro syntax.
+ * Revision 1.58 2016/11/08 16:42:52 martin
+ * New GPS cmd codes PC_GPS_XFEATURE_BUFFER and PC_GPS_TLV_INFO.
+ * Revision 1.57 2016/11/08 16:40:39 martin
+ * Doxygen cleanup.
+ * Revision 1.56 2016/10/26 13:22:41 martin
+ * Added definitions for GRC181PEX.
+ * New symbol IRIG_TIME_UNKNOWN_YEAR.
+ * Removed trailing spaces.
+ * Updated doxygen comments.
+ * Revision 1.55 2014/07/17 10:52:24 martin
+ * Increased safety of firmware builds.
+ * Revision 1.54 2014/07/17 09:54:19 martin
+ * New command codes PC_GPS_XMR_HOLDOVER_STATUS
+ * and PC_GPS_ALL_GPIO_STATUS.
+ * Huge update and cleanup on doxygen comments.
+ * Revision 1.53 2014/05/27 10:13:20 martin
+ * Support GPS180AMC.
+ * Moved some signal constant definitions to pcpsdefs.h.
+ * Simplified declaration of code/name tables.
+ * Huge rework of comments in doxygen format.
+ * Revision 1.52 2013/09/26 09:02:52Z martin
+ * Support GNSS API.
+ * Updated doxygen comments.
* Revision 1.51 2013/06/25 09:51:39 martin
* Support GLN180PEX.
* Revision 1.50 2013/01/30 15:59:54 martin
@@ -27,7 +58,7 @@
* Support GPIO configuration.
* Support PZF180PEX.
* Added commands to read CORR_INFO, read/write TR_DISTANCE,
- * PCPS_SYNC_PZF status, and associated structures.
+ * PCPS_SYNC_PZF status, and associated structures.
* Added an initializer for a table of GPS command code/names.
* Added definitions MBG_PCPS_FMT_STATUS.
* Updated some comments.
@@ -72,12 +103,12 @@
* Added new REF type PCPS_REF_MSF.
* Revision 1.35 2008/01/17 09:18:46Z daniel
* Made comments compatible for doxygen parser.
- * No sourcecode changes.
+ * No sourcecode changes.
* Revision 1.34 2007/07/17 08:22:47Z martin
* Added support for TCR511PEX and GPS170PEX.
* Revision 1.33 2007/05/20 21:39:51Z martin
* Added support for PEX511.
- * Added PCPS_GET_STATUS_PORT cmd code for devices
+ * Added PCPS_GET_STATUS_PORT cmd code for devices
* that do not support a hardware status port.
* Revision 1.32 2007/03/29 12:57:32Z martin
* Renamed some TZCODE numbers for unique naming conventions.
@@ -109,14 +140,14 @@
* Support configuration of on-board frequency synthesizer.
* Revision 1.21 2004/11/09 12:55:32Z martin
* Redefined interface data types using C99 fixed-size definitions.
- * Added workaround macros for some structure sizes because the C166
- * compiler always reports an even structure size even if the structure
- * size is in fact odd, which might lead to different sizes in C166 and
+ * Added workaround macros for some structure sizes because the C166
+ * compiler always reports an even structure size even if the structure
+ * size is in fact odd, which might lead to different sizes in C166 and
* other environments.
- * Modifications were required in order to be able to configure IRIG
+ * Modifications were required in order to be able to configure IRIG
* settings of cards which provide both IRIG input and output.
- * The existing codes have been renamed with .._RX.. and are used to
- * configure the IRIG receiver (input). New codes have been defined
+ * The existing codes have been renamed with .._RX.. and are used to
+ * configure the IRIG receiver (input). New codes have been defined
* used to configure the IRIG transmitter.
* Renamed PC_GPS_STAT to PC_GPS_BVAR_STAT.
* Use more specific data types than generic types.
@@ -134,12 +165,12 @@
* fill level.
* Revision 1.16 2003/04/03 10:48:53 martin
* Support for PCI510, GPS169PCI, and TCR510PCI.
- * New codes PCPS_GET_REF_OFFS, PCPS_SET_REF_OFFS
+ * New codes PCPS_GET_REF_OFFS, PCPS_SET_REF_OFFS
* and related structures.
* New codes PCPS_GET_OPT_INFO, PCPS_SET_OPT_SETTINGS
* and related structures.
* New codes PCPS_GET_IRIG_INFO, PCPS_SET_IRIG_SETTINGS.
- * Preliminary PCPS_TZDL structure and cmd codes
+ * Preliminary PCPS_TZDL structure and cmd codes
* to read/write that structure.
* Revision 1.15 2002/08/08 13:24:03 MARTIN
* Moved definition of ref time sources here.
@@ -203,8 +234,8 @@
* Changes before put under RCS control:
*
* Revision 1.5 2000/03/24
- * Introduced PCPS_GIVE_SERNUM
- * Cleaned up for definitions for serial parameter byte
+ * Introduced PCPS_GIVE_SERNUM.
+ * Cleaned up for definitions for serial parameter byte.
* Reviewed and updated comments.
*
* 1998/07/22
@@ -213,7 +244,7 @@
* Reviewed and updated comments.
*
* 1997/06/12
- * GPS definitions added.
+ * Added GPS definitions.
*
* 1996/01/25
* PCPS_TIME redefined from an array of bytes to a structure.
@@ -229,6 +260,13 @@
#include <words.h>
#include <use_pack.h>
+#ifndef _USE_PCPSPRIV
+ #define _USE_PCPSPRIV _IS_MBG_FIRMWARE
+#endif
+
+#if _USE_PCPSPRIV
+ #include <pcpspriv.h>
+#endif
/* Start of header body */
@@ -241,25 +279,30 @@
/**
* @brief Enumeration of the ref time signal sources used by Meinberg devices
*/
-enum
+enum PCPS_REF_TYPES
{
- PCPS_REF_NONE, /**< (unknown or not defined) */
- PCPS_REF_DCF, /**< see http://www.meinberg.de/english/info/dcf77.htm */
- PCPS_REF_GPS, /**< see http://www.meinberg.de/english/info/gps.htm */
- PCPS_REF_IRIG, /**< see http://www.meinberg.de/english/info/irig.htm */
- PCPS_REF_MSF, /**< MSF Receiver (UK) */
- PCPS_REF_PTP, /**< PTP/IEEE1588 network protocol */
- PCPS_REF_FRC, /**< Free Running Clock */
- PCPS_REF_WWVB, /**< WWVB Receiver (US) */
- PCPS_REF_JJY, /**< JJY Receiver (Japan) */
- N_PCPS_REF /**< number of valid ref time sources */
+ PCPS_REF_NONE, ///< unknown, or not defined
+ PCPS_REF_DCF, ///< DCF77 long wave signal (Germany), see http://www.meinberg.de/english/info/dcf77.htm
+ PCPS_REF_GPS, ///< GPS satellite system, see http://www.meinberg.de/english/info/gps.htm
+ PCPS_REF_IRIG, ///< IRIG or similar time code, see http://www.meinberg.de/english/info/irig.htm
+ PCPS_REF_MSF, ///< MSF long wave signal (UK)
+ PCPS_REF_PTP, ///< PTP/IEEE1588 network protocol
+ PCPS_REF_FRC, ///< Free Running Clock
+ PCPS_REF_WWVB, ///< WWVB long wave signal (U.S.)
+ PCPS_REF_JJY, ///< JJY long wave signal (Japan)
+ N_PCPS_REF ///< number of defined ref time sources
};
-/* Initializers for the reference source names */
+/**
+ * @defgroup group_pcps_ref_type_names Reference type names
+ *
+ * @see ::PCPS_REF_TYPES
+ *
+ * @{ */
-#define PCPS_REF_NAME_NONE_ENG "unknown"
-#define PCPS_REF_NAME_NONE_GER "nicht bekannt"
+#define PCPS_REF_NAME_NONE_ENG "unknown"
+#define PCPS_REF_NAME_NONE_GER "nicht bekannt"
#define PCPS_REF_NAME_DCF "DCF77"
#define PCPS_REF_NAME_GPS "GPS"
#define PCPS_REF_NAME_IRIG "IRIG"
@@ -269,7 +312,14 @@ enum
#define PCPS_REF_NAME_WWVB "WWVB"
#define PCPS_REF_NAME_JJY "JJY"
+/** @} @defgroup group_pcps_ref_type_names */
+
+/**
+ * @brief Initializer for an array of English reference type names
+ *
+ * @see ::PCPS_REF_TYPES
+ */
#define PCPS_REF_NAMES_ENG \
{ \
PCPS_REF_NAME_NONE_ENG, \
@@ -284,6 +334,11 @@ enum
}
+/**
+ * @brief Initializer for a multi-language array of reference type names
+ *
+ * @see ::PCPS_REF_TYPES
+ */
#define PCPS_REF_NAMES_LSTR \
{ \
{ PCPS_REF_NAME_NONE_ENG, PCPS_REF_NAME_NONE_GER }, \
@@ -300,14 +355,23 @@ enum
/**
- * @brief Meinberg PCI vendor ID (assigned by PCI SIG)
+ * @brief Meinberg PCI vendor ID (assigned by the PCI SIG)
+ *
+ * @see @ref MEINBERG_PCI_DEVICE_IDS
*/
#define PCI_VENDOR_MEINBERG 0x1360
-/* PCI device ID numbers (assigned by Meinberg) *
- * High byte: type of ref time source
- * Low Byte: enumeration of device types
- */
+
+/**
+ * @brief PCI device IDs assigned by Meinberg
+ *
+ * High byte: type of ref time source, see ::PCPS_REF_TYPES
+ * Low Byte: enumeration of device types
+ *
+ * @see ::PCI_VENDOR_MEINBERG
+ *
+ * @anchor MEINBERG_PCI_DEVICE_IDS @{ */
+
#define PCI_DEV_PCI32 ( ( PCPS_REF_DCF << 8 ) | 0x01 )
#define PCI_DEV_PCI509 ( ( PCPS_REF_DCF << 8 ) | 0x02 )
#define PCI_DEV_PCI510 ( ( PCPS_REF_DCF << 8 ) | 0x03 )
@@ -322,6 +386,8 @@ enum
#define PCI_DEV_GPS170PEX ( ( PCPS_REF_GPS << 8 ) | 0x05 )
#define PCI_DEV_GPS180PEX ( ( PCPS_REF_GPS << 8 ) | 0x06 )
#define PCI_DEV_GLN180PEX ( ( PCPS_REF_GPS << 8 ) | 0x07 )
+#define PCI_DEV_GPS180AMC ( ( PCPS_REF_GPS << 8 ) | 0x08 )
+#define PCI_DEV_GNS181PEX ( ( PCPS_REF_GPS << 8 ) | 0x09 )
#define PCI_DEV_TCR510PCI ( ( PCPS_REF_IRIG << 8 ) | 0x01 )
#define PCI_DEV_TCR167PCI ( ( PCPS_REF_IRIG << 8 ) | 0x02 )
@@ -334,37 +400,56 @@ enum
#define PCI_DEV_FRC511PEX ( ( PCPS_REF_FRC << 8 ) | 0x01 )
+/** @} anchor MEINBERG_PCI_DEVICE_IDS */
-// definitions used for the status port register
-// (not to be intermixed with PCPS_TIME_STATUS)
-typedef uint8_t PCPS_STATUS_PORT; /**< see @ref group_status_port "Bitmask" */
/**
- * @defgroup group_status_port Bit masks of PCPS_STATUS_PORT
+ * @defgroup group_status_port Definitions used with the status port
*
- * Bit definitions used with the #PCPS_STATUS_PORT register.
+ * The status port register on bus-level cards reflects some hardware
+ * signals (e.g. DCF-77 modulation), and flags used for communication
+ * with the card (e.g. the BUSY flag, ::PCPS_ST_BUSY).
*
- * The flags #PCPS_ST_SEC and #PCPS_ST_MIN are cleared whenever the clock
- * is read, so they are not very reliable in multitasking environments.
+ * @note Must not be confused with ::PCPS_TIME_STATUS which returns
+ * the synchronization status and associated information
*
- * @note The PCPS_ST_IRQF flag originates from old ISA cards.
+ * @{ */
+
+/**
+ * @brief Type of the status register port
+ */
+typedef uint8_t PCPS_STATUS_PORT; ///< see @ref PCPS_STATUS_PORT_BIT_MASKS
+
+
+/**
+ * @brief Bit masks used with ::PCPS_STATUS_PORT
+ *
+ * The flags ::PCPS_ST_SEC and ::PCPS_ST_MIN are cleared whenever the clock
+ * is read, so they are not very reliable in multitasking environments
+ * and thus should be considered deprecated.
+ *
+ * The ::PCPS_ST_IRQF flag was used with old ISA cards to check
+ * if the device has generated an IRQ.
* Some PCI cards also support this, but in case of PCI cards the
* associated flag of the PCI interface chip should be checked to see
- * if a certain card has generated an IRQ on the PC bus.
+ * if a particular card has generated an IRQ on the PC bus.
*
- * The macro _pcps_ddev_has_gen_irq() cares about this and should be used
+ * The macro ::_pcps_ddev_has_gen_irq() cares about this and should be used
* to determine in a portable way whether a card has generated an IRQ.
*
- * @{ */
+ * @anchor PCPS_STATUS_PORT_BIT_MASKS @{ */
+
+#define PCPS_ST_BUSY 0x01 ///< the clock is busy filling the output FIFO
+#define PCPS_ST_IRQF 0x02 ///< the clock has generated an IRQ on the PC bus (ISA cards only)
+#define PCPS_ST_MOD 0x20 ///< the raw demodulated DCF77 signal
+#define PCPS_ST_SEC 0x40 ///< seconds have changed since last reading
+#define PCPS_ST_MIN 0x80 ///< minutes have changed since last reading
-#define PCPS_ST_BUSY 0x01 /**< the clock is busy filling the output FIFO */
-#define PCPS_ST_IRQF 0x02 /**< the clock has generated an IRQ on the PC bus (ISA only)*/
-#define PCPS_ST_MOD 0x20 /**< the raw demodulated DCF77 signal */
-#define PCPS_ST_SEC 0x40 /**< seconds have changed since last reading */
-#define PCPS_ST_MIN 0x80 /**< minutes have changed since last reading */
+/** @} anchor PCPS_STATUS_PORT_BIT_MASKS */
+
+/** @} defgroup group_status_port */
-/** @} group_status_port */
/**
* A format string to be used with snprintb() which is available on some Unix
@@ -376,624 +461,491 @@ typedef uint8_t PCPS_STATUS_PORT; /**< see @ref group_status_port "Bitmask" */
-/** @defgroup group_cmd_bytes Command bytes used to access the device
-
- The commands described below are used to access computer peripherals
- manufactured by Meinberg.
-
- The header files pcpsdev.h and pcpsdrvr.h contain macros which can be
- used to check if a detected device supports a certain feature or command.
- If checking is required then the name of the macro is given in the
- comments below.
-
- Some commands expect parameters to be passed to the board. In that
- case, the board returns the number of parameter bytes expected when
- the command code is passed. Every parameter byte has to be supplied
- to the board exactly like a command byte.
- Refer to function pcps_write_data() and the macro _pcps_write_var()
- for details.
-
-
- - #PCPS_GIVE_TIME<br>
- Return a PCPS_TIME structure with current date,
- time and status. Supported by all clocks.
-
- - #PCPS_GIVE_TIME_NOCLEAR<br>
- Same as #PCPS_GIVE_TIME but the bits #PCPS_ST_SEC
- and #PCPS_ST_MIN (see pcpsdev.h) of the status
- port are not cleared.
- Supported by all clocks except PC31/PS31 with
- firmware version older than v3.0.
- This is mainly used by the DOS TSR and should
- not be used in other environments.
-
- - #PCPS_GIVE_SYNC_TIME<br>
- Return a ::PCPS_TIME structure with date and time
- of last synchronization of the clock or
- the last time set via the interface.
- _pcps_has_sync_time() checks whether supported.
-
- - #PCPS_GIVE_HR_TIME<br>
- Return a PCPS_HR_TIME structure with current
- date, time and status. This command should be
- used to read the clock with higher resolution.
- _pcps_has_hr_time() checks whether supported.
-
- - #PCPS_GIVE_IRIG_TIME<br>
- Return a PCPS_IRIG_TIME structure with day-of-year,
- time and status as decoded from the IRIG signal.
- _pcps_has_irig_time() checks whether supported.
-
- - #PCPS_SET_TIME<br>
- Set the board date, time and status. This
- command expects sizeof( ::PCPS_STIME ) parameter
- bytes.
- _pcps_can_set_time() checks whether supported.
-
- - #PCPS_SET_EVENT_TIME<br>
- Send a high resolution time stamp to the clock to
- configure a %UTC time when the clock shall generate
- some event. This command expects a PCPS_TIME_STAMP
- parameter.
- _pcps_has_event_time() checks whether supported.
- (requires custom GPS CERN firmware)
-
- - #PCPS_IRQ_NONE<br>
- Disable the board's hardware IRQ<br>
- - #PCPS_IRQ_1_SEC<br>
- Enable hardware IRQs once per second<br>
- - #PCPS_IRQ_1_MIN<br>
- Enable hardware IRQs once per minute<br>
- - #PCPS_IRQ_10_MIN<br>
- Enable hardware IRQs once per 10 minutes<br>
- - #PCPS_IRQ_30_MIN<br>
- Enable hardware IRQs once per 30 minutes<br>
-
- - #PCPS_GET_SERIAL<br>
- #PCPS_SET_SERIAL<br>
- These commands read or set the configuration
- of a clock's serial port COM0. The commands
- expect PCPS_SERIAL_BYTES parameter bytes and
- should be used preferably with the DCF77
- clocks which have only one COM port.
- _pcps_has_serial() checks whether supported.
- Recent GPS clocks' COM ports should be cfg'd
- using the structures RECEIVER_INFO, PORT_INFO,
- and STR_TYPE_INFO.
- _pcps_has_receiver_info() checks whether
- these are supported. If they are not, then
- the code #PC_GPS_PORT_PARM together with the
- #PCPS_READ_GPS_DATA and #PCPS_WRITE_GPS_DATA
- commands should be used.
-
- - #PCPS_GET_TZCODE<br>
- #PCPS_SET_TZCODE<br>
- These commands read or set a DCF77 clock's
- time zone code and should be used preferably
- with the newer DCF77 clocks which have limited
- support of different time zones.
- _pcps_has_tzcode() checks whether supported.
- A GPS clock's time zone must be cfg'd using
- the code #PC_GPS_TZDL together with the
- #PCPS_READ_GPS_DATA and #PCPS_WRITE_GPS_DATA
- commands.
-
- - #PCPS_GET_PCPS_TZDL<br>
- #PCPS_SET_PCPS_TZDL<br>
- These commands read or set a DCF77 clock's
- time zone / daylight saving configuration.
- _pcps_has_pcps_tzdl() checks whether supported.
- A GPS clock's time zone must be cfg'd using
- the code #PC_GPS_TZDL together with the
- #PCPS_READ_GPS_DATA and #PCPS_WRITE_GPS_DATA
- commands.
-
- - #PCPS_GET_REF_OFFS<br>
- #PCPS_SET_REF_OFFS<br>
- These commands can be used to configure the
- reference time offset from %UTC for clocks
- which can't determine the offset automatically,
- e.g. from an IRIG input signal.
- _pcps_has_ref_offs() checks whether supported.
-
- - #PCPS_GET_OPT_INFO<br>
- #PCPS_SET_OPT_SETTINGS<br>
- These commands can be used to configure some
- optional settings, controlled by flags.
- When reading, the clock returns a MBG_OPT_INFO
- structure which contains the supported values,
- plus the current settings.
- When writing, clocks accepts a MBG_OPT_SETTINGS
- structure only which contain the desired settings
- of the supported flags only.
- _pcps_has_opt_flags() checks whether supported.
-
- - #PCPS_GET_IRIG_RX_INFO<br>
- #PCPS_SET_IRIG_RX_SETTINGS<br>
- #PCPS_GET_IRIG_TX_INFO<br>
- #PCPS_SET_IRIG_TX_SETTINGS<br>
- These commands can be used to configure IRIG
- inputs and outputs.<br>
- When reading, the clock returns an IRIG_INFO
- structure which contains the supported values,
- plus the current settings.<br>
- When writing, clocks accepts an IRIG_SETTINGS
- structure only which contain the desired settings
- only. _pcps_is_irig_rx() and _pcps_is_irig_tx()
- check whether supported.
-
- - #PCPS_GET_IRIG_CTRL_BITS<br>
- This command can be used to retrieve the control function
- bits of the latest IRIG input frame. Those bits may carry
- some well-known information as in the IEEE1344 code, but
- may also contain some customized information, depending on
- the IRIG frame type and the configuration of the IRIG generator.
- So these bits are returned as-is and must be interpreted
- by the application.
- _pcps_has_irig_ctrl_bits() checks whether supported.
-
- - #PCPS_GET_SYNTH<br>
- #PCPS_SET_SYNTH<br>
- #PCPS_GET_SYNTH_STATE<br>
- These commands can be used to configure an on-board
- frequency synthesizer and query the synthesizer
- status. The commands are only supported if the board
- supports the RECEIVER_INFO structure and the flag
- #GPS_HAS_SYNTH is set in the RECEIVER_INFO::features.
- _pcps_has_synth() checks whether supported.
- The structures SYNTH and SYNTH_STATE used with these
- commands are defined in gpsdefs.h.
-
- - #PCPS_GIVE_FW_ID_1<br>
- #PCPS_GIVE_FW_ID_2<br>
- Returns the first/second block of PCPS_FIFO_SIZE
- characters of the firmware ID string. These
- commands can be used to check if the board
- responds properly. This is done by the clock
- detection functions.
-
- - #PCPS_GIVE_SERNUM<br>
- Returns PCPS_FIFO_SIZE characters of the
- clock's serial number.
- _pcps_has_sernum() checks whether supported.
-
- - #PCPS_GENERIC_IO<br>
- Generic I/O read and write. Can be used to query
- specific data, e.g. a selected element of an array.
- _pcps_has_generic_io() checks whether supported.
-
- - #PCPS_GET_DEBUG_STATUS<br>
- This command reads a MBG_DEBUG_STATUS structure
- which represents the internal status of the
- IRIG decoder and some additional debug info.
- _pcps_has_debug_status() checks whether supported.
-
- - #PCPS_READ_GPS_DATA<br>
- #PCPS_WRITE_GPS_DATA<br>
- These commands are used by the functions
- pcps_read_gps_data() and pcps_write_gps_data()
- to read or write large data structures to
- Meinberg GPS plug-in clocks.
- _pcps_is_gps() checks whether supported.
-
- - #PCPS_CLR_UCAP_BUFF<br>
- Clear a clock's time capture buffer.
- _pcps_can_clr_ucap_buff() checks whether
- supported.
-
- - #PCPS_GIVE_UCAP_ENTRIES<br>
- Read a PCPS_UCAP_ENTRIES structure which
- reports the max number of entries and the
- currently used number of entries in the
- user capture buffer.
- _pcps_has_ucap() checks whether supported.
-
- - #PCPS_GIVE_UCAP_EVENT<br>
- Read capture events using a PCPS_HR_TIME
- structure. This is faster than reading using the
- GPS command #PC_GPS_UCAP. If no capture event is
- available then the structure is filled with 0s.
- _pcps_has_ucap() checks whether supported.
-
- - #PCPS_GET_CORR_INFO<br>
- Read PZF correlation info using a CORR_INFO
- structure.
- _pcps_has_pzf() checks whether supported.
-
- - #PCPS_GET_TR_DISTANCE<br>
- #PCPS_SET_TR_DISTANCE<br>
- Read or write distance from the RF transmitter.
- This is used to compensate the RF propagation delay
- for PZF receivers.
- _pcps_has_tr_distance() checks whether supported.
-
- - #PCPS_CLR_EVT_LOG<br>
- Clear on-board event log.
- _pcps_has_evt_log() checks whether supported.
-
- - #PCPS_NUM_EVT_LOG_ENTRIES<br>
- Read max number of num event log entries which can
- be saved on the board, and how many entries actually
- have been saved.
- _pcps_has_evt_log() checks whether supported.
-
- - #PCPS_FIRST_EVT_LOG_ENTRY<br>
- - #PCPS_NEXT_EVT_LOG_ENTRY<br>
- Read first (oldest) or next event log entry.
- _pcps_has_evt_log() checks whether supported.
-
- - #PCPS_FORCE_RESET<br>
- Resets the microprocessor on the device. This is
- for special test scenarios only and should not be
- used by standard applications since this may lock up
- the PC.
-
- The command codes listed above are defined below.
-
- @{ */
-
-
-#if _IS_MBG_FIRMWARE //##++
-
-// These group codes are obsolete and should be removed.
-// The explicite command codes defined below should be used instead.
-#define PCPS_GIVE_TIME_GROUP 0x00
-#define PCPS_SET_TIME_GROUP 0x10
-#define PCPS_IRQ_GROUP 0x20
-#define PCPS_CFG_GROUP 0x30
-#define PCPS_GIVE_DATA_GROUP 0x40
-#define PCPS_GPS_DATA_GROUP 0x50
-#define PCPS_CTRL_GROUP 0x60
-#define PCPS_CFG2_GROUP 0x70
-
-#endif
-
-
-
-#define PCPS_GIVE_TIME 0x00
-#define PCPS_GIVE_TIME_NOCLEAR 0x01
-#define PCPS_GIVE_SYNC_TIME 0x02 // only supported if _pcps_has_sync_time()
-#define PCPS_GIVE_HR_TIME 0x03 // only supported if _pcps_has_hr_time()
-#define PCPS_GIVE_IRIG_TIME 0x04 // only supported if _pcps_has_irig_time()
-
-#define PCPS_SET_TIME 0x10
-/* on error, return PCPS_ERR_STIME */
-
-/* Attention: The code below can be used EXCLUSIVELY */
-/* with a GPS167PCI with customized CERN firmware !! */
-/* _pcps_has_event_time() checks whether supported. */
-#define PCPS_SET_EVENT_TIME 0x14
-
-#define PCPS_IRQ_NONE 0x20
-#define PCPS_IRQ_1_SEC 0x21
-#define PCPS_IRQ_1_MIN 0x22
-#define PCPS_IRQ_10_MIN 0x24
-#define PCPS_IRQ_30_MIN 0x28
-
-#define PCPS_GET_SERIAL 0x30
-#define PCPS_SET_SERIAL 0x31
-/* on error, return PCPS_ERR_CFG */
-
-typedef uint8_t PCPS_SERIAL;
-
-
-#define PCPS_GET_TZCODE 0x32
-#define PCPS_SET_TZCODE 0x33
-/* on error, return PCPS_ERR_CFG */
-
-typedef uint8_t PCPS_TZCODE;
-
/**
- * @brief Enumeration of codes used with PCPS_TZCODE
- */
-enum PCPS_TZCODES
-{
- PCPS_TZCODE_CET_CEST, /* default as broadcasted by DCF77 (UTC+1h/UTC+2h) */
- PCPS_TZCODE_CET, /* always CET (UTC+1h), discard DST */
- PCPS_TZCODE_UTC, /* always %UTC */
- PCPS_TZCODE_EET_EEST, /* East European Time, CET/CEST + 1h */
- N_PCPS_TZCODE /* the number of valid codes */
-};
-
-/* the definitions below are for compatibily only: */
-#define PCPS_TZCODE_MEZMESZ PCPS_TZCODE_CET_CEST
-#define PCPS_TZCODE_MEZ PCPS_TZCODE_CET
-#define PCPS_TZCODE_OEZ PCPS_TZCODE_EET_EEST
-
-
-#define PCPS_GET_PCPS_TZDL 0x34
-#define PCPS_SET_PCPS_TZDL 0x35
-/* on error, return PCPS_ERR_CFG */
-
-
-/**
- * The structures below can be used to configure a clock's
- * time zone/daylight saving setting. This structure is shorter
- * than the TZDL structure used with GPS clocks.
- */
-typedef struct
-{
- // The year_or_wday field below contains the full year number
- // or 0..6 == Sun..Sat if the DL_AUTO_FLAG is set; see below.
- uint16_t year_or_wday;
- uint8_t month;
- uint8_t mday;
- uint8_t hour;
- uint8_t min;
-} PCPS_DL_ONOFF;
-
-#define _mbg_swab_pcps_dl_onoff( _p ) \
-{ \
- _mbg_swab16( &(_p)->year_or_wday ); \
-}
-
-/**
- * If the field year_or_wday is or'ed with the constant DL_AUTO_FLAG
- * defined below then this means that start and end of daylight saving
- * time shall be computed automatically for each year. In this case
- * the remaining bits represent the day-of-week after the specified
- * mday/month at which the change shall occur. If that flag is not set
- * then the field contains the full four-digit year number and the
- * mday/month values specify the exact date of that year.
- */
-#define DL_AUTO_FLAG 0x8000 // also defined in gpsdefs.h
-
-typedef struct
-{
- int16_t offs; /**< offset from %UTC to local time [min] */
- int16_t offs_dl; /**< additional offset if DST enabled [min] */
- PCPS_DL_ONOFF tm_on; /**< date/time when daylight saving starts */
- PCPS_DL_ONOFF tm_off; /**< date/time when daylight saving ends */
-} PCPS_TZDL;
-
-#define _mbg_swab_pcps_tzdl( _p ) \
-{ \
- _mbg_swab16( &(_p)->offs ); \
- _mbg_swab16( &(_p)->offs_dl ); \
- _mbg_swab_pcps_dl_onoff( &(_p)->tm_on ); \
- _mbg_swab_pcps_dl_onoff( &(_p)->tm_off ); \
-}
+ * @brief Command codes used to communicate with bus level devices
+ *
+ * These commands are used for low level access to bus-level devices
+ * manufactured by Meinberg.
+ *
+ * Applications should instead use the API functions declared in mbgdevio.h.
+ *
+ * The header files pcpsdev.h and pcpsdrvr.h contain macros which can be
+ * used to check if a detected device supports a certain feature or command.
+ * If checking is required then the name of the macro is given in the
+ * comments associated with the command codes.
+ *
+ * Some commands expect parameters to be passed to the board. In that
+ * case, the board returns the number of parameter bytes expected when
+ * the command code is passed. Every parameter byte has to be supplied
+ * to the board exactly like a command byte.
+ *
+ * Refer to function ::pcps_write() and the macro ::_pcps_write_var()
+ * for details.
+ *
+ * - ::PCPS_GIVE_TIME<br>
+ * Return a ::PCPS_TIME structure with current date,
+ * time and status. Supported by all clocks.
+ *
+ * - ::PCPS_GIVE_TIME_NOCLEAR<br>
+ * Same as ::PCPS_GIVE_TIME but the bits ::PCPS_ST_SEC
+ * and ::PCPS_ST_MIN of the status port are not cleared.
+ * Supported by all clocks except PC31/PS31 with
+ * firmware version older than v3.0.
+ * This is mainly used by the DOS TSR and should
+ * not be used in other environments.
+ *
+ * - ::PCPS_GIVE_SYNC_TIME<br>
+ * Return a ::PCPS_TIME structure with date and time
+ * of last synchronization of the clock or
+ * the last time set via the interface.
+ * ::_pcps_has_sync_time() checks whether supported.
+ *
+ * - ::PCPS_GIVE_HR_TIME<br>
+ * Return a ::PCPS_HR_TIME structure with current
+ * date, time and status. This command should be
+ * used to read the clock with higher resolution.
+ * ::_pcps_has_hr_time() checks whether supported.
+ *
+ * - ::PCPS_GIVE_IRIG_TIME<br>
+ * Return a ::PCPS_IRIG_TIME structure with day-of-year,
+ * time and status as decoded from the IRIG signal.
+ * ::_pcps_has_irig_time() checks whether supported.
+ *
+ * - ::PCPS_SET_TIME<br>
+ * Set the board date, time and status. This command
+ * expects sizeof( ::PCPS_STIME ) parameter bytes.
+ * ::_pcps_can_set_time() checks whether supported.
+ *
+ * - ::PCPS_SET_EVENT_TIME<br>
+ * Send a high resolution time stamp to the clock to
+ * configure a %UTC time when the clock shall generate
+ * some event. This command expects a ::PCPS_TIME_STAMP
+ * parameter.
+ * ::_pcps_has_event_time() checks whether supported.
+ * (requires custom GPS CERN firmware)
+ *
+ * - ::PCPS_IRQ_NONE<br>
+ * Disable the card's hardware IRQ<br>
+ * - ::PCPS_IRQ_1_SEC<br>
+ * Enable hardware IRQs once per second<br>
+ * - ::PCPS_IRQ_1_MIN<br>
+ * Enable hardware IRQs once per minute (deprecated)<br>
+ * - ::PCPS_IRQ_10_MIN<br>
+ * Enable hardware IRQs once per 10 minutes (deprecated)<br>
+ * - ::PCPS_IRQ_30_MIN<br>
+ * Enable hardware IRQs once per 30 minutes (deprecated)<br>
+ *
+ * - ::PCPS_GET_SERIAL<br>
+ * ::PCPS_SET_SERIAL<br>
+ * Deprecated. Read or write the configuration of a card's
+ * serial port COM0 in ::PCPS_SERIAL format.
+ * ::_pcps_has_serial() checks whether supported.
+ * Newer cards should be configured using the structures ::RECEIVER_INFO,
+ * ::PORT_INFO, and STR_TYPE_INFO.
+ * ::_pcps_has_receiver_info() checks whether these are supported.
+ *
+ * - ::PCPS_GET_TZCODE<br>
+ * ::PCPS_SET_TZCODE<br>
+ * These commands read or set a DCF77 clock's
+ * time zone code and should be used preferably
+ * with older DCF77 receivers which have limited
+ * support of different time zones.
+ * ::_pcps_has_tzcode() checks whether supported.
+ * Most newer devices support the ::TZDL structure which can be
+ * read or written using ::PC_GPS_TZDL.
+ *
+ * - ::PCPS_GET_PCPS_TZDL<br>
+ * ::PCPS_SET_PCPS_TZDL<br>
+ * Read or write time zone / daylight saving information
+ * in ::PCPS_TZDL format.
+ * ::_pcps_has_pcps_tzdl() checks whether supported.
+ *
+ * - ::PCPS_GET_REF_OFFS<br>
+ * ::PCPS_SET_REF_OFFS<br>
+ * These commands can be used to configure the
+ * reference time offset from %UTC for clocks
+ * which can't determine the offset automatically,
+ * e.g. from an IRIG input signal.
+ * ::_pcps_has_ref_offs() checks whether supported.
+ *
+ * - ::PCPS_GET_OPT_INFO<br>
+ * ::PCPS_SET_OPT_SETTINGS<br>
+ * These commands can be used to configure some
+ * optional settings, controlled by flags.
+ * When reading, the clock returns a ::MBG_OPT_INFO
+ * structure which contains the supported values,
+ * plus the current settings.
+ * When writing, clocks accepts a ::MBG_OPT_SETTINGS
+ * structure only which contain the desired settings
+ * of the supported flags only.
+ * ::_pcps_has_opt_flags() checks whether supported.
+ *
+ * - ::PCPS_GET_IRIG_RX_INFO<br>
+ * ::PCPS_SET_IRIG_RX_SETTINGS<br>
+ * ::PCPS_GET_IRIG_TX_INFO<br>
+ * ::PCPS_SET_IRIG_TX_SETTINGS<br>
+ * These commands can be used to configure IRIG
+ * inputs and outputs.<br>
+ * When reading, the clock returns an ::IRIG_INFO
+ * structure which contains the supported values,
+ * plus the current settings.<br>
+ * When writing, clocks accepts an ::IRIG_SETTINGS
+ * structure only which contain the desired settings
+ * only. ::_pcps_is_irig_rx() and ::_pcps_has_irig_tx()
+ * check whether supported.
+ *
+ * - ::PCPS_GET_IRIG_CTRL_BITS<br>
+ * This command can be used to retrieve the control function
+ * bits of the latest IRIG input frame. Those bits may carry
+ * some well-known information as in the IEEE 1344 code, but
+ * may also contain some customized information, depending on
+ * the IRIG frame type and the configuration of the IRIG generator.
+ * So these bits are returned as-is and must be interpreted
+ * by the application.
+ * ::_pcps_has_irig_ctrl_bits() checks whether supported.
+ *
+ * - ::PCPS_GET_SYNTH<br>
+ * ::PCPS_SET_SYNTH<br>
+ * ::PCPS_GET_SYNTH_STATE<br>
+ * These commands can be used to configure an on-board
+ * frequency synthesizer and query the synthesizer
+ * status. The commands are only supported if the board
+ * supports the ::RECEIVER_INFO structure and the flag
+ * #GPS_HAS_SYNTH is set in the ::RECEIVER_INFO::features.
+ * ::_pcps_has_synth() checks whether supported.
+ * The structures ::SYNTH and ::SYNTH_STATE used with these
+ * commands are defined in gpsdefs.h.
+ *
+ * - ::PCPS_GIVE_FW_ID_1<br>
+ * ::PCPS_GIVE_FW_ID_2<br>
+ * Returns the first/second block of ::PCPS_FIFO_SIZE
+ * characters of the firmware ID string. These
+ * commands can be used to check if the board
+ * responds properly. This is done by the clock
+ * detection functions.
+ *
+ * - ::PCPS_GIVE_SERNUM<br>
+ * Returns ::PCPS_FIFO_SIZE characters of the
+ * clock's serial number.
+ * ::_pcps_has_sernum() checks whether supported.
+ *
+ * - ::PCPS_GENERIC_IO<br>
+ * Generic I/O read and write. Can be used to query
+ * specific data, e.g. a selected element of an array.
+ * ::_pcps_has_generic_io() checks whether supported.
+ *
+ * - ::PCPS_GET_DEBUG_STATUS<br>
+ * This command reads an ::MBG_DEBUG_STATUS structure
+ * which represents the internal status of the
+ * IRIG decoder and some additional debug info.
+ * ::_pcps_has_debug_status() checks whether supported.
+ *
+ * - ::PCPS_READ_GPS_DATA<br>
+ * ::PCPS_WRITE_GPS_DATA<br>
+ * These commands are used by the functions
+ * ::pcps_read_gps() and ::pcps_write_gps()
+ * to read or write large data structures to
+ * Meinberg GPS plug-in clocks.
+ * ::_pcps_is_gps() checks whether supported.
+ *
+ * - ::PCPS_CLR_UCAP_BUFF<br>
+ * Clear a clock's time capture buffer.
+ * ::_pcps_can_clr_ucap_buff() checks whether
+ * supported.
+ *
+ * - ::PCPS_GIVE_UCAP_ENTRIES<br>
+ * Read a ::PCPS_UCAP_ENTRIES structure which
+ * reports the max number of entries and the
+ * currently used number of entries in the
+ * user capture buffer.
+ * ::_pcps_has_ucap() checks whether supported.
+ *
+ * - ::PCPS_GIVE_UCAP_EVENT<br>
+ * Read capture events using a PCPS_HR_TIME
+ * structure. This is faster than reading using the
+ * GPS command ::PC_GPS_UCAP. If no capture event is
+ * available then the returned structure is all 0.
+ * ::_pcps_has_ucap() checks whether supported.
+ *
+ * - ::PCPS_GET_CORR_INFO<br>
+ * Read PZF correlation info using a ::CORR_INFO
+ * structure.
+ * ::_pcps_has_pzf() checks whether supported.
+ *
+ * - ::PCPS_GET_TR_DISTANCE<br>
+ * ::PCPS_SET_TR_DISTANCE<br>
+ * Read or write distance from the RF transmitter.
+ * This is used to compensate the RF propagation delay
+ * for PZF receivers.
+ * ::_pcps_has_tr_distance() checks whether supported.
+ *
+ * - ::PCPS_CLR_EVT_LOG<br>
+ * Clear on-board event log.
+ * ::_pcps_has_evt_log() checks whether supported.
+ *
+ * - ::PCPS_NUM_EVT_LOG_ENTRIES<br>
+ * Read max. number of num event log entries which can
+ * be saved on the board, and how many entries have currently
+ * been saved.
+ * ::_pcps_has_evt_log() checks whether supported.
+ *
+ * - ::PCPS_FIRST_EVT_LOG_ENTRY<br>
+ * ::PCPS_NEXT_EVT_LOG_ENTRY<br>
+ * Read first (oldest) or next event log entry.
+ * ::_pcps_has_evt_log() checks whether supported.
+ *
+ * - ::PCPS_FORCE_RESET<br>
+ * Resets the card's hardware. This may lock up the computer
+ * and thus should only be used by very specific applications.
+ *
+ * @anchor PCPS_CMD_CODES @{ */
+#define PCPS_GIVE_TIME 0x00 ///< (r-) Read current time in ::PCPS_TIME format
+#define PCPS_GIVE_TIME_NOCLEAR 0x01 ///< (r-) Read current time in ::PCPS_TIME format, don't clear sec and min flags (deprecated)
+#define PCPS_GIVE_SYNC_TIME 0x02 ///< (r-) Read last sync time as ::PCPS_TIME, only if ::_pcps_has_sync_time()
+#define PCPS_GIVE_HR_TIME 0x03 ///< (r-) Read high res. time as ::PCPS_HR_TIME, only if ::_pcps_has_hr_time()
+#define PCPS_GIVE_IRIG_TIME 0x04 ///< (r-) Read raw IRIG time as ::PCPS_IRIG_TIME, only if ::_pcps_has_irig_time()
+#define PCPS_SET_TIME 0x10 ///< (-w) Set on-board time, see ::PCPS_STIME. Returns ::MBG_ERR_STIME on error.
-#define PCPS_GET_REF_OFFS 0x36
-#define PCPS_SET_REF_OFFS 0x37
-/* on error, return PCPS_ERR_CFG */
+#define PCPS_SET_EVENT_TIME 0x14 ///< (-w) Write event time as ::PCPS_TIME_STAMP, only if ::_pcps_has_event_time()
-/* The associated type MBG_REF_OFFS is defined in gpsdefs.h. */
+#define PCPS_IRQ_NONE 0x20 ///< (-w) Disable IRQs
+#define PCPS_IRQ_1_SEC 0x21 ///< (-w) Enable IRQ per 1 second
+#define PCPS_IRQ_1_MIN 0x22 ///< (-w) Enable IRQ per 1 minute (deprecated)
+#define PCPS_IRQ_10_MIN 0x24 ///< (-w) Enable IRQ per 10 minutes (deprecated)
+#define PCPS_IRQ_30_MIN 0x28 ///< (-w) Enable IRQ per 10 minutes (deprecated)
+#define PCPS_GET_SERIAL 0x30 ///< (r-) Read serial settings as ::PCPS_SERIAL, deprecated by ::PC_GPS_ALL_PORT_INFO
+#define PCPS_SET_SERIAL 0x31 ///< (-w) Write serial settings as ::PCPS_SERIAL, deprecated by ::PC_GPS_PORT_SETTINGS_IDX, returns ::MBG_ERR_CFG on error
-#define PCPS_GET_OPT_INFO 0x38
-#define PCPS_SET_OPT_SETTINGS 0x39
-/* on error, return PCPS_ERR_CFG */
+#define PCPS_GET_TZCODE 0x32 ///< (r-) Read ::PCPS_TZCODE, only if ::_pcps_has_tzcode()
+#define PCPS_SET_TZCODE 0x33 ///< (-w) Write ::PCPS_TZCODE, only if ::_pcps_has_tzcode(), returns ::MBG_ERR_CFG on error
-/* The associated structures MBG_OPT_INFO and MBG_OPT_SETTINGS
- are defined in gpsdefs.h. */
+#define PCPS_GET_PCPS_TZDL 0x34 ///< (r-) Read ::PCPS_TZDL, only if ::_pcps_has_pcps_tzdl()
+#define PCPS_SET_PCPS_TZDL 0x35 ///< (-w) Write ::PCPS_TZDL, only if ::_pcps_has_pcps_tzdl(), returns ::MBG_ERR_CFG on error
+#define PCPS_GET_REF_OFFS 0x36 ///< (r-) Read ::MBG_REF_OFFS, only if ::_pcps_has_ref_offs()
+#define PCPS_SET_REF_OFFS 0x37 ///< (-w) Write ::MBG_REF_OFFS, only if ::_pcps_has_ref_offs(), returns ::MBG_ERR_CFG on error
-#define PCPS_GET_IRIG_RX_INFO 0x3A
-#define PCPS_SET_IRIG_RX_SETTINGS 0x3B
-/* on error, return PCPS_ERR_CFG */
+#define PCPS_GET_OPT_INFO 0x38 ///< (r-) Read ::MBG_OPT_INFO, only if ::_pcps_has_opt_flags()
+#define PCPS_SET_OPT_SETTINGS 0x39 ///< (-w) Write ::MBG_OPT_SETTINGS, only if ::_pcps_has_opt_flags(), returns ::MBG_ERR_CFG on error
-#define PCPS_GET_IRIG_TX_INFO 0x3C
-#define PCPS_SET_IRIG_TX_SETTINGS 0x3D
-/* on error, return PCPS_ERR_CFG */
+#define PCPS_GET_IRIG_RX_INFO 0x3A ///< (r-) Read ::IRIG_INFO, only if ::_pcps_is_irig_rx()
+#define PCPS_SET_IRIG_RX_SETTINGS 0x3B ///< (-w) Write ::IRIG_SETTINGS, only if ::_pcps_is_irig_rx(), returns ::MBG_ERR_CFG on error
-/* The associated structures IRIG_INFO and IRIG_SETTINGS
- are defined in gpsdefs.h. */
+#define PCPS_GET_IRIG_TX_INFO 0x3C ///< (r-) Read ::IRIG_INFO, only if ::_pcps_has_irig_tx()
+#define PCPS_SET_IRIG_TX_SETTINGS 0x3D ///< (-w) Write ::IRIG_SETTINGS, only if ::_pcps_has_irig_tx(), returns ::MBG_ERR_CFG on error
+#define PCPS_GET_SYNTH 0x3E ///< (r-) Read ::SYNTH, only if ::_pcps_has_synth()
+#define PCPS_SET_SYNTH 0x3F ///< (-w) Write ::SYNTH, only if ::_pcps_has_synth(), returns ::MBG_ERR_CFG on error
-#define PCPS_GET_SYNTH 0x3E
-#define PCPS_SET_SYNTH 0x3F
-/* on error, return PCPS_ERR_CFG */
+#define PCPS_GIVE_FW_ID_1 0x40 ///< (r-) Read first ::PCPS_FIFO_SIZE chars of firmware ID
+#define PCPS_GIVE_FW_ID_2 0x41 ///< (r-) Read last ::PCPS_FIFO_SIZE chars of firmware ID
+#define PCPS_GIVE_SERNUM 0x42 ///< (r-) Read serial number as ::PCPS_SN_STR, only if _pcps_has_sernum()
+#define PCPS_GENERIC_IO 0x43 ///< (rw) See ::pcps_generic_io() or ::_mbgdevio_gen_io()
+#define PCPS_GET_SYNTH_STATE 0x44 ///< (r-) Read ::SYNTH_STATE, only if ::_pcps_has_synth()
+#define PCPS_GET_IRIG_CTRL_BITS 0x45 ///< (r-) Read ::MBG_IRIG_CTRL_BITS, only if ::_pcps_has_irig_ctrl_bits()
+#define PCPS_GET_RAW_IRIG_DATA 0x46 ///< (r-) Read ::MBG_RAW_IRIG_DATA, only if ::_pcps_has_raw_irig_data()
-/* The associated structure SYNTH is defined in gpsdefs.h. */
+#define PCPS_GET_STATUS_PORT 0x4B ///< (r-) Read ::PCPS_STATUS_PORT
+#define PCPS_GET_DEBUG_STATUS 0x4C ///< (r-) Read ::MBG_DEBUG_STATUS, only if ::_pcps_has_debug_status()
+/// @note Command codes 0x4D, 0x4E, and 0x4F are reserved.
-#define PCPS_GIVE_FW_ID_1 0x40
-#define PCPS_GIVE_FW_ID_2 0x41
-#define PCPS_GIVE_SERNUM 0x42
-#define PCPS_GENERIC_IO 0x43
-#define PCPS_GET_SYNTH_STATE 0x44
-#define PCPS_GET_IRIG_CTRL_BITS 0x45
-#define PCPS_GET_RAW_IRIG_DATA 0x46
+#define PCPS_READ_GPS_DATA 0x50 ///< (r-) Read large data structure, see ::PC_GPS_CMD_CODES
+#define PCPS_WRITE_GPS_DATA 0x51 ///< (-w) Write large data structure, see ::PC_GPS_CMD_CODES
+#define PCPS_CLR_UCAP_BUFF 0x60 ///< (-w) No param., clear on-board capture FIFO, only if ::_pcps_has_ucap()
+#define PCPS_GIVE_UCAP_ENTRIES 0x61 ///< (r-) Read ::PCPS_UCAP_ENTRIES, only if ::_pcps_has_ucap()
+#define PCPS_GIVE_UCAP_EVENT 0x62 ///< (r-) Return oldest event as ::PCPS_HR_TIME, only if ::_pcps_has_ucap()
+#define PCPS_GET_CORR_INFO 0x63 ///< (r-) Read ::CORR_INFO structure, only if ::_pcps_has_pzf()
+#define PCPS_GET_TR_DISTANCE 0x64 ///< (r-) Read ::TR_DISTANCE, only if ::_pcps_has_tr_distance()
+#define PCPS_SET_TR_DISTANCE 0x65 ///< (-w) Write ::TR_DISTANCE, only if ::_pcps_has_tr_distance()
-#define PCPS_GET_STATUS_PORT 0x4B
-#define PCPS_GET_DEBUG_STATUS 0x4C
-// expects sizeof( MBG_DEBUG_STATUS ) chars
+#define PCPS_CLR_EVT_LOG 0x66 ///< (-w) Write clear on-board event log, only if ::_pcps_has_evt_log()
+#define PCPS_NUM_EVT_LOG_ENTRIES 0x67 ///< (r-) Read ::MBG_NUM_EVT_LOG_ENTRIES, only if ::_pcps_has_evt_log()
+#define PCPS_FIRST_EVT_LOG_ENTRY 0x68 ///< (r-) Read first (oldest) ::MBG_EVT_LOG_ENTRY, only if ::_pcps_has_evt_log()
+#define PCPS_NEXT_EVT_LOG_ENTRY 0x69 ///< (r-) Read next ::MBG_EVT_LOG_ENTRY, only if ::_pcps_has_evt_log()
-// Command codes 0x4D, 0x4E, and 0x4F are reserved.
+#define PCPS_FORCE_RESET 0x80 ///< (-w) No param., reset the device (deprecated, this can lock up the computer!!)
+/// @note Command codes 0xF0 through 0xFF are reserved.
-#define PCPS_READ_GPS_DATA 0x50
-#define PCPS_WRITE_GPS_DATA 0x51
+/** @} anchor PCPS_CMD_CODES */
-#define PCPS_CLR_UCAP_BUFF 0x60
-#define PCPS_GIVE_UCAP_ENTRIES 0x61
-#define PCPS_GIVE_UCAP_EVENT 0x62
-
-typedef struct
-{
- uint32_t used; /**< the number of saved capture events */
- uint32_t max; /**< capture buffer size */
-} PCPS_UCAP_ENTRIES;
-
-#define _mbg_swab_pcps_ucap_entries( _p ) \
-{ \
- _mbg_swab32( &(_p)->used ); \
- _mbg_swab32( &(_p)->max ); \
-}
+#if _IS_MBG_FIRMWARE
-#define PCPS_GET_CORR_INFO 0x63 // read CORR_INFO structure, only if _pcps_has_pzf()
-#define PCPS_GET_TR_DISTANCE 0x64 // read TR_DISTANCE, only if _pcps_has_tr_distance()
-#define PCPS_SET_TR_DISTANCE 0x65 // write TR_DISTANCE, only if _pcps_has_tr_distance()
-
-
-#define PCPS_CLR_EVT_LOG 0x66 // clear on-board event log, only if _pcps_has_evt_log()
-#define PCPS_NUM_EVT_LOG_ENTRIES 0x67 // read num event log entries, only if _pcps_has_evt_log()
-#define PCPS_FIRST_EVT_LOG_ENTRY 0x68 // read first (oldest) event log entry, only if _pcps_has_evt_log()
-#define PCPS_NEXT_EVT_LOG_ENTRY 0x69 // read next event log entry, only if _pcps_has_evt_log()
+/**
+ * @brief Deprecated command group codes
+ *
+ * @deprecated These group codes are deprecated.
+ * They should not be used anymore but removed
+ * from existing source code. The explicite command
+ * codes @ref PCPS_CMD_CODES should be used instead.
+ *
+ * @anchor PCPS_CMD_GROUP_CODES @{ */
+#define PCPS_GIVE_TIME_GROUP 0x00
+#define PCPS_SET_TIME_GROUP 0x10
+#define PCPS_IRQ_GROUP 0x20
+#define PCPS_CFG_GROUP 0x30
+#define PCPS_GIVE_DATA_GROUP 0x40
+#define PCPS_GPS_DATA_GROUP 0x50
+#define PCPS_CTRL_GROUP 0x60
+#define PCPS_CFG2_GROUP 0x70
-/**
- special -- use with care !
-*/
-#define PCPS_FORCE_RESET 0x80
+/** @} anchor PCPS_CMD_GROUP_CODES */
-// Command codes 0xF0 through 0xFF are reserved.
+#endif // _IS_MBG_FIRMWARE
-/** @} group_cmd_bytes */
#if !defined( MBG_CMD_TABLE_EXT )
- #define MBG_CMD_TABLE_EXT { 0, NULL }
+ #define MBG_CMD_TABLE_EXT _mbg_cn_table_end()
#endif
/**
* @brief An initializer for a table of code/name entries of non-GPS commands.
*
- * This can e.g. be assigned to an array of MBG_CODE_NAME_TABLE_ENTRY elements
+ * This can e.g. initialize an array of ::MBG_CODE_NAME_TABLE_ENTRY elements
* and may be helpful when debugging.
+ *
+ * @see @ref PCPS_CMD_CODES
*/
-#define MBG_CMD_TABLE \
-{ \
- { PCPS_GIVE_TIME, "PCPS_GIVE_TIME" }, /* 00 */ \
- { PCPS_GIVE_TIME_NOCLEAR, "PCPS_GIVE_TIME_NOCLEAR" }, /* 01 */ \
- { PCPS_GIVE_SYNC_TIME, "PCPS_GIVE_SYNC_TIME" }, /* 02 */ \
- { PCPS_GIVE_HR_TIME, "PCPS_GIVE_HR_TIME" }, /* 03 */ \
- { PCPS_GIVE_IRIG_TIME, "PCPS_GIVE_IRIG_TIME" }, /* 04 */ \
- { PCPS_SET_TIME, "PCPS_SET_TIME" }, /* 10 */ \
- { PCPS_SET_EVENT_TIME, "PCPS_SET_EVENT_TIME" }, /* 14 */ \
- { PCPS_IRQ_NONE, "PCPS_IRQ_NONE" }, /* 20 */ \
- { PCPS_IRQ_1_SEC, "PCPS_IRQ_1_SEC" }, /* 21 */ \
- { PCPS_IRQ_1_MIN, "PCPS_IRQ_1_MIN" }, /* 22 */ \
- { PCPS_IRQ_10_MIN, "PCPS_IRQ_10_MIN" }, /* 24 */ \
- { PCPS_IRQ_30_MIN, "PCPS_IRQ_30_MIN" }, /* 28 */ \
- { PCPS_GET_SERIAL, "PCPS_GET_SERIAL" }, /* 30 */ \
- { PCPS_SET_SERIAL, "PCPS_SET_SERIAL" }, /* 31 */ \
- { PCPS_GET_TZCODE, "PCPS_GET_TZCODE" }, /* 32 */ \
- { PCPS_SET_TZCODE, "PCPS_SET_TZCODE" }, /* 33 */ \
- { PCPS_GET_PCPS_TZDL, "PCPS_GET_PCPS_TZDL" }, /* 34 */ \
- { PCPS_SET_PCPS_TZDL, "PCPS_SET_PCPS_TZDL" }, /* 35 */ \
- { PCPS_GET_REF_OFFS, "PCPS_GET_REF_OFFS" }, /* 36 */ \
- { PCPS_SET_REF_OFFS, "PCPS_SET_REF_OFFS" }, /* 37 */ \
- { PCPS_GET_OPT_INFO, "PCPS_GET_OPT_INFO" }, /* 38 */ \
- { PCPS_SET_OPT_SETTINGS, "PCPS_SET_OPT_SETTINGS" }, /* 39 */ \
- { PCPS_GET_IRIG_RX_INFO, "PCPS_GET_IRIG_RX_INFO" }, /* 3A */ \
- { PCPS_SET_IRIG_RX_SETTINGS, "PCPS_SET_IRIG_RX_SETTINGS" }, /* 3B */ \
- { PCPS_GET_IRIG_TX_INFO, "PCPS_GET_IRIG_TX_INFO" }, /* 3C */ \
- { PCPS_SET_IRIG_TX_SETTINGS, "PCPS_SET_IRIG_TX_SETTINGS" }, /* 3D */ \
- { PCPS_GET_SYNTH, "PCPS_GET_SYNTH" }, /* 3E */ \
- { PCPS_SET_SYNTH, "PCPS_SET_SYNTH" }, /* 3F */ \
- { PCPS_GIVE_FW_ID_1, "PCPS_GIVE_FW_ID_1" }, /* 40 */ \
- { PCPS_GIVE_FW_ID_2, "PCPS_GIVE_FW_ID_2" }, /* 41 */ \
- { PCPS_GIVE_SERNUM, "PCPS_GIVE_SERNUM" }, /* 42 */ \
- { PCPS_GENERIC_IO, "PCPS_GENERIC_IO" }, /* 43 */ \
- { PCPS_GET_SYNTH_STATE, "PCPS_GET_SYNTH_STATE" }, /* 44 */ \
- { PCPS_GET_IRIG_CTRL_BITS, "PCPS_GET_IRIG_CTRL_BITS" }, /* 45 */ \
- { PCPS_GET_RAW_IRIG_DATA, "PCPS_GET_RAW_IRIG_DATA" }, /* 46 */ \
- { PCPS_GET_STATUS_PORT, "PCPS_GET_STATUS_PORT" }, /* 4B */ \
- { PCPS_GET_DEBUG_STATUS, "PCPS_GET_DEBUG_STATUS" }, /* 4C */ \
- { PCPS_READ_GPS_DATA, "PCPS_READ_GPS_DATA" }, /* 50 */ \
- { PCPS_WRITE_GPS_DATA, "PCPS_WRITE_GPS_DATA" }, /* 51 */ \
- { PCPS_CLR_UCAP_BUFF, "PCPS_CLR_UCAP_BUFF" }, /* 60 */ \
- { PCPS_GIVE_UCAP_ENTRIES, "PCPS_GIVE_UCAP_ENTRIES" }, /* 61 */ \
- { PCPS_GIVE_UCAP_EVENT, "PCPS_GIVE_UCAP_EVENT" }, /* 62 */ \
- { PCPS_GET_CORR_INFO, "PCPS_GET_CORR_INFO" }, /* 63 */ \
- { PCPS_GET_TR_DISTANCE, "PCPS_GET_TR_DISTANCE" }, /* 64 */ \
- { PCPS_SET_TR_DISTANCE, "PCPS_SET_TR_DISTANCE" }, /* 65 */ \
- { PCPS_CLR_EVT_LOG, "PCPS_CLR_EVT_LOG" }, /* 66 */ \
- { PCPS_NUM_EVT_LOG_ENTRIES, "PCPS_NUM_EVT_LOG_ENTRIES" }, /* 67 */ \
- { PCPS_FIRST_EVT_LOG_ENTRY, "PCPS_FIRST_EVT_LOG_ENTRY" }, /* 68 */ \
- { PCPS_NEXT_EVT_LOG_ENTRY, "PCPS_NEXT_EVT_LOG_ENTRY" }, /* 69 */ \
- { PCPS_FORCE_RESET, "PCPS_FORCE_RESET" }, /* 80 */ \
- MBG_CMD_TABLE_EXT, \
- { 0, NULL } \
+#define PCPS_CMD_CODES_TABLE \
+{ \
+ _mbg_cn_table_entry( PCPS_GIVE_TIME ), /* 0x00 */ \
+ _mbg_cn_table_entry( PCPS_GIVE_TIME_NOCLEAR ), /* 0x01 */ \
+ _mbg_cn_table_entry( PCPS_GIVE_SYNC_TIME ), /* 0x02 */ \
+ _mbg_cn_table_entry( PCPS_GIVE_HR_TIME ), /* 0x03 */ \
+ _mbg_cn_table_entry( PCPS_GIVE_IRIG_TIME ), /* 0x04 */ \
+ _mbg_cn_table_entry( PCPS_SET_TIME ), /* 0x10 */ \
+ _mbg_cn_table_entry( PCPS_SET_EVENT_TIME ), /* 0x14 */ \
+ _mbg_cn_table_entry( PCPS_IRQ_NONE ), /* 0x20 */ \
+ _mbg_cn_table_entry( PCPS_IRQ_1_SEC ), /* 0x21 */ \
+ _mbg_cn_table_entry( PCPS_IRQ_1_MIN ), /* 0x22 */ \
+ _mbg_cn_table_entry( PCPS_IRQ_10_MIN ), /* 0x24 */ \
+ _mbg_cn_table_entry( PCPS_IRQ_30_MIN ), /* 0x28 */ \
+ _mbg_cn_table_entry( PCPS_GET_SERIAL ), /* 0x30 */ \
+ _mbg_cn_table_entry( PCPS_SET_SERIAL ), /* 0x31 */ \
+ _mbg_cn_table_entry( PCPS_GET_TZCODE ), /* 0x32 */ \
+ _mbg_cn_table_entry( PCPS_SET_TZCODE ), /* 0x33 */ \
+ _mbg_cn_table_entry( PCPS_GET_PCPS_TZDL ), /* 0x34 */ \
+ _mbg_cn_table_entry( PCPS_SET_PCPS_TZDL ), /* 0x35 */ \
+ _mbg_cn_table_entry( PCPS_GET_REF_OFFS ), /* 0x36 */ \
+ _mbg_cn_table_entry( PCPS_SET_REF_OFFS ), /* 0x37 */ \
+ _mbg_cn_table_entry( PCPS_GET_OPT_INFO ), /* 0x38 */ \
+ _mbg_cn_table_entry( PCPS_SET_OPT_SETTINGS ), /* 0x39 */ \
+ _mbg_cn_table_entry( PCPS_GET_IRIG_RX_INFO ), /* 0x3A */ \
+ _mbg_cn_table_entry( PCPS_SET_IRIG_RX_SETTINGS ), /* 0x3B */ \
+ _mbg_cn_table_entry( PCPS_GET_IRIG_TX_INFO ), /* 0x3C */ \
+ _mbg_cn_table_entry( PCPS_SET_IRIG_TX_SETTINGS ), /* 0x3D */ \
+ _mbg_cn_table_entry( PCPS_GET_SYNTH ), /* 0x3E */ \
+ _mbg_cn_table_entry( PCPS_SET_SYNTH ), /* 0x3F */ \
+ _mbg_cn_table_entry( PCPS_GIVE_FW_ID_1 ), /* 0x40 */ \
+ _mbg_cn_table_entry( PCPS_GIVE_FW_ID_2 ), /* 0x41 */ \
+ _mbg_cn_table_entry( PCPS_GIVE_SERNUM ), /* 0x42 */ \
+ _mbg_cn_table_entry( PCPS_GENERIC_IO ), /* 0x43 */ \
+ _mbg_cn_table_entry( PCPS_GET_SYNTH_STATE ), /* 0x44 */ \
+ _mbg_cn_table_entry( PCPS_GET_IRIG_CTRL_BITS ), /* 0x45 */ \
+ _mbg_cn_table_entry( PCPS_GET_RAW_IRIG_DATA ), /* 0x46 */ \
+ _mbg_cn_table_entry( PCPS_GET_STATUS_PORT ), /* 0x4B */ \
+ _mbg_cn_table_entry( PCPS_GET_DEBUG_STATUS ), /* 0x4C */ \
+ _mbg_cn_table_entry( PCPS_READ_GPS_DATA ), /* 0x50 */ \
+ _mbg_cn_table_entry( PCPS_WRITE_GPS_DATA ), /* 0x51 */ \
+ _mbg_cn_table_entry( PCPS_CLR_UCAP_BUFF ), /* 0x60 */ \
+ _mbg_cn_table_entry( PCPS_GIVE_UCAP_ENTRIES ), /* 0x61 */ \
+ _mbg_cn_table_entry( PCPS_GIVE_UCAP_EVENT ), /* 0x62 */ \
+ _mbg_cn_table_entry( PCPS_GET_CORR_INFO ), /* 0x63 */ \
+ _mbg_cn_table_entry( PCPS_GET_TR_DISTANCE ), /* 0x64 */ \
+ _mbg_cn_table_entry( PCPS_SET_TR_DISTANCE ), /* 0x65 */ \
+ _mbg_cn_table_entry( PCPS_CLR_EVT_LOG ), /* 0x66 */ \
+ _mbg_cn_table_entry( PCPS_NUM_EVT_LOG_ENTRIES ), /* 0x67 */ \
+ _mbg_cn_table_entry( PCPS_FIRST_EVT_LOG_ENTRY ), /* 0x68 */ \
+ _mbg_cn_table_entry( PCPS_NEXT_EVT_LOG_ENTRY ), /* 0x69 */ \
+ _mbg_cn_table_entry( PCPS_FORCE_RESET ), /* 0x80 */ \
+ MBG_CMD_TABLE_EXT, \
+ _mbg_cn_table_end() \
}
-/* Codes returned when commands with parameters have been passed */
-/* to the board */
-#define PCPS_SUCCESS 0 /**< OK, no error */
-#define PCPS_ERR_STIME -1 /**< invalid date/time/status passed */
-#define PCPS_ERR_CFG -2 /**< invalid parms for a cmd writing config parameters */
+/**
+ * @brief Bus level command return codes
+ *
+ * @deprecated These codes are deprecated and @ref MBG_RETURN_CODES should be used
+ * instead which provide corresponding symbols with same numeric values.
+ *
+ * @anchor PCPS_LEVEL_CMD_RETURN_CODES @{ */
+
+#define PCPS_SUCCESS 0 ///< OK, no error (see ::MBG_SUCCESS)
+#define PCPS_ERR_STIME -1 ///< invalid date/time/status passed (see ::MBG_ERR_STIME)
+#define PCPS_ERR_CFG -2 ///< invalid parms for a cmd writing config parameters (see ::MBG_ERR_CFG)
+
+/** @} anchor PCPS_LEVEL_CMD_RETURN_CODES */
-#ifndef BITMASK
+#if !defined( BITMASK )
#define BITMASK( b ) ( ( 1 << b ) - 1 )
#endif
-/** The size of the plug-in card's on-board FIFO */
+/** @brief The size of a bus level device's command/data FIFO */
#define PCPS_FIFO_SIZE 16
+/** @brief A data buffer for a bus level device's command/data */
typedef int8_t PCPS_BUFF[PCPS_FIFO_SIZE];
-#define PCPS_ID_SIZE ( 2 * PCPS_FIFO_SIZE + 1 ) /**< ASCIIZ string */
+/** @brief The maximum length of an ID string, including terminating 0 */
+#define PCPS_ID_SIZE ( 2 * PCPS_FIFO_SIZE + 1 ) ///< ASCIIZ string
+
+/** @brief A buffer for an ID string, including terminating 0 */
typedef char PCPS_ID_STR[PCPS_ID_SIZE];
-#define PCPS_SN_SIZE ( PCPS_FIFO_SIZE + 1 ) /**< ASCIIZ string */
+/** @brief The maximum length of a serial number string, including terminating 0 */
+#define PCPS_SN_SIZE ( PCPS_FIFO_SIZE + 1 ) ///< ASCIIZ string
+
+/** @brief A buffer for a serial number string, including terminating 0 */
typedef char PCPS_SN_STR[PCPS_SN_SIZE];
+
/**
- * The structure has been introduced to be able to handle
- * high resolution time stamps.
+ * @brief A high resolution time stamp
*/
typedef struct
{
- uint32_t sec; /**< seconds since 1970 (UTC) */
- uint32_t frac; /**< fractions of second ( 0xFFFFFFFF == 0.9999.. sec) */
+ uint32_t sec; ///< seconds since 1970, usually %UTC scale
+ uint32_t frac; ///< binary fractions of second (0x80000000 == 0.5 s, 0xFFFFFFFF == 0.9999999.. s)
+
} PCPS_TIME_STAMP;
#define _mbg_swab_pcps_time_stamp( _p ) \
+do \
{ \
_mbg_swab32( &(_p)->sec ); \
_mbg_swab32( &(_p)->frac ); \
-}
-
+} while ( 0 )
-// Depending on the target environment define a data type
-// which can be used to convert binary fractions without
-// range overflow.
-#if defined( MBG_TGT_UNIX )
- #define PCPS_HRT_FRAC_CONVERSION_TYPE int64_t
-#elif defined( MBG_TGT_WIN32 )
- #define PCPS_HRT_FRAC_CONVERSION_TYPE int64_t
-#elif defined( __WATCOMC__ ) && ( __WATCOMC__ >= 1100 )
- #define PCPS_HRT_FRAC_CONVERSION_TYPE int64_t
-#else
- #define PCPS_HRT_FRAC_CONVERSION_TYPE double
-#endif
-
-// Max value of PCPS_TIME_STAMP::frac + 1 used for scaling
-#define PCPS_HRT_BIN_FRAC_SCALE ( (PCPS_HRT_FRAC_CONVERSION_TYPE) 4294967296.0 ) // == 0x100000000
-
-
-// The scale and format to be used to print the fractions
-// of a second as returned in the PCPS_TIME_STAMP structure.
-// The function frac_sec_from_bin() can be used for
-// the conversion.
-#ifndef PCPS_HRT_FRAC_SCALE
- #define PCPS_HRT_FRAC_SCALE 10000000UL
-#endif
-#ifndef PCPS_HRT_FRAC_SCALE_FMT
- #define PCPS_HRT_FRAC_SCALE_FMT "%07lu"
-#endif
-
-
-
-typedef uint16_t PCPS_TIME_STATUS_X; /**< extended status */
+/**
+ * @brief Extended status code
+ *
+ * Low byte corresponds to ::PCPS_TIME_STATUS, high byte
+ * contains additional flags.
+ *
+ * @see ::PCPS_TIME_STATUS
+ * @see @ref PCPS_TIME_STATUS_FLAGS
+ */
+typedef uint16_t PCPS_TIME_STATUS_X;
#define _mbg_swab_pcps_time_status_x( _p ) _mbg_swab16( _p )
@@ -1006,89 +958,147 @@ typedef struct
} PCPS_TIME_STATUS_X_MASKS;
#define _mbg_swab_pcps_time_status_x_masks( _p ) \
+do \
{ \
_mbg_swab_pcps_time_status_x( &(_p)->set_mask ); \
_mbg_swab_pcps_time_status_x( &(_p)->clr_mask ); \
-}
+} while ( 0 )
+
+
+
+/**
+ * @brief Definitions used to report a signal strength
+ *
+ * @anchor PCPS_SIG_VAL_DEFS @{ */
+
+/**
+ * @brief A data type used to report the signal value
+ */
+typedef uint8_t PCPS_SIG_VAL;
+
+// The following constants are used to draw a signal bar
+// depending on a DCF77 clock's signal value:
+#define PCPS_SIG_BIAS 55
+#define PCPS_SIG_ERR 1
+#define PCPS_SIG_MIN 20
+#define PCPS_SIG_MAX 68
+
+// These constants are used by non-DCF77 devices to indicate
+// if an input signal is available or not:
+#define PCPS_SIG_LVL_SIG_NOT_AVAIL 0
+#define PCPS_SIG_LVL_SIG_AVAIL 128
+
+/** @} anchor PCPS_SIG_VAL_DEFS */
/**
- * The structure has been introduced to be able to read the
- * current time with higher resolution of fractions of seconds and
- * more detailed information on the time zone and status.
- * The structure is returned if the new command #PCPS_GIVE_HR_TIME
- * is written to the board.
- * _pcps_has_hr_time() checks whether supported.
- *
- * Newer GPS boards also accept the #PCPS_GIVE_UCAP_EVENT command
- * to return user capture event times using this format. In this
- * case, the "signal" field contains the number of the capture
- * input line, e.g. 0 or 1.
- * _pcps_has_ucap() checks whether supported.
+ * @brief High resolution time including status and local time offset
+ *
+ * Used to read time with high resolution of fractions of seconds and
+ * more detailed information on the local time offset and status.
+ * Should be prefered over ::PCPS_TIME.
+ *
+ * ::_pcps_has_hr_time checks whether the command ::PCPS_GIVE_TIME is
+ * supported to read a device's current time using this format.
+ *
+ * Newer devices providing time capture input may also accept the
+ * ::PCPS_GIVE_UCAP_EVENT command to read user capture event times
+ * using this format. In this case, the "signal" field contains
+ * the number of the capture input line, e.g. 0 or 1.
+ * ::_pcps_has_ucap checks whether this is supported.
*/
typedef struct
{
- PCPS_TIME_STAMP tstamp; /**< High resolution time stamp (UTC) */
- int32_t utc_offs; /**< %UTC offs [sec] (loc_time = %UTC + utc_offs) */
- PCPS_TIME_STATUS_X status; /**< status flags as defined below */
- uint8_t signal; /**< for normal time, the relative RF signal level, for ucap, the channel number */
+ PCPS_TIME_STAMP tstamp; ///< High resolution time stamp (%UTC)
+ int32_t utc_offs; ///< %UTC offs [sec] (loc_time = tstamp + utc_offs)
+ PCPS_TIME_STATUS_X status; ///< status bits, see @ref PCPS_TIME_STATUS_FLAGS
+ PCPS_SIG_VAL signal; ///< signal strength, see @ref PCPS_SIG_VAL_DEFS, or capture input channel number
+
} PCPS_HR_TIME;
#define _mbg_swab_pcps_hr_time( _p ) \
+do \
{ \
_mbg_swab_pcps_time_stamp( &(_p)->tstamp ); \
_mbg_swab32( &(_p)->utc_offs ); \
_mbg_swab_pcps_time_status_x( &(_p)->status ); \
-}
+} while ( 0 )
+/**
+ * @brief Time synchronization status
+ *
+ * Used by legacy API calls. New API calls provide
+ * an extended status word ::PCPS_TIME_STATUS_X.
+ *
+ * @see ::PCPS_TIME_STATUS_FLAGS_COMMON
+ * @see ::PCPS_TIME_STATUS_X
+ */
typedef uint8_t PCPS_TIME_STATUS;
-/**
- The standard structure used to read times from the board.
- The time has a resultion of 10 ms.
-*/
-typedef struct PCPS_TIME_s
+
+
+/**
+ * @brief Local calendar date and time, plus sync status
+ *
+ * This legacy structure is supported by all bus level devices but
+ * has a time resultion of 10 ms only. For more accurate time stamps
+ * the structures ::PCPS_HR_TIME and ::PCPS_TIME_STAMP should be
+ * used preferably.
+ *
+ * @see ::PCPS_HR_TIME
+ * @see ::PCPS_TIME_STAMP
+ * @see ::PCPS_STIME
+ */
+typedef struct
{
- uint8_t sec100; /**< hundredths of seconds, 0..99 */
- uint8_t sec; /**< seconds, 0..59, or 60 if leap second */
- uint8_t min; /**< minutes, 0..59 */
- uint8_t hour; /**< hours, 0..23 */
-
- uint8_t mday; /**< day of month, 0..31 */
- uint8_t wday; /**< day of week, 1..7, 1 = Monday */
- uint8_t month; /**< month, 1..12 */
- uint8_t year; /**< year of the century, 0..99 */
-
- PCPS_TIME_STATUS status; /**< status bits, see below */
- uint8_t signal; /**< relative signal strength, range depends on device type */
- int8_t offs_utc; /**< [hours], 0 if !_pcps_has_utc_offs() */
+ uint8_t sec100; ///< hundredths of seconds, 0..99, 10 ms resolution
+ uint8_t sec; ///< seconds, 0..59, or 60 if leap second
+ uint8_t min; ///< minutes, 0..59
+ uint8_t hour; ///< hours, 0..23
+
+ uint8_t mday; ///< day of month, 0..31
+ uint8_t wday; ///< day of week, 1..7, 1 = Monday
+ uint8_t month; ///< month, 1..12
+ uint8_t year; ///< year of the century, 0..99
+
+ PCPS_TIME_STATUS status; ///< status bits, see ::PCPS_TIME_STATUS_FLAGS_COMMON
+ PCPS_SIG_VAL signal; ///< signal strength, see @ref PCPS_SIG_VAL_DEFS
+ int8_t offs_utc; ///< [hours], 0 if not ::_pcps_has_utc_offs
+
} PCPS_TIME;
-/**
- The structure is passed as parameter with the PCPS_SET_TIME cmd
-*/
-typedef struct PCPS_STIME_s
+
+/**
+ * @brief Date time and status used with the ::PCPS_SET_TIME command
+ *
+ * Similar to ::PCPS_TIME, but missing the ::PCPS_TIME::signal
+ * and ::PCPS_TIME::offs_utc fields.
+ *
+ * @see ::PCPS_TIME
+ */
+typedef struct
{
- uint8_t sec100; /**< hundredths of seconds, 0..99 */
- uint8_t sec; /**< seconds, 0..59, or 60 if leap second */
- uint8_t min; /**< minutes, 0..59 */
- uint8_t hour; /**< hours, 0..23 */
+ uint8_t sec100; ///< hundredths of seconds, 0..99, 10 ms resolution
+ uint8_t sec; ///< seconds, 0..59, or 60 if leap second
+ uint8_t min; ///< minutes, 0..59
+ uint8_t hour; ///< hours, 0..23
+
+ uint8_t mday; ///< day of month, 0..31
+ uint8_t wday; ///< day of week, 1..7, 1 = Monday
+ uint8_t month; ///< month, 1..12
+ uint8_t year; ///< year of the century, 0..99
- uint8_t mday; /**< day of month, 0..31 */
- uint8_t wday; /**< day of week, 1..7, 1 = Monday */
- uint8_t month; /**< month, 1..12 */
- uint8_t year; /**< year of the century, 0..99 */
+ PCPS_TIME_STATUS status; ///< status bits, see ::PCPS_TIME_STATUS_FLAGS_COMMON
- PCPS_TIME_STATUS status; /**< status bits, see below */
} PCPS_STIME;
#ifdef _C166
- // This is a workaround to specify some structure sizes. The C166 compiler
- // always reports an even structure size although the structure size may
- // be odd due to the number of bytes. This might lead to errors between
+ // This is a workaround to specify some structure sizes. The C166 compiler
+ // always reports an even structure size although the structure size may
+ // be odd due to the number of bytes. This might lead to errors between
// the C166 and other build environments.
#define sizeof_PCPS_TIME ( sizeof( PCPS_TIME ) - 1 )
#define sizeof_PCPS_STIME ( sizeof( PCPS_STIME ) - 1 )
@@ -1101,129 +1111,174 @@ typedef union
{
PCPS_TIME t;
PCPS_STIME stime;
+
} PCPS_TIME_UNION;
/**
- The structure below can be used to read the raw IRIG time
- from an IRIG receiver card, if the card supports this.
- See the #PCPS_GIVE_IRIG_TIME command.
-
- The granularity of the value in the .frac field depends on
- the update interval of the structure as implementation
- in the firmware. I.e. if the raw IRIG time is updated
- only once per second, the .frac value can always be 0.
-*/
-typedef struct PCPS_IRIG_TIME_s
+ * @brief Raw IRIG time
+ *
+ * Used to read the raw IRIG time from an IRIG receiver card, if the card
+ * supports this. See the ::PCPS_GIVE_IRIG_TIME command.
+ *
+ * The granularity of the value in the ::PCPS_IRIG_TIME::frac field
+ * depends on the update interval at which the structure is updated
+ * by the firmeware. I.e., if the raw IRIG time is updated only
+ * once per second, the ::PCPS_IRIG_TIME::frac value can always be 0.
+ *
+ * @see @ref group_icode
+ * @see ::ICODE_RX_CODES
+ */
+typedef struct
{
- PCPS_TIME_STATUS_X status; /**< status bits, see below */
- int16_t offs_utc; /**< [minutes] */
- uint16_t yday; /**< day of year, 1..365/366 */
- uint16_t frac; /**< fractions of seconds, 0.1 ms units */
- uint8_t sec; /**< seconds, 0..59, or 60 if leap second */
- uint8_t min; /**< minutes, 0..59 */
- uint8_t hour; /**< hours, 0..23 */
- uint8_t year; /**< 2 digit year number, 0xFF if year not supp. by the IRIG code */
- uint8_t signal; /**< relative signal strength, range depends on device type */
- uint8_t reserved; /**< currently not used, always 0 */
+ PCPS_TIME_STATUS_X status; ///< status bits, see @ref PCPS_TIME_STATUS_FLAGS
+ int16_t offs_utc; ///< [minutes], 0 unless supported by the code format, see ::MSK_ICODE_RX_HAS_TZI
+ uint16_t yday; ///< day of year, 1..365/366
+ uint16_t frac; ///< fractions of seconds, 0.1 ms units
+ uint8_t sec; ///< seconds, 0..59, may be 60 for leap second
+ uint8_t min; ///< minutes, 0..59
+ uint8_t hour; ///< hours, 0..23
+ uint8_t year; ///< 2 digit year number, or ::IRIG_TIME_UNKNOWN_YEAR if year not supported
+ ///< by the time code, see ::MSK_ICODE_RX_HAS_ANY_SHORT_YEAR
+ PCPS_SIG_VAL signal; ///< signal strength, see @ref PCPS_SIG_VAL_DEFS
+ uint8_t reserved; ///< currently not used, always 0
+
} PCPS_IRIG_TIME;
#define _mbg_swab_pcps_irig_time( _p ) \
+do \
{ \
_mbg_swab_pcps_time_status_x( &(_p)->status ); \
_mbg_swab16( &(_p)->offs_utc ); \
_mbg_swab16( &(_p)->yday ); \
_mbg_swab16( &(_p)->frac ); \
-}
-
-
+} while ( 0 )
/**
- * Bit masks used with both PCPS_TIME_STATUS and PCPS_TIME_STATUS_X
+ * @brief A constant representing a 2 digit unknown IRIG year number
+ *
+ * Used with ::PCPS_IRIG_TIME::year
*/
-#define PCPS_FREER 0x01 /**< DCF77 clock running on xtal */
- /**< GPS receiver has not verified its position */
-
-#define PCPS_DL_ENB 0x02 /**< daylight saving enabled */
+#define IRIG_TIME_UNKNOWN_YEAR 0xFF
-#define PCPS_SYNCD 0x04 /**< clock has sync'ed at least once after pwr up */
-
-#define PCPS_DL_ANN 0x08 /**< a change in daylight saving is announced */
-
-#define PCPS_UTC 0x10 /**< a special %UTC firmware is installed */
-
-#define PCPS_LS_ANN 0x20 /**< leap second announced */
- /**< (requires firmware rev. REV_PCPS_LS_ANN_...) */
-
-#define PCPS_IFTM 0x40 /**< the current time was set via PC */
- /**< (requires firmware rev. REV_PCPS_IFTM_...) */
-
-#define PCPS_INVT 0x80 /**< invalid time because battery was disconn'd */
/**
- * Bit masks used only with PCPS_TIME_STATUS_X
- */
-#define PCPS_LS_ENB 0x0100 /**< current second is leap second */
-#define PCPS_ANT_FAIL 0x0200 /**< antenna failure */
-#define PCPS_LS_ANN_NEG 0x0400 /**< announced leap second is negative */
-#define PCPS_SCALE_GPS 0x0800 /**< time stamp is GPS scale */
-#define PCPS_SCALE_TAI 0x1000 /**< time stamp is TAI scale */
+ * @brief Time status flags
+ *
+ * @anchor PCPS_TIME_STATUS_FLAGS @{ */
/**
- * Bit masks used only with time stamps representing user capture events
+ * @brief Legacy time status flags
+ *
+ * Bit masks used with both ::PCPS_TIME_STATUS and ::PCPS_TIME_STATUS_X
*/
-#define PCPS_UCAP_OVERRUN 0x2000 /**< events interval too short */
-#define PCPS_UCAP_BUFFER_FULL 0x4000 /**< events read too slow */
+enum PCPS_TIME_STATUS_FLAGS_COMMON
+{
+ PCPS_FREER = 0x01, ///< long wave or time code receiver running on xtal, satellite receiver has not verified its position
+ PCPS_DL_ENB = 0x02, ///< daylight saving currently enabled
+ PCPS_SYNCD = 0x04, ///< long wave or time code receiver has sync'ed at least once after pwr up, sat receiver is synchronized
+ PCPS_DL_ANN = 0x08, ///< a change in daylight saving status is announced
+ PCPS_UTC = 0x10, ///< returned time is always %UTC instead of some local time
+ PCPS_LS_ANN = 0x20, ///< leap second announced, for *very* old clocks see ::REV_PCPS_LS_ANN_PC31PS31
+ PCPS_IFTM = 0x40, ///< the current time has been set by an API call, for *very* old clocks see ::REV_PCPS_IFTM_PC31PS31
+ PCPS_INVT = 0x80 ///< invalid time because battery had been disconnected, or absolute time can't be decoded safely
+};
-/**
- * Bit masks used only with time stamps representing the current board time.
- * A DCF77 PZF receiver can set this bit if it is actually synchronized
- * using PZF correlation and thus provides higher accuracy than AM receivers.
- */
-#define PCPS_SYNC_PZF 0x2000 /**< same code as PCPS_UCAP_OVERRUN */
/**
- * Immediately after a clock has been accessed, subsequent accesses
- * are blocked for up to 1.5 msec to give the clock's microprocessor
- * some time to decode the incoming time signal.
- * The flag below is set if a program tries to read the PCPS_HR_TIME
- * during this interval. In this case the read function returns the
- * proper time stamp which is taken if the command byte is written,
- * however, the read function returns with delay.
- * This flag is not supported by all clocks.
+ * @brief Extended time status flags
+ *
+ * Bit masks used with ::PCPS_TIME_STATUS_X only
*/
-#define PCPS_IO_BLOCKED 0x8000
+enum PCPS_TIME_STATUS_FLAGS_EXT
+{
+ PCPS_LS_ENB = 0x0100, ///< current second is leap second
+ PCPS_ANT_FAIL = 0x0200, ///< antenna failure
+ PCPS_LS_ANN_NEG = 0x0400, ///< announced leap second is negative
+ PCPS_SCALE_GPS = 0x0800, ///< time stamp is GPS scale
+ PCPS_SCALE_TAI = 0x1000, ///< time stamp is TAI scale
+
+ PCPS_UCAP_OVERRUN = 0x2000, ///< events interval too short (capture events only)
+ PCPS_UCAP_BUFFER_FULL = 0x4000, ///< events read too slow (capture events only)
+
+ /**
+ * Bit masks used only with time stamps representing the current board time.
+ * A DCF77 PZF receiver can set this bit if it is actually synchronized
+ * using PZF correlation and thus provides higher accuracy than AM receivers.
+ * Same numeric code as ::PCPS_UCAP_OVERRUN
+ */
+ PCPS_SYNC_PZF = 0x2000,
+
+ /**
+ * Immediately after a clock has been accessed, subsequent accesses
+ * may be blocked for up to 1.5 msec to give the clock's microprocessor
+ * some time to decode the incoming time signal.
+ * The flag below is eventually set if a program tries to read ::PCPS_HR_TIME
+ * during this interval. In this case the read function returns the
+ * proper time stamp which is taken if the command byte is written,
+ * however, the read function returns with delay.
+ * This flag is not supported by all clocks.
+ */
+ PCPS_IO_BLOCKED = 0x8000
+};
+
+
/**
* This bit mask can be used to extract the time scale information out
* of a PCPS_TIME_STATUS_X value.
-*/
+ */
#define PCPS_SCALE_MASK ( PCPS_SCALE_TAI | PCPS_SCALE_GPS )
+/** @} anchor PCPS_TIME_STATUS_FLAGS */
+
+
+
/**
- * Some DCF77 clocks have a serial interface that can be controlled
- * using the commands PCPS_SET_SERIAL and PCPS_GET_SERIAL. Both commands
- * use a parameter byte describing transmission speed, framing and mode
- * of operation. The parameter byte can be build using the constants
- * defined below, by or'ing one of the constants of each group, shifted
- * to the right position. PCPS_GET_SERIAL expects that parameter byte
- * and PCPS_GET_SERIAL returns the current configuration from the board.
+ * @brief Legacy definitions used to configure a device's serial port
+ *
+ * @deprecated This structure and the associated command codes
+ * are deprecated. ::PORT_SETTINGS, ::PORT_INFO and associated
+ * definitions should be used instead, if supported.
+ *
+ * @anchor PCPS_OLD_SERIAL_CFG @{ */
+
+/**
+ * @brief Configuration information for a device's serial port
+ *
+ * Used with ::PCPS_GET_SERIAL and ::PCPS_SET_SERIAL
+ *
+ * The serial interface on some old DCF77 clocks can be configured
+ * using the commands ::PCPS_SET_SERIAL and ::PCPS_GET_SERIAL.
+ * Both commands use a parameter byte describing transmission speed,
+ * framing and mode of operation. The parameter byte can be assembled
+ * using the constants defined in ::PCPS_BD_CODES, ::PCPS_FR_CODES,
+ * and ::PCPS_MOD_CODES, by or'ing one of the constants of each group,
+ * shifted to the right position. ::PCPS_GET_SERIAL expects that parameter
+ * byte and ::PCPS_GET_SERIAL returns the current configuration from
+ * the board.
* _pcps_has_serial() checks whether supported.
- * For GPS clocks, please refer to the comments for the PCPS_GET_SERIAL
+ * For old GPS clocks refer to the comments for the ::PCPS_GET_SERIAL
* command.
*/
+typedef uint8_t PCPS_SERIAL;
+
/**
- * Baud rate indices. The values below are obsolete and should
- * be replaced by the codes named MBG_BAUD_RATE_... which are
- * defined in gpsdefs.h. The resulting index numbers, however,
- * have not changed.
+ * @brief Deprecated baud rate indices
+ *
+ * @deprecated These values are deprecated.
+ * ::MBG_BAUD_RATE_CODES and associated structures
+ * should be used preferably.
+ *
+ * The sequence of codes matches the sequence
+ * defined in ::MBG_BAUD_RATE_CODES.
*/
-enum
+enum PCPS_BD_CODES
{
PCPS_BD_300,
PCPS_BD_600,
@@ -1232,95 +1287,225 @@ enum
PCPS_BD_4800,
PCPS_BD_9600,
PCPS_BD_19200,
- N_PCPS_BD /* number of codes */
+ N_PCPS_BD ///< number of codes
};
-#define PCPS_BD_BITS 4 /* field with in the cfg byte */
-#define PCPS_BD_SHIFT 0 /* num of bits to shift left */
+#define PCPS_BD_BITS 4 ///< field with in the cfg byte
+#define PCPS_BD_SHIFT 0 ///< num of bits to shift left
-/*
- * Initializers for a table of all baud rate strings
- * and values can be found in gpsdefs.h.
- */
/**
- * Unfortunately, the framing codes below can not simply be
- * replaced by the newer MBG_FRAMING_... definitions since
- * the order of indices does not match.
+ * @brief Deprecated framing code indices
+ *
+ * @deprecated These values are deprecated.
+ * ::MBG_FRAMING_CODES and associated structures
+ * should be used preferably.
+ *
+ * Unfortunately, these framing codes can *not* simply
+ * be replaced by the newer MBG_FRAMING_... definitions
+ * since the order of indices doesn't match.
*/
-enum
+enum PCPS_FR_CODES
{
PCPS_FR_8N1,
PCPS_FR_7E2,
PCPS_FR_8N2,
PCPS_FR_8E1,
- N_PCPS_FR_DCF /* number of valid codes */
+ N_PCPS_FR_DCF ///< number of valid codes
};
-#define PCPS_FR_BITS 2 /* field with in the cfg byte */
-#define PCPS_FR_SHIFT PCPS_BD_BITS /* num of bits to shift left */
+#define PCPS_FR_BITS 2 ///< field with in the cfg byte
+#define PCPS_FR_SHIFT PCPS_BD_BITS ///< num of bits to shift left
+
+
-/*
- * An initializer for a table of framing strings is only defined for
- * the new MBG_FRAMING_... definitions. For editing the serial port
- * configuration, the old codes above should be translated to the new
- * codes to unify handling inside the edit functions.
+/**
+ * @brief Deprecated codes for modes of operation
+ *
+ * @deprecated These values are deprecated.
+ * ::STR_MODES and associated structures
+ * should be used preferably.
+ *
+ * The sequence of codes matches the sequence
+ * defined in ::STR_MODES.
*/
+enum PCPS_MOD_CODES
+{
+ PCPS_MOD_REQ, ///< time string on request '?' only
+ PCPS_MOD_SEC, ///< time string once per second
+ PCPS_MOD_MIN, ///< time string once per minute
+ PCPS_MOD_RSVD, ///< reserved
+ N_PCPS_MOD_DCF ///< number of possible codes
+};
+
+#define PCPS_MOD_BITS 2 ///< field with in the cfg byte
+#define PCPS_MOD_SHIFT ( PCPS_BD_BITS + PCPS_FR_BITS ) ///< num of bits to shift left
-/**
- Modes of operation
+/** @} anchor PCPS_OLD_SERIAL_CFG */
- * Indices for modes of operation. The values below are obsolete
- * and should be replaced by the codes named STR_... which are
- * defined in gpsdefs.h. The resulting index numbers, however,
- * have not changed.
+
+
+/**
+ * @brief Type of variable to hold a TZ code
+ *
+ * This is used with the PCI interface but differs from ::TZCODE
+ * which is used with the binary protocol.
+ *
+ * @see ::TZCODE
+ * @see ::TZCODE_UNION
*/
-enum
+typedef uint8_t PCPS_TZCODE;
+
+
+/**
+ * @brief Enumeration of codes used with PCPS_TZCODE
+ */
+enum PCPS_TZCODES
{
- PCPS_MOD_REQ, /* time string on request '?' only */
- PCPS_MOD_SEC, /* time string once per second */
- PCPS_MOD_MIN, /* time string once per minute */
- PCPS_MOD_RSVD, /* reserved */
- N_PCPS_MOD_DCF /* number of possible codes */
+ PCPS_TZCODE_CET_CEST, ///< default as broadcasted by DCF77 (UTC+1h/UTC+2h)
+ PCPS_TZCODE_CET, ///< always CET (UTC+1h), discard DST
+ PCPS_TZCODE_UTC, ///< always %UTC
+ PCPS_TZCODE_EET_EEST, ///< East European Time, CET/CEST + 1h
+ N_PCPS_TZCODE ///< the number of valid codes
};
-#define PCPS_MOD_BITS 2 /* field with in the cfg byte */
-#define PCPS_MOD_SHIFT ( PCPS_BD_BITS + PCPS_FR_BITS )
- /* num of bits to shift left */
+/* the definitions below are for compatibily only: */
+#define PCPS_TZCODE_MEZMESZ PCPS_TZCODE_CET_CEST
+#define PCPS_TZCODE_MEZ PCPS_TZCODE_CET
+#define PCPS_TZCODE_OEZ PCPS_TZCODE_EET_EEST
/**
- * Some definitions used with PZF receivers
+ * @brief Daylight changeover specification
+ *
+ * Used as member field of ::PCPS_TZDL only. Most devices supporting
+ * conversion to local time support the ::TZDL structure instead.
+ *
+ * @see ::TZDL
*/
+typedef struct
+{
+ uint16_t year_or_wday; ///< The full year number, or 0..6 == Sun..Sat if the ::DL_AUTO_FLAG is set
+ uint8_t month; ///< [1..12]
+ uint8_t mday; ///< [1..31]
+ uint8_t hour; ///< [0..23]
+ uint8_t min; ///< [0..59]
-/* receiver distance from transmitter [km] */
-typedef uint16_t TR_DISTANCE;
+} PCPS_DL_ONOFF;
+
+#define _mbg_swab_pcps_dl_onoff( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->year_or_wday ); \
+} while ( 0 )
+
+/**
+ * @brief A flag indicating if DST changeovers are to be computed automatically
+ *
+ * If ::PCPS_DL_ONOFF::year_or_wday is or'ed with the constant ::DL_AUTO_FLAG
+ * then start and end of daylight saving time shall be computed automatically
+ * for each year. In this case the remaining bits represent the day-of-week
+ * after the specified mday/month at which the change shall occur.
+ * If that flag is not set then the field contains the full four-digit year number
+ * and the ::PCPS_DL_ONOFF::mday and ::PCPS_DL_ONOFF::month values specify
+ * the exact date of that year. Most devices supporting conversion to local time
+ * support the ::TZDL structure instead.
+ *
+ * @see ::TZDL
+ * @see ::PCPS_TZDL
+ */
+#define DL_AUTO_FLAG 0x8000 // also defined in gpsdefs.h
+
+
+/**
+ * @brief Specification of a local time zone
+ *
+ * Most devices supporting conversion to local time support
+ * the ::TZDL structure instead.
+ *
+ * @see ::DL_AUTO_FLAG
+ * @see ::TZDL
+ */
+typedef struct
+{
+ int16_t offs; ///< offset from %UTC to local time [min] (local time = %UTC + offs)
+ int16_t offs_dl; ///< additional offset if DST enabled [min] (DST time = local time + offs_dl)
+ PCPS_DL_ONOFF tm_on; ///< date/time when daylight saving starts
+ PCPS_DL_ONOFF tm_off; ///< date/time when daylight saving ends
+
+} PCPS_TZDL;
+
+#define _mbg_swab_pcps_tzdl( _p ) \
+do \
+{ \
+ _mbg_swab16( &(_p)->offs ); \
+ _mbg_swab16( &(_p)->offs_dl ); \
+ _mbg_swab_pcps_dl_onoff( &(_p)->tm_on ); \
+ _mbg_swab_pcps_dl_onoff( &(_p)->tm_off ); \
+} while ( 0 )
+
+
+
+/**
+ * @brief Status of the time capture FIFO buffer
+ *
+ * Only supported if ::RECEIVER_INFO::n_ucaps > 0.
+ */
+typedef struct
+{
+ uint32_t used; ///< the number of saved capture events
+ uint32_t max; ///< capture buffer size
+
+} PCPS_UCAP_ENTRIES;
+
+#define _mbg_swab_pcps_ucap_entries( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->used ); \
+ _mbg_swab32( &(_p)->max ); \
+} while ( 0 )
+
+
+
+/**
+ * @defgroup group_pzf_supp Definitions used with PZF receivers
+ *
+ * @{ */
+
+/**
+ * @brief Receiver distance from transmitter [km]
+ */
+typedef uint16_t TR_DISTANCE; ///< Range may vary with receiver type
#define _mbg_swab_tr_distance( _p ) \
_mbg_swab16( _p )
-
-/* correlation status info */
+/**
+ * @brief PZF correlation status info
+ */
typedef struct
{
- uint8_t val; /**< correlation value, or check count if status == PZF_CORR_CHECK */
- uint8_t status; /**< status codes, see below */
- char corr_dir; /**< space, '<', or '>' */
- uint8_t signal; /**< signal level, may always be 0 for devices which do not support this */
+ uint8_t val; ///< correlation value, or check count if status ==:: PZF_CORR_CHECK
+ uint8_t status; ///< status codes, see ::PZF_CORR_STATES
+ char corr_dir; ///< space, '<', or '>', just for information
+ PCPS_SIG_VAL signal; ///< signal strength, see @ref PCPS_SIG_VAL_DEFS
+
} CORR_INFO;
#define _mbg_swab_corr_info( _p ) \
_nop_macro_fnc()
-/** Codes used with CORR_INFO::status: */
-enum
+/**
+ * @brief Codes used with ::CORR_INFO::status
+ */
+enum PZF_CORR_STATES
{
- PZF_CORR_RAW, /**< trying raw correlation, combi receivers running in AM mode */
- PZF_CORR_CHECK, /**< raw correlation achieved, doing plausibility checks */
- PZF_CORR_FINE, /**< fine correlation achieved */
+ PZF_CORR_RAW, ///< trying raw correlation, combi receivers running in AM mode
+ PZF_CORR_CHECK, ///< raw correlation achieved, doing plausibility checks
+ PZF_CORR_FINE, ///< fine correlation achieved
N_PZF_CORR_STATE
};
@@ -1349,142 +1534,182 @@ enum
{ PZF_CORR_STATE_NAME_FINE_ENG, PZF_CORR_STATE_NAME_FINE_GER } \
}
+/** @} defgroup group_pzf_supp */
-/** @defgroup group_gps_cmds_bus GPS commands passed via the system bus
- This enumeration defines the various types of data that can be read
- from or written to Meinberg bus level devices which support this.
- Access should be done using the functions pcps_read_gps_data()
- and pcps_write_gps_data() since the size of some of the structures
- exceeds the size of the device's I/O buffer and must therefore be
- accessed in several blocks.
-
- The structures to be used are defined in gpsdefs.h. Not all structures
- are supported, yet. Check the R/W indicators for details.
-
- * @{ */
-enum
-{ // R/W data type description
- // system data -----------------------------------------------
- PC_GPS_TZDL = 0, // R/W TZDL time zone / daylight saving
- PC_GPS_SW_REV, // R/- SW_REV software revision
- PC_GPS_BVAR_STAT, // R/- BVAR_STAT status of buffered variables
- PC_GPS_TIME, // R/W TTM curr. time
- PC_GPS_POS_XYZ, // -/W XYZ curr. pos. in ECEF coords
- PC_GPS_POS_LLA, // -/W LLA curr. pos. in geogr. coords
- PC_GPS_PORT_PARM, // R/W PORT_PARM param. of the serial ports
- PC_GPS_ANT_INFO, // R/- ANT_INFO time diff after ant. disconn.
- PC_GPS_UCAP, // R/- TTM user capture
- PC_GPS_ENABLE_FLAGS, // R/W ENABLE_FLAGS controls when to enable outp.
- PC_GPS_STAT_INFO, // R/- GPS_STAT_INFO
- PC_GPS_CMD, // -/W GPS_CMD commands as described below
- PC_GPS_IDENT, // R/- GPS_IDENT serial number
- PC_GPS_POS, // R/- POS position XYZ, LLA, and DMS
- PC_GPS_ANT_CABLE_LEN, // R/W ANT_CABLE_LEN used to compensate delay
- // The codes below are supported by new GPS receiver boards:
- PC_GPS_RECEIVER_INFO, // R/- RECEIVER_INFO rcvr model info
- PC_GPS_ALL_STR_TYPE_INFO, // R/- n*STR_TYPE_INFO_IDX all string types
- PC_GPS_ALL_PORT_INFO, // R/- n*PORT_INFO_IDX all port info
- PC_GPS_PORT_SETTINGS_IDX, // -/W PORT_SETTINGS_IDX port settings only
- PC_GPS_ALL_POUT_INFO, // R/- n*POUT_INFO_IDX all pout info
- PC_GPS_POUT_SETTINGS_IDX, // -/W POUT_SETTINGS_IDX pout settings only
- PC_GPS_TIME_SCALE, // R/W MBG_TIME_SCALE_{SETTINGS|INFO}, only if PCPS_HAS_TIME_SCALE
- PC_GPS_LAN_IF_INFO, // R/- LAN_IF_INFO LAN interface info, only if PCPS_HAS_LAN_INTF
- PC_GPS_IP4_STATE, // R/- IP4_SETTINGS LAN interface state, only if PCPS_HAS_LAN_INTF
- PC_GPS_IP4_SETTINGS, // R/W IP4_SETTINGS LAN interface configuration, only if PCPS_HAS_LAN_INTF
- PC_GPS_PTP_STATE, // R/- PTP_STATE, only if PCPS_HAS_PTP
- PC_GPS_PTP_CFG, // R/W PTP_CFG_{SETTINGS|INFO}, only if PCPS_HAS_PTP
- PC_GPS_PTP_UC_MASTER_CFG_LIMITS, // R/- PTP_UC_MASTER_CFG_LIMITS, only if can be unicast master
- PC_GPS_ALL_PTP_UC_MASTER_INFO, // R/- n*PTP_UC_MASTER_INFO_IDX, only if can be unicast master
- PC_GPS_PTP_UC_MASTER_SETTINGS_IDX, // -/W PTP_UC_MASTER_SETTINGS_IDX, only if can be unicast master
- PC_GPS_GPIO_CFG_LIMITS, // R/- MBG_GPIO_CFG_LIMITS, only if PCPS_HAS_GPIO
- PC_GPS_ALL_GPIO_INFO, // R/- n*MBG_GPIO_INFO, all GPIO info, only if PCPS_HAS_GPIO
- PC_GPS_GPIO_SETTINGS_IDX, // -/W MBG_GPIO_SETTINGS_IDX, GPIO cfg for a specific port, only if PCPS_HAS_GPIO
+/**
+ * @brief GPS Command codes passed via the system bus
+ *
+ * Codes specifying various types of data that can be read from or
+ * written to Meinberg bus level devices which support this.
+ * Access is done using the low level functions ::pcps_read_gps
+ * and ::pcps_write_gps since the size of some of the structures
+ * exceeds the size of the device's I/O buffer and must therefore be
+ * accessed in several blocks.
+ *
+ * Applications should instead use the API functions declared in mbgdevio.h.
+ *
+ * The structures to be used are defined in gpsdefs.h. Not all structures
+ * are supported, yet. Check the r/w indicators for details.
+ *
+ * @see @ref PCPS_CMD_CODES
+ * @see ::PC_GPS_CMD_CODES_TABLE
+ */
+enum PC_GPS_CMD_CODES
+{
+ PC_GPS_TZDL, ///< (r/w) ::TZDL, time zone / daylight saving, only if ::GPS_MODEL_HAS_TZDL
+ PC_GPS_SW_REV, ///< (r/-) ::SW_REV, software revision, deprecated by ::PC_GPS_RECEIVER_INFO
+ PC_GPS_BVAR_STAT, ///< (r/-) ::BVAR_STAT, status of buffered variables, only if ::GPS_MODEL_HAS_BVAR_STAT
+ PC_GPS_TIME, ///< (r/w) ::TTM, current time, deprecated by ::PCPS_GIVE_HR_TIME
+ PC_GPS_POS_XYZ, ///< (-/w) ::XYZ, current position in ECEF coordinates, only if ::GPS_MODEL_HAS_POS_XYZ
+ PC_GPS_POS_LLA, ///< (-/w) ::LLA, current position in geographic coordinates, only if ::GPS_MODEL_HAS_POS_LLA
+ PC_GPS_PORT_PARM, ///< (r/w) ::PORT_PARM, param. of the serial ports, deprecated by ::PC_GPS_ALL_PORT_INFO
+ PC_GPS_ANT_INFO, ///< (r/-) ::ANT_INFO, time diff at sync. after antenna had been disconn., only if ::GPS_MODEL_HAS_ANT_INFO
+
+ PC_GPS_UCAP, ///< (r/-) ::TTM, user capture events, deprecated by ::PCPS_GIVE_UCAP_EVENT
+ PC_GPS_ENABLE_FLAGS, ///< (r/w) ::ENABLE_FLAGS, when to enable serial, pulses, and synth, only if ::GPS_MODEL_HAS_ENABLE_FLAGS
+ PC_GPS_STAT_INFO, ///< (r/-) ::GPS_STAT_INFO, satellite info, mode of operation, and DAC info, only if ::GPS_MODEL_HAS_STAT_INFO
+ PC_GPS_CMD, ///< (-/w) ::GPS_CMD, send one of the ::PC_GPS_COMMANDS
+ PC_GPS_IDENT, ///< (r/-) ::IDENT, serial number, deprecated by ::PC_GPS_RECEIVER_INFO
+ PC_GPS_POS, ///< (r/-) ::POS, position ::XYZ, ::LLA, and ::DMS combined, only if ::GPS_MODEL_HAS_POS
+ PC_GPS_ANT_CABLE_LEN, ///< (r/w) ::ANT_CABLE_LEN, length of antenna cable, only if ::GPS_MODEL_HAS_ANT_CABLE_LEN
+ PC_GPS_RECEIVER_INFO, ///< (r/-) ::RECEIVER_INFO, rcvr model info, only if ::PCPS_HAS_RECEIVER_INFO
+
+ PC_GPS_ALL_STR_TYPE_INFO, ///< (r/-) n * ::STR_TYPE_INFO_IDX, names and capabilities of all supp. string types, only if ::RECEIVER_INFO::n_str_type > 0
+ PC_GPS_ALL_PORT_INFO, ///< (r/-) n * ::PORT_INFO_IDX, settings and capabilities of all serial ports, only if ::RECEIVER_INFO::n_com_ports > 0
+ PC_GPS_PORT_SETTINGS_IDX, ///< (-/w) ::PORT_SETTINGS_IDX, settings for specified serial port, only if ::RECEIVER_INFO::n_com_ports > 0
+ PC_GPS_ALL_POUT_INFO, ///< (r/-) n * ::POUT_INFO_IDX, all programmable output info
+ PC_GPS_POUT_SETTINGS_IDX, ///< (-/w) ::POUT_SETTINGS_IDX, settings for one programmable output
+ PC_GPS_TIME_SCALE, ///< (r/w) ::MBG_TIME_SCALE_SETTINGS / ::MBG_TIME_SCALE_INFO, only if ::PCPS_HAS_TIME_SCALE
+ PC_GPS_LAN_IF_INFO, ///< (r/-) ::LAN_IF_INFO, LAN interface info, only if ::PCPS_HAS_LAN_INTF
+ PC_GPS_IP4_STATE, ///< (r/-) ::IP4_SETTINGS, LAN interface state, only if ::PCPS_HAS_LAN_INTF
+
+ PC_GPS_IP4_SETTINGS, ///< (r/w) ::IP4_SETTINGS, LAN interface configuration, only if ::PCPS_HAS_LAN_INTF
+ PC_GPS_PTP_STATE, ///< (r/-) ::PTP_STATE, only if ::PCPS_HAS_PTP
+ PC_GPS_PTP_CFG, ///< (r/w) ::PTP_CFG_SETTINGS / ::PTP_CFG_INFO, only if ::PCPS_HAS_PTP
+ PC_GPS_PTP_UC_MASTER_CFG_LIMITS, ///< (r/-) ::PTP_UC_MASTER_CFG_LIMITS, only if ::PTP_CFG_MSK_SUPPORT_PTP_UNICAST
+ PC_GPS_ALL_PTP_UC_MASTER_INFO, ///< (r/-) n * ::PTP_UC_MASTER_INFO_IDX, only if ::PTP_CFG_MSK_SUPPORT_PTP_UNICAST
+ PC_GPS_PTP_UC_MASTER_SETTINGS_IDX, ///< (-/w) ::PTP_UC_MASTER_SETTINGS_IDX, only if ::PTP_CFG_MSK_SUPPORT_PTP_UNICAST
+ PC_GPS_GPIO_CFG_LIMITS, ///< (r/-) ::MBG_GPIO_CFG_LIMITS, only if ::GPS_HAS_GPIO
+ PC_GPS_ALL_GPIO_INFO, ///< (r/-) n * ::MBG_GPIO_INFO_IDX, all GPIO info, only if ::GPS_HAS_GPIO
+
+ PC_GPS_GPIO_SETTINGS_IDX, ///< (-/w) ::MBG_GPIO_SETTINGS_IDX, settings for a specific port, only if ::GPS_HAS_GPIO
+ PC_GPS_GNSS_MODE, ///< (r/w) ::MBG_GNSS_MODE_INFO / ::MBG_GNSS_MODE_SETTINGS, only if ::PCPS_IS_GNSS
+ PC_GPS_ALL_GNSS_SAT_INFO, ///< (r/-) n * ::GNSS_SAT_INFO_IDX, satellite info, only if ::PCPS_IS_GNSS
+ PC_GPS_XMR_INSTANCES, ///< (r/-) ::XMULTI_REF_INSTANCES, only if ::GPS_HAS_XMULTI_REF and ::GPS_HAS_XMRS_MULT_INSTC
+ PC_GPS_XMR_SETTINGS_IDX, ///< (-/w) ::XMULTI_REF_SETTINGS_IDX, idx 0..::XMULTI_REF_INSTANCES::n_xmr_settings-1, only if ::GPS_HAS_XMULTI_REF
+ PC_GPS_ALL_XMR_INFO, ///< (r/-) n * ::XMULTI_REF_INFO_IDX, where n == ::XMULTI_REF_INSTANCES::n_xmr_settings, only if ::GPS_HAS_XMULTI_REF
+ PC_GPS_ALL_XMR_STATUS, ///< (r/w) n * ::XMULTI_REF_STATUS_IDX, where n == ::XMULTI_REF_INSTANCES::n_xmr_settings, one structure on write, only if ::GPS_HAS_XMULTI_REF
+ PC_GPS_XMR_HOLDOVER_STATUS, ///< (r/-) ::XMR_HOLDOVER_STATUS, only if ::XMRIF_MSK_HOLDOVER_STATUS_SUPP
+
+ PC_GPS_ALL_GPIO_STATUS, ///< (r/-) n * ::MBG_GPIO_STATUS_IDX, where n == ::MBG_GPIO_CFG_LIMITS::num_io, only if ::MBG_GPIO_CFG_LIMIT_FLAG_MASK_STATUS_SUPP
+ PC_GPS_XFEATURE_BUFFER, ///< (r/-) ::MBG_XFEATURE_BUFFER, only if ::GPS_HAS_XFEATURE
+ PC_GPS_TLV_INFO, ///< (r/-) ::MBG_TLV_INFO, only if ::MBG_XFEATURE_TLV_API
// GPS data
- PC_GPS_CFGH = 0x80, // -/- CFGH SVs' config. and health codes
- PC_GPS_ALM, // -/- SV_ALM one SV's num and almanac
- PC_GPS_EPH, // -/- SV_EPH one SV's num and ephemeris
- PC_GPS_UTC, // R/W UTC %UTC corr. param., only if PCPS_HAS_UTC_PARM
- PC_GPS_IONO, // -/- IONO ionospheric corr. param.
- PC_GPS_ASCII_MSG // -/- ASCII_MSG the GPS ASCII message
+ PC_GPS_CFGH = 0x80, ///< (-/-) ::CFGH, SVs' config. and health codes (yet not used)
+ PC_GPS_ALM, ///< (-/-) ::SV_ALM, one SV's num and almanac (yet not used)
+ PC_GPS_EPH, ///< (-/-) ::SV_EPH, one SV's num and ephemeris (yet not used)
+ PC_GPS_UTC, ///< (r/w) ::UTC, %UTC corr. param., only if ::PCPS_HAS_UTC_PARM
+ PC_GPS_IONO, ///< (-/-) ::IONO, ionospheric corr. param. (yet not used)
+ PC_GPS_ASCII_MSG ///< (-/-) ::ASCII_MSG, the GPS ASCII message (yet not used)
};
-/** @} group_gps_cmds_bus */
-
/**
* @brief An initializer for a table of code/name entries of GPS commands.
*
- * This can e.g. be assigned to an array of MBG_CODE_NAME_TABLE_ENTRY elements
+ * This can e.g. be assigned to an array of ::MBG_CODE_NAME_TABLE_ENTRY elements
* and may be helpful when debugging.
+ *
+ * @see ::PC_GPS_CMD_CODES
*/
-#define MBG_PC_GPS_CMD_TABLE \
-{ \
- { PC_GPS_TZDL, "PC_GPS_TZDL" }, \
- { PC_GPS_SW_REV, "PC_GPS_SW_REV" }, \
- { PC_GPS_BVAR_STAT, "PC_GPS_BVAR_STAT" }, \
- { PC_GPS_TIME, "PC_GPS_TIME" }, \
- { PC_GPS_POS_XYZ, "PC_GPS_POS_XYZ" }, \
- { PC_GPS_POS_LLA, "PC_GPS_POS_LLA" }, \
- { PC_GPS_PORT_PARM, "PC_GPS_PORT_PARM" }, \
- { PC_GPS_ANT_INFO, "PC_GPS_ANT_INFO" }, \
- { PC_GPS_UCAP, "PC_GPS_UCAP" }, \
- { PC_GPS_ENABLE_FLAGS, "PC_GPS_ENABLE_FLAGS" }, \
- { PC_GPS_STAT_INFO, "PC_GPS_STAT_INFO" }, \
- { PC_GPS_CMD, "PC_GPS_CMD" }, \
- { PC_GPS_IDENT, "PC_GPS_IDENT" }, \
- { PC_GPS_POS, "PC_GPS_POS" }, \
- { PC_GPS_ANT_CABLE_LEN, "PC_GPS_ANT_CABLE_LEN" }, \
- { PC_GPS_RECEIVER_INFO, "PC_GPS_RECEIVER_INFO" }, \
- { PC_GPS_ALL_STR_TYPE_INFO, "PC_GPS_ALL_STR_TYPE_INFO" }, \
- { PC_GPS_ALL_PORT_INFO, "PC_GPS_ALL_PORT_INFO" }, \
- { PC_GPS_PORT_SETTINGS_IDX, "PC_GPS_PORT_SETTINGS_IDX" }, \
- { PC_GPS_ALL_POUT_INFO, "PC_GPS_ALL_POUT_INFO" }, \
- { PC_GPS_POUT_SETTINGS_IDX, "PC_GPS_POUT_SETTINGS_IDX" }, \
- { PC_GPS_TIME_SCALE, "PC_GPS_TIME_SCALE" }, \
- { PC_GPS_LAN_IF_INFO, "PC_GPS_LAN_IF_INFO" }, \
- { PC_GPS_IP4_STATE, "PC_GPS_IP4_STATE" }, \
- { PC_GPS_IP4_SETTINGS, "PC_GPS_IP4_SETTINGS" }, \
- { PC_GPS_PTP_STATE, "PC_GPS_PTP_STATE" }, \
- { PC_GPS_PTP_CFG, "PC_GPS_PTP_CFG" }, \
- { PC_GPS_PTP_UC_MASTER_CFG_LIMITS, "PC_GPS_PTP_UC_MASTER_CFG_LIMITS" }, \
- { PC_GPS_ALL_PTP_UC_MASTER_INFO, "PC_GPS_ALL_PTP_UC_MASTER_INFO" }, \
- { PC_GPS_PTP_UC_MASTER_SETTINGS_IDX, "PC_GPS_PTP_UC_MASTER_SETTINGS_IDX" }, \
- { PC_GPS_GPIO_CFG_LIMITS, "PC_GPS_GPIO_CFG_LIMITS" }, \
- { PC_GPS_ALL_GPIO_INFO, "PC_GPS_ALL_GPIO_INFO" }, \
- { PC_GPS_GPIO_SETTINGS_IDX, "PC_GPS_GPIO_SETTINGS_IDX" }, \
- { PC_GPS_CFGH, "PC_GPS_CFGH" }, \
- { PC_GPS_ALM, "PC_GPS_ALM" }, \
- { PC_GPS_EPH, "PC_GPS_EPH" }, \
- { PC_GPS_UTC, "PC_GPS_UTC" }, \
- { PC_GPS_IONO, "PC_GPS_IONO" }, \
- { PC_GPS_ASCII_MSG, "PC_GPS_ASCII_MSG" }, \
- { 0, NULL } \
+#define PC_GPS_CMD_CODES_TABLE \
+{ \
+ _mbg_cn_table_entry( PC_GPS_TZDL ), \
+ _mbg_cn_table_entry( PC_GPS_SW_REV ), \
+ _mbg_cn_table_entry( PC_GPS_BVAR_STAT ), \
+ _mbg_cn_table_entry( PC_GPS_TIME ), \
+ _mbg_cn_table_entry( PC_GPS_POS_XYZ ), \
+ _mbg_cn_table_entry( PC_GPS_POS_LLA ), \
+ _mbg_cn_table_entry( PC_GPS_PORT_PARM ), \
+ _mbg_cn_table_entry( PC_GPS_ANT_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_UCAP ), \
+ _mbg_cn_table_entry( PC_GPS_ENABLE_FLAGS ), \
+ _mbg_cn_table_entry( PC_GPS_STAT_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_CMD ), \
+ _mbg_cn_table_entry( PC_GPS_IDENT ), \
+ _mbg_cn_table_entry( PC_GPS_POS ), \
+ _mbg_cn_table_entry( PC_GPS_ANT_CABLE_LEN ), \
+ _mbg_cn_table_entry( PC_GPS_RECEIVER_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_ALL_STR_TYPE_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_ALL_PORT_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_PORT_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( PC_GPS_ALL_POUT_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_POUT_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( PC_GPS_TIME_SCALE ), \
+ _mbg_cn_table_entry( PC_GPS_LAN_IF_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_IP4_STATE ), \
+ _mbg_cn_table_entry( PC_GPS_IP4_SETTINGS ), \
+ _mbg_cn_table_entry( PC_GPS_PTP_STATE ), \
+ _mbg_cn_table_entry( PC_GPS_PTP_CFG ), \
+ _mbg_cn_table_entry( PC_GPS_PTP_UC_MASTER_CFG_LIMITS ), \
+ _mbg_cn_table_entry( PC_GPS_ALL_PTP_UC_MASTER_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_PTP_UC_MASTER_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( PC_GPS_GPIO_CFG_LIMITS ), \
+ _mbg_cn_table_entry( PC_GPS_ALL_GPIO_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_GPIO_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( PC_GPS_GNSS_MODE ), \
+ _mbg_cn_table_entry( PC_GPS_ALL_GNSS_SAT_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_XMR_INSTANCES ), \
+ _mbg_cn_table_entry( PC_GPS_XMR_SETTINGS_IDX ), \
+ _mbg_cn_table_entry( PC_GPS_ALL_XMR_INFO ), \
+ _mbg_cn_table_entry( PC_GPS_ALL_XMR_STATUS ), \
+ _mbg_cn_table_entry( PC_GPS_XMR_HOLDOVER_STATUS ), \
+ _mbg_cn_table_entry( PC_GPS_ALL_GPIO_STATUS ), \
+ _mbg_cn_table_entry( PC_GPS_XFEATURE_BUFFER ), \
+ _mbg_cn_table_entry( PC_GPS_TLV_INFO ), \
+ \
+ _mbg_cn_table_entry( PC_GPS_CFGH ), \
+ _mbg_cn_table_entry( PC_GPS_ALM ), \
+ _mbg_cn_table_entry( PC_GPS_EPH ), \
+ _mbg_cn_table_entry( PC_GPS_UTC ), \
+ _mbg_cn_table_entry( PC_GPS_IONO ), \
+ _mbg_cn_table_entry( PC_GPS_ASCII_MSG ), \
+ _mbg_cn_table_end() \
}
-/** codes used with PC_GPS_CMD */
-enum
+/**
+ * @brief Codes used with ::PC_GPS_CMD
+ *
+ * @note These commands should only used with care, in very rare cases!
+ */
+enum PC_GPS_COMMANDS //##++++++++++++++
{
- PC_GPS_CMD_BOOT = 1, /**< force the clock to boot mode */
- PC_GPS_CMD_INIT_SYS, /**< let the clock clear its system variables */
- PC_GPS_CMD_INIT_USER, /**< reset the clock's user parameters to defaults */
- PC_GPS_CMD_INIT_DAC, /**< initialize the oscillator disciplining values */
- N_PC_GPS_CMD /**< no command, just the number of known commands */
+ PC_GPS_CMD_BOOT = 1, ///< force a GPS receiver to boot mode
+ PC_GPS_CMD_INIT_SYS, ///< let the clock clear its system variables
+ PC_GPS_CMD_INIT_USER, ///< reset the clock's user parameters to defaults
+ PC_GPS_CMD_INIT_DAC, ///< initialize the oscillator disciplining values
+ N_PC_GPS_CMD_CODES ///< no command, just the number of known commands
};
-// The type below can be used to store an unambiguous command code.
-// In case of the standard PCPS_... commands the lower byte contains
-// the command code and the upper byte is 0.
-// In case of a GPS command the lower byte contains PCPS_READ_GPS_DATA
-// or PCPS_WRITE_GPS_DATA, as appropriate, and the upper byte contains
-// the associated PC_GPS_... type code.
+/**
+ * @brief A type used to store an unambiguous command code
+ *
+ * In case of the standard @ref PCPS_CMD_CODES the lower byte contains
+ * the command code and the upper byte is 0.
+ * In case of a GPS command the lower byte contains ::PCPS_READ_GPS_DATA
+ * or ::PCPS_WRITE_GPS_DATA, as appropriate, and the upper byte contains
+ * the associated type code from ::PC_GPS_CMD_CODES.
+ *
+ * Used internally by the firmware only.
+ */
typedef uint16_t PCPS_CMD_INFO;
@@ -1493,6 +1718,8 @@ typedef uint16_t PCPS_CMD_INFO;
#undef _USING_BYTE_ALIGNMENT
#endif
+#define _PCPSDEFS_H_INCLUDED
+
/* End of header body */
#endif /* _PCPSDEFS_H */
diff --git a/mbglib/common/pcpsdev.h b/mbglib/common/pcpsdev.h
index 63cb67b..ded733d 100755
--- a/mbglib/common/pcpsdev.h
+++ b/mbglib/common/pcpsdev.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcpsdev.h 1.51.1.2 2013/06/25 09:52:00 martin TRASH $
+ * $Id: pcpsdev.h 1.55 2017/04/25 11:36:40 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -17,9 +17,29 @@
*
* -----------------------------------------------------------------------
* $Log: pcpsdev.h $
- * Revision 1.51.1.2 2013/06/25 09:52:00 martin
- * Support GLN180PEX.
- * Revision 1.51.1.1 2013/05/08 10:56:53 martin
+ * Revision 1.55 2017/04/25 11:36:40 martin
+ * Renamed GRC181PEX to GNS181PEX.
+ * Revision 1.54 2017/01/27 09:10:57 martin
+ * Support GPS180AMC.
+ * Support GRC181PEX.
+ * Support GPIO ports.
+ * IRIG TX support for GPS180PEX and TCR180PEX only
+ * if GPS_HAS_IRIG_TX flag is set.
+ * New type PCPS_FW_REV_NUM.
+ * Moved some code to new module mbgsystm.h.
+ * Moved NANO_TIME_64 to gpsdefs.h.
+ * Moved inline function num_bits_set() to cfg_hlp.h.
+ * Added macro _ri_addr().
+ * Added macro _pcps_has_ri_xmr().
+ * Fixed macro syntax.
+ * Doxygen stuff.
+ * Removed trailing spaces.
+ * Cleanup.
+ * Revision 1.53 2013/11/08 08:46:00 martin
+ * Doxygen comment updates.
+ * Revision 1.52 2013/09/26 09:06:47Z martin
+ * Support GLN180PEX and GNSS API.
+ * Added inline fnc num_bits_set().
* Revision 1.51 2013/01/25 15:44:21 martin
* Added inline function setup_hr_time_cycles_from_timestamp_cycles() which sets
* up a PCPS_HR_TIME_CYCLES structure from PCPS_TIME_STAMP_CYCLES.
@@ -91,7 +111,7 @@
* Moved some inline functions dealing with MBG_PC_CYCLES
* from mbgdevio.h here.
* Merged the code from _pcps_get_cycles() and _pcps_get_cycles_frequency()
- * to the mbg_get_pc_cycles...() inline functions which now replace the
+ * to the mbg_get_pc_cycles...() inline functions which now replace the
* _pcps_get_cycles...() macros.
* Fixed cycles code for non-x86 architectures.
* Revision 1.39 2008/12/05 16:24:24Z martin
@@ -102,7 +122,7 @@
* Defined firmware version numbers which fix an IRQ problem with PEX511,
* TCR511PEX, and GPS170PEX cards. The fix also requires specific ASIC
* versions specified in pci_asic.h.
- * Defined firmware versions at which PCI511 and PEX511 start
+ * Defined firmware versions at which PCI511 and PEX511 start
* to support HR time.
* Support mapped I/O resources.
* Changed MBG_PC_CYCLES type for Windows to int64_t.
@@ -122,11 +142,11 @@
* _psps_has_asic_version(), _pcps_has_asic_features().
* Revision 1.37 2008/01/17 09:58:11Z daniel
* Made comments compatible for doxygen parser.
- * No sourcecode changes.
+ * No sourcecode changes.
* Revision 1.36 2007/09/26 09:34:38Z martin
* Added support for USB in general and new USB device USB5131.
* Added new types PCPS_DEV_ID and PCPS_REF_TYPE.
- * Removed old PCPS_ERR_... codes. Use MBG_ERR_... codes
+ * Removed old PCPS_ERR_... codes. Use MBG_ERR_... codes
* from mbgerror.h instead. The old values haven't changed.
* Revision 1.35 2007/07/17 08:22:47Z martin
* Added support for TCR511PEX and GPS170PEX.
@@ -139,15 +159,15 @@
* Preliminary support for *BSD.
* Preliminary support for USB.
* Revision 1.32 2006/10/23 08:47:55Z martin
- * Don't use abs() in _pcps_ref_offs_out_of_range() since this might
+ * Don't use abs() in _pcps_ref_offs_out_of_range() since this might
* not work properly for 16 bit integers and value 0x8000.
* Revision 1.31 2006/06/14 12:59:13Z martin
* Added support for TCR511PCI.
* Revision 1.30 2006/04/05 14:58:41 martin
* Support higher baud rates for PCI511.
* Revision 1.29 2006/04/03 07:29:07Z martin
- * Added a note about the missing PCPS_ST_IRQF signal
- * on PCI510 cards.
+ * Added a note about the missing PCPS_ST_IRQF signal
+ * on PCI510 cards.
* Revision 1.28 2006/03/10 10:32:56Z martin
* Added support for PCI511.
* Added support for programmable pulse outputs.
@@ -168,8 +188,8 @@
* New type PCPS_STATUS_PORT.
* Removed obsolete inclusion of asm/timex.h for Linux.
* Revision 1.21 2004/09/06 15:19:49Z martin
- * Support a GPS_DATA interface where sizes are specified
- * by 16 instead of the original 8 bit quantities, thus allowing
+ * Support a GPS_DATA interface where sizes are specified
+ * by 16 instead of the original 8 bit quantities, thus allowing
* to transfer data blocks which exceed 255 bytes.
* Modified inclusion of header files under Linux.
* Modified definition of MBG_PC_CYCLES for Linux.
@@ -248,6 +268,7 @@
#include <mbg_tgt.h>
#include <mbgtime.h>
+#include <mbgsystm.h>
#include <mbgpccyc.h>
#include <pcpsdefs.h>
#include <gpsdefs.h>
@@ -258,20 +279,10 @@
#include <string.h>
#endif
-#if defined( MBG_TGT_WIN32 )
-
- #include <mbg_w32.h>
-
-#elif defined( MBG_TGT_LINUX )
+#if defined( MBG_TGT_LINUX )
- #if defined( MBG_TGT_KERNEL )
- #include <linux/delay.h>
- #include <linux/time.h>
- #else
+ #if !defined( MBG_TGT_KERNEL )
#include <unistd.h>
- #include <time.h>
- #include <sys/time.h>
- #include <sys/sysinfo.h>
#endif
#elif defined( MBG_TGT_FREEBSD )
@@ -318,55 +329,14 @@
#endif
-#if defined( MBG_TGT_UNIX )
- #define USE_GENERIC_SYS_TIME 1
-#else
- #define USE_GENERIC_SYS_TIME 0
-#endif
-
-
-#if USE_GENERIC_SYS_TIME
-
- typedef struct
- {
- uint64_t sec;
- uint64_t nsec;
- } NANO_TIME_64;
-
- typedef NANO_TIME_64 MBG_SYS_TIME;
-
-#endif
-
-
-
-/**
- Define generic types to hold PC cycle counter values and system timestamps.
- The generic types are defined using native types used by the target operating
- systems.
-
- The cycle counter value is usually derived from the PC CPU's TSC or some other
- timer hardware on the mainboard.
- */
-#if defined( MBG_TGT_WIN32 )
-
- #define MBG_TGT_SUPP_MEM_ACC 1
-
- typedef int64_t MBG_SYS_UPTIME; // [s]
-
- typedef LARGE_INTEGER MBG_SYS_TIME;
-
-#elif defined( MBG_TGT_LINUX )
+#if defined( MBG_TGT_LINUX )
#define MBG_TGT_SUPP_MEM_ACC 1
- typedef int64_t MBG_SYS_UPTIME; // [s]
-
#elif defined( MBG_TGT_BSD )
#define MBG_TGT_SUPP_MEM_ACC 1
- typedef int64_t MBG_SYS_UPTIME; // [s]
-
#if defined( MBG_TGT_NETBSD )
#ifdef __LP64__
#define MBG_MEM_ADDR uint64_t
@@ -375,26 +345,14 @@
#endif
#endif
-#elif defined( MBG_TGT_OS2 )
+#elif defined( MBG_TGT_WIN32 )
- typedef long MBG_SYS_UPTIME; //## dummy
-
- typedef uint32_t MBG_SYS_TIME; //## dummy
+ #define MBG_TGT_SUPP_MEM_ACC 1
#elif defined( MBG_TGT_DOS )
#define MBG_MEM_ADDR uint32_t // 64 bit not supported, nor required.
- typedef long MBG_SYS_UPTIME; //## dummy
-
- typedef uint32_t MBG_SYS_TIME; //## dummy
-
-#else // other target OSs which access the hardware directly
-
- typedef long MBG_SYS_UPTIME; //## dummy
-
- typedef uint32_t MBG_SYS_TIME; //## dummy
-
#endif
@@ -403,332 +361,55 @@
#endif
-// MBG_SYS_TIME is always read in native machine endianess,
-// so no endianess conversion is required.
-#define _mbg_swab_mbg_sys_time( _p ) \
- _nop_macro_fnc()
+#if !defined( MBG_MEM_ADDR )
+ // By default a memory address is stored
+ // as a 64 bit quantitiy.
+ #define MBG_MEM_ADDR uint64_t
+#endif
+
+
+
+typedef uint8_t MBG_DBG_DATA;
+typedef uint16_t MBG_DBG_PORT;
/**
- The structure holds a system timestamp in a format depending on the target OS
- plus two cycles counter values which can be taken before and after reading
- the system time. These cycles values can be used to determine the execution
- time required to read the system time.
-
- Limitations of the operating system need to be taken into account,
- e.g. the Windows system time may increase once every ~16 ms only.
- */
+ * @brief System time plus associated cycles counter values
+ *
+ * The structure holds a system timestamp in a format depending on the target OS
+ * plus two cycles counter values which can be taken before and after reading
+ * the system time. These cycles values can be used to determine the execution
+ * time required to read the system time.
+ *
+ * Limitations of the operating system need to be taken into account,
+ * e.g. the Windows system time may increase once every ~16 ms or ~1 ms only,
+ * depending on the Windows version.
+ */
typedef struct
{
- MBG_PC_CYCLES cyc_before; /**< cycles count before sys time is read */
- MBG_PC_CYCLES cyc_after; /**< cycles count after sys time has been read */
- MBG_SYS_TIME sys_time; /**< system time stamp */
+ MBG_PC_CYCLES cyc_before; ///< cycles count before sys time is read
+ MBG_PC_CYCLES cyc_after; ///< cycles count after sys time has been read
+ MBG_SYS_TIME sys_time; ///< system time stamp
+
} MBG_SYS_TIME_CYCLES;
#define _mbg_swab_mbg_sys_time_cycles( _p ) \
+do \
{ \
_mbg_swab_mbg_pc_cycles( &(_p)->cyc_before ); \
_mbg_swab_mbg_pc_cycles( &(_p)->cyc_after ); \
_mbg_swab_mbg_sys_time( &(_p)->sys_time ); \
-}
-
-
-
+} while ( 0 )
-static __mbg_inline
-void mbg_get_sys_time( MBG_SYS_TIME *p )
-{
- #if defined( MBG_TGT_WIN32 )
-
- #if defined( MBG_TGT_KERNEL ) // kernel space
- #if defined( MBG_TGT_WIN32_PNP ) && !defined( MBG_TGT_WIN32_PNP_X64 )
- extern KE_QUERY_SYSTEM_TIME_FNC ke_query_system_time_fnc;
- ke_query_system_time_fnc( p );
- #else
- KeQuerySystemTime( p );
- #endif
- #else // user space
- {
- FILETIME ft;
- GetSystemTimeAsFileTime( &ft );
- p->LowPart = ft.dwLowDateTime;
- p->HighPart = ft.dwHighDateTime;
- }
- #endif
-
- #elif defined( MBG_TGT_LINUX )
-
- #if defined( MBG_TGT_KERNEL )
-
- #if ( LINUX_VERSION_CODE >= KERNEL_VERSION( 2, 6, 22 ) ) //##+++++++++++++
- {
- // getnstimeofday() supported
- struct timespec ts;
-
- getnstimeofday( &ts );
-
- p->sec = ts.tv_sec;
- p->nsec = ts.tv_nsec;
- }
- #else
- {
- // getnstimeofday() *not* supported
- struct timeval tv;
-
- do_gettimeofday( &tv );
-
- p->sec = tv.tv_sec;
- p->nsec = tv.tv_usec * 1000;
- }
- #endif
-
- #else // Linux user space
- {
- struct timespec ts;
-
- clock_gettime( CLOCK_REALTIME, &ts );
-
- p->sec = ts.tv_sec;
- p->nsec = ts.tv_nsec;
- }
- #endif
-
- #elif defined( MBG_TGT_BSD )
-
- struct timespec ts;
-
- #if defined( MBG_TGT_KERNEL )
- nanotime( &ts );
- #else
- #if defined( MBG_TGT_FREEBSD )
- clock_gettime( CLOCK_REALTIME_PRECISE, &ts );
- #else // MBG_TGT_NETBSD, ...
- clock_gettime( CLOCK_REALTIME, &ts );
- #endif
- #endif
-
- p->sec = ts.tv_sec;
- p->nsec = ts.tv_nsec;
-
- #else
-
- *p = 0;
-
- #endif
-
-} // mbg_get_sys_time
-
-
-
-static __mbg_inline
-void mbg_get_sys_uptime( MBG_SYS_UPTIME *p )
-{
- #if defined( MBG_TGT_WIN32 )
-
- #if defined( MBG_TGT_KERNEL ) // kernel space
-
- ULONGLONG time_increment = KeQueryTimeIncrement();
- LARGE_INTEGER tick_count;
-
- KeQueryTickCount( &tick_count );
-
- // multiplication by time_increment yields HNS units,
- // but we need seconds
- *p = ( tick_count.QuadPart * time_increment ) / HNS_PER_SEC;
-
- #else // user space
-
- DWORD tickCount;
- DWORD timeAdjustment;
- DWORD timeIncrement;
- BOOL timeAdjustmentDisabled;
-
- if ( !GetSystemTimeAdjustment( &timeAdjustment, &timeIncrement, &timeAdjustmentDisabled ) )
- *p = -1; // failed
-
- // ATTENTION: This is compatible with older Windows versions, but
- // the returned tick count wraps around to zero after 49.7 days.
- // A new GetTickCount64() call is available under Windows Vista and newer,
- // but the function call had to be imported dynamically since otherwise
- // programs refused to start under pre-Vista versions due to undefined DLL symbol.
- tickCount = GetTickCount();
-
- *p = ( ( (MBG_SYS_UPTIME) tickCount ) * timeIncrement ) / HNS_PER_SEC;
-
- #endif
-
- #elif defined( MBG_TGT_LINUX )
-
- #if defined( MBG_TGT_KERNEL )
- // getrawmonotonic() can possibly be used for this in newer kernels
- {
- // Using a simple 64 bit division may result in a linker error
- // in kernel mode due to a missing symbol __udivdi3, so we use
- // a specific inline function do_div().
- // Also, the jiffies counter is not set to 0 at startup but to
- // a defined initialization value we need to account for.
- uint64_t tmp = get_jiffies_64() - INITIAL_JIFFIES;
- do_div( tmp, HZ );
- *p = tmp;
- }
- #else
- {
- struct sysinfo si;
- int rc = sysinfo( &si );
- *p = ( rc == 0 ) ? si.uptime : -1;
- }
- #endif
-
- #elif defined( MBG_TGT_BSD )
-
- #if defined( MBG_TGT_KERNEL )
- {
- struct timespec ts;
- #if 0 //##+++++++
- {
- struct bintime bt;
-
- binuptime( &bt );
- #if defined( DEBUG )
- printf( "binuptime: %lli.%09lli\n",
- (long long) bt.sec,
- (long long) bt.frac );
- #endif
- }
- #endif
-
- nanouptime( &ts );
- #if defined( DEBUG )
- printf( "nanouptime: %lli.%09lli\n",
- (long long) ts.tv_sec,
- (long long) ts.tv_nsec );
- #endif
- *p = ts.tv_sec;
- }
- #elif defined( MBG_TGT_FREEBSD )
- {
- struct timespec ts;
- // CLOCK_UPTIME_FAST is specific to FreeBSD
- int rc = clock_gettime( CLOCK_UPTIME_FAST, &ts );
- *p = ( rc == 0 ) ? ts.tv_sec : -1;
- }
- #else // MBG_TGT_NETBSD, ...
-
- *p = -1; //##++ needs to be implemented
-
- #endif
-
- #else
-
- *p = -1; // not supported
-
- #endif
-
-} // mbg_get_sys_uptime
-
-
-
-static __mbg_inline
-void mbg_sleep_sec( long sec )
-{
- #if defined( MBG_TGT_WIN32 )
-
- #if defined( MBG_TGT_KERNEL ) // kernel space
- LARGE_INTEGER delay;
-
- // we need to pass a negative value to KeDelayExecutionThread()
- // since the given time is a relative time interval, not absolute
- // time. See the API docs for KeDelayExecutionThread().
- delay.QuadPart = - ((LONGLONG) sec * HNS_PER_SEC);
-
- KeDelayExecutionThread( KernelMode, FALSE, &delay );
- #else // user space
- // Sleep() expects milliseconds
- Sleep( sec * 1000 );
- #endif
-
- #elif defined( MBG_TGT_LINUX )
-
- #if defined( MBG_TGT_KERNEL )
- // msleep is not defined in older kernels, so we use this
- // only if it is surely supported.
- #if ( LINUX_VERSION_CODE >= KERNEL_VERSION( 2, 6, 16 ) ) //##+++++
- msleep( sec * 1000 );
- #else
- {
- DECLARE_WAIT_QUEUE_HEAD( tmp_wait );
- wait_event_interruptible_timeout( tmp_wait, 0, sec * HZ + 1 );
- }
- #endif
- #else
- sleep( sec );
- #endif
-
- #elif defined( MBG_TGT_BSD )
-
- #if defined( MBG_TGT_KERNEL )
- #if defined( MBG_TGT_FREEBSD )
- struct timeval tv = { 0 };
- int ticks;
- tv.tv_sec = sec;
- ticks = tvtohz( &tv );
- #if defined( DEBUG )
- printf( "pause: %lli.%06lli (%i ticks)\n",
- (long long) tv.tv_sec,
- (long long) tv.tv_usec,
- ticks );
- #endif
- pause( "pause", ticks );
- #elif defined( MBG_TGT_NETBSD )
- int timeo = mstohz( sec * 1000 );
- #if defined( DEBUG )
- printf( "kpause: %i s (%i ticks)\n", sec, timeo );
- #endif
- kpause( "pause", 1, timeo, NULL );
- #endif
- #else
- sleep( sec );
- #endif
-
- #elif defined( MBG_TGT_QNX_NTO )
-
- // Actually only tested under Neutrino.
- sleep( sec );
-
- #elif defined( MBG_TGT_DOS )
-
- delay( (unsigned) ( sec * 1000 ) );
-
- #else
-
- // This needs to be implemented for the target OS
- // and thus will probably yield a linker error.
- do_sleep_sec( sec );
-
- #endif
-
-} // mbg_sleep_sec
-
-
-
-#if !defined( MBG_MEM_ADDR )
- // By default a memory address is stored
- // as a 64 bit quantitiy.
- #define MBG_MEM_ADDR uint64_t
-#endif
-
-
-typedef uint8_t MBG_DBG_DATA;
-typedef uint16_t MBG_DBG_PORT;
// The following flags describe the bus types which are
// supported by the plugin clocks.
-#define PCPS_BUS_ISA 0x0001 // IBM compatible PC/AT ISA bus
-#define PCPS_BUS_MCA 0x0002 // IBM PS/2 micro channel
-#define PCPS_BUS_PCI 0x0004 // PCI
-#define PCPS_BUS_USB 0x0008 // USB
+#define PCPS_BUS_ISA 0x0001 ///< IBM compatible PC/AT ISA bus
+#define PCPS_BUS_MCA 0x0002 ///< IBM PS/2 micro channel
+#define PCPS_BUS_PCI 0x0004 ///< PCI
+#define PCPS_BUS_USB 0x0008 ///< USB
// The flags below are or'ed to the PC_BUS_PCI code
@@ -736,10 +417,10 @@ typedef uint16_t MBG_DBG_PORT;
// on a PCI card. If no flag is set then the S5933 chip is
// installed which has been used for the first generation
// of Meinberg PCI cards.
-#define PCPS_BUS_PCI_CHIP_S5920 0x8000 // S5920 PCI interface chip.
-#define PCPS_BUS_PCI_CHIP_ASIC 0x4000 // Meinberg's own PCI interface chip.
-#define PCPS_BUS_PCI_CHIP_PEX8311 0x2000 // PEX8311 PCI Express interface chip
-#define PCPS_BUS_PCI_CHIP_MBGPEX 0x1000 // Meinberg's own PCI Express interface chip
+#define PCPS_BUS_PCI_CHIP_S5920 0x8000 ///< S5920 PCI interface chip.
+#define PCPS_BUS_PCI_CHIP_ASIC 0x4000 ///< Meinberg's own PCI interface chip.
+#define PCPS_BUS_PCI_CHIP_PEX8311 0x2000 ///< PEX8311 PCI Express interface chip
+#define PCPS_BUS_PCI_CHIP_MBGPEX 0x1000 ///< Meinberg's own PCI Express interface chip
// The constants below combine the PCI bus flags:
#define PCPS_BUS_PCI_S5933 ( PCPS_BUS_PCI )
@@ -760,7 +441,9 @@ typedef uint16_t MBG_DBG_PORT;
-/** A list of known radio clocks. */
+/**
+ * @brief A list of known devices
+ */
enum PCPS_TYPES
{
PCPS_TYPE_PC31,
@@ -797,6 +480,8 @@ enum PCPS_TYPES
PCPS_TYPE_MSF600USB,
PCPS_TYPE_WVB600USB,
PCPS_TYPE_GLN180PEX,
+ PCPS_TYPE_GPS180AMC,
+ PCPS_TYPE_GNS181PEX,
N_PCPS_DEV_TYPE
};
@@ -808,11 +493,13 @@ typedef uint16_t PCPS_REF_TYPE;
typedef uint16_t PCPS_BUS_FLAGS;
/**
- The structure contains the characteristics of each
- of the clocks listed above. These fields are always the
- same for a single type of clock and do not change with
- firmware version, port address, etc.
- */
+ * @brief Device type specification
+ *
+ * Contains the characteristics of one of the ::PCPS_TYPES.
+ * These specifications are always the same for a particular
+ * type of device and do not change with firmware version,
+ * port address, etc.
+ */
typedef struct
{
uint16_t num;
@@ -820,11 +507,12 @@ typedef struct
PCPS_DEV_ID dev_id;
PCPS_REF_TYPE ref_type;
PCPS_BUS_FLAGS bus_flags;
+
} PCPS_DEV_TYPE;
-#if !defined( MBG_TGT_UNIX ) || defined( MBG_ARCH_X86 )
+#if !defined( MBG_TGT_POSIX ) || defined( MBG_ARCH_X86 )
typedef uint16_t PCPS_PORT_ADDR;
#else
typedef uint64_t PCPS_PORT_ADDR;
@@ -833,16 +521,18 @@ typedef struct
/**
- The structure below describes an I/O port resource
- used by a clock.
-*/
+ * @brief An I/O port resource used by a device
+ */
typedef struct
{
PCPS_PORT_ADDR base;
uint16_t num;
+
} PCPS_PORT_RSRC;
-/** The max number of I/O port resources used by a clock. */
+/**
+ * @brief The max. number of I/O port resources used by a clock
+ */
#define N_PCPS_PORT_RSRC 2
@@ -856,61 +546,83 @@ typedef struct
#else
ulong len;
#endif
+
} PCPS_MAPPED_MEM;
-typedef uint32_t PCPS_ERR_FLAGS; /**< see \ref group_err_flags "Error flags" */
-typedef uint32_t PCPS_FEATURES; /**< see \ref group_features "Features" */
+typedef uint32_t PCPS_ERR_FLAGS; ///< see @ref PCPS_ERR_FLAG_MASKS
+typedef uint32_t PCPS_FEATURES; ///< see @ref PCPS_FEATURE_MASKS
typedef uint16_t PCPS_BUS_NUM;
typedef uint16_t PCPS_SLOT_NUM;
+typedef uint16_t PCPS_FW_REV_NUM; ///< firmware revision number, MSB major, LSB minor version
/**
- The structure below contains data which depends
- on a individual instance of the clock, e.g.
- the firmware which is currently installed, the
- port address which has been configured, etc.
-*/
+ * @brief Device information
+ *
+ * Contains variable data which depends on a particular instance
+ * of a device, e.g. the firmware which is currently installed,
+ * the port address which has actually been assigned, etc.
+ */
typedef struct
{
- PCPS_ERR_FLAGS err_flags; /**< See \ref group_err_flags "Error flags" */
+ PCPS_ERR_FLAGS err_flags; ///< See @ref PCPS_ERR_FLAG_MASKS
PCPS_BUS_NUM bus_num;
PCPS_SLOT_NUM slot_num;
PCPS_PORT_RSRC port[N_PCPS_PORT_RSRC];
uint16_t status_port;
int16_t irq_num;
uint32_t timeout_clk;
- uint16_t fw_rev_num;
- PCPS_FEATURES features; /**< See \ref group_features "Feature flags" */
+ PCPS_FW_REV_NUM fw_rev_num;
+ PCPS_FEATURES features; ///< See @ref PCPS_FEATURE_MASKS
PCPS_ID_STR fw_id;
PCPS_SN_STR sernum;
+
} PCPS_DEV_CFG;
-/** @defgroup group_err_flags Error flags in PCPS_DEV_CFG
- Flags used with PCPS_DEV_CFG::err_flags
- @{
-*/
-#define PCPS_EF_TIMEOUT 0x00000001 /**< timeout occured */
-#define PCPS_EF_INV_EPROM_ID 0x00000002 /**< invalid EPROM ID */
-#define PCPS_EF_IO_INIT 0x00000004 /**< I/O intf not init'd */
-#define PCPS_EF_IO_CFG 0x00000008 /**< I/O intf not cfg'd */
-#define PCPS_EF_IO_ENB 0x00000010 /**< I/O intf not enabled */
-#define PCPS_EF_IO_RSRC 0x00000020 /**< I/O not registered w/ rsrcmgr */
-/** @} */
-
-/** @defgroup group_features Feature flags used with PCPS_FEATURES
-
- Some features of the radio clocks have been introduced with
- specific firmware versions, so depending on the firmware version
- a clock may support a feature or not. The clock detection function
- checks the clock model and firmware version and updates the field
- PCPS_DEV_CFG::features accordingly. There are some macros which
- can easily be used to query whether a clock device actually
- supports a function, or not. The definitions define
- the possible features.
- @{
-*/
-enum
+
+
+/**
+ * @brief Possible device initialization error flags
+ *
+ * Used with ::PCPS_DEV_CFG::err_flags
+ *
+ * @see ::PCPS_ERR_FLAGS
+ *
+ * @anchor PCPS_ERR_FLAG_MASKS @{ */
+
+#define PCPS_EF_TIMEOUT 0x00000001 ///< timeout occured
+#define PCPS_EF_INV_FW_ID 0x00000002 ///< invalid firmware ID
+#define PCPS_EF_IO_INIT 0x00000004 ///< I/O interface not initialized
+#define PCPS_EF_IO_CFG 0x00000008 ///< I/O interface not configured
+#define PCPS_EF_IO_ENB 0x00000010 ///< I/O interface not enabled
+#define PCPS_EF_IO_RSRC 0x00000020 ///< I/O resource not registered with resource manager
+
+/** @} anchor PCPS_ERR_FLAG_MASKS */
+
+
+
+/**
+ * @defgroup group_pcps_features Feature flags used with PCPS_FEATURES
+ *
+ * Some features of the radio clocks have been introduced with
+ * specific firmware versions, so depending on the firmware version
+ * a clock may support a feature or not. The clock detection function
+ * checks the clock model and firmware version and updates the field
+ * ::PCPS_DEV_CFG::features accordingly. There are some macros which
+ * can easily be used to query whether a clock device actually
+ * supports a function, or not.
+ *
+ * @see ::PCPS_FEATURES
+ *
+ * @{ */
+
+/**
+ * @brief Feature bits for bus-level devices
+ *
+ * @see @ref PCPS_FEATURE_MASKS
+ */
+enum PCPS_FEATURE_BITS
{
PCPS_BIT_CAN_SET_TIME,
PCPS_BIT_HAS_SERIAL,
@@ -944,41 +656,58 @@ enum
PCPS_BIT_HAS_RAW_IRIG_DATA,
PCPS_BIT_HAS_PZF, // can also demodulate DCF77 PZF
PCPS_BIT_HAS_EVT_LOG,
+ PCPS_BIT_IS_GNSS, // supports several satellite systems and GNSS API calls
- N_PCPS_FEATURE // must not exceed 32 !!
+ N_PCPS_FEATURE_BITS // must not exceed 32 !!
};
-#define PCPS_CAN_SET_TIME ( 1UL << PCPS_BIT_CAN_SET_TIME )
-#define PCPS_HAS_SERIAL ( 1UL << PCPS_BIT_HAS_SERIAL )
-#define PCPS_HAS_SYNC_TIME ( 1UL << PCPS_BIT_HAS_SYNC_TIME )
-#define PCPS_HAS_TZDL ( 1UL << PCPS_BIT_HAS_TZDL )
-#define PCPS_HAS_IDENT ( 1UL << PCPS_BIT_HAS_IDENT )
-#define PCPS_HAS_UTC_OFFS ( 1UL << PCPS_BIT_HAS_UTC_OFFS )
-#define PCPS_HAS_HR_TIME ( 1UL << PCPS_BIT_HAS_HR_TIME )
-#define PCPS_HAS_SERNUM ( 1UL << PCPS_BIT_HAS_SERNUM )
-#define PCPS_HAS_TZCODE ( 1UL << PCPS_BIT_HAS_TZCODE )
-#define PCPS_HAS_CABLE_LEN ( 1UL << PCPS_BIT_HAS_CABLE_LEN )
-#define PCPS_HAS_EVENT_TIME ( 1UL << PCPS_BIT_HAS_EVENT_TIME )
-#define PCPS_HAS_RECEIVER_INFO ( 1UL << PCPS_BIT_HAS_RECEIVER_INFO )
-#define PCPS_CAN_CLR_UCAP_BUFF ( 1UL << PCPS_BIT_CAN_CLR_UCAP_BUFF )
-#define PCPS_HAS_PCPS_TZDL ( 1UL << PCPS_BIT_HAS_PCPS_TZDL )
-#define PCPS_HAS_UCAP ( 1UL << PCPS_BIT_HAS_UCAP )
-#define PCPS_HAS_IRIG_TX ( 1UL << PCPS_BIT_HAS_IRIG_TX )
-#define PCPS_HAS_GPS_DATA_16 ( 1UL << PCPS_BIT_HAS_GPS_DATA_16 )
-#define PCPS_HAS_SYNTH ( 1UL << PCPS_BIT_HAS_SYNTH )
-#define PCPS_HAS_GENERIC_IO ( 1UL << PCPS_BIT_HAS_GENERIC_IO )
-#define PCPS_HAS_TIME_SCALE ( 1UL << PCPS_BIT_HAS_TIME_SCALE )
-#define PCPS_HAS_UTC_PARM ( 1UL << PCPS_BIT_HAS_UTC_PARM )
-#define PCPS_HAS_IRIG_CTRL_BITS ( 1UL << PCPS_BIT_HAS_IRIG_CTRL_BITS )
-#define PCPS_HAS_LAN_INTF ( 1UL << PCPS_BIT_HAS_LAN_INTF )
-#define PCPS_HAS_PTP ( 1UL << PCPS_BIT_HAS_PTP )
-#define PCPS_HAS_IRIG_TIME ( 1UL << PCPS_BIT_HAS_IRIG_TIME )
-#define PCPS_HAS_FAST_HR_TSTAMP ( 1UL << PCPS_BIT_HAS_FAST_HR_TSTAMP )
-#define PCPS_HAS_RAW_IRIG_DATA ( 1UL << PCPS_BIT_HAS_RAW_IRIG_DATA )
-#define PCPS_HAS_PZF ( 1UL << PCPS_BIT_HAS_PZF )
-#define PCPS_HAS_EVT_LOG ( 1UL << PCPS_BIT_HAS_EVT_LOG )
+/**
+ * @brief Feature bit masks for bus-level devices
+ *
+ * Used with ::PCPS_DEV_CFG::features
+ *
+ * @see ::PCPS_FEATURE_BITS
+ * @see ::PCPS_FEATURES
+ *
+ * @anchor PCPS_FEATURE_MASKS @{ */
+
+#define PCPS_CAN_SET_TIME ( 1UL << PCPS_BIT_CAN_SET_TIME ) ///< see ::PCPS_BIT_CAN_SET_TIME
+#define PCPS_HAS_SERIAL ( 1UL << PCPS_BIT_HAS_SERIAL ) ///< see ::PCPS_BIT_HAS_SERIAL
+#define PCPS_HAS_SYNC_TIME ( 1UL << PCPS_BIT_HAS_SYNC_TIME ) ///< see ::PCPS_BIT_HAS_SYNC_TIME
+#define PCPS_HAS_TZDL ( 1UL << PCPS_BIT_HAS_TZDL ) ///< see ::PCPS_BIT_HAS_TZDL
+#define PCPS_HAS_IDENT ( 1UL << PCPS_BIT_HAS_IDENT ) ///< see ::PCPS_BIT_HAS_IDENT
+#define PCPS_HAS_UTC_OFFS ( 1UL << PCPS_BIT_HAS_UTC_OFFS ) ///< see ::PCPS_BIT_HAS_UTC_OFFS
+#define PCPS_HAS_HR_TIME ( 1UL << PCPS_BIT_HAS_HR_TIME ) ///< see ::PCPS_BIT_HAS_HR_TIME
+#define PCPS_HAS_SERNUM ( 1UL << PCPS_BIT_HAS_SERNUM ) ///< see ::PCPS_BIT_HAS_SERNUM
+
+#define PCPS_HAS_TZCODE ( 1UL << PCPS_BIT_HAS_TZCODE ) ///< see ::PCPS_BIT_HAS_TZCODE
+#define PCPS_HAS_CABLE_LEN ( 1UL << PCPS_BIT_HAS_CABLE_LEN ) ///< see ::PCPS_BIT_HAS_CABLE_LEN
+#define PCPS_HAS_EVENT_TIME ( 1UL << PCPS_BIT_HAS_EVENT_TIME ) ///< see ::PCPS_BIT_HAS_EVENT_TIME
+#define PCPS_HAS_RECEIVER_INFO ( 1UL << PCPS_BIT_HAS_RECEIVER_INFO ) ///< see ::PCPS_BIT_HAS_RECEIVER_INFO
+#define PCPS_CAN_CLR_UCAP_BUFF ( 1UL << PCPS_BIT_CAN_CLR_UCAP_BUFF ) ///< see ::PCPS_BIT_CAN_CLR_UCAP_BUFF
+#define PCPS_HAS_PCPS_TZDL ( 1UL << PCPS_BIT_HAS_PCPS_TZDL ) ///< see ::PCPS_BIT_HAS_PCPS_TZDL
+#define PCPS_HAS_UCAP ( 1UL << PCPS_BIT_HAS_UCAP ) ///< see ::PCPS_BIT_HAS_UCAP
+#define PCPS_HAS_IRIG_TX ( 1UL << PCPS_BIT_HAS_IRIG_TX ) ///< see ::PCPS_BIT_HAS_IRIG_TX
+
+#define PCPS_HAS_GPS_DATA_16 ( 1UL << PCPS_BIT_HAS_GPS_DATA_16 ) ///< see ::PCPS_BIT_HAS_GPS_DATA_16
+#define PCPS_HAS_SYNTH ( 1UL << PCPS_BIT_HAS_SYNTH ) ///< see ::PCPS_BIT_HAS_SYNTH
+#define PCPS_HAS_GENERIC_IO ( 1UL << PCPS_BIT_HAS_GENERIC_IO ) ///< see ::PCPS_BIT_HAS_GENERIC_IO
+#define PCPS_HAS_TIME_SCALE ( 1UL << PCPS_BIT_HAS_TIME_SCALE ) ///< see ::PCPS_BIT_HAS_TIME_SCALE
+#define PCPS_HAS_UTC_PARM ( 1UL << PCPS_BIT_HAS_UTC_PARM ) ///< see ::PCPS_BIT_HAS_UTC_PARM
+#define PCPS_HAS_IRIG_CTRL_BITS ( 1UL << PCPS_BIT_HAS_IRIG_CTRL_BITS ) ///< see ::PCPS_BIT_HAS_IRIG_CTRL_BITS
+#define PCPS_HAS_LAN_INTF ( 1UL << PCPS_BIT_HAS_LAN_INTF ) ///< see ::PCPS_BIT_HAS_LAN_INTF
+#define PCPS_HAS_PTP ( 1UL << PCPS_BIT_HAS_PTP ) ///< see ::PCPS_BIT_HAS_PTP
+
+#define PCPS_HAS_IRIG_TIME ( 1UL << PCPS_BIT_HAS_IRIG_TIME ) ///< see ::PCPS_BIT_HAS_IRIG_TIME
+#define PCPS_HAS_FAST_HR_TSTAMP ( 1UL << PCPS_BIT_HAS_FAST_HR_TSTAMP ) ///< see ::PCPS_BIT_HAS_FAST_HR_TSTAMP
+#define PCPS_HAS_RAW_IRIG_DATA ( 1UL << PCPS_BIT_HAS_RAW_IRIG_DATA ) ///< see ::PCPS_BIT_HAS_RAW_IRIG_DATA
+#define PCPS_HAS_PZF ( 1UL << PCPS_BIT_HAS_PZF ) ///< see ::PCPS_BIT_HAS_PZF
+#define PCPS_HAS_EVT_LOG ( 1UL << PCPS_BIT_HAS_EVT_LOG ) ///< see ::PCPS_BIT_HAS_EVT_LOG
+#define PCPS_IS_GNSS ( 1UL << PCPS_BIT_IS_GNSS ) ///< see ::PCPS_BIT_IS_GNSS
+
+/** @} anchor PCPS_FEATURE_MASKS */
#define PCPS_FEATURE_NAMES \
@@ -1011,10 +740,11 @@ enum
"PCPS_HAS_FAST_HR_TSTAMP", \
"PCPS_HAS_RAW_IRIG_DATA", \
"PCPS_HAS_PZF", \
- "PCPS_HAS_EVT_LOG" \
+ "PCPS_HAS_EVT_LOG", \
+ "PCPS_IS_GNSS" \
}
-/** @} */
+/** @} defgroup group_pcps_features */
@@ -1131,9 +861,11 @@ enum
#define PCPS_FEAT_WWVB51USB ( PCPS_FEAT_MSF51USB )
-#define PCPS_FEAT_GPS180PEX ( PCPS_FEAT_GPS170PEX | PCPS_HAS_FAST_HR_TSTAMP )
+#define PCPS_FEAT_GPS180PEX ( ( PCPS_FEAT_GPS170PEX | PCPS_HAS_FAST_HR_TSTAMP ) \
+ & ~PCPS_HAS_IRIG_TX ) ///< IRIG TX only supp. if ::GPS_HAS_IRIG_TX
-#define PCPS_FEAT_TCR180PEX ( PCPS_FEAT_TCR170PEX | PCPS_HAS_FAST_HR_TSTAMP )
+#define PCPS_FEAT_TCR180PEX ( ( PCPS_FEAT_TCR170PEX | PCPS_HAS_FAST_HR_TSTAMP ) \
+ & ~PCPS_HAS_IRIG_TX ) ///< IRIG TX only supp. if ::GPS_HAS_IRIG_TX
#define PCPS_FEAT_DCF600USB ( PCPS_FEAT_USB5131 )
@@ -1158,7 +890,11 @@ enum
#define PCPS_FEAT_WVB600USB ( PCPS_FEAT_WWVB51USB )
-#define PCPS_FEAT_GLN180PEX ( PCPS_FEAT_GPS180PEX )
+#define PCPS_FEAT_GLN180PEX ( PCPS_FEAT_GPS180PEX | PCPS_IS_GNSS )
+
+#define PCPS_FEAT_GPS180AMC ( PCPS_FEAT_GPS180PEX )
+
+#define PCPS_FEAT_GNS181PEX ( PCPS_FEAT_GLN180PEX )
// Some features of the API used to access Meinberg plug-in devices
// have been implemented starting with the special firmware revision
@@ -1169,12 +905,12 @@ enum
// There are some versions of PCI Express cards out there which do not
-// safely support hardware IRQs. The following firmware versions are required
+// safely support hardware IRQs. The following firmware versions are required
// for safe IRQ operation:
#define REV_HAS_IRQ_FIX_MINOR_PEX511 0x0106
#define REV_HAS_IRQ_FIX_MINOR_TCR511PEX 0x0105
#define REV_HAS_IRQ_FIX_MINOR_GPS170PEX 0x0104
-// Additionally there are certain revisions of the bus interface logic
+// Additionally there are certain revisions of the bus interface logic
// required. The associated version codes are defined in pci_asic.h.
// The macro below can be used to check whether the required versions are there:
@@ -1199,8 +935,8 @@ enum
#define REV_HAS_IRIG_CTRL_BITS_TCR511PCI 0x0107
#define REV_HAS_IRIG_CTRL_BITS_TCR51USB 0x0106
-/* This board uses the GPS_DATA interface with 16 bit buffer sizes
- instead of the original 8 bit sizes, thus allowing to transfer
+/* This board uses the GPS_DATA interface with 16 bit buffer sizes
+ instead of the original 8 bit sizes, thus allowing to transfer
data blocks which exceed 255 bytes (PCPS_HAS_GPS_DATA_16) */
#define REV_HAS_GPS_DATA_16_GPS169PCI 0x0202
@@ -1255,13 +991,16 @@ enum
/**
- The structure has been defined to pass all
- information on a clock device from a device driver
- to a user program. */
+ * @brief Device info structure
+ *
+ * Used to pass all information on a bus-level device
+ * from a device driver to a user space application.
+ */
typedef struct
{
PCPS_DEV_TYPE type;
PCPS_DEV_CFG cfg;
+
} PCPS_DEV;
@@ -1288,6 +1027,7 @@ typedef struct
#define _pcps_is_irig_rx( _d ) ( _pcps_ref_type( _d ) == PCPS_REF_IRIG )
#define _pcps_is_ptp( _d ) ( _pcps_ref_type( _d ) == PCPS_REF_PTP )
#define _pcps_is_frc( _d ) ( _pcps_ref_type( _d ) == PCPS_REF_FRC )
+#define _pcps_is_gnss( _d ) _pcps_has_feature( (_d), PCPS_IS_GNSS )
#define _pcps_is_lwr( _d ) ( _pcps_is_dcf( _d ) || _pcps_is_msf( _d ) || _pcps_is_wwvb( _d ) )
@@ -1337,12 +1077,13 @@ typedef struct
#define _pcps_clr_err_flags( _d, _msk ) ( _pcps_err_flags( _d ) &= ~(_msk) )
-// Query whether a special feature is supported:
+/// Check whether a special feature is supported
#define _pcps_has_feature( _d, _f ) ( ( (_d)->cfg.features & (_f) ) != 0 )
-// Query whether a special feature is supported according to RECEIVER_INFO:
+/// Check whether a special feature is supported according to ::RECEIVER_INFO
#define _pcps_has_ri_feature( _p_ri, _f ) ( ( (_p_ri)->features & (_f) ) != 0 )
+#define _ri_addr( _p ) &(_p)->xdev_features.receiver_info
#define _pcps_can_set_time( _d ) _pcps_has_feature( (_d), PCPS_CAN_SET_TIME )
#define _pcps_has_serial( _d ) _pcps_has_feature( (_d), PCPS_HAS_SERIAL )
@@ -1448,6 +1189,13 @@ typedef struct
#define _pcps_has_stat_info_svs( _d ) _pcps_is_gps( _d )
+#define _pcps_has_ri_gpio( _p_ri ) _pcps_has_ri_feature( (_p_ri), GPS_HAS_GPIO )
+
+// We only report that XMR is supported if all required features are supported.
+#define _pcps_has_ri_xmr( _p_ri ) ( _pcps_has_ri_feature( (_p_ri), GPS_HAS_XMULTI_REF ) && \
+ _pcps_has_ri_feature( (_p_ri), GPS_HAS_XMRS_MULT_INSTC ) )
+//### TODO should also check GPS_MODEL_HAS_XMR_HOLDOVER_INTV, which is a builtin feature flag only
+
// There are some versions of IRIG receiver cards which ignore the TFOM code
@@ -1456,7 +1204,7 @@ typedef struct
// signal even if the TFOM code reports the IRIG generator is not synchronized.
// The intended behaviour is that the IRIG receiver card changes its status
// to "freewheeling" in this case, unless it has been configured to ignore
-// the TFOM code of the incoming IRIG signal (see the IFLAGS_DISABLE_TFOM flag
+// the TFOM code of the incoming IRIG signal (see the ::IFLAGS_DISABLE_TFOM flag
// defined in gpsdefs.h).
// The macro below can be used to check based on the device info if a specific
@@ -1485,8 +1233,8 @@ typedef struct
// There are some versions of GPS PCI firmware which may occasionally return
// a HR time stamp which is wrong by 20 milliseconds, if the HR time is read
-// right after some GPS data. As a workaround for that bug an application
-// must wait at least 1.5 ms and then just read the PCPS_TIME structure
+// right after some GPS data. As a workaround for that bug an application
+// must wait at least 1.5 ms and then just read the PCPS_TIME structure
// in order to re-initialize the software interface state.
// This has been fixed in more recent versions of the affected firmware,
// but this macro can be used to let an application determine whether it
@@ -1500,13 +1248,17 @@ typedef struct
/**
- The structure is used to return info
- on the device driver.*/
+ * @brief Device driver information
+ *
+ * Used to pass info on the device driver to
+ * a user space application.
+ */
typedef struct
{
- uint16_t ver_num; /**< the device driver's version number */
- uint16_t n_devs; /**< the number of radio clocks handled by the driver */
- PCPS_ID_STR id_str; /**< the device driver's ID string */
+ uint16_t ver_num; ///< the device driver's version number
+ uint16_t n_devs; ///< the number of devices handled by the driver
+ PCPS_ID_STR id_str; ///< the device driver's ID string
+
} PCPS_DRVR_INFO;
@@ -1520,96 +1272,115 @@ typedef struct
/**
- The structure is used to read the current time from
- a device, combined with an associated PC cycle counter value
- to compensate program execution time.
- */
+ * @brief Time read from a device plus associated system cycles count
+ *
+ * Contains current time from a device, plus an associated PC
+ * cycles counter value useful to compensate execution time.
+ */
typedef struct
{
MBG_PC_CYCLES cycles;
PCPS_TIME t;
+
} PCPS_TIME_CYCLES;
/**
- The structure is used to read a high resolution UTC time stamp
- plus associated PC cycles counter value to compensate the latency.
- */
+ * @brief High resolution time stamp plus associated system cycles count
+ *
+ * Contains current high resolution UTC time stamp from a device, plus
+ * an associated PC cycles counter value useful to compensate execution time.
+ */
typedef struct
{
MBG_PC_CYCLES cycles;
- PCPS_TIME_STAMP tstamp; /**< High resolution time stamp (UTC) */
+ PCPS_TIME_STAMP tstamp; ///< High resolution time stamp (%UTC)
+
} PCPS_TIME_STAMP_CYCLES;
#define _mbg_swab_pcps_time_stamp_cycles( _p ) \
+do \
{ \
_mbg_swab_mbg_pc_cycles( &(_p)->cycles ); \
_mbg_swab_pcps_time_stamp( &(_p)->tstamp ); \
-}
+} while ( 0 )
/**
- The structure is used to read the current high resolution time
- from a device, combined with an associated PC cycle counter value
- to compensate program execution time.
- */
+ * @brief High resolution time plus associated system cycles count
+ *
+ * Contains current high resolution %UTC time from a device, including
+ * local time offset and status, plus an associated PC cycles counter value
+ * useful to compensate execution time.
+ */
typedef struct
{
MBG_PC_CYCLES cycles;
PCPS_HR_TIME t;
+
} PCPS_HR_TIME_CYCLES;
#define _mbg_swab_pcps_hr_time_cycles( _p ) \
+do \
{ \
_mbg_swab_mbg_pc_cycles( &(_p)->cycles ); \
_mbg_swab_pcps_hr_time( &(_p)->t ); \
-}
+} while ( 0 )
/**
- The structure below can be used to let the kernel driver read
- the current system time plus the associated HR time from a plugin card
- as close as possibly, and return the results to a user space application
- which can then compute the time difference and latencies.
- This structure also contains the card's status information (e.g. sync status).
- */
+ * @brief High resolution device time, system time, and associated cycles counts
+ *
+ * Used to let the kernel driver read the current system time plus the associated
+ * high resolution time from a bus-level device as close as possible, and return
+ * the results to the caller which can then compute the time difference, taking
+ * into account the latencies determined from the cycles counts.
+ *
+ * This structure also contains the card's status information (e.g. sync status).
+ */
typedef struct
{
- PCPS_HR_TIME_CYCLES ref_hr_time_cycles; /**< HR time read from the card, plus cycles */
- MBG_SYS_TIME_CYCLES sys_time_cycles; /**< system timestamp plus associated cycles */
+ PCPS_HR_TIME_CYCLES ref_hr_time_cycles; ///< HR time read from the card, plus cycles
+ MBG_SYS_TIME_CYCLES sys_time_cycles; ///< system time stamp plus associated cycles
+
} MBG_TIME_INFO_HRT;
#define _mbg_swab_mbg_time_info_hrt( _p ) \
+do \
{ \
_mbg_swab_pcps_hr_time_cycles( &(_p)->ref_hr_time_cycles ); \
_mbg_swab_mbg_sys_time_cycles( &(_p)->sys_time_cycles ); \
-}
+} while ( 0 )
/**
- The structure below can be used to let the kernel driver read
- the current system time plus an associated HR timestamp from a plugin card
- as close as possibly, and return the results to a user space application
- which can then compute the time difference and latencies.
- Since the card's time stamp is usually taken using the fast memory mapped
- access this structure does *not* contain the card's status information
- (e.g. sync status).
- */
+ * @brief High resolution device time stamp, system time, and associated cycles counts
+ *
+ * Used to let the kernel driver read the current system time plus the associated
+ * high resolution time stamp from a bus-level device as close as possible, and return
+ * the results to the caller which can then compute the time difference, taking
+ * into account the latencies determined from the cycles counts.
+ *
+ * Since the card's time stamp is taken from the fast memory mapped registers
+ * this structure does *not* contain the card's status information (e.g. sync status).
+ */
typedef struct
{
- PCPS_TIME_STAMP_CYCLES ref_tstamp_cycles; /**< HR timestamp from the card, plus cycles */
- MBG_SYS_TIME_CYCLES sys_time_cycles; /**< system timestamp plus associated cycles */
+ PCPS_TIME_STAMP_CYCLES ref_tstamp_cycles; ///< HR timestamp from the card, plus cycles
+ MBG_SYS_TIME_CYCLES sys_time_cycles; ///< system timestamp plus associated cycles
+
} MBG_TIME_INFO_TSTAMP;
#define _mbg_swab_mbg_time_info_tstamp( _p ) \
+do \
{ \
_mbg_swab_pcps_time_stamp_cycles( &(_p)->ref_tstamp_cycles ); \
_mbg_swab_mbg_sys_time_cycles( &(_p)->sys_time_cycles ); \
-}
+} while ( 0 )
@@ -1657,9 +1428,13 @@ typedef uint32_t PCPS_IRQ_STAT_INFO;
#if USE_IOCTL_GENERIC_REQ
-// This does not yet work properly under Linux/Sparc where the kernel may be 64 bit
-// while user space is 32 bit, which leads to different sizes for pointers and size_t.
-
+/**
+ * @brief A structure used to pass generic IOCTL requests to the kernel driver
+ *
+ * @note This does not work properly under Linux/Sparc where the kernel
+ * may be 64 bit while user space is 32 bit, which leads to different sizes
+ * for pointers, size_t, etc.
+ */
typedef struct
{
ulong info;
@@ -1674,18 +1449,36 @@ typedef struct
#else
-// The structure below is used by the IOCTL_PCPS_GENERIC_... calls.
+/**
+ * @brief Control structure used for generic IOCTL requests
+ *
+ * Used by the IOCTL_PCPS_GENERIC_... calls.
+ *
+ * @note Is slower, but avoids OS-specific problems occurring
+ * with IOCTL_GENERIC_REQ.
+ */
typedef struct
{
uint32_t info;
uint32_t data_size_in;
uint32_t data_size_out;
+
} IOCTL_GENERIC_CTL;
+
+/**
+ * @brief Data buffer used for generic IOCTL requests
+ *
+ * Used by the IOCTL_PCPS_GENERIC_... calls.
+ *
+ * @note Is slower, but avoids OS-specific problems occurring
+ * with IOCTL_GENERIC_REQ.
+ */
typedef struct
{
IOCTL_GENERIC_CTL ctl;
uint8_t data[1];
+
} IOCTL_GENERIC_BUFFER;
#define _MBG_IOG( _t, _n, _s ) _MBG_IO( _t, _n )
diff --git a/mbglib/common/pcpsdrvr.c b/mbglib/common/pcpsdrvr.c
index 93d2a52..9b7caa9 100755
--- a/mbglib/common/pcpsdrvr.c
+++ b/mbglib/common/pcpsdrvr.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcpsdrvr.c 1.50.1.1 2013/06/25 09:52:39 martin TRASH $
+ * $Id: pcpsdrvr.c 1.51.1.37 2017/04/25 11:36:47 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -25,7 +25,7 @@
* USB v1: USB5131, TCR51USB, MSF51USB, WWVB51USB
* PCI express: PEX511, TCR511PEX, GPS170PEX, PTP270PEX,
* FRC511PEX, TCR170PEX, GPS180PEX, TCR180PEX
- * PZF180PEX
+ * PZF180PEX, GLN180PEX, GPS180AMC, GNS181PEX
* PCI bus 5V/3.3V: PCI510, PCI511, GPS169PCI, GPS170PCI,
* TCR510PCI, TCR167PCI, TCR511PCI
* PCI bus 5V: PCI32, GPS167PCI, PCI509, GPS168PCI
@@ -63,7 +63,81 @@
*
* -----------------------------------------------------------------------
* $Log: pcpsdrvr.c $
- * Revision 1.50.1.1 2013/06/25 09:52:39 martin
+ * Revision 1.51.1.37 2017/04/25 11:36:47 martin
+ * Renamed GRC181PEX to GNS181PEX.
+ * Revision 1.51.1.36 2017/04/19 13:55:58 martin
+ * Increase MAX_BOOT_TIME_PTP270PEX from 27 to 40 seconds
+ * to be safe in case a firmware update is applied at startup.
+ * Added some doxygen comments.
+ * Revision 1.51.1.35 2017/02/22 15:23:46 martin
+ * Fixed macro definition syntax to avoid clang compiler warnings.
+ * Revision 1.51.1.34 2017/02/22 11:32:12 martin
+ * Avoid 'redundant redeclaration' warning under FreeBSD 8.2.
+ * Revision 1.51.1.33 2017/02/10 15:27:45 martin
+ * Fixed type of a register address.
+ * Revision 1.51.1.32 2016/09/26 16:23:22 martin
+ * Revision 1.51.1.31 2016/09/23 09:03:34Z martin
+ * *** empty log message ***
+ * Revision 1.51.1.30 2016/09/19 14:29:22 martin
+ * *** empty log message ***
+ * Revision 1.51.1.29 2016/09/16 09:57:43 martin
+ * Use macro _ri_addr().
+ * Revision 1.51.1.28 2016/09/15 14:55:51 martin
+ * Support GRC181PEX.
+ * Revision 1.51.1.27 2016/09/14 16:21:42 martin
+ * Started code cleanup.
+ * Added doxygen comments.
+ * Revision 1.51.1.26 2016/09/13 10:12:08 martin
+ * Fixed some compiler warnings.
+ * Revision 1.51.1.25 2016/09/07 07:35:36Z martin
+ * Provided a driver name string for debug build on direct-access targets.
+ * Revision 1.51.1.24 2016/08/10 12:28:55 martin
+ * Check for MBG_TGT_POSIX instead of MBG_TGT_UNIX.
+ * Revision 1.51.1.23 2016/08/09 16:01:43 martin
+ * Attribute always_inline is now in __mbg_inline.
+ * Revision 1.51.1.22 2016/08/09 07:12:57 martin
+ * *** empty log message ***
+ * Revision 1.51.1.21 2016/05/30 15:03:46 martin
+ * Conditional USB debug code.
+ * Revision 1.51.1.20 2016/04/06 13:54:37 martin
+ * *** empty log message ***
+ * Revision 1.51.1.19 2015/10/27 16:22:26 martin
+ * Older defines N_SUPP_DEV, PCPS_MAX_DDEVS, and MBG_MAX_DEVICES
+ * have been obsoleted by new defines N_SUPP_DEV_BUS, N_SUPP_DEV_EXT,
+ * and N_SUPP_DEV_TOTAL.
+ * Revision 1.51.1.18 2015/10/22 14:42:54 martin
+ * *** empty log message ***
+ * Revision 1.51.1.17 2015/09/18 14:54:24 martin
+ * Removed obsolete include file for FreeBSD.
+ * Revision 1.51.1.16 2015/09/15 09:16:04 martin
+ * Moved mbg_delta_sys_time_ms() to new module mbgsystm.c.
+ * Removed trailing white space.
+ * Revision 1.51.1.15 2014/10/30 16:03:10 martin
+ * Doxygen fixes.
+ * Revision 1.51.1.14 2014/10/29 10:32:13 martin
+ * Revision 1.51.1.13 2014/10/28 16:58:05 martin
+ * Revision 1.51.1.12 2014/05/26 16:03:00 martin
+ * Revision 1.51.1.11 2014/05/19 14:46:15 martin
+ * Fixed comment grammar.
+ * Revision 1.51.1.10 2014/04/17 08:38:12 martin
+ * Fixed DEBUG build under *BSD.
+ * Added DEBUG code dumping RECEIVER_INFO.
+ * Revision 1.51.1.9 2014/04/07 15:25:37 martin
+ * Started to rework Windows event logging.
+ * Revision 1.51.1.8 2014/04/07 10:35:25Z martin
+ * Revision 1.51.1.7 2014/04/07 09:56:45 martin
+ * Revision 1.51.1.6 2014/04/02 11:16:53 martin
+ * Revision 1.51.1.5 2014/03/20 16:40:25 martin
+ * Revision 1.51.1.4 2014/03/20 16:34:44 martin
+ * Runtime support for forcing I/O rather than MM access.
+ * Revision 1.51.1.3 2014/01/23 15:35:48 martin
+ * Support GPS180AMC.
+ * Revision 1.51.1.2 2013/12/16 10:45:52 martin
+ * Account for renamed symbols.
+ * Revision 1.51.1.1 2013/12/12 11:29:22 martin
+ * Doxygen stuff.
+ * Revision 1.51 2013/10/01 14:19:03 martin
+ * Support GLN180PEX.
* Revision 1.50 2013/03/15 10:01:58 martin
* Modified/added some debug messages.
* Revision 1.49 2013/03/15 08:35:08 martin
@@ -120,17 +194,17 @@
* Revision 1.38 2009/03/17 15:33:53 martin
* Support reading IRIG control function bits.
* Revision 1.37 2009/03/13 09:17:00Z martin
- * Bug fix: Hadn't checked whether TCR170PEX card provides the
+ * Bug fix: Hadn't checked whether TCR170PEX card provides the
* programmable synthesizer.
- * As a fix moved the code from the body of check_opt_features()
- * into pcps_start_device() so that the check is done for every
+ * As a fix moved the code from the body of check_opt_features()
+ * into pcps_start_device() so that the check is done for every
* type of card.
* Swap receiver_info to make this work on non-x86 architectures.
- * Support configurable time scales, and reading/writing GPS UTC
+ * Support configurable time scales, and reading/writing GPS UTC
* parameters via the PC bus.
* Use mbg_get_pc_cycles() instead of _pcps_get_cycles().
* Revision 1.36 2009/01/13 12:03:57Z martin
- * Generate a separate warning message if the firmware could not
+ * Generate a separate warning message if the firmware could not
* be read from an ISA card.
* Care about "long long" in debug msg.
* Revision 1.35 2008/12/16 14:38:49Z martin
@@ -140,10 +214,10 @@
* Check whether PEX511 and PCI511 support HR time.
* Moved initialization of common spinlocks and mutexes to pcps_start_device().
* Take access cycles count in the low level routines, with interrupts disabled.
- * Cleanup for pcps_read_usb() which is now possible since access cycles count
+ * Cleanup for pcps_read_usb() which is now possible since access cycles count
* is now taken inside the low evel routines.
* Support mapped I/O resources, unaligned access and endianess conversion.
- * Account for ASIC_FEATURES being coded as flags, and account for
+ * Account for ASIC_FEATURES being coded as flags, and account for
* new symbol PCI_ASIC_HAS_MM_IO.
* Account for new MBG_PC_CYCLES type.
* Account for signed irq_num.
@@ -151,8 +225,8 @@
* Use MBG_MEM_ADDR type for memory rather than split high/low types.
* Distinguish device port variables for IRQ handling.
* Preliminarily support USB latency compensation under Win32 PNP targets
- * and account for USB EHCI microframe timing which requires a different
- * latency compensation approach. This is useful if a USB 2.0 hub is connected
+ * and account for USB EHCI microframe timing which requires a different
+ * latency compensation approach. This is useful if a USB 2.0 hub is connected
* between device and host.
* Also read the ASIC version at device initialization.
* pcps_alloc_ddev() does not take a parameter anymore.
@@ -160,9 +234,9 @@
* Revision 1.34 2008/02/27 10:03:02 martin
* Support TCR51USB and MSF51USB.
* Preliminary support for mapped memory access under Windows and Linux.
- * Enabled PCPS_IRQ_1_SEC for USB within WIN32 targets
+ * Enabled PCPS_IRQ_1_SEC for USB within WIN32 targets
* in pcps_start_device().
- * Fixed a bug in pcps_write() where the error code
+ * Fixed a bug in pcps_write() where the error code
* that was returned from a USB device was misinterpreted
* due to a signed/unsigned mismatch (added typecast).
* Removed obsolete function pcps_cleanup_all_devices().
@@ -207,7 +281,7 @@
* OS requirements, in order to avoid naming conflicts.
* Revision 1.26 2006/06/19 15:28:52 martin
* Added support for TCR511PCI.
- * Modified parameters required to detect ISA cards.
+ * Modified parameters required to detect ISA cards.
* The array of port addresses does no more require a 0 address
* as last value.
* Revision 1.25 2006/03/10 11:01:27 martin
@@ -227,8 +301,8 @@
* Revision 1.19 2004/10/14 15:01:24 martin
* Added support for TCR167PCI.
* Revision 1.18 2004/09/06 15:16:57Z martin
- * Support a GPS_DATA interface where sizes are specified
- * by 16 instead of the original 8 bit quantities, thus allowing
+ * Support a GPS_DATA interface where sizes are specified
+ * by 16 instead of the original 8 bit quantities, thus allowing
* to transfer data blocks which exceed 255 bytes.
* Conditionally skip assertions under Linux.
* Revision 1.17 2004/04/22 14:47:54 martin
@@ -266,9 +340,9 @@
* Use new header mbg_tgt.h to check the target environment.
* Removed function pcps_sn_str_from_ident(), use new
* function mbg_gps_ident_decode() from identdec.c now.
- * If a PCI clock's interface is not properly configured don't
- * enable the device and set the read function to the new
- * dummy function pcps_read_null() to prevent driver from
+ * If a PCI clock's interface is not properly configured don't
+ * enable the device and set the read function to the new
+ * dummy function pcps_read_null() to prevent driver from
* accessing random ports.
* Revision 1.5 2002/02/01 12:06:12 MARTIN
* Added support for GPS168PCI.
@@ -291,13 +365,12 @@
#include <pcpsdrvr.h>
#undef _PCPSDRVR
-#include <parmpcps.h>
-#include <parmgps.h>
#include <identdec.h>
#include <mbgddmsg.h>
#include <plxdefs.h>
#include <pci_asic.h>
#include <amccdefs.h>
+#include <pcidefs.h>
#if defined( MBG_TGT_WIN32_PNP )
#include <usbdrv.h>
@@ -317,7 +390,6 @@
#if defined( MBG_TGT_FREEBSD )
#include <sys/rman.h>
- #include <sys/libkern.h>
#endif
#if _PCPS_USE_MCA
@@ -349,25 +421,45 @@
#if !defined( DEBUG_ACCESS_TIMING )
// test how much cycles it takes to read/write a register on the board
- #define DEBUG_ACCESS_TIMING ( defined( DEBUG ) && ( DEBUG >= 10 ) )
+ #if ( defined( DEBUG ) && ( DEBUG >= 10 ) )
+ #define DEBUG_ACCESS_TIMING 1
+ #else
+ #define DEBUG_ACCESS_TIMING 0
+ #endif
#endif
#if !defined( DEBUG_IO_TIMING )
// test how much cycles it takes for a low level function to execute
- #define DEBUG_IO_TIMING ( defined( DEBUG ) && ( DEBUG >= 10 ) )
+ #if ( defined( DEBUG ) && ( DEBUG >= 10 ) )
+ #define DEBUG_IO_TIMING 1
+ #else
+ #define DEBUG_IO_TIMING 0
+ #endif
#endif
#if !defined( DEBUG_IO )
// debug which bytes are written to or read from the board
- #define DEBUG_IO ( defined( DEBUG ) && ( DEBUG >= DEBUG_LVL_IO ) )
+ #if ( defined( DEBUG ) && ( DEBUG >= DEBUG_LVL_IO ) )
+ #define DEBUG_IO 1
+ #else
+ #define DEBUG_IO 0
+ #endif
#endif
#if !defined( DEBUG_PORTS )
- #define DEBUG_PORTS ( defined( DEBUG ) && ( DEBUG >= DEBUG_LVL_PORTS ) )
+ #if ( defined( DEBUG ) && ( DEBUG >= DEBUG_LVL_PORTS ) )
+ #define DEBUG_PORTS 1
+ #else
+ #define DEBUG_PORTS 0
+ #endif
#endif
#if !defined( DEBUG_SERNUM )
- #define DEBUG_SERNUM ( defined( DEBUG ) && ( DEBUG >= DEBUG_LVL_SERNUM ) )
+ #if ( defined( DEBUG ) && ( DEBUG >= DEBUG_LVL_SERNUM ) )
+ #define DEBUG_SERNUM 1
+ #else
+ #define DEBUG_SERNUM 0
+ #endif
#endif
#if !defined( USE_USB_MICRO_FRAMES )
@@ -375,11 +467,47 @@
#endif
-// max. time required for PTP270PEX to be ready after booting
-#define MAX_BOOT_TIME_PTP270PEX 27 // [s]
+/**
+ * @brief Max. time required for PTP270PEX v1 card to be ready after power-up.
+ *
+ * The PTP270PEX cards have an on-board Linux system which must have
+ * finished booting before the card can be accessed via the PCI bus.
+ * If the card is accessed earlier then the PCI bus and thus the computer
+ * may hang.
+ *
+ * There are 2 different hardware versions of the PTP270PEX card.
+ * PTP270PEX v2 hardware and firmware can flag via a bit in the PCI
+ * configuration space when the card is ready, so the driver can just
+ * wait until the card has flagged that it's ready.
+ *
+ * However, the PTP270PEX v1 hardware doesn't support this, so the driver
+ * checks the system uptime and waits until it is greater or equal the
+ * maximum time required for a PTP270PEX v1 card to finish booting.
+ *
+ * The nominal time is 27 s, but if a firmware update has been submitted
+ * then the update is applied first, which takes another few seconds.
+ *
+ * @see ::wait_ptp270pex_ready
+ * @see ::report_uptime
+ */
+#define MAX_BOOT_TIME_PTP270PEX 40 // [s]
-extern const char pcps_driver_name[];
+#if defined( MBG_TGT_BSD )
+ // Avoid compiler warnings "redundant redeclaration of ..."
+ // e.g. under FreeBSD 8.2 with gcc 4.2.1.
+ #define AVOID_REDUNDANT_REDECLARATION 1
+#endif
+
+#if defined( MBG_TGT_KERNEL )
+ // Driver name defined by the skeleton driver for the target OS.
+ extern const char pcps_driver_name[];
+#else
+ // No skeleton driver, but we need a string to pass to debug messages.
+ #if DEBUG
+ const char pcps_driver_name[] = "pcpsdrvr";
+ #endif
+#endif
// In some environments special far functions are are neither
@@ -473,6 +601,85 @@ extern const char pcps_driver_name[];
+/**
+ * @brief A table used to map ::RECEIVER_INFO::features to ::PCPS_DEV_CFG::features
+ *
+ * The enumerated ::GPS_FEATURE_BITS can be used as index
+ * to this table, and the table entry contains a combination
+ * of associated @ref PCPS_FEATURE_MASKS, if there are any.
+ *
+ * @note Devices which support a configurable time scale do also
+ * support reading/writing the GPS %UTC parameters via the PC bus.
+ * This is not explicitely coded in the ::RECEIVER_INFO::features
+ * since the the ::RECEIVER_INFO structure can also be read via
+ * the serial port, and reading/writing the GPS %UTC parameters
+ * via the serial port is supported by all GPS devices anyway.
+ *
+ * @note Devices which support reading ::MBG_RAW_IRIG_DATA via the PC bus
+ * interface also support reading ::PCPS_IRIG_TIME. However, there is
+ * no associated flag in ::RECEIVER_INFO::features since this call
+ * is not supported via the serial interface. Thus we use the
+ * ::GPS_HAS_RAW_IRIG_DATA flag to check both features.
+ *
+ * @see ::GPS_FEATURE_BITS
+ * @see @ref PCPS_FEATURE_MASKS
+ */
+static uint32_t ri_feat_tbl[N_GPS_FEATURE] =
+{
+ 0, ///< see ::GPS_FEAT_PPS
+ 0, ///< see ::GPS_FEAT_PPM
+ PCPS_HAS_SYNTH, ///< see ::GPS_FEAT_SYNTH
+ 0, ///< see ::GPS_FEAT_DCFMARKS
+ PCPS_HAS_IRIG_TX, ///< see ::GPS_FEAT_IRIG_TX
+ 0, ///< see ::GPS_FEAT_IRIG_RX
+ PCPS_HAS_LAN_INTF, ///< see ::GPS_FEAT_LAN_IP4
+ 0, ///< see ::GPS_FEAT_MULTI_REF
+
+ 0, ///< see ::GPS_FEAT_RCV_TIMEOUT
+ 0, ///< see ::GPS_FEAT_IGNORE_LOCK
+ 0, ///< see ::GPS_FEAT_5_MHZ
+ 0, ///< see ::GPS_FEAT_XMULTI_REF
+ 0, ///< see ::GPS_FEAT_OPT_SETTINGS
+ PCPS_HAS_TIME_SCALE | PCPS_HAS_UTC_PARM, ///< see ::GPS_FEAT_TIME_SCALE
+ PCPS_HAS_IRIG_CTRL_BITS, ///< see ::GPS_FEAT_IRIG_CTRL_BITS
+ PCPS_HAS_PTP, ///< see ::GPS_FEAT_PTP
+
+ 0, ///< see ::GPS_FEAT_NAV_ENGINE_SETTINGS
+ PCPS_HAS_IRIG_TIME | PCPS_HAS_RAW_IRIG_DATA, ///< see ::GPS_FEAT_RAW_IRIG_DATA
+ 0, ///< see ::GPS_FEAT_RAW_IRIG_TIME
+ 0, ///< see ::GPS_FEAT_PTP_UNICAST
+ 0, ///< see ::GPS_FEAT_GPIO
+ 0, ///< see ::GPS_FEAT_XMRS_MULT_INSTC
+ 0, ///< see ::GPS_FEAT_10MHZ_DISBD
+ PCPS_HAS_EVT_LOG, ///< see ::GPS_FEAT_EVT_LOG
+
+ 0, ///< see ::GPS_FEAT_IMS
+ 0, ///< see ::GPS_FEAT_HAVEQUICK
+ 0, ///< see ::GPS_FEAT_NTP
+ 0, ///< see ::GPS_FEAT_NET_CFG
+ 0, ///< see ::GPS_FEAT_VST
+ 0, ///< see ::GPS_FEAT_SHS
+ 0 ///< see ::GPS_FEAT_XBP
+};
+
+
+
+#if defined( DEBUG )
+
+/**
+ * @brief A table of name strings associated with ::GPS_FEATURE_BITS
+ */
+static const char *gps_ri_feature_names[N_GPS_FEATURE] = DEFAULT_GPS_FEATURE_NAMES;
+
+/**
+ * @brief A table of name strings associated with ::PCPS_FEATURE_BITS
+ */
+static const char *pcps_feature_names[N_PCPS_FEATURE_BITS] = PCPS_FEATURE_NAMES;
+
+#endif // defined( DEBUG )
+
+
+
static __mbg_inline /*HDR*/
int pcps_ddev_is_ptp270pex( const PCPS_DDEV *pddev )
{
@@ -487,6 +694,15 @@ int pcps_ddev_is_ptp270pex( const PCPS_DDEV *pddev )
#if defined( MBG_TGT_LINUX )
static /*HDR*/
+/**
+ * @brief Read a dword from a PLX PECS register
+ *
+ * @param[in] pNode Device structure
+ * @param[in] reg Number of the register to read
+ * @param[out] pval Pointer to a variable to take the value read from the register
+ *
+ * @return ::PCI_SUCCESS on success, or one of the PCI BIOS error codes
+ */
int mbg_plx_read_pecs_reg( struct pci_dev *pNode,
uint16_t reg, uint32_t *pval )
{
@@ -536,7 +752,7 @@ static /*HDR*/
/**
* @brief Check if a PTP270PEX card can indicate when it's ready
*
- * A PTP270PEX card must only be accessed by the driver
+ * A PTP270PEX card must be accessed by the driver only
* after it has finished booting. Otherwise the host system
* may be locked up.
*
@@ -548,15 +764,17 @@ static /*HDR*/
*
* @param pddev The device to be checked
*
- * @see ptp270pex_has_flagged_ready
+ * @return true if the card can flag "ready"
+ *
+ * @see ::ptp270pex_has_flagged_ready
*/
-int ptp270pex_can_flag_ready( const PCPS_DDEV *pddev )
+bool ptp270pex_can_flag_ready( const PCPS_DDEV *pddev )
{
// The GPIO3 input level can only be read via a register
// which is located inside the PCI configuration space
// of the built-in PLX8111 PCIe-to-PCI bridge.
//
- // So we must first locate the PCI bridge associated to our device,
+ // So we must first locate the PCI bridge associated with our device,
// read the PECS_GPIOCTL register and return 1 if the GPIO3 bit
// has been pulled down to 0.
@@ -584,7 +802,7 @@ int ptp270pex_can_flag_ready( const PCPS_DDEV *pddev )
if ( ( rc == PCI_SUCCESS ) && ( uc == pddev->dev.cfg.bus_num ) )
{
#if defined( DEBUG )
- printk( KERN_INFO "%s: Found bridge associated to device %s\n",
+ printk( KERN_INFO "%s: Found bridge associated with device %s\n",
pcps_driver_name, _pcps_ddev_type_name( pddev ) );
#endif
break;
@@ -614,7 +832,7 @@ int ptp270pex_can_flag_ready( const PCPS_DDEV *pddev )
// actually can't then the driver just waits until the maximum
// required uptime has been reached or exceeded, so there's no danger
// that the system might lock up.
- rc = 0;
+ rc = PCI_SUCCESS;
reg_val = 0;
#elif defined( MBG_TGT_DOS )
@@ -632,7 +850,7 @@ int ptp270pex_can_flag_ready( const PCPS_DDEV *pddev )
// The device can indicate when it's ready if reg_val
// has been read successfully, and the GPIO3 bit is 0.
- return ( rc == 0 ) && ( ( reg_val & PLX_PECS_GPIOCTL_GPIO3_DATA ) == 0 );
+ return ( rc == PCI_SUCCESS ) && ( ( reg_val & PLX_PECS_GPIOCTL_GPIO3_DATA ) == 0 );
} // ptp270pex_can_flag_ready
@@ -642,7 +860,7 @@ static /*HDR*/
/**
* @brief Check if a PTP270PEX card indicates it is ready
*
- * A PTP270PEX card must only be accessed by the driver
+ * A PTP270PEX card must be accessed by the driver only
* after it has finished booting. Otherwise the host system
* may be locked up.
*
@@ -650,15 +868,17 @@ static /*HDR*/
* ready to be accessed, so the driver can call this function
* to check this.
*
- * @note The function ptp270pex_can_flag_ready() should
+ * @note The function ::ptp270pex_can_flag_ready should
* have been called before to check if the card actually
* supports this.
*
* @param pddev The device to be checked
*
- * @see ptp270pex_can_flag_ready
+ * @return true if the card has flagged "ready"
+ *
+ * @see ::ptp270pex_can_flag_ready
*/
-int ptp270pex_has_flagged_ready( const PCPS_DDEV *pddev )
+bool ptp270pex_has_flagged_ready( const PCPS_DDEV *pddev )
{
// GPIO pin USERI is pulled down to 0 by the firmware
// as soon as the card is ready to be accessed.
@@ -667,8 +887,8 @@ int ptp270pex_has_flagged_ready( const PCPS_DDEV *pddev )
// Read the LCS_CNTRL register and return 1 if the USERI
// bit is set.
- uint32_t cntrl_reg = _pcps_ddev_io_base_mapped( pddev, 1 )
- + PLX_LCS_CNTRL;
+ PCPS_IO_ADDR_MAPPED cntrl_reg = _pcps_ddev_io_base_mapped( pddev, 1 )
+ + PLX_LCS_CNTRL;
uint32_t reg_val = _mbg_inp32_to_cpu( pddev, 0, cntrl_reg );
return ( reg_val & PLX_LCS_CNTRL_USERI ) == 0;
@@ -677,32 +897,19 @@ int ptp270pex_has_flagged_ready( const PCPS_DDEV *pddev )
-static /*HDR*/
-long mbg_delta_sys_time_ms( const MBG_SYS_TIME *t2, const MBG_SYS_TIME *t1 )
-{
- #if USE_GENERIC_SYS_TIME
- long dt = ( t2->sec - t1->sec ) * 1000;
- #if defined ( MBG_TGT_LINUX ) && defined( MBG_TGT_KERNEL )
- int64_t tmp64 = t2->nsec - t1->nsec;
- do_div( tmp64, 1000000 );
- dt += tmp64;
- #else
- dt += ( t2->nsec - t1->nsec ) / 1000000;
- #endif
- return dt;
- #elif defined( MBG_TGT_WIN32 )
- return (long) ( ( t2->QuadPart - t1->QuadPart ) / HNS_PER_MS );
- #else
- return 0;
- #endif
-
-} // mbg_delta_sys_time_ms
-
-
-
#if MBG_TGT_HAS_UPTIME
static /*HDR*/
+/**
+ * @brief Report the system uptime
+ *
+ * This is mainly used for debugging, and informational.
+ *
+ * @param p_uptime The system uptime
+ *
+ * @see ::wait_ptp270pex_ready
+ * @see ::MAX_BOOT_TIME_PTP270PEX
+ */
void report_uptime( const MBG_SYS_UPTIME *p_uptime )
{
#if defined( MBG_TGT_WIN32 )
@@ -712,7 +919,7 @@ void report_uptime( const MBG_SYS_UPTIME *p_uptime )
swprintf( wcs_msg, L"system uptime: %I64u s, required %u s",
(int64_t) *p_uptime, MAX_BOOT_TIME_PTP270PEX );
- _evt_msg( GlbDriverObject, wcs_msg );
+ _evt_msg_w( GlbDriverObject, wcs_msg );
#else
@@ -753,18 +960,32 @@ void report_uptime( const MBG_SYS_UPTIME *p_uptime )
static /*HDR*/
+/**
+ * @brief Wait until a PTP270PEX card is ready after power-up
+ *
+ * A PTP270PEX card must be accessed by the driver only
+ * after it has finished booting. Otherwise the host system
+ * may be locked up.
+ *
+ * @param pddev The device to be checked
+ *
+ * @see ::ptp270pex_can_flag_ready
+ * @see ::ptp270pex_has_flagged_ready
+ * @see ::report_uptime
+ * @see ::MAX_BOOT_TIME_PTP270PEX
+ */
void wait_ptp270pex_ready( const PCPS_DDEV *pddev )
{
MBG_SYS_TIME t1;
MBG_SYS_TIME t2;
MBG_SYS_UPTIME uptime;
int delayed = 0;
- int can_flag_ready;
+ bool can_flag_ready;
int i = 0;
- // A newer PTP270PEX card (HW v2.0) can indicate if it
- // has finished booting and thus is ready to be accessed,
- // but older PTP270PEX hardware does not support this.
+ // A newer PTP270PEX card (HW v2.0) can indicate if it has
+ // finished booting and thus is ready to be accessed, but
+ // older PTP270PEX cards (HW v1.0) don't support this.
can_flag_ready = ptp270pex_can_flag_ready( pddev );
mbg_get_sys_time( &t1 );
@@ -828,8 +1049,10 @@ void wait_ptp270pex_ready( const PCPS_DDEV *pddev )
WCHAR wcs_msg[128];
swprintf( wcs_msg, L"PTP270PEX startup delay: %li.%03li s",
dt / 1000, ( ( dt < 0 ) ? -dt : dt ) % 1000 );
- _evt_msg( GlbDriverObject, wcs_msg );
+ _evt_msg_w( GlbDriverObject, wcs_msg );
}
+ #else
+ (void) dt;
#endif
}
@@ -838,14 +1061,25 @@ void wait_ptp270pex_ready( const PCPS_DDEV *pddev )
static /*HDR*/
-int pcps_check_pex_irq_unsafe( PCPS_DDEV *pddev, uint16_t req_fw_ver,
- uint8_t req_asic_ver_major, uint8_t req_asic_ver_minor )
+/**
+ * @brief Check if IRQ usage with a device is unsafe
+ *
+ * A few early PCI Express cards had a problem where usage
+ * of IRQs was unsafe. Firmware upgrades are available to fix this.
+ * See http://www.meinberg.de/english/info/pex-upgrades.htm
+ *
+ * @param pddev The device to be checked
+ *
+ * @return true if IRQ operation is unsafe
+ */
+bool pcps_check_pex_irq_unsafe( PCPS_DDEV *pddev, uint16_t req_fw_ver,
+ uint8_t req_asic_ver_major, uint8_t req_asic_ver_minor )
{
- int rc = !_pcps_pex_irq_is_safe( _pcps_ddev_fw_rev_num( pddev ), req_fw_ver,
+ bool b = !_pcps_pex_irq_is_safe( _pcps_ddev_fw_rev_num( pddev ), req_fw_ver,
_pcps_ddev_asic_version( pddev ),
req_asic_ver_major, req_asic_ver_minor );
- if ( rc )
+ if ( b )
{
pddev->irq_stat_info |= PCPS_IRQ_STAT_UNSAFE;
@@ -855,7 +1089,7 @@ int pcps_check_pex_irq_unsafe( PCPS_DDEV *pddev, uint16_t req_fw_ver,
pddev->irq_ack_mask = 0;
}
- return rc;
+ return b;
} // pcps_check_pex_irq_unsafe
@@ -877,22 +1111,22 @@ int map_sys_virtual_address( PCPS_DDEV *pddev )
{
pddev->mm_tstamp_addr = NULL; // unless configured below
- #if defined ( MBG_TGT_WIN32 )
+ #if defined( MBG_TGT_WIN32 )
{
PHYSICAL_ADDRESS pAD;
pAD.QuadPart = pddev->rsrc_info.mem[0].start;
pddev->mm_addr = MmMapIoSpace( pAD, sizeof( *pddev->mm_addr ), MmNonCached );
}
- #elif defined ( MBG_TGT_LINUX )
+ #elif defined( MBG_TGT_LINUX )
pddev->mm_addr = ioremap( ( (ulong) pddev->rsrc_info.mem[0].start ), sizeof( *pddev->mm_addr ) );
- #elif defined ( MBG_TGT_FREEBSD )
+ #elif defined( MBG_TGT_FREEBSD )
pddev->mm_addr = rman_get_virtual( pddev->rsrc_info.mem[0].bsd.res );
- #elif defined ( MBG_TGT_NETBSD )
+ #elif defined( MBG_TGT_NETBSD )
pddev->mm_addr = bus_space_vaddr( pddev->rsrc_info.mem[0].bsd.bst, pddev->rsrc_info.mem[0].bsd.bsh );
@@ -915,9 +1149,11 @@ int map_sys_virtual_address( PCPS_DDEV *pddev )
if ( _pcps_ddev_is_pci_pex8311( pddev ) )
pddev->mm_tstamp_addr = &pddev->mm_addr->pex8311.tstamp;
+#if 0 //### FIXME
_mbgddmsg_3( MBG_DBG_INIT_DEV, "MM addr: base: 0x%p, tstamp: 0x%p, offs: 0x%02lX",
pddev->mm_addr, pddev->mm_tstamp_addr,
- (ulong) pddev->mm_tstamp_addr - (ulong) pddev->mm_addr );
+ (ulong) ( (uint8_t *) pddev->mm_tstamp_addr - (uint8_t *) pddev->mm_addr ) );
+#endif
return 0;
@@ -931,9 +1167,9 @@ void unmap_sys_virtual_address( PCPS_DDEV *pddev )
if ( has_mapped_sys_virtual_address( pddev ) )
{
- #if defined ( MBG_TGT_WIN32 )
+ #if defined( MBG_TGT_WIN32 )
MmUnmapIoSpace( pddev->mm_addr, sizeof( *pddev->mm_addr ) );
- #elif defined ( MBG_TGT_LINUX )
+ #elif defined( MBG_TGT_LINUX )
iounmap( pddev->mm_addr );
#else // DOS, ...
// nothing to do
@@ -955,7 +1191,7 @@ void unmap_sys_virtual_address( PCPS_DDEV *pddev )
#if DEBUG_PRINT_ACCESS_TIMES
-#if 0 //##++++
+#if 0 //### TODO FIXME if we need it
static inline
long _cyc_to_us( long long cyc )
{
@@ -970,7 +1206,11 @@ static inline
long long _cyc_to_ps( long long cyc )
{
cyc *= 1000000000;
- do_div( cyc, cpu_khz );
+ #if defined( MBG_TGT_LINUX )
+ do_div( cyc, cpu_khz );
+ #else
+ cyc = 0; //### TODO FIXME for different targets
+ #endif
return cyc;
}
@@ -985,7 +1225,7 @@ long long _cyc_to_ps( long long cyc )
uint32_t dummy;
-static
+static /*HDR*/
void report_access_timing( const PCPS_DDEV *pddev, const char *info,
MBG_PC_CYCLES t_after_cmd, MBG_PC_CYCLES t_after_reread )
{
@@ -1013,17 +1253,18 @@ void report_access_timing( const PCPS_DDEV *pddev, const char *info,
} // report_access_timing
-#endif
+#endif // DEBUG_ACCESS_TIMING
+
#if DEBUG_IO_TIMING
-static
+static /*HDR*/
void report_io_timing( const PCPS_DDEV *pddev, const char *info,
uint8_t cmd, uint16_t count, MBG_PC_CYCLES t_after_cmd,
MBG_PC_CYCLES t_after_busy, MBG_PC_CYCLES t_done )
{
- #if defined( MBG_TGT_LINUX )
+ #if defined( MBG_TGT_LINUX ) //##++++ TODO support other OSs
long long cmd_cycles = t_after_cmd - pddev->acc_cycles;
long long busy_cycles = t_after_busy - t_after_cmd;
long long read_cycles = t_done - t_after_busy;
@@ -1059,26 +1300,74 @@ void report_io_timing( const PCPS_DDEV *pddev, const char *info,
, cmd_time, busy_time, read_time, time_per_read, (ulong) cpu_khz
#endif
);
- #endif
-
printk( KERN_ERR "cycles after cmd: %lli, after busy: %lli, when done: %lli\n",
(long long) t_after_cmd,
(long long) t_after_busy,
(long long) t_done );
+ #endif
+
} // report_io_timing
-#endif
+#endif // DEBUG_IO_TIMING
+
+
+
+#if DEBUG_USB_IO
+
+// This is the prototype of the standard usb_bulk_msg() prototype
+// provided by the Linux kernel. We include it here to make sure
+// our debug wrapper function usb_bulk_msg_dbg() has the same
+// prototype, otherwise we'd expect a compiler warning.
+
+int usb_bulk_msg( struct usb_device *usb_dev,
+ unsigned int pipe,
+ void *data,
+ int len,
+ int *actual_length,
+ int timeout );
+
+
+ /*HDR*/ //### TODO Do we need a prototype?
+int usb_bulk_msg_dbg( struct usb_device *usb_dev,
+ unsigned int pipe,
+ void *data,
+ int len,
+ int *actual_length,
+ int timeout )
+{
+ int rc = usb_bulk_msg( usb_dev, pipe, data, len, actual_length, timeout );
+
+ _mbgddmsg_6( MBG_DBG_ERR, "usb_bulk_msg: pipe %u, data %p, len %i, actual_len %i, timeout %i: returned %i",
+ pipe, data, len, *actual_length, timeout, rc );
+
+ return rc;
+
+} // usb_bulk_msg_dbg
+
+#endif // DEBUG_USB_IO
#if defined( __GNUC__ )
// Avoid "no previous prototype" with some gcc versions.
__mbg_inline
-int pcps_wait_busy( PCPS_DDEV *pddev ) __attribute__((always_inline));
+int pcps_wait_busy( PCPS_DDEV *pddev );
#endif
__mbg_inline /*HDR*/
+/**
+ * @brief Wait as long as a device is busy, or until timeout
+ *
+ * Used by the @ref pcps_read_fncs to wait after the command byte has been
+ * written until the requested data has been made available by the device.
+ *
+ * @param[in] pddev Pointer to the device structure
+ *
+ * @return ::MBG_SUCCESS on success, or ::MBG_ERR_TIMEOUT
+ *
+ * @see @ref pcps_read_fncs
+ */
int pcps_wait_busy( PCPS_DDEV *pddev )
{
if ( _pcps_ddev_status_busy( pddev ) )
@@ -1114,56 +1403,81 @@ int pcps_wait_busy( PCPS_DDEV *pddev )
#endif
}
- return 0;
+ return MBG_SUCCESS;
} // pcps_wait_busy
-/*--------------------------------------------------------------
- * Name: pcps_read_null()
- * pcps_read_std()
- * pcps_read_amcc_s5933()
- * pcps_read_amcc_s5920()
- * pcps_read_asic()
- * pcps_read_usb()
- *
- * Purpose: These functions are used for low level access
- * to Meinberg plug-in devices. The function
- * to be used depends on the clock's bus type and
- * interface chip.
+/**
+ * @defgroup pcps_read_fncs Device read functions
*
- * Input: pcfg pointer to the clock's configuration
- * cmd the command code for the board
- * count the number of bytes to be read
+ * These group of functions is used for low level access to Meinberg
+ * bus-level devices. Which of the function is actually to be used
+ * depends on the device's bus type and interface chip and is determined
+ * by the function ::pcps_start_device which is called at device startup.
*
- * Output: buffer the bytes that could be read
+ * @see ::pcps_read_null
+ * @see ::pcps_read_std
+ * @see ::pcps_read_amcc_s5933
+ * @see ::pcps_read_amcc_s5920
+ * @see ::pcps_read_asic
+ * @see ::pcps_read_usb
*
- * Ret value: MBG_SUCCESS no error
- * MBG_ERR_TIMEOUT board is busy for too long
- *-------------------------------------------------------------*/
+ * @{ */
-// The dummy read function below is used if a clock is
-// not properly initialized, in order to avoid I/O access
-// on unspecified ports.
-static /*HDR*/ /* PCPS_READ_FNC */
-short pcps_read_null( PCPS_DDEV *pddev, uint8_t cmd,
- void FAR *buffer, uint16_t count )
+static /*HDR*/
+/**
+ * @brief Dummy read function
+ *
+ * Used if a clock is not properly initialized, in order to
+ * avoid I/O access on unspecified ports.
+ *
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] cmd The command code for the board, see @ref PCPS_CMD_CODES
+ * @param[out] buffer A buffer to take the bytes to be read
+ * @param[in] count The number of bytes to be read into the buffer
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_read_fncs
+ * @see @ref pcps_read_fncs
+ */
+int pcps_read_null( PCPS_DDEV *pddev, uint8_t cmd,
+ void FAR *buffer, uint16_t count )
{
+ // avoid compiler warnings
+ (void) pddev;
+ (void) cmd;
+ (void) buffer;
+ (void) count;
return MBG_ERR_TIMEOUT;
} // pcps_read_null
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_READ_FNC pcps_read_null;
+#endif
-// The function below must be used to access a clock with
-// standard ISA or micro channel bus.
-
-static /*HDR*/ /* PCPS_READ_FNC */
-short pcps_read_std( PCPS_DDEV *pddev, uint8_t cmd,
- void FAR *buffer, uint16_t count )
+static /*HDR*/
+/**
+ * @brief Read function for devices with ISA or micro channel bus
+ *
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] cmd The command code for the board, see @ref PCPS_CMD_CODES
+ * @param[out] buffer A buffer to take the bytes to be read
+ * @param[in] count The number of bytes to be read into the buffer
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_read_fncs
+ * @see @ref pcps_read_fncs
+ */
+int pcps_read_std( PCPS_DDEV *pddev, uint8_t cmd,
+ void FAR *buffer, uint16_t count )
{
uint8_t FAR *p = (uint8_t FAR *) buffer;
PCPS_IO_ADDR_MAPPED port = _pcps_ddev_io_base_mapped( pddev, 0 );
@@ -1199,18 +1513,31 @@ short pcps_read_std( PCPS_DDEV *pddev, uint8_t cmd,
return MBG_SUCCESS;
-} // pcps_read_std
+} // pcps_read_std
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_READ_FNC pcps_read_std;
+#endif
#if _PCPS_USE_PCI
-// The function below must be used to access a clock with
-// PCI bus and AMCC S5933 interface chip.
-
-static /*HDR*/ /* PCPS_READ_FNC */
-short pcps_read_amcc_s5933( PCPS_DDEV *pddev, uint8_t cmd,
- void FAR *buffer, uint16_t count )
+static /*HDR*/
+/**
+ * @brief Read function for devices with AMCC S5933 PCI interface chip
+ *
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] cmd The command code for the board, see @ref PCPS_CMD_CODES
+ * @param[out] buffer A buffer to take the bytes to be read
+ * @param[in] count The number of bytes to be read into the buffer
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_read_fncs
+ * @see @ref pcps_read_fncs
+ */
+int pcps_read_amcc_s5933( PCPS_DDEV *pddev, uint8_t cmd,
+ void FAR *buffer, uint16_t count )
{
uint8_t FAR *p = (uint8_t FAR *) buffer;
PCPS_IO_ADDR_MAPPED port = _pcps_ddev_io_base_mapped( pddev, 0 );
@@ -1260,7 +1587,11 @@ short pcps_read_amcc_s5933( PCPS_DDEV *pddev, uint8_t cmd,
return MBG_SUCCESS;
-} /* pcps_read_amcc_s5933 */
+} // pcps_read_amcc_s5933
+
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_READ_FNC pcps_read_amcc_s5933;
+#endif
#endif /* _PCPS_USE_PCI */
@@ -1268,12 +1599,22 @@ short pcps_read_amcc_s5933( PCPS_DDEV *pddev, uint8_t cmd,
#if _PCPS_USE_PCI
-// The function below must be used to access a clock with
-// PCI bus and AMCC S5920 interface chip.
-
-static /*HDR*/ /* PCPS_READ_FNC */
-short pcps_read_amcc_s5920( PCPS_DDEV *pddev, uint8_t cmd,
- void FAR *buffer, uint16_t count )
+static /*HDR*/
+/**
+ * @brief Read function for devices with AMCC S5920 PCI interface chip
+ *
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] cmd The command code for the board, see @ref PCPS_CMD_CODES
+ * @param[out] buffer A buffer to take the bytes to be read
+ * @param[in] count The number of bytes to be read into the buffer
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_read_fncs
+ * @see @ref pcps_read_fncs
+ */
+int pcps_read_amcc_s5920( PCPS_DDEV *pddev, uint8_t cmd,
+ void FAR *buffer, uint16_t count )
{
uint8_t FAR *p = (uint8_t FAR *) buffer;
PCPS_IO_ADDR_MAPPED data_port = _pcps_ddev_io_base_mapped( pddev, 1 );
@@ -1351,18 +1692,33 @@ short pcps_read_amcc_s5920( PCPS_DDEV *pddev, uint8_t cmd,
} // pcps_read_amcc_s5920
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_READ_FNC pcps_read_amcc_s5920;
+#endif
+
#endif /* _PCPS_USE_PCI */
#if _PCPS_USE_PCI
-// The function below must be used to access a clock with
-// PCI bus and Meinberg PCI interface ASIC.
-
-static /*HDR*/ /* PCPS_READ_FNC */
-short pcps_read_asic( PCPS_DDEV *pddev, uint8_t cmd,
- void FAR *buffer, uint16_t count )
+static /*HDR*/
+/**
+ * @brief Read function for devices with Meinberg PCI interface ASIC
+ *
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] cmd The command code for the board, see @ref PCPS_CMD_CODES
+ * @param[out] buffer A buffer to take the bytes to be read
+ * @param[in] count The number of bytes to be read into the buffer
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_read_fncs
+ * @see ::pcps_read_asic_mm
+ * @see @ref pcps_read_fncs
+ */
+int pcps_read_asic( PCPS_DDEV *pddev, uint8_t cmd,
+ void FAR *buffer, uint16_t count )
{
short ret_val = MBG_SUCCESS;
uint8_t FAR *p = (uint8_t FAR *) buffer;
@@ -1473,16 +1829,34 @@ done:
} // pcps_read_asic
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_READ_FNC pcps_read_asic;
+#endif
#if _PCPS_USE_MM_IO
-// The function below must be used to access a clock with
-// PCI bus and Meinberg PCI interface ASIC.
-
-static /*HDR*/ /* type: PCPS_READ_FNC */
-short pcps_read_asic_mm( PCPS_DDEV *pddev, uint8_t cmd,
- void FAR *buffer, uint16_t count )
+static /*HDR*/
+/**
+ * @brief Read function for devices with Meinberg PCI interface ASIC
+ *
+ * Unlike ::pcps_read_asic and most of the other read functions,
+ * this function accesses the memory mapped registers rather than
+ * the I/O ports, so this is significantly faster.
+ *
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] cmd The command code for the board, see @ref PCPS_CMD_CODES
+ * @param[out] buffer A buffer to take the bytes to be read
+ * @param[in] count The number of bytes to be read into the buffer
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_read_fncs
+ * @see ::pcps_read_asic
+ * @see @ref pcps_read_fncs
+ */
+int pcps_read_asic_mm( PCPS_DDEV *pddev, uint8_t cmd,
+ void FAR *buffer, uint16_t count )
{
short ret_val = MBG_SUCCESS;
uint8_t FAR *p = (uint8_t FAR *) buffer;
@@ -1507,7 +1881,7 @@ short pcps_read_asic_mm( PCPS_DDEV *pddev, uint8_t cmd,
#endif
#if DEBUG_IO
- _mbgddmsg_3( MBG_DBG_INIT_DEV, "pcps_read_asic_mm: cmd: 0x%02X (0x%08X), cnt: %u",
+ _mbgddmsg_3( MBG_DBG_INIT_DEV, "pcps_read_asic_mm: cmd: 0x%02X (0x%08X), cnt: %u",
cmd, _cpu_to_mbg32( cmd ), count );
#endif
@@ -1597,6 +1971,10 @@ done:
} // pcps_read_asic_mm
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_READ_FNC pcps_read_asic_mm;
+#endif
+
#endif // _PCPS_USE_MM_IO
#endif // _PCPS_USE_PCI
@@ -1605,11 +1983,23 @@ done:
#if _PCPS_USE_USB
-// The function below must be used to access a device connected via USB.
-
-static /*HDR*/ /* PCPS_READ_FNC */
-short pcps_read_usb( PCPS_DDEV *pddev, uint8_t cmd,
- void FAR *buffer, uint16_t count )
+static /*HDR*/
+/**
+ * @brief Read function for USB devices
+ *
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] cmd The command code for the board, see @ref PCPS_CMD_CODES
+ * @param[out] buffer A buffer to take the bytes to be read
+ * @param[in] count The number of bytes to be read into the buffer
+ *
+ * @return ::MBG_SUCCESS on success, or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_read_fncs
+ * @see ::pcps_read_asic
+ * @see @ref pcps_read_fncs
+ */
+int pcps_read_usb( PCPS_DDEV *pddev, uint8_t cmd,
+ void FAR *buffer, uint16_t count )
{
int actual_count = 0;
short rc;
@@ -1618,7 +2008,16 @@ short pcps_read_usb( PCPS_DDEV *pddev, uint8_t cmd,
rc = _pcps_usb_write_var( pddev, &cmd );
- if ( ( rc == MBG_SUCCESS ) && ( count && buffer ) )
+ #if DEBUG_USB_IO
+ if ( rc == 0 )
+ _mbgddmsg_4( MBG_DBG_INFO, "%s: %s _pcps_usb_write_var cmd 0x%02X, %i bytes: succeeded",
+ pcps_driver_name, _pcps_ddev_type_name( pddev ), cmd, actual_count );
+ else
+ _mbgddmsg_5( MBG_DBG_ERR, "%s: %s _pcps_usb_write_var cmd 0x%02X, %i bytes: failed with rc %i",
+ pcps_driver_name, _pcps_ddev_type_name( pddev ), cmd, actual_count, rc );
+ #endif // DEBUG_USB_IO
+
+ if ( ( rc == 0 ) && ( count && buffer ) )
{
#if defined( MBG_TGT_WIN32_PNP )
#if USE_USB_MICRO_FRAMES
@@ -1635,9 +2034,18 @@ short pcps_read_usb( PCPS_DDEV *pddev, uint8_t cmd,
rc = _pcps_usb_read( pddev, buffer, count );
+ #if DEBUG_USB_IO
+ if ( rc == 0 )
+ _mbgddmsg_4( MBG_DBG_INFO, "%s: %s _pcps_usb_read after cmd 0x%02X succeeded, bytes read: %i",
+ pcps_driver_name, _pcps_ddev_type_name( pddev ), cmd, actual_count );
+ else
+ _mbgddmsg_5( MBG_DBG_ERR, "%s: %s _pcps_usb_read after cmd 0x%02X failed after with rc %i, bytes read: %i",
+ pcps_driver_name, _pcps_ddev_type_name( pddev ), cmd, rc, actual_count );
+ #endif // DEBUG_USB_IO
+
#if defined( MBG_TGT_WIN32_PNP )
- if ( cmd == PCPS_GIVE_HR_TIME && rc == PCPS_SUCCESS )
+ if ( cmd == PCPS_GIVE_HR_TIME && rc == 0 )
{
ULONGLONG usb_latency_cycles;
ULONGLONG cycles_diff;
@@ -1678,7 +2086,7 @@ short pcps_read_usb( PCPS_DDEV *pddev, uint8_t cmd,
if ( ( temp_fn1 == 0 ) && ( temp_fn2 == 0 ) )
{
if ( cycles_diff > frame_length_cycles )
- usb_latency_cycles = cycles_diff - frame_length_cycles;
+ usb_latency_cycles = cycles_diff - frame_length_cycles;
else
usb_latency_cycles = frame_length_cycles - cycles_diff;
}
@@ -1688,7 +2096,7 @@ short pcps_read_usb( PCPS_DDEV *pddev, uint8_t cmd,
#if defined( DEBUG )
swprintf( pddev->wcs_msg, L"FD %d CD %I64u l %I64u fl %I64u", FrameNumberDiff,
cycles_diff, usb_latency_cycles, frame_length_cycles );
- _dbg_evt_msg( GlbDriverObject, pddev->wcs_msg );
+ _dbg_evt_msg_w( GlbDriverObject, pddev->wcs_msg );
#endif
}
@@ -1701,36 +2109,38 @@ short pcps_read_usb( PCPS_DDEV *pddev, uint8_t cmd,
} // pcps_read_usb
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_READ_FNC pcps_read_usb;
#endif
+#endif // _PCPS_USE_USB
+/** @} defgroup group_pcps_read_fnc */
-/*--------------------------------------------------------------
- * Name: pcps_write()
- *
- * Purpose: Write data to a device.
+
+
+/*HDR*/
+/**
+ * @brief Write data to a device
*
- * Input: pddev pointer to the device information
- * cmd the address of buffer holding the
- * date/time/status information
- * read_fnc function to access the board
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] cmd The command code for the board, see @ref PCPS_CMD_CODES
+ * @param[in] buffer A buffer with data to be written according to the cmd code
+ * @param[in] count The number of bytes to be written according to the cmd code
*
- * Output: --
+ * @return ::MBG_SUCCESS on success,
+ * ::MBG_ERR_TIMEOUT if device didn't respond in time,
+ * ::MBG_ERR_NBYTES if the number of parameter bytes did not match
+ * the number of data bytes expected by the device,
+ * or one of the other @ref MBG_RETURN_CODES
*
- * Ret value: MBG_SUCCESS no error
- * MBG_ERR_TIMEOUT board is busy for too long
- * MBG_ERR_NBYTES the number of parameter bytes
- * did not match the number of
- * data bytes expected
- * MBG_ERR_STIME the date, time or status
- * has been invalid
- *-------------------------------------------------------------*/
-
-/*HDR*/ /* PCPS_WRITE_FNC */
-short pcps_write( PCPS_DDEV *pddev, uint8_t cmd,
- const void FAR *buffer, uint16_t count )
+ * @ingroup pcps_io_fncs
+ * @see @ref pcps_io_fncs
+ */
+int pcps_write( PCPS_DDEV *pddev, uint8_t cmd,
+ const void FAR *buffer, uint16_t count )
{
- short rc;
+ int rc;
#if _PCPS_USE_USB
if ( _pcps_ddev_is_usb( pddev ) )
@@ -1824,37 +2234,39 @@ done:
} // pcps_write
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_WRITE_FNC pcps_write;
+#endif
-/*--------------------------------------------------------------
- * Name: pcps_generic_io()
- *
- * Purpose: Write data to and/or read data from a device.
+
+/*HDR*/
+/**
+ * @brief Generic I/O function
*
- * Input: pddev pointer to the device information
- * cmd the address of buffer holding the
- * date/time/status information
- * read_fnc function to access the board
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] type The type of data to be read/written, see @ref PCPS_CMD_CODES
+ * @param[in] in_buff A buffer with data to be written according to the type code
+ * @param[in] in_cnt The number of bytes to be written according to the type code
+ * @param[out] out_buff A buffer with data to be read according to the type code
+ * @param[in] out_cnt The number of bytes to be read according to the type code
*
- * Output: --
+ * @return ::MBG_SUCCESS on success,
+ * ::MBG_ERR_TIMEOUT if device didn't respond in time,
+ * ::MBG_ERR_NBYTES if the number of parameter bytes did not match
+ * the number of data bytes expected by the device,
+ * or one of the other @ref MBG_RETURN_CODES
*
- * Ret value: MBG_SUCCESS no error
- * MBG_ERR_TIMEOUT board is busy for too long
- * MBG_ERR_NBYTES the number of parameter bytes
- * did not match the number of
- * data bytes expected
- * MBG_ERR_STIME the date, time or status
- * has been invalid
- *-------------------------------------------------------------*/
-
-/*HDR*/
-short pcps_generic_io( PCPS_DDEV *pddev, uint8_t type,
- const void FAR *in_buff, uint8_t in_cnt,
- void FAR *out_buff, uint8_t out_cnt )
+ * @ingroup pcps_io_fncs
+ * @see @ref pcps_io_fncs
+ */
+int pcps_generic_io( PCPS_DDEV *pddev, uint8_t type,
+ const void FAR *in_buff, uint8_t in_cnt,
+ void FAR *out_buff, uint8_t out_cnt )
{
const uint8_t FAR *p;
int i;
- short rc;
+ int rc;
uint8_t tmp_byte;
int8_t data_read[PCPS_FIFO_SIZE];
uint8_t bytes_to_read;
@@ -1874,7 +2286,7 @@ short pcps_generic_io( PCPS_DDEV *pddev, uint8_t type,
// the number of data bytes that must follow.
rc = _pcps_read_var( pddev, PCPS_GENERIC_IO, tmp_byte );
- if ( rc < 0 )
+ if ( mbg_rc_is_error( rc ) )
return rc;
@@ -1884,20 +2296,20 @@ short pcps_generic_io( PCPS_DDEV *pddev, uint8_t type,
#if DEBUG_IO
- _mbgddmsg_3( MBG_DBG_DETAIL, "pcps_generic_io: going to write type 0x%02X, in_sz %u, out_sz %u",
+ _mbgddmsg_3( MBG_DBG_DETAIL, "pcps_generic_io: going to write type 0x%02X, in_sz %i, out_sz %i",
type, in_cnt, out_cnt );
#endif
// Write the 3 bytes which are expected:
rc = _pcps_write_byte( pddev, type );
- if ( rc != MBG_SUCCESS )
+ if ( mbg_rc_is_error( rc ) )
goto done;
rc = _pcps_write_byte( pddev, in_cnt );
- if ( rc != MBG_SUCCESS )
+ if ( mbg_rc_is_error( rc ) )
goto done;
@@ -1907,7 +2319,7 @@ short pcps_generic_io( PCPS_DDEV *pddev, uint8_t type,
{
rc = _pcps_write_byte( pddev, out_cnt );
- if ( rc != MBG_SUCCESS )
+ if ( mbg_rc_is_error( rc ) )
goto done;
@@ -1923,7 +2335,7 @@ short pcps_generic_io( PCPS_DDEV *pddev, uint8_t type,
{
rc = _pcps_write_byte( pddev, *p++ );
- if ( rc < 0 )
+ if ( mbg_rc_is_error( rc ) )
goto done;
}
@@ -1940,8 +2352,8 @@ short pcps_generic_io( PCPS_DDEV *pddev, uint8_t type,
// Write the last byte and read the completion code.
rc = _pcps_read( pddev, tmp_byte, data_read, bytes_to_read );
- if ( out_cnt ) //##++ should do some more plausibility checks
- if ( rc == MBG_SUCCESS )
+ if ( out_cnt ) //### TODO should do some more plausibility checks
+ if ( mbg_rc_is_success( rc ) )
{
_fmemcpy( out_buff, &data_read[2], out_cnt );
}
@@ -1950,7 +2362,7 @@ done:
// If an error code has been returned by the I/O function,
// return that code, otherwise return the completion code
// read from the board.
- return ( rc < 0 ) ? rc : data_read[0];
+ return mbg_rc_is_error( rc ) ? rc : data_read[0];
} // pcps_generic_io
@@ -1977,14 +2389,14 @@ done:
*-------------------------------------------------------------*/
static /*HDR*/
-short pcps_read_gps_block( PCPS_DDEV *pddev,
- uint8_t data_type,
- void FAR *buffer,
- uint16_t buffer_size,
- uint8_t block_num,
- uint8_t block_size )
+int pcps_read_gps_block( PCPS_DDEV *pddev,
+ uint8_t data_type,
+ void FAR *buffer,
+ uint16_t buffer_size,
+ uint8_t block_num,
+ uint8_t block_size )
{
- short rc;
+ int rc;
uint16_t n_bytes;
uint8_t size_n_bytes;
uint8_t uc;
@@ -2051,7 +2463,7 @@ short pcps_read_gps_block( PCPS_DDEV *pddev,
#endif
#if DEBUG_IO
- _mbgddmsg_2( MBG_DBG_DETAIL, "pcps_read_gps_block: board expects data size %u, buffer size %u",
+ _mbgddmsg_2( MBG_DBG_DETAIL, "pcps_read_gps_block: device expects data size %u, buffer size %u",
n_bytes, buffer_size );
#endif
@@ -2087,21 +2499,21 @@ short pcps_read_gps_block( PCPS_DDEV *pddev,
* MBG_ERR_NBYTES
*-------------------------------------------------------------*/
-/*HDR*/ /* PCPS_READ_FNC */
-short pcps_read_gps( PCPS_DDEV *pddev,
- uint8_t data_type,
- void FAR *buffer,
- uint16_t buffer_size )
+/*HDR*/
+int pcps_read_gps( PCPS_DDEV *pddev,
+ uint8_t data_type,
+ void FAR *buffer,
+ uint16_t buffer_size )
{
uint8_t FAR *p = (uint8_t FAR *) buffer;
- short rc = 0;
+ int rc = 0;
int dt_quot;
int dt_rem;
int block_num;
#if DEBUG_IO
- _mbgddmsg_3( MBG_DBG_DETAIL, "Going to read GPS data, type: %02X, addr: %p, size: %u",
+ _mbgddmsg_3( MBG_DBG_DETAIL, "Going to read GPS data, type: 0x%02X, addr: %p, size: %u",
data_type, buffer, buffer_size );
#endif
@@ -2138,6 +2550,9 @@ done:
} // pcps_read_gps
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_READ_FNC pcps_read_gps;
+#endif
/*--------------------------------------------------------------
@@ -2158,14 +2573,14 @@ done:
* MBG_ERR_NBYTES
*-------------------------------------------------------------*/
-/*HDR*/ /* PCPS_WRITE_FNC */
-short pcps_write_gps( PCPS_DDEV *pddev,
- uint8_t data_type,
- const void FAR *buffer,
- uint16_t buffer_size )
+/*HDR*/
+int pcps_write_gps( PCPS_DDEV *pddev,
+ uint8_t data_type,
+ const void FAR *buffer,
+ uint16_t buffer_size )
{
const uint8_t FAR *p = (const uint8_t FAR *) buffer;
- short rc;
+ int rc;
short i;
uint16_t n_bytes;
uint8_t size_n_bytes;
@@ -2231,12 +2646,12 @@ short pcps_write_gps( PCPS_DDEV *pddev,
#endif
#if DEBUG_IO
- _mbgddmsg_2( MBG_DBG_DETAIL, "pcps_write_gps: board expects data size %u, buffer size %u",
+ _mbgddmsg_2( MBG_DBG_DETAIL, "pcps_write_gps: device expects data size %u, buffer size is %u",
n_bytes, buffer_size );
#endif
if ( n_bytes != buffer_size ) // The board doesn't expect the number
- return MBG_ERR_NBYTES; // of bytes we were going to write.
+ return MBG_ERR_NBYTES; // of bytes we were going to write.
// Write all bytes but the last one without reading.
@@ -2260,71 +2675,65 @@ short pcps_write_gps( PCPS_DDEV *pddev,
} // pcps_write_gps
+#if !defined( AVOID_REDUNDANT_REDECLARATION )
+ PCPS_WRITE_FNC pcps_write_gps;
+#endif
-/*--------------------------------------------------------------
- * Name: pcps_get_fw_id()
- *
- * Purpose: This function tries to read the firmware ID
- * from the board. It should be used to check
- * if the board is properly installed and can
- * be accessed without problems.
+
+static /*HDR*/
+/**
+ * @brief Read the firmware ID from a device
*
- * Input: pddev pointer to the device information
+ * This is usually done first when probing a device to check if the
+ * device is properly installed and can be accessed without problems.
*
- * Output: fw_id buffer filled with ASCIIZ string
+ * @param[in] pddev Pointer to a device structure
+ * @param[out] fw_id A buffer to be filled withtthe firmware ID
*
- * Ret value: MBG_SUCCESS no error
- * MBG_ERR_TIMEOUT the board is busy for too long
- *-------------------------------------------------------------*/
-
-/*HDR*/
-short pcps_get_fw_id( PCPS_DDEV *pddev, PCPS_ID_STR FAR fw_id )
+ * @return ::MBG_SUCCESS if the the signature was found, or signature was specified, or
+ * ::MBG_ERR_FW_ID if the firmware ID is unknown or invalid
+ */
+int pcps_get_fw_id( PCPS_DDEV *pddev, PCPS_ID_STR FAR fw_id )
{
- short rc;
+ int rc;
+ memset( fw_id, 0, sizeof( PCPS_ID_STR ) ); // sizeof( fw_id ) would yield pointer size only
- // read first part of the firmware ID
+ // read the first part of the firmware ID
rc = _pcps_read( pddev, PCPS_GIVE_FW_ID_1, &fw_id[0], PCPS_FIFO_SIZE );
- if ( rc != MBG_SUCCESS )
- return rc; // may be timeout
-
+ if ( mbg_rc_is_error( rc ) )
+ goto out;
- // read second part of the firmware ID
+ // read the second part of the firmware ID
rc = _pcps_read( pddev, PCPS_GIVE_FW_ID_2, &fw_id[PCPS_FIFO_SIZE], PCPS_FIFO_SIZE );
- if ( rc != MBG_SUCCESS )
- return rc; // may be timeout
-
-
- // terminate the string with 0
-
+ // force termination with 0
fw_id[PCPS_ID_SIZE - 1] = 0;
-
- return MBG_SUCCESS;
+out:
+ return rc;
} // pcps_get_fw_id
-/*--------------------------------------------------------------
- * Name: pcps_check_id()
+static /*HDR*/
+/**
+ * @brief Check an ASCIIZ string for a valid signature.
*
- * Purpose: Check an ASCIIZ string for a valid signature.
+ * This function is only used to determine the type of a legacy ISA card.
+ * For PCI and USB devices the type can be determined from the device ID.
*
- * Input: pddev pointer to the device information
- * ref the reference signature
+ * @param[in] pddev Pointer to a device structure
+ * @param[in] ref The reference signature, i.e. the expected signature
+ * at the beginning of the device's firmware ID
*
- * Output: --
- *
- * Ret value: MBG_SUCCESS no error
- * MBG_ERR_FW_ID the firmware ID is not valid
- *-------------------------------------------------------------*/
-
-/*HDR*/
-short pcps_check_id( PCPS_DDEV *pddev, const char FAR *ref )
+ * @return ::MBG_SUCCESS if a signature was specified and the signature was found, or
+ * ::MBG_ERR_FW_ID if the firmware ID is unknown or invalid
+ */
+int pcps_check_id( PCPS_DDEV *pddev, const char FAR *ref )
{
// check if the first characters of the string match the reference
@@ -2338,38 +2747,36 @@ short pcps_check_id( PCPS_DDEV *pddev, const char FAR *ref )
-/*--------------------------------------------------------------
- * Name: pcps_get_rev_num()
- *
- * Purpose: Get a version number from an ID string.
- *
- * Input: idstr the ID string
+static /*HDR*/
+/**
+ * @brief Retrieve a version number from a firmware ID string
*
- * Output: --
+ * @param[in] idstr The ID string, e.g. a ::PCPS_ID_STR
*
- * Ret value: on success: the version number in hex
- * (e.g. 0x0270 for version 2.7)
- * on error: 0
- *-------------------------------------------------------------*/
-
-/*HDR*/
-short pcps_get_rev_num( char FAR *idstr )
+ * @return A version number in hex format, e.g. 0x0270 for version 2.7,
+ * or 0 if no version number could be found.
+ */
+PCPS_FW_REV_NUM pcps_get_rev_num( char FAR *idstr )
{
+ int len = _fstrlen( idstr );
int i;
- int len = _fstrlen( idstr ) - 2;
- char c;
- uchar rev_num_hi;
- uchar rev_num_lo;
+ if ( len < 2 )
+ goto no_rev_num;
+
+ len -= 2;
for ( i = 0; i < len; i++ )
{
if ( idstr[i + 1] == '.' )
{
- rev_num_hi = idstr[i] & 0x0F;
- rev_num_lo = ( idstr[i + 2] & 0x0F ) << 4;
+ uint8_t rev_num_hi = idstr[i] & 0x0F;
+ uint8_t rev_num_lo = ( idstr[i + 2] & 0x0F ) << 4;
- c = idstr[i + 3];
+ // If the minor part of the version string has 2 digits
+ // then evaluate the 2nd digit, too.
+
+ char c = idstr[i + 3];
if ( c >= '0' && c <= '9' )
rev_num_lo |= c & 0x0F;
@@ -2378,6 +2785,7 @@ short pcps_get_rev_num( char FAR *idstr )
}
}
+no_rev_num:
return 0;
} // pcps_get_rev_num
@@ -2439,11 +2847,13 @@ int pcps_read_sernum( PCPS_DDEV *pddev )
// so use that one, if supported.
if ( _pcps_ddev_has_receiver_info( pddev ) )
{
+ RECEIVER_INFO *p_ri = _ri_addr( pddev );
+
#if DEBUG_SERNUM
_mbgddmsg_0( MBG_DBG_DETAIL, "getting S/N from receiver info" );
#endif
- rc = _pcps_read_gps_var( pddev, PC_GPS_RECEIVER_INFO, pddev->ri );
+ rc = _pcps_read_gps_var( pddev, PC_GPS_RECEIVER_INFO, *p_ri );
if ( rc != MBG_SUCCESS )
{
@@ -2452,9 +2862,9 @@ int pcps_read_sernum( PCPS_DDEV *pddev )
goto fail;
}
- _mbg_swab_receiver_info( &pddev->ri );
+ _mbg_swab_receiver_info( p_ri );
- strncpy( pddev->dev.cfg.sernum, pddev->ri.sernum,
+ strncpy( pddev->dev.cfg.sernum, p_ri->sernum,
sizeof( pddev->dev.cfg.sernum ) );
goto check;
}
@@ -2542,7 +2952,7 @@ fail:
fail:
// No valid serial number has been found, though the device
- // should have one. In order to distinguish from devices which
+ // should have one. In order to distinguish from devices which
// don't even support a serial number we return a number of '?'
// rather than "N/A".
memset( pddev->dev.cfg.sernum, '?', 8 );
@@ -2561,7 +2971,14 @@ done:
#if _PCPS_USE_RSRCMGR
-/*HDR*/
+static /*HDR*/
+/**
+ * @brief Try to claim an I/O port resource range
+ *
+ * @param[in,out] pddev The device structure
+ *
+ * @return ::MBG_SUCCESS if the port range could be claimed, else ::MBG_ERR_CLAIM_RSRC
+ */
int pcps_rsrc_claim( PCPS_DDEV *pddev )
{
ushort decode_width;
@@ -2585,14 +3002,14 @@ int pcps_rsrc_claim( PCPS_DDEV *pddev )
// If the resource manager was unable to alloc the resources
// then the selected range of ports is probably in use
// by another hardware device and/or driver
- if ( rc )
+ if ( mbg_rc_is_error( rc ) )
{
_pcps_ddev_set_err_flags( pddev, PCPS_EF_IO_RSRC );
return MBG_ERR_CLAIM_RSRC;
}
}
- return 0;
+ return MBG_SUCCESS;
} // pcps_rsrc_claim
@@ -2725,7 +3142,7 @@ uchar pcps_pos_from_port( ushort port )
static /*HDR*/
-void pcps_detect_mca_clocks( PCPS_DDEV_ALLOC_FNC alloc_fnc, void *alloc_arg )
+void pcps_detect_mca_clocks( PCPS_DDEV_ALLOC_FNC *alloc_fnc, void *alloc_arg )
{
short rc;
ushort type_idx;
@@ -2815,7 +3232,7 @@ PCPS_DDEV *pcps_alloc_ddev( void )
#if !_PCPS_STATIC_DEV_LIST
pddev = _pcps_kmalloc( sizeof( *pddev ) );
#else
- if ( n_ddevs >= PCPS_MAX_DDEVS )
+ if ( n_ddevs >= N_SUPP_DEV_BUS )
{
_mbgddmsg_0( MBG_DBG_INIT_DEV,
"Unable to add new device: max count reached" );
@@ -2929,7 +3346,7 @@ int pcps_add_rsrc_mem( PCPS_DDEV *pddev, MBG_MEM_ADDR start, ulong len )
p->len = len;
prsrci->num_rsrc_mem++;
- #if defined( MBG_TGT_UNIX )
+ #if defined( MBG_TGT_POSIX )
_mbgddmsg_3( MBG_DBG_INIT_DEV, "Adding mem rsrc #%i: %08llX(%lu)",
prsrci->num_rsrc_mem, (unsigned long long) start, len );
#else
@@ -2999,14 +3416,13 @@ int pcps_init_ddev( PCPS_DDEV *pddev, int bus_flags, ushort dev_id )
#if defined( DEBUG )
+
static /*HDR*/
const char *get_feature_name( PCPS_FEATURES flag )
{
- static const char *pcps_feature_names[N_PCPS_FEATURE] = PCPS_FEATURE_NAMES;
-
int i;
- for ( i = 0; i < N_PCPS_FEATURE; i++ )
+ for ( i = 0; i < N_PCPS_FEATURE_BITS; i++ )
if ( ( 1UL << i ) == flag )
return pcps_feature_names[i];
@@ -3040,23 +3456,57 @@ void check_feature( PCPS_DDEV *pddev, ushort req_rev_num,
static /*HDR*/
-void check_ri_feature( PCPS_DDEV *pddev, const RECEIVER_INFO *p_ri,
- RI_FEATURES ri_flag, PCPS_FEATURES flag )
+void check_ri_features( PCPS_DDEV *pddev, const RECEIVER_INFO *p_ri )
{
- int supported = ( p_ri->features & ri_flag ) != 0;
+ int gps_feat_bit;
- if ( supported )
- pddev->dev.cfg.features |= flag;
+ for ( gps_feat_bit = 0; gps_feat_bit < N_GPS_FEATURE; gps_feat_bit++ )
+ {
+ int supported = ( p_ri->features & ( 1UL << gps_feat_bit ) ) != 0;
+ PCPS_FEATURES pcps_flags = ri_feat_tbl[gps_feat_bit];
- #if defined( DEBUG )
- _mbgddmsg_5( MBG_DBG_INIT_DEV, "%s v%03X: feature 0x%08lX (%s) %ssupported according to RECEIVER_INFO",
- _pcps_ddev_type_name( pddev ),
- _pcps_ddev_fw_rev_num( pddev ),
- (ulong) flag, get_feature_name( flag ),
- supported ? "" : "not " );
- #endif
+ if ( supported )
+ {
+ if ( pcps_flags )
+ {
+ pddev->dev.cfg.features |= pcps_flags;
+
+ #if defined( DEBUG )
+ {
+ int i;
+
+ for ( i = 0; i < 8 * sizeof( pcps_flags ); i++ )
+ if ( pcps_flags & ( 1UL << i ) )
+ _mbgddmsg_4( MBG_DBG_INIT_DEV, "%s v%03X: Supported RI feature \"%s\" maps to PCPS feature %s",
+ _pcps_ddev_type_name( pddev ),
+ _pcps_ddev_fw_rev_num( pddev ),
+ gps_ri_feature_names[gps_feat_bit],
+ pcps_feature_names[i] );
+ }
+ #endif
+ }
+ else
+ {
+ #if defined( DEBUG )
+ _mbgddmsg_3( MBG_DBG_INIT_DEV, "%s v%03X: RI feature \"%s\" supported, but no corresponding PCPS feature",
+ _pcps_ddev_type_name( pddev ),
+ _pcps_ddev_fw_rev_num( pddev ),
+ gps_ri_feature_names[gps_feat_bit] );
+ #endif
+ }
+ }
+ else
+ {
+ #if defined( DEBUG )
+ _mbgddmsg_3( MBG_DBG_INIT_DEV, "%s v%03X: RI feature \"%s\" not supported by device",
+ _pcps_ddev_type_name( pddev ),
+ _pcps_ddev_fw_rev_num( pddev ),
+ gps_ri_feature_names[gps_feat_bit] );
+ #endif
+ }
+ }
-} // check_ri_feature
+} // check_ri_features
@@ -3065,6 +3515,7 @@ int pcps_start_device( PCPS_DDEV *pddev,
PCPS_BUS_NUM bus_num,
PCPS_SLOT_NUM dev_fnc_num )
{
+ RECEIVER_INFO *p_ri = _ri_addr( pddev );
ushort port_rsrc_len[N_PCPS_PORT_RSRC] = { 0 };
int port_ranges_required = 0;
ushort status_port_offs = 0;
@@ -3107,6 +3558,9 @@ int pcps_start_device( PCPS_DDEV *pddev,
#endif
+ // Next we do some setup depending on the interface type
+ // and chip.
+
switch ( _pcps_ddev_bus_flags( pddev ) )
{
#if _PCPS_USE_USB
@@ -3155,9 +3609,9 @@ int pcps_start_device( PCPS_DDEV *pddev,
#elif defined( MBG_TGT_WIN32_PNP )
swprintf( pddev->wcs_msg, L"device supports only %d endpoints while %d are required",
pddev->n_usb_ep, MBGUSB_MIN_ENDPOINTS_REQUIRED );
- _evt_msg( GlbDriverObject, pddev->wcs_msg );
+ _evt_msg_w( GlbDriverObject, pddev->wcs_msg );
#else
- //##++
+ //##++
#endif
rc = MBG_ERR_GENERIC;
@@ -3242,17 +3696,17 @@ int pcps_start_device( PCPS_DDEV *pddev,
#elif defined( MBG_TGT_WIN32 )
swprintf( pddev->wcs_msg, L"unhandled bus flags %04X for device %S",
_pcps_ddev_bus_flags( pddev ), _pcps_ddev_type_name( pddev ) );
- _evt_msg( GlbDriverObject, pddev->wcs_msg );
+ _evt_msg_w( GlbDriverObject, pddev->wcs_msg );
#endif
goto fail;
} // switch ( _pcps_ddev_bus_flags( pddev ) )
#if _PCPS_USE_MM_IO
- if ( !_pcps_ddev_is_pci_mbgpex( pddev ) )
+ if ( !_pcps_ddev_is_pci_mbgpex( pddev ) || force_io_access )
#endif
{
- // check if all required resources have been assigned
+ // check if all required I/O resources have been assigned
if ( pddev->rsrc_info.num_rsrc_io < port_ranges_required )
{
_mbgddmsg_3( MBG_DBG_INIT_DEV, "PCPS start device %X fails: port ranges (%u) less than required (%u)",
@@ -3262,6 +3716,10 @@ int pcps_start_device( PCPS_DDEV *pddev,
}
}
+ #if _PCPS_USE_MM_IO
+ pddev->use_mm_io = 0; // default, eventually changed later
+ #endif
+
if ( _pcps_ddev_is_pci_mbgpex( pddev ) )
{
pddev->irq_enb_disb_port = _pcps_ddev_io_base_mapped( pddev, 0 )
@@ -3272,34 +3730,47 @@ int pcps_start_device( PCPS_DDEV *pddev,
pddev->irq_ack_port = pddev->irq_enb_disb_port;
pddev->irq_ack_mask = PCI_ASIC_PCI_IRQF;
- #if _PCPS_USE_MM_IO
- _mbgddmsg_1( MBG_DBG_INIT_DEV, "%s: pcps_start_device: interface is MBGPEX",
- pcps_driver_name );
- if ( map_sys_virtual_address( pddev ) < 0 )
- goto fail_with_cleanup;
+ _mbgddmsg_1( MBG_DBG_INIT_DEV, "%s: pcps_start_device: interface is MBGPEX",
+ pcps_driver_name );
- #if DEBUG_IO && defined( MBG_TGT_LINUX )
- printk( KERN_ERR "io_addr: 0x%llX, cmd: 0x%llX\n",
- (unsigned long long) _pcps_ddev_io_base_mapped( pddev, 0 ),
- (unsigned long long) _pcps_ddev_io_base_mapped( pddev, 0 ) + offsetof( PCI_ASIC, pci_data )
- );
-
- printk( KERN_ERR "mm_addr: %p, cmd: %p, tstamp: %p\n",
- pddev->mm_addr,
- &pddev->mm_addr->mbgpex.asic.pci_data.ul,
- pddev->mm_tstamp_addr
- );
- #endif
+ #if _PCPS_USE_MM_IO
+ if ( force_io_access )
+ {
+ #if defined( MBG_TGT_LINUX ) //##+++++++++++++++++++++++
+ printk( KERN_INFO "%s: Forced I/O access for %s\n",
+ pcps_driver_name, _pcps_ddev_type_name( pddev ) );
+ #endif
+ }
+ else
+ {
+ if ( map_sys_virtual_address( pddev ) < 0 )
+ goto fail_with_cleanup;
+
+ #if DEBUG_IO && defined( MBG_TGT_LINUX )
+ printk( KERN_ERR "io_addr: 0x%llX, cmd: 0x%llX\n",
+ (unsigned long long) _pcps_ddev_io_base_mapped( pddev, 0 ),
+ (unsigned long long) _pcps_ddev_io_base_mapped( pddev, 0 ) + offsetof( PCI_ASIC, pci_data )
+ );
+
+ printk( KERN_ERR "mm_addr: %p, cmd: %p, tstamp: %p\n",
+ pddev->mm_addr,
+ &pddev->mm_addr->mbgpex.asic.pci_data.ul,
+ pddev->mm_tstamp_addr
+ );
+ #endif
- pddev->read = pcps_read_asic_mm;
+ pddev->read = pcps_read_asic_mm;
+ pddev->use_mm_io = 1;
+ }
#endif // _PCPS_USE_MM_IO
goto chip_setup_done;
}
- // setup additional properties depending on the
- // type of bus interface chip
+ // Setup additional properties depending on the
+ // type of bus interface chip.
+
if ( _pcps_ddev_is_pci_pex8311( pddev ) )
{
// I/O and memory ranges must be swapped for the
@@ -3374,6 +3845,8 @@ int pcps_start_device( PCPS_DDEV *pddev,
chip_setup_done:
+ // Chip-specific setup done. Continue with common device setup.
+
pddev->status_port = _pcps_ddev_io_base_mapped( pddev, 0 ) + status_port_offs;
// Set up the resource list in pddev->dev.cfg which
@@ -3388,8 +3861,8 @@ chip_setup_done:
prsrc = &pddev->rsrc_info.port[i];
- // if the resource len has not yet been set
- // then use the default resource len
+ // If the resource len has not yet been set
+ // then use the default resource len.
if ( prsrc->num == 0 )
prsrc->num = port_rsrc_len[i];
@@ -3422,7 +3895,7 @@ chip_setup_done:
#if _PCPS_USE_RSRCMGR
rc = pcps_rsrc_claim( pddev );
- if ( rc < 0 )
+ if ( mbg_rc_is_error( rc ) )
{
_mbgddmsg_1( MBG_DBG_INIT_DEV, "PCPS start device %X: failed to alloc resources",
_pcps_ddev_dev_id( pddev ) );
@@ -3433,7 +3906,7 @@ chip_setup_done:
// There are some BIOSs out there which don't configure some PEX cards
// properly, and thus the cards can not be accessed properly.
- // See note near the definition of _pcps_pci_cfg_err() for details.
+ // See note near the definition of ::_pcps_pci_cfg_err for details.
if ( _pcps_ddev_pci_cfg_err( pddev ) )
{
#if defined( MBG_TGT_LINUX )
@@ -3445,7 +3918,7 @@ chip_setup_done:
#elif defined( MBG_TGT_WIN32 )
swprintf( pddev->wcs_msg, L"duplicate base address 0x%04lX, device %s will not work properly (BIOS faulty)",
(ulong) _pcps_ddev_port_base( pddev, 0 ), _pcps_ddev_type_name( pddev ) );
- _evt_msg( GlbDriverObject, pddev->wcs_msg );
+ _evt_msg_w( GlbDriverObject, pddev->wcs_msg );
#endif
}
@@ -3467,7 +3940,7 @@ chip_setup_done:
// try to read firmware ID
rc = pcps_get_fw_id( pddev, pddev->dev.cfg.fw_id );
- if ( rc < 0 )
+ if ( mbg_rc_is_error( rc ) )
{
if ( _pcps_ddev_is_isa( pddev ) )
{
@@ -3475,9 +3948,9 @@ chip_setup_done:
// a given port, so if the firmware ID could not be read then this
// just means there is no device using the given port address.
#if defined( MBG_TGT_WIN32 )
- swprintf( pddev->wcs_msg, L"No ISA card found at port %03lXh.",
+ swprintf( pddev->wcs_msg, L"No ISA card found at port %03lXh.",
(ulong) _pcps_ddev_port_base( pddev, 0 ) );
- _evt_msg( GlbDriverObject, pddev->wcs_msg );
+ _evt_msg_w( GlbDriverObject, pddev->wcs_msg );
#else
_mbgddmsg_1( MBG_DBG_INIT_DEV, "No ISA card found at port %03lXh.",
(ulong) _pcps_ddev_port_base( pddev, 0 ) );
@@ -3488,7 +3961,7 @@ chip_setup_done:
// Non-ISA devices are detected by some other means, so if the firmware
// ID could not be read this is a serious error.
#if defined( MBG_TGT_WIN32 ) //##+++ debug or not debug ... ;-)
- _evt_msg( GlbDriverObject, L"StartDevice: failed to read firmware ID" );
+ _evt_msg_w( GlbDriverObject, L"StartDevice: failed to read firmware ID" );
#else
_mbgddmsg_1( MBG_DBG_INIT_DEV, "PCPS start device %X: failed to read firmware ID",
_pcps_ddev_dev_id( pddev ) );
@@ -3509,7 +3982,7 @@ chip_setup_done:
dev_type = PCPS_TYPE_GPS167PC;
else
{
- if ( pcps_check_id( pddev, fw_id_ref_pcps ) == MBG_SUCCESS )
+ if ( mbg_rc_is_success( pcps_check_id( pddev, fw_id_ref_pcps ) ) )
{
// Device is a PC31, or a PC32 if it has signature code.
// If no support for MCA has been compiled in, it may even
@@ -3521,7 +3994,7 @@ chip_setup_done:
}
else
{
- _pcps_ddev_set_err_flags( pddev, PCPS_EF_INV_EPROM_ID );
+ _pcps_ddev_set_err_flags( pddev, PCPS_EF_INV_FW_ID );
goto fail_with_cleanup;
}
}
@@ -3539,26 +4012,30 @@ chip_setup_done:
// If the device has an ASIC or EPLD read the ASIC version number
if ( _pcps_ddev_has_asic_version( pddev ) )
{
- #if _PCPS_USE_MM_IO
- if ( _pcps_ddev_bus_flags( pddev ) == PCPS_BUS_PCI_MBGPEX )
- {
- _mbgddmsg_1( MBG_DBG_INIT_DEV, "%s: pcps_start_device: MM reading ASIC version",
- pcps_driver_name );
- pddev->raw_asic_version = pddev->mm_addr->mbgpex.asic.raw_version;
- }
- else
- #endif // _PCPS_USE_MM_IO
- pddev->raw_asic_version = _mbg_inp32_to_cpu( pddev, 0, _pcps_ddev_io_base_mapped( pddev, 0 )
- + offsetof( PCI_ASIC, raw_version ) );
-
- _mbg_swab_asic_version( &pddev->raw_asic_version );
+ #if _PCPS_USE_MM_IO
+ if ( pddev->use_mm_io )
+ {
+ pddev->raw_asic_version = pddev->mm_addr->mbgpex.asic.raw_version;
+ _mbg_swab_asic_version( &pddev->raw_asic_version );
+ _mbgddmsg_2( MBG_DBG_INIT_DEV, "%s: pcps_start_device: raw ASIC version %04X read via MM",
+ pcps_driver_name, pddev->raw_asic_version );
+ }
+ else
+ #endif // _PCPS_USE_MM_IO
+ {
+ pddev->raw_asic_version = _mbg_inp32_to_cpu( pddev, 0, _pcps_ddev_io_base_mapped( pddev, 0 )
+ + offsetof( PCI_ASIC, raw_version ) );
+ _mbg_swab_asic_version( &pddev->raw_asic_version );
+ _mbgddmsg_2( MBG_DBG_INIT_DEV, "%s: pcps_start_device: raw ASIC version %04X read via I/O",
+ pcps_driver_name, pddev->raw_asic_version );
+ }
pddev->asic_version = _convert_asic_version_number( pddev->raw_asic_version );
}
- // Setup some feature flags which depend on the device type
+ // Setup some feature flags which depend on the device type
// and firmware version.
- switch( _pcps_ddev_type_num( pddev ) )
+ switch ( _pcps_ddev_type_num( pddev ) )
{
case PCPS_TYPE_PC31:
case PCPS_TYPE_PS31_OLD:
@@ -3637,7 +4114,7 @@ chip_setup_done:
case PCPS_TYPE_PEX511:
pddev->dev.cfg.features = PCPS_FEAT_PEX511;
- // HR time support for the PEX511 requires both a certain ASIC
+ // HR time support for the PEX511 requires both a certain ASIC
// version plus a certain firmware version.
if ( _pcps_asic_version_greater_equal( _pcps_ddev_asic_version( pddev ),
PCI_ASIC_MAJOR_PEX511, PCI_ASIC_HR_TIME_MINOR_PEX511 ) )
@@ -3725,6 +4202,14 @@ chip_setup_done:
pddev->dev.cfg.features = PCPS_FEAT_GLN180PEX;
break;
+ case PCPS_TYPE_GPS180AMC:
+ pddev->dev.cfg.features = PCPS_FEAT_GPS180AMC;
+ break;
+
+ case PCPS_TYPE_GNS181PEX:
+ pddev->dev.cfg.features = PCPS_FEAT_GNS181PEX;
+ break;
+
default:
#if defined( MBG_TGT_LINUX )
printk( KERN_WARNING "%s: no feature detection for device %s\n",
@@ -3735,7 +4220,7 @@ chip_setup_done:
#elif defined( MBG_TGT_WIN32 )
swprintf( pddev->wcs_msg, L"no feature detection for device %S",
_pcps_ddev_type_name( pddev ) );
- _evt_msg( GlbDriverObject, pddev->wcs_msg );
+ _evt_msg_w( GlbDriverObject, pddev->wcs_msg );
#endif
goto fail_with_cleanup;
@@ -3744,15 +4229,15 @@ chip_setup_done:
if ( _pcps_ddev_has_receiver_info( pddev ) )
{
- rc = _pcps_read_gps_var( pddev, PC_GPS_RECEIVER_INFO, pddev->ri );
+ rc = _pcps_read_gps_var( pddev, PC_GPS_RECEIVER_INFO, *p_ri );
- if ( rc == MBG_SUCCESS )
+ if ( mbg_rc_is_success( rc ) )
{
- _mbg_swab_receiver_info( &pddev->ri );
+ _mbg_swab_receiver_info( p_ri );
_mbgddmsg_1( MBG_DBG_INIT_DEV, "Successfully read receiver info from dev %X",
_pcps_ddev_dev_id( pddev ) );
- goto check;
+ goto receiver_info_done;
}
_mbgddmsg_1( MBG_DBG_INIT_DEV, "Failed to read receiver info from dev %X",
@@ -3764,19 +4249,68 @@ chip_setup_done:
_pcps_ddev_dev_id( pddev ) );
if ( _pcps_ddev_is_gps( pddev ) )
- _setup_default_receiver_info_gps( &pddev->ri );
+ _setup_default_receiver_info_gps( p_ri );
else
- _setup_default_receiver_info_dcf( &pddev->ri, &pddev->dev );
+ _setup_default_receiver_info_dcf( p_ri, &pddev->dev );
+receiver_info_done:
-check:
- #if DEBUG_IO
- _mbgddmsg_1( MBG_DBG_DETAIL, "ri.sw_rev.code: %04X", pddev->ri.sw_rev.code );
- _mbgddmsg_1( MBG_DBG_DETAIL, "ri.model_code: %04X", pddev->ri.model_code );
- _mbgddmsg_3( MBG_DBG_DETAIL, "ri.model_name: %-*.*s", (int) sizeof( pddev->ri.model_name ),
- (int) sizeof( pddev->ri.model_name ), pddev->ri.model_name );
- #endif
+ #if defined( DEBUG )
+ _mbgddmsg_1( MBG_DBG_DETAIL, "ri.model_code: 0x%04X",
+ p_ri->model_code );
+
+ _mbgddmsg_3( MBG_DBG_DETAIL, "ri.model_name: \"%-*.*s\"",
+ (int) sizeof( p_ri->model_name ),
+ (int) sizeof( p_ri->model_name ),
+ p_ri->model_name );
+
+ _mbgddmsg_4( MBG_DBG_DETAIL, "ri.sw_rev: code 0x%04X, name \"%-*.*s\"",
+ p_ri->sw_rev.code,
+ (int) sizeof( p_ri->sw_rev.name ),
+ (int) sizeof( p_ri->sw_rev.name ),
+ p_ri->sw_rev.name );
+
+ _mbgddmsg_3( MBG_DBG_DETAIL, "ri.sernum: \"%-*.*s\"",
+ (int) sizeof( p_ri->sernum ),
+ (int) sizeof( p_ri->sernum ),
+ p_ri->sernum );
+
+ _mbgddmsg_3( MBG_DBG_DETAIL, "ri.epld_name: \"%-*.*s\"",
+ (int) sizeof( p_ri->epld_name ),
+ (int) sizeof( p_ri->epld_name ),
+ p_ri->epld_name );
+
+ _mbgddmsg_1( MBG_DBG_DETAIL, "ri.n_channels: %u",
+ p_ri->n_channels );
+
+ _mbgddmsg_1( MBG_DBG_DETAIL, "ri.ticks_per_sec: %lu",
+ (ulong) p_ri->ticks_per_sec );
+
+ _mbgddmsg_1( MBG_DBG_DETAIL, "ri.features: 0x%08lX",
+ (ulong) p_ri->features );
+
+ _mbgddmsg_2( MBG_DBG_DETAIL, "ri.fixed_freq: khz_val %u, range %i",
+ p_ri->fixed_freq.khz_val,
+ p_ri->fixed_freq.range );
+
+ _mbgddmsg_2( MBG_DBG_DETAIL, "ri.osc type: %u, flags: 0x%02X",
+ p_ri->osc_type, p_ri->osc_flags );
+
+ _mbgddmsg_1( MBG_DBG_DETAIL, "ri.n_ucaps: %u",
+ p_ri->n_ucaps );
+ _mbgddmsg_1( MBG_DBG_DETAIL, "ri.n_com_ports: %u",
+ p_ri->n_com_ports );
+
+ _mbgddmsg_1( MBG_DBG_DETAIL, "ri.n_str_type: %u",
+ p_ri->n_str_type );
+
+ _mbgddmsg_1( MBG_DBG_DETAIL, "ri.n_prg_out: %u",
+ p_ri->n_prg_out );
+
+ _mbgddmsg_1( MBG_DBG_DETAIL, "ri.flags: 0x%04X",
+ p_ri->flags );
+#endif
#if 0 //##+++++++++ check if this is reasonnable
@@ -3799,36 +4333,16 @@ check:
}
#endif
-
// detect the presence of some optional features at run time
_mbgddmsg_3( MBG_DBG_INIT_DEV, "%s v%03X RECEIVER_INFO features: 0x%08lX",
_pcps_ddev_type_name( pddev ), _pcps_ddev_fw_rev_num( pddev ),
- (ulong) pddev->ri.features );
-
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_IRIG_TX, PCPS_HAS_IRIG_TX );
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_IRIG_CTRL_BITS, PCPS_HAS_IRIG_CTRL_BITS );
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_SYNTH, PCPS_HAS_SYNTH );
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_TIME_SCALE, PCPS_HAS_TIME_SCALE );
-
- // Devices which support a configurable time scale do also
- // support reading/writing the GPS UTC parameters via the PC bus.
- // This is not explicitely coded in the rcvr_info structure
- // since the the rcvr_info structure can also be read via
- // the serial port, and reading/writing the GPS UTC parameters
- // via the serial port is supported by all GPS devices anyway.
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_TIME_SCALE, PCPS_HAS_UTC_PARM );
-
- // Devices which support reading raw IRIG data via the PC interface also support
- // reading the raw IRIG time. However, there is no receiver info feature flag
- // since this call is not supported via the serial interface, so we use the
- // GPS_HAS_RAW_IRIG_DATA flag to check both features.
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_RAW_IRIG_DATA, PCPS_HAS_IRIG_TIME );
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_RAW_IRIG_DATA, PCPS_HAS_RAW_IRIG_DATA );
-
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_LAN_IP4, PCPS_HAS_LAN_INTF );
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_PTP, PCPS_HAS_PTP );
- // check_ri_feature( pddev, &pddev->ri, GPS_HAS_PTP_UNICAST, 0 ); // no equivalent in PCPS_DDEV features
- check_ri_feature( pddev, &pddev->ri, GPS_HAS_EVT_LOG, PCPS_HAS_EVT_LOG );
+ (ulong) *_ri_addr( pddev ).features );
+
+ check_ri_features( pddev, _ri_addr( pddev ) );
+
+ _mbgddmsg_3( MBG_DBG_INIT_DEV, "%s v%03X actual features 1: 0x%08lX",
+ _pcps_ddev_type_name( pddev ), _pcps_ddev_fw_rev_num( pddev ),
+ (ulong) _pcps_ddev_features( pddev ) );
#if !defined( MBG_TGT_OS2 ) && !defined( MBG_TGT_BSD )
// Function strstr may not be supported at kernel level,
@@ -3927,8 +4441,7 @@ void pcps_cleanup_device( PCPS_DDEV *pddev )
static /*HDR*/
PCPS_ERR_FLAGS pcps_read_pci_rsrc( PCPS_BUS_NUM bus_num,
PCPS_SLOT_NUM dev_fnc_num,
- PCPS_DDEV *pddev,
- PCPS_BUS_FLAGS bus_flags )
+ PCPS_DDEV *pddev )
{
PCPS_ERR_FLAGS err_flags = 0;
uchar irq;
@@ -4030,8 +4543,7 @@ void pcps_setup_and_start_pci_dev( PCPS_DDEV *pddev,
{
PCPS_ERR_FLAGS err_flags;
- err_flags = pcps_read_pci_rsrc( bus_num, dev_fnc_num,
- pddev, _pcps_ddev_bus_flags( pddev ) );
+ err_flags = pcps_read_pci_rsrc( bus_num, dev_fnc_num, pddev );
_pcps_ddev_set_err_flags( pddev, err_flags );
if ( !( err_flags & PCPS_EF_IO_INIT ) )
@@ -4048,9 +4560,9 @@ void pcps_setup_and_start_pci_dev( PCPS_DDEV *pddev,
/*HDR*/
-void pcps_detect_pci_clocks( PCPS_DDEV_ALLOC_FNC alloc_fnc, void *alloc_arg,
- PCPS_DDEV_CLEANUP_FNC cleanup_fnc,
- ushort vendor_id, PCPS_DEV_TYPE dev_type[],
+void pcps_detect_pci_clocks( PCPS_DDEV_ALLOC_FNC *alloc_fnc, void *alloc_arg,
+ PCPS_DDEV_CLEANUP_FNC *cleanup_fnc,
+ ushort vendor_id, PCPS_DEV_TYPE dev_type[],
int n_dev_types )
{
#if defined( MBG_TGT_QNX )
@@ -4144,6 +4656,8 @@ void pcps_detect_pci_clocks( PCPS_DDEV_ALLOC_FNC alloc_fnc, void *alloc_arg,
if ( cleanup_fnc )
cleanup_fnc( pddev );
}
+ #else
+ (void) cleanup_fnc; // avoid compiler warning
#endif
}
}
@@ -4154,6 +4668,8 @@ void pcps_detect_pci_clocks( PCPS_DDEV_ALLOC_FNC alloc_fnc, void *alloc_arg,
_mbg_pci_fnc_deinit();
#endif
+ (void) alloc_arg; // avoid compiler warning
+
} // pcps_detect_pci_clocks
#endif // _PCPS_USE_PCI_BIOS
@@ -4167,9 +4683,9 @@ void pcps_detect_pci_clocks( PCPS_DDEV_ALLOC_FNC alloc_fnc, void *alloc_arg,
#if !_PCPS_USE_ISA_PNP
/*HDR*/
-void pcps_detect_isa_clocks( PCPS_DDEV_ALLOC_FNC alloc_fnc,
- PCPS_DDEV_CLEANUP_FNC cleanup_fnc,
- PCPS_DDEV_REGISTER_FNC register_fnc,
+void pcps_detect_isa_clocks( PCPS_DDEV_ALLOC_FNC *alloc_fnc,
+ PCPS_DDEV_CLEANUP_FNC *cleanup_fnc,
+ PCPS_DDEV_REGISTER_FNC *register_fnc,
int isa_ports[PCPS_MAX_ISA_CARDS],
int isa_irqs[PCPS_MAX_ISA_CARDS] )
{
@@ -4249,9 +4765,9 @@ void pcps_detect_isa_clocks( PCPS_DDEV_ALLOC_FNC alloc_fnc,
*-------------------------------------------------------------*/
/*HDR*/
-void _MBG_INIT_CODE_ATTR pcps_detect_clocks_alloc( PCPS_DDEV_ALLOC_FNC alloc_fnc,
+void _MBG_INIT_CODE_ATTR pcps_detect_clocks_alloc( PCPS_DDEV_ALLOC_FNC *alloc_fnc,
void *alloc_arg,
- PCPS_DDEV_CLEANUP_FNC cleanup_fnc,
+ PCPS_DDEV_CLEANUP_FNC *cleanup_fnc,
int isa_ports[PCPS_MAX_ISA_CARDS],
int isa_irqs[PCPS_MAX_ISA_CARDS] )
{
@@ -4260,7 +4776,7 @@ void _MBG_INIT_CODE_ATTR pcps_detect_clocks_alloc( PCPS_DDEV_ALLOC_FNC alloc_fnc
#endif
#if _PCPS_USE_PCI_BIOS
- pcps_detect_pci_clocks( alloc_fnc, alloc_arg, cleanup_fnc,
+ pcps_detect_pci_clocks( alloc_fnc, alloc_arg, cleanup_fnc,
PCI_VENDOR_MEINBERG, pcps_dev_type, N_PCPS_DEV_TYPE );
#endif
diff --git a/mbglib/common/pcpsdrvr.h b/mbglib/common/pcpsdrvr.h
index 90a5ee7..82b1342 100755
--- a/mbglib/common/pcpsdrvr.h
+++ b/mbglib/common/pcpsdrvr.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcpsdrvr.h 1.44.1.1 2013/06/25 09:53:16 martin TRASH $
+ * $Id: pcpsdrvr.h 1.45.1.17 2017/04/25 11:36:51 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,7 +10,42 @@
*
* -----------------------------------------------------------------------
* $Log: pcpsdrvr.h $
- * Revision 1.44.1.1 2013/06/25 09:53:16 martin
+ * Revision 1.45.1.17 2017/04/25 11:36:51 martin
+ * Renamed GRC181PEX to GNS181PEX.
+ * Revision 1.45.1.16 2017/02/22 15:23:46 martin
+ * Fixed macro definition syntax to avoid clang compiler warnings.
+ * Revision 1.45.1.15 2016/09/26 16:24:27 martin
+ * Revision 1.45.1.14 2016/09/19 14:29:22Z martin
+ * *** empty log message ***
+ * Revision 1.45.1.13 2016/09/16 09:57:43 martin
+ * Use macro _ri_addr().
+ * Revision 1.45.1.12 2016/09/15 14:56:18 martin
+ * Support GRC181PEX.
+ * Revision 1.45.1.11 2016/09/14 16:20:54 martin
+ * Use more versatile types for function pointers.
+ * Prepare to use MBG_XDEV_FEATURES in PCPS_DDEV.
+ * Updated function prototypes.
+ * Revision 1.45.1.10 2016/08/09 07:13:04 martin
+ * *** empty log message ***
+ * Revision 1.45.1.9 2016/05/30 15:03:47 martin
+ * Conditional USB debug code.
+ * Revision 1.45.1.8 2016/01/04 11:24:20 martin
+ * Revision 1.45.1.7 2015/10/27 16:22:27Z martin
+ * Older defines N_SUPP_DEV, PCPS_MAX_DDEVS, and MBG_MAX_DEVICES
+ * have been obsoleted by new defines N_SUPP_DEV_BUS, N_SUPP_DEV_EXT,
+ * and N_SUPP_DEV_TOTAL.
+ * Revision 1.45.1.6 2014/05/22 14:54:35 martin
+ * Added _pcps_ddev_has_xmr() macro.
+ * Revision 1.45.1.5 2014/04/15 15:35:24 martin
+ * Support GPIO ports.
+ * Revision 1.45.1.4 2014/04/07 08:38:52 martin
+ * Revision 1.45.1.3 2014/03/20 16:40:39 martin
+ * Support new module parameter force_io_access.
+ * Revision 1.45.1.2 2014/01/23 15:35:49 martin
+ * Support GPS180AMC.
+ * Revision 1.45.1.1 2013/12/18 14:46:29 martin
+ * Revision 1.45 2013/09/26 09:08:09 martin
+ * Support GLN180PEX and GNSS API.
* Revision 1.44 2013/03/15 10:01:09 martin
* Optionally override setting to support memory mapped I/O.
* Revision 1.43 2012/11/02 09:48:04 martin
@@ -33,14 +68,14 @@
* Revision 1.41 2010/06/30 13:44:49 martin
* Use new preprocessor symbol MBG_ARCH_X86.
* Revision 1.40 2010/01/12 14:05:05 daniel
- * Added macro to check if reading the
+ * Added macro to check if reading the
* raw IRIG data bits is supported.
* Revision 1.39 2009/09/29 07:24:51Z martin
* Use standard feature flag to check if fast HR time is supported.
* Revision 1.38 2009/06/19 12:13:05 martin
* Added _pcps_ddev_has_irig_time() macro.
* Revision 1.37 2009/06/09 10:13:59 daniel
- * Added macros _pcps_ddev_has_lan_intf( _p ) and
+ * Added macros _pcps_ddev_has_lan_intf( _p ) and
* _pcps_ddev_has_ptp_cfg( _p ).
* Cleaned up the low level interface and provided a
* possibility to override the macros for special purposes.
@@ -53,13 +88,13 @@
* and replaced/merged them with mbg_get_pc_cycles...() functions.
* Under Linux use own inline function to read TSC on x86 architectures.
* Normally USB timeouts are short with retries in order to increase
- * responsiveness. On some systems this may lead to problems, so
+ * responsiveness. On some systems this may lead to problems, so
* optionally one long timeout can be used now by define.
* Revision 1.34 2008/12/16 14:40:47 martin
* Account for new devices PTP270PEX, FRC270PEX, TCR170PEX, and WWVB51USB.
- * Added macros _pcps_ddev_is_ptp(), _pcps_ddev_is_frc(),
+ * Added macros _pcps_ddev_is_ptp(), _pcps_ddev_is_frc(),
* and _pcps_ddev_is_wwvb().
- * Don't use pragma pack( 1 ) but use native alignment since structures
+ * Don't use pragma pack( 1 ) but use native alignment since structures
* defined here are not used across system boundaries.
* Added fields to PCPS_DDEV to store the ASIC version, and macros
* _pcps_ddev_raw_asic_version() and _pcps_ddev_asic_version().
@@ -109,11 +144,11 @@
* Added macro _pcps_ddev_status_busy().
* Added kernel malloc/free macros and USB I/O macros.
* Use PCPS_DDEV as private device data.
- * Use ms values for USB timeouts also under Linux. This may not be
+ * Use ms values for USB timeouts also under Linux. This may not be
* appropriate for older kernels.
* Limited length of some older RCS log messages.
* Revision 1.30 2007/07/25 14:22:23Z martin
- * Under Linux include param.h for definition of HZ under
+ * Under Linux include param.h for definition of HZ under
* kernels 2.6.21 and newer.
* Revision 1.29 2007/07/17 08:22:48 martin
* Added support for TCR511PEX and GPS170PEX.
@@ -129,7 +164,7 @@
* Preliminary support for *BSD.
* Preliminary support for USB.
* Revision 1.26 2006/07/07 09:44:23 martin
- * Fixed definition of control macros for the case where
+ * Fixed definition of control macros for the case where
* _PCPS_USE_PCI_PNP is overridden from the command line.
* Revision 1.25 2006/06/19 15:31:09 martin
* Added support for TCR511PCI.
@@ -151,8 +186,8 @@
* Revision 1.19 2004/10/14 15:01:24Z martin
* Added support for TCR167PCI.
* Revision 1.18 2004/09/06 15:11:04Z martin
- * Support a GPS_DATA interface where sizes are specified
- * by 16 instead of the original 8 bit quantities, thus allowing
+ * Support a GPS_DATA interface where sizes are specified
+ * by 16 instead of the original 8 bit quantities, thus allowing
* to transfer data blocks which exceed 255 bytes.
* Revision 1.17 2004/04/14 10:29:45Z martin
* Pack structures 1 byte aligned.
@@ -189,7 +224,7 @@
* New macro _pcps_ddev_has_mod().
* Revision 1.8 2002/02/26 09:34:03 MARTIN
* Removed macro _pcps_read_sernum() which was replaced
- * by a function pcps_read_sernum() which reads the S/N from
+ * by a function pcps_read_sernum() which reads the S/N from
* any clock that supports a S/N.
* Updated function prototypes.
* Revision 1.7 2002/02/19 09:28:01 MARTIN
@@ -200,12 +235,12 @@
* to follow naming conventions.
* Source code cleanup.
* Revision 1.5 2001/11/30 09:52:48 martin
- * Added support for event_time which, however, requires
+ * Added support for event_time which, however, requires
* a custom GPS firmware.
* Revision 1.4 2001/10/16 10:15:44 MARTIN
- * New Macro _pcps_ddev_has_serial_hs() which determines
+ * New Macro _pcps_ddev_has_serial_hs() which determines
* whether DCF77 clock supports baud rate higher than default.
- * Added some macros and comments corresponding to
+ * Added some macros and comments corresponding to
* pcpsdev.h.
* Revision 1.3 2001/09/18 06:53:57 MARTIN
* Two sets of preprocessor symbols for Win9x/ME and WinNT/2k.
@@ -232,6 +267,7 @@
#include <mbg_tgt.h>
+#include <xdevfeat.h>
#if defined( MBG_TGT_NETWARE )
#define _DEFAULT_PCPS_USE_CLOCK_TICK 1
@@ -357,10 +393,19 @@
#define _MBG_INIT_CODE_ATTR
#endif
+#if !defined( DEBUG_USB_IO )
+ #if ( 0 && defined( DEBUG ) && defined( MBG_TGT_LINUX ) )
+ #define DEBUG_USB_IO 1
+ #else
+ #define DEBUG_USB_IO 0
+ #endif
+#endif
+
/* Other headers to be included */
#include <pcpsdev.h>
+#include <cfg_hlp.h>
#include <mbgmutex.h>
#include <pci_asic.h>
#include <mbgerror.h>
@@ -390,6 +435,8 @@
#endif
#if defined( MBG_TGT_LINUX )
+ #include <linux/slab.h> // for kmalloc()/kfree()
+
#if _PCPS_USE_USB
#include <linux/usb.h>
#endif
@@ -444,14 +491,16 @@
extern "C" {
#endif
+#define _DEFAULT_PCPS_USE_MM_IO ( MBG_TGT_SUPP_MEM_ACC && !MBG_USE_MM_IO_FOR_PCI )
+
#if !defined( _PCPS_USE_MM_IO )
- #define _PCPS_USE_MM_IO ( MBG_TGT_SUPP_MEM_ACC && !MBG_USE_MM_IO_FOR_PCI )
+ #define _PCPS_USE_MM_IO _DEFAULT_PCPS_USE_MM_IO
#endif
#if _PCPS_USE_MM_IO
#define _mbg_inp32_ex( _d, _i, _p, _r ) \
- ( _pcps_ddev_is_pci_mbgpex( _d ) ? \
+ ( (_d)->use_mm_io ? \
(_d)->mm_addr->mbgpex.asic.control_status.ul : \
_mbg_inp32( (_d), (_i), (_p) ) \
)
@@ -459,7 +508,7 @@ extern "C" {
#define _mbg_outp32_ex( _d, _i, _p, _r, _v ) \
do \
{ \
- if ( _pcps_ddev_is_pci_mbgpex( _d ) ) \
+ if ( (_d)->use_mm_io ) \
(_d)->mm_addr->mbgpex.asic.control_status.ul = (_v); \
else \
_mbg_outp32( _d, _i, _p, _v ); \
@@ -627,12 +676,12 @@ extern "C" {
typedef struct
{
-#if defined ( MBG_TGT_FREEBSD )
+#if defined( MBG_TGT_FREEBSD )
int rid; /* resource ID */
struct resource *res;
bus_space_tag_t bst;
bus_space_handle_t bsh;
-#elif defined ( MBG_TGT_NETBSD )
+#elif defined( MBG_TGT_NETBSD )
int reg; /* BAR */
int type; /* type */
int valid; /* valid flag */
@@ -766,11 +815,11 @@ typedef union
struct PCPS_DDEV_s;
-typedef short (*PCPS_READ_FNC)( struct PCPS_DDEV_s *pddev, uint8_t cmd, void FAR *buffer, uint16_t count );
-typedef short (*PCPS_WRITE_FNC)( struct PCPS_DDEV_s *pddev, uint8_t cmd, const void FAR *buffer, uint16_t count );
-typedef struct PCPS_DDEV_s *(*PCPS_DDEV_ALLOC_FNC)( void );
-typedef void (*PCPS_DDEV_CLEANUP_FNC)( struct PCPS_DDEV_s * );
-typedef int (*PCPS_DDEV_REGISTER_FNC)( struct PCPS_DDEV_s * );
+typedef int PCPS_READ_FNC( struct PCPS_DDEV_s *pddev, uint8_t cmd, void FAR *buffer, uint16_t count );
+typedef int PCPS_WRITE_FNC( struct PCPS_DDEV_s *pddev, uint8_t cmd, const void FAR *buffer, uint16_t count );
+typedef struct PCPS_DDEV_s *PCPS_DDEV_ALLOC_FNC( void );
+typedef void PCPS_DDEV_CLEANUP_FNC( struct PCPS_DDEV_s * );
+typedef int PCPS_DDEV_REGISTER_FNC( struct PCPS_DDEV_s * );
typedef struct PCPS_DDEV_s
@@ -778,7 +827,7 @@ typedef struct PCPS_DDEV_s
// the device info data
PCPS_DEV dev;
- PCPS_READ_FNC read;
+ PCPS_READ_FNC *read;
PCPS_IO_ADDR_MAPPED status_port;
PCPS_IO_ADDR_MAPPED irq_enb_disb_port;
@@ -812,7 +861,11 @@ typedef struct PCPS_DDEV_s
// IRQ is possibly unsafe, and whether IRQ has been enabled on the device.
PCPS_IRQ_STAT_INFO irq_stat_info;
- RECEIVER_INFO ri;
+ MBG_XDEV_FEATURES xdev_features; ///< Receiver info plus extended device features
+
+ #if _PCPS_USE_MM_IO
+ int use_mm_io;
+ #endif
#if _PCPS_USE_USB
int n_usb_ep; // number of endpoints supp. by the device
@@ -969,28 +1022,27 @@ _ext PCPS_DEV_TYPE pcps_dev_type[N_PCPS_DEV_TYPE]
{ PCPS_TYPE_TCR600USB, "TCR600USB", USB_DEV_TCR600USB, PCPS_REF_IRIG, PCPS_BUS_USB_V2 },
{ PCPS_TYPE_MSF600USB, "MSF600USB", USB_DEV_MSF600USB, PCPS_REF_MSF, PCPS_BUS_USB_V2 },
{ PCPS_TYPE_WVB600USB, "WVB600USB", USB_DEV_WVB600USB, PCPS_REF_WWVB, PCPS_BUS_USB_V2 },
- { PCPS_TYPE_GLN180PEX, "GLN180PEX", PCI_DEV_GLN180PEX, PCPS_REF_GPS, PCPS_BUS_PCI_MBGPEX }
+ { PCPS_TYPE_GLN180PEX, "GLN180PEX", PCI_DEV_GLN180PEX, PCPS_REF_GPS, PCPS_BUS_PCI_MBGPEX },
+ { PCPS_TYPE_GPS180AMC, "GPS180AMC", PCI_DEV_GPS180AMC, PCPS_REF_GPS, PCPS_BUS_PCI_MBGPEX },
+ { PCPS_TYPE_GNS181PEX, "GNS181PEX", PCI_DEV_GNS181PEX, PCPS_REF_GPS, PCPS_BUS_PCI_MBGPEX }
// If a new device is added here, don't forget to add it also
- // to the Windows .inf file of supported PCI an USB devices,
- // and in case of USB to the Linux driver file mbgdrvr.c.
+ // to the Windows .inf file of supported PCI and USB devices,
+ // and in case of USB to the table mbgclock_usb_tbl of the Linux
+ // driver file mbgclock_main.c.
}
#endif
;
-#if !defined( PCPS_MAX_DDEVS )
- #define PCPS_MAX_DDEVS 16
-#endif
-
#if !defined( PCPS_MAX_ISA_CARDS )
- #define PCPS_MAX_ISA_CARDS PCPS_MAX_DDEVS // the number of ISA cards supported
+ #define PCPS_MAX_ISA_CARDS N_SUPP_DEV_BUS // the number of ISA cards supported
#endif
_ext int pcps_isa_ports[PCPS_MAX_ISA_CARDS + 1];
#if _PCPS_STATIC_DEV_LIST
- _ext PCPS_DDEV pcps_ddev[PCPS_MAX_DDEVS];
+ _ext PCPS_DDEV pcps_ddev[N_SUPP_DEV_BUS];
_ext int n_ddevs;
#endif
@@ -1010,7 +1062,7 @@ _ext const char *fw_id_ref[]
= {
"PC3", // PC31, PS31, PC32
"PCI", // PCI32, PCI509, PCI510, PCI511
- "GPS", // GPS167PC, GPS167PCI, GPS168PCI, GPS169PCI, GPS170PCI, GPS170PEX, GPS180PEX
+ "GPS", // GPS167PC, GPS167PCI, GPS168PCI, GPS169PCI, GPS170PCI, GPS170PEX, GPS180PEX, GPS180AMC
"TCR", // TCR510PCI, TCR167PCI, TCR511PCI, TCR511PEX, TCR51USB, TCR170PEX, TCR180PEX
"PEX", // PEX511
"USB", // USB5131
@@ -1019,6 +1071,7 @@ _ext const char *fw_id_ref[]
"DCF", // DCF600USB
"PZF", // PZF180PEX
"GLN", // GLN180PEX
+ "GNS", // GNS181PEX
NULL
}
#endif
@@ -1031,6 +1084,10 @@ _ext const char *fw_id_ref[]
#define fw_id_ref_gps fw_id_ref[2]
+#if _PCPS_USE_MM_IO
+ _ext int force_io_access;
+#endif
+
// The macros below accept a (PCPS_DDEV *) for easy access
// to the information stored in PCPS_DDEV structures.
@@ -1052,6 +1109,8 @@ _ext const char *fw_id_ref[]
#define _pcps_ddev_is_frc( _p ) _pcps_is_frc( &(_p)->dev )
#define _pcps_ddev_is_lwr( _p ) _pcps_is_lwr( &(_p)->dev )
+#define _pcps_ddev_is_gnss( _p ) _pcps_is_gnss( &(_p)->dev )
+
// Generic bus types:
#define _pcps_ddev_is_isa( _p ) _pcps_is_isa( &(_p)->dev )
@@ -1185,7 +1244,7 @@ _ext const char *fw_id_ref[]
_pcps_has_ptp( &(_p)->dev )
#define _pcps_ddev_has_ptp_unicast( _p ) \
- _pcps_has_ri_ptp_unicast( &(_p)->ri )
+ _pcps_has_ri_ptp_unicast( _ri_addr( _p ) )
#define _pcps_ddev_has_pzf( _p ) \
_pcps_has_pzf( &(_p)->dev )
@@ -1217,6 +1276,12 @@ _ext const char *fw_id_ref[]
#define _pcps_ddev_pci_cfg_err( _p ) \
_pcps_pci_cfg_err( &(_p)->dev )
+#define _pcps_ddev_has_gpio( _p ) \
+ _pcps_has_ri_gpio( _ri_addr( _p ) )
+
+#define _pcps_ddev_has_xmr( _p ) \
+ _pcps_has_ri_xmr( _ri_addr( _p ) )
+
// The macros below simplify read/write access to the clocks.
@@ -1298,7 +1363,7 @@ _ext const char *fw_id_ref[]
#if _PCPS_USE_MM_IO
#define _pcps_ddev_read_status_port( _d ) \
- ( _pcps_ddev_is_pci_mbgpex( _d ) ? \
+ ( (_d)->use_mm_io ? \
(uint8_t) (_d)->mm_addr->mbgpex.asic.status_port.ul : \
_mbg_inp8( (_d), 0, (_d)->status_port ) \
)
@@ -1390,19 +1455,31 @@ _ext const char *fw_id_ref[]
_pcps_usb_read_ep_tmo( _d, _p, _sz, MBGUSB_EP_IDX_HOST_IN_CYCLIC, MBGUSB_TIMEOUT_RECEIVE_CYCLIC, _irp )
#define _pcps_usb_read_var_cyclic( _d, _p, _irp ) \
- _pcps_usb_read_cyclic( _d, _p, sizeof( *(_p) ), _irp )
+ _pcps_usb_read_cyclic( _d, _p, sizeof( *(_p) ), _irp )
#elif defined( MBG_TGT_LINUX )
- #define _pcps_usb_write_ep_tmo( _d, _p, _sz, _ep_idx, _tmo ) \
- usb_bulk_msg( (_d)->udev, \
- usb_sndbulkpipe( (_d)->udev, (_d)->ep[_ep_idx].addr ), \
- _p, _sz, &actual_count, _tmo )
+ #if DEBUG_USB_IO
+ #define _pcps_usb_write_ep_tmo( _d, _p, _sz, _ep_idx, _tmo ) \
+ usb_bulk_msg_dbg( (_d)->udev, \
+ usb_sndbulkpipe( (_d)->udev, (_d)->ep[_ep_idx].addr ), \
+ _p, _sz, &actual_count, _tmo )
- #define _pcps_usb_read_ep_tmo( _d, _p, _sz, _ep_idx, _tmo ) \
- usb_bulk_msg( (_d)->udev, \
- usb_rcvbulkpipe( (_d)->udev, (_d)->ep[_ep_idx].addr ), \
- _p, _sz, &actual_count, _tmo )
+ #define _pcps_usb_read_ep_tmo( _d, _p, _sz, _ep_idx, _tmo ) \
+ usb_bulk_msg_dbg( (_d)->udev, \
+ usb_rcvbulkpipe( (_d)->udev, (_d)->ep[_ep_idx].addr ), \
+ _p, _sz, &actual_count, _tmo )
+ #else
+ #define _pcps_usb_write_ep_tmo( _d, _p, _sz, _ep_idx, _tmo ) \
+ usb_bulk_msg( (_d)->udev, \
+ usb_sndbulkpipe( (_d)->udev, (_d)->ep[_ep_idx].addr ), \
+ _p, _sz, &actual_count, _tmo )
+
+ #define _pcps_usb_read_ep_tmo( _d, _p, _sz, _ep_idx, _tmo ) \
+ usb_bulk_msg( (_d)->udev, \
+ usb_rcvbulkpipe( (_d)->udev, (_d)->ep[_ep_idx].addr ), \
+ _p, _sz, &actual_count, _tmo )
+ #endif
#define _pcps_usb_write( _d, _p, _sz ) \
_pcps_usb_write_ep_tmo( _d, _p, _sz, MBGUSB_EP_IDX_HOST_OUT, MBGUSB_TIMEOUT_SEND )
@@ -1414,7 +1491,7 @@ _ext const char *fw_id_ref[]
_pcps_usb_read_ep_tmo( _d, _p, _sz, MBGUSB_EP_IDX_HOST_IN_CYCLIC, MBGUSB_TIMEOUT_RECEIVE_CYCLIC )
#define _pcps_usb_read_var_cyclic( _d, _p ) \
- _pcps_usb_read_cyclic( _d, _p, sizeof( *(_p) ) )
+ _pcps_usb_read_cyclic( _d, _p, sizeof( *(_p) ) )
#endif // target specific definitions
@@ -1434,21 +1511,49 @@ _ext const char *fw_id_ref[]
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
-/* PCPS_WRITE_FNC */
- short pcps_write( PCPS_DDEV *pddev, uint8_t cmd, const void FAR *buffer, uint16_t count ) ;
-
- short pcps_generic_io( PCPS_DDEV *pddev, uint8_t type, const void FAR *in_buff, uint8_t in_cnt, void FAR *out_buff, uint8_t out_cnt ) ;
-/* PCPS_READ_FNC */
- short pcps_read_gps( PCPS_DDEV *pddev, uint8_t data_type, void FAR *buffer, uint16_t buffer_size ) ;
+ /**
+ * @brief Write data to a device
+ *
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] cmd The command code for the board, see @ref PCPS_CMD_CODES
+ * @param[in] buffer A buffer with data to be written according to the cmd code
+ * @param[in] count The number of bytes to be written according to the cmd code
+ *
+ * @return ::MBG_SUCCESS on success,
+ * ::MBG_ERR_TIMEOUT if device didn't respond in time,
+ * ::MBG_ERR_NBYTES if the number of parameter bytes did not match
+ * the number of data bytes expected by the device,
+ * or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_io_fncs
+ * @see @ref pcps_io_fncs
+ */
+ int pcps_write( PCPS_DDEV *pddev, uint8_t cmd, const void FAR *buffer, uint16_t count ) ;
-/* PCPS_WRITE_FNC */
- short pcps_write_gps( PCPS_DDEV *pddev, uint8_t data_type, const void FAR *buffer, uint16_t buffer_size ) ;
+ /**
+ * @brief Generic I/O function
+ *
+ * @param[in] pddev Pointer to the device structure
+ * @param[in] type The type of data to be read/written, see @ref PCPS_CMD_CODES
+ * @param[in] in_buff A buffer with data to be written according to the type code
+ * @param[in] in_cnt The number of bytes to be written according to the type code
+ * @param[out] out_buff A buffer with data to be read according to the type code
+ * @param[in] out_cnt The number of bytes to be read according to the type code
+ *
+ * @return ::MBG_SUCCESS on success,
+ * ::MBG_ERR_TIMEOUT if device didn't respond in time,
+ * ::MBG_ERR_NBYTES if the number of parameter bytes did not match
+ * the number of data bytes expected by the device,
+ * or one of the other @ref MBG_RETURN_CODES
+ *
+ * @ingroup pcps_io_fncs
+ * @see @ref pcps_io_fncs
+ */
+ int pcps_generic_io( PCPS_DDEV *pddev, uint8_t type, const void FAR *in_buff, uint8_t in_cnt, void FAR *out_buff, uint8_t out_cnt ) ;
- short pcps_get_fw_id( PCPS_DDEV *pddev, PCPS_ID_STR FAR fw_id ) ;
- short pcps_check_id( PCPS_DDEV *pddev, const char FAR *ref ) ;
- short pcps_get_rev_num( char FAR *idstr ) ;
+ int pcps_read_gps( PCPS_DDEV *pddev, uint8_t data_type, void FAR *buffer, uint16_t buffer_size ) ;
+ int pcps_write_gps( PCPS_DDEV *pddev, uint8_t data_type, const void FAR *buffer, uint16_t buffer_size ) ;
int pcps_read_sernum( PCPS_DDEV *pddev ) ;
- int pcps_rsrc_claim( PCPS_DDEV *pddev ) ;
void pcps_rsrc_release( PCPS_DDEV *pddev ) ;
ushort pcps_port_from_pos( ushort pos ) ;
uchar pcps_pos_from_port( ushort port ) ;
@@ -1462,9 +1567,9 @@ _ext const char *fw_id_ref[]
int pcps_start_device( PCPS_DDEV *pddev, PCPS_BUS_NUM bus_num, PCPS_SLOT_NUM dev_fnc_num ) ;
void pcps_cleanup_device( PCPS_DDEV *pddev ) ;
void pcps_setup_and_start_pci_dev( PCPS_DDEV *pddev, PCPS_BUS_NUM bus_num, PCPS_SLOT_NUM dev_fnc_num ) ;
- void pcps_detect_pci_clocks( PCPS_DDEV_ALLOC_FNC alloc_fnc, void *alloc_arg, PCPS_DDEV_CLEANUP_FNC cleanup_fnc, ushort vendor_id, PCPS_DEV_TYPE dev_type[], int n_dev_types ) ;
- void pcps_detect_isa_clocks( PCPS_DDEV_ALLOC_FNC alloc_fnc, PCPS_DDEV_CLEANUP_FNC cleanup_fnc, PCPS_DDEV_REGISTER_FNC register_fnc, int isa_ports[PCPS_MAX_ISA_CARDS], int isa_irqs[PCPS_MAX_ISA_CARDS] ) ;
- void _MBG_INIT_CODE_ATTR pcps_detect_clocks_alloc( PCPS_DDEV_ALLOC_FNC alloc_fnc, void *alloc_arg, PCPS_DDEV_CLEANUP_FNC cleanup_fnc, int isa_ports[PCPS_MAX_ISA_CARDS], int isa_irqs[PCPS_MAX_ISA_CARDS] ) ;
+ void pcps_detect_pci_clocks( PCPS_DDEV_ALLOC_FNC *alloc_fnc, void *alloc_arg, PCPS_DDEV_CLEANUP_FNC *cleanup_fnc, ushort vendor_id, PCPS_DEV_TYPE dev_type[], int n_dev_types ) ;
+ void pcps_detect_isa_clocks( PCPS_DDEV_ALLOC_FNC *alloc_fnc, PCPS_DDEV_CLEANUP_FNC *cleanup_fnc, PCPS_DDEV_REGISTER_FNC *register_fnc, int isa_ports[PCPS_MAX_ISA_CARDS], int isa_irqs[PCPS_MAX_ISA_CARDS] ) ;
+ void _MBG_INIT_CODE_ATTR pcps_detect_clocks_alloc( PCPS_DDEV_ALLOC_FNC *alloc_fnc, void *alloc_arg, PCPS_DDEV_CLEANUP_FNC *cleanup_fnc, int isa_ports[PCPS_MAX_ISA_CARDS], int isa_irqs[PCPS_MAX_ISA_CARDS] ) ;
void _MBG_INIT_CODE_ATTR pcps_detect_clocks( int isa_ports[PCPS_MAX_ISA_CARDS], int isa_irqs[PCPS_MAX_ISA_CARDS] ) ;
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/pcpslstr.c b/mbglib/common/pcpslstr.c
index e71e0d8..c9b1529 100755
--- a/mbglib/common/pcpslstr.c
+++ b/mbglib/common/pcpslstr.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcpslstr.c 1.23 2012/10/15 13:09:35 martin REL_M $
+ * $Id: pcpslstr.c 1.24.1.2 2015/10/01 14:23:42 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -11,7 +11,13 @@
*
* -----------------------------------------------------------------------
* $Log: pcpslstr.c $
- * Revision 1.23 2012/10/15 13:09:35 martin
+ * Revision 1.24.1.2 2015/10/01 14:23:42 martin
+ * Revision 1.24.1.1 2015/08/27 16:11:51Z martin
+ * Made string functions safe against buffer overruns.
+ * Started to add doxygen comments.
+ * Revision 1.24 2014/03/13 14:32:27 martin
+ * Fixed compiler warning.
+ * Revision 1.23 2012/10/15 13:09:35Z martin
* Added function sprint_utc_offs().
* Cleaned up get_tz_name().
* Fixed potential compiler warning for sprintf().
@@ -38,7 +44,7 @@
* Revision 1.15 2007/07/20 10:55:27Z martin
* Some modifications to avoid compiler warnings.
* Revision 1.14 2007/03/30 13:23:42 martin
- * In pcps_status_strs() handle case where time has been
+ * In pcps_status_strs() handle case where time has been
* set manually.
* Revision 1.13 2007/03/29 12:58:18Z martin
* Moved some definitions to the header file to make them public.
@@ -106,26 +112,41 @@ typedef struct
} CLSTR_STATUS;
-static const char *tz_name_utc = TZ_NAME_UTC;
+static const char tz_name_utc[] = TZ_NAME_UTC;
static CLSTR str_dst = { "DST", "Sommerzeit" };
/*HDR*/
+/**
+ * @brief Return a language dependend string for "invalid"
+ *
+ * @return A language dependend string for "invalid"
+ */
const char *inv_str( void )
{
static CLSTR s = { "** invalid **", "** ung" LCUE "ltig **" };
return _lstr( s );
-} /* inv_str */
+} // inv_str
/*HDR*/
-int sprint_utc_offs( char *s, const char *info, long utc_offs )
+/**
+ * @brief Print the UTC offset into a string
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] info An optional info string to be prepended, may be NULL
+ * @param[in] utc_offs UTC offset in [s]
+ *
+ * @return Number of characters written to the output buffer, except the terminating 0
+ */
+size_t snprint_utc_offs( char *s, size_t max_len, const char *info, long utc_offs )
{
- int n = 0;
+ size_t n = 0;
// utc_offs is in [s]
char utc_offs_sign = ( utc_offs < 0 ) ? '-' : '+';
@@ -136,17 +157,17 @@ int sprint_utc_offs( char *s, const char *info, long utc_offs )
ulong utc_offs_secs = tmp % MINS_PER_HOUR;
if ( info )
- n += sprintf( &s[n], "%s", info );
+ n += snprintf_safe( &s[n], max_len - n, "%s", info );
- n += sprintf( &s[n], "%c%lu", utc_offs_sign, utc_offs_hours );
+ n += snprintf_safe( &s[n], max_len - n, "%c%lu", utc_offs_sign, utc_offs_hours );
if ( utc_offs_mins || utc_offs_secs )
- n += sprintf( &s[n], ":%02lu", utc_offs_mins );
+ n += snprintf_safe( &s[n], max_len - n, ":%02lu", utc_offs_mins );
if ( utc_offs_secs )
- n += sprintf( &s[n], ":%02lu", utc_offs_secs );
+ n += snprintf_safe( &s[n], max_len - n, ":%02lu", utc_offs_secs );
- n += sprintf( &s[n], "h" );
+ n += sn_cpy_str_safe( &s[n], max_len - n, "h" );
return n;
@@ -155,12 +176,28 @@ int sprint_utc_offs( char *s, const char *info, long utc_offs )
static /*HDR*/
+/**
+ * @brief Return a static string with the name of the timezone, depending on the UTC offset
+ *
+ * @param[in] pcps_status Status flags read from a clock device
+ * @param[in] utc_offs UTC offset in [s]
+ * @param[in] flags A combination of ::PCPS_TZ_NAME_FLAGS contolling the output string format
+ * @param[in] is_msf A Flag used to indicate if the clock is an MSF receiver
+ *
+ * @return Pointer to a static string which has been set up
+ *
+ * @see ::pcps_tz_name
+ * @see ::pcps_tz_name_from_hr_time
+ * @see ::pcps_tz_name_hr_status
+ * @see ::pcps_tz_name_from_status
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
const char *get_tz_name( PCPS_TIME_STATUS_X pcps_status, long utc_offs,
ushort flags, int is_msf )
{
static char ws[40];
const char *cp = NULL;
- int n = 0;
+ size_t n = 0;
if ( ( pcps_status & PCPS_UTC ) && ( utc_offs == 0 ) )
return tz_name_utc; // no offset, no DST
@@ -195,7 +232,7 @@ const char *get_tz_name( PCPS_TIME_STATUS_X pcps_status, long utc_offs,
}
}
- n = sprint_utc_offs( ws, tz_name_utc, utc_offs );
+ n = snprint_utc_offs( ws, sizeof( ws ), tz_name_utc, utc_offs );
check_flags:
if ( cp )
@@ -203,30 +240,45 @@ check_flags:
if ( flags == 0 )
return cp;
- strcpy( ws, cp );
+ n = sn_cpy_str_safe( ws, sizeof( ws ), cp );
if ( flags & PCPS_TZ_NAME_FORCE_UTC_OFFS )
{
- n = strlen( ws );
- n += sprintf( &ws[n], "%*c(", pcps_time_tz_dist, ' ' );
- n += sprint_utc_offs( &ws[n], tz_name_utc, utc_offs );
- sprintf( &ws[n], ")" );
+ n += snprintf_safe( &ws[n], sizeof( ws ) - n, "%*c(", pcps_time_tz_dist, ' ' );
+ n += snprint_utc_offs( &ws[n], sizeof( ws ) - n, tz_name_utc, utc_offs );
+ n += sn_cpy_char_safe( &ws[n], sizeof( ws ) - n, ')' );
}
}
if ( flags & PCPS_TZ_NAME_APP_DST )
{
if ( pcps_status & PCPS_DL_ENB )
- sprintf( _eos( ws ), ",%*c%s", pcps_time_tz_dist,
- ' ', _lstr( str_dst ) );
+ snprintf_safe( &ws[n], sizeof( ws ) - n, ",%*c%s", pcps_time_tz_dist,
+ ' ', _lstr( str_dst ) );
}
return ws;
-}
+
+} // get_tz_name
/*HDR*/
+/**
+ * @brief Return a static time zone string depending on the UTC offset from a ::PCPS_TIME structure
+ *
+ * @param[in] t A ::PCPS_TIME structure read from a clock device
+ * @param[in] flags A combination of ::PCPS_TZ_NAME_FLAGS contolling the output string format
+ * @param[in] is_msf A Flag used to indicate if the clock is an MSF receiver
+ *
+ * @return Pointer to a static string which has been set up
+ *
+ * @see ::pcps_tz_name_from_hr_time
+ * @see ::pcps_tz_name_hr_status
+ * @see ::pcps_tz_name_from_status
+ * @see ::get_tz_name
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
const char *pcps_tz_name( const PCPS_TIME *t, ushort flags, int is_msf )
{
return get_tz_name( t->status, t->offs_utc * SECS_PER_HOUR, flags, is_msf );
@@ -236,6 +288,21 @@ const char *pcps_tz_name( const PCPS_TIME *t, ushort flags, int is_msf )
/*HDR*/
+/**
+ * @brief Return a static time zone string depending on the UTC offset from a ::PCPS_HR_TIME structure
+ *
+ * @param[in] hrt A ::PCPS_HR_TIME structure read from a clock device
+ * @param[in] flags A combination of ::PCPS_TZ_NAME_FLAGS contolling the output string format
+ * @param[in] is_msf A Flag used to indicate if the clock is an MSF receiver
+ *
+ * @return Pointer to a static string which has been set up
+ *
+ * @see ::pcps_tz_name
+ * @see ::pcps_tz_name_hr_status
+ * @see ::pcps_tz_name_from_status
+ * @see ::get_tz_name
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
const char *pcps_tz_name_from_hr_time( const PCPS_HR_TIME *hrt, ushort flags, int is_msf )
{
return get_tz_name( hrt->status, hrt->utc_offs, flags, is_msf );
@@ -244,22 +311,36 @@ const char *pcps_tz_name_from_hr_time( const PCPS_HR_TIME *hrt, ushort flags, in
-// The function below can be used to build a name for
-// the time zone if the TIMESCALE, the UTC/DST status and the
-// UTC offset are known, e.g. from plug-in clocks.
-
/*HDR*/
+/**
+ * @brief Return a static time zone string depending on the UTC offset from a ::PCPS_HR_TIME structure
+ *
+ * This function can be used to build a name for the time zone if the timescale,
+ * the %UTC/DST status and the %UTC offset are known, e.g. from plug-in clock devices.
+ *
+ * @param[in] t A ::PCPS_HR_TIME structure read from a clock device
+ * @param[in] flags A combination of ::PCPS_TZ_NAME_FLAGS contolling the output string format
+ * @param[in] is_msf A Flag used to indicate if the clock is an MSF receiver
+ *
+ * @return Pointer to a static string which has been set up
+ *
+ * @see ::pcps_tz_name
+ * @see ::pcps_tz_name_from_hr_time
+ * @see ::pcps_tz_name_from_status
+ * @see ::get_tz_name
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
const char *pcps_tz_name_hr_status( const PCPS_HR_TIME *t, ushort flags, int is_msf )
{
static char ws[40];
if ( t->status & PCPS_SCALE_GPS )
- strcpy( ws, "GPS" );
+ strncpy_safe( ws, "GPS", sizeof( ws ) );
else
if ( t->status & PCPS_SCALE_TAI )
- strcpy( ws, "TAI" );
+ strncpy_safe( ws, "TAI", sizeof( ws ) );
else
- return pcps_tz_name_from_hr_time( t, flags, is_msf);
+ return pcps_tz_name_from_hr_time( t, flags, is_msf );
return ws;
@@ -267,13 +348,25 @@ const char *pcps_tz_name_hr_status( const PCPS_HR_TIME *t, ushort flags, int is_
-// The function below can be used to build a name for
-// the time zone if only the UTC/DST status is known
-// but the UTC offset is not. This is the case, for example,
-// if the Meinberg standard time string is decoded.
-
/*HDR*/
-const char *pcps_tz_name_from_status( ushort status )
+/**
+ * @brief Return a static time zone string depending on the UTC offset from a ::PCPS_HR_TIME structure
+ *
+ * This function can be used to build a name for the time zone
+ * if only the %UTC/DST status is known, but the UTC offset is not.
+ * This is the case, for example, if the Meinberg standard time string is decoded.
+ *
+ * @param[in] status Clock status in ::PCPS_TIME_STATUS_X format
+ *
+ * @return Pointer to a static string which has been set up
+ *
+ * @see ::pcps_tz_name
+ * @see ::pcps_tz_name_from_hr_time
+ * @see ::pcps_tz_name_hr_status
+ * @see ::get_tz_name
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
+const char *pcps_tz_name_from_status( PCPS_TIME_STATUS_X status )
{
if ( status & PCPS_UTC )
return tz_name_utc;
@@ -285,33 +378,39 @@ const char *pcps_tz_name_from_status( ushort status )
/*HDR*/
-char *pcps_date_time_str( char *s, const PCPS_TIME *t,
+char *pcps_date_time_str( char *s, size_t max_len, const PCPS_TIME *t,
ushort year_limit, const char *tz_str )
{
if ( !_pcps_time_is_read( t ) )
- strcpy( s, str_not_avail );
+ strncpy_safe( s, str_not_avail, max_len );
else
{
- char *cp;
+ size_t n;
int i;
- _pcps_sprint_wday( s, t, language );
- cp = _eos( s );
- *cp++ = ',';
+ _pcps_snprint_wday( s, max_len, t, language );
+ n = strlen( s );
+
+ n += sn_cpy_char_safe( &s[n], max_len - n, ',' );
+
for ( i = 0; i < pcps_wday_date_dist; i++ )
- *cp++ = ' ';
- _pcps_sprint_date( cp, t, year_limit );
- cp = _eos( s );
+ n += sn_cpy_char_safe( &s[n], max_len - n, ' ' );
+
+ _pcps_snprint_date( &s[n], max_len - n, t, year_limit );
+ n = strlen( s );
+
for ( i = 0; i < pcps_date_time_dist; i++ )
- *cp++ = ' ';
- _pcps_sprint_time_long( cp, t );
+ n += sn_cpy_char_safe( &s[n], max_len - n, ' ' );
+
+ _pcps_snprint_time_long( &s[n], max_len - n, t );
+ n = strlen( s );
if ( tz_str )
{
- cp = _eos( s );
for ( i = 0; i < pcps_time_tz_dist; i++ )
- *cp++ = ' ';
- strcpy( cp, tz_str );
+ n += sn_cpy_char_safe( &s[n], max_len - n, ' ' );
+
+ n += sn_cpy_str_safe( &s[n], max_len - n, tz_str );
}
}
@@ -324,34 +423,22 @@ char *pcps_date_time_str( char *s, const PCPS_TIME *t,
#if MBG_TGT_HAS_WCHAR_T && defined( MBG_TGT_WIN32 )
/*HDR*/
-wchar_t *pcps_date_time_wstr( wchar_t *ws, const PCPS_TIME *t,
+wchar_t *pcps_date_time_wstr( wchar_t *ws, size_t count, const PCPS_TIME *t,
ushort year_limit, const wchar_t *tz_str )
{
- char stemp[80];
- wchar_t wstemp[80];
+ //#error Remove this error directive and check if the function works properly.
+ char tmp_str[80];
- if ( !_pcps_time_is_read( t ) )
- mbstowcs( ws, str_not_avail, 32 );
- else
- {
- char *cp;
- int i;
+ pcps_date_time_str( tmp_str, sizeof( tmp_str ), t, year_limit, NULL );
- _pcps_sprint_wday( stemp, t, language );
- cp = _eos( stemp );
- *cp++ = ',';
- for ( i = 0; i < pcps_wday_date_dist; i++ )
- *cp++ = ' ';
- _pcps_sprint_date( cp, t, year_limit );
- cp = _eos( stemp );
- for ( i = 0; i < pcps_date_time_dist; i++ )
- *cp++ = ' ';
- _pcps_sprint_time_long( cp, t );
-
- mbstowcs( wstemp, stemp, sizeof( wstemp ) );
+ mbstowcs( ws, tmp_str, count );
+ ws[count - 1] = L'0'; // force terminating 0
- if ( tz_str )
- _snwprintf( ws, sizeof( wstemp ) + 32, L"%s %s", wstemp, tz_str );
+ if ( tz_str )
+ {
+ size_t n = wcslen( ws );
+ _snwprintf( &ws[n], count - n, L" %s", tz_str );
+ ws[count - 1] = L'0'; // force terminating 0
}
return ws;
@@ -445,16 +532,16 @@ void pcps_status_strs( ushort status, int status_is_read,
/*HDR*/
-char *pcps_port_str( char *s, const PCPS_DEV *pdev )
+char *pcps_port_str( char *s, size_t max_len, const PCPS_DEV *pdev )
{
ushort port = _pcps_port_base( pdev, 0 );
- ushort n = sprintf( s, "%3Xh", port );
+ size_t n = snprintf_safe( s, max_len, "%3Xh", port );
port = _pcps_port_base( pdev, 1 );
if ( port )
- sprintf( &s[n], ", %3Xh", port );
+ snprintf_safe( &s[n], max_len - n, ", %3Xh", port );
return s;
@@ -475,25 +562,26 @@ const char *pcps_tzcode_str( PCPS_TZCODE tzcode )
/*HDR*/
-char *pcps_serial_str( char *s, int i, const RECEIVER_PORT_CFG *p,
+char *pcps_serial_str( char *s, size_t max_len, int i, const RECEIVER_PORT_CFG *p,
const RECEIVER_INFO *p_ri, int short_strs )
{
const PORT_SETTINGS *p_ps = &p->pii[i].port_info.port_settings;
const STR_TYPE_INFO *p_sti = &p->stii[p_ps->str_type].str_type_info;
+ size_t n;
- sprintf( s, "%lu,%s", (ulong) p_ps->parm.baud_rate, p_ps->parm.framing );
+ n = snprintf_safe( s, max_len, "%lu,%s", (ulong) p_ps->parm.baud_rate, p_ps->parm.framing );
if ( short_strs )
- sprintf( _eos( s ), ",%s", short_mode_name[p_ps->mode] );
+ n += snprintf_safe( &s[n], max_len - n, ",%s", short_mode_name[p_ps->mode] );
else
{
if ( p_ri->n_str_type > 1 )
- sprintf( _eos( s ), ", %s", p_sti->long_name );
+ n += snprintf_safe( &s[n], max_len - n, ", %s", p_sti->long_name );
- sprintf( _eos( s ), ", %s", _lstr( mode_name[p_ps->mode] ) );
+ n += snprintf_safe( &s[n], max_len - n, ", %s", _lstr( mode_name[p_ps->mode] ) );
}
- return( s );
+ return s;
} // pcps_serial_str
diff --git a/mbglib/common/pcpslstr.h b/mbglib/common/pcpslstr.h
index 637d587..71f9519 100755
--- a/mbglib/common/pcpslstr.h
+++ b/mbglib/common/pcpslstr.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcpslstr.h 1.28 2012/10/15 13:01:23 martin REL_M $
+ * $Id: pcpslstr.h 1.29.1.6 2016/08/10 12:29:03 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,20 @@
*
* -----------------------------------------------------------------------
* $Log: pcpslstr.h $
+ * Revision 1.29.1.6 2016/08/10 12:29:03 martin
+ * Check for MBG_TGT_POSIX instead of MBG_TGT_UNIX.
+ * Revision 1.29.1.5 2015/11/20 14:50:02 martin
+ * Revision 1.29.1.4 2015/10/26 13:43:00Z martin
+ * Revision 1.29.1.3 2015/10/01 13:41:32Z martin
+ * Revision 1.29.1.2 2015/08/27 16:13:10Z martin
+ * Made string functions safe against buffer overruns.
+ * Started to add doxygen comments.
+ * Updated function prototypes.
+ * Revision 1.29.1.1 2014/05/13 11:17:28 martin
+ * Account for new GPIO mode for programmable pulse outputs.
+ * Revision 1.29 2012/11/20 10:47:29 martin
+ * Moved some code definitions for special chars
+ * to new header charcode.h.
* Revision 1.28 2012/10/15 13:01:23 martin
* Include cfg_hlp.h.
* Made all declarations extern C.
@@ -80,7 +94,7 @@
* Updated function prototypes.
* Revision 1.6 2002/12/18 13:57:53 martin
* Some definitions and variables made global.
- * Added some new macros _pcps_sprint_vernum...()
+ * Added some new macros _pcps_sprint_vernum...()
* and _pcps_sprint_dev_id().
* Revision 1.5 2002/02/19 10:01:36Z MARTIN
* New initializers for string mode names.
@@ -108,15 +122,13 @@
/* Other headers to be included */
-#include <mbg_tgt.h>
+#include <str_util.h>
+#include <charcode.h>
#include <cfg_hlp.h>
-#include <parmpcps.h>
+#include <pcpsdev.h>
#include <ctrydttm.h>
#include <cnv_wday.h>
-#if MBG_TGT_HAS_WCHAR_T
- #include <wchar.h>
-#endif
#ifdef _PCPSLSTR
#define _ext
@@ -132,92 +144,53 @@
extern "C" {
#endif
-// upper case 'A' umlaut
-#define ANSI_UC_A_UML '\xC4' // single char
-#define ANSI_US_A_UML "\xC4" // string
-
-// upper case 'O' umlaut
-#define ANSI_UC_O_UML '\xD6' // single char
-#define ANSI_US_O_UML "\xD6" // string
-
-// upper case 'U' umlaut
-#define ANSI_UC_U_UML '\xDC' // single char
-#define ANSI_US_U_UML "\xDC" // string
-
-// lower case 'a' umlaut
-#define ANSI_LC_A_UML '\xE4' // single char
-#define ANSI_LS_A_UML "\xE4" // string
-
-// lower case 'o' umlaut
-#define ANSI_LC_O_UML '\xF6' // single char
-#define ANSI_LS_O_UML "\xF6" // string
-
-// lower case 'u' umlaut
-#define ANSI_LC_U_UML '\xFC' // single char
-#define ANSI_LS_U_UML "\xFC" // string
-
-// 'sz' umlaut
-#define ANSI_LC_SZ_UML '\xDF' // single char
-#define ANSI_LS_SZ_UML "\xDF" // string
-
-// degree character
-#define ANSI_C_DEGREE '\xB0' // single char
-#define ANSI_S_DEGREE "\xB0" // string
-
-// greek mu character
-#define ANSI_C_MU '\xB5' //single char
-#define ANSI_S_MU "\xB5" //string
#if defined( MBG_TGT_WIN32 ) \
- || defined( MBG_TGT_UNIX ) \
+ || defined( MBG_TGT_POSIX ) \
|| defined( MBG_TGT_QNX )
+
#define DEFAULT_PCPS_WDAY_DATE_DIST 1
#define DEFAULT_PCPS_DATE_TIME_DIST 2
#define DEFAULT_PCPS_TIME_TZ_DIST 1
- #define UCAE ANSI_US_A_UML
- #define UCOE ANSI_US_O_UML
- #define UCUE ANSI_US_U_UML
-
- #define LCAE ANSI_LS_A_UML
- #define LCOE ANSI_LS_O_UML
- #define LCUE ANSI_LS_U_UML
-
- #define LCSZ ANSI_LS_SZ_UML
- #define DEG ANSI_S_DEGREE
- #define MU ANSI_S_MU
#else
+
#define DEFAULT_PCPS_WDAY_DATE_DIST 1
#define DEFAULT_PCPS_DATE_TIME_DIST 2
#define DEFAULT_PCPS_TIME_TZ_DIST 1
- #define UCAE "\x8E"
- #define UCOE "\x99"
- #define UCUE "\x9A"
-
- #define LCAE "\x84"
- #define LCOE "\x94"
- #define LCUE "\x81"
-
- #define LCSZ "\xE1"
- #define DEG "\xF8"
- #define MU "\xE6"
#endif
-// The flags defined below can be passed to pcps_tz_name()
-// in order to control the generation of time zone names
-enum
+/**
+ * @brief Flag bits used to define ::PCPS_TZ_NAME_FLAGS
+ *
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
+enum PCPS_TZ_NAME_BITS
{
- PCPS_TZ_NAME_BIT_FORCE_UTC_OFFS, // always print "UTC+offs"
- PCPS_TZ_NAME_BIT_APP_DST, // append DST status
+ PCPS_TZ_NAME_BIT_FORCE_UTC_OFFS, ///< always print "UTC+offs"
+ PCPS_TZ_NAME_BIT_APP_DST, ///< append DST status
N_PCPS_TZ_NAME_FLAG
};
-// bit masks corresponding to the flags above
-#define PCPS_TZ_NAME_FORCE_UTC_OFFS ( 1UL << PCPS_TZ_NAME_BIT_FORCE_UTC_OFFS )
-#define PCPS_TZ_NAME_APP_DST ( 1UL << PCPS_TZ_NAME_BIT_APP_DST )
+
+/**
+ * @brief Flag bits used to control the string generated by ::pcps_tz_name
+ *
+ * The flags defined below can be passed to ::pcps_tz_name
+ * to control the formatting of the generated time zone names
+ *
+ * @see ::pcps_tz_name
+ * @see ::PCPS_TZ_NAME_BITS
+ */
+enum PCPS_TZ_NAME_FLAGS
+{
+ PCPS_TZ_NAME_FORCE_UTC_OFFS = ( 1UL << PCPS_TZ_NAME_BIT_FORCE_UTC_OFFS ), ///< see ::PCPS_TZ_NAME_FORCE_UTC_OFFS
+ PCPS_TZ_NAME_APP_DST = ( 1UL << PCPS_TZ_NAME_BIT_APP_DST ), ///< see ::PCPS_TZ_NAME_APP_DST
+};
+
// The definitions below are used with pcps_get_status_strs().
@@ -807,11 +780,12 @@ typedef struct
#define GER_POUT_NAME_TIME_SYNC "Zeit synchron"
#define GER_POUT_NAME_ALL_SYNC "alles synchron"
#define GER_POUT_NAME_TIMECODE "DCLS-Zeitcode"
-#define GER_POUT_NAME_TIMESTR "COM-Zeittelegramm"
+#define GER_POUT_NAME_TIMESTR "Serielles Zeittelegramm"
#define GER_POUT_NAME_10MHZ "Festfrequenz 10 MHz"
#define GER_POUT_NAME_DCF77_M59 "DCF77-Zeitmarken mit 59. Impuls"
#define GER_POUT_NAME_SYNTH "Frequenz-Synthesizer"
#define GER_POUT_NAME_TIME_SLOTS "Zeitschlitze pro Minute"
+#define GER_POUT_NAME_GPIO "GPIO-Signal"
#define DEFAULT_GER_POUT_NAMES \
{ \
@@ -831,7 +805,8 @@ typedef struct
GER_POUT_NAME_10MHZ, \
GER_POUT_NAME_DCF77_M59, \
GER_POUT_NAME_SYNTH, \
- GER_POUT_NAME_TIME_SLOTS \
+ GER_POUT_NAME_TIME_SLOTS, \
+ GER_POUT_NAME_GPIO \
}
/*
@@ -855,6 +830,7 @@ typedef struct
#define GER_POUT_HINT_DCF77_M59 "Zeitmarken wie DCF77, aber mit 500 ms Impuls in 59. Sekunde"
#define GER_POUT_HINT_SYNTH "Durch programmierbaren Synthesizer erzeugte Frequenz"
#define GER_POUT_HINT_TIME_SLOTS "Programmierbare Zeitslots, die in jeder Minute aktiviert werden"
+#define GER_POUT_HINT_GPIO "Signal des spezifizierten GPIO-Ein- oder Ausgangs"
#define DEFAULT_GER_POUT_HINTS \
{ \
@@ -874,83 +850,77 @@ typedef struct
GER_POUT_HINT_10MHZ, \
GER_POUT_HINT_DCF77_M59, \
GER_POUT_HINT_SYNTH, \
- GER_POUT_HINT_TIME_SLOTS \
+ GER_POUT_HINT_TIME_SLOTS, \
+ GER_POUT_HINT_GPIO \
}
// some macros which generate proper function calls
-#define _pcps_sprint_vernum_dec( _s, _v ) \
- sprintf( (_s), "v%u.%02u", \
- ( (unsigned) (_v) ) / 100, \
- ( (unsigned) (_v) ) % 100 )
+#define _pcps_snprint_vernum_dec( _s, _sz, _v ) \
+ snprintf_safe( (_s), (_sz), "v%u.%02u", \
+ ( (unsigned) (_v) ) / 100, \
+ ( (unsigned) (_v) ) % 100 )
-#define _pcps_sprint_vernum_hex( _s, _v ) \
- sprintf( (_s), "v%X.%02X", \
- ( (unsigned) (_v) ) >> 8, \
+#define _pcps_snprint_vernum_hex( _s, _sz, _v ) \
+ snprintf_safe( (_s), (_sz), "v%X.%02X", \
+ ( (unsigned) (_v) ) >> 8, \
( (unsigned) (_v) ) & 0xFF )
#if defined( MBG_TGT_WIN32 )
- #define _pcps_sprint_vernum _pcps_sprint_vernum_dec
+ #define _pcps_snprint_vernum _pcps_snprint_vernum_dec
#else
- #define _pcps_sprint_vernum _pcps_sprint_vernum_hex
+ #define _pcps_snprint_vernum _pcps_snprint_vernum_hex
#endif
-#define _pcps_sprint_dev_id( _s, _n ) \
- sprintf( (_s), "%04Xh", _n )
+#define _pcps_snprint_dev_id( _s, _sz, _n ) \
+ snprintf_safe( (_s), (_sz), "%04Xh", _n )
-#define _pcps_sprint_wday( _s, _t, _l ) \
- sprint_ctry_wday( (_s), _wday_mon17_to_sun06( (_t)->wday ), (_l) )
+#define _pcps_snprint_wday( _s, _sz, _t, _l ) \
+ snprint_ctry_wday( (_s), (_sz), _wday_mon17_to_sun06( (_t)->wday ), (_l) )
-#define _pcps_sprint_date( _s, _t, _yl ) \
- sprint_ctry_dt( (_s), (_t)->mday, (_t)->month, \
+#define _pcps_snprint_date( _s, _sz, _t, _yl ) \
+ snprint_ctry_dt( (_s), (_sz), (_t)->mday, (_t)->month, \
pcps_exp_year( (_t)->year, (_yl) ) )
-#define _pcps_sprint_time( _s, _t ) \
- sprint_ctry_tm( (_s), (_t)->hour, (_t)->min, (_t)->sec )
+#define _pcps_snprint_time( _s, _sz, _t ) \
+ snprint_ctry_tm( (_s), (_sz), (_t)->hour, (_t)->min, (_t)->sec )
-#define _pcps_sprint_time_long( _s, _t ) \
- sprint_ctry_tm_long( (_s), (_t)->hour, (_t)->min, (_t)->sec, (_t)->sec100, 2 )
+#define _pcps_snprint_time_long( _s, _sz, _t ) \
+ snprint_ctry_tm_long( (_s), (_sz), (_t)->hour, (_t)->min, (_t)->sec, (_t)->sec100, 2 )
-#define _cput_pcps_date( _t, _yl ) \
-{ \
- char s[80]; \
- _pcps_sprint_date( s, (_t), (_yl) ); \
- cputs( s ); \
+#define _cput_pcps_date( _t, _yl ) \
+{ \
+ char s[80]; \
+ _pcps_snprint_date( s, sizeof( s ), (_t), (_yl) ); \
+ cputs( s ); \
}
-#define _cput_pcps_time( _t ) \
-{ \
- char s[80]; \
- _pcps_sprint_time( s, (_t) ); \
- cputs( s ); \
+#define _cput_pcps_time( _t ) \
+{ \
+ char s[80]; \
+ _pcps_snprint_time( s, sizeof( s ), (_t) ); \
+ cputs( s ); \
}
-#define _cput_pcps_time_long( _t ) \
-{ \
- char s[80]; \
- _pcps_sprint_time_long( s, (_t) ); \
- cputs( s ); \
+#define _cput_pcps_time_long( _t ) \
+{ \
+ char s[80]; \
+ _pcps_snprint_time_long( s, sizeof( s ), (_t) ); \
+ cputs( s ); \
}
-#define _cput_pcps_date_and_time( _t, _yl, _tz ) \
-{ \
- char s[80]; \
- cputs( pcps_date_time_str( s, (_t), (_yl), (_tz) ) ); \
+#define _cput_pcps_date_and_time( _t, _yl, _tz ) \
+{ \
+ char s[80]; \
+ cputs( pcps_date_time_str( s, sizeof( s ), (_t), (_yl), (_tz) ) ); \
}
-_ext const char *str_not_avail
-#ifdef _DO_INIT
- = "N/A"
-#endif
-;
-
-
_ext CLSTR lstr_cet
#ifdef _DO_INIT
= { TZ_NAME_CET, TZ_NAME_MEZ }
@@ -1024,18 +994,104 @@ _ext const char *short_mode_name[N_STR_MODE]
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
+ /**
+ * @brief Return a language dependend string for "invalid"
+ *
+ * @return A language dependend string for "invalid"
+ */
const char *inv_str( void ) ;
- int sprint_utc_offs( char *s, const char *info, long utc_offs ) ;
+
+ /**
+ * @brief Print the UTC offset into a string
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] info An optional info string to be prepended, may be NULL
+ * @param[in] utc_offs UTC offset in [s]
+ *
+ * @return Number of characters written to the output buffer, except the terminating 0
+ */
+ size_t snprint_utc_offs( char *s, size_t max_len, const char *info, long utc_offs ) ;
+
+ /**
+ * @brief Return a static time zone string depending on the UTC offset from a ::PCPS_TIME structure
+ *
+ * @param[in] t A ::PCPS_TIME structure read from a clock device
+ * @param[in] flags A combination of ::PCPS_TZ_NAME_FLAGS contolling the output string format
+ * @param[in] is_msf A Flag used to indicate if the clock is an MSF receiver
+ *
+ * @return Pointer to a static string which has been set up
+ *
+ * @see ::pcps_tz_name_from_hr_time
+ * @see ::pcps_tz_name_hr_status
+ * @see ::pcps_tz_name_from_status
+ * @see ::get_tz_name
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
const char *pcps_tz_name( const PCPS_TIME *t, ushort flags, int is_msf ) ;
+
+ /**
+ * @brief Return a static time zone string depending on the UTC offset from a ::PCPS_HR_TIME structure
+ *
+ * @param[in] hrt A ::PCPS_HR_TIME structure read from a clock device
+ * @param[in] flags A combination of ::PCPS_TZ_NAME_FLAGS contolling the output string format
+ * @param[in] is_msf A Flag used to indicate if the clock is an MSF receiver
+ *
+ * @return Pointer to a static string which has been set up
+ *
+ * @see ::pcps_tz_name
+ * @see ::pcps_tz_name_hr_status
+ * @see ::pcps_tz_name_from_status
+ * @see ::get_tz_name
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
const char *pcps_tz_name_from_hr_time( const PCPS_HR_TIME *hrt, ushort flags, int is_msf ) ;
+
+ /**
+ * @brief Return a static time zone string depending on the UTC offset from a ::PCPS_HR_TIME structure
+ *
+ * This function can be used to build a name for the time zone if the timescale,
+ * the %UTC/DST status and the %UTC offset are known, e.g. from plug-in clock devices.
+ *
+ * @param[in] t A ::PCPS_HR_TIME structure read from a clock device
+ * @param[in] flags A combination of ::PCPS_TZ_NAME_FLAGS contolling the output string format
+ * @param[in] is_msf A Flag used to indicate if the clock is an MSF receiver
+ *
+ * @return Pointer to a static string which has been set up
+ *
+ * @see ::pcps_tz_name
+ * @see ::pcps_tz_name_from_hr_time
+ * @see ::pcps_tz_name_from_status
+ * @see ::get_tz_name
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
const char *pcps_tz_name_hr_status( const PCPS_HR_TIME *t, ushort flags, int is_msf ) ;
- const char *pcps_tz_name_from_status( ushort status ) ;
- char *pcps_date_time_str( char *s, const PCPS_TIME *t, ushort year_limit, const char *tz_str ) ;
- wchar_t *pcps_date_time_wstr( wchar_t *ws, const PCPS_TIME *t, ushort year_limit, const wchar_t *tz_str ) ;
+
+ /**
+ * @brief Return a static time zone string depending on the UTC offset from a ::PCPS_HR_TIME structure
+ *
+ * This function can be used to build a name for the time zone
+ * if only the %UTC/DST status is known, but the UTC offset is not.
+ * This is the case, for example, if the Meinberg standard time string is decoded.
+ *
+ * @param[in] status Clock status in ::PCPS_TIME_STATUS_X format
+ *
+ * @return Pointer to a static string which has been set up
+ *
+ * @see ::pcps_tz_name
+ * @see ::pcps_tz_name_from_hr_time
+ * @see ::pcps_tz_name_hr_status
+ * @see ::get_tz_name
+ * @see ::PCPS_TZ_NAME_FLAGS
+ */
+ const char *pcps_tz_name_from_status( PCPS_TIME_STATUS_X status ) ;
+
+ char *pcps_date_time_str( char *s, size_t max_len, const PCPS_TIME *t, ushort year_limit, const char *tz_str ) ;
+ wchar_t *pcps_date_time_wstr( wchar_t *ws, size_t count, const PCPS_TIME *t, ushort year_limit, const wchar_t *tz_str ) ;
void pcps_status_strs( ushort status, int status_is_read, int is_gps, PCPS_STATUS_STRS *pstrs ) ;
- char *pcps_port_str( char *s, const PCPS_DEV *pdev ) ;
+ char *pcps_port_str( char *s, size_t max_len, const PCPS_DEV *pdev ) ;
const char *pcps_tzcode_str( PCPS_TZCODE tzcode ) ;
- char *pcps_serial_str( char *s, int i, const RECEIVER_PORT_CFG *p, const RECEIVER_INFO *p_ri, int short_strs ) ;
+ char *pcps_serial_str( char *s, size_t max_len, int i, const RECEIVER_PORT_CFG *p, const RECEIVER_INFO *p_ri, int short_strs ) ;
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/pcpsmktm.c b/mbglib/common/pcpsmktm.c
index 212dfb3..8ef3781 100755
--- a/mbglib/common/pcpsmktm.c
+++ b/mbglib/common/pcpsmktm.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcpsmktm.c 1.4 2006/12/14 15:27:49 martin REL_M $
+ * $Id: pcpsmktm.c 1.4.1.3 2014/10/14 10:23:21 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,9 @@
*
* -----------------------------------------------------------------------
* $Log: pcpsmktm.c $
+ * Revision 1.4.1.3 2014/10/14 10:23:21 martin
+ * Revision 1.4.1.2 2014/10/14 10:04:49 martin
+ * Revision 1.4.1.1 2014/10/14 08:59:11Z martin
* Revision 1.4 2006/12/14 15:27:49 martin
* Include time.h.
* Revision 1.3 2006/08/22 09:10:03 martin
@@ -27,25 +30,40 @@
#include <mbgmktm.h>
-#include <time.h>
/*HDR*/
-long pcps_mktime( PCPS_TIME *tp )
+/**
+ * @brief Compute a linear time_t value from ::PCPS_TIME
+ *
+ * This function works like the standard mktime() function but does not
+ * account for a timezone setting configured for the standard C library.
+ * Instead, since ::PCPS_TIME contains local time with specified UTC offset
+ * the UTC offset is removed to yield UTC time.
+ *
+ * @param[in] tp A timestamp in ::PCPS_TIME format
+ *
+ * @return seconds since 1970-01-01 (Unix time_t format) or ((time_t) -1) if range overflow
+ */
+time_t pcps_mktime( const PCPS_TIME *tp )
{
time_t secs;
int year = tp->year;
+ // Expand 2 digit year number (year of the century) to 4 digits
+ // including the century.
if ( year < 70 )
year += 100;
+ // Plausibility checks are made by mbg_mktime().
secs = mbg_mktime( year, tp->month - 1, tp->mday - 1,
tp->hour, tp->min, tp->sec );
- if ( secs != -1 )
- secs -= tp->offs_utc * 3600;
+ // Convert to UTC if result is valid.
+ if ( secs != ( (time_t) -1 ) )
+ secs -= tp->offs_utc * 3600UL;
- return( secs );
+ return secs;
} // pcps_mktime
diff --git a/mbglib/common/pcpsmktm.h b/mbglib/common/pcpsmktm.h
index efcc2df..1ba5ded 100755
--- a/mbglib/common/pcpsmktm.h
+++ b/mbglib/common/pcpsmktm.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcpsmktm.h 1.1 2001/02/02 15:31:07 MARTIN REL_M $
+ * $Id: pcpsmktm.h 1.1.1.1 2014/10/14 10:36:38 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,8 @@
*
* -----------------------------------------------------------------------
* $Log: pcpsmktm.h $
+ * Revision 1.1.1.1 2014/10/14 10:36:38 martin
+ * Updated function prototypes.
* Revision 1.1 2001/02/02 15:31:07 MARTIN
*
**************************************************************************/
@@ -22,9 +24,12 @@
#include <pcpsdefs.h>
+#include <time.h>
+
#ifdef _PCPSMKTM
#define _ext
+ #define _DO_INIT
#else
#define _ext extern
#endif
@@ -32,25 +37,32 @@
/* Start of header body */
-//_ext PCPS_TIME tx;
-
-/* End of header body */
-
-#undef _ext
-
-
-/* function prototypes: */
-
#ifdef __cplusplus
extern "C" {
#endif
+
+/* function prototypes: */
+
/* ----- function prototypes begin ----- */
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
- long pcps_mktime( PCPS_TIME *tp ) ;
+ /**
+ * @brief Compute a linear time_t value from ::PCPS_TIME
+ *
+ * This function works like the standard mktime() function but does not
+ * account for a timezone setting configured for the standard C library.
+ * Instead, since ::PCPS_TIME contains local time with specified UTC offset
+ * the UTC offset is removed to yield UTC time.
+ *
+ * @param[in] tp A timestamp in ::PCPS_TIME format
+ *
+ * @return seconds since 1970-01-01 (Unix time_t format) or ((time_t) -1) if range overflow
+ */
+ time_t pcps_mktime( const PCPS_TIME *tp ) ;
+
/* ----- function prototypes end ----- */
@@ -58,5 +70,9 @@ extern "C" {
}
#endif
+/* End of header body */
+
+#undef _ext
+#undef _DO_INIT
#endif /* _PCPSMKTM_H */
diff --git a/mbglib/common/pcpsutil.c b/mbglib/common/pcpsutil.c
deleted file mode 100755
index d5fe621..0000000
--- a/mbglib/common/pcpsutil.c
+++ /dev/null
@@ -1,162 +0,0 @@
-
-/**************************************************************************
- *
- * $Id: pcpsutil.c 1.14 2011/06/29 11:03:44 martin REL_M $
- *
- * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
- *
- * Description:
- * Utility functions used with programs for Meinberg devices.
- *
- * -----------------------------------------------------------------------
- * $Log: pcpsutil.c $
- * Revision 1.14 2011/06/29 11:03:44 martin
- * Updated a comment.
- * Revision 1.13 2009/03/09 13:39:45 martin
- * Made pcps_exp_year() an inline function.
- * Revision 1.12 2008/12/10 19:59:48 martin
- * Made frac_sec_from_bin() an inline function.
- * Revision 1.11 2008/11/25 10:00:25 martin
- * Use new definitions of fraction conversion type and scale
- * from pcpsdefs.h.
- * Revision 1.10 2006/06/29 10:38:24Z martin
- * New function pcps_time_is_valid().
- * Modified pcps_str_to_port(), doesn't add a 0 entry to the list anymore.
- * Fixed a compiler warning related to type conversion.
- * Revision 1.9 2005/01/14 10:14:31Z martin
- * Changed type of ISA port addr to int.
- * Revision 1.8 2004/11/09 14:29:27Z martin
- * Rewrote functions using C99 fixed-size definitions.
- * Revision 1.7 2003/04/17 10:08:59Z martin
- * Added some type casts to fix compiler warnings.
- * Revision 1.6 2001/11/28 14:39:16Z MARTIN
- * In frac_sec_from_bin(), define the divisor as floating point
- * constant to avoid a domain errors on 16 bit systems.
- * Revision 1.5 2001/09/17 07:28:01 MARTIN
- * New function frac_sec_from_bin() to convert
- * PCPS_HR_TIME fractions.
- * Revision 1.4 2001/03/01 14:01:09 MARTIN
- * Modified parameters for pcps_setup_isa_ports().
- * Revision 1.3 2000/08/31 14:05:30 MARTIN
- * Replaced pcps_str_to_port() by pcps_setup_isa_ports().
- * Revision 1.2 2000/07/21 13:42:54 MARTIN
- * Initial revision
- *
- **************************************************************************/
-
-#define _PCPSUTIL
- #include <pcpsutil.h>
-#undef _PCPSUTIL
-
-#include <stdlib.h>
-
-
-/*--------------------------------------------------------------
- * Name: pcps_time_is_valid()
- *
- * Purpose: Pack a structure with serial port parameters
- *
- * Input/Output: p address of a structure holding both the
- * packed and unpacked information
- *
- * Ret value: --
- *-------------------------------------------------------------*/
-
-/*HDR*/
-int pcps_time_is_valid( const PCPS_TIME *p )
-{
- return ( p->sec100 <= 99 )
- && ( p->sec <= 60 ) /* allow for leap second */
- && ( p->min <= 59 )
- && ( p->hour <= 23 )
- && ( p->mday >= 1 ) && ( p->mday <= 31 )
- && ( p->wday >= 1 ) && ( p->wday <= 7 )
- && ( p->month >= 1 ) && ( p->month <= 12 )
- && ( p->year <= 99 );
-
-} /* pcps_time_is_valid */
-
-
-
-/*--------------------------------------------------------------
- * Name: pcps_str_to_port()
- *
- * Purpose: Try to convert a string to a valid port
- * address.
- *
- * Input: s the string
- *
- * Output: --
- *
- * Ret value: a valid port number or 0
- *+-------------------------------------------------------------*/
-
-/*HDR*/
-void pcps_setup_isa_ports( char *s,
- int *port_vals,
- int n_vals )
-{
- ushort i;
-
-
- for ( i = 0; i < n_vals; i++ )
- {
- if ( *s == 0 )
- break;
-
- *port_vals++ = (uint16_t) strtoul( s, &s, 16 );
-
- if ( *s == ',' )
- s++;
- }
-
-} // pcps_setup_isa_ports
-
-
-
-/*--------------------------------------------------------------
- * Name: pcps_unpack_serial()
- *
- * Purpose: Unpack a structure with serial port parameters
- *
- * Input/Output: p address of a structure holding both the
- * packed and unpacked information
- *
- * Ret value: --
- *-------------------------------------------------------------*/
-
-/*HDR*/
-void pcps_unpack_serial( PCPS_SER_PACK *p )
-{
- uint8_t pack = p->pack;
-
- p->baud = (uint8_t) ( pack & BITMASK( PCPS_BD_BITS ) );
- p->frame = (uint8_t) ( ( pack >> PCPS_FR_SHIFT ) & BITMASK( PCPS_FR_BITS ) );
- p->mode = (uint8_t) ( ( pack >> PCPS_MOD_SHIFT ) & BITMASK( PCPS_MOD_BITS ) );
-
-} // pcps_unpack_serial
-
-
-
-/*--------------------------------------------------------------
- * Name: pcps_pack_serial()
- *
- * Purpose: Pack a structure with serial port parameters
- *
- * Input/Output: p address of a structure holding both the
- * packed and unpacked information
- *
- * Ret value: --
- *-------------------------------------------------------------*/
-
-/*HDR*/
-void pcps_pack_serial( PCPS_SER_PACK *p )
-{
- p->pack = (uint8_t) ( ( p->baud & BITMASK( PCPS_BD_BITS ) )
- | ( ( p->frame & BITMASK( PCPS_FR_BITS ) ) << PCPS_FR_SHIFT )
- | ( ( p->mode & BITMASK( PCPS_MOD_BITS ) ) << PCPS_MOD_SHIFT ) );
-
-} /* pcps_pack_serial */
-
-
-
diff --git a/mbglib/common/pcpsutil.h b/mbglib/common/pcpsutil.h
index 7bb0c28..c65bd6b 100755
--- a/mbglib/common/pcpsutil.h
+++ b/mbglib/common/pcpsutil.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: pcpsutil.h 1.16 2013/03/04 15:51:02 martin REL_M $
+ * $Id: pcpsutil.h 1.22 2017/03/17 11:45:51 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,7 +10,22 @@
*
* -----------------------------------------------------------------------
* $Log: pcpsutil.h $
- * Revision 1.16 2013/03/04 15:51:02 martin
+ * Revision 1.22 2017/03/17 11:45:51 martin
+ * Moved binary fraction conversion functions to cfg_hlp.h.
+ * Revision 1.21 2015/10/26 16:09:58 martin
+ * Moved definition of PCPS_SER_PACK to deviohlp.h.
+ * The .c file is now obsolete, so there are no prototypes anymore.
+ * Revision 1.20 2014/07/22 12:22:27Z martin
+ * Fixed a compiler warning.
+ * Revision 1.19 2014/07/14 15:43:23Z martin
+ * Updated doxygen comment.
+ * Revision 1.18 2014/06/26 14:52:50 martin
+ * Fixed build on targets not supporting 64 bit types.
+ * Updated some comments to doxygen format.
+ * Revision 1.17 2014/05/27 10:39:33Z martin
+ * More inline functions to convert binary fractions by thomas-b.
+ * Moved definitions of some signal constants to pcpsdefs.h.
+ * Revision 1.16 2013/03/04 15:51:02Z martin
* Added dfrac_sec_from_bin().
* Revision 1.15 2012/10/15 09:41:32 martin
* Cleaned up handling of pragma pack().
@@ -73,43 +88,18 @@
#endif
-// The following constants are used to draw a signal bar
-// depending on a DCF77 clock's signal value:
-#define PCPS_SIG_BIAS 55
-#define PCPS_SIG_ERR 1
-#define PCPS_SIG_MIN 20
-#define PCPS_SIG_MAX 68
-
-// the structure below is used with a DCF77 clock's serial interface
-typedef struct
-{
- PCPS_SERIAL pack; // this byte is passed to the board as parameter
-
- uint8_t baud; // the other bytes can hold the unpacked values
- uint8_t frame;
- uint8_t mode;
-
-} PCPS_SER_PACK;
-
-
-
-/*--------------------------------------------------------------
- * Name: pcps_exp_year()
+/**
+ * @brief Expand a 2-digit year number to a 4-digit year number
*
- * Purpose: Convert a 2-digit year number to a 4-digit
- * year number. The resulting year number is in
- * the range [year_lim ... ( year_lim + 99 )].
+ * The resulting year number includes the century and is
+ * in the range [year_lim ... ( year_lim + 99 )].
*
- * Input: year the 2-digit year number
- * year_lim the smallest 4-digit year number
- * to be returned
+ * @param[in] year The 2-digit year number to be converted
+ * @param[in] year_lim The smallest 4-digit year number to be returned
*
- * Output: --
- *
- * Ret value: the calculated 4-digit year num
- *+-------------------------------------------------------------*/
-
+ * @return The resulting 4 digit year number including century
+ */
static __mbg_inline
uint16_t pcps_exp_year( uint8_t year, uint16_t year_lim )
{
@@ -136,10 +126,7 @@ extern "C" {
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
- int pcps_time_is_valid( const PCPS_TIME *p ) ;
- void pcps_setup_isa_ports( char *s, int *port_vals, int n_vals ) ;
- void pcps_unpack_serial( PCPS_SER_PACK *p ) ;
- void pcps_pack_serial( PCPS_SER_PACK *p ) ;
+/* (no header definitions found) */
/* ----- function prototypes end ----- */
@@ -148,42 +135,6 @@ extern "C" {
#endif
-/*--------------------------------------------------------------
- * Name: frac_sec_from_bin()
- *
- * Purpose: Convert a fraction of a second from binary
- * format (as returned in a PCPS_HR_TIME structure
- * to a decimal fraction, using a specified scale
- * factor. See also the definitions of
- * PCPS_HRT_FRAC_SCALE and PCPS_HRT_FRAC_SCALE_FMT
- * in the header file.
- *
- * Input: b the binary fraction
- * scale the scale factor
- *
- * Output: --
- *
- * Ret value: the calculated number
- *+-------------------------------------------------------------*/
-
-static __mbg_inline
-uint32_t frac_sec_from_bin( uint32_t b, uint32_t scale )
-{
- return (uint32_t) ( (PCPS_HRT_FRAC_CONVERSION_TYPE) b * scale
- / PCPS_HRT_BIN_FRAC_SCALE );
-
-} // frac_sec_from_bin
-
-
-
-static __mbg_inline
-double dfrac_sec_from_bin( uint32_t b )
-{
- return (double) b / (double) PCPS_HRT_BIN_FRAC_SCALE;
-
-} // dfrac_sec_from_bin
-
-
#if defined( _USING_BYTE_ALIGNMENT )
#pragma pack() // set default alignment
diff --git a/mbglib/common/ptp_util.h b/mbglib/common/ptp_util.h
new file mode 100755
index 0000000..d8fa556
--- /dev/null
+++ b/mbglib/common/ptp_util.h
@@ -0,0 +1,190 @@
+
+/**************************************************************************
+ *
+ * $Id: ptp_util.h 1.5 2017/04/25 12:54:21 gregoire.diehl TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Definitions and prototypes for ptp_util.c.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: ptp_util.h $
+ * Revision 1.5 2017/04/25 12:54:21 gregoire.diehl
+ * Merge changes from 1.3.1.7 & 1.4
+ * Revision 1.4 2016/11/10 09:05:26Z martin
+ * Support for PTP Time Monitor role added by udo.
+ * Support for NTP modes added by daniel.
+ * Updated some comments.
+ * Revision 1.3 2013/09/12 11:05:44 martin
+ * Added inline function get_supp_ptp_role_mask().
+ * Revision 1.2 2013/08/06 12:08:06 udo
+ * new ptp_clock_id_from_str()
+ * Revision 1.1 2011/11/14 16:03:39 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#ifndef _PTP_UTIL_H
+#define _PTP_UTIL_H
+
+
+/* Other headers to be included */
+#include <stdio.h>
+#include <lan_util.h>
+#include <gpsdefs.h>
+
+
+#ifdef _PTP_UTIL
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#if defined( _USE_PACK )
+ #pragma pack( 1 ) // set byte alignment
+ #define _USING_BYTE_ALIGNMENT
+#endif
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+/**
+ * @brief Derive a "supported PTP roles" bit mask from ::PTP_CFG_INFO::supp_flags
+ *
+ * The relevant bits used with ::PTP_CFG_INFO::supp_flags have not been
+ * defined sequentially, so we need to test them individually to put a
+ * supported roles bit mask together.
+ *
+ * @note Originally, all devices supported the multicast slave role, so
+ * there was no extra flag to indicate this. However, some newer devices
+ * may not support the multicast slave role, so two new flags have been
+ * introduced to cope with this:<br>
+ * If ::PTP_CFG_SUPP_MCAST_SLAVE_FLAG is set then a different flag
+ * ::PTP_CFG_CAN_BE_MULTICAST_SLAVE needs to be checked to tell if
+ * the multicast slave role is supported, or not.<br>
+ * If ::PTP_CFG_SUPP_MCAST_SLAVE_FLAG is not set then the device
+ * definitely supports the multicast slave role.
+ *
+ * @param flags bit mask from ::PTP_CFG_INFO::supp_flags, see @ref PTP_CFG_FLAG_MASKS
+ *
+ * @return bit mask of supported PTP roles, see ::PTP_ROLE_MASKS
+ */
+static __mbg_inline
+uint32_t get_supp_ptp_role_mask( uint32_t flags )
+{
+ uint32_t role_mask = 0;
+
+ if ( flags & PTP_CFG_MSK_SUPP_MCAST_SLAVE_FLAG )
+ {
+ // multicast slave role is only supported
+ // if a different flag is also set
+ if ( flags & PTP_CFG_MSK_CAN_BE_MULTICAST_SLAVE )
+ role_mask |= PTP_ROLE_MSK_MULTICAST_SLAVE;
+ }
+ else // multicast slave role is definitely supported
+ role_mask |= PTP_ROLE_MSK_MULTICAST_SLAVE;
+
+ if ( flags & PTP_CFG_MSK_CAN_BE_UNICAST_SLAVE )
+ role_mask |= PTP_ROLE_MSK_UNICAST_SLAVE;
+
+ if ( flags & PTP_CFG_MSK_CAN_BE_MULTICAST_MASTER )
+ role_mask |= PTP_ROLE_MSK_MULTICAST_MASTER;
+
+ if ( flags & PTP_CFG_MSK_CAN_BE_UNICAST_MASTER )
+ role_mask |= PTP_ROLE_MSK_UNICAST_MASTER;
+
+ if ( flags & PTP_CFG_MSK_CAN_BE_MULTICAST_AUTO )
+ role_mask |= PTP_ROLE_MSK_MULTICAST_AUTO;
+
+ if ( flags & PTP_CFG_MSK_CAN_BE_BOTH_MASTER )
+ role_mask |= PTP_ROLE_MSK_BOTH_MASTER;
+
+ if ( flags & PTP_CFG_MSK_NTP_HW_TS_MASTER )
+ role_mask |= PTP_ROLE_MSK_NTP_SERVER;
+
+ if ( flags & PTP_CFG_MSK_NTP_HW_TS_SLAVE )
+ role_mask |= PTP_ROLE_MSK_NTP_CLIENT;
+
+ if ( flags & PTP_CFG_MSK_CAN_BE_TIME_MONITOR )
+ role_mask |= PTP_ROLE_MSK_TIME_MONITOR;
+
+ if ( flags & PTP_CFG_MSK_CAN_BE_V1_MASTER )
+ role_mask |= PTP_ROLE_MSK_V1_MASTER;
+
+ if ( flags & PTP_CFG_MSK_CAN_BE_V1_SLAVE )
+ role_mask |= PTP_ROLE_MSK_V1_SLAVE;
+
+ return role_mask;
+
+} // get_supp_ptp_role_mask
+
+
+
+/* function prototypes: */
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+ /**
+ * @brief Get the MAC addr from a PTP clock ID
+ *
+ * The clock ID is usually the MAC ID with 2 octets
+ * 0xFF and 0xFE inserted in the middle.
+ *
+ * @param p_mac_addr The MAC ID to be filled up
+ * @param p_clock_id The PTP clock ID
+ */
+ void mac_from_ptp_clock_id( MBG_MAC_ADDR *p_mac_addr, const PTP_CLOCK_ID *p_clock_id ) ;
+
+ /**
+ * @brief Get the PTP clock ID from the MAC addr
+ *
+ * The clock ID is usually the MAC ID with 2 octets
+ * 0xFF and 0xFE inserted in the middle.
+ *
+ * @param p_clock_id The PTP clock ID
+ * @param p_mac_addr The MAC ID to be filled up
+ */
+ void ptp_clock_id_from_mac( PTP_CLOCK_ID *p_clock_id, const MBG_MAC_ADDR *p_mac_addr ) ;
+
+ /**
+ * @brief Get the PTP clock ID from a string
+ *
+ * The clock ID is usually the MAC ID with 2 octets
+ * 0xFF and 0xFE inserted in the middle.
+ *
+ * @param p_clock_id The PTP clock ID
+ * @param p_str The UUID as string with format e.g. 0050C2FFFED287DE
+ */
+ void ptp_clock_id_from_str( PTP_CLOCK_ID *p_clock_id, const char *p_str ) ;
+
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+
+#if defined( _USING_BYTE_ALIGNMENT )
+ #pragma pack() // set default alignment
+ #undef _USING_BYTE_ALIGNMENT
+#endif
+
+/* End of header body */
+
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _PTP_UTIL_H */
+
diff --git a/mbglib/common/str_util.c b/mbglib/common/str_util.c
new file mode 100755
index 0000000..c3c89cb
--- /dev/null
+++ b/mbglib/common/str_util.c
@@ -0,0 +1,449 @@
+
+/**************************************************************************
+ *
+ * $Id: str_util.c 1.3 2016/10/24 08:10:04 thomas-b REL_M $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Meinberg Library module providing portable, safe string functions.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: str_util.c $
+ * Revision 1.3 2016/10/24 08:10:04 thomas-b
+ * Fixed counter var check in mbg_memcpy_reversed
+ * Revision 1.2 2016/08/05 12:31:04 martin
+ * New functions mbg_memcpy() and mbg_memcpy_reversed().
+ * Moved string trim functions from cfg_util module here.
+ * Fixed some compiler warnings.
+ * Revision 1.1 2015/08/25 15:57:21 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#define _STR_UTIL
+ #include <str_util.h>
+#undef _STR_UTIL
+
+#include <stdio.h>
+#include <string.h>
+
+
+#if defined( MBG_TGT_WIN32 ) && !defined( MBG_TGT_CVI )
+ #define mbg_vsnprintf _vsnprintf
+#else
+ #define mbg_vsnprintf vsnprintf
+#endif
+
+
+#if defined( MBG_TGT_DOS )
+
+static /*HDR*/
+// Under DOS we use the Borland C/C++ v3.1 compiler by default, which
+// doesn't provide a vsnprintf() function, so we use a simple replacement
+// here. Since we share most of the source code between several target
+// systems we assume that if it our code works properly for other targets
+// which really provide a vsnprintf() function then it also works properly
+// under DOS. ;-)
+int vsnprintf( char *s, size_t max_len, const char *fmt, va_list arg_list )
+{
+ (void) max_len; // quiet compiler warning "not used"
+
+ return vsprintf( s, fmt, arg_list );
+
+} // vsnprintf
+
+#endif
+
+
+
+/*HDR*/
+/**
+ * @brief A portable, safe implementation of vsnprintf()
+ *
+ * Unfortunately the behaviour of vsnprintf() and thus snprintf()
+ * differs in detail across various build environments and run time
+ * libraries.
+ *
+ * If the output exceeds the buffer size and thus is truncated then:<br>
+ *
+ * - Under Windows a negative value is returned and eventually *no*
+ * terminating 0 is written to the output buffer, so the output string
+ * may not be terminated properly.
+ *
+ * - Some versions of glibc return the number of bytes that *would*
+ * have been written to the buffer *if* the buffer would have been
+ * large enough, instead of the true number of characters that have
+ * been written to the buffer.
+ *
+ * So subsequent calls like
+ *
+ * n = snprintf( s, max_len, ... );
+ * n += snprintf( &s[n], max_len - n, ... );
+ *
+ * may always work properly, or fail with buffer overruns or stack
+ * corruption depending on the build environment.
+ * This wrapper function takes care that strings are always terminated
+ * properly, and that the returned value always matches the number of
+ * characters really written to the string buffer, excluding the
+ * terminating 0
+ *
+ * @note The "size_t" type parameter used to specify the buffer size
+ * can be larger (e.g. "unsigned long") than the "int" type returned
+ * by mostly all functions of the printf() family. So if a very large
+ * buffer is specified, and a large number of characters (more than
+ * MAXINT) are written to that buffer then how can an "int" type
+ * return the large number of characters written to the buffer?
+ * We also try to workaround this here.
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] fmt Format string according to subsequent parameters
+ * @param[in] ap Variable argument list in va_list format
+ *
+ * @return Number of characters written to the output buffer, except the terminating 0
+ *
+ * @see ::snprintf_safe
+ * @see ::strncpy_safe
+ * @see ::sn_cpy_str_safe
+ * @see ::sn_cpy_char_safe
+ */
+size_t __attribute__( ( format( printf, 3, 0 ) ) )
+vsnprintf_safe( char *s, size_t max_len, const char *fmt, va_list ap )
+{
+ if ( s == NULL || max_len == 0 )
+ return 0; // nothing to do anyway
+
+
+ mbg_vsnprintf( s, max_len, fmt, ap );
+
+ // Force proper worst-case termination of the output string.
+ s[max_len - 1] = 0;
+
+ // The return type of strlen() is usually size_t, so
+ // we can safely return the true length of the string
+ // written to the buffer.
+ return strlen( s );
+
+} // vsnprintf_safe
+
+
+
+/*HDR*/
+/**
+ * @brief A portable, safe implementation of snprintf()
+ *
+ * For a detailed description see ::vsnprintf_safe
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] fmt Format string according to subsequent parameters
+ * @param[in] ... Variable argument list according to the format string
+ *
+ * @return Number of characters written to the output buffer, except the terminating 0
+ *
+ * @see ::vsnprintf_safe
+ * @see ::strncpy_safe
+ * @see ::sn_cpy_str_safe
+ * @see ::sn_cpy_char_safe
+ */
+size_t __attribute__( ( format( printf, 3, 4 ) ) )
+snprintf_safe( char *s, size_t max_len, const char * fmt, ... )
+{
+ va_list ap;
+ size_t len;
+
+ va_start( ap, fmt );
+
+ len = vsnprintf_safe( s, max_len, fmt, ap );
+
+ va_end( ap );
+
+ return len;
+
+} // snprintf_safe
+
+
+
+static __mbg_inline
+/* (explicitly excluded from doxygen)
+ * @brief A portable, safe implementation of a copy function
+ *
+ * This is the basic function used to implemment ::strncpy_safe and
+ * ::sn_cpy_safe. This function takes care that the copied string
+ * is always terminated by 0, but any remaining buffer space
+ * is *not* filled up with '0' characters.
+ *
+ * @param[out] dst Pointer to the output buffer
+ * @param[in] src Pointer to the input buffer
+ * @param[in] n Number of characters to copy at most
+ * @param[in,out] p_i Pointer to a counter variable
+ *
+ * @see ::vsnprintf_safe
+ * @see ::snprintf_safe
+ * @see ::strncpy_safe
+ * @see ::sn_cpy_str_safe
+ * @see ::sn_cpy_char_safe
+ */
+void do_str_copy_safe( char *dst, const char *src, size_t n, size_t *p_i )
+{
+ *p_i = 0;
+
+ if ( n > 0 )
+ {
+ for (;;)
+ {
+ *dst = *src;
+
+ if ( *dst == 0 )
+ break; // just copied the terminating 0, done
+
+ if ( --n == 0 ) // no more space left in buffer
+ {
+ *dst = 0; // force terminating 0
+ break;
+ }
+
+ (*p_i)++; // count normal characters
+ src++;
+ dst++;
+ }
+ }
+
+} // do_str_copy_safe
+
+
+
+/*HDR*/
+/**
+ * @brief A portable, safe implementation of strncpy()
+ *
+ * In the original implementation of strncpy(), if the length of the
+ * string to be copied into the destination buffer exceeds the specified
+ * buffer length then the string in the output buffer is not 0-terminated.
+ *
+ * Our implementation always forces a proper termination by 0, but unlike
+ * the original implementation of strncpy() it does *not* fill the whole
+ * remaining buffer space with '0' characters.
+ *
+ * @param[out] dst Pointer to the output buffer
+ * @param[in] src Pointer to the input buffer
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ *
+ * @return Pointer to the destination buffer
+ *
+ * @see ::vsnprintf_safe
+ * @see ::snprintf_safe
+ * @see ::sn_cpy_str_safe
+ * @see ::sn_cpy_char_safe
+ */
+char *strncpy_safe( char *dst, const char *src, size_t max_len )
+{
+ size_t i = 0;
+
+ do_str_copy_safe( dst, src, max_len, &i );
+
+ return dst;
+
+} // strncpy_safe
+
+
+
+/*HDR*/
+/**
+ * @brief A function to copy a string safely, returning the number of characters copied
+ *
+ * This basically works like ::strncpy_safe but instead of a pointer to
+ * the destination buffer it returns the number of characters copied
+ * to the destination buffer.
+ *
+ * @param[out] dst Pointer to the output buffer
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] src Pointer to the input buffer
+ *
+ * @return Number of characters copied to the destination buffer
+ *
+ * @see ::vsnprintf_safe
+ * @see ::snprintf_safe
+ * @see ::strncpy_safe
+ * @see ::sn_cpy_char_safe
+ */
+size_t sn_cpy_str_safe( char *dst, size_t max_len, const char *src )
+{
+ size_t i = 0;
+
+ do_str_copy_safe( dst, src, max_len, &i );
+
+ return i;
+
+} // sn_cpy_str_safe
+
+
+
+/*HDR*/
+/**
+ * @brief A function to copy a character safely to a string buffer
+ *
+ * This basically works like ::sn_cpy_str_safe but expects a character
+ * to be copied to the destination buffer. Appends a terminating 0 to
+ * the string buffer and returns the number of characters copied to
+ * the destination buffer, usually 0 or 1.
+ *
+ * @param[out] dst Pointer to the output buffer
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] c Character to be copied to the destination buffer
+ *
+ * @return Number of characters copied to the destination buffer, without the terminating 0
+ *
+ * @see ::vsnprintf_safe
+ * @see ::snprintf_safe
+ * @see ::strncpy_safe
+ * @see ::sn_cpy_str_safe
+ */
+size_t sn_cpy_char_safe( char *dst, size_t max_len, char c )
+{
+ size_t i = 0;
+ char tmp_str[2];
+
+ tmp_str[0] = c;
+ tmp_str[1] = 0;
+
+ do_str_copy_safe( dst, tmp_str, max_len, &i );
+
+ return i;
+
+} // sn_cpy_char_safe
+
+
+
+/*HDR*/
+/**
+ * @brief Trim whitespace at the end of a string
+ *
+ * @param[in,out] s The string to be trimmed
+ */
+void trim_trailing_whitespace( char *s )
+{
+ char *cp;
+
+ // set all trailing spaces to 0
+ for ( cp = &s[strlen( s )]; cp > s; )
+ {
+ --cp;
+
+ if ( *cp >= ' ' )
+ break;
+
+ *cp = 0;
+ }
+
+} // trim_trailing_whitespace
+
+
+
+/*HDR*/
+/**
+ * @brief Trim whitespace at the beginning of a string
+ *
+ * @param[in,out] s The string to be trimmed
+ */
+void trim_leading_whitespace( char *s )
+{
+ char *srcp;
+ char *dstp;
+
+ // Search the first non-space character.
+ for ( srcp = s; *srcp; srcp++ )
+ if ( *srcp > ' ' )
+ break;
+
+ // If there are leading spaces then srcp now
+ // points behind the beginning of the string,
+ // otherwise there's nothing to do.
+ if ( srcp > s )
+ {
+ // Copy the remaining string.
+ dstp = s;
+
+ while ( *srcp )
+ *dstp++ = *srcp++;
+
+ *dstp = 0;
+ }
+
+} // trim_leading_whitespace
+
+
+
+/*HDR*/
+/**
+ * @brief Trim both leading and trailing whitespace from a string
+ *
+ * @param[in,out] s The string to be trimmed
+ */
+void trim_whitespace( char *s )
+{
+ trim_trailing_whitespace( s );
+ trim_leading_whitespace( s );
+
+} // trim_whitespace
+
+
+
+/*HDR*/
+/**
+ * @brief Copy array of bytes starting at beginning of buffer
+ *
+ * Can be used if the destination address is in the same buffer
+ * in front of the source address. Even though you would expect
+ * that memcpy() would also work for this properly, we have seen
+ * cases where it didn't, and only memmove() worked correctly.
+ * Anyway, we try to avoid the overhead of memmove().
+ *
+ * @param[out] dst Destination address behind the source address
+ * @param[in] src Source address
+ * @param[in] n_bytes Number of bytes to copy
+ *
+ * @see ::mbg_memcpy_reversed
+ */
+void mbg_memcpy( void *dst, const void *src, size_t n_bytes )
+{
+ uint8_t *dstp = (uint8_t *) dst;
+ uint8_t *srcp = (uint8_t *) src;
+
+ while ( n_bytes-- )
+ *dstp++ = *srcp++;
+
+} // mbg_memcpy
+
+
+
+/*HDR*/
+/**
+ * @brief Copy an array of bytes in reversed order, starting at end of buffer
+ *
+ * Can be used if the destination address is in the same buffer
+ * behind the source address, so the source address would be
+ * overwritten by a normal memcpy().
+ *
+ * @param[out] dst Destination address behind the source address
+ * @param[in] src Source address
+ * @param[in] n_bytes Number of bytes to copy
+ *
+ * @see ::mbg_memcpy
+ */
+void mbg_memcpy_reversed( void *dst, const void *src, size_t n_bytes )
+{
+ if ( n_bytes ) // just to be sure it isn't 0
+ {
+ uint8_t *dstp = ( (uint8_t *) dst ) + n_bytes;
+ uint8_t *srcp = ( (uint8_t *) src ) + n_bytes;
+
+ while ( n_bytes-- )
+ *(--dstp) = *(--srcp);
+ }
+
+} // mbg_memcpy_reversed
+
+
+
diff --git a/mbglib/common/str_util.h b/mbglib/common/str_util.h
new file mode 100755
index 0000000..02f5b35
--- /dev/null
+++ b/mbglib/common/str_util.h
@@ -0,0 +1,269 @@
+
+/**************************************************************************
+ *
+ * $Id: str_util.h 1.3 2016/12/14 16:22:24 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Definitions and prototypes for str_util.c
+ *
+ * -----------------------------------------------------------------------
+ * $Log: str_util.h $
+ * Revision 1.3 2016/12/14 16:22:24 martin
+ * Added macro _sn_cpy_str_safe() to simplify calls.
+ * Revision 1.2 2016/08/05 12:33:17 martin
+ * Moved string trim functions from cfg_util module here.
+ * Added variable str_not_avail.
+ * Fixed some spelling.
+ * Updated function prototypes.
+ * Revision 1.1 2015/08/25 15:57:43 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#ifndef _STR_UTIL_H
+#define _STR_UTIL_H
+
+/* Other headers to be included */
+
+#include <words.h> // implicitly includes mbg_tgt.h for non-firmware projects
+
+#include <stdlib.h>
+#include <stdarg.h>
+
+
+#ifdef _STR_UTIL
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+_ext const char *str_not_avail
+#ifdef _DO_INIT
+ = "N/A"
+#endif
+;
+
+#define _sn_cpy_str_safe( _dst, _src ) sn_cpy_str_safe( _dst, sizeof( _dst ), _src )
+
+
+/* function prototypes: */
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+ /**
+ * @brief A portable, safe implementation of vsnprintf()
+ *
+ * Unfortunately the behaviour of vsnprintf() and thus snprintf()
+ * differs in detail across various build environments and run time
+ * libraries.
+ *
+ * If the output exceeds the buffer size and thus is truncated then:<br>
+ *
+ * - Under Windows a negative value is returned and eventually *no*
+ * terminating 0 is written to the output buffer, so the output string
+ * may not be terminated properly.
+ *
+ * - Some versions of glibc return the number of bytes that *would*
+ * have been written to the buffer *if* the buffer would have been
+ * large enough, instead of the true number of characters that have
+ * been written to the buffer.
+ *
+ * So subsequent calls like
+ *
+ * n = snprintf( s, max_len, ... );
+ * n += snprintf( &s[n], max_len - n, ... );
+ *
+ * may always work properly, or fail with buffer overruns or stack
+ * corruption depending on the build environment.
+ * This wrapper function takes care that strings are always terminated
+ * properly, and that the returned value always matches the number of
+ * characters really written to the string buffer, excluding the
+ * terminating 0
+ *
+ * @note The "size_t" type parameter used to specify the buffer size
+ * can be larger (e.g. "unsigned long") than the "int" type returned
+ * by mostly all functions of the printf() family. So if a very large
+ * buffer is specified, and a large number of characters (more than
+ * MAXINT) are written to that buffer then how can an "int" type
+ * return the large number of characters written to the buffer?
+ * We also try to workaround this here.
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] fmt Format string according to subsequent parameters
+ * @param[in] ap Variable argument list in va_list format
+ *
+ * @return Number of characters written to the output buffer, except the terminating 0
+ *
+ * @see ::snprintf_safe
+ * @see ::strncpy_safe
+ * @see ::sn_cpy_str_safe
+ * @see ::sn_cpy_char_safe
+ */
+ size_t __attribute__( ( format( printf, 3, 0 ) ) ) vsnprintf_safe( char *s, size_t max_len, const char *fmt, va_list ap ) ;
+
+ /**
+ * @brief A portable, safe implementation of snprintf()
+ *
+ * For a detailed description see ::vsnprintf_safe
+ *
+ * @param[out] s The string buffer to be filled
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] fmt Format string according to subsequent parameters
+ * @param[in] ... Variable argument list according to the format string
+ *
+ * @return Number of characters written to the output buffer, except the terminating 0
+ *
+ * @see ::vsnprintf_safe
+ * @see ::strncpy_safe
+ * @see ::sn_cpy_str_safe
+ * @see ::sn_cpy_char_safe
+ */
+ size_t __attribute__( ( format( printf, 3, 4 ) ) ) snprintf_safe( char *s, size_t max_len, const char * fmt, ... ) ;
+
+ /**
+ * @brief A portable, safe implementation of strncpy()
+ *
+ * In the original implementation of strncpy(), if the length of the
+ * string to be copied into the destination buffer exceeds the specified
+ * buffer length then the string in the output buffer is not 0-terminated.
+ *
+ * Our implementation always forces a proper termination by 0, but unlike
+ * the original implementation of strncpy() it does *not* fill the whole
+ * remaining buffer space with '0' characters.
+ *
+ * @param[out] dst Pointer to the output buffer
+ * @param[in] src Pointer to the input buffer
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ *
+ * @return Pointer to the destination buffer
+ *
+ * @see ::vsnprintf_safe
+ * @see ::snprintf_safe
+ * @see ::sn_cpy_str_safe
+ * @see ::sn_cpy_char_safe
+ */
+ char *strncpy_safe( char *dst, const char *src, size_t max_len ) ;
+
+ /**
+ * @brief A function to copy a string safely, returning the number of characters copied
+ *
+ * This basically works like ::strncpy_safe but instead of a pointer to
+ * the destination buffer it returns the number of characters copied
+ * to the destination buffer.
+ *
+ * @param[out] dst Pointer to the output buffer
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] src Pointer to the input buffer
+ *
+ * @return Number of characters copied to the destination buffer
+ *
+ * @see ::vsnprintf_safe
+ * @see ::snprintf_safe
+ * @see ::strncpy_safe
+ * @see ::sn_cpy_char_safe
+ */
+ size_t sn_cpy_str_safe( char *dst, size_t max_len, const char *src ) ;
+
+ /**
+ * @brief A function to copy a character safely to a string buffer
+ *
+ * This basically works like ::sn_cpy_str_safe but expects a character
+ * to be copied to the destination buffer. Appends a terminating 0 to
+ * the string buffer and returns the number of characters copied to
+ * the destination buffer, usually 0 or 1.
+ *
+ * @param[out] dst Pointer to the output buffer
+ * @param[in] max_len Size of the output buffer for 0-terminated string
+ * @param[in] c Character to be copied to the destination buffer
+ *
+ * @return Number of characters copied to the destination buffer, without the terminating 0
+ *
+ * @see ::vsnprintf_safe
+ * @see ::snprintf_safe
+ * @see ::strncpy_safe
+ * @see ::sn_cpy_str_safe
+ */
+ size_t sn_cpy_char_safe( char *dst, size_t max_len, char c ) ;
+
+ /**
+ * @brief Trim whitespace at the end of a string
+ *
+ * @param[in,out] s The string to be trimmed
+ */
+ void trim_trailing_whitespace( char *s ) ;
+
+ /**
+ * @brief Trim whitespace at the beginning of a string
+ *
+ * @param[in,out] s The string to be trimmed
+ */
+ void trim_leading_whitespace( char *s ) ;
+
+ /**
+ * @brief Trim both leading and trailing whitespace from a string
+ *
+ * @param[in,out] s The string to be trimmed
+ */
+ void trim_whitespace( char *s ) ;
+
+ /**
+ * @brief Copy array of bytes starting at beginning of buffer
+ *
+ * Can be used if the destination address is in the same buffer
+ * in front of the source address. Even though you would expect
+ * that memcpy() would also work for this properly, we have seen
+ * cases where it didn't, and only memmove() worked correctly.
+ * Anyway, we try to avoid the overhead of memmove().
+ *
+ * @param[out] dst Destination address behind the source address
+ * @param[in] src Source address
+ * @param[in] n_bytes Number of bytes to copy
+ *
+ * @see ::mbg_memcpy_reversed
+ */
+ void mbg_memcpy( void *dst, const void *src, size_t n_bytes ) ;
+
+ /**
+ * @brief Copy an array of bytes in reversed order, starting at end of buffer
+ *
+ * Can be used if the destination address is in the same buffer
+ * behind the source address, so the source address would be
+ * overwritten by a normal memcpy().
+ *
+ * @param[out] dst Destination address behind the source address
+ * @param[in] src Source address
+ * @param[in] n_bytes Number of bytes to copy
+ *
+ * @see ::mbg_memcpy
+ */
+ void mbg_memcpy_reversed( void *dst, const void *src, size_t n_bytes ) ;
+
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+
+/* End of header body */
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _STR_UTIL_H */
diff --git a/mbglib/common/timeutil.c b/mbglib/common/timeutil.c
new file mode 100755
index 0000000..37b29e0
--- /dev/null
+++ b/mbglib/common/timeutil.c
@@ -0,0 +1,172 @@
+
+/**************************************************************************
+ *
+ * $Id: timeutil.c 1.1.1.5 2017/04/10 12:37:46 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Meinberg Library module for safe time conversion routines.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: timeutil.c $
+ * Revision 1.1.1.5 2017/04/10 12:37:46 martin
+ * Fixed some compiler warnings.
+ * Revision 1.1.1.4 2017/02/06 11:45:57Z martin
+ * Fixed build under Windows, and implemented mbg_clock_settime(),
+ * but system time is actually not yet set.
+ * Revision 1.1.1.3 2016/11/21 15:22:37Z martin
+ * Revision 1.1.1.2 2016/08/11 15:09:46Z martin
+ * *** empty log message ***
+ * Revision 1.1.1.1 2016/08/11 07:54:40 martin
+ * Fixed build with old Visual Studio.
+ * Revision 1.1 2016/07/15 14:14:19Z martin
+ * Initial revision
+ *
+ **************************************************************************/
+
+#define _TIMEUTIL
+ #include <timeutil.h>
+#undef _TIMEUTIL
+
+#include <str_util.h>
+#include <mbgerror.h>
+
+#if defined( MBG_TGT_WIN32 )
+ #include <stdio.h>
+#endif
+
+
+
+/*HDR*/
+size_t snprint_gmtime_error( char *s, size_t max_len, int mbg_errno, time_t t, const char *calling_fnc )
+{
+ size_t n = snprintf_safe( s, max_len, "gmtime() call failed" );
+
+ if ( calling_fnc )
+ n += snprintf_safe( &s[n], max_len - n, " in %s", calling_fnc );
+
+ #if defined( _MSC_VER ) && ( _MSC_VER < 1500 )
+ //### TODO E.g. in VC6 time_t is only 32 bit anyway.
+ n += snprintf_safe( &s[n], max_len - n, " for time_t %lu: %s",
+ (unsigned long) t, mbg_strerror( mbg_errno ) );
+ #else
+ n += snprintf_safe( &s[n], max_len - n, " for time_t %llu: %s",
+ (unsigned long long) t, mbg_strerror( mbg_errno ) );
+ #endif
+
+ return n;
+
+} // snprint_gmtime_error
+
+
+
+#if defined( MBG_TGT_WIN32 )
+
+typedef int clockid_t;
+#define clockid_t clockid_t
+
+#define CLOCK_REALTIME ( (clockid_t) 0 )
+
+/*HDR*/
+int mbg_clock_gettime( clockid_t clock_id, struct timespec *tp )
+{
+ if ( clock_id == CLOCK_REALTIME )
+ {
+ #if defined( TIME_UTC ) // C11 / VS2015+
+ int rc = timespec_get( tp, TIME_UTC ); // TODO Check this code
+ return ( rc == 0 ) ? -1 : 0 // rc == 0 means error
+ #else
+ #define EPOCH_HNS 116444736000000000i64
+ #define NSEC_PER_SEC 1000000000i64
+ FILETIME ft;
+ unsigned __int64 tmp;
+ gstaft_fnc( &ft );
+ tmp = ( (__int64) ft.dwHighDateTime << 32 ) | ft.dwLowDateTime;
+ tmp -= EPOCH_HNS; // convert to Unix epoch
+ tmp *= 100; // convert to nanoseconds
+ tp->tv_sec = ( tmp / NSEC_PER_SEC );
+ tp->tv_nsec = ( tmp % NSEC_PER_SEC );
+ return 0;
+ #endif
+ }
+ else
+ return -1; // TODO this is e.g. in case of CLOCK_MONOTONIC, we could use QPC then.
+
+} // mbg_clock_gettime
+
+
+
+/*HDR*/
+int mbg_clock_settime( clockid_t clock_id, const struct timespec *tp )
+{
+ if ( clock_id == CLOCK_REALTIME )
+ {
+#if 0 // ### TODO FIXME This needs to be implemented.
+ #if defined( TIME_UTC ) // C11 / VS2015+
+ int rc = timespec_get( res, TIME_UTC ); // TODO Check this code
+ return ( rc == 0 ) ? -1 : 0 // rc == 0 means error
+ #else
+ #define EPOCH_HNS 116444736000000000i64
+ #define NSEC_PER_SEC 1000000000i64
+ FILETIME ft;
+ unsigned __int64 tmp;
+ gstaft_fnc( &ft );
+ tmp = ( (__int64) ft.dwHighDateTime << 32 ) | ft.dwLowDateTime;
+ tmp -= EPOCH_HNS; // convert to Unix epoch
+ tmp *= 100; // convert to nanoseconds
+ res->tv_sec = ( tmp / NSEC_PER_SEC );
+ res->tv_nsec = ( tmp % NSEC_PER_SEC );
+ return 0;
+ #endif
+#endif
+
+ return 0; // FIXME this is actually not true
+ }
+ else
+ return -1; // TODO this is e.g. in case of CLOCK_MONOTONIC, we could use QPC then.
+
+} // mbg_clock_settime
+
+
+
+bool force_legacy_gstaft;
+
+
+/*HDR*/
+void check_precise_time_api( void )
+{
+ const char *info ="";
+ GSTAFT_FNC tmp_fnc;
+ HINSTANCE h = LoadLibrary( "kernel32.dll" );
+
+ if ( h == NULL )
+ {
+ info = "Precise system time may not be supported; failed to get handle for kernel32.dll.";
+ goto out;
+ }
+
+ tmp_fnc = (GSTAFT_FNC) GetProcAddress( h, "GetSystemTimePreciseAsFileTime" );
+
+ if ( tmp_fnc == NULL )
+ {
+ info = "Precise system time NOT supported";
+ goto out;
+ }
+
+ if ( force_legacy_gstaft )
+ {
+ info = "Precise system time is supported, but legacy function used by request";
+ goto out;
+ }
+
+ gstaft_fnc = tmp_fnc;
+ info = "Precise system time is supported and used";
+
+out:
+ printf( "%s\n", info );
+
+} // check_precise_time_api
+
+#endif
+
diff --git a/mbglib/common/timeutil.h b/mbglib/common/timeutil.h
new file mode 100755
index 0000000..2eb9a39
--- /dev/null
+++ b/mbglib/common/timeutil.h
@@ -0,0 +1,136 @@
+
+/**************************************************************************
+ *
+ * $Id: timeutil.h 1.2.1.3 2017/04/10 13:30:04 martin TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Definitions and prototypes for timeutil.c
+ *
+ * -----------------------------------------------------------------------
+ * $Log: timeutil.h $
+ * Revision 1.2.1.3 2017/04/10 13:30:04 martin
+ * Fixed some compiler warnings.
+ * Revision 1.2.1.2 2017/02/06 11:14:13Z martin
+ * Fixed build under windows.
+ * Updated function prototypes.
+ * Revision 1.2.1.1 2016/08/11 15:09:51Z martin
+ * *** empty log message ***
+ * Revision 1.2 2016/08/11 13:44:00 martin
+ * Include stddef.h.
+ * Revision 1.1 2016/07/15 14:14:20Z martin
+ * Initial revision
+ *
+ **************************************************************************/
+
+#ifndef _TIMEUTIL_H
+#define _TIMEUTIL_H
+
+/* Other headers to be included */
+
+#include <words.h> // implicitly includes mbg_tgt.h for non-firmware projects
+#include <mbgerror.h>
+
+#include <time.h>
+#include <stddef.h>
+
+
+#ifdef _TIMEUTIL
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+
+/* Start of header body */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+#if defined( MBG_TGT_WIN32 ) || defined( MBG_TGT_DOS )
+
+typedef int clockid_t;
+#define clockid_t clockid_t
+
+#define CLOCK_REALTIME ( (clockid_t) 0 )
+
+#endif
+
+
+
+#if defined( MBG_TGT_WIN32 )
+
+#define __const__ const
+
+/**
+ * @brief A pointer to a function returning the system time as FILETIME
+ *
+ * This can be e.g. the standard Windows API call GetSystemTimeAsFileTime()
+ * or the GetSystemTimeAsPreciseFileTime() API call introduced with Windows 8.
+ */
+typedef VOID (WINAPI *GSTAFT_FNC)(LPFILETIME lpSystemTimeAsFileTime);
+
+_ext GSTAFT_FNC gstaft_fnc
+#ifdef _DO_INIT
+ = GetSystemTimeAsFileTime
+#endif
+;
+
+#endif
+
+
+/* function prototypes: */
+
+static __mbg_inline
+time_t cvt_to_time_t( time_t t )
+{
+ // Eventually we can do some epoch check here.
+ return (time_t) t;
+
+} // cvt_to_time_t
+
+
+
+static __mbg_inline
+int mbg_gmtime( struct tm *p_tm, const time_t *p_time )
+{
+ struct tm *p_tm_tmp = gmtime( p_time );
+
+ if ( p_tm_tmp == NULL ) // conversion failed
+ return mbg_get_last_error( NULL );
+
+ *p_tm = *p_tm_tmp;
+
+ return MBG_SUCCESS;
+
+} // mbg_gmtime
+
+
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+ size_t snprint_gmtime_error( char *s, size_t max_len, int mbg_errno, time_t t, const char *calling_fnc ) ;
+ int mbg_clock_gettime( clockid_t clock_id, struct timespec *tp ) ;
+ int mbg_clock_settime( clockid_t clock_id, const struct timespec *tp ) ;
+ void check_precise_time_api( void ) ;
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+
+/* End of header body */
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _TIMEUTIL_H */
diff --git a/mbglib/common/toolutil.c b/mbglib/common/toolutil.c
index 9c9b2f2..b92401a 100755
--- a/mbglib/common/toolutil.c
+++ b/mbglib/common/toolutil.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: toolutil.c 1.4.1.4 2013/02/05 15:27:30 martin TEST martin $
+ * $Id: toolutil.c 1.4.1.26 2016/10/20 11:25:49 martin TEST $
*
* Description:
* Common functions which can be used with Meinberg command line
@@ -9,6 +9,44 @@
*
* -----------------------------------------------------------------------
* $Log: toolutil.c $
+ * Revision 1.4.1.26 2016/10/20 11:25:49 martin
+ * *** empty log message ***
+ * Revision 1.4.1.25 2016/08/11 07:27:26 martin
+ * Revision 1.4.1.24 2016/08/10 13:13:25Z martin
+ * *** empty log message ***
+ * Revision 1.4.1.23 2016/08/09 16:01:59 martin
+ * Fixed build for QNX Neutrino.
+ * Revision 1.4.1.22 2016/07/22 09:57:12 martin
+ * Quieted some compiler warninges.
+ * Revision 1.4.1.21 2016/07/15 14:12:00 martin
+ * *** empty log message ***
+ * Revision 1.4.1.20 2015/11/09 11:20:59 martin
+ * *** empty log message ***
+ * Revision 1.4.1.19 2015/10/26 13:58:39 martin
+ * Revision 1.4.1.18 2015/10/21 12:40:41Z martin
+ * Fixed some compiler warnings under Windows.
+ * Revision 1.4.1.17 2015/09/03 11:19:15Z martin
+ * Made mbg_snprint_hr_tstamp() more versatile
+ * by passing a new optional UTC offset parameter.
+ * Revision 1.4.1.16 2015/08/27 16:16:00 martin
+ * Use safe string functions.
+ * Revision 1.4.1.15 2015/07/14 15:16:29 martin
+ * Reworked error checking after opening device.
+ * Make stdout unbuffered if output is redirected.
+ * Revision 1.4.1.14 2014/10/22 15:36:12 martin
+ * Revision 1.4.1.13 2014/04/28 13:34:21 martin
+ * Print special firmware version info, if appropriate.
+ * Revision 1.4.1.12 2014/01/31 14:45:45 martin
+ * Revision 1.4.1.11 2013/12/04 09:58:53 martin
+ * Print device options with OS-specific device names.
+ * Revision 1.4.1.10 2013/07/22 16:25:11Z martin
+ * Revision 1.4.1.9 2013/07/17 09:55:52 martin
+ * Revision 1.4.1.8 2013/07/16 15:45:19 martin
+ * Revision 1.4.1.7 2013/07/16 09:52:34 martin
+ * Revision 1.4.1.6 2013/07/11 15:31:17 martin
+ * Revision 1.4.1.5 2013/07/11 08:37:55 martin
+ * Add a parameter to mbg_check_devices() which controls if only one
+ * or all devices should be handled if no device has been specified.
* Revision 1.4.1.4 2013/02/05 15:27:30 martin
* Revision 1.4.1.3 2013/02/05 15:24:46 martin
* Revision 1.4.1.2 2013/02/05 14:39:38 martin
@@ -39,12 +77,24 @@
#undef _TOOLUTIL
// include Meinberg headers
+#include <cfg_hlp.h>
#include <pcpsutil.h>
+#include <timeutil.h>
+#include <str_util.h>
// include system headers
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
+#include <errno.h>
+
+
+
+#if defined( MBG_TGT_WIN32 )
+ #define isatty _isatty
+ #define fileno _fileno
+#endif
+
static __mbg_inline
@@ -61,21 +111,46 @@ double delta_timestamps( const PCPS_TIME_STAMP *p_ts, const PCPS_TIME_STAMP *p_p
/*HDR*/
+int mbg_program_version_str( char *s, size_t max_len, int micro_version )
+{
+ int n;
+
+ #if defined( MBG_MICRO_VERSION_CODE_DEV )
+ micro_version = MBG_MICRO_VERSION_CODE_DEV;
+ #endif
+
+ n = snprintf_safe( s, max_len, "%i.%i.%i", MBG_MAJOR_VERSION_CODE,
+ MBG_MINOR_VERSION_CODE, micro_version );
+
+ return n;
+
+} // mbg_program_version_str
+
+
+
+/*HDR*/
int mbg_program_info_str( char *s, size_t max_len, const char *pname,
int micro_version, int first_year, int last_year )
{
- int n;
+ int n = 0;
+
+ #if defined( MBG_MICRO_VERSION_CODE_DEV )
+ micro_version = MBG_MICRO_VERSION_CODE_DEV;
+ #endif
if ( last_year == 0 )
last_year = MBG_CURRENT_COPYRIGHT_YEAR;
- n = snprintf( s, max_len, "%s v%i.%i.%i copyright Meinberg ", pname,
- MBG_MAJOR_VERSION_CODE, MBG_MINOR_VERSION_CODE, micro_version );
+ n += snprintf_safe( &s[n], max_len - n, "%s v", pname );
+
+ n += mbg_program_version_str( &s[n], max_len - n, micro_version );
+
+ n += snprintf_safe( &s[n], max_len - n, " copyright Meinberg " );
if ( first_year != last_year )
- n += snprintf( &s[n], max_len - n, "%04i-", first_year );
+ n += snprintf_safe( &s[n], max_len - n, "%04i-", first_year );
- n += snprintf( &s[n], max_len - n, "%04i", last_year );
+ n += snprintf_safe( &s[n], max_len - n, "%04i", last_year );
return n;
@@ -87,9 +162,7 @@ int mbg_program_info_str( char *s, size_t max_len, const char *pname,
void mbg_print_program_info( const char *pname, int micro_version, int first_year, int last_year )
{
char ws[256];
- #if defined( MBG_MICRO_VERSION_CODE_DEV )
- micro_version = MBG_MICRO_VERSION_CODE_DEV;
- #endif
+
mbg_program_info_str( ws, sizeof( ws ), pname, micro_version, first_year, last_year );
printf( "\n%s\n\n", ws );
@@ -139,9 +212,14 @@ void mbg_print_help_options( void )
/*HDR*/
void mbg_print_device_options( void )
{
- puts( "\nwhere dev is the name of a device, e.g.:\n"
- " /dev/mbgclock0"
- );
+ printf( "\n" );
+
+ #if ( defined( MBG_TGT_POSIX ) || defined( MBG_TGT_WIN32 ) ) && !defined( MBG_TGT_QNX_NTO )
+ printf( "where dev is the device name, e.g.:\n"
+ " %s or %s", EXAMPLE_DEVICE_NAME_1, EXAMPLE_DEVICE_NAME_2 );
+ #else
+ printf( "where dev is the device name or index." );
+ #endif
} // mbg_print_device_options
@@ -159,27 +237,10 @@ void mbg_print_default_usage( const char *pname, const char *prog_info )
-// test if ioctl error and print msg if true
-
-/*HDR*/
-int mbg_ioctl_err( int rc, const char *descr )
-{
- if ( rc < 0 )
- {
- fprintf( stderr, "** IOCTL error %i: ", rc );
- perror( descr );
- return -1;
- }
-
- return 0;
-
-} // mbg_ioctl_err
-
-
-
/*HDR*/
int mbg_get_show_dev_info( MBG_DEV_HANDLE dh, const char *dev_name, PCPS_DEV *p_dev )
{
+ RECEIVER_INFO ri;
unsigned long port;
int irq_num;
int ret_val = 0;
@@ -194,18 +255,26 @@ int mbg_get_show_dev_info( MBG_DEV_HANDLE dh, const char *dev_name, PCPS_DEV *p_
if ( mbg_ioctl_err( rc, "mbg_get_device_info" ) )
goto fail;
+ rc = mbg_setup_receiver_info( dh, p_dev, &ri );
+
+ if ( mbg_ioctl_err( rc, "mbg_setup_receiver_info" ) )
+ goto fail;
+
printf( "%s", _pcps_type_name( p_dev ) );
- if ( strlen( _pcps_sernum( p_dev ) ) &&
+ if ( strlen( _pcps_sernum( p_dev ) ) &&
strcmp( _pcps_sernum( p_dev ), "N/A" ) )
printf( " %s", _pcps_sernum( p_dev ) );
- printf( " (FW %X.%02X",
+ printf( " (FW %X.%02X",
_pcps_fw_rev_num_major( _pcps_fw_rev_num( p_dev ) ),
_pcps_fw_rev_num_minor( _pcps_fw_rev_num( p_dev ) )
);
+ if ( chk_sw_rev_name( &ri.sw_rev, 0 ) )
+ printf( " \"%s\"", ri.sw_rev.name );
+
if ( _pcps_has_asic_version( p_dev ) )
{
PCI_ASIC_VERSION av;
@@ -253,20 +322,11 @@ done:
/*HDR*/
-int mbg_check_device( MBG_DEV_HANDLE dh, const char *dev_name,
+int mbg_check_device( MBG_DEV_HANDLE dh, const char *dev_name,
int (*fnc)( MBG_DEV_HANDLE, const PCPS_DEV *) )
{
PCPS_DEV dev;
- int ret_val = 0;
-
- if ( dh == MBG_INVALID_DEV_HANDLE )
- {
- if ( dev_name )
- fprintf( stderr, "%s: ", dev_name );
-
- perror( "Unable to open device" );
- return -1;
- }
+ int ret_val = MBG_SUCCESS;
if ( mbg_get_show_dev_info( dh, dev_name, &dev ) < 0 )
goto fail;
@@ -290,51 +350,127 @@ done:
/*HDR*/
-int mbg_check_devices( int argc, char *argv[], int optind, int (*fnc)( MBG_DEV_HANDLE, const PCPS_DEV *) )
+int mbg_check_open_result( MBG_DEV_HANDLE dh, const char *dev_name )
{
- MBG_DEV_HANDLE dh;
- int ret_val = 0;
- int num_devices = argc - optind;
-
- if ( num_devices == 0 ) // no device name given on the command line
+ if ( dh == MBG_INVALID_DEV_HANDLE )
{
- // No devices specified on the command line, so
- // try to find devices.
- int devices = mbg_find_devices();
+ int this_errno = errno;
- if ( devices == 0 )
- {
- printf( "No device found.\n" );
- return 1;
- }
+ const char *err_info = strerror( this_errno );
- // Handle only first device found.
- dh = mbg_open_device( 0 );
- ret_val = mbg_check_device( dh, NULL, fnc );
+ fprintf( stderr, "Failed to open device" );
+
+ if ( dev_name )
+ fprintf( stderr, " %s", dev_name );
+
+ fprintf( stderr, ": %s\n", err_info );
+
+ return mbg_posix_errno_to_mbg( this_errno, NULL );
}
- else
+
+ return MBG_SUCCESS;
+
+} // mbg_check_open_result
+
+
+
+/*HDR*/
+int mbg_check_devices( int argc, char *argv[], int optind,
+ int (*fnc)( MBG_DEV_HANDLE, const PCPS_DEV *),
+ int chk_dev_flags )
+{
+ MBG_DEV_HANDLE dh;
+ int ret_val = 0;
+ int devices_specified = argc - optind;
+ int i;
+
+ // If the output has been redirected then make stdout unbuffered,
+ // e.g. to see the output immediately even though piped through 'tee'.
+ if ( !isatty( fileno( stdout ) ) )
+ setvbuf( stdout, NULL, _IONBF, 0 );
+
+ if ( devices_specified )
{
- int i;
- // One or more device names have been specified
+ // One or more device names have been specified
// on the command line, so handle each device.
for ( i = optind; i < argc; i++ )
{
// Print device name only if output for several devices
// shall be displayed.
- const char *fn = ( num_devices > 1 ) ? argv[i] : NULL;
+ const char *fn = ( devices_specified > 1 ) ? argv[i] : NULL;
- #if defined( MBG_TGT_WIN32 )
- mbg_find_devices();
- dh = mbg_open_device_by_name( argv[i], MBG_MATCH_MODEL );
- #else
+ #if defined( MBG_TGT_POSIX ) && !defined( MBG_TGT_QNX_NTO )
dh = open( argv[i], O_RDWR );
+ #else
+ dh = mbg_open_device_by_name( argv[i], MBG_MATCH_MODEL );
#endif
- ret_val = mbg_check_device( dh, fn, fnc );
+ ret_val = mbg_check_open_result( dh, argv[i] );
- if ( ret_val )
+ if ( ret_val == MBG_SUCCESS )
+ ret_val = mbg_check_device( dh, fn, fnc );
+
+ // Don't continue if one of the specified devices failed.
+ if ( ret_val != MBG_SUCCESS )
break;
}
}
+ else // no device specified on the command line
+ {
+ if ( chk_dev_flags & CHK_DEV_WITHOUT_DEV )
+ {
+ // TODO: check if this branch is useful
+ // We have been called without a device to be used.
+ // This may be useful e.g. if we just want to print
+ // some general usage information.
+ if ( fnc )
+ {
+ dh = MBG_INVALID_DEV_HANDLE;
+ ret_val = fnc( dh, NULL );
+ }
+ else
+ {
+ // should we report an error if we have been called
+ // without callback function and without device?
+ }
+ }
+ else
+ {
+ int devices_foundx = mbg_find_devices();
+
+ if ( devices_foundx == 0 ) // no device found
+ {
+ // Don't continue without any device, unless
+ // explicitely requested to do so.
+ if ( !( chk_dev_flags & CHK_DEV_WITHOUT_DEV ) )
+ {
+ printf( "No device found.\n" );
+ return 1;
+ }
+
+ // We may continue even if no device is available,
+ // but must process the callback loop only once.
+ devices_foundx = 1;
+ }
+
+ // Unless explicitely requested to handle all devices
+ // we have found, we only handle the first one.
+ if ( !( chk_dev_flags & CHK_DEV_ALL_DEVICES ) )
+ devices_foundx = 1;
+
+ for ( i = 0; i < devices_foundx; i++ )
+ {
+ dh = mbg_open_device( i );
+
+ ret_val = mbg_check_open_result( dh, NULL );
+
+ if ( ret_val == MBG_SUCCESS )
+ ret_val = mbg_check_device( dh, NULL, fnc );
+ }
+
+ // If one of the unspecified devices failed we continue anyway
+ // and don't break here.
+ }
+ }
return ret_val;
@@ -343,18 +479,20 @@ int mbg_check_devices( int argc, char *argv[], int optind, int (*fnc)( MBG_DEV_H
/*HDR*/
-int mbg_snprint_date_time( char *s, int len_s, const PCPS_TIME *p, int verbose )
+size_t mbg_snprint_date_time( char *s, size_t max_len, const PCPS_TIME *p, int verbose )
{
- int n = 0;
+ size_t n = 0;
+
+ n += snprintf_safe( &s[n], max_len - n, "%04u-%02u-%02u %02u:%02u:%02u.%02u",
+ pcps_exp_year( p->year, mbg_exp_year_limit ), p->month, p->mday,
+ p->hour, p->min, p->sec, p->sec100 );
- n += snprintf( s + n, len_s - n, "%04u-%02u-%02u %02u:%02u:%02u.%02u",
- pcps_exp_year( p->year, mbg_exp_year_limit ), p->month, p->mday,
- p->hour, p->min, p->sec, p->sec100
- );
+ if ( verbose > 0 )
+ n += snprintf_safe( &s[n], max_len - n, " (UTC%+ih), st: %02Xh",
+ p->offs_utc, p->status );
- if ( verbose )
- n += snprintf( s + n, len_s - n, " (UTC%+ih), st: %02Xh",
- p->offs_utc, p->status );
+ if ( verbose > 1 )
+ n += snprintf_safe( &s[n], max_len - n, ", sig: %i", p->signal );
return n;
@@ -363,33 +501,37 @@ int mbg_snprint_date_time( char *s, int len_s, const PCPS_TIME *p, int verbose )
/*HDR*/
-int mbg_snprint_hr_tstamp( char *s, int len_s, const PCPS_TIME_STAMP *p, int show_raw )
+size_t mbg_snprint_hr_tstamp( char *s, size_t max_len, const PCPS_TIME_STAMP *p,
+ long utc_offs, int show_raw )
{
- int n = 0;
+ long l;
+ time_t t;
+ struct tm tm = { 0 };
+ size_t n = 0;
+ int rc;
+
+ if ( show_raw )
+ n += snprintf_safe( &s[n], max_len - n, "raw: 0x%08lX.%08lX, ",
+ (ulong) p->sec, (ulong) p->frac );
// We'll use the standard C library functions to convert the seconds
// to broken-down calendar date and time.
- time_t t = p->sec;
+ l = (long) p->sec + utc_offs;
+ t = cvt_to_time_t( l );
// Our time stamp may be UTC, or have been converted to local time.
- // Anyway, since we don't want to account for the system's time zone
- // settings, we always use the gmtime() function for conversion:
- struct tm *tmp = gmtime( &t );
-
- if ( show_raw )
- n += snprintf( s + n, len_s - n, "raw: 0x%08lX.%08lX, ",
- (ulong) p->sec,
- (ulong) p->frac );
-
- n += snprintf( s + n, len_s - n, "%04i-%02i-%02i %02i:%02i:%02i." PCPS_HRT_FRAC_SCALE_FMT,
- tmp->tm_year + 1900,
- tmp->tm_mon + 1,
- tmp->tm_mday,
- tmp->tm_hour,
- tmp->tm_min,
- tmp->tm_sec,
- (ulong) frac_sec_from_bin( p->frac, PCPS_HRT_FRAC_SCALE )
- );
+ // Anyway, since we don't want to account for the system's time zone
+ // settings, we always use the gmtime() function for conversion,
+ // or our own wrapper, respectively:
+ rc = mbg_gmtime( &tm, &t );
+
+ if ( mbg_rc_is_success( rc ) )
+ n += snprintf_safe( &s[n], max_len - n, "%04i-%02i-%02i %02i:%02i:%02i." PCPS_HRT_FRAC_SCALE_FMT,
+ tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday,
+ tm.tm_hour, tm.tm_min, tm.tm_sec,
+ (ulong) frac_sec_from_bin( p->frac, PCPS_HRT_FRAC_SCALE ) );
+ else
+ n += snprint_gmtime_error( &s[n], max_len - n, rc, t, __func__ );
return n;
@@ -398,11 +540,11 @@ int mbg_snprint_hr_tstamp( char *s, int len_s, const PCPS_TIME_STAMP *p, int sho
/*HDR*/
-int mbg_snprint_hr_time( char *s, int len_s, const PCPS_HR_TIME *p, int show_raw )
+size_t mbg_snprint_hr_time( char *s, int max_len, const PCPS_HR_TIME *p, int show_raw )
{
char ws[80];
PCPS_TIME_STAMP ts = p->tstamp;
- int n;
+ size_t n;
const char *time_scale_name;
const char *cp;
@@ -410,19 +552,13 @@ int mbg_snprint_hr_time( char *s, int len_s, const PCPS_HR_TIME *p, int show_raw
// and set up a string telling the offset.
if ( p->utc_offs )
{
- ldiv_t ldt;
-
- ts.sec += p->utc_offs;
-
// The local time offset is in seconds and may be negative, so we
// convert to absolute hours and minutes first.
- ldt = ldiv( labs( p->utc_offs ) / 60, 60 );
+ ldiv_t ldt = ldiv( labs( p->utc_offs ) / 60, 60 );
- snprintf( ws, sizeof( ws ), "%c%lu:%02luh",
- ( p->utc_offs < 0 ) ? '-' : '+',
- ldt.quot,
- ldt.rem
- );
+ snprintf_safe( ws, sizeof( ws ), "%c%lu:%02luh",
+ ( p->utc_offs < 0 ) ? '-' : '+',
+ ldt.quot, ldt.rem );
cp = ws;
}
else
@@ -430,7 +566,7 @@ int mbg_snprint_hr_time( char *s, int len_s, const PCPS_HR_TIME *p, int show_raw
// Convert the local time stamp to calendar date and time.
- n = mbg_snprint_hr_tstamp( s, len_s, &ts, show_raw );
+ n = mbg_snprint_hr_tstamp( s, max_len, &ts, p->utc_offs, show_raw );
// By default the time stamp represents UTC plus an optional local time offset.
time_scale_name = "UTC";
@@ -442,7 +578,7 @@ int mbg_snprint_hr_time( char *s, int len_s, const PCPS_HR_TIME *p, int show_raw
if ( p->status & PCPS_SCALE_GPS )
time_scale_name = "GPS"; // time stamp represents GPS system time
- n += snprintf( s + n, len_s - n, " %s%s", time_scale_name, cp );
+ n += snprintf_safe( &s[n], max_len - n, " %s%s", time_scale_name, cp );
return n;
@@ -456,7 +592,7 @@ void mbg_print_hr_timestamp( PCPS_TIME_STAMP *p_ts, int32_t hns_latency, PCPS_TI
{
char ws[80];
- mbg_snprint_hr_tstamp( ws, sizeof( ws ), p_ts, show_raw );
+ mbg_snprint_hr_tstamp( ws, sizeof( ws ), p_ts, 0, show_raw );
printf( "HR time %s", ws );
if ( p_prv_ts )
@@ -486,9 +622,12 @@ void mbg_print_hr_time( PCPS_HR_TIME *p_ht, int32_t hns_latency, PCPS_TIME_STAMP
if ( !no_latency )
printf( ", latency: %.1f us", ( (double) hns_latency ) / 10 );
- if ( verbose )
+ if ( verbose > 0 )
printf( ", st: 0x%04lX", (ulong) p_ht->status );
+ if ( verbose > 1 )
+ printf( ", sig: %i", p_ht->signal );
+
puts( "" );
} // mbg_print_hr_time
@@ -512,12 +651,11 @@ int mbg_show_pzf_corr_info( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, int show_c
cp = pzf_corr_state_name[ci.status];
else
{
- snprintf( ws, sizeof( ws ) - 1, "(unknown, code: 0x%02X)", ci.status );
- ws[sizeof( ws ) - 1] = 0; // force terminating 0
+ snprintf_safe( ws, sizeof( ws ), "unknown status code: 0x%02X", ci.status );
cp = ws;
}
- printf( "PZF correlation: %u%%, status: %s", ci.val, cp );
+ printf( "%s, PZF correlation: %u%%", cp, ci.val );
if ( show_corr_step )
if ( ci.corr_dir != ' ' )
@@ -528,3 +666,21 @@ int mbg_show_pzf_corr_info( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, int show_c
} // mbg_show_pzf_corr_info
+
+/*HDR*/
+int mbg_get_gps_gnss_mode_info_chk( MBG_DEV_HANDLE dh, MBG_GNSS_MODE_INFO *p )
+{
+ int rc;
+
+ if ( dh == MBG_INVALID_DEV_HANDLE )
+ return MBG_ERR_INV_HANDLE;
+
+ rc = mbg_get_gps_gnss_mode_info( dh, p );
+ mbg_ioctl_err( rc, "mbg_get_gps_gnss_mode_info" );
+
+ return rc;
+
+} // mbg_get_gps_gnss_mode_info_chk
+
+
+
diff --git a/mbglib/common/toolutil.h b/mbglib/common/toolutil.h
index 3657fda..05bece7 100755
--- a/mbglib/common/toolutil.h
+++ b/mbglib/common/toolutil.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: toolutil.h 1.3.1.1 2013/02/05 14:38:26 martin TEST $
+ * $Id: toolutil.h 1.3.1.11 2016/08/10 12:29:34 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,23 @@
*
* -----------------------------------------------------------------------
* $Log: toolutil.h $
+ * Revision 1.3.1.11 2016/08/10 12:29:34 martin
+ * Check for MBG_TGT_POSIX instead of MBG_TGT_UNIX.
+ * Revision 1.3.1.10 2015/11/09 11:20:59 martin
+ * *** empty log message ***
+ * Revision 1.3.1.9 2015/09/03 11:19:15 martin
+ * Made mbg_snprint_hr_tstamp() more versatile
+ * by passing a new optional UTC offset parameter.
+ * Revision 1.3.1.8 2015/08/27 16:16:29 martin
+ * Updated function prototypes.
+ * Revision 1.3.1.7 2014/01/31 14:45:45 martin
+ * Revision 1.3.1.6 2013/12/04 09:59:44 martin
+ * Defined some OS-specific strings.
+ * Revision 1.3.1.5 2013/07/22 16:25:11Z martin
+ * Revision 1.3.1.4 2013/07/16 15:45:19 martin
+ * Revision 1.3.1.3 2013/07/16 09:52:34 martin
+ * Revision 1.3.1.2 2013/07/11 08:38:20 martin
+ * Updated function prototypes.
* Revision 1.3.1.1 2013/02/05 14:38:26 martin
* Started to support Windows target.
* Revision 1.3 2012/10/15 09:36:22 martin
@@ -34,7 +51,7 @@
#include <mbgdevio.h>
#include <mbgversion.h>
-#if defined( MBG_TGT_UNIX)
+#if defined( MBG_TGT_POSIX )
#include <unistd.h>
@@ -69,6 +86,33 @@
extern "C" {
#endif
+
+enum CHK_DEV_FLAGS
+{
+ CHK_DEV_ALL_DEVICES = 0x0001, ///< call callback for all devices
+ CHK_DEV_WITHOUT_DEV = 0x0002 ///< call callback once if no device found
+};
+
+
+#if defined( MBG_TGT_WIN32 )
+
+ #define EXAMPLE_DEVICE_NAME_1 "gps180pex"
+ #define EXAMPLE_DEVICE_NAME_1_TCR "tcr167pci"
+ #define EXAMPLE_DEVICE_NAME_2 "tcr170pex_027911002000"
+
+ #define ROOT_PRIVILEGES_STR "as administrator"
+
+#elif defined( MBG_TGT_POSIX ) && !defined( MBG_TGT_QNX_NTO )
+
+ #define EXAMPLE_DEVICE_NAME_1 "/dev/mbgclock0"
+ #define EXAMPLE_DEVICE_NAME_1_TCR EXAMPLE_DEVICE_NAME_1
+ #define EXAMPLE_DEVICE_NAME_2 "/dev/mbgclock3"
+
+ #define ROOT_PRIVILEGES_STR "with root privileges"
+#endif
+
+
+
#if !defined( MBG_EXP_YEAR_LIMIT )
#define MBG_EXP_YEAR_LIMIT 1980
#endif
@@ -93,6 +137,7 @@ _ext const char *pzf_corr_state_name[N_PZF_CORR_STATE]
/* This section was generated automatically */
/* by MAKEHDR, do not remove the comments. */
+ int mbg_program_version_str( char *s, size_t max_len, int micro_version ) ;
int mbg_program_info_str( char *s, size_t max_len, const char *pname, int micro_version, int first_year, int last_year ) ;
void mbg_print_program_info( const char *pname, int micro_version, int first_year, int last_year ) ;
void mbg_print_usage_intro( const char *pname, const char *info ) ;
@@ -100,16 +145,17 @@ _ext const char *pzf_corr_state_name[N_PZF_CORR_STATE]
void mbg_print_help_options( void ) ;
void mbg_print_device_options( void ) ;
void mbg_print_default_usage( const char *pname, const char *prog_info ) ;
- int mbg_ioctl_err( int rc, const char *descr ) ;
int mbg_get_show_dev_info( MBG_DEV_HANDLE dh, const char *dev_name, PCPS_DEV *p_dev ) ;
- int mbg_check_device( MBG_DEV_HANDLE dh, const char *dev_name, int (*fnc)( MBG_DEV_HANDLE, const PCPS_DEV *) ) ;
- int mbg_check_devices( int argc, char *argv[], int optind, int (*fnc)( MBG_DEV_HANDLE, const PCPS_DEV *) ) ;
- int mbg_snprint_date_time( char *s, int len_s, const PCPS_TIME *p, int verbose ) ;
- int mbg_snprint_hr_tstamp( char *s, int len_s, const PCPS_TIME_STAMP *p, int show_raw ) ;
- int mbg_snprint_hr_time( char *s, int len_s, const PCPS_HR_TIME *p, int show_raw ) ;
+ int mbg_check_device( MBG_DEV_HANDLE dh, const char *dev_name, int (*fnc)( MBG_DEV_HANDLE, const PCPS_DEV *) ) ;
+ int mbg_check_open_result( MBG_DEV_HANDLE dh, const char *dev_name ) ;
+ int mbg_check_devices( int argc, char *argv[], int optind, int (*fnc)( MBG_DEV_HANDLE, const PCPS_DEV *), int chk_dev_flags ) ;
+ size_t mbg_snprint_date_time( char *s, size_t max_len, const PCPS_TIME *p, int verbose ) ;
+ size_t mbg_snprint_hr_tstamp( char *s, size_t max_len, const PCPS_TIME_STAMP *p, long utc_offs, int show_raw ) ;
+ size_t mbg_snprint_hr_time( char *s, int max_len, const PCPS_HR_TIME *p, int show_raw ) ;
void mbg_print_hr_timestamp( PCPS_TIME_STAMP *p_ts, int32_t hns_latency, PCPS_TIME_STAMP *p_prv_ts, int no_latency, int show_raw ) ;
void mbg_print_hr_time( PCPS_HR_TIME *p_ht, int32_t hns_latency, PCPS_TIME_STAMP *p_prv_ts, int no_latency, int show_raw, int verbose ) ;
int mbg_show_pzf_corr_info( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, int show_corr_step ) ;
+ int mbg_get_gps_gnss_mode_info_chk( MBG_DEV_HANDLE dh, MBG_GNSS_MODE_INFO *p ) ;
/* ----- function prototypes end ----- */
diff --git a/mbglib/common/usbdefs.h b/mbglib/common/usbdefs.h
index 5bc12e8..b7034a4 100755
--- a/mbglib/common/usbdefs.h
+++ b/mbglib/common/usbdefs.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: usbdefs.h 1.19 2013/06/04 10:45:53 daniel TRASH $
+ * $Id: usbdefs.h 1.28 2017/04/04 10:43:34 paul.kretz TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,36 @@
*
* -----------------------------------------------------------------------
* $Log: usbdefs.h $
+ * Revision 1.28 2017/04/04 10:43:34 paul.kretz
+ * Added ID, name string and table entry for FDM180M
+ * Added missing table entry for MicroSync power supply module
+ * Revision 1.27 2017/03/28 09:37:15Z paul.kretz
+ * Added ID, name string and table entry for MicroSync power supply module
+ * Revision 1.26 2017/02/13 09:57:45Z paul.kretz
+ * Added ID, name string and table entry for PZF180.
+ * Revision 1.25 2016/11/11 09:24:04Z lars.meihost
+ * Added ID, name string and table entry for TCR180.
+ * Revision 1.24 2016/11/04 11:49:15Z paul.kretz
+ * Added device ID and associated class code for MDU312
+ * Revision 1.23 2016/09/26 07:28:10Z paul.kretz
+ * Added class code and device for N2X180
+ * Revision 1.22 2016/07/06 13:55:15Z martin
+ * Definitions for IMS-SPT, REL1000, MDU300, and SDI added by stephan.
+ * Class code and device ID for LUE added by daniel-vdh.
+ * Class code and device ID for HPS added by daniel.
+ * Device IDs and associated class codes for SCG, FDM180, CPC180,
+ * VSG180, and GTS180 added by paul.
+ * Removed obsolete multiple definitions for FTDI serial interface chips.
+ * Added a new definition for unique FTDI chip.
+ * Added definitions for serial refclocks.
+ * Added definitions for LNE180SFP, GRC180 and GRC181.
+ * Added definitions USB_VENDOR_WILDCARD and USB_PROD_WILDCARD.
+ * Added device name string and string table initializers.
+ * Doxygen fixes.
+ * Revision 1.21 2014/01/16 15:26:09 daniel
+ * Added class codes and devices for USB to serial adapters and ASIX network chips
+ * Revision 1.20 2013/10/08 09:13:04 daniel
+ * Added definition and class code for RSC.
* Revision 1.19 2013/06/04 10:45:53 daniel
* Added class codes and device IDs for IMS devices MRI and BPE
* Revision 1.18 2013/01/24 11:29:21 joerg
@@ -67,79 +97,302 @@ extern "C" {
#endif
-/* Meinberg's USB vendor ID number (assigned by USB-IF Administration) */
+/** Meinberg's USB vendor ID number (assigned by USB-IF administration) */
#define USB_VENDOR_MEINBERG 0x1938
+#define USB_VENDOR_WILDCARD 0
+#define USB_PROD_WILDCARD 0
-/*
- * USB device class codes (assigned by Meinberg)
+
+/**
+ * @brief USB device class codes assigned by Meinberg
*/
-enum
+enum MBG_USB_CLASS_CODES
{
- MBG_USB_CLASS_NONE, // (unknown or not defined)
- MBG_USB_CLASS_CPC, // Control Panel Controller
- MBG_USB_CLASS_TSU, // Time Stamp Unit
- MBG_USB_CLASS_DCF, // DCF77 Radio Clock
- MBG_USB_CLASS_CMC, // nCipher Crypto Module Carrier
- MBG_USB_CLASS_TCR, // IRIG Time Code Receiver
- MBG_USB_CLASS_MSF, // MSF Radio Clock
- MBG_USB_CLASS_WWVB, // WWVB Radio Clock
- MBG_USB_CLASS_SCU, // Meinberg Signal Changeover Unit
- MBG_USB_CLASS_ESI, // External Synchronization Interface
- MBG_USB_CLASS_FCU, // Fan Control Unit
- MBG_USB_CLASS_CPE, // Configurable Port Expander
- MBG_USB_CLASS_GPS, // GPS Receiver
- MBG_USB_CLASS_LNO, // Low Phase Noise Option
- MBG_USB_CLASS_LIU, // Line Interface Unit
- MBG_USB_CLASS_LNE, // LNE-GB
- MBG_USB_CLASS_MRI, // MRS Input card for IMS
- MBG_USB_CLASS_BPE, // IMS Backplane Port Expander
- N_MBG_USB_CLASS // number of known device class codes
+ MBG_USB_CLASS_NONE, ///< (unknown or not defined)
+ MBG_USB_CLASS_CPC, ///< Control Panel Controller
+ MBG_USB_CLASS_TSU, ///< Time Stamp Unit
+ MBG_USB_CLASS_DCF, ///< DCF77 Radio Clock
+ MBG_USB_CLASS_CMC, ///< nCipher Crypto Module Carrier
+ MBG_USB_CLASS_TCR, ///< IRIG Time Code Receiver
+ MBG_USB_CLASS_MSF, ///< MSF Radio Clock
+ MBG_USB_CLASS_WWVB, ///< WWVB Radio Clock
+
+ MBG_USB_CLASS_SCU, ///< Meinberg Signal Changeover Unit
+ MBG_USB_CLASS_ESI, ///< External Synchronization Interface
+ MBG_USB_CLASS_FCU, ///< Fan Control Unit
+ MBG_USB_CLASS_CPE, ///< Configurable Port Expander
+ MBG_USB_CLASS_GPS, ///< GPS Receiver
+ MBG_USB_CLASS_LNO, ///< Low Phase Noise Option
+ MBG_USB_CLASS_LIU, ///< Line Interface Unit
+ MBG_USB_CLASS_LNE, ///< LNE-GB
+
+ MBG_USB_CLASS_MRI, ///< MRS Input card for IMS
+ MBG_USB_CLASS_BPE, ///< IMS Backplane Port Expander
+ MBG_USB_CLASS_RSC, ///< RSC Redundant Switch Control
+ MBG_USB_CLASS_SERIAL, ///< USB to Serial controller, FTDI chip connected to Meinberg serial device
+ MBG_USB_CLASS_SCG, ///< Studio Clock Generator
+ MBG_USB_CLASS_SDI, ///< SDI Input card for IMS
+ MBG_USB_CLASS_FDM, ///< Frequency Deviation Monitor
+ MBG_USB_CLASS_NIC, ///< ASIX AX88179 Network interface chips on LNE, modified by Meinberg (this *must* be 0x17)
+
+ MBG_USB_CLASS_MDU, ///< Modular Distribution Unit
+ MBG_USB_CLASS_SPT, ///< Single Path Through
+ MBG_USB_CLASS_REL, ///< Relais Error Card
+ MBG_USB_CLASS_LUE, ///< Lantime USB Expansion
+ MBG_USB_CLASS_HPS, ///< High Performance Synchronization Card (PTP/NTP)
+ MBG_USB_CLASS_VSG, ///< Video Sync Generator
+ MBG_USB_CLASS_GTS, ///< Greenwich Time Signal
+ MBG_USB_CLASS_GRC, ///< GNSS receivers (GPS, GLONASS, ... )
+
+ MBG_USB_CLASS_N2X, ///< NTP/PTP receiver
+ MBG_USB_CLASS_USYNC, ///< MicroSync
+
+ N_MBG_USB_CLASS ///< number of known Meinberg USB device class codes
};
-/*
- * USB device ID numbers (assigned by Meinberg)
- * High byte: USB device class as specified above
- * Low byte: enumeration of device of a class
+/**
+ * @brief USB device ID numbers assigned by Meinberg
+ *
+ * High byte: USB device class, see ::MBG_USB_CLASS_CODES<br>
+ * Low byte: enumeration of devices of a class
+ *
+ * @see @ref MBG_USB_DEVICE_NAMES
+ * @see ::DEFAULT_MBG_USB_DEVICE_NAMES
+ * @see ::MBG_USB_CLASS_CODES
+ *
+ * @anchor MBG_USB_DEVICE_IDS @{
*/
-#define USB_DEV_CPC_01 ( ( MBG_USB_CLASS_CPC << 8 ) | 0x01 )
-#define USB_DEV_TSU_01 ( ( MBG_USB_CLASS_TSU << 8 ) | 0x01 )
+#define USB_DEV_CPC_01 ( ( MBG_USB_CLASS_CPC << 8 ) | 0x01 )
+#define USB_DEV_CPC180 ( ( MBG_USB_CLASS_CPC << 8 ) | 0x02 )
+
+#define USB_DEV_TSU_01 ( ( MBG_USB_CLASS_TSU << 8 ) | 0x01 )
+
+#define USB_DEV_USB5131 ( ( MBG_USB_CLASS_DCF << 8 ) | 0x01 )
+#define USB_DEV_DCF600USB ( ( MBG_USB_CLASS_DCF << 8 ) | 0x02 )
+#define USB_DEV_PZF180 ( ( MBG_USB_CLASS_DCF << 8 ) | 0x03 )
+
+#define USB_DEV_CMC ( ( MBG_USB_CLASS_CMC << 8 ) | 0x01 )
+
+#define USB_DEV_TCR51USB ( ( MBG_USB_CLASS_TCR << 8 ) | 0x01 )
+#define USB_DEV_TCR600USB ( ( MBG_USB_CLASS_TCR << 8 ) | 0x02 )
+#define USB_DEV_TCR180 ( ( MBG_USB_CLASS_TCR << 8 ) | 0x03 )
+
+#define USB_DEV_MSF51USB ( ( MBG_USB_CLASS_MSF << 8 ) | 0x01 )
+#define USB_DEV_MSF600USB ( ( MBG_USB_CLASS_MSF << 8 ) | 0x02 )
+
+#define USB_DEV_WWVB51USB ( ( MBG_USB_CLASS_WWVB << 8 ) | 0x01 )
+#define USB_DEV_WVB600USB ( ( MBG_USB_CLASS_WWVB << 8 ) | 0x02 )
+
+#define USB_DEV_SCU_USB ( ( MBG_USB_CLASS_SCU << 8 ) | 0x01 )
+
+#define USB_DEV_ESI_01 ( ( MBG_USB_CLASS_ESI << 8 ) | 0x01 )
+
+#define USB_DEV_FCU_01 ( ( MBG_USB_CLASS_FCU << 8 ) | 0x01 )
+
+#define USB_DEV_CPE_01 ( ( MBG_USB_CLASS_CPE << 8 ) | 0x01 )
+
+#define USB_DEV_GPS180 ( ( MBG_USB_CLASS_GPS << 8 ) | 0x01 )
+
+#define USB_DEV_LNO180 ( ( MBG_USB_CLASS_LNO << 8 ) | 0x01 )
+
+#define USB_DEV_LIU_01 ( ( MBG_USB_CLASS_LIU << 8 ) | 0x01 )
-#define USB_DEV_USB5131 ( ( MBG_USB_CLASS_DCF << 8 ) | 0x01 )
-#define USB_DEV_DCF600USB ( ( MBG_USB_CLASS_DCF << 8 ) | 0x02 )
+#define USB_DEV_LNE_01 ( ( MBG_USB_CLASS_LNE << 8 ) | 0x01 ) // LNE with standard copper
+#define USB_DEV_LNE180SFP ( ( MBG_USB_CLASS_LNE << 8 ) | 0x02 ) // LNE with SFP (fiber optic)
-#define USB_DEV_CMC ( ( MBG_USB_CLASS_CMC << 8 ) | 0x01 )
+#define USB_DEV_MRI_01 ( ( MBG_USB_CLASS_MRI << 8 ) | 0x01 )
-#define USB_DEV_TCR51USB ( ( MBG_USB_CLASS_TCR << 8 ) | 0x01 )
-#define USB_DEV_TCR600USB ( ( MBG_USB_CLASS_TCR << 8 ) | 0x02 )
+#define USB_DEV_BPE_01 ( ( MBG_USB_CLASS_BPE << 8 ) | 0x01 )
-#define USB_DEV_MSF51USB ( ( MBG_USB_CLASS_MSF << 8 ) | 0x01 )
-#define USB_DEV_MSF600USB ( ( MBG_USB_CLASS_MSF << 8 ) | 0x02 )
+#define USB_DEV_RSC_01 ( ( MBG_USB_CLASS_RSC << 8 ) | 0x01 )
-#define USB_DEV_WWVB51USB ( ( MBG_USB_CLASS_WWVB << 8 ) | 0x01 )
-#define USB_DEV_WVB600USB ( ( MBG_USB_CLASS_WWVB << 8 ) | 0x02 )
+#define USB_DEV_SPT_01 ( ( MBG_USB_CLASS_SPT << 8 ) | 0x01 )
-#define USB_DEV_SCU_USB ( ( MBG_USB_CLASS_SCU << 8 ) | 0x01 )
+#define USB_DEV_REL_01 ( ( MBG_USB_CLASS_REL << 8 ) | 0x01 )
-#define USB_DEV_ESI_01 ( ( MBG_USB_CLASS_ESI << 8 ) | 0x01 )
+/// LANTIME CPU quad FTDI serial interface chip
+#define USB_DEV_LAN_CPU_SERIAL ( ( MBG_USB_CLASS_SERIAL << 8 ) | 0x01 )
-#define USB_DEV_FCU_01 ( ( MBG_USB_CLASS_FCU << 8 ) | 0x01 )
+#define USB_DEV_SCG_01 ( ( MBG_USB_CLASS_SCG << 8 ) | 0x01 )
+
+#define USB_DEV_SDI_01 ( ( MBG_USB_CLASS_SDI << 8 ) | 0x01 )
+
+#define USB_DEV_FDM180 ( ( MBG_USB_CLASS_FDM << 8 ) | 0x01 ) // FDM for IMS Systems
+#define USB_DEV_FDM180M ( ( MBG_USB_CLASS_FDM << 8 ) | 0x02 ) // FDM for old Lantime Systems (M300/M600/M900)
+
+#define USB_DEV_MDU300 ( ( MBG_USB_CLASS_MDU << 8 ) | 0x01 )
+#define USB_DEV_MDU312 ( ( MBG_USB_CLASS_MDU << 8 ) | 0x02 )
+
+#define USB_DEV_LUE_01 ( ( MBG_USB_CLASS_LUE << 8 ) | 0x01 )
+
+#define USB_DEV_HPS100 ( ( MBG_USB_CLASS_HPS << 8 ) | 0x01 )
+
+#define USB_DEV_VSG180 ( ( MBG_USB_CLASS_VSG << 8 ) | 0x01 )
+
+#define USB_DEV_GTS180 ( ( MBG_USB_CLASS_GTS << 8 ) | 0x01 )
+
+#define USB_DEV_GRC180 ( ( MBG_USB_CLASS_GRC << 8 ) | 0x01 )
+#define USB_DEV_GRC181 ( ( MBG_USB_CLASS_GRC << 8 ) | 0x02 )
+
+#define USB_DEV_N2X180 ( ( MBG_USB_CLASS_N2X << 8 ) | 0x01 )
+
+#define USB_DEV_USYNCPWR ( ( MBG_USB_CLASS_USYNC << 8 ) | 0x01 ) // MicroSync Power Supply Module
+
+// If new devices are defined here then appropriate definitions should also
+// be added to MBG_USB_DEVICE_NAMES and DEFAULT_MBG_USB_DEVICE_NAMES.
+
+/** @} anchor MBG_USB_DEVICE_IDS */
+
+
+
+/**
+ * @brief Device name strings for Meinberg USB devices
+ *
+ * @see @ref MBG_USB_DEVICE_IDS
+ * @see ::DEFAULT_MBG_USB_DEVICE_NAMES
+ *
+ * @anchor MBG_USB_DEVICE_NAMES @{
+ */
-#define USB_DEV_CPE_01 ( ( MBG_USB_CLASS_CPE << 8 ) | 0x01 )
+#define USB_DEV_NAME_CPC_01 "CPC_01"
+#define USB_DEV_NAME_CPC180 "CPC180"
-#define USB_DEV_GPS180 ( ( MBG_USB_CLASS_GPS << 8 ) | 0x01 )
+#define USB_DEV_NAME_TSU_01 "TSU_01"
-#define USB_DEV_LNO180_01 ( ( MBG_USB_CLASS_LNO << 8 ) | 0x01 )
+#define USB_DEV_NAME_USB5131 "USB5131"
+#define USB_DEV_NAME_DCF600USB "DCF600USB"
+#define USB_DEV_NAME_PZF180 "PZF180"
-#define USB_DEV_LIU_01 ( ( MBG_USB_CLASS_LIU << 8 ) | 0x01 )
+#define USB_DEV_NAME_CMC "CMC"
-#define USB_DEV_LNE_01 ( ( MBG_USB_CLASS_LNE << 8 ) | 0x01 )
+#define USB_DEV_NAME_TCR51USB "TCR51USB"
+#define USB_DEV_NAME_TCR600USB "TCR600USB"
+#define USB_DEV_NAME_TCR180 "TCR180"
+
+#define USB_DEV_NAME_MSF51USB "MSF51USB"
+#define USB_DEV_NAME_MSF600USB "MSF600USB"
+
+#define USB_DEV_NAME_WWVB51USB "WWVB51USB"
+#define USB_DEV_NAME_WVB600USB "WVB600USB"
+
+#define USB_DEV_NAME_SCU_USB "SCU_USB"
+
+#define USB_DEV_NAME_ESI_01 "ESI_01"
+
+#define USB_DEV_NAME_FCU_01 "FCU_01"
+
+#define USB_DEV_NAME_CPE_01 "CPE_01"
+
+#define USB_DEV_NAME_GPS180 "GPS180"
+
+#define USB_DEV_NAME_LNO180 "LNO180"
+
+#define USB_DEV_NAME_LIU_01 "LIU_01"
+
+#define USB_DEV_NAME_LNE_01 "LNE_01"
+#define USB_DEV_NAME_LNE180SFP "LNE180SFP"
+
+#define USB_DEV_NAME_MRI_01 "MRI_01"
+
+#define USB_DEV_NAME_BPE_01 "BPE_01"
+
+#define USB_DEV_NAME_RSC_01 "RSC_01"
+
+#define USB_DEV_NAME_SPT_01 "SPT_01"
+
+#define USB_DEV_NAME_REL_01 "REL_01"
+
+#define USB_DEV_NAME_LAN_CPU_SERIAL "LAN_CPU_SERIAL"
+
+#define USB_DEV_NAME_SCG_01 "SCG_01"
+
+#define USB_DEV_NAME_SDI_01 "SDI_01"
+
+#define USB_DEV_NAME_FDM180 "FDM180"
+#define USB_DEV_NAME_FDM180M "FDM180M"
+
+#define USB_DEV_NAME_MDU300 "MDU300"
+#define USB_DEV_NAME_MDU312 "MDU312"
+
+#define USB_DEV_NAME_LUE_01 "LUE_01"
+
+#define USB_DEV_NAME_HPS100 "HPS100"
+
+#define USB_DEV_NAME_VSG180 "VSG180"
+
+#define USB_DEV_NAME_GTS180 "GTS180"
+
+#define USB_DEV_NAME_GRC180 "GRC180"
+#define USB_DEV_NAME_GRC181 "GRC181"
+
+#define USB_DEV_NAME_N2X180 "N2X180"
+
+#define USB_DEV_NAME_USYNCPWR "MICROSYNC-PWR"
+
+/** @} anchor MBG_USB_DEVICE_NAMES */
+
+
+
+/**
+ * @brief Initializer for a table of USB device ISs and name strings
+ *
+ * Can be used e.g. to initialize an array of ::MBG_CODE_NAME_TABLE_ENTRY.
+ *
+ * @see @ref MBG_USB_DEVICE_IDS
+ * @see @ref MBG_USB_DEVICE_NAMES
+ */
+#define DEFAULT_MBG_USB_DEVICE_NAMES \
+{ \
+ { USB_DEV_CPC_01, USB_DEV_NAME_CPC_01 }, \
+ { USB_DEV_CPC180, USB_DEV_NAME_CPC180 }, \
+ { USB_DEV_TSU_01, USB_DEV_NAME_TSU_01 }, \
+ { USB_DEV_USB5131, USB_DEV_NAME_USB5131 }, \
+ { USB_DEV_DCF600USB, USB_DEV_NAME_DCF600USB }, \
+ { USB_DEV_CMC, USB_DEV_NAME_CMC }, \
+ { USB_DEV_TCR51USB, USB_DEV_NAME_TCR51USB }, \
+ { USB_DEV_TCR600USB, USB_DEV_NAME_TCR600USB }, \
+ { USB_DEV_TCR180, USB_DEV_NAME_TCR180 }, \
+ { USB_DEV_MSF51USB, USB_DEV_NAME_MSF51USB }, \
+ { USB_DEV_MSF600USB, USB_DEV_NAME_MSF600USB }, \
+ { USB_DEV_WWVB51USB, USB_DEV_NAME_WWVB51USB }, \
+ { USB_DEV_WVB600USB, USB_DEV_NAME_WVB600USB }, \
+ { USB_DEV_SCU_USB, USB_DEV_NAME_SCU_USB }, \
+ { USB_DEV_ESI_01, USB_DEV_NAME_ESI_01 }, \
+ { USB_DEV_FCU_01, USB_DEV_NAME_FCU_01 }, \
+ { USB_DEV_CPE_01, USB_DEV_NAME_CPE_01 }, \
+ { USB_DEV_GPS180, USB_DEV_NAME_GPS180 }, \
+ { USB_DEV_LNO180, USB_DEV_NAME_LNO180 }, \
+ { USB_DEV_LIU_01, USB_DEV_NAME_LIU_01 }, \
+ { USB_DEV_LNE_01, USB_DEV_NAME_LNE_01 }, \
+ { USB_DEV_MRI_01, USB_DEV_NAME_MRI_01 }, \
+ { USB_DEV_BPE_01, USB_DEV_NAME_BPE_01 }, \
+ { USB_DEV_RSC_01, USB_DEV_NAME_RSC_01 }, \
+ { USB_DEV_SPT_01, USB_DEV_NAME_SPT_01 }, \
+ { USB_DEV_REL_01, USB_DEV_NAME_REL_01 }, \
+ { USB_DEV_LAN_CPU_SERIAL, USB_DEV_NAME_LAN_CPU_SERIAL }, \
+ { USB_DEV_SCG_01, USB_DEV_NAME_SCG_01 }, \
+ { USB_DEV_SDI_01, USB_DEV_NAME_SDI_01 }, \
+ { USB_DEV_FDM180, USB_DEV_NAME_FDM180 }, \
+ { USB_DEV_MDU300, USB_DEV_NAME_MDU300 }, \
+ { USB_DEV_LUE_01, USB_DEV_NAME_LUE_01 }, \
+ { USB_DEV_HPS100, USB_DEV_NAME_HPS100 }, \
+ { USB_DEV_VSG180, USB_DEV_NAME_VSG180 }, \
+ { USB_DEV_LNE180SFP, USB_DEV_NAME_LNE180SFP }, \
+ { USB_DEV_GTS180, USB_DEV_NAME_GTS180 }, \
+ { USB_DEV_GRC180, USB_DEV_NAME_GRC180 }, \
+ { USB_DEV_GRC181, USB_DEV_NAME_GRC181 }, \
+ { USB_DEV_N2X180, USB_DEV_NAME_N2X180 }, \
+ { USB_DEV_MDU312, USB_DEV_NAME_MDU312 }, \
+ { USB_DEV_PZF180, USB_DEV_NAME_PZF180 }, \
+ { USB_DEV_USYNCPWR, USB_DEV_NAME_USYNCPWR }, \
+ { USB_DEV_FDM180M, USB_DEV_NAME_FDM180M }, \
+ { 0, /* end of table */ NULL } \
+}
-#define USB_DEV_MRI_01 ( ( MBG_USB_CLASS_MRI << 8 ) | 0x01 )
-#define USB_DEV_BPE_01 ( ( MBG_USB_CLASS_BPE << 8 ) | 0x01 )
enum
{
diff --git a/mbglib/common/words.h b/mbglib/common/words.h
index 0331508..26057d6 100755
--- a/mbglib/common/words.h
+++ b/mbglib/common/words.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: words.h 1.31 2012/11/29 11:54:39 martin REL_M $
+ * $Id: words.h 1.39 2017/03/15 10:01:09 martin REL_M $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,7 +10,33 @@
*
* -----------------------------------------------------------------------
* $Log: words.h $
- * Revision 1.31 2012/11/29 11:54:39 martin
+ * Revision 1.39 2017/03/15 10:01:09 martin
+ * Added comments how to represent negative numbers in NANO_TIME
+ * and NANO_TIME_64 structures.
+ * Added macros _nano_time_zero() and _nano_time_64_zero().
+ * Revision 1.38 2017/02/22 11:56:33 martin
+ * Made MBG_CODE_NAME_TABLE_ENTRY::code signed to
+ * avoid signed/unsigned warnings with some code tables.
+ * Revision 1.37 2017/01/27 12:24:35Z martin
+ * Moved STRINGIFY() macro here.
+ * Revision 1.36 2017/01/27 08:59:43 martin
+ * Fixed macro syntax.
+ * Revision 1.35 2016/08/05 12:17:21 martin
+ * Moved definitions for NANO_TIME and NANO_TIME_64 here.
+ * New macro _nano_time_64_negative().
+ * Conditionally define _abs64() macro.
+ * Include <inttypes.h> for Keil ARMCC target.
+ * Added some conditional debugging code.
+ * Fixed some spelling.
+ * Revision 1.34 2014/10/20 12:31:20 martin
+ * Moved macro _isdigit() here.
+ * Revision 1.33 2014/05/27 10:18:35Z martin
+ * Finer control of which types are required for or already
+ * available on particular target systems.
+ * Added macros helpful to simplify declarations of code/name tables.
+ * Revision 1.32 2014/01/07 15:43:52 martin
+ * Define __mbg_inline for ARM firmware targets.
+ * Revision 1.31 2012/11/29 11:54:39Z martin
* Removed #if sizeof() definitions which may cause build errors
* with some older compilers.
* Include stdbool.h for __ARMCC_VERSION targets.
@@ -113,7 +139,9 @@
#include <mbg_tgt.h>
#else
#if defined( __ARMCC_VERSION ) // Keil RealView Compiler for ARM
+ #define __mbg_inline __inline
#include <stdint.h>
+ #include <inttypes.h>
#include <stdbool.h>
#define MBG_TGT_HAS_EXACT_SIZE_TYPES 1
#else
@@ -187,7 +215,7 @@
// The build environment does not support 64 bit types. However,
// 64 bit types need to be defined to avoid build errors
// if these types are formally used in function prototypes.
- // We explicitely use abnormal data types to hopefully
+ // We explicitly use abnormal data types to hopefully
// cause compiler errors in case these types are
// unexpectedly used to generate real code for a target
// platform which does not support 64 bit types.
@@ -216,67 +244,176 @@
#define MBG_TGT_HAS_64BIT_TYPES 1
+ #if !defined( MBG_TGT_HAS_ABS64 )
+ #define _abs64( _i ) ( (int64_t) ( ( (_i) < 0 ) ? -(_i) : (_i) ) )
+ #endif
+
#endif
// Some commonly used types
-typedef unsigned char uchar;
+#if !defined( _UCHAR_DEFINED )
+ typedef unsigned char uchar;
+ #define uchar uchar
+#endif
-#if !defined( MBG_TGT_LINUX ) \
- && !( defined ( MBG_TGT_NETBSD ) \
- && defined ( MBG_TGT_KERNEL ) )
+#if !defined( _USHORT_DEFINED )
typedef unsigned short ushort;
+ #define ushort ushort
+#endif
+
+#if !defined( _UINT_DEFINED )
typedef unsigned int uint;
+ #define uint uint
+#endif
+
+#if !defined( _ULONG_DEFINED )
typedef unsigned long ulong;
+ #define ulong ulong
#endif
-typedef double udouble;
+#if !defined( _UDOUBLE_DEFINED )
+ typedef double udouble;
+ #define udouble udouble
+#endif
-typedef unsigned char byte;
-typedef unsigned short word;
-typedef unsigned long longword;
-typedef unsigned long dword;
+#if !defined( _BYTE_DEFINED )
+ typedef unsigned char byte;
+ #define byte byte
+#endif
+#if !defined( _WORD_DEFINED )
+ typedef unsigned short word;
+ #define word word
+#endif
-#if !defined( _BIT_DEFINED )
+#if !defined( _LONGWORD_DEFINED )
+ typedef unsigned long longword;
+ #define longword longword
+#endif
+
+#if !defined( _DWORD_DEFINED )
+// typedef unsigned long dword;
+// #define dword dword
+#endif
- // We need to implement a "bit" type. Preferably we use "bool"
- // to do this, but this is only supported by C++ compilers, and
- // by C compilers supporting the C99 standard.
- #if !defined( MBG_TGT_MISSING_BOOL_TYPE ) && \
- ( defined( __cplusplus ) || defined( __bool_true_false_are_defined ) )
+#if defined( MBG_TGT_MISSING_BOOL_TYPE )
+ //#error MBG_TGT_MISSING_BOOL_TYPE is defined
+ // BDS/Borland C++ Builder 2006 (non-C++ mode)
+ // Borland C++ Builder 5 (non-C++ mode)
+ // BC 3.1
+ // VC6
+ // DDKbuild
+ // VS2008
+#endif
- typedef bool bit;
+#if defined( __cplusplus )
+ //#error __cplusplus is defined
+#endif
- #else // C99 types not supported
+#if defined( __bool_true_false_are_defined )
+ //#error __bool_true_false_are_defined is defined
+ // Keil armcc
+ // gcc / Linux user space
+ // clang / FreeBSD user space and kernel
+#endif
- // Falling back to use "int" for "bit". This prevents error
- // messages if "bit" is used in function prototypes, but may
- // yield unexpected results for code like:
- // return (bit) ( val & 0x10 );
- typedef int bit;
+#if defined( MBG_TGT_MISSING_BOOL_TYPE ) /* from mbg_tgt.h */ \
+ || ( !defined( __cplusplus ) /* C++ */ \
+ && !defined( __bool_true_false_are_defined ) /* C99 */ \
+ && !defined( _LINUX_TYPES_H ) )
+
+ // There's no native support for a "bool" type, so we
+ // need a substitute.
+
+ #if defined( _BIT_DEFINED )
+ // A native "bit" type is supported, so we use it for bool.
+ //#error substituting bit for bool
+ // C166
+ typedef bit bool;
+ #else
+ // Fall back to "int". This is just a hack which
+ // may yield unexpected results with code like:
+ // return (bool) ( val & 0x10 );
+ // A safe way of coding would be:
+ // return (bool) ( ( val & 0x10 ) != 0 );
+ //#error substituting int for bool
+ // Borland C++ Builder 5
+ // BC 3.1
+ // VC6
+ // DDKbuild
+ // VS2008
+ typedef int bool;
#endif
+ // Eventually provoke a build error if the build
+ // environment unexpectedly supports "bool" natively.
+ #define bool bool
+ #define true 1
+ #define false 0
+#else
+ //#error native bool type supported
+ // Borland C++ Builder 5 and newer (C++ mode only)
+ // Keil armcc
+ // gcc / Linux user space
+ // gcc / Linux kernel
+ // clang / FreeBSD user space and kernel
+#endif
+
+
+#if !defined( _BIT_DEFINED )
+
+ // There's no native support for a "bit" type, so we
+ // need a substitute. The "bool" type would fit best
+ // and should be fine if it's supported natively.
+ //
+ // However, if "bool" has been substituted above
+ // by "int"then this is just a hack which may yield
+ // unexpected results with code like:
+ // return (bit) ( val & 0x10 );
+ // A safe way of coding would be:
+ // return (bit) ( ( val & 0x10 ) != 0 );
+
+ //#error substituting bool for bit
+ // Keil armcc
+ // Borland C++ Builder 5
+ // BC 3.1
+ // VC6
+ // DDKbuild
+ // VS2008
+ // gcc / Linux user space
+ // gcc / Linux kernel
+ // clang / FreeBSD user space and kernel
+ typedef bool bit;
+
+ // Eventually provoke a build error if the build
+ // environment unexpectedly supports "bit" natively.
+ #define bit bit
+
#define _BIT_REDEFINED 1
+#else
+ //#error native bit type supported
+ // C166
#endif
-#define BYTE_0( _x ) ( ( (ulong) (_x) ) & 0xFF )
-#define BYTE_1( _x ) ( ( ( (ulong) (_x) ) >> 8 ) & 0xFF )
-#define BYTE_2( _x ) ( ( ( (ulong) (_x) ) >> 16 ) & 0xFF )
-#define BYTE_3( _x ) ( ( ( (ulong) (_x) ) >> 24 ) & 0xFF )
+#define BYTE_0( _x ) ( (uint8_t ) ( (_x) & 0xFF ) )
+#define BYTE_1( _x ) ( (uint8_t ) ( ( ( (uint16_t) (_x) ) >> 8 ) & 0xFF ) )
+#define BYTE_2( _x ) ( (uint8_t ) ( ( ( (uint32_t) (_x) ) >> 16 ) & 0xFF ) )
+#define BYTE_3( _x ) ( (uint8_t ) ( ( ( (uint32_t) (_x) ) >> 24 ) & 0xFF ) )
-#define HI_BYTE( _x ) ( (_x) >> 8 )
-#define LO_BYTE( _x ) ( (_x) & 0xFF )
-#define HI_WORD( _x ) ( (_x) >> 16 )
-#define LO_WORD( _x ) ( (_x) & 0xFFFF )
+#define HI_BYTE( _x ) ( (uint8_t ) ( (_x) >> 8 ) )
+#define LO_BYTE( _x ) ( (uint8_t ) ( (_x) & 0xFF ) )
+
+#define HI_WORD( _x ) ( (uint16_t ) ( (_x) >> 16 ) )
+#define LO_WORD( _x ) ( (uint16_t ) ( (_x) & 0xFFFF ) )
// the macros below assume little endianess
// these macros expect the name of a variable
@@ -333,9 +470,36 @@ typedef unsigned long dword;
#endif
+
+#define _set_array_bit( _n, _byte_array, _max_bytes ) \
+do \
+{ \
+ int byte_idx = (_n) >> 3; \
+ \
+ if ( byte_idx < _max_bytes ) \
+ _byte_array[byte_idx] |= ( 1 << ( (_n) & 0x07 ) ); \
+ \
+} while ( 0 )
+
+
+#define _clear_array_bit( _n, _byte_array, _max_bytes ) \
+do \
+{ \
+ int byte_idx = (_n) >> 3; \
+ \
+ if ( byte_idx < _max_bytes ) \
+ _byte_array[byte_idx] &= ~( 1 << ( (_n) & 0x07 ) ); \
+ \
+} while ( 0 )
+
+
+
+#define _isdigit( _c ) ( (_c) >= '0' && (_c) <= '9' )
+
+
// A macro function which can safely be used without
// side effects as a macro doing nothing.
-// This is useful to define debug macros away in
+// This is useful to define debug macros away in
// release builds, etc.
#if !defined( _nop_macro_fnc )
#define _nop_macro_fnc() do {} while (0)
@@ -347,10 +511,147 @@ typedef unsigned long dword;
*/
typedef struct
{
- ulong code;
+ long code;
const char *name;
+
} MBG_CODE_NAME_TABLE_ENTRY;
+/**
+ * @brief A macro defining a ::MBG_CODE_NAME_TABLE_ENTRY
+ *
+ * The stringified parameter is used for the name.
+ *
+ * @param _n The symbolic name of the numeric code
+ */
+#define _mbg_cn_table_entry( _n ) { _n, #_n }
+
+/**
+ * @brief A macro defining an empty ::MBG_CODE_NAME_TABLE_ENTRY
+ *
+ * This is used to terminate a table.
+ */
+#define _mbg_cn_table_end() { 0, NULL }
+
+
+
+/**
+ * @brief A timestamp with nanosecond resolution
+ *
+ * @note If the structure is to represent a negative value then both the
+ * fields nano_secs and secs have to be set to the negative values.
+ * Otherwise the sign of the represented number was ambiguous if either
+ * of the fields was accidentally 0, and only the other field was not 0.
+ * The macro ::_nano_time_negative should always be used to determine
+ * if the sign of the represented value is negative, or not.
+ *
+ * @note The secs field will roll over on 2038-01-19 03:14:07
+ * if used for the number of seconds since 1970-01-01, just like
+ * 32 bit POSIX time_t.
+ *
+ * @see ::_nano_time_negative
+ * @see ::_nano_time_zero
+ * @see ::NANO_TIME_64
+ */
+typedef struct
+{
+ // ATTENTION:
+ // This structure is and has has been used in public API calls for a long time,
+ // so even though the order of member fields is different than in NANO_TIME_64
+ // this must *NOT* be changed, or API compatibility will get lost!
+ int32_t nano_secs; ///< [nanoseconds]
+ int32_t secs; ///< [seconds], usually since 1970-01-01 00:00:00
+
+} NANO_TIME;
+
+#define _mbg_swab_nano_time( _p ) \
+do \
+{ \
+ _mbg_swab32( &(_p)->nano_secs ); \
+ _mbg_swab32( &(_p)->secs ); \
+} while ( 0 )
+
+/**
+ * Check if the value of the ::NANO_TIME structure _nt is negative
+ */
+#define _nano_time_negative( _nt ) \
+ ( ( (_nt)->secs < 0 ) || ( (_nt)->nano_secs < 0 ) )
+
+/**
+ * Check if the value of the ::NANO_TIME structure _nt is 0
+ */
+#define _nano_time_zero( _nt ) \
+ ( ( (_nt)->secs == 0 ) && ( (_nt)->nano_secs == 0 ) )
+
+
+
+/**
+ * @brief A timestamp with nanosecond resolution, but 64 bit size
+ *
+ * @note If the structure is to represent a negative value then both the
+ * fields nano_secs and secs have to be set to the negative values.
+ * Otherwise the sign of the represented number was ambiguous if either
+ * of the fields was accidentally 0, and only the other field was not 0.
+ * The macro ::_nano_time_64_negative should always be used to determine
+ * if the sign of the represented value is negative, or not.
+ *
+ * @see ::_nano_time_64_negative
+ * @see ::_nano_time_64_zero
+ * @see ::NANO_TIME
+ */
+typedef struct
+{
+ // ATTENTION:
+ // This structure is and has been used in public API calls for a long time,
+ // so even though the order of member fields is different than in NANO_TIME
+ // this must *NOT* be changed, or API compatibility will get lost!
+ int64_t secs; ///< [seconds], usually since 1970-01-01 00:00:00
+ int64_t nano_secs; ///< [nanoseconds]
+
+} NANO_TIME_64;
+
+#define _mbg_swab_nano_time_64( _p ) \
+do \
+{ \
+ _mbg_swab64( &(_p)->secs ); \
+ _mbg_swab64( &(_p)->nano_secs ); \
+} while ( 0 )
+
+/**
+ * Check if the value of the ::NANO_TIME_64 structure _nt is negative
+ */
+#define _nano_time_64_negative( _nt ) \
+ ( ( (_nt)->secs < 0 ) || ( (_nt)->nano_secs < 0 ) )
+
+/**
+ * Check if the value of the ::NANO_TIME_64 structure _nt is 0
+ */
+#define _nano_time_64_zero( _nt ) \
+ ( ( (_nt)->secs == 0 ) && ( (_nt)->nano_secs == 0 ) )
+
+
+
+/**
+ * @brief Make a string from a constant definition
+ *
+ * This macro can be used e.g. to define a constant string on the
+ * compiler's command line, e.g. like -DVERSION_STRING="v1.0 BETA".
+ * Source code like
+ * @code{.c}
+ const char version_string[] = VERSION_STRING;
+ * @endcode
+ *
+ * may not work for every compiler since the double quotes
+ * in VERSION_STRING may be removed when the definition is evaluated.
+ * A proper solution is to use the STRINGIFY() macro defined here:
+ * @code{.c}
+ const char version_string[] = STRINGIFY( VERSION_STRING );
+ * @endcode
+ */
+#define STRINGIFY(x) XSTRINGIFY(x)
+
+// The XSTRINGIFY() macro is just a helper macro to implement STRINGIFY()
+// and should not be used alone.
+#define XSTRINGIFY(x) #x
/* End of header body */
diff --git a/mbglib/common/xdevfeat.c b/mbglib/common/xdevfeat.c
new file mode 100755
index 0000000..5d5d17c
--- /dev/null
+++ b/mbglib/common/xdevfeat.c
@@ -0,0 +1,1556 @@
+
+/**************************************************************************
+ *
+ * $Id: xdevfeat.c 1.1.1.28.1.13 2017/04/20 04:58:10 thomas-b TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Meinberg API functions to check extended device features.
+ *
+ * See notes near "defgroup xdevfeat_chk_supp_fncs" in xdevfeat.h.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: xdevfeat.c $
+ * Revision 1.1.1.28.1.13 2017/04/20 04:58:10 thomas-b
+ * Added function to check for extended features MBG_XFEATURE_USB_LOCK
+ * Revision 1.1.1.28.1.12 2017/03/07 13:45:34 thomas-b
+ * Check receiver info feature instead of builtin feature for ignore lock
+ * Revision 1.1.1.28.1.11 2017/02/22 11:32:47 martin
+ * Fixed warnings due to preliminary, unfinished code.
+ * Revision 1.1.1.28.1.10 2017/02/07 14:24:09 thomas-b
+ * Added function xdevfeat_has_monitoring, which checks if the extended feature MBG_XFEATURE_MONITORING is set
+ * Revision 1.1.1.28.1.9 2017/02/07 14:10:36 daniel
+ * Check license feature types
+ * Revision 1.1.1.28.1.8 2016/12/06 10:43:37 thomas-b
+ * Added function xdevfeat_has_sv_info
+ * Revision 1.1.1.28.1.7 2016/12/01 13:47:49 philipp
+ * Moved helper function check_byte_array_bit from xdevfeat.c to xtiocomm.c and make it public
+ * Revision 1.1.1.28.1.6 2016/11/30 16:12:26 thomas-b
+ * Added function xdevfeat_has_scu_stat
+ * Revision 1.1.1.28.1.5 2016/11/22 10:33:16 philipp
+ * Implemented I/O ports
+ * Revision 1.1.1.28.1.4 2016/11/02 12:16:18 thomas-b
+ * Fixed documentation
+ * Revision 1.1.1.28.1.3 2016/11/02 12:08:21 thomas-b
+ * Added function to check for new MBG_XFEATURE_REQ_TTM
+ * Revision 1.1.1.28.1.2 2016/11/01 09:34:43 martin
+ * Doxygen fixes.
+ * Revision 1.1.1.28.1.1 2016/10/25 08:07:54 martin
+ * Merged changes from 1.1.1.23.1.x.
+ * Revision 1.1.1.28 2016/10/20 14:46:04 thomas-b
+ * Added function to check if XBP is supported
+ * Revision 1.1.1.27 2016/10/20 10:43:36 thomas-b
+ * Added function to check if a device is a bus level device
+ * Revision 1.1.1.26 2016/10/14 11:09:41 thomas-b
+ * Added function to check MBG_XFEATURE_UCAP_NET
+ * Revision 1.1.1.25 2016/09/29 14:35:35 thomas-b
+ * Added function to check reboot feature
+ * Revision 1.1.1.24 2016/09/29 12:19:59 thomas-b
+ * Added function to check transactions feature
+ * Revision 1.1.1.23 2016/07/07 15:04:11 martin
+ * Renamed functions due to renamed library symbols.
+ * Revision 1.1.1.22 2016/06/15 10:15:51 thomas-b
+ * Added functions which check if the user capture feature is supported by a device
+ * Revision 1.1.1.21 2016/06/14 10:33:23 thomas-b
+ * Added functions which check if the event log feature is supported by a device
+ * Revision 1.1.1.20 2016/06/07 07:43:08 philipp
+ * New function to check for Irig Rx feature
+ * Revision 1.1.1.19 2016/06/02 10:15:40 philipp
+ * Renaming all MBG_EXT_REV_INFO related stuff to MBG_EXT_SYS_INFO.
+ * Revision 1.1.1.18 2016/05/30 08:10:47 thomas-b
+ * Added functions to check several builtin features
+ * Revision 1.1.1.17 2016/05/20 09:41:38 thomas-b
+ * Removed functions which check for a specific IMS card
+ * Revision 1.1.1.16 2016/05/20 08:50:46 thomas-b
+ * Added functions xdevfeat_has_time_scale and xdevfeat_has_tzcode
+ * Revision 1.1.1.15 2016/05/17 06:33:12 philipp
+ * New function to check whether a device has serial outputs
+ * Revision 1.1.1.14 2016/05/12 10:41:40 philipp
+ * New functions to check bpe card and IRIG Tx feature
+ * Revision 1.1.1.13 2016/05/10 06:15:32 philipp
+ * New function to check whether a device has programmable pulses
+ * Revision 1.1.1.12 2016/04/26 06:52:46 thomas-b
+ * Added functions to check if NET_CFG and LAN_IP4 APIs are supported
+ * Revision 1.1.1.11 2016/04/22 10:54:01 philipp
+ * New function to check whether device is LIU
+ * Revision 1.1.1.10 2016/04/20 13:21:06 thomas-b
+ * Added function to check if a device supports NTP
+ * Revision 1.1.1.9 2016/04/20 09:26:03 philipp
+ * Moved all HPS-PTP related structures to gpspriv.h and removed related extended feature bit from gpsdefs.h.
+ * Also removed functions from mbgextio and xdevfeat since HPS-PTP handling needs a redesign concerning structures.
+ * Thus, handle everything explicitly for now!
+ * -> Redesing this A.S.A.P.!!!
+ * Revision 1.1.1.8 2016/04/15 08:17:27 philipp
+ * New feature MBG_XFEATURE_EXT_PTP
+ * Revision 1.1.1.7 2016/04/13 07:01:22 philipp
+ * New function to check whether device is HPS
+ * Revision 1.1.1.6 2016/04/12 13:27:42 philipp
+ * Several new functions to check for device models and device features
+ * Revision 1.1.1.5 2016/04/11 13:57:13 thomas-b
+ * Added function xdevfeat_has_xmulti_ref
+ * Revision 1.1.1.4 2016/04/07 12:36:37 martin
+ * New function xdevfeat_has_ext_rev_info().
+ * Revision 1.1.1.3 2016/04/04 15:31:25 martin
+ * New function xdevfeat_is_vsg().
+ * Revision 1.1.1.2 2016/03/24 14:08:52 martin
+ * *** empty log message ***
+ * Revision 1.1.1.1 2016/03/18 10:48:10 martin
+ * *** empty log message ***
+ * Revision 1.1 2016/03/16 14:32:52 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#define _XDEVFEAT
+ #include <xdevfeat.h>
+#undef _XDEVFEAT
+
+#include <mbgerror.h>
+#include <xtiocomm.h>
+
+
+
+typedef uint32_t BUILTIN_FEATURE_MASK;
+
+
+/**
+ * @brief Entry for a table to specify model-depending built-in features
+ */
+typedef struct
+{
+ /// Model code according to ::RECEIVER_INFO::model_code, see ::GPS_MODEL_CODES
+ uint16_t model_code;
+
+ /// A combination of @ref GPS_FEATURE_MASKS bit masks specifying the
+ /// built-in features supported by the specified device model.
+ BUILTIN_FEATURE_MASK feature_mask;
+
+} BUILTIN_FEATURE_TABLE_ENTRY;
+
+
+/**
+ * @brief A static table of builtin features
+ *
+ * Used to lookup the builtin features of a particular device model.
+ */
+static BUILTIN_FEATURE_TABLE_ENTRY builtin_feature_table[] = GPS_MODEL_BUILTIN_FEATURES;
+
+
+
+static /*HDR*/
+/**
+ * @brief Check if a device supports a specific built-in feature or API
+ *
+ * Some features or API calls are implicitly supported by particular devices.
+ * This function uses the ::RECEIVER_INFO::model_code to look up the specific
+ * device in a table of ::BUILTIN_FEATURE_TABLE_ENTRY entries, and checks if
+ * the requested feature bits are set for this device model.
+ * If the model code of the specific device can't be found in the table then
+ * then ::MBG_ERR_DEV_NOT_SUPP is returned and the source code files probably
+ * need to be updated to support this device.
+ *
+ * @param[in] msk One of the @ref GPS_FEATURE_MASKS bit masks
+ * @param[in] p_ri A ::RECEIVER_INFO structure read from the device before
+ *
+ * @return ::MBG_SUCCESS if all specified mask bits are set in ::RECEIVER_INFO::features,
+ * ::MBG_ERR_NOT_SUPP_BY_DEV if the bits are not set, and ::MBG_ERR_DEV_NOT_SUPP
+ * if the model code can't be found in the table.
+ */
+int check_builtin_feature( BUILTIN_FEATURE_MASK msk, const RECEIVER_INFO *p_ri )
+{
+ BUILTIN_FEATURE_TABLE_ENTRY *p;
+
+ //### TODO Implement a kind of cache so we don't have to search the whole
+ // table if several features of the same device are checked after each other.
+
+ for ( p = builtin_feature_table; p->model_code || p->feature_mask; p++ )
+ if ( p->model_code == p_ri->model_code )
+ return ( ( p->feature_mask & msk ) == msk ) ? MBG_SUCCESS : MBG_ERR_NOT_SUPP_BY_DEV;
+
+ return MBG_ERR_DEV_NOT_SUPP;
+
+} // check_builtin_feature
+
+
+
+static /*HDR*/
+/**
+ * @brief Check if a device supports a specific feature or API
+ *
+ * This API call checks if a specific feature or API is supported
+ * according to the ::RECEIVER_INFO::features mask read from the device.
+ *
+ * @param[in] msk One of the @ref GPS_FEATURE_MASKS bit masks
+ * @param[in] p_ri A ::RECEIVER_INFO structure read from the device before
+ *
+ * @return ::MBG_SUCCESS if all specified mask bits are set in ::RECEIVER_INFO::features,
+ * else ::MBG_ERR_NOT_SUPP_BY_DEV
+ */
+int check_ri_feature( RI_FEATURES msk, const RECEIVER_INFO *p_ri )
+{
+ return ( ( p_ri->features & msk ) == msk ) ? MBG_SUCCESS : MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // check_ri_feature
+
+
+
+static /*HDR*/
+/**
+ * @brief Check if a specific extended feature is supported
+ *
+ * This API call checks if a specific extended feature or API is supported
+ * according to the ::MBG_XFEATURE_BUFFER read from the device.
+ *
+ * @param[in] xf_bit One of the ::MBG_XFEATURE_BITS
+ * @param[in] xv_buf Pointer to a ::MBG_XFEATURE_BUFFER read from the device before
+ *
+ * @return ::MBG_SUCCESS if the specified feature bit is set, else ::MBG_ERR_NOT_SUPP_BY_DEV or ::MBG_ERR_RANGE
+ *
+ * @see ::check_byte_array_bit
+ */
+int check_xfeature( int xf_bit, const MBG_XFEATURE_BUFFER *xv_buf )
+{
+ return check_byte_array_bit( xf_bit, xv_buf->b, sizeof( xv_buf->b ) );
+
+} // check_xfeature
+
+
+
+#if defined( _PRELIMINARY_CODE ) //### TODO do we need this?
+
+static /*HDR*/
+/**
+ * @brief Check if a specific bit is set in TLV's byte array.
+ *
+ * This API call checks if a specific TLV feature is supported according to
+ * the ::MBG_TLV_INFO read from the device.
+ *
+ * @param[in] tlv_feat_bit One of the ::MBG_TLV_FEAT_TYPES
+ * @param[in] tlv_info Pointer to a ::MBG_TLV_INFO read from the device before
+ *
+ * @return ::MBG_SUCCESS if the specified feature bit is set, else ::MBG_ERR_NOT_SUPP_BY_DEV or ::MBG_ERR_RANGE
+ *
+ * @see ::check_byte_array_bit
+ */
+int check_tlv_feat_supp( int tlv_feat_bit, const MBG_TLV_INFO *tlv_info )
+{
+ return check_byte_array_bit( tlv_feat_bit, tlv_info->supp_tlv_feat.b, sizeof( tlv_info->supp_tlv_feat.b ) );
+
+} // check_tlv_feat_supp
+
+#endif // defined( _PRELIMINARY_CODE )
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device can receive the GPS satellite system
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_is_gps
+ * @see ::mbg_chk_dev_is_gps
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_gps( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_IS_GPS, &p_xdf->receiver_info );
+
+} // xdevfeat_is_gps
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_is_gps;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the GNSS API
+ *
+ * This is usually supported by devices which can receive signals
+ * from different satellite systems, e.g. GPS, GLONASS, ...
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_is_gnss
+ * @see ::mbg_chk_dev_is_gnss
+ * @see ::MBG_GNSS_TYPES
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_gnss( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_IS_GNSS, &p_xdf->receiver_info );
+
+} // xdevfeat_is_gnss
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_is_gnss;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a time code receiver (IRIG or similar)
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_is_tcr //### TODO
+ * @see ::mbg_chk_dev_is_tcr //### TODO
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_tcr( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_IS_TCR, &p_xdf->receiver_info );
+
+} // xdevfeat_is_tcr
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_is_tcr;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a DCF77 AM receiver
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_is_dcf //### TODO
+ * @see ::mbg_chk_dev_is_dcf
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_dcf( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_IS_DCF_AM, &p_xdf->receiver_info );
+
+} // xdevfeat_is_dcf_am
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_is_dcf;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device can receive DCF77 PZF
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_has_pzf //### TODO
+ * @see ::mbg_chk_dev_has_pzf
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_pzf( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_IS_DCF_PZF, &p_xdf->receiver_info );
+
+} // xdevfeat_has_pzf
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_pzf;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is an MSF receiver
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_msf( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_IS_MSF, &p_xdf->receiver_info );
+
+} // xdevfeat_is_msf
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_is_msf;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a JJY receiver
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_jjy( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_IS_JJY, &p_xdf->receiver_info );
+
+} // xdevfeat_is_jjy
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_is_jjy;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a WWVB receiver
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_wwvb( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_IS_WWVB, &p_xdf->receiver_info );
+
+} // xdevfeat_is_wwvb
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_is_wwvb;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device is a bus level device
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_bus_lvl_dev( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_IS_BUS_LVL_DEV, &p_xdf->receiver_info );
+
+} // xdevfeat_is_bus_lvl_dev
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_is_bus_lvl_dev;
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ims( const MBG_XDEV_FEATURES *p_xdf )
+{
+ if ( mbg_rc_is_success( check_ri_feature( GPS_HAS_IMS, &p_xdf->receiver_info ) ) )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // xdevfeat_has_ims
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_ims;
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_gpio( const MBG_XDEV_FEATURES *p_xdf )
+{
+ if ( mbg_rc_is_success( check_ri_feature( GPS_HAS_GPIO, &p_xdf->receiver_info ) ) )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // xdevfeat_has_gpio
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_gpio;
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_synth( const MBG_XDEV_FEATURES *p_xdf )
+{
+ if ( mbg_rc_is_success( check_ri_feature( GPS_HAS_SYNTH, &p_xdf->receiver_info ) ) )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // xdevfeat_has_synth
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_synth;
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_prog_pulses( const MBG_XDEV_FEATURES *p_xdf )
+{
+ const RECEIVER_INFO *ri = &p_xdf->receiver_info;
+
+ if ( ri->n_prg_out > 0 )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // xdevfeat_has_prog_pulses
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_prog_pulses;
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_irig_tx( const MBG_XDEV_FEATURES *p_xdf )
+{
+ if ( mbg_rc_is_success( check_ri_feature( GPS_HAS_IRIG_TX, &p_xdf->receiver_info ) ) )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // xdevfeat_has_irig_tx
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_irig_tx;
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_irig_rx( const MBG_XDEV_FEATURES *p_xdf )
+{
+ if ( mbg_rc_is_success( check_ri_feature( GPS_HAS_IRIG_RX, &p_xdf->receiver_info ) ) )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // xdevfeat_has_irig_rx
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_irig_rx;
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_serouts( const MBG_XDEV_FEATURES *p_xdf )
+{
+ const RECEIVER_INFO *ri = &p_xdf->receiver_info;
+
+ if ( ri->n_com_ports > 0 )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // xdevfeat_has_serouts
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_serouts;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::BVAR_STAT structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_bvar_stat( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_BVAR_STAT, &p_xdf->receiver_info );
+
+} // xdevfeat_has_bvar_stat
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_bvar_stat;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports reading the position as ::XYZ array
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_pos_xyz( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_POS_XYZ, &p_xdf->receiver_info );
+
+} // xdevfeat_has_pos_xyz
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_pos_xyz;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports reading the position as ::LLA array
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_pos_lla( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_POS_LLA, &p_xdf->receiver_info );
+
+} // xdevfeat_has_pos_lla
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_pos_lla;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if the device supports the builtin feature TIME
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_time_ttm( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_TIME_TTM, &p_xdf->receiver_info );
+
+} // xdevfeat_has_time_ttm
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::MBG_TIME_SCALE_INFO structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_time_scale_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_time_scale( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_TIME_SCALE, &p_xdf->receiver_info );
+
+} // xdevfeat_has_time_scale
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_time_scale;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::TZDL structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_tzdl( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_TZDL, &p_xdf->receiver_info );
+
+} // xdevfeat_has_tzdl
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_tzdl;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::TZCODE API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_tzcode( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_TZCODE, &p_xdf->receiver_info );
+
+} // xdevfeat_has_tzcode
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_tzcode;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::ANT_INFO structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ant_info( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_ANT_INFO, &p_xdf->receiver_info );
+
+} // xdevfeat_has_ant_info
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_ant_info;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::ENABLE_FLAGS structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_enable_flags( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_ENABLE_FLAGS, &p_xdf->receiver_info );
+
+} // xdevfeat_has_enable_flags
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_enable_flags;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::STAT_INFO structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_gps_stat_info( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_STAT_INFO, &p_xdf->receiver_info );
+
+} // xdevfeat_has_gps_stat_info
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_gps_stat_info;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::ANT_CABLE_LEN structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ant_cable_length( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_ANT_CABLE_LEN, &p_xdf->receiver_info );
+
+} // xdevfeat_has_ant_cable_length
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_ant_cable_length;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::IGNORE_LOCK structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_gps_ignore_lock( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_IGNORE_LOCK, &p_xdf->receiver_info );
+
+} // xdevfeat_has_gps_ignore_lock
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_gps_ignore_lock;
+
+
+
+#if 0 //### TODO
+
+ /*HDR*/
+/**
+ * @brief Check if a device supports the :: structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_, &p_xdf->receiver_info );
+
+} // xdevfeat_has_
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_;
+
+
+
+ /*HDR*/
+/**
+ * @brief Check if a device supports the :: structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_, &p_xdf->receiver_info );
+
+} // xdevfeat_has_
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_;
+
+#endif // ###
+
+
+/*HDR*/
+/**
+ * @brief Check if the device supports the SCU_STAT structures
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ * @see @ref group_scu
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_scu_stat( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_SCU_STAT, &p_xdf->receiver_info );
+
+} // xdevfeat_has_scu_stat
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_scu_stat;
+
+
+/*HDR*/
+/**
+ * @brief Check if the device supports the SV_INFO structures
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_sv_info( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_builtin_feature( GPS_MODEL_HAS_SV_INFO, &p_xdf->receiver_info );
+
+} // xdevfeat_has_sv_info
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_sv_info;
+
+
+/*HDR*/
+/**
+ * @brief Check if a timecode receiver provides ::MBG_RAW_IRIG_DATA
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_raw_irig_data
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_raw_irig_data( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_RAW_IRIG_DATA, &p_xdf->receiver_info );
+
+} // xdevfeat_has_raw_irig_data
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_raw_irig_data;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the old LAN_IP4 API
+ *
+ * The LAN_IP4 API provides structures and functions to configure
+ * parts of the networking of a device and is superseded by the
+ * NET_CFG API. Some devices combine NET_CFG and LAN_IP4.
+ * Therefore, ::mbgextio_get_all_net_cfg_info should be used
+ * preferably to read the network configuration.
+ * It will translate the old structures into the new ones.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_net_cfg_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_lan_ip4( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_LAN_IP4, &p_xdf->receiver_info );
+
+} // xdevfeat_has_lan_ip4
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_lan_ip4;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the new NET_CFG API
+ *
+ * The NET_CFG API provides structures and functions to configure
+ * the complete networking part of a device and supersedes the
+ * LAN_IP4 API. Not all devices support the whole feature set
+ * of the NET_CFG API or combine NET_CFG and LAN_IP4.
+ * Therefore, ::mbgextio_get_all_net_cfg_info should be used
+ * preferably to read the network configuration.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_net_cfg_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_net_cfg( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_NET_CFG, &p_xdf->receiver_info );
+
+} // xdevfeat_has_net_cfg
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_net_cfg;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the PTP API
+ *
+ * The PTP API consists of different calls and associated structures
+ * which * have evolved over time. Not all devices support every call,
+ * so ::mbgextio_get_all_ptp_cfg_info takes care to check which parts are
+ * supported and thus should be used preferably to read PTP information.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_ptp_cfg_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ptp( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_PTP, &p_xdf->receiver_info );
+
+} // xdevfeat_has_ptp
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_ptp;
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the NTP API
+ *
+ * The NTP API consists of different calls and associated structures
+ * which have evolved over time. Not all devices support every call,
+ * so ::mbgextio_get_all_ntp_cfg_info takes care to check which parts are
+ * supported and thus should be used preferably to read NTP information.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_ntp_cfg_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ntp( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_NTP, &p_xdf->receiver_info );
+
+} // xdevfeat_has_ntp
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_ntp;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the event log API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_evt_log( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_EVT_LOG, &p_xdf->receiver_info );
+
+} // xdevfeat_has_evt_log
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_evt_log;
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the USB lock feature, see ::MBG_XFEATURE_USB_LOCK
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref group_usb_lock
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_usb_lock( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_USB_LOCK, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_usb_lock
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_usb_lock;
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the user capture API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ucap( const MBG_XDEV_FEATURES *p_xdf )
+{
+ const RECEIVER_INFO *ri = &p_xdf->receiver_info;
+
+ if ( ri->n_ucaps > 0 )
+ return MBG_SUCCESS;
+
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+
+} // xdevfeat_has_ucap
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_ucap;
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the user capture via network feature
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref group_ucap_net
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ucap_net( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_UCAP_NET, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_ucap_net
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_ucap_net;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the TLV API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref group_tlv_api
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_tlv_api( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_TLV_API, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_ptp
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_tlv_api;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports a firmware update via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_xmt_fw_update
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_fw_update( const MBG_XDEV_FEATURES *p_xdf )
+{
+#if defined( _PRELIMINARY_CODE )
+ return check_tlv_feat_supp( MBG_TLV_FEAT_TYPE_FW_UPDATE, &p_xdf->tlv_info );
+#else
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+#endif
+
+} // xdevfeat_supp_tlv_fw_update
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_supp_tlv_fw_update;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports creating / sending a diagnostics file via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO //refer to get diag function
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_diag_file( const MBG_XDEV_FEATURES *p_xdf )
+{
+#if defined( _PRELIMINARY_CODE )
+ return check_tlv_feat_supp( MBG_TLV_FEAT_TYPE_DIAG_FILE, &p_xdf->tlv_info );
+#else
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+#endif
+
+} // xdevfeat_supp_tlv_diag_file
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_supp_tlv_diag_file;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports PTPv2 license infos
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_ptpv2_license( const MBG_XDEV_FEATURES *p_xdf )
+{
+#if defined( _PRELIMINARY_CODE )
+ return check_tlv_feat_supp( MBG_TLV_FEAT_TYPE_LICENSE_PTPV2_IDX, &p_xdf->tlv_info );
+#else
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+#endif
+
+} // xdevfeat_supp_tlv_ptpv2_license
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_supp_tlv_ptpv2_license;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports NTP license infos via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_ntp_license( const MBG_XDEV_FEATURES *p_xdf )
+{
+#if defined( _PRELIMINARY_CODE )
+ return check_tlv_feat_supp( MBG_TLV_FEAT_TYPE_LICENSE_NTP_IDX, &p_xdf->tlv_info );
+#else
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+#endif
+
+} // xdevfeat_supp_tlv_ntp_license
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_supp_tlv_ntp_license;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports PTPv1 License Infos via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_ptpv1_license( const MBG_XDEV_FEATURES *p_xdf )
+{
+#if defined( _PRELIMINARY_CODE )
+ return check_tlv_feat_supp( MBG_TLV_FEAT_TYPE_LICENSE_PTPV1_IDX, &p_xdf->tlv_info );
+#else
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+#endif
+
+} // xdevfeat_supp_tlv_ptpv1_license
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_supp_tlv_ptpv1_license;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports Time Monitor License infos via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_time_monitor_license( const MBG_XDEV_FEATURES *p_xdf )
+{
+#if defined( _PRELIMINARY_CODE )
+ return check_tlv_feat_supp( MBG_TLV_FEAT_TYPE_LICENSE_TIME_MONITOR_IDX, &p_xdf->tlv_info );
+#else
+ return MBG_ERR_NOT_SUPP_BY_DEV;
+#endif
+
+} // xdevfeat_supp_tlv_time_monitor_license
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_supp_tlv_time_monitor_license;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::GPS_SAVE_CFG command
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_cmd_save_cfg
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_cmd_save_cfg( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_SAVE_CFG, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_cmd_save_cfg
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_cmd_save_cfg;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the extended feature monitoring
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_monitoring( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_MONITORING, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_monitoring
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_monitoring;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the LED API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_led_api( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_LED_API, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_led_api
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_led_api;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the LNE API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_lne_api( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_LNE_API, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_lne_api
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_lne_api;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the power control API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_pwr_ctl_api( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_PWR_CTL_API, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_pwr_ctl_api
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_pwr_ctl_api;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the ::MBG_EXT_SYS_INFO command
+ *
+ * @param[in,out] p_xdf Pointer to a valid message control structure
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ext_sys_info( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_EXT_SYS_INFO, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_ext_sys_info
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_ext_sys_info;
+
+
+
+/*HDR*/
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_io_ports( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_IO_PORTS, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_io_ports
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_io_ports;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device has ::MBG_XFEATURE_TRANSACTIONS
+ *
+ * @param[in,out] p_xdf Pointer to a valid message control structure
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_transactions( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_TRANSACTIONS, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_transactions
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_transactions;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device has ::MBG_XFEATURE_REBOOT
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_reboot( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_REBOOT, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_reboot
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_reboot;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device has ::MBG_XFEATURE_REQ_TTM
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ * @see mbgextio_get_time
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_req_ttm( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_xfeature( MBG_XFEATURE_REQ_TTM, &p_xdf->xfeature_buffer );
+
+} // xdevfeat_has_req_ttm
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_req_ttm;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the extended multi ref features including multi instances
+ *
+ * The different multi ref feature and its appropriate flags have evolved over time.
+ * This function only checks the currently up-to-date GPS_HAS_XMRS_MULT_INSTC flag.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_xmulti_ref_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_xmulti_ref( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_XMRS_MULT_INSTC, &p_xdf->receiver_info );
+
+} // xdevfeat_has_xmulti_ref
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_xmulti_ref;
+
+
+
+/*HDR*/
+/**
+ * @brief Check if a device supports the extended binary protocol (XBP) feature
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+_NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_xbp( const MBG_XDEV_FEATURES *p_xdf )
+{
+ return check_ri_feature( GPS_HAS_XBP, &p_xdf->receiver_info );
+
+} // xdevfeat_has_xbp
+
+XDEVFEAT_CHK_SUPP_FNC xdevfeat_has_xbp;
diff --git a/mbglib/common/xdevfeat.h b/mbglib/common/xdevfeat.h
new file mode 100755
index 0000000..3ce99d9
--- /dev/null
+++ b/mbglib/common/xdevfeat.h
@@ -0,0 +1,892 @@
+
+/**************************************************************************
+ *
+ * $Id: xdevfeat.h 1.1.1.28.1.13 2017/04/20 04:58:10 thomas-b TEST $
+ *
+ * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
+ *
+ * Description:
+ * Definitions and prototypes for xdevfeat.c.
+ *
+ * -----------------------------------------------------------------------
+ * $Log: xdevfeat.h $
+ * Revision 1.1.1.28.1.13 2017/04/20 04:58:10 thomas-b
+ * Added function to check for extended features MBG_XFEATURE_USB_LOCK
+ * Revision 1.1.1.28.1.12 2017/03/07 13:45:34 thomas-b
+ * Check receiver info feature instead of builtin feature for ignore lock
+ * Revision 1.1.1.28.1.11 2017/02/22 11:32:52 martin
+ * Fixed warnings due to preliminary, unfinished code.
+ * Revision 1.1.1.28.1.10 2017/02/07 14:24:09 thomas-b
+ * Added function xdevfeat_has_monitoring, which checks if the extended feature MBG_XFEATURE_MONITORING is set
+ * Revision 1.1.1.28.1.9 2017/02/07 14:10:48 daniel
+ * Updated function prototypes
+ * Revision 1.1.1.28.1.8 2016/12/06 10:43:37 thomas-b
+ * Added function xdevfeat_has_sv_info
+ * Revision 1.1.1.28.1.7 2016/11/30 16:12:27 thomas-b
+ * Added function xdevfeat_has_scu_stat
+ * Revision 1.1.1.28.1.6 2016/11/22 10:33:16 philipp
+ * Implemented I/O ports
+ * Revision 1.1.1.28.1.5 2016/11/07 11:31:49 thomas-b
+ * Fixed typedef for XDEVFEAT_CHK_SUPP_FNC
+ * Revision 1.1.1.28.1.4 2016/11/02 12:16:19 thomas-b
+ * Fixed documentation
+ * Revision 1.1.1.28.1.3 2016/11/02 12:08:22 thomas-b
+ * Added function to check for new MBG_XFEATURE_REQ_TTM
+ * Revision 1.1.1.28.1.2 2016/11/01 09:39:32 martin
+ * Doxygen changes
+ * Revision 1.1.1.28.1.1 2016/10/25 08:08:37 martin
+ * Updated function prototypes with preliminary changes.
+ * Revision 1.1.1.28 2016/10/20 14:46:05 thomas-b
+ * Added function to check if XBP is supported
+ * Revision 1.1.1.27 2016/10/20 10:43:36 thomas-b
+ * Added function to check if a device is a bus level device
+ * Revision 1.1.1.26 2016/10/14 11:09:41 thomas-b
+ * Added function to check MBG_XFEATURE_UCAP_NET
+ * Revision 1.1.1.25 2016/09/29 14:35:35 thomas-b
+ * Added function to check reboot feature
+ * Revision 1.1.1.24 2016/09/29 12:19:59 thomas-b
+ * Added function to check transactions feature
+ * Revision 1.1.1.23 2016/07/07 15:03:33 martin
+ * Updated function prototypes.
+ * Revision 1.1.1.22 2016/06/15 10:15:52 thomas-b
+ * Added functions which check if the user capture feature is supported by a device
+ * Revision 1.1.1.21 2016/06/14 10:33:23 thomas-b
+ * Added functions which check if the event log feature is supported by a device
+ * Revision 1.1.1.20 2016/06/07 07:43:09 philipp
+ * New function to check for Irig Rx feature
+ * Revision 1.1.1.19 2016/06/02 11:44:37 philipp
+ * Fixed prototype
+ * Revision 1.1.1.18 2016/05/30 08:10:47 thomas-b
+ * Added functions to check several builtin features
+ * Revision 1.1.1.17 2016/05/20 09:41:39 thomas-b
+ * Removed functions which check for a specific IMS card
+ * Revision 1.1.1.16 2016/05/20 08:50:47 thomas-b
+ * Added functions xdevfeat_has_time_scale and xdevfeat_has_tzcode
+ * Revision 1.1.1.15 2016/05/17 06:33:13 philipp
+ * New function to check whether a device has serial outputs
+ * Revision 1.1.1.14 2016/05/12 10:41:41 philipp
+ * New functions to check bpe card and IRIG Tx feature
+ * Revision 1.1.1.13 2016/05/10 06:15:32 philipp
+ * New function to check whether a device has programmable pulses
+ * Revision 1.1.1.12 2016/04/26 06:52:46 thomas-b
+ * Added functions to check if NET_CFG and LAN_IP4 APIs are supported
+ * Revision 1.1.1.11 2016/04/22 10:54:01 philipp
+ * New function to check whether device is LIU
+ * Revision 1.1.1.10 2016/04/20 13:12:58 thomas-b
+ * Added function to check if a device supports NTP
+ * Revision 1.1.1.9 2016/04/20 09:26:04 philipp
+ * Moved all HPS-PTP related structures to gpspriv.h and removed related extended feature bit from gpsdefs.h.
+ * Also removed functions from mbgextio and xdevfeat since HPS-PTP handling needs a redesign concerning structures.
+ * Thus, handle everything explicitly for now!
+ * -> Redesing this A.S.A.P.!!!
+ * Revision 1.1.1.8 2016/04/15 08:17:27 philipp
+ * New feature MBG_XFEATURE_EXT_PTP
+ * Revision 1.1.1.7 2016/04/13 07:01:22 philipp
+ * New function to check whether device is HPS
+ * Revision 1.1.1.6 2016/04/12 13:27:42 philipp
+ * Several new functions to check for device models and device features
+ * Revision 1.1.1.5 2016/04/11 13:57:17 thomas-b
+ * Added function xdevfeat_has_xmulti_ref
+ * Revision 1.1.1.4 2016/04/07 12:36:57 martin
+ * Updated function prototypes.
+ * Revision 1.1.1.3 2016/04/04 15:31:25 martin
+ * New function xdevfeat_is_vsg().
+ * Revision 1.1.1.2 2016/03/24 14:08:52 martin
+ * *** empty log message ***
+ * Revision 1.1.1.1 2016/03/18 10:48:19 martin
+ * *** empty log message ***
+ * Revision 1.1 2016/03/16 14:32:52 martin
+ * Initial revision.
+ *
+ **************************************************************************/
+
+#ifndef _XDEVFEAT_H
+#define _XDEVFEAT_H
+
+
+/* Other headers to be included */
+
+#include <gpsdefs.h>
+
+#ifdef _XDEVFEAT
+ #define _ext
+ #define _DO_INIT
+#else
+ #define _ext extern
+#endif
+
+/* Start of header body */
+
+/**
+ * @defgroup chk_supp_fncs Groups of functions used to check if a particular feature is supported
+ *
+ * Each of these functions can be used to check if a device supports a particular
+ * feature. ::MBG_SUCCESS is returned if the requested feature is supported,
+ * otherwise one of the @ref MBG_ERROR_CODES is returned, as appropriate.
+ *
+ * Some features are supported by a device if an associated bit is set in the
+ * ::RECEIVER_INFO::features field, but since the number of bits in this field
+ * is limited, newer feature bits are defined in a ::MBG_XFEATURE_BUFFER.
+ * Finally there are some builtin features which may be implicitly supported
+ * by a particular device model, or not.
+ *
+ * These functions provide a unified API for all feature types to make
+ * application code more straightforward.
+ *
+ * If the mbgextio API is used then a ::MBG_XDEV_FEATURES structure embedded in
+ * the ::MBG_MSG_CTL structure is set up automatically when the device is opened,
+ * and there are mbgextio_... wrapper functions available which just expect the
+ * MBG_MSG_CTL * associated with the device to check if a feature is supported.
+ * See @ref mbgextio_chk_supp_fncs.
+ *
+ * Other implementations which retrieve the ::MBG_XDEV_FEATURES structure of
+ * a device in a different way can use some lower level functions.
+ * See @ref xdevfeat_chk_supp_fncs.
+ */
+
+
+/**
+ * @defgroup xdevfeat_chk_supp_fncs Low level functions used to check if a particular feature is supported
+ * @ingroup chk_supp_fncs
+ *
+ * @note Applications using the mbgextio API should use the mbgextio_ wrapper
+ * functions preferably. See @ref mbgextio_chk_supp_fncs.
+ */
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * @brief A structure combining all device feature information
+ */
+typedef struct
+{
+ uint32_t reserved; ///< Currently reserved, unused, always 0
+ RECEIVER_INFO receiver_info; ///< Receiver info provided by the device
+ MBG_XFEATURE_BUFFER xfeature_buffer; ///< Extended features provided by the device
+ MBG_TLV_INFO tlv_info; ///< TLV info provided by a device
+
+} MBG_XDEV_FEATURES;
+
+
+
+/**
+ * @brief Type of functions to check if a feature is supported
+ */
+typedef int _NO_MBG_API XDEVFEAT_CHK_SUPP_FNC( const MBG_XDEV_FEATURES *p_xdf );
+
+
+
+/* function prototypes: */
+
+/* ----- function prototypes begin ----- */
+
+/* This section was generated automatically */
+/* by MAKEHDR, do not remove the comments. */
+
+ /**
+ * @brief Check if a device can receive the GPS satellite system
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_is_gps
+ * @see ::mbg_chk_dev_is_gps
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_gps( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the GNSS API
+ *
+ * This is usually supported by devices which can receive signals
+ * from different satellite systems, e.g. GPS, GLONASS, ...
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_is_gnss
+ * @see ::mbg_chk_dev_is_gnss
+ * @see ::MBG_GNSS_TYPES
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_gnss( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device is a time code receiver (IRIG or similar)
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_is_tcr //### TODO
+ * @see ::mbg_chk_dev_is_tcr //### TODO
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_tcr( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device is a DCF77 AM receiver
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_is_dcf //### TODO
+ * @see ::mbg_chk_dev_is_dcf
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_dcf( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device can receive DCF77 PZF
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_dev_has_pzf //### TODO
+ * @see ::mbg_chk_dev_has_pzf
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_pzf( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device is an MSF receiver
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_msf( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device is a JJY receiver
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_jjy( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device is a WWVB receiver
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_wwvb( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device is a bus level device
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_is_bus_lvl_dev( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ims( const MBG_XDEV_FEATURES *p_xdf ) ;
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_gpio( const MBG_XDEV_FEATURES *p_xdf ) ;
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_synth( const MBG_XDEV_FEATURES *p_xdf ) ;
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_prog_pulses( const MBG_XDEV_FEATURES *p_xdf ) ;
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_irig_tx( const MBG_XDEV_FEATURES *p_xdf ) ;
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_irig_rx( const MBG_XDEV_FEATURES *p_xdf ) ;
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_serouts( const MBG_XDEV_FEATURES *p_xdf ) ;
+ /**
+ * @brief Check if a device supports the ::BVAR_STAT structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_bvar_stat( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports reading the position as ::XYZ array
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_pos_xyz( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports reading the position as ::LLA array
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_pos_lla( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if the device supports the builtin feature TIME
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_time_ttm( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::MBG_TIME_SCALE_INFO structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_time_scale_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_time_scale( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::TZDL structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_tzdl( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::TZCODE API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_tzcode( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::ANT_INFO structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ant_info( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::ENABLE_FLAGS structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_enable_flags( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::STAT_INFO structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_gps_stat_info( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::ANT_CABLE_LEN structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ant_cable_length( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::IGNORE_LOCK structure and API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_gps_ignore_lock( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if the device supports the SCU_STAT structures
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ * @see @ref group_scu
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_scu_stat( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if the device supports the SV_INFO structures
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else ::MBG_ERR_NOT_SUPP_BY_DEV
+ * or ::MBG_ERR_DEV_NOT_SUPP (see @ref xdevfeat_chk_supp_fncs)
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_sv_info( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a timecode receiver provides ::MBG_RAW_IRIG_DATA
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_raw_irig_data
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_raw_irig_data( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the old LAN_IP4 API
+ *
+ * The LAN_IP4 API provides structures and functions to configure
+ * parts of the networking of a device and is superseded by the
+ * NET_CFG API. Some devices combine NET_CFG and LAN_IP4.
+ * Therefore, ::mbgextio_get_all_net_cfg_info should be used
+ * preferably to read the network configuration.
+ * It will translate the old structures into the new ones.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_net_cfg_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_lan_ip4( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the new NET_CFG API
+ *
+ * The NET_CFG API provides structures and functions to configure
+ * the complete networking part of a device and supersedes the
+ * LAN_IP4 API. Not all devices support the whole feature set
+ * of the NET_CFG API or combine NET_CFG and LAN_IP4.
+ * Therefore, ::mbgextio_get_all_net_cfg_info should be used
+ * preferably to read the network configuration.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_net_cfg_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_net_cfg( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the PTP API
+ *
+ * The PTP API consists of different calls and associated structures
+ * which * have evolved over time. Not all devices support every call,
+ * so ::mbgextio_get_all_ptp_cfg_info takes care to check which parts are
+ * supported and thus should be used preferably to read PTP information.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_ptp_cfg_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ptp( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the NTP API
+ *
+ * The NTP API consists of different calls and associated structures
+ * which have evolved over time. Not all devices support every call,
+ * so ::mbgextio_get_all_ntp_cfg_info takes care to check which parts are
+ * supported and thus should be used preferably to read NTP information.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_ntp_cfg_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ntp( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the event log API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_evt_log( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the USB lock feature, see ::MBG_XFEATURE_USB_LOCK
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref group_usb_lock
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_usb_lock( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the user capture API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ucap( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the user capture via network feature
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref group_ucap_net
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ucap_net( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the TLV API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref group_tlv_api
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_tlv_api( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports a firmware update via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_xmt_fw_update
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_fw_update( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports creating / sending a diagnostics file via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO //refer to get diag function
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_diag_file( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports PTPv2 license infos
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_ptpv2_license( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports NTP license infos via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_ntp_license( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports PTPv1 License Infos via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_ptpv1_license( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports Time Monitor License infos via TLV
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_tlv_feat_supp
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_supp_tlv_time_monitor_license( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::GPS_SAVE_CFG command
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_cmd_save_cfg
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_cmd_save_cfg( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the extended feature monitoring
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_monitoring( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the LED API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_led_api( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the LNE API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_lne_api( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the power control API
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_pwr_ctl_api( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the ::MBG_EXT_SYS_INFO command
+ *
+ * @param[in,out] p_xdf Pointer to a valid message control structure
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_ext_sys_info( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_io_ports( const MBG_XDEV_FEATURES *p_xdf ) ;
+ /**
+ * @brief Check if a device has ::MBG_XFEATURE_TRANSACTIONS
+ *
+ * @param[in,out] p_xdf Pointer to a valid message control structure
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::TODO ###
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_transactions( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device has ::MBG_XFEATURE_REBOOT
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_reboot( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device has ::MBG_XFEATURE_REQ_TTM
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_xfeature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ * @see mbgextio_get_time
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_req_ttm( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the extended multi ref features including multi instances
+ *
+ * The different multi ref feature and its appropriate flags have evolved over time.
+ * This function only checks the currently up-to-date GPS_HAS_XMRS_MULT_INSTC flag.
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see ::mbgextio_get_all_xmulti_ref_info
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_xmulti_ref( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+ /**
+ * @brief Check if a device supports the extended binary protocol (XBP) feature
+ *
+ * @param[in,out] p_xdf Pointer to a ::MBG_XDEV_FEATURES buffer associated with the device
+ *
+ * @return ::MBG_SUCCESS if supported, else error code from ::check_ri_feature
+ *
+ * @ingroup xdevfeat_chk_supp_fncs
+ * @see @ref xdevfeat_chk_supp_fncs
+ */
+ _NO_MBG_API_ATTR int _NO_MBG_API xdevfeat_has_xbp( const MBG_XDEV_FEATURES *p_xdf ) ;
+
+
+/* ----- function prototypes end ----- */
+
+#ifdef __cplusplus
+}
+#endif
+
+/* End of header body */
+
+#undef _ext
+#undef _DO_INIT
+
+#endif /* _XDEVFEAT_H */
diff --git a/mbgsetsystime/Makefile b/mbgsetsystime/Makefile
index c68401c..4670b88 100755
--- a/mbgsetsystime/Makefile
+++ b/mbgsetsystime/Makefile
@@ -1,13 +1,32 @@
#########################################################################
#
-# $Id: Makefile 1.8.1.3 2011/09/26 16:07:30 martin TEST $
+# $Id: Makefile 1.8.1.13 2017/02/09 11:23:31 martin TEST $
#
# Description:
# Makefile for mbgsetsystime.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.8.1.13 2017/02/09 11:23:31 martin
+# *** empty log message ***
+# Revision 1.8.1.12 2016/08/10 11:32:23 martin
+# *** empty log message ***
+# Revision 1.8.1.11 2016/08/09 16:02:13 martin
+# Fixed build for QNX Neutrino.
+# Revision 1.8.1.10 2016/07/15 14:07:25 martin
+# Added new module timeutil.o.
+# Revision 1.8.1.9 2016/05/30 15:14:21 martin
+# *** empty log message ***
+# Revision 1.8.1.8 2015/12/17 14:26:48 martin
+# Added -lrt to LDFLAGS. Required for clock_settime and glibc before 2.17.
+# Revision 1.8.1.7 2015/12/16 14:51:30 martin
+# Removed obsolete module cfg_hlp.o.
+# Revision 1.8.1.6 2015/08/31 14:22:02 martin
+# Revision 1.8.1.5 2015/07/14 15:07:20 martin
+# Added object module mbgerror.o.
+# Revision 1.8.1.4 2014/04/28 13:19:51 martin
+# Added module cfg_hlp.o.
# Revision 1.8.1.3 2011/09/26 16:07:30 martin
# Updated for use with latest base Makefile.
# Revision 1.8.1.2 2010/08/30 09:05:23 martin
@@ -36,10 +55,16 @@ INST_TO_SBIN = 1
OBJS = $(TARGET).o
OBJS += mbgdevio.o
+OBJS += timeutil.o
+OBJS += str_util.o
OBJS += toolutil.o
+OBJS += mbgerror.o
+OBJS += cfg_hlp.o
OBJS += gpsutils.o
OBJS += mbgmktm.o
OBJS += pcpsmktm.o
+LDFLAGS += -lrt
+
BASEDIR := ..
include $(BASEDIR)/Makefile
diff --git a/mbgsetsystime/mbgsetsystime.c b/mbgsetsystime/mbgsetsystime.c
index 0dad203..97e9480 100755
--- a/mbgsetsystime/mbgsetsystime.c
+++ b/mbgsetsystime/mbgsetsystime.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgsetsystime.c 1.8.1.3 2013/01/24 14:39:51 martin TEST $
+ * $Id: mbgsetsystime.c 1.8.1.20 2017/02/06 11:32:35 martin TEST $
*
* Description:
* Main file for mbgsetsystime program which reads the current date
@@ -14,7 +14,36 @@
*
* -----------------------------------------------------------------------
* $Log: mbgsetsystime.c $
- * Revision 1.8.1.3 2013/01/24 14:39:51 martin
+ * Revision 1.8.1.20 2017/02/06 11:32:35 martin
+ * Fixec build under Windows, but system time is
+ * actually not yet set.
+ * Revision 1.8.1.19 2016/08/11 07:44:34Z martin
+ * Revision 1.8.1.18 2016/08/10 11:32:40Z martin
+ * *** empty log message ***
+ * Revision 1.8.1.17 2016/07/22 09:57:12 martin
+ * Quieted some compiler warninges.
+ * Revision 1.8.1.16 2016/07/15 14:11:31 martin
+ * Use functions from new module timeutil.
+ * Revision 1.8.1.15 2016/05/30 15:13:40 martin
+ * *** empty log message ***
+ * Revision 1.8.1.14 2015/12/17 12:00:07 martin
+ * Fixed a compiler warning.
+ * Revision 1.8.1.13 2015/12/16 15:05:21 martin
+ * Use mbg_rc_is_success() to evaluate return codes.
+ * Revision 1.8.1.12 2015/12/16 14:52:40 martin
+ * Use high resolution time if the device supports it.
+ * Revision 1.8.1.11 2014/10/28 16:06:48 martin
+ * Revision 1.8.1.10 2014/10/28 15:19:17 martin
+ * Revision 1.8.1.9 2014/10/28 13:53:33Z martin
+ * Revision 1.8.1.8 2014/10/14 10:20:07 martin
+ * Cleanup fixing compiler warnings under Windows.
+ * Revision 1.8.1.7 2013/07/22 16:25:11Z martin
+ * Revision 1.8.1.6 2013/07/11 08:29:30 martin
+ * Account for modified function call parameter list.
+ * Revision 1.8.1.5 2013/07/10 13:13:20 martin
+ * Revision 1.8.1.4 2013/07/10 13:03:29 martin
+ * Support build under Windows.
+ * Revision 1.8.1.3 2013/01/24 14:39:51Z martin
* Revision 1.8.1.2 2011/07/05 15:35:55 martin
* Modified version handling.
* Revision 1.8.1.1 2011/07/05 14:36:01 martin
@@ -46,14 +75,16 @@
// include Meinberg headers
#include <mbgdevio.h>
#include <pcpsmktm.h>
+#include <pcpsutil.h>
#include <toolutil.h>
+#include <timeutil.h>
+#include <str_util.h>
+#include <mbgerror.h>
// include system headers
#include <stdio.h>
#include <stdlib.h>
-#include <unistd.h>
-#include <sys/time.h>
#include <sys/types.h>
@@ -66,63 +97,239 @@ static const char *pname = "mbgsetsystime";
static /*HDR*/
-void set_system_time( PCPS_TIME *tp )
+size_t sn_printf_timespec( char *s, size_t max_len, const struct timespec *p_ts )
{
- struct timeval tv_set;
+ struct tm tm = { 0 };
+ int rc = mbg_gmtime( &tm, &p_ts->tv_sec );
+ if ( mbg_rc_is_error( rc ) ) // conversion failed
+ return sn_cpy_str_safe( s, max_len, "(invalid time)" );
- tv_set.tv_sec = pcps_mktime( tp );
- tv_set.tv_usec = (ulong) tp->sec100 * 10000;
- settimeofday( &tv_set, NULL );
+ return snprintf_safe( s, max_len, "%04i-%02i-%02i %02i:%02i:%02i.%09li UTC",
+ tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday,
+ tm.tm_hour, tm.tm_min, tm.tm_sec,
+ (long) p_ts->tv_nsec );
- printf( "Date/time set to %02u.%02u.%02u %02u:%02u:%02u.%02u (UTC %+02ih)\n",
- tp->mday, tp->month, tp->year,
- tp->hour, tp->min, tp->sec, tp->sec100,
- tp->offs_utc
- );
+} // sn_printf_timespec
+
+
+
+static /*HDR*/
+int set_system_time( const struct timespec *p_ts )
+{
+ char ws[100];
+
+#if defined( MBG_TGT_WIN32 )
+ #define clock_settime mbg_clock_settime //### TODO cleanup
+#endif
+
+ int rc = clock_settime( CLOCK_REALTIME, p_ts );
+
+ sn_printf_timespec( ws, sizeof( ws ), p_ts );
+
+ if ( rc < 0 ) // usually 0 on success, -1 on error
+ {
+ rc = mbg_get_last_error( NULL );
+
+ fprintf( stderr, "Failed to set system time to %s: %s\n", ws, mbg_strerror( rc ) );
+ return rc;
+ }
+
+ printf( "Date/time set to %s\n", ws );
+
+ return MBG_SUCCESS;
} // set_system_time
static /*HDR*/
-int do_mbgsetsystime( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
+int set_system_time_from_pcps_time( const PCPS_TIME *p_t )
{
- static int system_time_has_been_set;
-
- PCPS_TIME t;
- int ret_val = 0;
+ struct tm tm = { 0 };
+ time_t t_rev;
+ time_t t;
int rc;
- if ( system_time_has_been_set )
- goto done;
+ t = pcps_mktime( p_t );
- rc = mbg_get_time( dh, &t );
+ if ( t == (time_t) -1 ) // error
+ {
+ fprintf( stderr, "Failed to convert %02u.%02u.%02u %02u:%02u:%02u.%02u (UTC%+02ih) to system time\n",
+ p_t->mday, p_t->month, p_t->year,
+ p_t->hour, p_t->min, p_t->sec, p_t->sec100,
+ p_t->offs_utc
+ );
+ return MBG_ERR_OVERFLOW;
+ }
- if ( mbg_ioctl_err( rc, "mbg_get_time" ) )
+ t_rev = t + p_t->offs_utc * SECS_PER_HOUR;
+
+ rc = mbg_gmtime( &tm, &t_rev );
+
+ if ( mbg_rc_is_error( rc ) )
+ return rc;
+
+ if ( ( tm.tm_year % 100 != p_t->year ) ||
+ ( tm.tm_mon + 1 != p_t->month ) ||
+ ( tm.tm_mday != p_t->mday ) ||
+ ( tm.tm_hour != p_t->hour ) ||
+ ( tm.tm_min != p_t->min ) ||
+ ( tm.tm_sec != p_t->sec ) )
{
- ret_val = -2;
- goto done;
+ fprintf( stderr, "reversely computed date/time differs from original\n" );
+ return MBG_ERR_RANGE;
}
+ #if defined( MBG_TGT_WIN32 )
+ {
+ SYSTEMTIME st;
+
+ union
+ {
+ FILETIME ft;
+ ULONGLONG ull;
+ } u;
+
+ // Convert seconds and fractions to 100 ns units.
+ u.ull = FILETIME_1970 +
+ (ULONGLONG) t * 10 * 1000 * 1000 +
+ (ULONGLONG) (ulong) p_t->sec100 * 100000;
+
+ if ( !FileTimeToSystemTime( &u.ft, &st ) )
+ {
+ int err = mbg_win32_last_err_to_mbg( GetLastError(), NULL );
+
+ fprintf( stderr, "Failed to convert FILETIME to system time: %s\n",
+ mbg_strerror( err ) );
+ return err;
+ }
+
+ if ( !SetSystemTime( &st ) )
+ {
+ #if 0
+ LPVOID lpMsgBuf;
+ DWORD last_error = GetLastError();
+
+ FormatMessage( FORMAT_MESSAGE_ALLOCATE_BUFFER |
+ FORMAT_MESSAGE_FROM_SYSTEM |
+ FORMAT_MESSAGE_IGNORE_INSERTS,
+ NULL,
+ last_error,
+ MAKELANGID( LANG_NEUTRAL, SUBLANG_DEFAULT ), // Default language
+ (LPTSTR) &lpMsgBuf,
+ 0,
+ NULL
+ );
+
+ fprintf( stderr, "Failed to set system time: %s (code 0x%08lX)\n",
+ lpMsgBuf, (ulong) last_error );
+
+ // Free the buffer.
+ LocalFree( lpMsgBuf );
+ #else
+ int err = mbg_win32_last_err_to_mbg( GetLastError(), NULL );
+
+ fprintf( stderr, "Failed to set system time: err %i\n", err );
+ #endif
+ return err;
+ }
+
+ return MBG_SUCCESS;
+ }
+ #else // assuming POSIX
+ {
+ struct timespec ts;
+
+ ts.tv_sec = t;
+ ts.tv_nsec = (long) p_t->sec100 * ( NSECS_PER_SEC / 100 ); // convert to nanoseconds
+
+ return set_system_time( &ts );
+ }
+ #endif
+
+} // set_system_time_from_pcps_time
+
+
+
+static /*HDR*/
+int do_set_system_time_from_pcps_time( MBG_DEV_HANDLE dh )
+{
+ PCPS_TIME t;
+
+ int rc = mbg_get_time( dh, &t );
+
+ if ( mbg_ioctl_err( rc, "mbg_get_time" ) )
+ return rc;
+
if ( t.status & PCPS_INVT )
{
// This may happen if the radio clock's battery
- // was low or disconnected.
+ // has been discharged or disconnected.
printf( "Radio clock has no valid date/time.\n" );
- ret_val = -1;
- goto done;
+ return MBG_ERR_INV_TIME;
}
- set_system_time( &t );
- system_time_has_been_set = 1;
+ rc = set_system_time_from_pcps_time( &t );
+
+ return rc;
+
+} // do_set_system_time_from_pcps_time
+
+
+
+static /*HDR*/
+int do_set_system_time_from_pcps_hr_time( MBG_DEV_HANDLE dh )
+{
+ PCPS_HR_TIME ht;
+ struct timespec ts = { 0 };
+
+ int rc = mbg_get_hr_time( dh, &ht );
+
+ if ( mbg_ioctl_err( rc, "mbg_get_hr_time" ) )
+ return rc;
+
+ if ( ht.status & PCPS_INVT )
+ {
+ // This may happen if the radio clock's battery
+ // has been discharged or disconnected.
+ printf( "Radio clock has no valid date/time.\n" );
+ return MBG_ERR_INV_TIME;
+ }
+
+ ts.tv_sec = ht.tstamp.sec;
+ ts.tv_nsec = frac_sec_from_bin( ht.tstamp.frac, NSECS_PER_SEC );
+
+ return set_system_time( &ts );
+
+} // do_set_system_time_from_pcps_hr_time
+
+
+
+static /*HDR*/
+int do_mbgsetsystime( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
+{
+ static int system_time_has_been_set;
+
+ int rc = MBG_SUCCESS;
+
+ if ( system_time_has_been_set )
+ goto done;
+
+ rc = mbg_chk_dev_has_hr_time( dh );
+
+ if ( mbg_rc_is_success( rc ) )
+ rc = do_set_system_time_from_pcps_hr_time( dh );
+ else
+ rc = do_set_system_time_from_pcps_time( dh );
+
+ if ( mbg_rc_is_success( rc ) )
+ system_time_has_been_set = 1;
puts( "" );
done:
- mbg_close_device( &dh );
-
- return ret_val;
+ return rc;
} // do_mbgsetsystime
@@ -133,7 +340,8 @@ void usage( void )
{
mbg_print_usage_intro( pname,
"This program can be used to set the system time to the card's time.\n"
- "This should be done only at boot time, before the NTP daemon is started."
+ "This should be done only at boot time, before the NTP daemon is started.\n"
+ "Please *don't* run this program while ntpd is already active."
);
mbg_print_help_options();
mbg_print_device_options();
@@ -172,8 +380,16 @@ int main( int argc, char *argv[] )
// on the command, and for each device
// - tries to open the device
// - shows basic device info
- // - calls the function passed as last parameter
- rc = mbg_check_devices( argc, argv, optind, do_mbgsetsystime );
+ // - calls the specified callback function
+ rc = mbg_check_devices( argc, argv, optind, do_mbgsetsystime, 0 );
+
+ // determine the exit code based on the return code
+
+ if ( mbg_rc_is_success( rc ) )
+ return 0; // success
+
+ if ( rc == MBG_ERR_INV_TIME )
+ return 1; // device has no valid time
- return abs( rc );
+ return 2; // any error occurred
}
diff --git a/mbgshowsignal/Makefile b/mbgshowsignal/Makefile
index 16120bb..a70b943 100755
--- a/mbgshowsignal/Makefile
+++ b/mbgshowsignal/Makefile
@@ -1,13 +1,20 @@
#########################################################################
#
-# $Id: Makefile 1.7.1.3 2011/09/26 16:07:30 martin TEST $
+# $Id: Makefile 1.7.1.7 2016/07/15 14:07:29 martin TEST $
#
# Description:
# Makefile for mbgshowsignal.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.7.1.7 2016/07/15 14:07:29 martin
+# *** empty log message ***
+# Revision 1.7.1.6 2015/08/31 14:24:12 martin
+# Revision 1.7.1.5 2015/07/14 15:07:20 martin
+# Added object module mbgerror.o.
+# Revision 1.7.1.4 2014/04/28 13:19:52 martin
+# Added module cfg_hlp.o.
# Revision 1.7.1.3 2011/09/26 16:07:30 martin
# Updated for use with latest base Makefile.
# Revision 1.7.1.2 2010/08/30 09:05:23 martin
@@ -34,7 +41,11 @@ INST_TO_BIN = 1
OBJS = $(TARGET).o
OBJS += mbgdevio.o
+OBJS += timeutil.o
+OBJS += str_util.o
OBJS += toolutil.o
+OBJS += mbgerror.o
+OBJS += cfg_hlp.o
OBJS += gpsutils.o
BASEDIR := ..
diff --git a/mbgshowsignal/mbgshowsignal.c b/mbgshowsignal/mbgshowsignal.c
index 73f66a5..0e086ae 100755
--- a/mbgshowsignal/mbgshowsignal.c
+++ b/mbgshowsignal/mbgshowsignal.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgshowsignal.c 1.8.1.4 2011/10/05 15:10:56 martin TEST $
+ * $Id: mbgshowsignal.c 1.8.1.9 2016/05/30 15:08:59 martin TEST $
*
* Description:
* Main file for mbgshowsignal program which demonstrates how to
@@ -10,7 +10,15 @@
*
* -----------------------------------------------------------------------
* $Log: mbgshowsignal.c $
- * Revision 1.8.1.4 2011/10/05 15:10:56 martin
+ * Revision 1.8.1.9 2016/05/30 15:08:59 martin
+ * *** empty log message ***
+ * Revision 1.8.1.8 2015/10/26 13:51:51 martin
+ * Revision 1.8.1.7 2013/07/22 16:25:11Z martin
+ * Revision 1.8.1.6 2013/07/11 08:29:30 martin
+ * Account for modified function call parameter list.
+ * Revision 1.8.1.5 2013/07/10 13:02:10 martin
+ * Removed obsolete include to fix build under Windows.
+ * Revision 1.8.1.4 2011/10/05 15:10:56Z martin
* Show PZF correlation state.
* Revision 1.8.1.3 2011/07/05 15:35:55 martin
* Modified version handling.
@@ -45,11 +53,9 @@
// include Meinberg headers
#include <mbgdevio.h>
-#include <pcpsutil.h>
#include <toolutil.h> // common utility functions
// include system headers
-#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
@@ -117,16 +123,18 @@ int show_modulation( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
static /*HDR*/
int do_mbgshowsignal( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
{
- int has_mod = 0;
- int rc = mbg_dev_has_mod( dh, &has_mod );
+ int rc = mbg_chk_dev_has_mod( dh );
- if ( mbg_ioctl_err( rc, "mbg_dev_has_mod" ) )
- goto fail;
-
- if ( !has_mod )
+ if ( mbg_rc_is_error( rc ) )
{
- printf( "This device does not support monitoring signal modulation.\n" );
- goto done;
+ if ( rc == MBG_ERR_NOT_SUPP_BY_DEV ) // ### TODO not_supp
+ {
+ printf( "This device does not support monitoring signal modulation.\n" );
+ goto done;
+ }
+
+ mbg_ioctl_err( rc, "mbg_dev_has_mod" );
+ goto fail;
}
printf( "\nMonitoring signal modulation:\n" );
@@ -189,8 +197,8 @@ int main( int argc, char *argv[] )
// on the command, and for each device
// - tries to open the device
// - shows basic device info
- // - calls the function passed as last parameter
- rc = mbg_check_devices( argc, argv, optind, do_mbgshowsignal );
+ // - calls the specified callback function
+ rc = mbg_check_devices( argc, argv, optind, do_mbgshowsignal, 0 );
return abs( rc );
}
diff --git a/mbgstatus/Makefile b/mbgstatus/Makefile
index 11d0742..2141869 100755
--- a/mbgstatus/Makefile
+++ b/mbgstatus/Makefile
@@ -1,13 +1,26 @@
#########################################################################
#
-# $Id: Makefile 1.7.1.5 2011/09/26 16:07:50 martin TEST $
+# $Id: Makefile 1.7.1.13 2016/09/05 11:31:32 martin TEST $
#
# Description:
# Makefile for mbgstatus.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.7.1.13 2016/09/05 11:31:32 martin
+# Removed mbgmktime from the list of object files.
+# Revision 1.7.1.12 2016/07/15 14:07:29 martin
+# *** empty log message ***
+# Revision 1.7.1.11 2015/10/27 15:07:38 martin
+# Removed obsolete object modules.
+# Revision 1.7.1.10 2015/08/31 14:20:35 martin
+# Revision 1.7.1.9 2015/07/14 15:07:21 martin
+# Added object module mbgerror.o.
+# Revision 1.7.1.8 2014/04/28 13:19:52 martin
+# Added module cfg_hlp.o.
+# Revision 1.7.1.7 2014/04/28 09:49:04 martin
+# Revision 1.7.1.6 2014/04/25 09:15:34 martin
# Revision 1.7.1.5 2011/09/26 16:07:50 martin
# Updated for use with latest base Makefile.
# Added module lan_util.
@@ -39,13 +52,15 @@ INST_TO_BIN = 1
OBJS := $(TARGET).o
OBJS += mbgdevio.o
+OBJS += mbgutil.o
+OBJS += timeutil.o
+OBJS += str_util.o
OBJS += toolutil.o
+OBJS += mbgerror.o
+OBJS += cfg_hlp.o
OBJS += gpsutils.o
-OBJS += pcpsutil.o
-OBJS += mbgmktm.o
OBJS += pcpslstr.o
-OBJS += parmpcps.o
-OBJS += parmgps.o
+OBJS += deviohlp.o
OBJS += ctrydttm.o
OBJS += ctry.o
OBJS += lan_util.o
diff --git a/mbgstatus/mbgstatus.c b/mbgstatus/mbgstatus.c
index 8e6bdd8..644495c 100755
--- a/mbgstatus/mbgstatus.c
+++ b/mbgstatus/mbgstatus.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgstatus.c 1.13.1.26 2013/06/25 09:54:09 martin TRASH martin $
+ * $Id: mbgstatus.c 1.13.1.56 2016/10/20 14:08:04 martin TEST $
*
* Description:
* Main file for mbgstatus program which demonstrates how to
@@ -10,6 +10,47 @@
*
* -----------------------------------------------------------------------
* $Log: mbgstatus.c $
+ * Revision 1.13.1.56 2016/10/20 14:08:04 martin
+ * Parameters -u and -s imply -c.
+ * Revision 1.13.1.55 2016/09/14 16:17:31 martin
+ * Account for changed APi function.
+ * Revision 1.13.1.54 2016/08/10 14:45:27 martin
+ * *** empty log message ***
+ * Revision 1.13.1.53 2016/07/22 09:57:12 martin
+ * Quieted some compiler warninges.
+ * Revision 1.13.1.52 2016/07/15 14:10:49 martin
+ * Use functions from new module timeutil.
+ * Revision 1.13.1.51 2015/11/10 16:20:18 martin
+ * *** empty log message ***
+ * Revision 1.13.1.50 2015/10/26 13:50:42 martin
+ * Revision 1.13.1.49 2015/10/07 10:58:09Z martin
+ * Account for changes in GNSS API.
+ * Revision 1.13.1.48 2015/08/27 16:34:10 martin
+ * Use safe string functions.
+ * Revision 1.13.1.47 2015/04/29 13:12:54 martin
+ * Support looping on device.
+ * Revision 1.13.1.46 2014/10/28 13:53:51Z martin
+ * Revision 1.13.1.45 2014/10/14 09:05:34 martin
+ * Revision 1.13.1.44 2014/07/14 15:42:44 martin
+ * Revision 1.13.1.43 2014/04/28 13:36:14 martin
+ * Revision 1.13.1.42 2014/04/28 12:39:59 martin
+ * Revision 1.13.1.41 2014/04/28 09:49:04 martin
+ * Revision 1.13.1.40 2014/04/25 09:15:57 martin
+ * Moved some functions to new module cfg_hlp.c.
+ * Revision 1.13.1.39 2014/04/23 14:56:42 martin
+ * Revision 1.13.1.38 2014/04/23 12:36:26 martin
+ * Revision 1.13.1.37 2014/04/23 08:44:45 martin
+ * Revision 1.13.1.36 2014/04/17 07:44:25 martin
+ * Revision 1.13.1.35 2014/04/15 13:39:07 martin
+ * Revision 1.13.1.34 2013/12/19 16:18:48 martin
+ * Revision 1.13.1.33 2013/08/01 16:51:33 martin
+ * Revision 1.13.1.32 2013/08/01 16:16:12 martin
+ * Revision 1.13.1.31 2013/07/22 16:25:11 martin
+ * Revision 1.13.1.30 2013/07/16 15:45:38 martin
+ * Revision 1.13.1.29 2013/07/11 08:29:30 martin
+ * Account for modified function call parameter list.
+ * Revision 1.13.1.28 2013/07/10 13:02:22 martin
+ * Revision 1.13.1.27 2013/07/08 12:04:39Z martin
* Revision 1.13.1.26 2013/06/25 09:54:09 martin
* Revision 1.13.1.25 2013/02/05 14:36:47 martin
* Revision 1.13.1.24 2012/04/11 16:26:44Z martin
@@ -102,11 +143,14 @@
// include Meinberg headers
#include <mbgdevio.h>
+#include <mbgutil.h>
#include <mbgtime.h>
#include <pcpslstr.h>
-#include <pcpsutil.h>
#include <toolutil.h> // common utility functions
#include <lan_util.h>
+#include <deviohlp.h>
+#include <timeutil.h>
+#include <str_util.h>
// include system headers
#include <stdio.h>
@@ -120,6 +164,9 @@
static const char *pname = "mbgstatus";
+static int loops;
+static long sleep_secs;
+static long sleep_usecs;
static unsigned int verbose;
static const char *ref_name[N_PCPS_REF]= PCPS_REF_NAMES_ENG;
@@ -131,6 +178,8 @@ static int year_limit = 1990;
static int max_ref_offs_h = MBG_REF_OFFS_MAX / MINS_PER_HOUR;
static int invt_reason;
+static const char *wdays[7] = { "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" };
+
LANGUAGE language;
CTRY ctry;
@@ -168,7 +217,8 @@ void print_pcps_time( const char *s, const PCPS_TIME *tp, const char *tail )
if ( s )
printf( fmt, s );
- printf( fmt, pcps_date_time_str( ws, tp, year_limit, pcps_tz_name( tp, PCPS_TZ_NAME_FORCE_UTC_OFFS, 0 ) ) );
+ printf( fmt, pcps_date_time_str( ws, sizeof( ws ), tp, year_limit,
+ pcps_tz_name( tp, PCPS_TZ_NAME_FORCE_UTC_OFFS, 0 ) ) );
if ( ( verbose > 0 ) && _pcps_time_is_read( tp ) )
printf( ", st: 0x%02lX", (ulong) tp->status );
@@ -185,7 +235,7 @@ void print_dms( const char *s, const DMS *p, const char *tail )
{
const char *fmt = "%s";
- printf( "%s %c %3i deg %02i min %05.2f sec",
+ printf( "%s %c %3i deg %02i min %06.3f sec",
s,
p->prefix,
p->deg,
@@ -237,6 +287,7 @@ void print_position( const char *s, const POS *p, const char *tail )
print_dms( " longitude:", &p->longitude, tail );
}
+
} // print_position
@@ -424,52 +475,133 @@ static /*HDR*/
void show_ext_stat_info( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev, const char *tail )
{
const char *fmt = "%s";
- RECEIVER_INFO ri;
- STAT_INFO si = { 0 };
+ RECEIVER_INFO ri = { 0 };
+ ALL_GNSS_INFO agi = { { 0 } };
+ GNSS_SAT_INFO *p_gsi;
char ws[80];
- char *mode_name;
+ const char *cp;
+ int i;
+ int rc;
- int rc = mbg_setup_receiver_info( dh, p_dev, &ri );
+ // first collect all information
+
+ rc = mbg_setup_receiver_info( dh, p_dev, &ri );
if ( mbg_ioctl_err( rc, "mbg_setup_receiver_info" ) )
return;
- if ( _pcps_has_stat_info( p_dev ) )
+#if !defined( DEBUG )
+ if ( mbg_rc_is_success( mbg_chk_dev_is_gps( dh ) ) )
+#endif
{
- rc = mbg_get_gps_stat_info( dh, &si );
+ rc = mbg_chk_get_all_gnss_info( dh, &agi );
- if ( mbg_ioctl_err( rc, "mbg_get_gps_stat_info" ) )
+ if ( mbg_ioctl_err( rc, "mbg_chk_get_gnss_info" ) )
return;
+ }
+ // now print information
+
+ #if DEBUG
+ if ( verbose )
+ printf( "Feature mask: 0x%08lX\n", (ulong) ri.features );
+ #endif
+ if ( _pcps_has_stat_info( p_dev ) )
+ {
if ( _pcps_has_stat_info_mode( p_dev ) )
{
- switch ( si.mode )
+ switch ( agi.stat_info.mode )
{
- case AUTO_166: mode_name = "Normal Operation"; break;
- case WARM_166: mode_name = "Warm Boot"; break;
- case COLD_166: mode_name = "Cold Boot"; break;
+ case AUTO_166: cp = "Normal Operation"; break;
+ case WARM_166: cp = "Warm Boot"; break;
+ case COLD_166: cp = "Cold Boot"; break;
default: // This should never happen!
- sprintf( ws, "Unknown mode of operation: %02Xh", si.mode );
- mode_name = ws;
+ snprintf_safe( ws, sizeof( ws ), "%s mode of operation: %02Xh",
+ str_unknown, agi.stat_info.mode );
+ cp = ws;
} // switch
+
+ printf( "%s", cp );
}
+ }
+
+ if ( agi.n_gnss_supp )
+ {
+ #if defined( DEBUG )
+ int must_print_sv_list = _pcps_has_stat_info_svs( p_dev ) && verbose;
+ #else
+ int must_print_sv_list = _pcps_is_gnss( p_dev ) && verbose;
+ #endif
+ int print_multi_lines = ( agi.n_gnss_supp > 1 ) || must_print_sv_list;
+
+ // print multiple lines
+ // otherwise append to line
+ printf( print_multi_lines ? ":\n" : ", " );
+
+ for ( i = 0; i < agi.n_gnss_supp; i++ )
+ {
+ static const char * const gnss_type_names[N_GNSS_TYPES] = GNSS_TYPE_STRS;
+ int gnss_type;
+
+ p_gsi = &agi.gnss_sat_info_idx[i].gnss_sat_info;
+ gnss_type = p_gsi->gnss_type;
+
+ if ( gnss_type >= N_GNSS_TYPES )
+ {
+ mbg_snprintf( ws, sizeof( ws ), "(%s GNSS type %i): ", str_unknown, gnss_type );
+ cp = ws;
+ }
+ else
+ cp = gnss_type_names[gnss_type];
+
+ if ( print_multi_lines )
+ printf( " " );
+
+ if ( agi.gnss_mode_info.settings.gnss_set & ( 1UL << gnss_type ) )
+ {
+ printf( "%i %s sats tracked, %i expected to be visible\n", p_gsi->good_svs, cp, p_gsi->svs_in_view );
+
+ if ( must_print_sv_list )
+ {
+ int sat_idx;
+
+ for ( sat_idx = 0; sat_idx < MAX_USED_SATS; sat_idx++ )
+ {
+ int sat_num = p_gsi->svs[sat_idx];
- if ( _pcps_has_stat_info_svs( p_dev ) )
- printf( "%s, %i sats in view, %i sats used\n", mode_name, si.svs_in_view, si.good_svs );
+ #if !defined( DEBUG )
+ if ( sat_num == 0 )
+ break;
+ #endif
+
+ printf( "%s%i", ( sat_idx == 0 ) ? " Sats: " : ", ", sat_num );
+ }
+
+ if ( sat_idx ) // the satellite list has been printed
+ printf( "\n" );
+ }
+ }
+ else
+ printf( "%s reception disabled by configuration\n", cp );
+ }
}
if ( verbose )
{
+ #if 0 //##+++++++++++++++++++++++++
+ printf( "Feature mask: 0x%08lX\n", (ulong) ri.features );
+ #endif
+
printf( "Osc type: %s", osc_name[( ri.osc_type < N_GPS_OSC ) ? ri.osc_type : GPS_OSC_UNKNOWN] );
if ( _pcps_has_stat_info( p_dev ) )
{
printf( ", DAC cal: %+i, fine: %+i",
- (int) ( si.dac_cal - OSC_DAC_BIAS ),
- (int) ( si.dac_val - OSC_DAC_BIAS ) );
+ (int) ( agi.stat_info.dac_cal - OSC_DAC_BIAS ),
+ (int) ( agi.stat_info.dac_val - OSC_DAC_BIAS ) );
}
puts( "" );
@@ -507,42 +639,56 @@ void show_utc_info( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
if ( mbg_ioctl_err( rc, "mbg_get_utc_parm" ) )
return;
- if ( !utc.valid )
- {
- puts( "** UTC parameters not valid" );
- return;
- }
- if ( verbose > 1 )
+ if ( utc.valid )
{
- //##++++ utc.delta_tls = utc.delta_tlsf - 1;
-
- printf( "CSUM: %04X, valid: %04X\n", utc.csum, utc.valid );
- printf( "t0t: %u|%u.%07u, A0: %g A1: %g\n",
- utc.t0t.wn, utc.t0t.sec, utc.t0t.tick,
- utc.A0, utc.A1 );
- printf( "WNlsf: %u, DN: %u, offs: %i/%i\n",
- utc.WNlsf, utc.DNt, utc.delta_tls, utc.delta_tlsf );
- }
+ char tmp_str[80];
+ struct tm tm = { 0 };
- if ( utc.delta_tls != utc.delta_tlsf )
- {
- // a leap second is currently being announced
- time_t t_ls = (time_t) utc.WNlsf * SECS_PER_WEEK
- + (time_t) utc.DNt * SECS_PER_DAY
- + GPS_SEC_BIAS - 1;
-
- struct tm *tm = gmtime( &t_ls );
-
- printf( "UTC offset transition from %is to %is due to leap second\n"
- "%s at UTC midnight at the end of %04i-%02i-%02i.\n",
- utc.delta_tls, utc.delta_tlsf,
- ( utc.delta_tls < utc.delta_tlsf ) ? "insertion" : "deletion",
- tm->tm_year + 1900, tm->tm_mon + 1, tm->tm_mday
- );
+ long t_ls_long = (long) utc.WNlsf * SECS_PER_WEEK
+ + (long) utc.DNt * SECS_PER_DAY
+ + GPS_SEC_BIAS - 1;
+ time_t t_ls = cvt_to_time_t( t_ls_long );
+
+ rc = mbg_gmtime( &tm, &t_ls );
+
+ if ( mbg_rc_is_success( rc ) )
+ mbg_snprintf( tmp_str, sizeof( tmp_str ), "at UTC midnight at the end of %s, %04i-%02i-%02i",
+ wdays[tm.tm_wday], tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday );
+ else
+ snprint_gmtime_error( tmp_str, sizeof( tmp_str ), rc, t_ls, __func__ );
+
+ if ( verbose > 1 )
+ {
+ //##++++++++++ utc.delta_tls = utc.delta_tlsf - 1;
+
+ printf( "CSUM: %04X, valid: %04X\n", utc.csum, utc.valid );
+ printf( "t0t: %u|%u.%07u, A0: %g A1: %g\n",
+ utc.t0t.wn, utc.t0t.sec, utc.t0t.tick,
+ utc.A0, utc.A1 );
+ printf( "WNlsf: %u, DN: %u, offs: %i/%i\n",
+ utc.WNlsf, utc.DNt, utc.delta_tls, utc.delta_tlsf );
+ }
+
+ if ( utc.delta_tls != utc.delta_tlsf )
+ {
+ // a leap second is currently being announced
+ printf( "UTC offset transition from %is to %is due to leap second\n"
+ "%s %s.\n",
+ utc.delta_tls, utc.delta_tlsf,
+ ( utc.delta_tls < utc.delta_tlsf ) ? "insertion" : "deletion",
+ tmp_str
+ );
+ }
+ else
+ if ( verbose )
+ printf( "Leap second eventually %s\n", tmp_str );
+ else
+ printf( "UTC offset parameter: %is, no leap second announced.\n", utc.delta_tls );
}
else
- printf( "UTC offset parameter: %is, no leap second announced.\n", utc.delta_tls );
+ puts( "** UTC parameters not valid" );
+
} // show_utc_info
@@ -575,10 +721,10 @@ char *str_raw_irig_utc_offs_hours( char *s, int max_len, const MBG_RAW_IRIG_DATA
| ( ( p->data_bytes[8] >> 4 ) & 0x02 )
| ( ( p->data_bytes[8] >> 6 ) & 0x01 );
- n = snprintf( s, max_len, "%c%li", ( p->data_bytes[8] & 0x80 ) ? '-' : '+', offs );
+ n = mbg_snprintf( s, max_len, "%c%li", ( p->data_bytes[8] & 0x80 ) ? '-' : '+', offs );
if ( p->data_bytes[8] & 0x02 )
- n += snprintf( &s[n], max_len - n, "%s", ".5" );
+ n += mbg_snprintf( &s[n], max_len - n, "%s", ".5" );
return s;
@@ -679,12 +825,24 @@ void show_lan_intf_state( MBG_DEV_HANDLE dh )
static /*HDR*/
void show_ptp_state( MBG_DEV_HANDLE dh )
{
- static const char *ptp_stat_str[N_PTP_PORT_STATE] = PTP_PORT_STATE_STRS;
+ static const char *ptp_role_strs[N_PTP_ROLES] = PTP_ROLE_STRS;
+ static const char *ptp_state_strs[N_PTP_PORT_STATE] = PTP_PORT_STATE_STRS;
+ static const char *ptp_nw_prot_strs[N_PTP_NW_PROT] = PTP_NW_PROT_STRS;
+ static const char *ptp_delay_mech_names[N_PTP_DELAY_MECH] = PTP_DELAY_MECH_NAMES;
+ static const PTP_TABLE ptp_time_source_tbl[] = PTP_TIME_SOURCE_TABLE;
+ static const char *ptp_clock_accuracy_strs[] = PTP_CLOCK_ACCURACY_STRS;
+
char ws[100];
const char *cp;
- int ptp_state_available;
+ int must_show_slave_mode_info;
+ int must_show_master_mode_info;
+ int slave_mode_active;
+ int master_mode_active;
+ int any_mode_active;
+ int utc_offset_valid;
PTP_STATE ptp_state;
PTP_CFG_INFO ptp_info;
+ int tmp;
int rc = mbg_get_ptp_state( dh, &ptp_state );
@@ -696,45 +854,185 @@ void show_ptp_state( MBG_DEV_HANDLE dh )
if ( mbg_ioctl_err( rc, "mbg_get_ptp_info" ) )
return;
- printf( "PTP port status:\n" );
- ptp_state_available = ( ptp_state.port_state == PTP_PORT_STATE_SLAVE );
+ // set up some flags controlling which information to be shown
- printf( " Port mode: %s%s\n", ( ptp_state_available && ptp_info.settings.ptp_role == PTP_ROLE_UNICAST_SLAVE ) ? "Unicast" : "",
- ( ptp_state.port_state < N_PTP_PORT_STATE ) ? ptp_stat_str[ptp_state.port_state] : "(undefined)" );
+ must_show_slave_mode_info = ( verbose > 1 ) ||
+ ( ( ( 1UL << ptp_info.settings.ptp_role ) & PTP_ROLE_MSK_SLAVES ) != 0 );
- cp = ptp_state_available ? ws : str_not_avail;
+ must_show_master_mode_info = ( verbose > 1 ) ||
+ ( ( ( 1UL << ptp_info.settings.ptp_role ) & PTP_ROLE_MSK_MASTERS ) != 0 );
-//##++++++++++
- snprintf( ws, sizeof( ws ), "%02X-%02X-%02X-%02X-%02X-%02X",
- ptp_state.gm_id.b[0],
- ptp_state.gm_id.b[1],
- ptp_state.gm_id.b[2],
- ptp_state.gm_id.b[5],
- ptp_state.gm_id.b[6],
- ptp_state.gm_id.b[7]
- );
- printf( " Grandmaster MAC: %s\n", cp );
+ slave_mode_active = ( ptp_state.port_state == PTP_PORT_STATE_UNCALIBRATED )
+ || ( ptp_state.port_state == PTP_PORT_STATE_SLAVE );
+ master_mode_active = ( ptp_state.port_state == PTP_PORT_STATE_PRE_MASTER )
+ || ( ptp_state.port_state == PTP_PORT_STATE_MASTER )
+ || ( ptp_state.port_state == PTP_PORT_STATE_PASSIVE );
- snprintf( ws, sizeof( ws ), "%c%li.%09li s",
- _nano_time_negative( &ptp_state.path_delay ) ? '-' : '+',
- labs( (long) ptp_state.path_delay.secs ),
- labs( (long) ptp_state.path_delay.nano_secs )
- );
- printf( " PTP path delay: %s\n", cp );
+ any_mode_active = slave_mode_active || master_mode_active;
- snprintf( ws, sizeof( ws ), "%c%li.%09li s",
- _nano_time_negative( &ptp_state.offset ) ? '-' : '+',
- labs( (long) ptp_state.offset.secs ),
- labs( (long) ptp_state.offset.nano_secs )
- );
- printf( " PTP time offset: %s\n", cp );
+ // PTP role and port state
+
+ printf( "PTP port state:\n" );
+
+ printf( " Port mode: " );
+
+ if ( any_mode_active )
+ printf( "%s", ( ptp_state.flags & PTP_FLAG_MSK_IS_UNICAST ) ?
+ "Unicast " : "Multicast " );
+
+ if ( ptp_state.port_state < N_PTP_PORT_STATE )
+ printf( "%s", ptp_state_strs[ptp_state.port_state] );
+ else
+ printf( "%s, code %i", str_undefined, ptp_state.port_state );
+
+ if ( !any_mode_active || ( verbose > 1 ) )
+ printf( " in %s role",
+ ( ptp_info.settings.ptp_role < N_PTP_ROLES ) ?
+ ptp_role_strs[ptp_info.settings.ptp_role] : str_undefined );
+
+ printf( "\n" );
+
+
+ if ( !any_mode_active || verbose )
+ {
+ printf( " PTP protocol: " );
+
+ // If not fully synchronized then not all fields of the PTP_STATE
+ // structure may have been filled, so we show configuration settings
+ // in this case.
+
+ if ( ptp_state.ptp_prot_version )
+ printf( "v%i, ", ptp_state.ptp_prot_version );
+
+ tmp = any_mode_active ? ptp_state.nw_prot : ptp_info.settings.nw_prot;
+ printf( "%s", ( tmp < N_PTP_NW_PROT ) ?
+ ptp_nw_prot_strs[tmp] : str_undefined );
+
+ printf( ", %s step",
+ ( ptp_state.flags & PTP_FLAG_MSK_ONE_STEP ) ? "one" : "two" );
+
+ tmp = any_mode_active ? ptp_state.domain_number : ptp_info.settings.domain_number;
+ printf( ", domain %i", tmp );
+
+ tmp = any_mode_active ? ptp_state.delay_mech : ptp_info.settings.delay_mech;
+ printf( ", delay mech. %s", ( tmp < N_PTP_DELAY_MECH ) ?
+ ptp_delay_mech_names[tmp] : str_undefined );
+
+ tmp = any_mode_active ? ptp_state.log_delay_req_intv : ptp_info.settings.delay_req_intv;
+ printf( ", dly req. intv. 2^%i s", tmp );
+
+ printf( "\n" );
+ }
+
+
+ if ( must_show_slave_mode_info )
+ {
+ cp = ( slave_mode_active || ( verbose > 1 ) ) ? ws : str_not_avail;
+
+ snprint_octets( ws, sizeof( ws ), ptp_state.gm_id.b,
+ sizeof( ptp_state.gm_id.b ), MAC_SEP_CHAR_ALT, NULL );
+ printf( " Grandmaster ID: %s\n", cp );
+
+ snprint_nano_time( ws, sizeof( ws ), &ptp_state.offset );
+ printf( " PTP time offset: %s\n", cp );
+
+ snprint_nano_time( ws, sizeof( ws ), &ptp_state.path_delay );
+ printf( " PTP path delay: %s\n", cp );
+
+ if ( verbose > 1 )
+ {
+ snprint_nano_time( ws, sizeof( ws ), &ptp_state.mean_path_delay );
+ printf( " Mean path delay: %s\n", cp );
+
+ snprint_nano_time( ws, sizeof( ws ), &ptp_state.delay_asymmetry );
+ printf( " Delay asymmetry: %s\n", cp );
+ }
+ }
+
+
+ // PTP time scale
+
+ cp = NULL;
+
+ if ( ptp_state.flags & PTP_FLAG_MSK_TIMESCALE_IS_PTP ) // this is the default
+ {
+ if ( must_show_master_mode_info || verbose )
+ cp = "TAI (standard)";
+ }
+ else // unusual case, print info if available
+ if ( any_mode_active )
+ cp = "arbitrary (non-standard)";
+
+ if ( cp )
+ printf( " PTP time scale: %s\n", cp );
+
+
+ // UTC offset and leap second status
+
+ utc_offset_valid = ( ptp_state.flags & PTP_FLAG_MSK_UTC_VALID ) != 0;
+
+ printf( " PTP UTC offset: " );
+
+ if ( !utc_offset_valid )
+ printf( " %s", str_unknown ); // UTC offset not valid
+
+ if ( utc_offset_valid || ( verbose > 1 ) )
+ {
+ printf( utc_offset_valid ? " " : " (" );
+
+ printf( "%+i s", ptp_state.utc_offset );
+
+ if ( ptp_state.flags & PTP_FLAG_MSK_LS_ANN ) // leap second is announced
+ {
+ // distinguish between leap second insertion and deletion
+ printf( ", leap second %s scheduled",
+ ( ptp_state.flags & PTP_FLAG_MSK_LS_ANN_NEG ) ? "deletion" : "insertion" );
+ }
+
+ if ( !utc_offset_valid )
+ printf( ")" );
+ }
+
+ printf( "\n" );
+
+
+ if ( verbose > 1 )
+ {
+ const PTP_TABLE *p_tbl;
+
+ printf( "PTP clock state:\n" );
+
+ for ( p_tbl = ptp_time_source_tbl; p_tbl->name; p_tbl++ )
+ if ( p_tbl->value == ptp_state.time_source )
+ break;
+
+ printf( " Time source: %s\n", p_tbl->name ? p_tbl->name : str_unknown );
+
+ printf( " Clock class: %i\n", ptp_state.clock_class );
+
+ tmp = N_PTP_CLOCK_ACCURACY - PTP_CLOCK_ACCURACY_NUM_BIAS;
+
+ if ( ( ptp_state.clock_accuracy >= PTP_CLOCK_ACCURACY_NUM_BIAS ) &&
+ ( ptp_state.clock_accuracy < N_PTP_CLOCK_ACCURACY ) )
+ cp = ptp_clock_accuracy_strs[ptp_state.clock_accuracy - PTP_CLOCK_ACCURACY_NUM_BIAS];
+ else
+ cp = str_undefined;
+
+ printf( " Clock accuracy: %s\n", cp );
+
+#if 0
+ time_source
+ clock_class
+ clock_accuracy
+#endif
+ printf( " Offs sc. log var: %u", ptp_state.clock_offset_scaled_log_variance );
+ printf( "\n" );
+ }
+
- if ( verbose )
- printf( " PTP UTC offset: %i, flags: 0x%02X\n",
- ptp_state.utc_offset, ptp_state.flags );
} // show_ptp_state
@@ -800,32 +1098,59 @@ int do_mbgstatus( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
if ( check_irq_unsafe( dh, p_dev ) < 0 )
goto done;
- if ( _pcps_has_gps_data( p_dev ) )
- show_ext_stat_info( dh, p_dev, NULL );
+ for (;;)
+ {
+ if ( _pcps_has_gps_data( p_dev ) )
+ show_ext_stat_info( dh, p_dev, NULL );
- show_time_and_status( dh, p_dev, "\n" );
- show_sync_time( dh, "\n" );
+ show_time_and_status( dh, p_dev, "\n" );
+ show_sync_time( dh, "\n" );
- if ( _pcps_is_gps( p_dev ) )
- show_gps_pos( dh, "\n" );
+ if ( _pcps_is_gps( p_dev ) )
+ show_gps_pos( dh, "\n" );
- if ( _pcps_has_utc_parm( p_dev ) && ( _pcps_is_gps( p_dev ) || ( verbose > 0 ) ) )
- show_utc_info( dh, p_dev );
+ if ( _pcps_has_utc_parm( p_dev ) && ( _pcps_is_gps( p_dev ) || ( verbose > 0 ) ) )
+ show_utc_info( dh, p_dev );
- if ( verbose && _pcps_has_irig_ctrl_bits( p_dev ) )
- show_irig_ctrl_bits( dh );
+ if ( verbose && _pcps_has_irig_ctrl_bits( p_dev ) )
+ show_irig_ctrl_bits( dh );
- if ( verbose && _pcps_has_raw_irig_data( p_dev ) )
- show_raw_irig_data( dh );
+ if ( verbose && _pcps_has_raw_irig_data( p_dev ) )
+ show_raw_irig_data( dh );
- if ( verbose && _pcps_is_irig_rx( p_dev ) )
- show_irig_debug_status( dh );
+ if ( verbose && _pcps_is_irig_rx( p_dev ) )
+ show_irig_debug_status( dh );
- if ( _pcps_has_lan_intf( p_dev ) )
- show_lan_intf_state( dh );
+ if ( _pcps_has_lan_intf( p_dev ) )
+ show_lan_intf_state( dh );
- if ( _pcps_has_ptp( p_dev ) )
- show_ptp_state( dh );
+ if ( _pcps_has_ptp( p_dev ) )
+ show_ptp_state( dh );
+
+ #if 0 && defined( DEBUG ) //##++++++++
+ if ( verbose > 1 )
+ {
+ test_xmr( dh, p_dev, verbose );
+ test_gpio( dh, p_dev, verbose );
+ }
+ #endif
+
+ if ( loops > 0 )
+ loops--;
+
+ if ( loops == 0 )
+ break;
+
+ if ( sleep_secs )
+ sleep( sleep_secs );
+ else
+ if ( sleep_usecs )
+ usleep( sleep_usecs );
+
+ printf( "\n" );
+
+ // if this_loops is < 0 then loop forever
+ }
show_invt_reason();
@@ -844,6 +1169,11 @@ void usage( void )
"The displayed information depends on the type of the card."
);
mbg_print_help_options();
+ mbg_print_opt_info( "-c", "run continuously" );
+ mbg_print_opt_info( "-n num", "run num loops" );
+ mbg_print_opt_info( "-s num", "sleep num seconds between calls (implies -c)" );
+ mbg_print_opt_info( "-u num", "sleep num microseconds between calls (implies -c)" );
+ mbg_print_opt_info( "-v", "increase verbosity" );
mbg_print_device_options();
puts( "" );
@@ -864,10 +1194,28 @@ int main( int argc, char *argv[] )
mbg_print_program_info( pname, MBG_MICRO_VERSION, MBG_FIRST_COPYRIGHT_YEAR, MBG_LAST_COPYRIGHT_YEAR );
// check command line parameters
- while ( ( c = getopt( argc, argv, "vh?" ) ) != -1 )
+ while ( ( c = getopt( argc, argv, "cn:s:u:vh?" ) ) != -1 )
{
switch ( c )
{
+ case 'c':
+ loops = -1;
+ break;
+
+ case 'n':
+ loops = atoi( optarg );
+ break;
+
+ case 's':
+ sleep_secs = atoi( optarg );
+ loops = -1;
+ break;
+
+ case 'u':
+ sleep_usecs = atoi( optarg );
+ loops = -1;
+ break;
+
case 'v':
verbose++;
break;
@@ -893,8 +1241,8 @@ int main( int argc, char *argv[] )
// on the command, and for each device
// - tries to open the device
// - shows basic device info
- // - calls the function passed as last parameter
- rc = mbg_check_devices( argc, argv, optind, do_mbgstatus );
+ // - calls the specified callback function
+ rc = mbg_check_devices( argc, argv, optind, do_mbgstatus, CHK_DEV_ALL_DEVICES );
return abs( rc );
}
diff --git a/mbgsvcd/BSDmakefile b/mbgsvcd/BSDmakefile
new file mode 100755
index 0000000..9f4742d
--- /dev/null
+++ b/mbgsvcd/BSDmakefile
@@ -0,0 +1,34 @@
+
+#########################################################################
+#
+# $Id: BSDmakefile 1.1 2017/04/25 20:21:30 martin TEST $
+#
+# Description:
+# Special Makefile for mbgsvcd under *BSD which doesn't contain
+# any code specific to GNU make.
+#
+# -----------------------------------------------------------------------
+# $Log: BSDmakefile $
+# Revision 1.1 2017/04/25 20:21:30 martin
+# Initial revision.
+#
+#########################################################################
+
+TARGET = mbgsvcd
+INST_TO_SBIN = 1
+
+OBJS = $(TARGET).o
+OBJS += mbgdevio.o
+OBJS += timeutil.o
+OBJS += str_util.o
+OBJS += toolutil.o
+OBJS += mbgerror.o
+OBJS += cfg_hlp.o
+OBJS += gpsutils.o
+OBJS += chk_time_info.o
+OBJS += ntp_shm.o
+
+LDFLAGS += -lrt
+
+BASEDIR := ..
+include $(BASEDIR)/Makefile
diff --git a/mbgsvcd/Makefile b/mbgsvcd/Makefile
deleted file mode 100755
index 5a520bc..0000000
--- a/mbgsvcd/Makefile
+++ /dev/null
@@ -1,39 +0,0 @@
-
-#########################################################################
-#
-# $Id: Makefile 1.1.1.5 2013/04/22 14:23:03 daniel TRASH $
-#
-# Description:
-# Makefile for mbgsvcd.
-#
-# -----------------------------------------------------------------------
-# $Log: Makefile $
-# Revision 1.1.1.5 2013/04/22 14:23:03 daniel
-# Add library rt
-# Revision 1.1.1.4 2012/08/06 11:27:11 martin
-# Added some object files to the list.
-# Revision 1.1.1.3 2011/09/26 16:07:31 martin
-# Updated for use with latest base Makefile.
-# Revision 1.1.1.2 2010/08/30 09:05:24 martin
-# Revision 1.1.1.1 2010/08/30 08:22:06 martin
-# Revision 1.1 2010/02/03 16:07:18 daniel
-# Revision 1.1 2009/09/29 08:34:23 martin
-#
-#########################################################################
-
-TARGET = mbgsvcd
-INST_TO_SBIN = 1
-
-OBJS = $(TARGET).o
-OBJS += mbgdevio.o
-OBJS += toolutil.o
-OBJS += gpsutils.o
-OBJS += mbgmktm.o
-OBJS += pcpsmktm.o
-OBJS += chk_time_info.o
-OBJS += ntp_shm.o
-
-LDFLAGS += -lrt
-
-BASEDIR := ..
-include $(BASEDIR)/Makefile
diff --git a/mbgsvcd/mbgsvcd.c b/mbgsvcd/mbgsvcd.c
index 9ad9201..9c1df73 100755
--- a/mbgsvcd/mbgsvcd.c
+++ b/mbgsvcd/mbgsvcd.c
@@ -1,16 +1,25 @@
/**************************************************************************
*
- * $Id: mbgsvcd.c 1.3.1.15.1.6 2013/06/26 16:33:21 martin TRASH $
+ * $Id: mbgsvcd.c 1.3.1.15.1.5.1.5 2017/02/17 11:49:39 martin TEST $
*
* Description:
- * Main file for mbgsvcd which compares the system time to a PCI card's
+ * Main file for mbgsvcd which compares the system time to a PCI card's
* time and transfers this data pair to the SHM driver of the ntpd.
*
* -----------------------------------------------------------------------
* $Log: mbgsvcd.c $
- * Revision 1.3.1.15.1.6 2013/06/26 16:33:21 martin
- * Don't include sys/sysinfo .h, doesn't build under FreeBSD.
+ * Revision 1.3.1.15.1.5.1.5 2017/02/17 11:49:39 martin
+ * Fixed a comiler warning.
+ * Revision 1.3.1.15.1.5.1.4 2017/01/30 09:05:54 martin
+ * Fixed a typo.
+ * Removed non-ASCII character in comment.
+ * Revision 1.3.1.15.1.5.1.3 2017/01/27 12:23:35 martin
+ * Account for renamed structure fields.
+ * Revision 1.3.1.15.1.5.1.2 2015/12/17 11:59:39 martin
+ * Fixed a compiler warning 'set but not used'.
+ * Revision 1.3.1.15.1.5.1.1 2014/11/25 13:47:04 martin
+ * Support options -q and -r.
* Revision 1.3.1.15.1.5 2013/04/24 08:19:53 daniel
* Use seconds for the trust time.
* Revision 1.3.1.15.1.3 2013/01/24 14:41:53 martin
@@ -76,7 +85,7 @@
#include <arpa/inet.h>
#include <sys/socket.h>
#include <sys/types.h>
-#include <sys/time.h>
+#include <sys/time.h>
#include <sys/stat.h>
#include <unistd.h>
#include <errno.h>
@@ -86,10 +95,6 @@
#include <stdarg.h>
#include <time.h>
#include <sys/time.h>
-
-// #include <sys/sysinfo.h>
-
-
#include <sys/ipc.h>
#include <sys/shm.h>
@@ -102,11 +107,14 @@
static const char *pname = "mbgsvcd";
-static int sleep_intv = 1;
-static unsigned long trust_time_seconds = 345600UL; // 4 days as default
-static int pretend_sync;
+static int foreground; // -f
+static int quiet; // -q
+static int pretend_sync; // -p
+static int print_raw; // -r
+static int sleep_intv = 1; // -s
+static unsigned long trust_time_seconds; // -t
+
static int frac_digits = 9;
-static int print_raw;
MBG_PC_CYCLES_FREQUENCY cyc_freq;
@@ -130,7 +138,7 @@ void mbg_log( int lvl, const char *fmt, ... )
vsnprintf( ws, sizeof( ws ), fmt, ap );
va_end( ap );
- syslog( lvl, ws );
+ syslog( lvl, "%s", ws );
fprintf( stdout, "%s\n", ws );
} // mbg_log
@@ -220,28 +228,27 @@ int do_mbgsvctasks( void )
cp = "";
leap = 0;
-
- if ( ( has_synced_after_reset[i] == 1 ) && ( ( ( cti.hrti.ref_hr_time_cycles.t.status & PCPS_FREER ) == 1 )
+
+ if ( ( has_synced_after_reset[i] == 1 ) && ( ( ( cti.hrti.ref_hr_time_cycles.t.status & PCPS_FREER ) == 1 )
|| ( ( cti.hrti.ref_hr_time_cycles.t.status & PCPS_SYNCD ) == 0 ) ))
-
{
struct timespec ts;
-
+
clock_gettime(CLOCK_MONOTONIC, &ts);
-
+
if (ref_trust_time_start[i] == 0 )
{
mbg_log( LOG_WARNING, "Device #%i, entering holdover mode", i );
ref_trust_time_start[i] = ts.tv_sec;
ref_trust_time_expire[i] = ts.tv_sec + trust_time_seconds;
}
-
+
if ( ts.tv_sec > ref_trust_time_expire[i] )
{
mbg_log( LOG_WARNING, "Device #%i, trust time expired", i );
has_synced_after_reset[i] = 0;
ref_trust_time_start[i] = 0;
- ref_trust_time_expire[i] = 0;
+ ref_trust_time_expire[i] = 0;
}
}
@@ -251,7 +258,7 @@ int do_mbgsvctasks( void )
( ( cti.hrti.ref_hr_time_cycles.t.status & PCPS_SYNCD ) != 0 ) ) ) )
{
struct shmTime *p = shmTime[i];
-
+
has_synced_after_reset[i] = 1;
if ( p )
@@ -262,13 +269,13 @@ int do_mbgsvctasks( void )
// fill SHM structure
p->count++;
p->clockTimeStampSec = (time_t) cti.d_ref_comp;
- p->clockTimeStampUSec = (int) ( ( cti.d_ref_comp - p->clockTimeStampSec ) * 1e6 ); // get µs from d_ref
- p->receiveTimeStampSec = (time_t) p_sys_tic->sys_time.sec;
- p->receiveTimeStampUSec = (int) ( p_sys_tic->sys_time.nsec / 1000 );
+ p->clockTimeStampUSec = (int) ( ( cti.d_ref_comp - p->clockTimeStampSec ) * 1e6 ); // get microseconds from d_ref
+ p->receiveTimeStampSec = (time_t) p_sys_tic->sys_time.secs;
+ p->receiveTimeStampUSec = (int) ( p_sys_tic->sys_time.nano_secs / 1000 );
// These fields are only supported by newer versions of ntpd //##++++++++++++++++++ which versions ?
- p->clockTimeStampNSec = (int) ( ( cti.d_ref_comp - p->clockTimeStampSec ) * 1e9 ); // get ns from d_ref
- p->receiveTimeStampNSec = (int) ( p_sys_tic->sys_time.nsec );
+ p->clockTimeStampNSec = (int) ( ( cti.d_ref_comp - p->clockTimeStampSec ) * 1e9 ); // get nanoseconds from d_ref
+ p->receiveTimeStampNSec = (int) ( p_sys_tic->sys_time.nano_secs );
// patch precision value according to the ref time accuracy
if ( _pcps_is_lwr( &devs[i] ) )
@@ -301,8 +308,11 @@ int do_mbgsvctasks( void )
}
}
- snprint_chk_time_info( ws, sizeof( ws ), &cti, &devs[i], frac_digits, print_raw );
- printf( "%s, leap: %02X%s\n", ws, leap, cp );
+ if ( !quiet )
+ {
+ snprint_chk_time_info( ws, sizeof( ws ), &cti, &devs[i], frac_digits, print_raw );
+ printf( "%s, leap: %02X%s\n", ws, leap, cp );
+ }
usleep( 10 );
}
@@ -337,6 +347,8 @@ void usage( void )
);
mbg_print_help_options();
mbg_print_opt_info( "-f", "run program in foreground" );
+ mbg_print_opt_info( "-q", "quiet, don't print time differences on stdout" );
+ mbg_print_opt_info( "-r", "print raw time stamps when printing on stdout" );
mbg_print_opt_info( "-s num", "sleep num seconds between calls" );
mbg_print_opt_info( "-p", "pretend device is always synchronized" );
mbg_print_opt_info( "-t num", "set num seconds for refclock trust time, default 4 days (345600 seconds)" );
@@ -387,7 +399,7 @@ void startup_daemon( void )
if ( lfp < 0 )
exit( 1 ); /* unable to open lock file */
- if ( lockf( lfp, F_TLOCK, 0 ) < 0 )
+ if ( lockf( lfp, F_TLOCK, 0 ) < 0 )
{
mbg_log( LOG_ERR, "Lock file already exists, another instance of this daemon seems to be running" );
closelog();
@@ -398,6 +410,8 @@ void startup_daemon( void )
snprintf( str, sizeof( str ), "%d\n", getpid() );
rc = write( lfp, str, strlen( str ) ); /* record pid to lockfile */
+ (void) rc; // avoid warning "set but not used"
+
signal( SIGCHLD, SIG_IGN ); /* ignore child */
signal( SIGTSTP, SIG_IGN ); /* ignore tty signals */
signal( SIGTTOU, SIG_IGN );
@@ -411,12 +425,11 @@ int main( int argc, char *argv[] )
{
int rc;
int c;
- int foreground = 0;
mbg_print_program_info( pname, MBG_MICRO_VERSION, MBG_FIRST_COPYRIGHT_YEAR, MBG_LAST_COPYRIGHT_YEAR );
// check command line parameters
- while ( ( c = getopt( argc, argv, "fpst:h?" ) ) != -1 )
+ while ( ( c = getopt( argc, argv, "fpqrst:h?" ) ) != -1 )
{
switch ( c )
{
@@ -428,16 +441,25 @@ int main( int argc, char *argv[] )
pretend_sync = 1;
break;
+ case 'q':
+ quiet++;
+ break;
+
+ case 'r':
+ print_raw = 1;
+ break;
+
case 's':
sleep_intv = atoi( optarg );
break;
case 't':
{
- unsigned long tt = atoi( optarg );
-
+ long tt = atol( optarg );
+
if ( tt > 0 )
- trust_time_seconds = tt;
+ trust_time_seconds = tt;
+
break;
}
@@ -466,7 +488,8 @@ int main( int argc, char *argv[] )
startup_daemon();
}
- mbg_log( LOG_INFO, "refclock trust time: %ul seconds", trust_time_seconds );
+ if ( trust_time_seconds )
+ mbg_log( LOG_INFO, "refclock trust time: %ul seconds", trust_time_seconds );
rc = do_mbgsvctasks();
diff --git a/mbgversion.h b/mbgversion.h
index c7df42f..6bf9c1e 100755
--- a/mbgversion.h
+++ b/mbgversion.h
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgversion.h 1.1.1.2 2013/03/11 14:40:34 martin TRASH $
+ * $Id: mbgversion.h 1.1.1.3 2017/02/23 15:24:05 martin TEST $
*
* Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
*
@@ -10,6 +10,8 @@
*
* -----------------------------------------------------------------------
* $Log: mbgversion.h $
+ * Revision 1.1.1.3 2017/02/23 15:24:05 martin
+ * Changed copyright year to 2017.
* Revision 1.1.1.2 2013/03/11 14:40:34 martin
* Changed copyright year to 2013.
* Revision 1.1.1.1 2012/10/16 10:23:20 martin
@@ -19,8 +21,8 @@
*
**************************************************************************/
-#define MBG_CURRENT_COPYRIGHT_YEAR 2013
-#define MBG_CURRENT_COPYRIGHT_YEAR_STR "2013"
+#define MBG_CURRENT_COPYRIGHT_YEAR 2017
+#define MBG_CURRENT_COPYRIGHT_YEAR_STR "2017"
#define MBG_MAJOR_VERSION_CODE 0
#define MBG_MINOR_VERSION_CODE 99
diff --git a/mbgxhrtime/Makefile b/mbgxhrtime/Makefile
index 4162670..51c10a3 100755
--- a/mbgxhrtime/Makefile
+++ b/mbgxhrtime/Makefile
@@ -1,13 +1,20 @@
#########################################################################
#
-# $Id: Makefile 1.2.1.3 2011/09/26 16:07:31 martin TEST $
+# $Id: Makefile 1.2.1.7 2016/07/15 14:07:29 martin TEST $
#
# Description:
# Makefile for mbgxhrtime.
#
# -----------------------------------------------------------------------
# $Log: Makefile $
+# Revision 1.2.1.7 2016/07/15 14:07:29 martin
+# *** empty log message ***
+# Revision 1.2.1.6 2015/08/31 14:29:41 martin
+# Revision 1.2.1.5 2015/07/14 15:07:21 martin
+# Added object module mbgerror.o.
+# Revision 1.2.1.4 2014/04/28 13:19:52 martin
+# Added module cfg_hlp.o.
# Revision 1.2.1.3 2011/09/26 16:07:31 martin
# Updated for use with latest base Makefile.
# Revision 1.2.1.2 2010/08/30 09:05:24 martin
@@ -26,7 +33,11 @@ USE_THREAD_API = 1
OBJS = $(TARGET).o
OBJS += mbgdevio.o
+OBJS += timeutil.o
+OBJS += str_util.o
OBJS += toolutil.o
+OBJS += mbgerror.o
+OBJS += cfg_hlp.o
OBJS += gpsutils.o
BASEDIR := ..
diff --git a/mbgxhrtime/mbgxhrtime.c b/mbgxhrtime/mbgxhrtime.c
index b7b8c79..392bab9 100755
--- a/mbgxhrtime/mbgxhrtime.c
+++ b/mbgxhrtime/mbgxhrtime.c
@@ -1,7 +1,7 @@
/**************************************************************************
*
- * $Id: mbgxhrtime.c 1.5.1.3 2011/09/07 15:08:56 martin TEST $
+ * $Id: mbgxhrtime.c 1.5.1.10 2016/08/09 07:13:30 martin TEST $
*
* Description:
* Main file for mbgxhrtime program which demonstrates how to retrieve
@@ -41,7 +41,16 @@
*
* -----------------------------------------------------------------------
* $Log: mbgxhrtime.c $
- * Revision 1.5.1.3 2011/09/07 15:08:56 martin
+ * Revision 1.5.1.10 2016/08/09 07:13:30 martin
+ * *** empty log message ***
+ * Revision 1.5.1.9 2015/10/26 13:53:10 martin
+ * Revision 1.5.1.8 2014/10/28 15:38:45Z martin
+ * Revision 1.5.1.7 2014/10/16 10:37:44Z martin
+ * Revision 1.5.1.6 2013/07/22 16:25:11Z martin
+ * Revision 1.5.1.5 2013/07/11 08:29:30 martin
+ * Account for modified function call parameter list.
+ * Revision 1.5.1.4 2013/07/10 13:02:58 martin
+ * Revision 1.5.1.3 2011/09/07 15:08:56Z martin
* Account for modified library functions which can now
* optionally print the raw (hex) HR time stamp.
* Revision 1.5.1.2 2011/07/05 15:35:56 martin
@@ -65,23 +74,24 @@
// include Meinberg headers
#include <mbgdevio.h>
-#include <pcpsutil.h>
#include <toolutil.h> // common utility functions
// include system headers
#include <time.h>
#include <stdio.h>
#include <stdlib.h>
-#include <unistd.h>
-#include <pthread.h>
-#include <sched.h>
+#if !defined( MBG_TGT_WIN32 )
+ #include <unistd.h>
+ #include <pthread.h>
+ #include <sched.h>
+#endif
#if !defined( MBGDEVIO_USE_THREAD_API )
#error Symbol MBGDEVIO_USE_THREAD_API needs to be defined, see the Makefile.
#endif
-#if !defined ( USE_PROCESS_AFFINITY )
+#if !defined( USE_PROCESS_AFFINITY )
#define USE_PROCESS_AFFINITY 1
#endif
@@ -219,10 +229,10 @@ int do_mbgxhrtime( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
{
puts( "" );
- printf( "PC cycles freq: %.6f MHz", ( (double) freq_hz ) / 1E6 );
+ printf( "PC cycles freq: %.6f MHz", ( (double) (int64_t) freq_hz ) / 1E6 );
if ( default_freq_hz )
- printf( ", default: %.6f MHz", ( (double) default_freq_hz ) / 1E6 );
+ printf( ", default: %.6f MHz", ( (double) (int64_t) default_freq_hz ) / 1E6 );
printf( "\n" );
@@ -239,7 +249,7 @@ int do_mbgxhrtime( MBG_DEV_HANDLE dh, const PCPS_DEV *p_dev )
goto fail;
// compute the latency
- latency = ( (double) cyc_2 - (double) cyc_1 ) / (double) freq_hz * 1E6;
+ latency = ( (double) cyc_2 - (double) cyc_1 ) / (double) (int64_t) freq_hz * 1E6;
// convert to human readable date and time
mbg_snprint_hr_time( ws, sizeof( ws ), &hrt, 0 ); // raw timestamp?
@@ -262,8 +272,6 @@ fail:
done:
mbg_xhrt_poll_thread_stop( &poll_thread_info );
- mbg_close_device( &dh );
-
return rc;
} // do_mbgxhrtime
@@ -337,8 +345,8 @@ int main( int argc, char *argv[] )
// on the command, and for each device
// - tries to open the device
// - shows basic device info
- // - calls the function passed as last parameter
- rc = mbg_check_devices( argc, argv, optind, do_mbgxhrtime );
+ // - calls the specified callback function
+ rc = mbg_check_devices( argc, argv, optind, do_mbgxhrtime, 0 );
return abs( rc );
}