1 /*
2 * PROJECT: ReactOS NetSh
3 * LICENSE: GPL-2.0-or-later (https://spdx.org/licenses/GPL-2.0-or-later)
4 * PURPOSE: Network Shell main file
5 * COPYRIGHT: Copyright 2023 Eric Kohl <eric.kohl@reactos.org>
6 */
7
8 /* INCLUDES *******************************************************************/
9
10 #include "precomp.h"
11
12 #define NDEBUG
13 #include <debug.h>
14
15 /* FUNCTIONS ******************************************************************/
16
17 BOOL
RunScript(_In_ LPCWSTR filename)18 RunScript(
19 _In_ LPCWSTR filename)
20 {
21 FILE *script;
22 WCHAR tmp_string[MAX_STRING_SIZE];
23
24 /* Open the file for processing */
25 script = _wfopen(filename, L"r");
26 if (script == NULL)
27 {
28 ConResPrintf(StdErr, IDS_OPEN_FAILED, filename);
29 return FALSE;
30 }
31
32 /* Read and process the script */
33 while (fgetws(tmp_string, MAX_STRING_SIZE, script) != NULL)
34 {
35 if (InterpretScript(tmp_string) == FALSE)
36 {
37 fclose(script);
38 return FALSE;
39 }
40 }
41
42 /* Close the file */
43 fclose(script);
44
45 return TRUE;
46 }
47
48 /*
49 * wmain():
50 * Main entry point of the application.
51 */
52 int
wmain(_In_ int argc,_In_ const LPWSTR argv[])53 wmain(
54 _In_ int argc,
55 _In_ const LPWSTR argv[])
56 {
57 LPCWSTR tmpBuffer = NULL;
58 LPCWSTR pszFileName = NULL;
59 int index;
60 int result = EXIT_SUCCESS;
61
62 DPRINT("main()\n");
63
64 /* Initialize the Console Standard Streams */
65 ConInitStdStreams();
66
67 /* FIXME: Init code goes here */
68 CreateRootContext();
69 LoadHelpers();
70
71 if (argc < 2)
72 {
73 /* If there are no command arguments, then go straight to the interpreter */
74 InterpretInteractive();
75 }
76 else
77 {
78 /* If there are command arguments, then process them */
79 for (index = 1; index < argc; index++)
80 {
81 if ((argv[index][0] == '/')||
82 (argv[index][0] == '-'))
83 {
84 tmpBuffer = argv[index] + 1;
85 }
86 else
87 {
88 if (pszFileName != NULL)
89 {
90 ConResPuts(StdOut, IDS_APP_USAGE);
91 result = EXIT_FAILURE;
92 goto done;
93 }
94
95 /* Run a command from the command line */
96 if (InterpretCommand((LPWSTR*)&argv[index], argc - index) == FALSE)
97 result = EXIT_FAILURE;
98 goto done;
99 }
100
101 if (_wcsicmp(tmpBuffer, L"?") == 0)
102 {
103 /* Help option */
104 ConResPuts(StdOut, IDS_APP_USAGE);
105 result = EXIT_SUCCESS;
106 goto done;
107 }
108 else if (_wcsicmp(tmpBuffer, L"a") == 0)
109 {
110 /* Aliasfile option */
111 if ((index + 1) < argc)
112 {
113 index++;
114 ConPuts(StdOut, L"\nThe -a option is not implemented yet\n");
115 // aliasfile = argv[index];
116 }
117 else
118 {
119 ConResPuts(StdOut, IDS_APP_USAGE);
120 result = EXIT_FAILURE;
121 }
122 }
123 else if (_wcsicmp(tmpBuffer, L"c") == 0)
124 {
125 /* Context option */
126 if ((index + 1) < argc)
127 {
128 index++;
129 ConPuts(StdOut, L"\nThe -c option is not implemented yet\n");
130 // context = argv[index];
131 }
132 else
133 {
134 ConResPuts(StdOut, IDS_APP_USAGE);
135 result = EXIT_FAILURE;
136 }
137 }
138 else if (_wcsicmp(tmpBuffer, L"f") == 0)
139 {
140 /* File option */
141 if ((index + 1) < argc)
142 {
143 index++;
144 pszFileName = argv[index];
145 }
146 else
147 {
148 ConResPuts(StdOut, IDS_APP_USAGE);
149 result = EXIT_FAILURE;
150 }
151 }
152 else if (_wcsicmp(tmpBuffer, L"r") == 0)
153 {
154 /* Remote option */
155 if ((index + 1) < argc)
156 {
157 index++;
158 ConPuts(StdOut, L"\nThe -r option is not implemented yet\n");
159 // remote = argv[index];
160 }
161 else
162 {
163 ConResPuts(StdOut, IDS_APP_USAGE);
164 result = EXIT_FAILURE;
165 }
166 }
167 else
168 {
169 /* Invalid command */
170 ConResPrintf(StdOut, IDS_INVALID_COMMAND, argv[index]);
171 result = EXIT_FAILURE;
172 goto done;
173 }
174 }
175
176 /* Now we process the filename if it exists */
177 if (pszFileName != NULL)
178 {
179 if (RunScript(pszFileName) == FALSE)
180 {
181 result = EXIT_FAILURE;
182 goto done;
183 }
184 }
185 }
186
187 done:
188 /* FIXME: Cleanup code goes here */
189 UnloadHelpers();
190
191 return result;
192 }
193
194
195 DWORD
196 WINAPI
MatchEnumTag(_In_ HANDLE hModule,_In_ LPCWSTR pwcArg,_In_ DWORD dwNumArg,_In_ const TOKEN_VALUE * pEnumTable,_Out_ PDWORD pdwValue)197 MatchEnumTag(
198 _In_ HANDLE hModule,
199 _In_ LPCWSTR pwcArg,
200 _In_ DWORD dwNumArg,
201 _In_ const TOKEN_VALUE *pEnumTable,
202 _Out_ PDWORD pdwValue)
203 {
204 DPRINT1("MatchEnumTag()\n");
205 return 0;
206 }
207
208 BOOL
209 WINAPI
MatchToken(_In_ LPCWSTR pwszUserToken,_In_ LPCWSTR pwszCmdToken)210 MatchToken(
211 _In_ LPCWSTR pwszUserToken,
212 _In_ LPCWSTR pwszCmdToken)
213 {
214 DPRINT1("MatchToken %S %S\n", pwszUserToken, pwszCmdToken);
215 return (_wcsicmp(pwszUserToken, pwszCmdToken) == 0) ? TRUE : FALSE;
216 }
217
218 DWORD
219 CDECL
PrintError(_In_opt_ HANDLE hModule,_In_ DWORD dwErrId,...)220 PrintError(
221 _In_opt_ HANDLE hModule,
222 _In_ DWORD dwErrId,
223 ...)
224 {
225 DPRINT1("PrintError()\n");
226 return 1;
227 }
228
229 DWORD
230 CDECL
PrintMessageFromModule(_In_ HANDLE hModule,_In_ DWORD dwMsgId,...)231 PrintMessageFromModule(
232 _In_ HANDLE hModule,
233 _In_ DWORD dwMsgId,
234 ...)
235 {
236 DPRINT1("PrintMessageFromModule()\n");
237 return 1;
238 }
239
240 DWORD
241 CDECL
PrintMessage(_In_ LPCWSTR pwszFormat,...)242 PrintMessage(
243 _In_ LPCWSTR pwszFormat,
244 ...)
245 {
246 INT Length;
247 va_list ap;
248
249 va_start(ap, pwszFormat);
250 Length = ConPrintf(StdOut, pwszFormat);
251 va_end(ap);
252
253 return Length;
254 }
255