2 * ReactOS Win32 Applications
3 * Copyright (C) 2005 ReactOS Team
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 * COPYRIGHT : See COPYING in the top level directory
22 * PROJECT : ReactOS/Win32 Session Manager Control Tool
23 * FILE : subsys/system/sm/sm.c
24 * PROGRAMMER: Emanuele Aliberti (ea@reactos.com)
33 #define NTOS_MODE_USER
34 #include <ndk/ntndk.h>
36 #include <sm/helper.h>
38 VOID
PrintWin32Error(PWCHAR
,DWORD
); /* win32err.c */
40 #define SM_CMD(n) cmd_##n
41 #define SM_CMD_DECL(n) int SM_CMD(n)(int argc, char * argv[])
42 #define SM_CMD_CALL(n,c,v) SM_CMD(n)((c),(v))
44 HANDLE hSmApiPort
= (HANDLE
) 0;
46 VOID STDCALL
PrintStatusError (NTSTATUS Status
)
48 DWORD Win32Error
= RtlNtStatusToDosError (Status
);
50 PrintWin32Error (L
"sm", Win32Error
);
53 typedef struct _SM_CMD_DESCRIPTOR
55 TCHAR Name
[RC_STRING_MAX_SIZE
];
56 int (*EntryPoint
)(int,TCHAR
**);
57 TCHAR Synopsis
[RC_STRING_MAX_SIZE
];
58 TCHAR Description
[RC_STRING_MAX_SIZE
];
60 } SM_CMD_DESCRIPTOR
, *PSM_CMD_DESCRIPTOR
;
66 SM_CMD_DECL(shutdown
);
68 /* internal commands directory */
69 SM_CMD_DESCRIPTOR Command
[] =
71 {"boot", SM_CMD(boot
), _T("boot subsystem_name"), _T("bootstrap an optional environment subsystem;")},
72 {"help", SM_CMD(help
), _T("help [command]"), _T("print help for command;")},
73 {"info", SM_CMD(info
), _T("info [subsystem_id]"), _T("print information about a booted subsystem\n"
74 "if subsystem_id is omitted, a list of booted\n"
75 "environment subsystems is printed.")},
76 {"reboot", SM_CMD(reboot
), _T("reboot subsystem_id"), _T("reboot an optional environment subsystem;")},
77 {"shutdown", SM_CMD(shutdown
), _T("shutdown subsystem_id"), _T("shutdown an optional environment subsystem;")},
80 TCHAR UsageMessage
[RC_STRING_MAX_SIZE
];
81 void loadlang(PSM_CMD_DESCRIPTOR
);
83 PSM_CMD_DESCRIPTOR
LookupCommand (const TCHAR
* CommandName
)
86 const int command_count
= (sizeof Command
/ sizeof Command
[0]);
88 /* parse the command... */
90 for (i
=0; (i
< command_count
); i
++)
92 if (0 == _tcscmp(CommandName
, Command
[i
].Name
))
97 if (i
== command_count
)
99 LoadString( GetModuleHandle(NULL
), IDS_Unknown
, (LPTSTR
) UsageMessage
,RC_STRING_MAX_SIZE
);
101 _ftprintf(stderr
, _T("%s '%s'.\n"), UsageMessage
, CommandName
);
104 return & Command
[i
];
111 int rc
= EXIT_SUCCESS
;
112 ANSI_STRING ProgramA
;
113 UNICODE_STRING ProgramW
;
114 NTSTATUS Status
= STATUS_SUCCESS
;
119 RtlInitAnsiString (& ProgramA
, argv
[2]);
120 RtlAnsiStringToUnicodeString (& ProgramW
, & ProgramA
, TRUE
);
121 Status
= SmExecuteProgram (hSmApiPort
, & ProgramW
);
122 RtlFreeUnicodeString (& ProgramW
);
125 Status
= SmExecuteProgram (hSmApiPort
, & ProgramW
);
127 if (STATUS_SUCCESS
!= Status
)
129 PrintStatusError (Status
);
136 return SM_CMD_CALL(help
,3,argv
);
144 PSM_CMD_DESCRIPTOR cmd
= NULL
;
145 int rc
= EXIT_SUCCESS
;
150 for (i
=0; (i
< (sizeof Command
/ sizeof Command
[0])); i
++)
152 _tprintf(_T("%s\n"), Command
[i
].Synopsis
);
156 cmd
= LookupCommand (argv
[2]);
162 _tprintf(_T("%s\n%s\n\n%s\n"),
173 int rc
= EXIT_SUCCESS
;
174 NTSTATUS Status
= STATUS_SUCCESS
;
175 SM_INFORMATION_CLASS InformationClass
= SmBasicInformation
;
177 SM_BASIC_INFORMATION bi
;
178 SM_SUBSYSTEM_INFORMATION ssi
;
180 ULONG DataLength
= 0;
181 ULONG ReturnDataLength
= 0;
184 RtlZeroMemory (& Info
, sizeof Info
);
187 case 2: /* sm info */
188 InformationClass
= SmBasicInformation
;
189 DataLength
= sizeof Info
.bi
;
191 case 3: /* sm info id */
192 InformationClass
= SmSubSystemInformation
;
193 DataLength
= sizeof Info
.ssi
;
194 Info
.ssi
.SubSystemId
= atol(argv
[2]);
200 Status
= SmQueryInformation (hSmApiPort
,
205 if (STATUS_SUCCESS
!= Status
)
207 PrintStatusError (Status
);
213 LoadString( GetModuleHandle(NULL
), IDS_SM1
, (LPTSTR
) UsageMessage
,RC_STRING_MAX_SIZE
);
214 _tprintf(UsageMessage
);
216 LoadString( GetModuleHandle(NULL
), IDS_SM2
, (LPTSTR
) UsageMessage
,RC_STRING_MAX_SIZE
);
217 for (i
= 0; i
< Info
.bi
.SubSystemCount
; i
++)
219 _tprintf(UsageMessage
,
220 Info
.bi
.SubSystem
[i
].Id
,
221 Info
.bi
.SubSystem
[i
].ProcessId
,
222 Info
.bi
.SubSystem
[i
].Flags
);
226 LoadString( GetModuleHandle(NULL
), IDS_ID
, (LPTSTR
) UsageMessage
,RC_STRING_MAX_SIZE
);
228 _tprintf (UsageMessage
, Info
.ssi
.SubSystemId
, Info
.ssi
.Flags
, Info
.ssi
.ProcessId
);
229 wprintf(L
" NSRootNode: '%s'\n", Info
.ssi
.NameSpaceRootNode
);
237 SM_CMD_DECL(shutdown
)
239 int rc
= EXIT_SUCCESS
;
241 LoadString( GetModuleHandle(NULL
), IDS_Not_Imp
, (LPTSTR
) UsageMessage
,RC_STRING_MAX_SIZE
);
243 _ftprintf(stderr
,UsageMessage
);
249 int rc
= SM_CMD(shutdown
)(argc
,argv
);
250 if(EXIT_SUCCESS
== rc
)
252 rc
= SM_CMD(boot
)(argc
,argv
);
257 /* print command's synopsys */
258 int print_synopsys (int argc
, TCHAR
*argv
[])
260 LoadString( GetModuleHandle(NULL
), IDS_Mangers
, (LPTSTR
) UsageMessage
,RC_STRING_MAX_SIZE
);
261 _ftprintf (stderr
, UsageMessage
);
263 LoadString( GetModuleHandle(NULL
), IDS_USING
, (LPTSTR
) UsageMessage
,RC_STRING_MAX_SIZE
);
264 _tprintf (UsageMessage
);
268 /* parse and execute */
269 int pande (int argc
, TCHAR
*argv
[])
271 PSM_CMD_DESCRIPTOR Command
= NULL
;
272 NTSTATUS Status
= STATUS_SUCCESS
;
274 /* Lookup the user command... */
275 Command
= LookupCommand (argv
[1]);
280 /* Connect to the SM in non-registering mode. */
281 Status
= SmConnectApiPort (0, 0, 0, & hSmApiPort
);
282 if (STATUS_SUCCESS
== Status
)
284 /* ...and execute it */
285 return Command
->EntryPoint (argc
, argv
);
287 LoadString( GetModuleHandle(NULL
), IDS_FAILS_MNG
, (LPTSTR
) UsageMessage
,RC_STRING_MAX_SIZE
);
288 _ftprintf (stderr
, UsageMessage
, Status
);
293 void loadlang(PSM_CMD_DESCRIPTOR cmd
)
296 if (cmd
==NULL
) return;
299 LoadString( GetModuleHandle(NULL
), IDS_boot
+i
, (LPTSTR
) &cmd
->Synopsis
[i
],RC_STRING_MAX_SIZE
);
303 int _tmain (int argc
, TCHAR
*argv
[])
308 ? print_synopsys (argc
, argv
)
309 : pande (argc
, argv
);