1 /* 2 * COPYRIGHT: See COPYING in the top level directory 3 * PROJECT: ReactOS net command 4 * FILE: base/applications/network/net/cmdGroup.c 5 * PROGRAMMERS: Eric Kohl <eric.kohl@reactos.org> 6 */ 7 8 #include "net.h" 9 10 11 static 12 int 13 CompareInfo(const void *a, 14 const void *b) 15 { 16 return _wcsicmp(((PGROUP_INFO_0)a)->grpi0_name, 17 ((PGROUP_INFO_0)b)->grpi0_name); 18 } 19 20 21 static 22 NET_API_STATUS 23 EnumerateGroups(VOID) 24 { 25 PGROUP_INFO_0 pBuffer = NULL; 26 PSERVER_INFO_100 pServer = NULL; 27 DWORD dwRead = 0, dwTotal = 0; 28 DWORD i; 29 DWORD_PTR ResumeHandle = 0; 30 NET_API_STATUS Status; 31 32 Status = NetServerGetInfo(NULL, 33 100, 34 (LPBYTE*)&pServer); 35 if (Status != NERR_Success) 36 return Status; 37 38 ConPuts(StdOut, L"\n"); 39 ConResPrintf(StdOut, IDS_GROUP_GROUPS, pServer->sv100_name); 40 ConPuts(StdOut, L"\n\n"); 41 PrintPadding(L'-', 79); 42 ConPuts(StdOut, L"\n"); 43 44 NetApiBufferFree(pServer); 45 46 Status = NetGroupEnum(NULL, 47 0, 48 (LPBYTE*)&pBuffer, 49 MAX_PREFERRED_LENGTH, 50 &dwRead, 51 &dwTotal, 52 &ResumeHandle); 53 if (Status != NERR_Success) 54 return Status; 55 56 qsort(pBuffer, 57 dwRead, 58 sizeof(PGROUP_INFO_0), 59 CompareInfo); 60 61 for (i = 0; i < dwRead; i++) 62 { 63 if (pBuffer[i].grpi0_name) 64 ConPrintf(StdOut, L"*%s\n", pBuffer[i].grpi0_name); 65 } 66 67 NetApiBufferFree(pBuffer); 68 69 return NERR_Success; 70 } 71 72 73 static 74 NET_API_STATUS 75 DisplayGroup(LPWSTR lpGroupName) 76 { 77 PGROUP_INFO_1 pGroupInfo = NULL; 78 PGROUP_USERS_INFO_0 pUsers = NULL; 79 LPWSTR *pNames = NULL; 80 DWORD dwRead = 0; 81 DWORD dwTotal = 0; 82 DWORD_PTR ResumeHandle = 0; 83 DWORD i; 84 INT nPaddedLength = 15; 85 NET_API_STATUS Status; 86 87 Status = NetGroupGetInfo(NULL, 88 lpGroupName, 89 1, 90 (LPBYTE*)&pGroupInfo); 91 if (Status != NERR_Success) 92 return Status; 93 94 Status = NetGroupGetUsers(NULL, 95 lpGroupName, 96 0, 97 (LPBYTE*)&pUsers, 98 MAX_PREFERRED_LENGTH, 99 &dwRead, 100 &dwTotal, 101 &ResumeHandle); 102 if (Status != NERR_Success) 103 goto done; 104 105 pNames = RtlAllocateHeap(RtlGetProcessHeap(), 106 HEAP_ZERO_MEMORY, 107 dwRead * sizeof(LPWSTR)); 108 if (pNames == NULL) 109 { 110 Status = ERROR_OUTOFMEMORY; 111 goto done; 112 } 113 114 for (i = 0; i < dwRead; i++) 115 { 116 pNames[i] = pUsers[i].grui0_name; 117 } 118 119 PrintPaddedResourceString(IDS_GROUP_NAME, nPaddedLength); 120 ConPrintf(StdOut, L"%s\n", pGroupInfo->grpi1_name); 121 122 PrintPaddedResourceString(IDS_GROUP_COMMENT, nPaddedLength); 123 ConPrintf(StdOut, L"%s\n", pGroupInfo->grpi1_comment); 124 125 ConPuts(StdOut, L"\n"); 126 127 ConResPuts(StdOut, IDS_GROUP_MEMBERS); 128 ConPuts(StdOut, L"\n\n"); 129 130 PrintPadding(L'-', 79); 131 ConPuts(StdOut, L"\n"); 132 133 for (i = 0; i < dwRead; i++) 134 { 135 if (pNames[i]) 136 ConPrintf(StdOut, L"%s\n", pNames[i]); 137 } 138 139 done: 140 if (pNames != NULL) 141 RtlFreeHeap(RtlGetProcessHeap(), 0, pNames); 142 143 if (pUsers != NULL) 144 NetApiBufferFree(pUsers); 145 146 if (pGroupInfo != NULL) 147 NetApiBufferFree(pGroupInfo); 148 149 return Status; 150 } 151 152 153 INT 154 cmdGroup( 155 INT argc, 156 WCHAR **argv) 157 { 158 INT i, j; 159 INT result = 0; 160 ULONG dwUserCount = 0; 161 BOOL bAdd = FALSE; 162 BOOL bDelete = FALSE; 163 #if 0 164 BOOL bDomain = FALSE; 165 #endif 166 PWSTR pGroupName = NULL; 167 PWSTR pComment = NULL; 168 PWSTR *pUsers = NULL; 169 GROUP_INFO_0 Info0; 170 GROUP_INFO_1 Info1; 171 GROUP_INFO_1002 Info1002; 172 NET_API_STATUS Status; 173 174 if (argc == 2) 175 { 176 Status = EnumerateGroups(); 177 ConPrintf(StdOut, L"Status: %lu\n", Status); 178 return 0; 179 } 180 else if (argc == 3) 181 { 182 Status = DisplayGroup(argv[2]); 183 ConPrintf(StdOut, L"Status: %lu\n", Status); 184 return 0; 185 } 186 187 i = 2; 188 if (argv[i][0] != L'/') 189 { 190 pGroupName = argv[i]; 191 i++; 192 } 193 194 for (j = i; j < argc; j++) 195 { 196 if (argv[j][0] == L'/') 197 break; 198 199 dwUserCount++; 200 } 201 202 if (dwUserCount > 0) 203 { 204 pUsers = RtlAllocateHeap(RtlGetProcessHeap(), 205 HEAP_ZERO_MEMORY, 206 dwUserCount * sizeof(PGROUP_USERS_INFO_0)); 207 if (pUsers == NULL) 208 return 0; 209 } 210 211 j = 0; 212 for (; i < argc; i++) 213 { 214 if (argv[i][0] == L'/') 215 break; 216 217 pUsers[j] = argv[i]; 218 j++; 219 } 220 221 for (; i < argc; i++) 222 { 223 if (_wcsicmp(argv[i], L"/help") == 0) 224 { 225 ConResPuts(StdOut, IDS_GENERIC_SYNTAX); 226 PrintNetMessage(MSG_GROUP_SYNTAX); 227 PrintNetMessage(MSG_GROUP_HELP); 228 return 0; 229 } 230 else if (_wcsicmp(argv[i], L"/add") == 0) 231 { 232 bAdd = TRUE; 233 } 234 else if (_wcsicmp(argv[i], L"/delete") == 0) 235 { 236 bDelete = TRUE; 237 } 238 else if (_wcsnicmp(argv[i], L"/comment:", 9) == 0) 239 { 240 pComment = &argv[i][9]; 241 } 242 else if (_wcsicmp(argv[i], L"/domain") == 0) 243 { 244 ConResPrintf(StdErr, IDS_ERROR_OPTION_NOT_SUPPORTED, L"/DOMAIN"); 245 #if 0 246 bDomain = TRUE; 247 #endif 248 } 249 else 250 { 251 PrintErrorMessage(3506/*, argv[i]*/); 252 result = 1; 253 goto done; 254 } 255 } 256 257 if (pGroupName == NULL) 258 { 259 result = 1; 260 goto done; 261 } 262 263 if (bAdd && bDelete) 264 { 265 result = 1; 266 goto done; 267 } 268 269 if (pUsers == NULL) 270 { 271 if (!bAdd && !bDelete && pComment != NULL) 272 { 273 /* Set group comment */ 274 Info1002.grpi1002_comment = pComment; 275 Status = NetGroupSetInfo(NULL, 276 pGroupName, 277 1002, 278 (LPBYTE)&Info1002, 279 NULL); 280 ConPrintf(StdOut, L"Status: %lu\n", Status); 281 } 282 else if (bAdd && !bDelete) 283 { 284 /* Add the group */ 285 if (pComment == NULL) 286 { 287 Info0.grpi0_name = pGroupName; 288 } 289 else 290 { 291 Info1.grpi1_name = pGroupName; 292 Info1.grpi1_comment = pComment; 293 } 294 295 Status = NetGroupAdd(NULL, 296 (pComment == NULL) ? 0 : 1, 297 (pComment == NULL) ? (LPBYTE)&Info0 : (LPBYTE)&Info1, 298 NULL); 299 ConPrintf(StdOut, L"Status: %lu\n", Status); 300 } 301 else if (!bAdd && bDelete && pComment == NULL) 302 { 303 /* Delete the group */ 304 Status = NetGroupDel(NULL, 305 pGroupName); 306 ConPrintf(StdOut, L"Status: %lu\n", Status); 307 } 308 else 309 { 310 result = 1; 311 } 312 } 313 else 314 { 315 if (bAdd && !bDelete && pComment == NULL) 316 { 317 /* Add group user */ 318 for (i = 0; i < dwUserCount; i++) 319 { 320 Status = NetGroupAddUser(NULL, 321 pGroupName, 322 pUsers[i]); 323 if (Status != NERR_Success) 324 break; 325 } 326 ConPrintf(StdOut, L"Status: %lu\n", Status); 327 } 328 else if (!bAdd && bDelete && pComment == NULL) 329 { 330 /* Delete group members */ 331 for (i = 0; i < dwUserCount; i++) 332 { 333 Status = NetGroupDelUser(NULL, 334 pGroupName, 335 pUsers[i]); 336 if (Status != NERR_Success) 337 break; 338 } 339 ConPrintf(StdOut, L"Status: %lu\n", Status); 340 } 341 else 342 { 343 result = 1; 344 } 345 } 346 347 done: 348 if (pUsers != NULL) 349 RtlFreeHeap(RtlGetProcessHeap(), 0, pUsers); 350 351 if (result != 0) 352 { 353 ConResPuts(StdOut, IDS_GENERIC_SYNTAX); 354 PrintNetMessage(MSG_GROUP_SYNTAX); 355 } 356 357 return result; 358 } 359 360 /* EOF */ 361