]> CyberLeo.Net >> Repos - FreeBSD/releng/9.2.git/blob - tools/test/ppsapi/ppsapitest.c
- Copy stable/9 to releng/9.2 as part of the 9.2-RELEASE cycle.
[FreeBSD/releng/9.2.git] / tools / test / ppsapi / ppsapitest.c
1 /*-
2  * Copyright (c) 1998-2003 Poul-Henning Kamp
3  *
4  * Please see src/share/examples/etc/bsd-style-copyright.
5  *
6  */
7
8 #include <sys/cdefs.h>
9 __FBSDID("$FreeBSD$");
10
11 #include <stdio.h>
12 #include <stdint.h>
13 #include <stdlib.h>
14 #include <unistd.h>
15 #include <fcntl.h>
16 #include <err.h>
17 #include <sys/timepps.h>
18
19 static int aflag, Aflag, cflag, Cflag, eflag, uflag, vflag;
20
21 static void
22 Chew(struct timespec *tsa, struct timespec *tsc, unsigned sa, unsigned sc)
23 {
24         printf("%jd .%09ld %u", (intmax_t)tsa->tv_sec, tsa->tv_nsec, sa);
25         printf(" %jd .%09ld %u\n", (intmax_t)tsc->tv_sec, tsc->tv_nsec, sc);
26         if (uflag)
27                 fflush(stdout);
28 }
29
30 int
31 main(int argc, char **argv)
32 {
33         int fd;
34         FILE *fdo;
35         pps_info_t pi;
36         pps_params_t pp;
37         pps_handle_t ph;
38         int i, mode;
39         u_int olda, oldc;
40         struct timespec to;
41         char const *ofn;
42
43         ofn = NULL;
44         while ((i = getopt(argc, argv, "aAbBcCeo:uv")) != -1) {
45                 switch (i) {
46                 case 'a': aflag = 1; break;
47                 case 'A': Aflag = 1; break;
48                 case 'b': aflag = 1; cflag = 1; break;
49                 case 'B': Aflag = 1; Cflag = 1; break;
50                 case 'c': cflag = 1; break;
51                 case 'C': Cflag = 1; break;
52                 case 'e': eflag = 1; break;
53                 case 'o': ofn = optarg; break;
54                 case 'u': uflag = 1; break;
55                 case 'v': vflag = 1; break;
56                 case '?':
57                 default:
58                         fprintf(stderr,
59                             "Usage: ppsapitest [-aAcC] device\n");
60                         exit (1);
61                 }
62         }
63         if (ofn != NULL) {
64                 fdo = fopen(ofn, "w");
65                 if (fdo == NULL)
66                         err(1, "Cannot open %s", ofn);
67         } else {
68                 fdo = NULL;
69         }
70         argc -= optind;
71         argv += optind;
72         if (argc > 0) {
73                 fd = open(argv[0], O_RDONLY);
74                 if (fd < 0) 
75                         err(1, argv[0]);
76         } else {
77                 fd = 0;
78         }
79         i = time_pps_create(fd, &ph);
80         if (i < 0)
81                 err(1, "time_pps_create");
82
83         i = time_pps_getcap(ph, &mode);
84         if (i < 0)
85                 err(1, "time_pps_getcap");
86         if (vflag) {
87                 fprintf(stderr, "Supported modebits:");
88                 if (mode & PPS_CAPTUREASSERT)
89                         fprintf(stderr, " CAPTUREASSERT");
90                 if (mode & PPS_CAPTURECLEAR)
91                         fprintf(stderr, " CAPTURECLEAR");
92                 if (mode & PPS_OFFSETASSERT)
93                         fprintf(stderr, " OFFSETASSERT");
94                 if (mode & PPS_OFFSETCLEAR)
95                         fprintf(stderr, " OFFSETCLEAR");
96                 if (mode & PPS_ECHOASSERT)
97                         fprintf(stderr, " ECHOASSERT");
98                 if (mode & PPS_ECHOCLEAR)
99                         fprintf(stderr, " ECHOCLEAR");
100                 if (mode & PPS_CANWAIT)
101                         fprintf(stderr, " CANWAIT");
102                 if (mode & PPS_CANPOLL)
103                         fprintf(stderr, " CANPOLL");
104                 if (mode & PPS_TSFMT_TSPEC)
105                         fprintf(stderr, " TSPEC");
106                 if (mode & PPS_TSFMT_NTPFP)
107                         fprintf(stderr, " NTPFP");
108                 fprintf(stderr, "\n");
109         }
110
111         if (!aflag && !cflag) {
112                 if (mode & PPS_CAPTUREASSERT)
113                         aflag = 1;
114                 if (mode & PPS_CAPTURECLEAR)
115                         cflag = 1;
116         }
117         if (!Aflag && !Cflag) {
118                 Aflag = aflag;
119                 Cflag = cflag;
120         }
121
122         if (Cflag && !(mode & PPS_CAPTURECLEAR))
123                 errx(1, "-C but cannot capture on clear flank");
124
125         if (Aflag && !(mode & PPS_CAPTUREASSERT))
126                 errx(1, "-A but cannot capture on assert flank");
127
128         i = time_pps_getparams(ph, &pp);
129         if (i < 0)
130                 err(1, "time_pps_getparams():");
131
132         if (aflag)
133                 pp.mode |= PPS_CAPTUREASSERT;
134         if (cflag)
135                 pp.mode |= PPS_CAPTURECLEAR;
136
137         if (eflag & aflag)
138                 pp.mode |= PPS_ECHOASSERT;
139
140         if (eflag & cflag)
141                 pp.mode |= PPS_ECHOCLEAR;
142
143         if (!(pp.mode & PPS_TSFMT_TSPEC))
144                 pp.mode |= PPS_TSFMT_TSPEC;
145         
146         i = time_pps_setparams(ph, &pp);
147         if (i < 0) {
148                 err(1, "time_pps_setparams(mode %x):", pp.mode);
149         }
150
151         /*
152          * Pick up first event outside the loop in order to not
153          * get something ancient into the outfile.
154          */
155         to.tv_nsec = 0;
156         to.tv_sec = 0;
157         i = time_pps_fetch(ph, PPS_TSFMT_TSPEC, &pi, &to);
158         if (i < 0)
159                 err(1, "time_pps_fetch()");
160         olda = pi.assert_sequence;
161         oldc = pi.clear_sequence;
162
163         while (1) {
164                 to.tv_nsec = 0;
165                 to.tv_sec = 0;
166                 i = time_pps_fetch(ph, PPS_TSFMT_TSPEC, &pi, &to);
167                 if (i < 0)
168                         err(1, "time_pps_fetch()");
169                 if (oldc != pi.clear_sequence && Cflag)
170                         ;
171                 else if (olda != pi.assert_sequence && Aflag)
172                         ;
173                 else {
174                         usleep(10000);
175                         continue;
176                 }
177                 if (fdo != NULL) {
178                         if (fwrite(&pi, sizeof pi, 1, fdo) != 1)
179                                 err(1, "Write error on %s", ofn);
180                         if (uflag)
181                                 fflush(fdo);
182                 }
183                 Chew(&pi.assert_timestamp, &pi.clear_timestamp,
184                         pi.assert_sequence, pi.clear_sequence);
185                 olda = pi.assert_sequence;
186                 oldc = pi.clear_sequence;
187         }
188         return(0);
189 }