Reactos
1/*
2 * DATE.C - date internal command.
3 *
4 *
5 * History:
6 *
7 * 08 Jul 1998 (John P. Price)
8 * started.
9 *
10 * 20 Jul 1998 (John P. Price)
11 * corrected number of days for December from 30 to 31.
12 * (Thanx to Steffen Kaiser for bug report)
13 *
14 * 27-Jul-1998 (John P Price <linux-guru@gcfl.net>)
15 * added config.h include
16 *
17 * 29-Jul-1998 (Rob Lake)
18 * fixed stand-alone mode.
19 * Added Pacific C compatible dos_getdate functions
20 *
21 * 09-Jan-1999 (Eric Kohl)
22 * Added locale support
23 *
24 * 23-Jan-1999 (Eric Kohl)
25 * Unicode and redirection safe!
26 *
27 * 04-Feb-1999 (Eric Kohl)
28 * Fixed date input bug.
29 *
30 * 03-Apr-2005 (Magnus Olsen <magnus@greatlord.com>)
31 * Remove all hardcoded strings in En.rc
32 */
33
34#include "precomp.h"
35
36#ifdef INCLUDE_CMD_DATE
37
38
39static WORD awMonths[2][13] =
40{
41 {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31},
42 {0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}
43};
44
45
46static VOID
47PromptDateString(VOID)
48{
49 switch (nDateFormat)
50 {
51 case 0: /* mmddyy */
52 default:
53 ConOutResPrintf(STRING_DATE_HELP1, cDateSeparator, cDateSeparator);
54 break;
55
56 case 1: /* ddmmyy */
57 ConOutResPrintf(STRING_DATE_HELP2, cDateSeparator, cDateSeparator);
58 break;
59
60 case 2: /* yymmdd */
61 ConOutResPrintf(STRING_DATE_HELP3, cDateSeparator, cDateSeparator);
62 break;
63 }
64}
65
66static BOOL
67ReadNumber (LPTSTR *s, LPWORD lpwValue)
68{
69 if (_istdigit (**s))
70 {
71 while (_istdigit (**s))
72 {
73 *lpwValue = *lpwValue * 10 + **s - _T('0');
74 (*s)++;
75 }
76 return TRUE;
77 }
78 return FALSE;
79}
80
81static BOOL
82ReadSeparator (LPTSTR *s)
83{
84 if (**s == _T('/') || **s == _T('-') || **s == cDateSeparator)
85 {
86 (*s)++;
87 return TRUE;
88 }
89 return FALSE;
90}
91
92static BOOL
93ParseDate (LPTSTR s)
94{
95 SYSTEMTIME d;
96 unsigned char leap;
97 LPTSTR p = s;
98
99 if (!*s)
100 return TRUE;
101
102 GetLocalTime (&d);
103
104 d.wYear = 0;
105 d.wDay = 0;
106 d.wMonth = 0;
107
108 switch (nDateFormat)
109 {
110 case 0: /* mmddyy */
111 default:
112 if (!ReadNumber (&p, &d.wMonth))
113 return FALSE;
114 if (!ReadSeparator (&p))
115 return FALSE;
116 if (!ReadNumber (&p, &d.wDay))
117 return FALSE;
118 if (!ReadSeparator (&p))
119 return FALSE;
120 if (!ReadNumber (&p, &d.wYear))
121 return FALSE;
122 break;
123
124 case 1: /* ddmmyy */
125 if (!ReadNumber (&p, &d.wDay))
126 return FALSE;
127 if (!ReadSeparator (&p))
128 return FALSE;
129 if (!ReadNumber (&p, &d.wMonth))
130 return FALSE;
131 if (!ReadSeparator (&p))
132 return FALSE;
133 if (!ReadNumber (&p, &d.wYear))
134 return FALSE;
135 break;
136
137 case 2: /* yymmdd */
138 if (!ReadNumber (&p, &d.wYear))
139 return FALSE;
140 if (!ReadSeparator (&p))
141 return FALSE;
142 if (!ReadNumber (&p, &d.wMonth))
143 return FALSE;
144 if (!ReadSeparator (&p))
145 return FALSE;
146 if (!ReadNumber (&p, &d.wDay))
147 return FALSE;
148 break;
149 }
150
151 /* if only entered two digits: */
152 /* assume 2000's if value less than 80 */
153 /* assume 1900's if value greater or equal 80 */
154 if (d.wYear <= 99)
155 {
156 if (d.wYear >= 80)
157 d.wYear = 1900 + d.wYear;
158 else
159 d.wYear = 2000 + d.wYear;
160 }
161
162 leap = (!(d.wYear % 4) && (d.wYear % 100)) || !(d.wYear % 400);
163
164 if ((d.wMonth >= 1 && d.wMonth <= 12) &&
165 (d.wDay >= 1 && d.wDay <= awMonths[leap][d.wMonth]) &&
166 (d.wYear >= 1980 && d.wYear <= 2099))
167 {
168 SetLocalTime (&d);
169 return TRUE;
170 }
171
172 return FALSE;
173}
174
175
176INT cmd_date(LPTSTR param)
177{
178 LPTSTR* arg;
179 INT argc;
180 INT i;
181 BOOL bPrompt = TRUE;
182 INT nDateString = -1;
183 TCHAR szDate[40];
184
185 if (!_tcsncmp(param, _T("/?"), 2))
186 {
187 ConOutResPaging(TRUE, STRING_DATE_HELP4);
188 return 0;
189 }
190
191 nErrorLevel = 0;
192
193 /* Build the parameter array */
194 arg = split(param, &argc, FALSE, FALSE);
195
196 /* Check for options */
197 for (i = 0; i < argc; i++)
198 {
199 if (bEnableExtensions && (_tcsicmp(arg[i], _T("/T")) == 0))
200 bPrompt = FALSE;
201
202 if ((*arg[i] != _T('/')) && (nDateString == -1))
203 nDateString = i;
204 }
205
206 if (nDateString == -1)
207 {
208 ConOutResPuts(STRING_DATE_NOW);
209 ConOutPrintf(_T("%s\n"), GetDateString());
210 }
211
212 if (!bPrompt)
213 {
214 freep(arg);
215 return 0;
216 }
217
218 while (TRUE)
219 {
220 if (nDateString == -1)
221 {
222 PromptDateString();
223 ConInString(szDate, ARRAYSIZE(szDate));
224
225 TRACE("\'%s\'\n", debugstr_aw(szDate));
226
227 while (*szDate && szDate[_tcslen(szDate) - 1] < _T(' '))
228 szDate[_tcslen(szDate) - 1] = _T('\0');
229
230 if (ParseDate(szDate))
231 {
232 freep(arg);
233 return 0;
234 }
235 }
236 else
237 {
238 if (ParseDate(arg[nDateString]))
239 {
240 freep(arg);
241 return 0;
242 }
243
244 /* Force input the next time around */
245 nDateString = -1;
246 }
247
248 ConErrResPuts(STRING_DATE_ERROR);
249 nErrorLevel = 1;
250 }
251
252 freep(arg);
253 return 0;
254}
255#endif /* INCLUDE_CMD_DATE */
256
257/* EOF */