1 /*
2 * DVB time functions
3 * Copyright (C) 2010-2011 Unix Solutions Ltd.
4 *
5 * Released under MIT license.
6 * See LICENSE-MIT.txt for license terms.
7 */
8 #include <stdio.h>
9 #include <unistd.h>
10 #include <netdb.h>
11 #include <stdlib.h>
12 #include <string.h>
13 #include <time.h>
14
15 #include "tsfuncs.h"
16
ts_time_encode_bcd(int duration_sec)17 uint32_t ts_time_encode_bcd(int duration_sec) {
18 int t_sec, t_min, t_hour, ret;
19 t_sec = duration_sec % 60;
20 t_min = (duration_sec - t_sec) / 60;
21 t_hour = (t_min - t_min % 60) / 60;
22 t_min = t_min - t_hour * 60;
23
24 ret = dec2bcd(t_hour) << 16;
25 ret |= dec2bcd(t_min ) << 8;
26 ret |= dec2bcd(t_sec );
27
28 return ret;
29 }
30
ts_time_decode_bcd(int duration_bcd,int * duration_sec,int * hour,int * min,int * sec)31 void ts_time_decode_bcd(int duration_bcd, int *duration_sec, int *hour, int *min, int *sec) {
32 *hour = bcd2dec( (duration_bcd &~ 0xff00ffff) >> 16 ); // 11111111 xxxxxxxx xxxxxxxx
33 *min = bcd2dec( (duration_bcd &~ 0xffff00ff) >> 8 ); // xxxxxxxx 11111111 xxxxxxxx
34 *sec = bcd2dec( (duration_bcd &~ 0xffffff00) ); // xxxxxxxx xxxxxxxx 11111111
35 if (duration_sec)
36 *duration_sec = *hour * 3600 + *min * 60 + *sec;
37 }
38
ts_time_encode_mjd(uint16_t * mjd,uint32_t * bcd,time_t * ts,struct tm * tm)39 void ts_time_encode_mjd(uint16_t *mjd, uint32_t *bcd, time_t *ts, struct tm *tm) {
40 struct tm *ltm = tm;
41 if (!ts && !tm)
42 return;
43 if (ts) { // Decompose ts into struct tm
44 struct tm dectm;
45 gmtime_r(ts, &dectm);
46 ltm = &dectm;
47 }
48 if (!ltm) // Paranoia
49 return;
50 if (mjd) { // Encode ymd into mjd
51 int Y = ltm->tm_year; // 1900 + Y gives the real year
52 int M = ltm->tm_mon + 1;
53 int D = ltm->tm_mday;
54 int L = (M == 1 || M == 2) ? 1 : 0;
55 *mjd = 14956 + D + (int)((Y - L) * 365.25) + (int)((M + 1 + L * 12) * 30.6001);
56 }
57 if (bcd) { // Encode hms into bcd
58 *bcd = 0;
59 *bcd = dec2bcd(ltm->tm_hour) << 16;
60 *bcd |= dec2bcd(ltm->tm_min ) << 8;
61 *bcd |= dec2bcd(ltm->tm_sec );
62 }
63 }
64
ts_time_decode_mjd(uint16_t mjd,uint32_t bcd,struct tm * tm)65 time_t ts_time_decode_mjd(uint16_t mjd, uint32_t bcd, struct tm *tm) {
66 int year = 0, month = 0, day = 0;
67 int hour = 0, min = 0, sec = 0;
68 time_t ret = 0;
69 if (mjd > 0) {
70 long tmp;
71 // Copied from ETSI EN 300 468 (ANNEX C)
72 year = (int)((mjd - 15078.2) / 365.25);
73 month = (int)((mjd - 14956.1 - (int)(year * 365.25)) / 30.6001);
74 day = mjd - 14956 - (int)(year * 365.25) - (int)(month * 30.6001);
75 tmp = (month == 14 || month == 15) ? 1 : 0;
76 year = year + tmp;
77 month = month - 1 - tmp * 12;
78 year += 1900;
79 }
80 if (bcd > 0) {
81 ts_time_decode_bcd(bcd, NULL, &hour, &min, &sec);
82 }
83 if (tm) {
84 memset(tm, 0, sizeof(struct tm));
85 tm->tm_year = year - 1900;
86 tm->tm_mon = month - 1;
87 tm->tm_mday = day;
88 tm->tm_hour = hour;
89 tm->tm_min = min;
90 tm->tm_sec = sec;
91 ret = timegm(tm);
92 }
93 return ret;
94 }
95