mbgtools-lx  4.2.8
pcpsdrvr.h
Go to the documentation of this file.
1 
2 /**************************************************************************
3  *
4  * $Id: pcpsdrvr.h 1.53 2019/03/19 16:46:24 martin TRASH $
5  *
6  * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany
7  *
8  * Description:
9  * Definitions and prototypes for pcpsdrvr.c.
10  *
11  * -----------------------------------------------------------------------
12  * $Log: pcpsdrvr.h $
13  * Revision 1.53 2019/03/19 16:46:24 martin
14  * Removed some obsolete DEBUG control settings.
15  * Revision 1.52 2019/03/18 16:11:40 martin
16  * Made a warning message more detailed.
17  * Revision 1.51 2019/03/13 16:20:15 martin
18  * Don't use local I/O buffer by default.
19  * Revision 1.50 2019/03/11 16:13:46 martin
20  * Temporarily use local I/O buffers by default. This may avoid a
21  * potential data corruption problem with PCI devices, but won't work
22  * with USB devices on Linux kernels 4.9 and later.
23  * Revision 1.49 2018/11/22 16:35:34 martin
24  * Refactored debug logging stuff.
25  * Moved definition of FAR to mbggenio.h.
26  * Moved some default DEBUG_* definitions here.
27  * Revision 1.48 2018/09/21 15:19:51 martin
28  * Added definitions for TCR180USB.
29  * Always use PCPS_IO_BUFFER which is defined
30  * in new header file pcpsiobf.h.
31  * Introduced cmd union.
32  * New macro _pcps_ddev_fw_has_20ms_bug().
33  * Updated macro _pcps_ddev_read_status_port().
34  * More unified resource handling.
35  * Renamed a number of symbols.
36  * Use _MBG_IOMEM.
37  * Workaround for DEBUG builds for older NetBSD versions.
38  * Don't use volatile.
39  * Unified kernel driver messages.
40  * Conditional DEBUG_RSRC.
41  * Added _pcps_ddev_mem_rsrc().
42  * Introduced access mode stuff.
43  * Updated naming for device feature stuff.
44  * Doxygen fixes.
45  * Moved some specific macros to pcpsirq.h.
46  * Renamed some inline functions.
47  * Define PCPS_TIMEOUT_CNT only if it wasn't defined before.
48  * Updated doxygen comments.
49  * Updated function prototypes.
50  * Revision 1.47 2017/08/10 13:59:52 martin
51  * Unified extended resource properties handling.
52  * String 'pcps_driver_name' is now defined here.
53  * Revision 1.46 2017/07/04 16:50:48 martin
54  * Support GPS180AMC and GNS181PEX.
55  * Support new module parameter force_io_access to provide
56  * runtime support for forcing I/O rather than MM access.
57  * Cleaned up I/O port usage.
58  * Added _pcps_ddev_has_xmr() macro.
59  * Older defines N_SUPP_DEV, PCPS_MAX_DDEVS, and MBG_MAX_DEVICES
60  * have been obsoleted by new defines N_SUPP_DEV_BUS, N_SUPP_DEV_EXT,
61  * and N_SUPP_DEV_TOTAL.
62  * Conditional USB debug code.
63  * Use more versatile types for function pointers.
64  * Fixed macro definition syntax to avoid clang compiler warnings.
65  * Prepare to use MBG_XDEV_FEATURES in PCPS_DDEV.
66  * Updated function prototypes.
67  * Revision 1.45 2013/09/26 09:08:09 martin
68  * Support GLN180PEX and GNSS API.
69  * Revision 1.44 2013/03/15 10:01:09 martin
70  * Optionally override setting to support memory mapped I/O.
71  * Revision 1.43 2012/11/02 09:48:04 martin
72  * Removed obsolete include.
73  * Revision 1.42 2012/10/02 19:09:20 martin
74  * Conditionally support memory mapped access for MBGPEX cards.
75  * Support on-board event logs.
76  * New macro _pcps_ddev_has_debug_status().
77  * Added some macros to test if specific stat_info stuff is supported.
78  * Updated function prototypes.
79  * Added macros _pcps_ddev_has_corr_info() and _pcps_ddev_has_tr_distance().
80  * Support GPS180PEX, TCR180PEX, and PZF180PEX.
81  * Support DCF600USB, TCR600USB, MSF600USB, and WVB600USB.
82  * New macros _pcps_ddev_is_usb_v2() and _pcps_ddev_has_pcf().
83  * Optionally support timespec for sys time (USE_TIMESPEC).
84  * Support FreeBSD and NetBSD.
85  * Specify I/O range number when calling port I/O macros
86  * so they can be used for different ranges under BSD.
87  * Added macro _pcps_ddev_features().
88  * Revision 1.41 2010/06/30 13:44:49 martin
89  * Use new preprocessor symbol MBG_ARCH_X86.
90  * Revision 1.40 2010/01/12 14:05:05 daniel
91  * Added macro to check if reading the
92  * raw IRIG data bits is supported.
93  * Revision 1.39 2009/09/29 07:24:51Z martin
94  * Use standard feature flag to check if fast HR time is supported.
95  * Revision 1.38 2009/06/19 12:13:05 martin
96  * Added _pcps_ddev_has_irig_time() macro.
97  * Revision 1.37 2009/06/09 10:13:59 daniel
98  * Added macros _pcps_ddev_has_lan_intf( _p ) and
99  * _pcps_ddev_has_ptp_cfg( _p ).
100  * Cleaned up the low level interface and provided a
101  * possibility to override the macros for special purposes.
102  * Set USB cyclic timeout interval to 1200 ms as default.
103  * Revision 1.36 2009/03/16 16:01:24Z martin
104  * Support reading IRIG control function bits.
105  * Revision 1.35 2009/03/13 09:23:36 martin
106  * Added _pcps_ddev_has_time_scale( _p ) and _pcps_ddev_has_utc_parm( _p ).
107  * Moved _pcps_get_cycles() and _pcps_get_cycles_frequency() to pcpsdev.h
108  * and replaced/merged them with mbg_get_pc_cycles...() functions.
109  * Under Linux use own inline function to read TSC on x86 architectures.
110  * Normally USB timeouts are short with retries in order to increase
111  * responsiveness. On some systems this may lead to problems, so
112  * optionally one long timeout can be used now by define.
113  * Revision 1.34 2008/12/16 14:40:47 martin
114  * Account for new devices PTP270PEX, FRC270PEX, TCR170PEX, and WWVB51USB.
115  * Added macros _pcps_ddev_is_ptp(), _pcps_ddev_is_frc(),
116  * and _pcps_ddev_is_wwvb().
117  * Don't use pragma pack( 1 ) but use native alignment since structures
118  * defined here are not used across system boundaries.
119  * Added fields to PCPS_DDEV to store the ASIC version, and macros
120  * _pcps_ddev_raw_asic_version() and _pcps_ddev_asic_version().
121  * Moved PC cycles types and macros here, and defined dummy _pcps_get_cycles()
122  * for targets which don't support this.
123  * Use generic spinlock/mutex macros and common device access mutex.
124  * Support getting cycles frequency from device driver.
125  * Use MBG_MEM_ADDR type for memory rather than split high/low types.
126  * Renamed MBG_VIRT_ADDR to MBG_MEM_ADDR.
127  * Additional device port variables for IRQ handling.
128  * Use new MBG_ARCH_I386 symbol.
129  * Added DEBUG_LVL_... symbols.
130  * Use PCPS_IRQ_STAT_INFO type.
131  * Account for signed irq_num.
132  * New PCPS_DDEV field acc_cycles.
133  * Added variable usb_20_mode in PCPS_DDEV.
134  * Added connected flag to PCPS_DDEV structure.
135  * Added macro _pcps_ddev_has_fast_hr_timestamp().
136  * Use macros for unaligned access and endianess conversion.
137  * Support mapped I/O resources.
138  * Use some atomic_t types under Linux.
139  * Conditionally use Linux kthread API.
140  * Updated function prototypes.
141  * Revision 1.33 2008/02/27 10:25:30 martin
142  * Added support for TCR51USB and MSF51USB.
143  * Increased N_PCPS_MEM_RSRC to 2.
144  * Modified MBG_IOMEM_RSRC to support memory mapped I/O.
145  * Added PCI_ASIC_FEATURES to PCPS_DDEV.
146  * Added new macros and modified some older macros to support
147  * cyclic reading for USB within WIN32 targets.
148  * New macros _pcps_ddev_is_lwr() (long wave receiver),
149  * _pcps_ddev_is_msf(), _pcps_ddev_has_asic_version(),
150  * _pcps_ddev_has_asic_features().
151  * Moved Linux version-specific stuff to mbg_lx.h.
152  * Don't support MCA under DOS by default.
153  * Updated function prototypes.
154  * Revision 1.32 2008/01/31 09:06:03Z martin
155  * Don't support MCA under DOS by default.
156  * Revision 1.31 2007/09/26 09:28:03Z martin
157  * Added support for USB in general and new USB device USB5131.
158  * Renamed ..._USE_PCIMGR symbols to ..._USE_PCI_PNP.
159  * Renamed ..._USE_PCIBIOS symbols to ..._USE_PCI_BIOS.
160  * Added definition _PCPS_USE_PNP.
161  * Added new symbol _USE_ISA_PNP to exclude non-PNP stuff.
162  * from build if ISA devices are also handled by the PNP manager.
163  * Include mbgerror.h for new MBG_... codes.
164  * Added macro _pcps_ddev_status_busy().
165  * Added kernel malloc/free macros and USB I/O macros.
166  * Use PCPS_DDEV as private device data.
167  * Use ms values for USB timeouts also under Linux. This may not be
168  * appropriate for older kernels.
169  * Limited length of some older RCS log messages.
170  * Revision 1.30 2007/07/25 14:22:23Z martin
171  * Under Linux include param.h for definition of HZ under
172  * kernels 2.6.21 and newer.
173  * Revision 1.29 2007/07/17 08:22:48 martin
174  * Added support for TCR511PEX and GPS170PEX.
175  * Revision 1.28 2007/07/16 12:58:00Z martin
176  * Added support for PEX511.
177  * Added new structures used for unified resource handling.
178  * Account for renamed library symbols.
179  * Revision 1.27 2007/03/02 09:41:05Z martin
180  * Use generic port I/O macros.
181  * Added DEVICE_OBJECT to PCPS_DDEV under Windows.
182  * Define init code qualifier.
183  * Added new _pcps_..._timeout_clk() macros.
184  * Preliminary support for *BSD.
185  * Preliminary support for USB.
186  * Revision 1.26 2006/07/07 09:44:23 martin
187  * Fixed definition of control macros for the case where
188  * _PCPS_USE_PCI_PNP is overridden from the command line.
189  * Revision 1.25 2006/06/19 15:31:09 martin
190  * Added support for TCR511PCI.
191  * Updated function prototypes.
192  * Revision 1.24 2006/03/10 11:01:51 martin
193  * Added support for PCI511.
194  * Revision 1.23 2005/11/03 15:50:45Z martin
195  * Added support for GPS170PCI.
196  * Revision 1.22 2005/06/02 10:35:09Z martin
197  * Added macro _pcps_ddev_is_pci_amcc().
198  * Added macro _pcps_ddev_has_generic_io().
199  * Updated function prototypes.
200  * Revision 1.21 2004/12/09 11:03:38Z martin
201  * Support configuration of on-board frequency synthesizer.
202  * Revision 1.20 2004/11/09 13:05:12Z martin
203  * Fixed syntax bug in macro _pcps_ddev_fw_rev_num().
204  * New macro _pcps_ddev_has_gps_data().
205  * New macro _pcps_ddev_requires_irig_workaround().
206  * Revision 1.19 2004/10/14 15:01:24Z martin
207  * Added support for TCR167PCI.
208  * Revision 1.18 2004/09/06 15:11:04Z martin
209  * Support a GPS_DATA interface where sizes are specified
210  * by 16 instead of the original 8 bit quantities, thus allowing
211  * to transfer data blocks which exceed 255 bytes.
212  * Revision 1.17 2004/04/14 10:29:45Z martin
213  * Pack structures 1 byte aligned.
214  * Revision 1.16 2004/04/07 09:47:19Z martin
215  * New macros _pcps_ddev_has_irig() and
216  * _pcps_ddev_has_irig_tx().
217  * Revision 1.15 2004/03/10 17:32:23Z martin
218  * Use CLOCKS_PER_SEC for timeout under QNX6 (Neutrino).
219  * Revision 1.14 2003/11/17 16:15:01 martin
220  * Support clock tick timeout for QNX.
221  * Revision 1.13 2003/07/08 15:07:32Z martin
222  * Simplified definitions of default preprocessor macros.
223  * Compile for plug'n'play for Linux kernels 2.4.0 or newer.
224  * Updated function prototypes.
225  * Revision 1.12 2003/06/19 09:56:29 MARTIN
226  * Renamed macro ..clr_cap_buffer to ..clr_ucap_buffer.
227  * New macro _pcps_ddev_has_ucap().
228  * Changes due to renamed symbols.
229  * Updated function prototypes.
230  * Revision 1.11 2003/05/16 09:31:54 MARTIN
231  * Increased timeout loop count from 0x1000 to 0x7FFFFF.
232  * Rearranged inclusion of headers depending on the target.
233  * Added array for ISA port addresses.
234  * Revision 1.10 2003/04/09 16:30:24 martin
235  * Supports PCI510, GPS169PCI, and TCR510PCI,
236  * and new PCI_ASIC used by those devices.
237  * Renamed macro _pcps_ddev_is_irig() to _pcps_ddev_is_irig_rx().
238  * New macros _pcps_ddev_has_ref_offs(), _pcps_ddev_has_opt_flags().
239  * Preliminary support for PCPS_TZDL.
240  * Revision 1.9 2002/08/09 08:53:53 MARTIN
241  * New macro _pcps_ddev_can_clr_cap_buff().
242  * New macro _pcps_ddev_is_irig().
243  * New macro _pcps_ddev_has_signal().
244  * New macro _pcps_ddev_has_mod().
245  * Revision 1.8 2002/02/26 09:34:03 MARTIN
246  * Removed macro _pcps_read_sernum() which was replaced
247  * by a function pcps_read_sernum() which reads the S/N from
248  * any clock that supports a S/N.
249  * Updated function prototypes.
250  * Revision 1.7 2002/02/19 09:28:01 MARTIN
251  * Use new header mbg_tgt.h to check the target environment.
252  * Revision 1.6 2002/02/01 12:00:10 MARTIN
253  * Added new definitions for GPS168PCI.
254  * Renamed macro _pcps_ddev_rev_num to _pcps_ddev_fw_rev_num
255  * to follow naming conventions.
256  * Source code cleanup.
257  * Revision 1.5 2001/11/30 09:52:48 martin
258  * Added support for event_time which, however, requires
259  * a custom GPS firmware.
260  * Revision 1.4 2001/10/16 10:15:44 MARTIN
261  * New Macro _pcps_ddev_has_serial_hs() which determines
262  * whether DCF77 clock supports baud rate higher than default.
263  * Added some macros and comments corresponding to
264  * pcpsdev.h.
265  * Revision 1.3 2001/09/18 06:53:57 MARTIN
266  * Two sets of preprocessor symbols for Win9x/ME and WinNT/2k.
267  * New preprocessor symbol controls usage of clock ticks for timeout.
268  * Changed type of PCPS_RSRC.irq_num from int to ushort.
269  * Updated function prototypes.
270  * Revision 1.2 2001/03/16 14:45:34 MARTIN
271  * New functions and definitions to support PNP drivers.
272  * Revision 1.1 2001/03/01 16:29:22 MARTIN
273  * Initial version for the new library.
274  *
275  **************************************************************************/
276 
277 #ifndef _PCPSDRVR_H
278 #define _PCPSDRVR_H
279 
280 /* Other headers to be included */
281 #include <mbg_tgt.h>
282 #include <xdevfeat.h>
283 #include <pcpsiobf.h>
284 
285 #if !defined( USE_LOCAL_IO_BUFFER )
286  #define USE_LOCAL_IO_BUFFER 0
287 #endif
288 
289 #if defined( MBG_TGT_NETWARE )
290  #define _DEFAULT_PCPS_USE_CLOCK_TICK 1
291  #define _DEFAULT_PCPS_USE_ISA 1
292  #define _DEFAULT_PCPS_USE_MCA 0
293  #define _DEFAULT_PCPS_USE_PCI 1
294  #define _DEFAULT_PCPS_USE_ISA_PNP 0
295  #define _DEFAULT_PCPS_USE_PCI_PNP 0
296  #define _DEFAULT_PCPS_USE_USB 0
297  #define _DEFAULT_PCPS_USE_RSRCMGR 0
298 #elif defined( MBG_TGT_OS2 )
299  #define _DEFAULT_PCPS_USE_CLOCK_TICK 0
300  #define _DEFAULT_PCPS_USE_ISA 1
301  #define _DEFAULT_PCPS_USE_MCA 0
302  #define _DEFAULT_PCPS_USE_PCI 1
303  #define _DEFAULT_PCPS_USE_ISA_PNP 0
304  #define _DEFAULT_PCPS_USE_PCI_PNP 0
305  #define _DEFAULT_PCPS_USE_USB 0
306  #define _DEFAULT_PCPS_USE_RSRCMGR 1
307 #elif defined( MBG_TGT_WIN32_PNP )
308  #define _DEFAULT_PCPS_USE_CLOCK_TICK 1
309  #define _DEFAULT_PCPS_USE_ISA 1
310  #define _DEFAULT_PCPS_USE_MCA 0
311  #define _DEFAULT_PCPS_USE_PCI 1
312  #define _DEFAULT_PCPS_USE_ISA_PNP 1
313  #define _DEFAULT_PCPS_USE_PCI_PNP 1
314  #define _DEFAULT_PCPS_USE_USB 1
315  #define _DEFAULT_PCPS_USE_RSRCMGR 0
316 #elif defined( MBG_TGT_WIN32 )
317  #define _DEFAULT_PCPS_USE_CLOCK_TICK 1
318  #define _DEFAULT_PCPS_USE_ISA 1
319  #define _DEFAULT_PCPS_USE_MCA 0
320  #define _DEFAULT_PCPS_USE_PCI 1
321  #define _DEFAULT_PCPS_USE_ISA_PNP 0
322  #define _DEFAULT_PCPS_USE_PCI_PNP 0
323  #define _DEFAULT_PCPS_USE_USB 0
324  #define _DEFAULT_PCPS_USE_RSRCMGR 0
325 #elif defined( MBG_TGT_LINUX )
326  #include <mbg_lx.h>
327  #define _DEFAULT_PCPS_USE_CLOCK_TICK 1
328  #define _DEFAULT_PCPS_USE_ISA defined( MBG_ARCH_X86 )
329  #define _DEFAULT_PCPS_USE_MCA 0
330  #define _DEFAULT_PCPS_USE_PCI 1
331  #define _DEFAULT_PCPS_USE_ISA_PNP 0
332  #define _DEFAULT_PCPS_USE_PCI_PNP _DEFAULT_MBG_TGT_LINUX_USE_PCI_PNP
333  #define _DEFAULT_PCPS_USE_USB _DEFAULT_MBG_TGT_LINUX_USE_USB
334  #define _DEFAULT_PCPS_USE_RSRCMGR 1
335 #elif defined( MBG_TGT_BSD ) //##++
336  #define _DEFAULT_PCPS_USE_CLOCK_TICK 1
337  #define _DEFAULT_PCPS_USE_ISA 1
338  #define _DEFAULT_PCPS_USE_MCA 0
339  #define _DEFAULT_PCPS_USE_PCI 1
340  #define _DEFAULT_PCPS_USE_ISA_PNP 0
341  #define _DEFAULT_PCPS_USE_PCI_PNP 1
342  #define _DEFAULT_PCPS_USE_USB 0
343  #define _DEFAULT_PCPS_USE_RSRCMGR 1
344 #elif defined( MBG_TGT_QNX )
345  #define _DEFAULT_PCPS_USE_CLOCK_TICK 1
346  #define _DEFAULT_PCPS_USE_ISA 1
347  #define _DEFAULT_PCPS_USE_MCA 0
348  #define _DEFAULT_PCPS_USE_PCI 1
349  #define _DEFAULT_PCPS_USE_ISA_PNP 0
350  #define _DEFAULT_PCPS_USE_PCI_PNP 0
351  #define _DEFAULT_PCPS_USE_USB 0
352  #define _DEFAULT_PCPS_USE_RSRCMGR 0
353 #else // DOS ...
354  #define _DEFAULT_PCPS_USE_CLOCK_TICK 1
355  #define _DEFAULT_PCPS_USE_ISA 1
356  #define _DEFAULT_PCPS_USE_MCA 0
357  #define _DEFAULT_PCPS_USE_PCI 1
358  #define _DEFAULT_PCPS_USE_PCI_PNP 0
359  #define _DEFAULT_PCPS_USE_ISA_PNP 0
360  #define _DEFAULT_PCPS_USE_USB 0
361  #define _DEFAULT_PCPS_USE_RSRCMGR 0
362 #endif
363 
364 #ifndef _PCPS_USE_CLOCK_TICK
365  #define _PCPS_USE_CLOCK_TICK _DEFAULT_PCPS_USE_CLOCK_TICK
366 #endif
367 
368 #ifndef _PCPS_USE_ISA
369  #define _PCPS_USE_ISA _DEFAULT_PCPS_USE_ISA
370 #endif
371 
372 #ifndef _PCPS_USE_MCA
373  #define _PCPS_USE_MCA _DEFAULT_PCPS_USE_MCA
374 #endif
375 
376 #ifndef _PCPS_USE_PCI
377  #define _PCPS_USE_PCI _DEFAULT_PCPS_USE_PCI
378 #endif
379 
380 #ifndef _PCPS_USE_ISA_PNP
381  #define _PCPS_USE_ISA_PNP _DEFAULT_PCPS_USE_ISA_PNP
382 #endif
383 
384 #ifndef _PCPS_USE_PCI_PNP
385  #define _PCPS_USE_PCI_PNP _DEFAULT_PCPS_USE_PCI_PNP
386 #endif
387 
388 #ifndef _PCPS_USE_USB
389  #define _PCPS_USE_USB _DEFAULT_PCPS_USE_USB
390 #endif
391 
392 #ifndef _PCPS_USE_RSRCMGR
393  #define _PCPS_USE_RSRCMGR _DEFAULT_PCPS_USE_RSRCMGR
394 #endif
395 
396 
397 #ifndef _PCPS_USE_PCI_BIOS
398  #define _PCPS_USE_PCI_BIOS ( _PCPS_USE_PCI && !_PCPS_USE_PCI_PNP )
399 #endif
400 
401 #define _PCPS_USE_PNP ( _PCPS_USE_PCI_PNP || _PCPS_USE_ISA_PNP || _PCPS_USE_USB )
402 
403 #if _PCPS_USE_PCI_PNP && _PCPS_USE_PCI_BIOS
404  #error "PCI PNP and non-PNP can't be used at the same time"
405 #endif
406 
407 
408 #if !defined( _MBG_INIT_CODE_ATTR )
409  // define to empty string by default
410  #define _MBG_INIT_CODE_ATTR
411 #endif
412 
413 #if !defined( DEBUG_DRVR )
414  #define DEBUG_DRVR 0
415 #endif
416 
417 #if !defined( DEBUG_DEV_INIT )
418  #define DEBUG_DEV_INIT 0
419 #endif
420 
421 #if !defined( DEBUG_USB_IO )
422  #define DEBUG_USB_IO 0
423 #endif
424 
425 #if !defined( DEBUG_IOCTL )
426  #define DEBUG_IOCTL 0
427 #endif
428 
429 
430 #include <pcpsdev.h>
431 #include <cfg_hlp.h>
432 #include <mbgmutex.h>
433 #include <pci_asic.h>
434 #include <mbgerror.h>
435 #include <use_pack.h>
436 #include <mbggenio.h>
437 #include <mbgddmsg.h>
438 
439 #if defined( MBG_TGT_FREEBSD )
440  #include <sys/malloc.h>
441  #include <sys/_null.h>
442  #include <sys/param.h>
443  #include <sys/lock.h>
444  #include <machine/bus.h>
445 #elif defined( MBG_TGT_NETBSD )
446  #include <sys/kmem.h>
447 #else
448  #include <stddef.h>
449 #endif
450 
451 #if defined( MBG_TGT_DOS )
452  #include <string.h>
453  #include <time.h>
454 #endif
455 
456 #if defined( MBG_TGT_WIN32 )
457  #include <mbg_w32.h>
458  #include <mbgnames.h>
459 #endif
460 
461 #if defined( MBG_TGT_LINUX )
462  #include <linux/slab.h> // for kmalloc()/kfree()
463  #include <linux/mm.h> // for is_vmalloc_addr()
464 
465  #if _PCPS_USE_USB
466  #include <linux/usb.h>
467  #endif
468 #endif
469 
470 #if defined( MBG_TGT_QNX )
471  #include <mbg_qnx.h>
472  #include <string.h>
473  #include <time.h>
474 #endif
475 
476 #if defined( MBG_TGT_NETWARE )
477  #include <string.h>
478  #include <time.h>
479  #include <conio.h>
480 #endif
481 
482 #if defined( MBG_TGT_OS2 )
483  #ifndef OS2_INCLUDED
484  #define INCL_DOSSEMAPHORES
485  #include <os2.h>
486  #include <rmbase.h>
487  #endif
488 
489  #include <string.h>
490  #include <time.h>
491  #include <conio.h>
492  #include <xportio.h>
493 #endif
494 
495 #if _PCPS_USE_RSRCMGR
496  #include <rsrc.h>
497 #endif
498 
499 
500 // If DEBUG is defined to build a debug version of this driver for
501 // older NetBSD versions then this collides with DEBUG being defined
502 // for the kernel itself, or not. As a workaround we define MBG_DEBUG
503 // instead when calling 'make', and we redefine DEBUG locally
504 // if MBG_DEBUG is defined.
505 #if defined( MBG_TGT_NETBSD ) && defined( MBG_DEBUG )
506  #undef DEBUG
507  #define DEBUG MBG_DEBUG
508 #endif
509 
510 
511 
512 #ifdef _PCPSDRVR
513  #define _ext
514  #define _DO_INIT
515 #else
516  #define _ext extern
517 #endif
518 
519 
520 /* Start of header body */
521 
522 // We use native alignment for structures which are not accessed across system boundaries.
523 
524 #ifdef __cplusplus
525 extern "C" {
526 #endif
527 
528 #if !defined( MBG_DRVR_NAME )
529  #if defined( MBG_TGT_WIN32 )
530  #define MBG_DRVR_NAME MBG_SVC_NAME_MBGCLOCK
531  #else
532  #define MBG_DRVR_NAME "mbgclock"
533  #endif
534 #endif
535 
536 _ext const char driver_name[]
537 #ifdef _DO_INIT
538  = MBG_DRVR_NAME
539 #endif
540 ;
541 
542 
543 #define _DEFAULT_PCPS_USE_MM_IO ( MBG_TGT_SUPP_MEM_ACC && !MBG_USE_MM_IO_FOR_PCI )
544 
545 #if !defined( _PCPS_USE_MM_IO )
546  #define _PCPS_USE_MM_IO _DEFAULT_PCPS_USE_MM_IO
547 #endif
548 
549 
550 // Define some OS-specific primitives to alloc / free memory and handle
551 // mutexes and spinlocks in kernel space.
552 
553 #if defined( MBG_TGT_LINUX )
554 
555  #define _pcps_kmalloc( _sz ) kmalloc( _sz, GFP_ATOMIC )
556  #define _pcps_kfree( _p, _sz ) kfree( _p )
557 
558 
559  // These special versions of _pcps_sem_inc() and _pcps_sem_dec()
560  // are only required to prevent interference with the IRQ handler
561  // under Linux which implements the serial port emulation for the
562  // NTP parse driver.
563  #define _pcps_sem_inc( _pddev ) \
564  { \
565  ulong flags; \
566  \
567  if ( _mbg_mutex_acquire( &(_pddev)->dev_mutex ) < 0 ) \
568  return -ERESTARTSYS; \
569  \
570  spin_lock_irqsave( &(_pddev)->irq_lock, flags ); \
571  atomic_inc( &(_pddev)->access_in_progress ); \
572  spin_unlock_irqrestore( &(_pddev)->irq_lock, flags ); \
573  }
574 
575  #define _pcps_sem_dec( _pddev ) \
576  atomic_dec( &(_pddev)->access_in_progress ); \
577  _mbg_mutex_release( &(_pddev)->dev_mutex )
578 
579 #elif defined( MBG_TGT_FREEBSD )
580 
581  // malloc/free in kernel mode require usage of the
582  // MALLOC_DECLARE() / MALLOC_DEFINE() macros.
583  // See "man 9 malloc" for details.
584 
585  MALLOC_DECLARE( M_MBGCLOCK );
586  #define _pcps_kmalloc( _sz ) malloc( _sz, M_MBGCLOCK, M_NOWAIT | M_ZERO )
587  #define _pcps_kfree( _p, _sv ) free( _p, M_MBGCLOCK )
588 
589 #elif defined( MBG_TGT_NETBSD )
590 
591  // For older NetBSD versions which do not suppport the calls
592  // used below, see 'man 9 malloc'.
593  #define _pcps_kmalloc( _sz ) kmem_alloc( _sz, KM_NOSLEEP )
594  #define _pcps_kfree( _p, _sz ) kmem_free( _p, _sz )
595 
596 #elif defined( MBG_TGT_WIN32 )
597 
598  #define _pcps_kmalloc( _sz ) ExAllocatePool( NonPagedPool, _sz )
599  #define _pcps_kfree( _p, _sz ) ExFreePool( _p )
600 
601 #elif defined( MBG_TGT_DOS )
602 
603  // No multitasking, no device driver,
604  // so we don't need this.
605 
606  #define _pcps_sem_inc( _pddev ) \
607  _nop_macro_fnc()
608 
609  #define _pcps_sem_dec( _pddev ) \
610  _nop_macro_fnc()
611 
612 #endif
613 
614 
615 #if !defined( _PCPS_STATIC_DEV_LIST )
616  // On PNP systems buffers for device specific data are by default malloc'ed
617  // whenever a device appears. However, a static array of a given maximum number
618  // of devices is used on non-PNP systems.
619  // This can be overridden for testing to avoid calling malloc in kernel space.
620  #define _PCPS_STATIC_DEV_LIST ( !_PCPS_USE_PNP )
621 #endif
622 
623 
624 
625 // If these macros have not yet been defined then define some dummies:
626 
627 #if !defined( _pcps_sem_inc ) || !defined( _pcps_sem_dec )
628 
629  #define _pcps_sem_inc( _pddev ) \
630  _mbg_mutex_acquire( &(_pddev)->dev_mutex )
631 
632  #define _pcps_sem_dec( _pddev ) \
633  _mbg_mutex_release( &(_pddev)->dev_mutex )
634 
635 #endif
636 
637 
638 
639 // Default timeout count when accessing a device
640 
641 #if !defined( PCPS_TIMEOUT_CNT )
642  #if _PCPS_USE_CLOCK_TICK
643  #if defined( MBG_TGT_NETWARE )
644  #define PCPS_TIMEOUT_CNT ( (ulong)( 200 * __get_CLK_TCK() ) / 1000 )
645  #elif defined( MBG_TGT_LINUX )
646  #define PCPS_TIMEOUT_CNT ( (ulong)( 200 * HZ ) / 1000 )
647  #elif defined( MBG_TGT_BSD )
648  #define PCPS_TIMEOUT_CNT ( (ulong)( 200 ) ) // [ms]
649  #elif defined( MBG_TGT_WIN32 )
650  #define PCPS_TIMEOUT_CNT ( (ulong)( 200 * MBG_TICKS_PER_SEC ) / 1000 )
651  #elif defined( MBG_TGT_QNX_NTO )
652  #define PCPS_TIMEOUT_CNT ( (ulong)( 200 * CLOCKS_PER_SEC ) / 1000 )
653  #else
654  #define PCPS_TIMEOUT_CNT ( (ulong)( 200 * CLK_TCK ) / 1000 )
655  #endif
656  #else
657  #define PCPS_TIMEOUT_CNT 0x7FFFFFUL
658  #endif
659 #endif
660 
661 
662 
666 #define N_PCPS_MEM_RSRC 2
667 
668 
672 #define MAX_PCPS_RSRC ( N_PCPS_MEM_RSRC + N_PCPS_PORT_RSRC )
673 
674 
678 typedef struct
679 {
686 
688 
689 
690 
691 #if _PCPS_USE_USB
692 
696 typedef struct
697 {
698  uint8_t addr;
699  uint8_t attrib;
700  uint16_t max_packet_size;
701 
702 } PCPS_USB_EP;
703 
704 
705 
706 static __mbg_inline
707 bool is_ep_rcv( uint8_t ep )
708 {
709  return ( ep & 0x80 ) != 0;
710 
711 } // is_ep_rcv
712 
713 
714 
715 #if defined( MBG_TGT_LINUX )
716 
717  // definitions used to control the cyclic USB read thread
718 
719  #if _PCPS_USE_LINUX_KTHREAD
720 
721  // Used by kthread_run() / kthread_stop()
722  typedef struct task_struct *PCPS_THREAD_INFO;
723 
724  #else
725 
726  // Used by kernel_thread() / daemonize() / kill_proc()
727  typedef struct
728  {
729  pid_t pid;
730  char name[17]; // 16 chars as supported by the kernel, plus trailing 0
731  struct completion exit;
732 
733  } PCPS_THREAD_INFO;
734 
735  #endif // _PCPS_USE_LINUX_KTHREAD
736 
737 #endif // defined( MBG_TGT_LINUX )
738 
739 #endif // _PCPS_USE_USB
740 
741 
742 
746 typedef union
747 {
748  struct pex8311
749  {
752  } pex8311;
753 
754  struct mbgpex
755  {
757  uint8_t b[256 - sizeof( PCI_ASIC ) ];
760  } mbgpex;
761 
763 
764 
765 
766 struct PCPS_DDEV_s;
767 typedef struct PCPS_DDEV_s PCPS_DDEV;
768 
769 typedef int PCPS_READ_FNC( PCPS_DDEV *pddev, uint8_t cmd, void FAR *buffer, uint16_t count );
770 typedef int PCPS_WRITE_FNC( PCPS_DDEV *pddev, uint8_t cmd, const void FAR *buffer, uint16_t count );
771 typedef int PCPS_DDEV_INIT_FNC( PCPS_DDEV **ppddev );
772 typedef void PCPS_DDEV_CLEANUP_FNC( PCPS_DDEV *pddev );
773 typedef int PCPS_DDEV_REGISTER_FNC( PCPS_DDEV *pddev );
774 
775 
776 
778 {
780 
789  uint32_t irq_enb_mask;
790  uint32_t irq_disb_mask;
791  uint32_t irq_flag_mask;
792  uint32_t irq_ack_mask;
793 
798 
800 
801  #if defined( _MBG_MUTEX_DEFINED )
803  #endif
804 
808 
812 
813  #if defined( _MBG_SPINLOCK_DEFINED )
814  MBG_SPINLOCK tstamp_lock;
815  MBG_SPINLOCK irq_lock;
816  #endif
817 
821 
824 
825  #if _PCPS_USE_USB
826  int n_usb_ep;
827  PCPS_USB_EP ep[MBGUSB_MAX_ENDPOINTS];
828  bool usb_20_mode;
829  #endif
830 
835  union
836  {
839 
842  struct
843  {
844  uint8_t cmd;
846  } gps_cmd_info;
847 
848  } cmd_info;
849 
853 
854  #if !USE_LOCAL_IO_BUFFER
856  #endif
857 
858  #if defined( MBG_TGT_WIN32 )
859  _pcps_ddev_data_win
860  #endif
861 
862  #if defined( MBG_TGT_LINUX )
863  atomic_t connected;
865  atomic_t data_avail;
866  unsigned long jiffies_at_irq;
867  struct fasync_struct *fasyncptr;
869 
870  #if NEW_WAIT_QUEUE
871  wait_queue_head_t wait_queue;
872  #else
873  struct wait_queue *wait_queue;
874  #endif
875 
876  atomic_t open_count;
877 
878  struct cdev cdev;
879  dev_t lx_dev;
880 
881  #if _PCPS_USE_USB
882  struct usb_device *udev;
883  struct usb_interface *intf;
884  PCPS_THREAD_INFO usb_read_thread;
885  struct semaphore sem_usb_cyclic;
886  PCPS_TIME t_cyc;
887  #endif
888  #endif
889 
890  #if defined( MBG_TGT_BSD )
891  int connected;
892  int open_count;
893  #endif
894 
895  #if _PCPS_USE_RSRCMGR
896  #if defined( MBG_TGT_OS2 )
897  PCPS_HDEV hDev;
898  RSRC_LIST rsrc;
899  #endif
900  #endif
901 };
902 
903 
904 
912 {
919 };
920 
921 
922 
929 #define PCPS_ACCESS_MODE_STRS \
930 { \
931  "No real port I/O (dummy fnc)", \
932  "I/O via USB", \
933  "Standard port I/O", \
934  "Memory mapped I/O", \
935  "16 bit memory mapped I/O" \
936 }
937 
943 #define PCPS_ACCESS_MODE_STR_FRCD " (forced)"
944 
945 
946 
950 #define PCPS_DECODE_WIDTH_PCI 16
951 
952 
953 /* ------ definitions used with MCA clocks -------------------------- */
954 
955 /*
956  * The MCA adapter ID number is used to detect a MCA clock in a
957  * system and query which resources have been assigned by the
958  * system's POS (programmable option select).
959  */
960 
961 #define MCA_ID_PS31 0x6AAC
962 #define MCA_ID_PS31_OLD 0x6303
963 
964 
967 #define PCPS_NUM_PORTS_MCA 16
968 
972 #define PCPS_DECODE_WIDTH_MCA 16
973 
974 
975 /* ------ definitions used with ISA clocks -------------------------- */
976 
985 #define ISA_ID_PCPS MCA_ID_PS31
986 
987 
994 #define PCPS_DEFAULT_PORT 0x0300
995 
996 
1000 #define PCPS_NUM_PORTS_ISA 4
1001 
1002 
1006 #define PCPS_DECODE_WIDTH_ISA 10
1007 
1008 
1009 /* ------ common definitions -------------------------- */
1010 
1011 #if defined( DEBUG )
1012  _ext int debug
1013  #ifdef _DO_INIT
1014  = DEBUG
1015  #endif
1016  ;
1017 #endif
1018 
1019 
1021 #ifdef _DO_INIT
1022 = { // attention, the name is limited to PCPS_CLOCK_NAME_SZ, including terminating 0
1023  { PCPS_TYPE_PC31, "PC31", 0, PCPS_REF_DCF, PCPS_BUS_ISA },
1025  { PCPS_TYPE_PS31, "PS31", MCA_ID_PS31, PCPS_REF_DCF, PCPS_BUS_MCA },
1026  { PCPS_TYPE_PC32, "PC32", ISA_ID_PCPS, PCPS_REF_DCF, PCPS_BUS_ISA },
1028  { PCPS_TYPE_GPS167PC, "GPS167PC", 0, PCPS_REF_GPS, PCPS_BUS_ISA },
1029  { PCPS_TYPE_GPS167PCI, "GPS167PCI", PCI_DEV_GPS167PCI, PCPS_REF_GPS, PCPS_BUS_PCI_S5933 },
1031  { PCPS_TYPE_GPS168PCI, "GPS168PCI", PCI_DEV_GPS168PCI, PCPS_REF_GPS, PCPS_BUS_PCI_S5920 },
1033  { PCPS_TYPE_GPS169PCI, "GPS169PCI", PCI_DEV_GPS169PCI, PCPS_REF_GPS, PCPS_BUS_PCI_ASIC },
1034  { PCPS_TYPE_TCR510PCI, "TCR510PCI", PCI_DEV_TCR510PCI, PCPS_REF_IRIG, PCPS_BUS_PCI_ASIC },
1035  { PCPS_TYPE_TCR167PCI, "TCR167PCI", PCI_DEV_TCR167PCI, PCPS_REF_IRIG, PCPS_BUS_PCI_ASIC },
1036  { PCPS_TYPE_GPS170PCI, "GPS170PCI", PCI_DEV_GPS170PCI, PCPS_REF_GPS, PCPS_BUS_PCI_ASIC },
1037  { PCPS_TYPE_PCI511, "PCI511", PCI_DEV_PCI511, PCPS_REF_DCF, PCPS_BUS_PCI_ASIC },
1038  { PCPS_TYPE_TCR511PCI, "TCR511PCI", PCI_DEV_TCR511PCI, PCPS_REF_IRIG, PCPS_BUS_PCI_ASIC },
1040  { PCPS_TYPE_TCR511PEX, "TCR511PEX", PCI_DEV_TCR511PEX, PCPS_REF_IRIG, PCPS_BUS_PCI_PEX8311 },
1041  { PCPS_TYPE_GPS170PEX, "GPS170PEX", PCI_DEV_GPS170PEX, PCPS_REF_GPS, PCPS_BUS_PCI_PEX8311 },
1043  { PCPS_TYPE_TCR51USB, "TCR51USB", USB_DEV_TCR51USB, PCPS_REF_IRIG, PCPS_BUS_USB },
1044  { PCPS_TYPE_MSF51USB, "MSF51USB", USB_DEV_MSF51USB, PCPS_REF_MSF, PCPS_BUS_USB },
1045  { PCPS_TYPE_PTP270PEX, "PTP270PEX", PCI_DEV_PTP270PEX, PCPS_REF_PTP, PCPS_BUS_PCI_PEX8311 },
1046  { PCPS_TYPE_FRC511PEX, "FRC511PEX", PCI_DEV_FRC511PEX, PCPS_REF_FRC, PCPS_BUS_PCI_PEX8311 },
1047  { PCPS_TYPE_TCR170PEX, "TCR170PEX", PCI_DEV_TCR170PEX, PCPS_REF_IRIG, PCPS_BUS_PCI_PEX8311 },
1048  { PCPS_TYPE_WWVB51USB, "WWVB51USB", USB_DEV_WWVB51USB, PCPS_REF_WWVB, PCPS_BUS_USB },
1050  { PCPS_TYPE_TCR180PEX, "TCR180PEX", PCI_DEV_TCR180PEX, PCPS_REF_IRIG, PCPS_BUS_PCI_MBGPEX },
1052  { PCPS_TYPE_PZF180PEX, "PZF180PEX", PCI_DEV_PZF180PEX, PCPS_REF_DCF, PCPS_BUS_PCI_MBGPEX },
1053  { PCPS_TYPE_TCR600USB, "TCR600USB", USB_DEV_TCR600USB, PCPS_REF_IRIG, PCPS_BUS_USB_V2 },
1054  { PCPS_TYPE_MSF600USB, "MSF600USB", USB_DEV_MSF600USB, PCPS_REF_MSF, PCPS_BUS_USB_V2 },
1055  { PCPS_TYPE_WVB600USB, "WVB600USB", USB_DEV_WVB600USB, PCPS_REF_WWVB, PCPS_BUS_USB_V2 },
1056  { PCPS_TYPE_GLN180PEX, "GLN180PEX", PCI_DEV_GLN180PEX, PCPS_REF_GPS, PCPS_BUS_PCI_MBGPEX },
1057  { PCPS_TYPE_GPS180AMC, "GPS180AMC", PCI_DEV_GPS180AMC, PCPS_REF_GPS, PCPS_BUS_PCI_MBGPEX },
1058  { PCPS_TYPE_GNS181PEX, "GNS181PEX", PCI_DEV_GNS181PEX, PCPS_REF_GPS, PCPS_BUS_PCI_MBGPEX },
1059  { PCPS_TYPE_TCR180USB, "TCR180USB", USB_DEV_TCR180USB, PCPS_REF_IRIG, PCPS_BUS_USB_V2 }
1060 
1061  // NOTE If a new device is added here, don't forget to add it also
1062  // to the Windows .inf file of supported PCI and USB devices,
1063  // and in case of USB to the table mbgclock_usb_tbl of the Linux
1064  // driver file mbgclock_main.c.
1065 }
1066 #endif
1067 ;
1068 
1069 
1070 #if !defined( PCPS_MAX_ISA_CARDS )
1071  #define PCPS_MAX_ISA_CARDS N_SUPP_DEV_BUS // the number of ISA cards supported
1072 #endif
1073 
1075 
1076 #if _PCPS_STATIC_DEV_LIST
1078  _ext int n_ddevs;
1079 #endif
1080 
1081 #if defined( MBG_TGT_DOS ) || defined( MBG_TGT_NETWARE ) //##++
1082  _ext int curr_ddev_num;
1083  _ext PCPS_DDEV *curr_ddev
1084  #ifdef _DO_INIT
1085  = &pcps_ddev[0]
1086  #endif
1087  ;
1088 #endif
1089 
1090 
1094 _ext const char *fw_id_ref[]
1095 #ifdef _DO_INIT
1096  = {
1097  "PC3", // PC31, PS31, PC32
1098  "PCI", // PCI32, PCI509, PCI510, PCI511
1099  "GPS", // GPS167PC, GPS167PCI, GPS168PCI, GPS169PCI, GPS170PCI, GPS170PEX, GPS180PEX, GPS180AMC
1100  "TCR", // TCR510PCI, TCR167PCI, TCR511PCI, TCR511PEX, TCR51USB, TCR170PEX, TCR180PEX
1101  "PEX", // PEX511
1102  "USB", // USB5131
1103  "MSF", // MSF51USB, MSF600USB
1104  "WWVB", // WWVB51USB, WVB600USB
1105  "DCF", // DCF600USB
1106  "PZF", // PZF180PEX
1107  "GLN", // GLN180PEX
1108  "GNS", // GNS181PEX
1109  NULL
1110  }
1111 #endif
1112 ;
1113 
1114 
1115 // These macros are used to distinguish ISA cards:
1116 #define fw_id_ref_pcps fw_id_ref[0]
1117 #define fw_id_ref_gps fw_id_ref[2]
1118 
1119 
1120 #if _PCPS_USE_MM_IO
1121  _ext int force_io_access;
1122  _ext int force_mm16_access;
1123 #endif
1124 
1125 
1126 // These macros accept a (PCPS_DDEV *) for easy access
1127 // to the information stored in PCPS_DDEV structures.
1128 
1129 // Access device type information:
1130 #define _pcps_ddev_type_num( _p ) _pcps_type_num( &(_p)->dev )
1131 #define _pcps_ddev_type_name( _p ) _pcps_type_name( &(_p)->dev )
1132 #define _pcps_ddev_dev_id( _p ) _pcps_dev_id( &(_p)->dev )
1133 #define _pcps_ddev_ref_type( _p ) _pcps_ref_type( &(_p)->dev )
1134 #define _pcps_ddev_bus_flags( _p ) _pcps_bus_flags( &(_p)->dev )
1135 
1136 // Query device type features:
1137 
1138 #define _pcps_ddev_is_gps( _p ) _pcps_is_gps( &(_p)->dev )
1139 #define _pcps_ddev_is_dcf( _p ) _pcps_is_dcf( &(_p)->dev )
1140 #define _pcps_ddev_is_msf( _p ) _pcps_is_msf( &(_p)->dev )
1141 #define _pcps_ddev_is_wwvb( _p ) _pcps_is_wwvb( &(_p)->dev )
1142 #define _pcps_ddev_is_irig_rx( _p ) _pcps_is_irig_rx( &(_p)->dev )
1143 #define _pcps_ddev_is_ptp( _p ) _pcps_is_ptp( &(_p)->dev )
1144 #define _pcps_ddev_is_frc( _p ) _pcps_is_frc( &(_p)->dev )
1145 
1146 #define _pcps_ddev_is_lwr( _p ) _pcps_is_lwr( &(_p)->dev )
1147 #define _pcps_ddev_is_gnss( _p ) _pcps_is_gnss( &(_p)->dev )
1148 
1149 
1150 // Generic bus types:
1151 #define _pcps_ddev_is_isa( _p ) _pcps_is_isa( &(_p)->dev )
1152 #define _pcps_ddev_is_mca( _p ) _pcps_is_mca( &(_p)->dev )
1153 #define _pcps_ddev_is_pci( _p ) _pcps_is_pci( &(_p)->dev )
1154 #define _pcps_ddev_is_usb( _p ) _pcps_is_usb( &(_p)->dev )
1155 
1156 // Special bus types:
1157 #define _pcps_ddev_is_usb_v2( _p ) _pcps_is_usb_v2( &(_p)->dev )
1158 #define _pcps_ddev_is_pci_s5933( _p ) _pcps_is_pci_s5933( &(_p)->dev )
1159 #define _pcps_ddev_is_pci_s5920( _p ) _pcps_is_pci_s5920( &(_p)->dev )
1160 #define _pcps_ddev_is_pci_amcc( _p ) _pcps_is_pci_amcc( &(_p)->dev )
1161 #define _pcps_ddev_is_pci_asic( _p ) _pcps_is_pci_asic( &(_p)->dev )
1162 #define _pcps_ddev_is_pci_pex8311( _p ) _pcps_is_pci_pex8311( &(_p)->dev )
1163 #define _pcps_ddev_is_pci_mbgpex( _p ) _pcps_is_pci_mbgpex( &(_p)->dev )
1164 
1165 
1166 // Access device configuration information:
1167 #define _pcps_ddev_bus_num( _p ) _pcps_bus_num( &(_p)->dev )
1168 #define _pcps_ddev_slot_num( _p ) _pcps_slot_num( &(_p)->dev )
1169 #define _pcps_ddev_pci_slot_num( _p ) ( _pcps_ddev_slot_num( _p ) >> 3 )
1170 #define _pcps_ddev_pci_fnc_num( _p ) ( _pcps_ddev_slot_num( _p ) & 0x07 )
1171 
1172 #define _pcps_ddev_short_port_rsrc( _p, _n ) _pcps_short_port_rsrc( &(_p)->dev, _n )
1173 #define _pcps_ddev_short_port_base( _p, _n ) _pcps_short_port_base( &(_p)->dev, _n )
1174 
1175 #define _pcps_ddev_io_rsrc( _p, _n ) ( (_p)->rsrc_info.port[_n] )
1176 #define _pcps_ddev_io_base_raw( _p, _n ) ( _pcps_ddev_io_rsrc( _p, _n ).base_raw )
1177 #define _pcps_ddev_io_base_mapped( _p, _n ) ( _pcps_ddev_io_rsrc( _p, _n ).base_mapped )
1178 #define _pcps_ddev_irq_num( _p ) _pcps_irq_num( &(_p)->dev )
1179 #define _pcps_ddev_timeout_clk( _p ) _pcps_timeout_clk( &(_p)->dev )
1180 
1181 #define _pcps_ddev_mem_rsrc( _p, _n ) ( (_p)->rsrc_info.mem[_n] )
1182 
1183 #define _pcps_ddev_fw_rev_num( _p ) _pcps_fw_rev_num( &(_p)->dev )
1184 #define _pcps_ddev_features( _p ) _pcps_features( &(_p)->dev )
1185 #define _pcps_ddev_fw_id( _p ) _pcps_fw_id( &(_p)->dev )
1186 #define _pcps_ddev_sernum( _p ) _pcps_sernum( &(_p)->dev )
1187 #define _pcps_ddev_sernum_size( _p ) sizeof( (_p)->dev.cfg.sernum )
1188 
1189 #define _pcps_ddev_raw_asic_version( _p ) ( (_p)->raw_asic_version )
1190 #define _pcps_ddev_asic_version( _p ) ( (_p)->asic_version )
1191 
1192 // These macros handle the device's err_flags:
1193 #define _pcps_ddev_err_flags( _p ) \
1194  _pcps_err_flags( &(_p)->dev )
1195 
1196 #define _pcps_ddev_chk_err_flags( _p, _msk ) \
1197  _pcps_chk_err_flags( &(_p)->dev, _msk )
1198 
1199 #define _pcps_ddev_set_err_flags( _p, _msk ) \
1200  _pcps_set_err_flags( &(_p)->dev, _msk )
1201 
1202 #define _pcps_ddev_clr_err_flags( _p, _msk ) \
1203  _pcps_clr_err_flags( &(_p)->dev, _msk )
1204 
1205 
1206 
1207 // These macros test whether access is done via MM
1208 // or via legacy port I/O:
1209 
1210 #define _pcps_ddev_access_mode_io( _p ) \
1211  ( (_p)->access_mode == PCPS_ACC_MODE_IO )
1212 
1213 #define _pcps_ddev_access_mode_mm( _p ) \
1214  ( ( (_p)->access_mode == PCPS_ACC_MODE_MM ) || \
1215  ( (_p)->access_mode == PCPS_ACC_MODE_MM16 ) )
1216 
1217 
1218 
1219 // Query whether a specific feature is supported:
1220 #define _pcps_ddev_can_set_time( _p ) _pcps_can_set_time( &(_p)->dev )
1221 #define _pcps_ddev_has_serial( _p ) _pcps_has_serial( &(_p)->dev )
1222 #define _pcps_ddev_has_sync_time( _p ) _pcps_has_sync_time( &(_p)->dev )
1223 #define _pcps_ddev_has_ident( _p ) _pcps_has_ident( &(_p)->dev )
1224 #define _pcps_ddev_has_utc_offs( _p ) _pcps_has_utc_offs( &(_p)->dev )
1225 #define _pcps_ddev_has_hr_time( _p ) _pcps_has_hr_time( &(_p)->dev )
1226 #define _pcps_ddev_has_sernum( _p ) _pcps_has_sernum( &(_p)->dev )
1227 #define _pcps_ddev_has_cab_len( _p ) _pcps_has_cab_len( &(_p)->dev )
1228 #define _pcps_ddev_has_tzdl( _p ) _pcps_has_tzdl( &(_p)->dev )
1229 #define _pcps_ddev_has_pcps_tzdl( _p ) _pcps_has_pcps_tzdl( &(_p)->dev )
1230 #define _pcps_ddev_has_tzcode( _p ) _pcps_has_tzcode( &(_p)->dev )
1231 #define _pcps_ddev_has_tz( _p ) _pcps_has_tz( &(_p)->dev )
1232 // The next one is supported only with a certain GPS firmware version:
1233 #define _pcps_ddev_has_event_time( _p ) _pcps_has_event_time( &(_p)->dev )
1234 #define _pcps_ddev_has_receiver_info( _p ) _pcps_has_receiver_info( &(_p)->dev )
1235 #define _pcps_ddev_can_clr_ucap_buff( _p ) _pcps_can_clr_ucap_buff( &(_p)->dev )
1236 #define _pcps_ddev_has_ucap( _p ) _pcps_has_ucap( &(_p)->dev )
1237 #define _pcps_ddev_has_irig_tx( _p ) _pcps_has_irig_tx( &(_p)->dev )
1238 
1239 // This macro determines whether a DCF77 clock
1240 // supports a higher baud rate than standard
1241 #define _pcps_ddev_has_serial_hs( _p ) \
1242  _pcps_has_serial_hs( &(_p)->dev )
1243 
1244 
1245 #define _pcps_ddev_has_signal( _p ) \
1246  _pcps_has_signal( &(_p)->dev )
1247 
1248 #define _pcps_ddev_has_mod( _p ) \
1249  _pcps_has_mod( &(_p)->dev )
1250 
1251 #define _pcps_ddev_has_irig( _p ) \
1252  _pcps_has_irig( &(_p)->dev )
1253 
1254 #define _pcps_ddev_has_irig_ctrl_bits( _p ) \
1255  _pcps_has_irig_ctrl_bits( &(_p)->dev )
1256 
1257 #define _pcps_ddev_has_irig_time( _p ) \
1258  _pcps_has_irig_time( &(_p)->dev )
1259 
1260 #define _pcps_ddev_has_raw_irig_data( _p ) \
1261  _pcps_has_raw_irig_data( &(_p)->dev )
1262 
1263 #define _pcps_ddev_has_ref_offs( _p ) \
1264  _pcps_has_ref_offs( &(_p)->dev )
1265 
1266 #define _pcps_ddev_has_opt_flags( _p ) \
1267  _pcps_has_opt_flags( &(_p)->dev )
1268 
1269 #define _pcps_ddev_has_gps_data_16( _p ) \
1270  _pcps_has_gps_data_16( &(_p)->dev )
1271 
1272 #define _pcps_ddev_has_gps_data( _p ) \
1273  _pcps_has_gps_data( &(_p)->dev )
1274 
1275 #define _pcps_ddev_has_synth( _p ) \
1276  _pcps_has_synth( &(_p)->dev )
1277 
1278 #define _pcps_ddev_has_generic_io( _p ) \
1279  _pcps_has_generic_io( &(_p)->dev )
1280 
1281 #define _pcps_ddev_has_time_scale( _p ) \
1282  _pcps_has_time_scale( &(_p)->dev )
1283 
1284 #define _pcps_ddev_has_utc_parm( _p ) \
1285  _pcps_has_utc_parm( &(_p)->dev )
1286 
1287 #define _pcps_ddev_has_asic_version( _p ) \
1288  _pcps_has_asic_version( &(_p)->dev )
1289 
1290 #define _pcps_ddev_has_asic_features( _p ) \
1291  _pcps_has_asic_features( &(_p)->dev )
1292 
1293 #define _pcps_ddev_has_fast_hr_timestamp( _p ) \
1294  _pcps_has_fast_hr_timestamp( &(_p)->dev )
1295 
1296 #define _pcps_ddev_has_lan_intf( _p ) \
1297  _pcps_has_lan_intf( &(_p)->dev )
1298 
1299 #define _pcps_ddev_has_ptp( _p ) \
1300  _pcps_has_ptp( &(_p)->dev )
1301 
1302 #define _pcps_ddev_has_ptp_unicast( _p ) \
1303  _pcps_has_ri_ptp_unicast( _ri_addr( _p ) )
1304 
1305 #define _pcps_ddev_has_pzf( _p ) \
1306  _pcps_has_pzf( &(_p)->dev )
1307 
1308 #define _pcps_ddev_has_corr_info( _p ) \
1309  _pcps_has_corr_info( &(_p)->dev )
1310 
1311 #define _pcps_ddev_has_tr_distance( _p ) \
1312  _pcps_has_tr_distance( &(_p)->dev )
1313 
1314 #define _pcps_ddev_has_evt_log( _p ) \
1315  _pcps_has_evt_log( &(_p)->dev )
1316 
1317 #define _pcps_ddev_has_debug_status( _p ) \
1318  _pcps_has_debug_status( &(_p)->dev )
1319 
1320 #define _pcps_ddev_has_stat_info( _p ) \
1321  _pcps_has_stat_info( &(_p)->dev )
1322 
1323 #define _pcps_ddev_has_stat_info_mode( _p ) \
1324  _pcps_has_stat_info_mode( &(_p)->dev ) \
1325 
1326 #define _pcps_ddev_has_stat_info_svs( _p ) \
1327  _pcps_has_stat_info_svs( &(_p)->dev ) \
1328 
1329 #define _pcps_ddev_incoming_tfom_ignored( _p ) \
1330  _pcps_incoming_tfom_ignored( &(_p)->dev )
1331 
1332 #define _pcps_ddev_pci_cfg_err( _p ) \
1333  _pcps_pci_cfg_err( &(_p)->dev )
1334 
1335 #define _pcps_ddev_has_gpio( _p ) \
1336  _pcps_has_ri_gpio( _ri_addr( _p ) )
1337 
1338 #define _pcps_ddev_has_xmr( _p ) \
1339  _pcps_has_ri_xmr( _ri_addr( _p ) )
1340 
1341 #define _pcps_ddev_fw_has_20ms_bug( _p ) \
1342  _pcps_fw_has_20ms_bug( &(_p)->dev )
1343 
1344 
1345 // These macros simplify read/write access to the clocks.
1346 
1347 // Call the device's read function to write the command byte _cmd
1348 // and read _n bytes to buffer _s.
1349 #if !defined( _pcps_read )
1350  #define _pcps_read( _pddev, _cmd, _p, _n ) \
1351  ( (_pddev)->read( _pddev, (_cmd), (uchar FAR *)(_p), (_n) ) )
1352 #endif
1353 
1354 // Write a byte _b to a device. This is typically done by just writing
1355 // the command byte from within the read function, without actually
1356 // reading any data bytes.
1357 #if !defined( _pcps_write_byte )
1358  #define _pcps_write_byte( _pddev, _b ) \
1359  _pcps_read( (_pddev), (_b), NULL, 0 )
1360 #endif
1361 
1362 // write a command plus the contents of a data buffer to a device.
1363 // This is typically implemented as a function which uses the
1364 // _pcps_write_byte() macro repeatedly.
1365 #if !defined( _pcps_write )
1366  #define _pcps_write( _pddev, _cmd, _p, _n ) \
1367  pcps_write( (_pddev), (_cmd), (uchar FAR *)(_p), (_n) )
1368 #endif
1369 
1370 // Read data structures which exceed ::PCPS_FIFO_SIZE bytes.
1371 // This can't be handled in a single read cycle and due to
1372 // limitations of the device's microprocessor the execution time
1373 // can be up to 20 milliseconds, depending on the device type.
1374 // This has been introduced with the first GPS devices but is
1375 // now in fact also used with non-GPS devices.
1376 #define _pcps_read_gps( _pddev, _cmd, _p, _n ) \
1377  pcps_read_gps( (_pddev), (_cmd), (uchar FAR *)(_p), (_n) )
1378 
1379 // The complementary write function for the read function above.
1380 #define _pcps_write_gps( _pddev, _cmd, _p, _n ) \
1381  pcps_write_gps( (_pddev), (_cmd), (uchar FAR *)(_p), (_n) )
1382 
1383 
1384 
1385 // These macros simplify reading/writing typed variables by
1386 // determining the size automatically from the type of the variable.
1387 
1388 // Read data from a device to variable _s.
1389 // The number of bytes to read is determined by the size
1390 // of _s. The accepted type of _s depends on the _cmd code.
1391 #define _pcps_read_var( _pddev, _cmd, _s ) \
1392  _pcps_read( (_pddev), (_cmd), &(_s), sizeof( (_s) ) )
1393 
1394 // Write data from variable _s to a device.
1395 // The number of bytes to write is determined by the size
1396 // of _s. The accepted type of _s depends on the _cmd code.
1397 #define _pcps_write_var( _pddev, _cmd, _s ) \
1398  _pcps_write( (_pddev), (_cmd), &(_s), sizeof( (_s) ) )
1399 
1400 
1401 // Read data structures which exceed PCPS_FIFO_SIZE bytes.
1402 // This can't be handled in a single read cycle and due to limitations
1403 // of the clock's microprocessor these calls can up to 20 milliseconds.
1404 // Currently these function is only used to read GPS specific data
1405 // from GPS clocks.
1406 #define _pcps_read_gps_var( _pddev, _cmd, _s ) \
1407  _pcps_read_gps( (_pddev), (_cmd), &(_s), sizeof( (_s) ) )
1408 
1409 // The complementary write function for the read function above.
1410 #define _pcps_write_gps_var( _pddev, _cmd, _s ) \
1411  _pcps_write_gps( (_pddev), (_cmd), &(_s), sizeof( (_s) ) )
1412 
1413 
1414 // Generate a hardware reset on a device. This macro should be used
1415 // VERY carefully and should be avoided, if possible, since resetting
1416 // a device could lock up the PC.
1417 #define _pcps_force_reset( _pddev ) \
1418  _pcps_write_byte( (_pddev), PCPS_FORCE_RESET )
1419 
1420 
1421 // This macro reads a device's status port which includes
1422 // the BUSY flag (::PCPS_ST_BUSY )and the modulation signal
1423 // of DCF77 and other long wave receivers.
1424 // The macro takes a (PCPS_DDEV *) as argument.
1425 #if _PCPS_USE_MM_IO
1426 
1427 #if 1 // TODO
1428 
1429 static __mbg_inline
1431 {
1432  return _pcps_ddev_access_mode_mm( pddev ) ?
1433  _mbg_mmrd8_offs( pddev, 0, pddev->status_port_offs ) :
1434  _mbg_inp8( pddev, 0, pddev->status_port ); // TODO Use _mbg_inp8_offs()
1435 }
1436 
1437 #else
1438 
1439  #define _pcps_ddev_read_status_port( _d ) \
1440  ( _pcps_ddev_access_mode_mm( (_d) ) ? \
1441  _mbg_mmrd8( &(_d)->mm_asic_addr->status_port.b ) : \
1442  _mbg_inp8( (_d), 0, (_d)->status_port ) \
1443  )
1444 
1445 #endif
1446 
1447 #else
1448 
1449  #define _pcps_ddev_read_status_port( _d ) \
1450  _mbg_inp8( (_d), 0, (_d)->status_port )
1451 
1452 #endif
1453 
1454 
1455 #define _pcps_ddev_status_busy( _d ) \
1456  ( _pcps_ddev_read_status_port( pddev ) & PCPS_ST_BUSY )
1457 
1458 
1459 // This macro checks whether a workaround is required to get/set
1460 // IRIG cfg from a GPS169PCI with IRIG output and early firmware version.
1461 // This is handled in mbgdevio.c for direct access environments, and in
1462 // macioctl.h for kernel device drivers.
1463 #define _pcps_ddev_requires_irig_workaround( _d ) \
1464  ( ( _pcps_ddev_type_num( _d ) == PCPS_TYPE_GPS169PCI ) && \
1465  ( _pcps_ddev_fw_rev_num( _d ) < REV_HAS_GPS_DATA_16_GPS169PCI ) )
1466 
1467 
1468 #if _PCPS_USE_USB
1469 
1470  #if !defined( MBGUSB_TIMEOUT_SEND_MS )
1471  #define MBGUSB_TIMEOUT_SEND_MS 500 // [ms]
1472  #endif
1473 
1474  #if !defined( MBGUSB_TIMEOUT_RECEIVE_MS )
1475  #define MBGUSB_TIMEOUT_RECEIVE_MS 500 // [ms]
1476  #endif
1477 
1478  #if !defined( MBGUSB_TIMEOUT_RECEIVE_CYCLIC_MS )
1479  // The USB read function may block until a packet has been received, or a
1480  // receive timeout has occurred. The cyclic USB read function has an overall
1481  // timeout of more than 1 second. In order to increase responsiveness we use
1482  // by default a shorter timeout interval plus some retries, if required.
1483  //
1484  // For some target environments it may be preferable to use only one
1485  // full timeout interval, so this setting can be overridden if required.
1486  #if !defined( _PCPS_USB_FULL_CYCLIC_INTV )
1487  #define _PCPS_USB_FULL_CYCLIC_INTV 1
1488  #endif
1489 
1490  #if _PCPS_USB_FULL_CYCLIC_INTV
1491  #define MBGUSB_TIMEOUT_RECEIVE_CYCLIC_MS 1200
1492  #else
1493  #define MBGUSB_TIMEOUT_RECEIVE_CYCLIC_MS 50
1494  #endif
1495  #endif
1496 
1497 
1498  #if !defined( _pcps_ms_to_usb_timeout )
1499  #define _pcps_ms_to_usb_timeout( _ms ) (_ms)
1500  #endif
1501 
1502 
1503  #if !defined( MBGUSB_TIMEOUT_SEND )
1504  #define MBGUSB_TIMEOUT_SEND _pcps_ms_to_usb_timeout( MBGUSB_TIMEOUT_SEND_MS )
1505  #endif
1506 
1507  #if !defined( MBGUSB_TIMEOUT_RECEIVE )
1508  #define MBGUSB_TIMEOUT_RECEIVE _pcps_ms_to_usb_timeout( MBGUSB_TIMEOUT_RECEIVE_MS )
1509  #endif
1510 
1511  #if !defined( MBGUSB_TIMEOUT_RECEIVE_CYCLIC )
1512  #define MBGUSB_TIMEOUT_RECEIVE_CYCLIC _pcps_ms_to_usb_timeout( MBGUSB_TIMEOUT_RECEIVE_CYCLIC_MS )
1513  #endif
1514 
1515 
1516 
1517 #if !defined( MBG_TGT_WIN32 )
1518 
1519 static __mbg_inline /*HDR*/
1520 int pcps_direct_usb_transfer( PCPS_DDEV *pddev, void *buffer, int len, int ep_idx,
1521  int timeout, const char *fnc_name )
1522 {
1523  int rc = MBG_ERR_NOT_SUPP_ON_OS;
1524 
1525  #if defined( MBG_TGT_LINUX )
1526 
1527  int usb_rc; // rc from system USB stack
1528  unsigned int ep = pddev->ep[ep_idx].addr;
1529  bool rcv = is_ep_rcv( ep );
1530  int pipe = rcv ? usb_rcvbulkpipe( pddev->udev, ep )
1531  : usb_sndbulkpipe( pddev->udev, ep );
1532  int actual_len = 0;
1533  void *p = NULL;
1534 
1535  (void) p; // Avoid compiler warning "never used"
1536 
1537  #if _PCPS_CHK_BUFFER_DMA_CAPABLE
1538  if ( !_pcps_buffer_is_dma_capable( buffer ) )
1539  {
1540  // Buffer is *NOT* DMA capable.
1541  _mbg_kdd_msg_4( MBG_LOG_WARN, "%s called to %s from " MBG_DEV_NAME_FMT " with non-DMA-capable buffer",
1542  fnc_name, rcv ? "rcv" : "snd", _pcps_ddev_type_name( pddev ),
1543  _pcps_ddev_sernum( pddev ) );
1544 
1545  p = _pcps_kmalloc( len );
1546 
1547  if ( p == NULL )
1548  return MBG_ERR_NO_MEM;
1549 
1550  if ( !rcv )
1551  memcpy( p, buffer, len );
1552 
1553  usb_rc = usb_bulk_msg( pddev->udev, pipe, p, len, &actual_len, timeout );
1554 
1555  if ( rcv && ( usb_rc == 0 ) )
1556  memcpy( buffer, p, actual_len );
1557 
1558  _pcps_kfree( p, len );
1559  }
1560  else
1561  #endif
1562  usb_rc = usb_bulk_msg( pddev->udev, pipe, buffer, len, &actual_len, timeout );
1563 
1564 
1565  #if DEBUG_USB_IO > 1
1566  _mbgddmsg_8( DEBUG_USB_IO, MBG_LOG_INFO, "%s: ep %02X, pipe %02X, malloc %p, len %i, actual_len %i, timeout %i, usb_rc: %i",
1567  fnc_name, ep, pipe, p ? p : NULL, len, actual_len, timeout, usb_rc );
1568  #endif
1569 
1570  if ( usb_rc < 0 )
1571  {
1572  rc = mbg_posix_errno_to_mbg( -usb_rc, NULL );
1573 
1574  #if DEBUG_USB_IO > 1
1575  _mbgddmsg_3( DEBUG_USB_IO, MBG_LOG_INFO, "%s: USB rc %i -> %i", fnc_name, usb_rc, rc );
1576  #endif
1577  }
1578  else
1579  rc = actual_len;
1580 
1581  #else
1582 
1583  #error Needs to be implemented for this target.
1584 
1585  #endif
1586 
1587  return rc;
1588 
1589 } // pcps_direct_usb_transfer
1590 
1591 #else
1592 
1593  int pcps_direct_usb_transfer( PCPS_DDEV *pddev, void *buffer, int len, int ep_idx, int timeout, const char *fnc_name );
1594 
1595 #endif
1596 
1597 
1598 
1599 static __mbg_inline /*HDR*/
1600 int pcps_direct_usb_write( PCPS_DDEV *pddev, void *buffer, int len )
1601 {
1602  return pcps_direct_usb_transfer( pddev, buffer, len, MBGUSB_EP_IDX_HOST_OUT,
1603  MBGUSB_TIMEOUT_SEND, __func__ );
1604 
1605 } // pcps_direct_usb_write
1606 
1607 #define _pcps_direct_usb_write_var( _d, _p ) \
1608  pcps_direct_usb_write( _d, _p, sizeof( *(_p) ) )
1609 
1610 
1611 
1612 static __mbg_inline /*HDR*/
1613 int pcps_direct_usb_read( PCPS_DDEV *pddev, void *buffer, int len )
1614 {
1615  return pcps_direct_usb_transfer( pddev, buffer, len, MBGUSB_EP_IDX_HOST_IN,
1616  MBGUSB_TIMEOUT_RECEIVE, __func__ );
1617 
1618 } // pcps_direct_usb_read
1619 
1620 #define _pcps_direct_usb_read_var( _d, _p ) \
1621  pcps_direct_usb_read( _d, _p, sizeof( *(_p) ) )
1622 
1623 
1624 
1625 static __mbg_inline /*HDR*/
1626 int pcps_direct_usb_read_cyclic( PCPS_DDEV *pddev, void *buffer, int len )
1627 {
1628  return pcps_direct_usb_transfer( pddev, buffer, len, MBGUSB_EP_IDX_HOST_IN_CYCLIC,
1629  MBGUSB_TIMEOUT_RECEIVE_CYCLIC, __func__ );
1630 
1631 } // pcps_direct_usb_read_cyclic
1632 
1633 #define _pcps_direct_usb_read_var_cyclic( _d, _p ) \
1634  pcps_direct_usb_read_cyclic( _d, _p, sizeof( *(_p) ) )
1635 
1636 
1637 #endif
1638 
1639 
1640 
1646 /* ----- function prototypes begin ----- */
1647 
1648 /* This section was generated automatically */
1649 /* by MAKEHDR, do not remove the comments. */
1650 
1651  void pcps_dump_data( const void *buffer, size_t count, const char *info ) ;
1669  int pcps_write( PCPS_DDEV *pddev, uint8_t cmd, const void FAR *buffer, uint16_t count ) ;
1670 
1690  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 ) ;
1691 
1717  int pcps_read_gps( PCPS_DDEV *pddev, uint8_t data_type, void FAR *buffer, uint16_t count ) ;
1718 
1739  int pcps_write_gps( PCPS_DDEV *pddev, uint8_t data_type, const void FAR *buffer, uint16_t count ) ;
1740 
1752 
1759 
1765  void pcps_release_rsrcs( PCPS_DDEV *pddev ) ;
1766 
1781 
1794  int pcps_init_ddev( PCPS_DDEV **ppddev ) ;
1795 
1803  void pcps_cleanup_ddev( PCPS_DDEV *pddev ) ;
1804 
1814  int pcps_add_rsrc_io( PCPS_DDEV *pddev, MBG_IOPORT_ADDR_RAW base, ulong num ) ;
1815 
1825  int pcps_add_rsrc_mem( PCPS_DDEV *pddev, MBG_IOMEM_ADDR_RAW start, ulong len ) ;
1826 
1835  int pcps_add_rsrc_irq( PCPS_DDEV *pddev, int16_t irq_num ) ;
1836 
1847  int pcps_setup_ddev( PCPS_DDEV *pddev, PCPS_BUS_FLAGS bus_mask, PCPS_DEV_ID dev_id ) ;
1848 
1868  int pcps_chk_dev_feat( PCPS_DDEV *p_ddev, uint feat_type, uint feat_num ) ;
1869 
1889  int pcps_probe_device( PCPS_DDEV *pddev, PCPS_BUS_NUM bus_num, PCPS_SLOT_NUM dev_fnc_num ) ;
1890 
1898  void pcps_cleanup_device( PCPS_DDEV *pddev ) ;
1899 
1907  int pcps_setup_and_start_pci_dev( PCPS_DDEV *pddev, PCPS_BUS_NUM bus_num, PCPS_SLOT_NUM dev_fnc_num ) ;
1908 
1918  void pcps_detect_pci_devices( PCPS_DDEV_INIT_FNC *ddev_init_fnc, PCPS_DDEV_CLEANUP_FNC *ddev_cleanup_fnc, ushort vendor_id, PCPS_DEV_TYPE dev_type[], int n_dev_types ) ;
1919 
1929  void pcps_detect_isa_devices( PCPS_DDEV_INIT_FNC *ddev_init_fnc, PCPS_DDEV_CLEANUP_FNC *ddev_cleanup_fnc, PCPS_DDEV_REGISTER_FNC *ddev_register_fnc, int isa_ports[PCPS_MAX_ISA_CARDS], int isa_irqs[PCPS_MAX_ISA_CARDS] ) ;
1930 
1940  void _MBG_INIT_CODE_ATTR pcps_detect_devices( int isa_ports[PCPS_MAX_ISA_CARDS], int isa_irqs[PCPS_MAX_ISA_CARDS] ) ;
1941 
1942 
1943 /* ----- function prototypes end ----- */
1944 
1945 #ifdef __cplusplus
1946 }
1947 #endif
1948 
1949 // We have used native alignment here, so no need to undo alignment at this place.
1950 
1951 /* End of header body */
1952 
1953 #undef _ext
1954 #undef _DO_INIT
1955 
1956 #endif /* _PCPSDRVR_H */
#define N_PCPS_MEM_RSRC
The max number of bus memory resources used by a device.
Definition: pcpsdrvr.h:666
#define USB_DEV_WWVB51USB
Definition: usbdefs.h:228
#define _pcps_ddev_sernum(_p)
Definition: pcpsdrvr.h:1186
PCPS_RSRC_INFO rsrc_info
Summary of resources used by the device.
Definition: pcpsdrvr.h:797
void pcps_cleanup_ddev(PCPS_DDEV *pddev)
Clean up and free a previously initialized device info structure.
Definition: pcpsdrvr.c:4845
uint8_t uc
Definition: pcpsdrvr.h:852
uint32_t irq_disb_mask
Bit mask to be cleared to disable IRQs.
Definition: pcpsdrvr.h:790
int force_mm16_access
const char * fw_id_ref[]
The first characters of a valid firmware ID.
#define PCI_DEV_TCR170PEX
Definition: pcpsdefs.h:405
#define _mbg_kdd_msg_4(_lvl, _fmt, _p1, _p2, _p3, _p4)
Definition: mbgddmsg.h:245
struct fasync_struct * fasyncptr
Used for asynchronous signalling when data is available.
Definition: pcpsdrvr.h:867
void pcps_detect_devices(int isa_ports[16], int isa_irqs[16])
Detect all bus-level devices in a non-PnP system.
int PCPS_WRITE_FNC(PCPS_DDEV *pddev, uint8_t cmd, const void *buffer, uint16_t count)
Definition: pcpsdrvr.h:770
uint8_t cmd
In case of small data we just need one of the PCPS_CMD_CODES.
Definition: pcpsdrvr.h:838
#define PCI_DEV_TCR510PCI
Definition: pcpsdefs.h:401
#define _mbgddmsg_3(_f, _lvl, _fmt, _p1, _p2, _p3)
Definition: mbgddmsg.h:330
#define PCI_DEV_TCR167PCI
Definition: pcpsdefs.h:402
#define PCI_DEV_PCI511
Definition: pcpsdefs.h:387
#define ISA_ID_PCPS
A board ID for later ISA bus devices.
Definition: pcpsdrvr.h:985
PTP/IEEE1588 network protocol.
Definition: pcpsdefs.h:298
PCPS_TIME t
Date and time read by IRQ handler.
Definition: pcpsdrvr.h:868
#define USB_DEV_TCR600USB
Definition: usbdefs.h:221
PCPS_IRQ_STAT_INFO irq_stat_info
Definition: pcpsdrvr.h:820
unsigned long jiffies_at_irq
Set by IRQ handler, used to check if cyclic IRQs still occur.
Definition: pcpsdrvr.h:866
short int16_t
Definition: words.h:212
int pcps_read_gps(PCPS_DDEV *pddev, uint8_t data_type, void *buffer, uint16_t count)
Read a large data structure from a device.
ulong MBG_IOPORT_ADDR_MAPPED
Definition: mbggenio.h:187
uint16_t PCPS_BUS_NUM
Definition: pcpsdev.h:580
uint32_t BUILTIN_FEATURE_MASK
Definitions used to classify devices and built-in features.
Definition: gpsdefs.h:1286
uint8_t gps_cmd
One of the PC_GPS_CMD_CODES.
Definition: pcpsdrvr.h:845
int pcps_add_rsrc_io(PCPS_DDEV *pddev, MBG_IOPORT_ADDR_RAW base, ulong num)
Add an I/O address range resource to the device structure.
Definition: pcpsdrvr.c:4897
unsigned short uint16_t
Definition: words.h:213
#define _MBG_IOMEM
Definition: mbggenio.h:165
void pcps_dump_data(const void *buffer, size_t count, const char *info)
Definition: pcpsdrvr.c:1219
#define MBG_DEV_NAME_FMT
A string format specifier for MBG_DEV_NAME.
Definition: pcpsdev.h:1534
uint32_t irq_flag_mask
Bit mask used to check if device has generated an IRQ.
Definition: pcpsdrvr.h:791
#define PCI_DEV_PZF180PEX
Definition: pcpsdefs.h:389
Resource info summary for a device.
Definition: pcpsdrvr.h:678
const char driver_name[]
#define _MBG_INIT_CODE_ATTR
Definition: pcpsdrvr.h:410
#define PCI_DEV_GPS180PEX
Definition: pcpsdefs.h:396
MBG_IOPORT_ADDR_MAPPED irq_ack_port
Address of the register to acknowledge an IRQ.
Definition: pcpsdrvr.h:788
#define PCI_DEV_GNS181PEX
Definition: pcpsdefs.h:399
#define PCI_DEV_GPS167PCI
Definition: pcpsdefs.h:391
#define PCI_DEV_GPS170PCI
Definition: pcpsdefs.h:394
Memory layout of Meinberg PCI interface register.
Definition: pcpsdrvr.h:746
PCPS_DEV_TYPE pcps_dev_type[N_PCPS_DEV_TYPE]
int pcps_write(PCPS_DDEV *pddev, uint8_t cmd, const void *buffer, uint16_t count)
Write data to a device.
#define PCI_DEV_PCI32
PCI device IDs assigned by Meinberg.
Definition: pcpsdefs.h:384
unsigned short ushort
Definition: words.h:282
int num_rsrc_io
Number of actually assigned I/O address ranges.
Definition: pcpsdrvr.h:680
Standard port I/O.
Definition: pcpsdrvr.h:915
#define PCI_DEV_TCR511PCI
Definition: pcpsdefs.h:403
atomic_t open_count
Number of processes that have opened this device.
Definition: pcpsdrvr.h:876
#define MCA_ID_PS31
MCA adapter ID assigned by IBM.
Definition: pcpsdrvr.h:961
#define _pcps_ddev_access_mode_mm(_p)
Definition: pcpsdrvr.h:1213
int mbg_posix_errno_to_mbg(int posix_errno, const char *info)
Translate a POSIX errno error code to one of the MBG_ERROR_CODES.
Definition: mbgerror.c:920
int num_rsrc_irq
Number of actually assigned IRQ numbers.
Definition: pcpsdrvr.h:682
Free Running Clock.
Definition: pcpsdefs.h:299
MBG_XDEV_FEATURES xdev_features
Receiver info plus extended device features.
Definition: pcpsdrvr.h:823
PCPS_READ_FNC * read
Pointer to the read function depending on the access mode.
Definition: pcpsdrvr.h:781
MBG_PC_CYCLES acc_cycles
Cycles count taken when device was accessed last time.
Definition: pcpsdrvr.h:799
32 bit memory mapped access
Definition: pcpsdrvr.h:916
No real I/O, dummy routine used.
Definition: pcpsdrvr.h:913
Register layout of a PCI ASIC.
Definition: pci_asic.h:198
#define USB_DEV_USB5131
Definition: usbdefs.h:214
int n_ddevs
PCI_ASIC_VERSION asic_version
ASIC version.
Definition: pcpsdrvr.h:795
IRIG or similar time code, see http://www.meinberg.de/english/info/irig.htm.
Definition: pcpsdefs.h:296
uint64_t MBG_IOMEM_ADDR_RAW
Definition: mbggenio.h:175
void pcps_detect_isa_devices(PCPS_DDEV_INIT_FNC *ddev_init_fnc, PCPS_DDEV_CLEANUP_FNC *ddev_cleanup_fnc, PCPS_DDEV_REGISTER_FNC *ddev_register_fnc, int isa_ports[16], int isa_irqs[16])
Detect and initialize ISA devices in a non-PnP system.
uint16_t n_bytes
Definition: pcpsdrvr.h:850
int pcps_chk_dev_feat(PCPS_DDEV *p_ddev, uint feat_type, uint feat_num)
Check if a specific feature of a specific feature type is supported.
Definition: pcpsdrvr.c:5112
#define PCI_DEV_PCI509
Definition: pcpsdefs.h:385
uint32_t irq_enb_mask
Bit mask to be set to enable IRQs.
Definition: pcpsdrvr.h:789
int PCPS_READ_FNC(PCPS_DDEV *pddev, uint8_t cmd, void *buffer, uint16_t count)
Definition: pcpsdrvr.h:769
#define PCPS_BUS_ISA
IBM compatible PC/AT ISA bus.
Definition: pcpsdev.h:413
#define MCA_ID_PS31_OLD
MCA adapter ID assigned by Meinberg, used with the first series of PS31 boards.
Definition: pcpsdrvr.h:962
uint16_t PCPS_DEV_ID
Definition: pcpsdev.h:500
PCPS_IO_BUFFER io_buffer
Definition: pcpsdrvr.h:855
#define PCPS_BUS_PCI_S5933
Definition: pcpsdev.h:430
bool access_mode_forced
Flag indicating that the access mode was forced.
Definition: pcpsdrvr.h:783
uint32_t PCI_ASIC_FEATURES
A data type to hold the PCI ASIC feature flags mask.
Definition: pci_asic.h:162
PCPS_ACCESS_MODES
Codes used with PCPS_DDEV::access_mode.
Definition: pcpsdrvr.h:911
dev_t lx_dev
Linux device associated with this device.
Definition: pcpsdrvr.h:879
PCI_ASIC_VERSION raw_asic_version
Raw ASIC version.
Definition: pcpsdrvr.h:794
PCI_ASIC volatile __iomem * mm_asic_addr
Definition: pcpsdrvr.h:807
#define PCI_DEV_PEX511
Definition: pcpsdefs.h:388
int pcps_generic_io(PCPS_DDEV *pddev, uint8_t type, const void *in_buff, uint8_t in_cnt, void *out_buff, uint8_t out_cnt)
Generic I/O function.
int debug
#define N_PCPS_PORT_RSRC
The max. number of I/O port resources used by a clock.
Definition: pcpsdev.h:555
#define DEBUG_USB_IO
Definition: pcpsdrvr.h:422
PCPS_TIME_STAMP volatile __iomem * mm_tstamp_addr
Definition: pcpsdrvr.h:811
int pcps_write_gps(PCPS_DDEV *pddev, uint8_t data_type, const void *buffer, uint16_t count)
Write a large data structure to a device.
#define _mbg_inp8(_dev, _rsrc_idx, _port_addr)
Definition: mbggenio.h:610
unsigned char uint8_t
Definition: words.h:210
#define PCI_DEV_GPS169PCI
Definition: pcpsdefs.h:393
int num_rsrc_mem
Number of actually assigned memory address ranges.
Definition: pcpsdrvr.h:681
#define USB_DEV_DCF600USB
Definition: usbdefs.h:215
int PCPS_DDEV_REGISTER_FNC(PCPS_DDEV *pddev)
Definition: pcpsdrvr.h:773
MBG_IOPORT_ADDR_MAPPED status_port_offs
Definition: pcpsdrvr.h:784
#define FAR
Definition: mbggenio.h:132
#define PCPS_BUS_PCI_MBGPEX
Definition: pcpsdev.h:434
void pcps_detect_pci_devices(PCPS_DDEV_INIT_FNC *ddev_init_fnc, PCPS_DDEV_CLEANUP_FNC *ddev_cleanup_fnc, ushort vendor_id, PCPS_DEV_TYPE dev_type[], int n_dev_types)
Detect and initialize PCI devices in a non-PnP system.
DCF77 long wave signal (Germany), see http://www.meinberg.de/english/info/dcf77.htm.
Definition: pcpsdefs.h:294
void pcps_release_rsrcs(PCPS_DDEV *pddev)
Release I/O port and memory resource that have been claimed before.
Definition: pcpsdrvr.c:4411
BUILTIN_FEATURE_MASK builtin_features
Mask of builtin features, depending on device type.
Definition: pcpsdrvr.h:822
IRQ resource information for a device.
Definition: mbggenio.h:311
#define MBG_ERR_NO_MEM
Failed to allocate memory.
Definition: mbgerror.h:282
PCPS_DDEV pcps_ddev[16]
#define _mbgddmsg_8(_f, _lvl, _fmt, _p1, _p2, _p3, _p4, _p5, _p6, _p7, _p8)
Definition: mbgddmsg.h:360
#define _pcps_kmalloc(_sz)
Definition: pcpsdrvr.h:555
An I/O buffer for bus level devices.
Definition: pcpsiobf.h:78
int force_io_access
uint32_t PCPS_IRQ_STAT_INFO
Definition: pcpsdev.h:1468
PCI_ASIC_FEATURES asic_features
ASIC feature mask.
Definition: pcpsdrvr.h:796
#define PCPS_BUS_MCA
IBM PS/2 micro channel.
Definition: pcpsdev.h:414
#define PCPS_BUS_USB
USB.
Definition: pcpsdev.h:416
void pcps_cleanup_device(PCPS_DDEV *pddev)
Clean up function called by pcps_probe_device on error.
Definition: pcpsdrvr.c:6247
MSF long wave signal (UK)
Definition: pcpsdefs.h:297
atomic_t connected
Flag indicating if the device is "connected".
Definition: pcpsdrvr.h:863
#define USB_DEV_WVB600USB
Definition: usbdefs.h:229
#define _pcps_kfree(_p, _sz)
Definition: pcpsdrvr.h:556
16 bit memory mapped access
Definition: pcpsdrvr.h:917
#define USB_DEV_MSF600USB
Definition: usbdefs.h:226
int pcps_add_rsrc_mem(PCPS_DDEV *pddev, MBG_IOMEM_ADDR_RAW start, ulong len)
Add a memory address range resource to the device structure.
Definition: pcpsdrvr.c:4959
MBG_IOPORT_ADDR_MAPPED irq_enb_disb_port
Address of the IRQ control register.
Definition: pcpsdrvr.h:786
int pcps_isa_ports[16+1]
uint access_mode
Access mode used for the device, depending on interface type. See PCPS_ACCESS_MODES.
Definition: pcpsdrvr.h:782
#define _pcps_ddev_type_name(_p)
Definition: pcpsdrvr.h:1131
GPS satellite system, see http://www.meinberg.de/english/info/gps.htm.
Definition: pcpsdefs.h:295
Device type specification.
Definition: pcpsdev.h:512
atomic_t access_in_progress
Flag indicating if device access is currently in progress.
Definition: pcpsdrvr.h:864
I/O port resource information for a device.
Definition: mbggenio.h:292
#define PCI_DEV_TCR511PEX
Definition: pcpsdefs.h:404
static __mbg_inline uint8_t _pcps_ddev_read_status_port(const PCPS_DDEV *pddev)
Definition: pcpsdrvr.h:1430
PCPS_TIME_STAMP tstamp
Definition: pcpsdrvr.h:751
ulong MBG_IOPORT_ADDR_RAW
Definition: mbggenio.h:186
#define PCI_DEV_PTP270PEX
Definition: pcpsdefs.h:408
#define PCPS_BUS_PCI_S5920
Definition: pcpsdev.h:431
#define USB_DEV_MSF51USB
Definition: usbdefs.h:225
int pcps_init_ddev(PCPS_DDEV **ppddev)
Allocate and initialize a device info structure.
Definition: pcpsdrvr.c:4799
#define PCI_DEV_GPS168PCI
Definition: pcpsdefs.h:392
#define PCI_DEV_GPS170PEX
Definition: pcpsdefs.h:395
uint8_t size_n_bytes
Definition: pcpsdrvr.h:851
uint32_t PCI_ASIC_VERSION
A data type to hold the PCI ASIC version code.
Definition: pci_asic.h:151
void check_receiver_info_and_features(PCPS_DDEV *pddev)
Check the receiver info and features.
Definition: pcpsdrvr.c:4274
int pcps_setup_ddev(PCPS_DDEV *pddev, PCPS_BUS_FLAGS bus_mask, PCPS_DEV_ID dev_id)
Initialize an allocated device structure for a specific device.
Local calendar date and time, plus sync status.
Definition: pcpsdefs.h:1128
atomic_t data_avail
Flag indicating if data has been made available by IRQ handler.
Definition: pcpsdrvr.h:865
A high resolution time stamp.
Definition: pcpsdefs.h:972
WWVB long wave signal (U.S.)
Definition: pcpsdefs.h:300
A structure combining all device feature information.
Definition: xdevfeat.h:88
#define PCPS_BUS_PCI_ASIC
Definition: pcpsdev.h:432
MBG_IOPORT_ADDR_MAPPED status_port
Address of the status port register.
Definition: pcpsdrvr.h:785
int pcps_add_rsrc_irq(PCPS_DDEV *pddev, int16_t irq_num)
Add an IRQ number resource to the device structure.
Definition: pcpsdrvr.c:5021
#define _pcps_buffer_is_dma_capable(_b)
Definition: mbg_lx.h:164
uint16_t PCPS_BUS_FLAGS
Definition: pcpsdev.h:502
#define PCPS_MAX_ISA_CARDS
Definition: pcpsdrvr.h:1071
#define PCI_DEV_FRC511PEX
Definition: pcpsdefs.h:410
uint32_t irq_ack_mask
Bit mask to be set to acknowledge an IRQ.
Definition: pcpsdrvr.h:792
#define PCI_DEV_GPS180AMC
Definition: pcpsdefs.h:398
MBG_IRQ_RSRC irq
Info on actually assigned IRQ numbers.
Definition: pcpsdrvr.h:685
MBG_MUTEX dev_mutex
Mutex used for device access serialization.
Definition: pcpsdrvr.h:802
#define USB_DEV_TCR180USB
Definition: usbdefs.h:223
#define PCPS_BUS_USB_V2
Definition: pcpsdev.h:444
#define PCI_DEV_GLN180PEX
Definition: pcpsdefs.h:397
#define _ext
Definition: pcpsdrvr.h:516
#define _mbg_mmrd8_offs(_dev, _rsrc_idx, _iomem_offs)
Definition: mbggenio.h:587
int PCPS_DDEV_INIT_FNC(PCPS_DDEV **ppddev)
Definition: pcpsdrvr.h:771
unsigned int uint
Definition: words.h:287
int pcps_probe_device(PCPS_DDEV *pddev, PCPS_BUS_NUM bus_num, PCPS_SLOT_NUM dev_fnc_num)
Probe if a device is supported, and allocate and setup the device structure.
Definition: pcpsdrvr.c:5409
PCPS_DEV dev
Device info data that can be passed to user space.
Definition: pcpsdrvr.h:779
int64_t MBG_PC_CYCLES
Generic types to hold PC cycle counter values.
Definition: mbgpccyc.h:97
pthread_mutex_t MBG_MUTEX
Definition: mbgmutex.h:181
#define MBG_ERR_NOT_SUPP_ON_OS
Function is not supported on this operating system.
Definition: mbgerror.h:289
#define PCI_DEV_PCI510
Definition: pcpsdefs.h:386
MBG_IOPORT_ADDR_MAPPED irq_flag_port
Address of the IRQ status register.
Definition: pcpsdrvr.h:787
unsigned long ulong
Definition: words.h:292
Bus memory resource information for a device.
Definition: mbggenio.h:273
#define USB_DEV_TCR51USB
Definition: usbdefs.h:220
int pcps_setup_and_start_pci_dev(PCPS_DDEV *pddev, PCPS_BUS_NUM bus_num, PCPS_SLOT_NUM dev_fnc_num)
Setup and start a PCI device in a non-PnP system.
#define PCPS_BUS_PCI_PEX8311
Definition: pcpsdev.h:433
#define N_SUPP_DEV_BUS
Definition: cfg_hlp.h:114
void PCPS_DDEV_CLEANUP_FNC(PCPS_DDEV *pddev)
Definition: pcpsdrvr.h:772
USB I/O, no direct port access.
Definition: pcpsdrvr.h:914
PCPS_TIME_STAMP tstamp
Definition: pcpsdrvr.h:759
struct wait_queue * wait_queue
Used for asynchronous I/O (older kernel API)
Definition: pcpsdrvr.h:873
#define PCI_DEV_TCR180PEX
Definition: pcpsdefs.h:406
Device info structure.
Definition: pcpsdev.h:1043
uint16_t PCPS_SLOT_NUM
Definition: pcpsdev.h:581
PCPS_DEV_TYPE * pcps_get_dev_type_table_entry(PCPS_BUS_FLAGS bus_mask, PCPS_DEV_ID dev_id)
Lookup a specific device in the device table.
Definition: pcpsdrvr.c:4672
int setup_sernum_and_receiver_info(PCPS_DDEV *pddev)
Read the serial number and receiver info from the device.
Definition: pcpsdrvr.c:4097
#define MBG_DRVR_NAME
Definition: pcpsdrvr.h:532