#if HAVE_CONFIG_H
# include <config.h>
#endif
#if defined(REFCLOCK) && defined(CLOCK_PARSE) && defined(CLOCK_SCHMID)
#include "ntp_fp.h"
#include "ntp_unixtime.h"
#include "ntp_calendar.h"
#include "parse.h"
#ifndef PARSESTREAM
#include "ntp_stdlib.h"
#include <stdio.h>
#else
#include "sys/parsestreams.h"
extern void printf P((const char *, ...));
#endif
#define WS_TIME 0x01
#define WS_SIGNAL 0x02
#define WS_ALTERNATE 0x01
#define WS_ANNOUNCE 0x02
#define WS_TZ 0x0c
#define WS_MET 0x08
#define WS_MEST 0x04
#define WS_LEAP 0x10
static u_long cvt_schmid P((unsigned char *, int, struct format *, clocktime_t *, void *));
static unsigned long inp_schmid P((parse_t *, unsigned int, timestamp_t *));
clockformat_t clock_schmid =
{
inp_schmid,
cvt_schmid,
0,
0,
"Schmid",
12,
0,
};
static u_long
cvt_schmid(
unsigned char *buffer,
int size,
struct format *format,
clocktime_t *clock_time,
void *local
)
{
if ((size != 11) || (buffer[10] != (unsigned char)'\375'))
{
return CVT_NONE;
}
else
{
if (buffer[0] > 23 || buffer[1] > 59 || buffer[2] > 59 || buffer[3] > 9)
{
return CVT_FAIL|CVT_BADTIME;
}
else
if (buffer[4] < 1 || buffer[4] > 31 || buffer[5] < 1 || buffer[5] > 12
|| buffer[6] > 99)
{
return CVT_FAIL|CVT_BADDATE;
}
else
{
clock_time->hour = buffer[0];
clock_time->minute = buffer[1];
clock_time->second = buffer[2];
clock_time->usecond = buffer[3] * 100000;
clock_time->day = buffer[4];
clock_time->month = buffer[5];
clock_time->year = buffer[6];
clock_time->flags = 0;
switch (buffer[8] & WS_TZ)
{
case WS_MET:
clock_time->utcoffset = -1*60*60;
break;
case WS_MEST:
clock_time->utcoffset = -2*60*60;
clock_time->flags |= PARSEB_DST;
break;
default:
return CVT_FAIL|CVT_BADFMT;
}
if (!(buffer[7] & WS_TIME))
{
clock_time->flags |= PARSEB_POWERUP;
}
if (!(buffer[7] & WS_SIGNAL))
{
clock_time->flags |= PARSEB_NOSYNC;
}
if (buffer[7] & WS_SIGNAL)
{
if (buffer[8] & WS_ALTERNATE)
{
clock_time->flags |= PARSEB_ALTERNATE;
}
if (buffer[8] & WS_ANNOUNCE)
{
clock_time->flags |= PARSEB_ANNOUNCE;
}
if (buffer[8] & WS_LEAP)
{
clock_time->flags |= PARSEB_LEAPADD;
}
}
clock_time->flags |= PARSEB_S_LEAP|PARSEB_S_ANTENNA;
return CVT_OK;
}
}
}
static u_long
inp_schmid(
parse_t *parseio,
unsigned int ch,
timestamp_t *tstamp
)
{
unsigned int rtc;
parseprintf(DD_PARSE, ("inp_schmid(0x%lx, 0x%x, ...)\n", (long)parseio, ch));
switch (ch)
{
case 0xFD:
parseprintf(DD_PARSE, ("mbg_input: ETX seen\n"));
if ((rtc = parse_addchar(parseio, ch)) == PARSE_INP_SKIP)
return parse_end(parseio);
else
return rtc;
default:
return parse_addchar(parseio, ch);
}
}
#else
int clk_schmid_bs;
#endif