summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--source3/client/client.c10
-rw-r--r--source3/include/proto.h46
-rw-r--r--source3/lib/util.c18
-rw-r--r--source3/rpc_client/cli_samr.c18
-rw-r--r--source3/rpcclient/cmd_reg.c2
-rw-r--r--source3/rpcclient/cmd_samr.c1692
-rw-r--r--source3/rpcclient/rpcclient.c627
7 files changed, 1506 insertions, 907 deletions
diff --git a/source3/client/client.c b/source3/client/client.c
index 8264476947..8d1e73c5c2 100644
--- a/source3/client/client.c
+++ b/source3/client/client.c
@@ -1586,7 +1586,7 @@ static pstring result;
/* Iterator function for do_list() */
-void complete_process_file(file_info *f)
+static void complete_process_file(file_info *f)
{
/* Do we have a partial match? */
@@ -1607,7 +1607,7 @@ void complete_process_file(file_info *f)
/* Complete a remote file */
-char *complete_remote_file(char *text, int state)
+static char *complete_remote_file(char *text, int state)
{
int attribute = aDIR | aSYSTEM | aHIDDEN;
pstring mask;
@@ -1638,7 +1638,7 @@ char *complete_remote_file(char *text, int state)
/* Complete a smbclient command */
-char *complete_cmd(char *text, int state)
+static char *complete_cmd(char *text, int state)
{
static int cmd_index;
char *name;
@@ -1667,7 +1667,7 @@ char *complete_cmd(char *text, int state)
filename_completion_function() builtin to GNU readline for local
files. */
-char **completion_fn(char *text, int start, int end)
+static char **completion_fn(char *text, int start, int end)
{
int i, num_words, cmd_index;
char lastch = ' ';
@@ -1734,7 +1734,7 @@ char **completion_fn(char *text, int start, int end)
completions are found, we assign this stub completion function
to the rl_completion_entry_function variable. */
-char *complete_cmd_null(char *text, int state)
+static char *complete_cmd_null(char *text, int state)
{
return NULL;
}
diff --git a/source3/include/proto.h b/source3/include/proto.h
index f7f54ab2ed..1602e1d056 100644
--- a/source3/include/proto.h
+++ b/source3/include/proto.h
@@ -6,11 +6,6 @@
/*The following definitions come from client/client.c */
void do_list(const char *mask,uint16 attribute,void (*fn)(file_info *),BOOL rec, BOOL dirs);
-void complete_process_file(file_info *f);
-char *complete_remote_file(char *text, int state);
-char *complete_cmd(char *text, int state);
-char **completion_fn(char *text, int start, int end);
-char *complete_cmd_null(char *text, int state);
struct cli_state *do_connect(char *server, char *share, int smb_port);
/*The following definitions come from client/clitar.c */
@@ -486,6 +481,7 @@ void reg_get_subkey(char *full_keyname, char *key_name, char *subkey_name);
BOOL reg_split_key(const char *full_keyname, uint32 *reg_type, char *key_name);
BOOL become_user_permanently(uid_t uid, gid_t gid);
void free_char_array(uint32 num_entries, char **entries);
+BOOL add_chars_to_array(uint32 *len, char ***array, const char *name);
/*The following definitions come from lib/util_file.c */
@@ -3216,18 +3212,6 @@ void cmd_reg_shutdown(struct client_info *info);
/*The following definitions come from rpcclient/cmd_samr.c */
-void cmd_sam_ntchange_pwd(struct client_info *info);
-void cmd_sam_test(struct client_info *info);
-void cmd_sam_lookup_domain(struct client_info *info);
-void cmd_sam_del_aliasmem(struct client_info *info);
-void cmd_sam_delete_dom_alias(struct client_info *info);
-void cmd_sam_add_aliasmem(struct client_info *info);
-void cmd_sam_create_dom_user(struct client_info *info);
-void cmd_sam_create_dom_alias(struct client_info *info);
-void cmd_sam_del_groupmem(struct client_info *info);
-void cmd_sam_delete_dom_group(struct client_info *info);
-void cmd_sam_add_groupmem(struct client_info *info);
-void cmd_sam_create_dom_group(struct client_info *info);
uint32 sam_query_usergroups(struct cli_state *cli, uint16 fnum,
POLICY_HND *pol_dom,
char *domain,
@@ -3246,13 +3230,8 @@ int msrpc_sam_enum_users(struct client_info *info,
USER_INFO_FN(usr_inf_fn),
USER_MEM_FN(usr_grp_fn),
USER_MEM_FN(usr_als_fn));
-void cmd_sam_enum_users(struct client_info *info);
-void cmd_sam_query_user(struct client_info *info);
-void cmd_sam_query_dispinfo(struct client_info *info);
BOOL sam_query_dominfo(struct client_info *info, DOM_SID *sid1,
uint32 switch_value, SAM_UNK_CTR *ctr);
-void cmd_sam_query_dominfo(struct client_info *info);
-void cmd_sam_enum_aliases(struct client_info *info);
BOOL sam_query_groupmem(struct cli_state *cli, uint16 fnum,
POLICY_HND *pol_dom,
uint32 group_rid,
@@ -3266,6 +3245,25 @@ uint32 msrpc_sam_enum_groups(struct client_info *info,
GROUP_FN(grp_fn),
GROUP_INFO_FN(grp_inf_fn),
GROUP_MEM_FN(grp_mem_fn));
+void cmd_sam_ntchange_pwd(struct client_info *info);
+void cmd_sam_test(struct client_info *info);
+void cmd_sam_lookup_domain(struct client_info *info);
+void cmd_sam_del_aliasmem(struct client_info *info);
+void cmd_sam_delete_dom_alias(struct client_info *info);
+void cmd_sam_add_aliasmem(struct client_info *info);
+void cmd_sam_create_dom_user(struct client_info *info);
+void cmd_sam_create_dom_alias(struct client_info *info);
+void cmd_sam_del_groupmem(struct client_info *info);
+void cmd_sam_delete_dom_group(struct client_info *info);
+void cmd_sam_add_groupmem(struct client_info *info);
+void cmd_sam_create_dom_group(struct client_info *info);
+void cmd_sam_enum_users(struct client_info *info);
+void cmd_sam_query_groupmem(struct client_info *info);
+void cmd_sam_query_group(struct client_info *info);
+void cmd_sam_query_user(struct client_info *info);
+void cmd_sam_query_dispinfo(struct client_info *info);
+void cmd_sam_query_dominfo(struct client_info *info);
+void cmd_sam_enum_aliases(struct client_info *info);
void cmd_sam_enum_groups(struct client_info *info);
/*The following definitions come from rpcclient/cmd_srvsvc.c */
@@ -3396,10 +3394,6 @@ void display_sam_unk_ctr(FILE *out_hnd, enum action_type action,
/*The following definitions come from rpcclient/rpcclient.c */
void rpcclient_init(void);
-char *complete_remote_regenum(char *text, int state);
-char *complete_cmd(char *text, int state);
-char **completion_fn(char *text, int start, int end);
-char *complete_cmd_null(char *text, int state);
/*The following definitions come from smbd/blocking.c */
diff --git a/source3/lib/util.c b/source3/lib/util.c
index 1d318c40a1..9e13e819be 100644
--- a/source3/lib/util.c
+++ b/source3/lib/util.c
@@ -3243,3 +3243,21 @@ void free_char_array(uint32 num_entries, char **entries)
free(entries);
}
}
+
+BOOL add_chars_to_array(uint32 *len, char ***array, const char *name)
+{
+ if (len == NULL || array == NULL)
+ {
+ return False;
+ }
+
+ (*array) = (char**)Realloc((*array), ((*len)+1) * sizeof((*array)[0]));
+
+ if ((*array) != NULL)
+ {
+ (*array)[(*len)] = strdup(name);
+ (*len)++;
+ return True;
+ }
+ return True;
+}
diff --git a/source3/rpc_client/cli_samr.c b/source3/rpc_client/cli_samr.c
index ccf76eb943..16925b0806 100644
--- a/source3/rpc_client/cli_samr.c
+++ b/source3/rpc_client/cli_samr.c
@@ -1903,7 +1903,7 @@ BOOL samr_query_lookup_names(struct cli_state *cli, uint16 fnum,
{
/* report error code */
DEBUG(4,("SAMR_R_LOOKUP_NAMES: %s\n", get_nt_error_msg(r_o.status)));
- p = False;
+ p = r_o.status == 0x107;
}
if (p)
@@ -1998,19 +1998,23 @@ BOOL samr_query_lookup_rids(struct cli_state *cli, uint16 fnum,
r_o.num_types1 == r_o.num_names1)
{
uint32 i;
-
valid_query = True;
- *num_names = r_o.num_names1;
- (*names) = (char**)malloc((*num_names) * sizeof(**names));
- for (i = 0; (*names) != NULL && i < r_o.num_names1; i++)
+ (*num_names) = 0;
+ (*names) = NULL;
+
+ for (i = 0; i < r_o.num_names1; i++)
{
fstring tmp;
unistr2_to_ascii(tmp, &r_o.uni_name[i], sizeof(tmp)-1);
- (*names)[i] = strdup(tmp);
+ add_chars_to_array(num_names, names, tmp);
+ }
+
+ if ((*num_names) != 0)
+ {
+ (*type) = (uint32*)malloc((*num_names) * sizeof(**type));
}
- (*type) = (uint32*)malloc((*num_names) * sizeof(**type));
for (i = 0; (*type) != NULL && i < r_o.num_types1; i++)
{
(*type)[i] = r_o.type[i];
diff --git a/source3/rpcclient/cmd_reg.c b/source3/rpcclient/cmd_reg.c
index 4b0c0d8398..4d9cdf5f15 100644
--- a/source3/rpcclient/cmd_reg.c
+++ b/source3/rpcclient/cmd_reg.c
@@ -155,7 +155,7 @@ BOOL msrpc_reg_enum_key(struct cli_state *cli, const char* full_keyname,
uint32 unk_1a_response;
- DEBUG(5, ("reg_enum_key: cli->fd:%d\n", cli->fd));
+ DEBUG(5, ("reg_enum_key: %s\n", full_keyname));
/* open WINREG session. */
res = res ? cli_nt_session_open(cli, PIPE_WINREG, &fnum) : False;
diff --git a/source3/rpcclient/cmd_samr.c b/source3/rpcclient/cmd_samr.c
index e0438801f8..1656f017da 100644
--- a/source3/rpcclient/cmd_samr.c
+++ b/source3/rpcclient/cmd_samr.c
@@ -38,6 +38,760 @@ extern struct cli_state *smb_cli;
extern FILE* out_hnd;
+static void sam_display_group_info(char *domain, DOM_SID *sid,
+ uint32 group_rid,
+ GROUP_INFO_CTR *ctr)
+{
+ display_group_info_ctr(out_hnd, ACTION_HEADER , ctr);
+ display_group_info_ctr(out_hnd, ACTION_ENUMERATE, ctr);
+ display_group_info_ctr(out_hnd, ACTION_FOOTER , ctr);
+}
+
+static void sam_display_group(char *domain, DOM_SID *sid,
+ uint32 group_rid, char *group_name)
+{
+ report(out_hnd, "Group RID: %8x Group Name: %s\n",
+ group_rid, group_name);
+}
+
+static void sam_display_group_members(char *domain, DOM_SID *sid,
+ uint32 group_rid, char *group_name,
+ uint32 num_names,
+ uint32 *rid_mem,
+ char **name,
+ uint32 *type)
+{
+ display_group_members(out_hnd, ACTION_HEADER , num_names, name, type);
+ display_group_members(out_hnd, ACTION_ENUMERATE, num_names, name, type);
+ display_group_members(out_hnd, ACTION_FOOTER , num_names, name, type);
+}
+
+static void sam_display_user_info(char *domain, DOM_SID *sid,
+ uint32 user_rid,
+ SAM_USER_INFO_21 *usr)
+{
+ display_sam_user_info_21(out_hnd, ACTION_HEADER , usr);
+ display_sam_user_info_21(out_hnd, ACTION_ENUMERATE, usr);
+ display_sam_user_info_21(out_hnd, ACTION_FOOTER , usr);
+}
+
+static void sam_display_user(char *domain, DOM_SID *sid,
+ uint32 user_rid, char *user_name)
+{
+ report(out_hnd, "User RID: %8x User Name: %s\n",
+ user_rid, user_name);
+}
+
+static BOOL req_user_info(struct cli_state *cli, uint16 fnum,
+ POLICY_HND *pol_dom,
+ char *domain,
+ DOM_SID *sid,
+ uint32 user_rid,
+ USER_INFO_FN(usr_inf))
+{
+ SAM_USER_INFO_21 usr;
+ /* send user info query, level 0x15 */
+ if (get_samr_query_userinfo(smb_cli, fnum,
+ pol_dom,
+ 0x15, user_rid, &usr))
+ {
+ if (usr_inf != NULL)
+ {
+ usr_inf(domain, sid, user_rid, &usr);
+ }
+ return True;
+ }
+ return False;
+}
+
+/****************************************************************************
+SAM Query User Groups.
+****************************************************************************/
+uint32 sam_query_usergroups(struct cli_state *cli, uint16 fnum,
+ POLICY_HND *pol_dom,
+ char *domain,
+ DOM_SID *sid,
+ uint32 user_rid,
+ char *user_name,
+ uint32 *num_groups,
+ DOM_GID **gid,
+ char ***name,
+ uint32 **type,
+ USER_MEM_FN(usr_mem))
+{
+ uint32 num_names = 0;
+ (*gid) = NULL;
+ /* send user group query */
+ if (get_samr_query_usergroups(smb_cli, fnum,
+ pol_dom,
+ user_rid, num_groups, gid) &&
+ gid != NULL)
+ {
+ uint32 i;
+ uint32 *rid_mem;
+
+ rid_mem = (uint32*)malloc((*num_groups) * sizeof(rid_mem[0]));
+
+ if (rid_mem == NULL)
+ {
+ free(*gid);
+ (*gid) = NULL;
+ return 0;
+ }
+
+ for (i = 0; i < (*num_groups); i++)
+ {
+ rid_mem[i] = (*gid)[i].g_rid;
+ }
+
+ if (samr_query_lookup_rids(smb_cli, fnum,
+ pol_dom, 0x3e8,
+ (*num_groups), rid_mem,
+ &num_names, name, type))
+ {
+ usr_mem(domain, sid,
+ user_rid, user_name,
+ num_names, rid_mem, *name, *type);
+ }
+ }
+
+ return num_names;
+}
+
+static uint32 req_group_info(struct cli_state *cli, uint16 fnum,
+ POLICY_HND *pol_dom,
+ char *domain, DOM_SID *sid,
+ uint32 user_rid, char *user_name,
+ USER_MEM_FN(usr_mem))
+{
+ uint32 num_groups;
+ uint32 num_names;
+ DOM_GID *gid = NULL;
+ char **name = NULL;
+ uint32 *type = NULL;
+
+ num_names = sam_query_usergroups(cli, fnum, pol_dom,
+ domain, sid,
+ user_rid, user_name,
+ &num_groups, &gid,
+ &name, &type, usr_mem);
+
+ free_char_array(num_names, name);
+ if (type != NULL)
+ {
+ free(type);
+ }
+
+ if (gid != NULL)
+ {
+ free(gid);
+ }
+
+ return num_names;
+}
+
+static void req_alias_info(struct cli_state *cli, uint16 fnum,
+ POLICY_HND *pol_dom,
+ char *domain,
+ DOM_SID *sid1, uint32 user_rid,
+ char *user_name,
+ USER_MEM_FN(usr_mem))
+{
+ uint32 num_aliases;
+ uint32 *rid_mem = NULL;
+ uint32 *ptr_sid;
+ DOM_SID2 *als_sid;
+
+ ptr_sid = (uint32*) malloc(sizeof(ptr_sid[0]) * 1);
+ als_sid = (DOM_SID2*)malloc(sizeof(als_sid[0]) * 1);
+
+ sid_copy(&als_sid[0].sid, sid1);
+ sid_append_rid(&als_sid[0].sid, user_rid);
+ als_sid[0].num_auths = als_sid[0].sid.num_auths;
+
+ ptr_sid[0] = 1;
+
+ /* send user alias query */
+ if (samr_query_useraliases(cli, fnum,
+ pol_dom,
+ ptr_sid, als_sid, &num_aliases, &rid_mem))
+ {
+ uint32 num_names;
+ char **name = NULL;
+ uint32 *type = NULL;
+
+ uint32 *rid_copy = (uint32*)malloc(num_aliases * sizeof(*rid_copy));
+
+ if (rid_copy != NULL)
+ {
+ uint32 i;
+ for (i = 0; i < num_aliases; i++)
+ {
+ rid_copy[i] = rid_mem[i];
+ }
+ if (samr_query_lookup_rids(cli, fnum,
+ pol_dom, 0x3e8,
+ num_aliases, rid_copy,
+ &num_names, &name, &type))
+ {
+ usr_mem(domain, sid1,
+ user_rid, user_name,
+ num_names, rid_mem, name, type);
+ }
+ }
+
+ free_char_array(num_names, name);
+ if (type != NULL)
+ {
+ free(type);
+ }
+ }
+
+ if (rid_mem != NULL)
+ {
+ free(rid_mem);
+ rid_mem = NULL;
+ }
+
+ if (ptr_sid != NULL)
+ {
+ free(ptr_sid);
+ ptr_sid = NULL;
+ }
+ if (als_sid != NULL)
+ {
+ free(als_sid);
+ als_sid = NULL;
+ }
+}
+
+/****************************************************************************
+experimental SAM users enum.
+****************************************************************************/
+int msrpc_sam_enum_users(struct client_info *info,
+ struct acct_info **sam,
+ uint32 *num_sam_entries,
+ USER_FN(usr_fn),
+ USER_INFO_FN(usr_inf_fn),
+ USER_MEM_FN(usr_grp_fn),
+ USER_MEM_FN(usr_als_fn))
+{
+ uint16 fnum;
+ fstring srv_name;
+ fstring domain;
+ fstring sid;
+ DOM_SID sid1;
+ DOM_SID sid_1_5_20;
+ uint32 user_idx;
+ BOOL res = True;
+ BOOL res1 = True;
+ BOOL res2 = True;
+ uint32 start_idx = 0x0;
+ uint16 unk_0 = 0x0;
+ uint16 acb_mask = 0;
+ uint16 unk_1 = 0x0;
+ uint32 ace_perms = 0x304; /* access control permissions */
+ uint32 status;
+ POLICY_HND sam_pol;
+ POLICY_HND pol_dom;
+ POLICY_HND pol_blt;
+
+ sid_copy(&sid1, &info->dom.level5_sid);
+ sid_to_string(sid, &sid1);
+ fstrcpy(domain, info->dom.level5_dom);
+
+ (*sam) = NULL;
+ (*num_sam_entries) = 0;
+
+ if (sid1.num_auths == 0)
+ {
+ report(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
+ return 0;
+ }
+
+
+ fstrcpy(srv_name, "\\\\");
+ fstrcat(srv_name, info->dest_host);
+ strupper(srv_name);
+
+ string_to_sid(&sid_1_5_20, "S-1-5-32");
+
+ DEBUG(5,("Number of entries:%d unk_0:%04x acb_mask:%04x unk_1:%04x\n",
+ start_idx, unk_0, acb_mask, unk_1));
+
+ /* open SAMR session. negotiate credentials */
+ res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
+
+ /* establish a connection. */
+ res = res ? samr_connect(smb_cli, fnum,
+ srv_name, 0x02000000,
+ &sam_pol) : False;
+
+ /* connect to the domain */
+ res1 = res ? samr_open_domain(smb_cli, fnum,
+ &sam_pol, ace_perms, &sid1,
+ &pol_dom) : False;
+
+ /* connect to the S-1-5-20 domain */
+ res2 = res ? samr_open_domain(smb_cli, fnum,
+ &sam_pol, ace_perms, &sid_1_5_20,
+ &pol_blt) : False;
+
+ if (res1)
+ {
+ /* read some users */
+ do
+ {
+ status = samr_enum_dom_users(smb_cli, fnum,
+ &pol_dom,
+ &start_idx, acb_mask, unk_1, 0x100000,
+ sam, num_sam_entries);
+
+ } while (status == STATUS_MORE_ENTRIES);
+
+ if ((*num_sam_entries) == 0)
+ {
+ report(out_hnd, "No users\n");
+ }
+
+ /* query all the users */
+ for (user_idx = 0; res && user_idx <
+ (*num_sam_entries); user_idx++)
+ {
+ uint32 user_rid = (*sam)[user_idx].rid;
+ char *user_name = (*sam)[user_idx].acct_name;
+
+ if (usr_fn != NULL)
+ {
+ usr_fn(domain, &sid1, user_rid, user_name);
+ }
+
+ if (usr_inf_fn != NULL)
+ {
+ req_user_info(smb_cli, fnum, &pol_dom,
+ domain, &sid1,
+ user_rid,
+ usr_inf_fn);
+ }
+
+ if (usr_grp_fn != NULL)
+ {
+ req_group_info(smb_cli, fnum, &pol_dom,
+ domain, &sid1,
+ user_rid, user_name,
+ usr_grp_fn);
+ }
+
+ if (usr_als_fn != NULL)
+ {
+ req_alias_info(smb_cli, fnum, &pol_dom,
+ domain, &sid1,
+ user_rid, user_name,
+ usr_als_fn);
+ req_alias_info(smb_cli, fnum, &pol_blt,
+ domain, &sid1,
+ user_rid, user_name,
+ usr_als_fn);
+ }
+ }
+ }
+
+ res2 = res2 ? samr_close(smb_cli, fnum, &pol_blt) : False;
+ res1 = res1 ? samr_close(smb_cli, fnum, &pol_dom) : False;
+ res = res ? samr_close(smb_cli, fnum, &sam_pol) : False;
+
+ /* close the session */
+ cli_nt_session_close(smb_cli, fnum);
+
+ if (res)
+ {
+ DEBUG(5,("msrpc_sam_enum_users: succeeded\n"));
+ }
+ else
+ {
+ DEBUG(5,("msrpc_sam_enum_users: failed\n"));
+ }
+
+ return (*num_sam_entries);
+}
+
+
+/****************************************************************************
+experimental SAM domain info query.
+****************************************************************************/
+BOOL sam_query_dominfo(struct client_info *info, DOM_SID *sid1,
+ uint32 switch_value, SAM_UNK_CTR *ctr)
+{
+ uint16 fnum;
+ fstring srv_name;
+ BOOL res = True;
+ BOOL res1 = True;
+ BOOL res2 = True;
+ uint32 ace_perms = 0x02000000; /* absolutely no idea. */
+ POLICY_HND sam_pol;
+ POLICY_HND pol_dom;
+
+ fstrcpy(srv_name, "\\\\");
+ fstrcat(srv_name, info->dest_host);
+ strupper(srv_name);
+
+ /* open SAMR session. negotiate credentials */
+ res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
+
+ /* establish a connection. */
+ res = res ? samr_connect(smb_cli, fnum,
+ srv_name, 0x02000000,
+ &sam_pol) : False;
+
+ /* connect to the domain */
+ res1 = res ? samr_open_domain(smb_cli, fnum,
+ &sam_pol, ace_perms, sid1,
+ &pol_dom) : False;
+
+ /* send a samr 0x8 command */
+ res2 = res ? samr_query_dom_info(smb_cli, fnum,
+ &pol_dom, switch_value, ctr) : False;
+
+ res1 = res1 ? samr_close(smb_cli, fnum,
+ &sam_pol) : False;
+
+ res = res ? samr_close(smb_cli, fnum,
+ &pol_dom) : False;
+
+ /* close the session */
+ cli_nt_session_close(smb_cli, fnum);
+
+ if (res2)
+ {
+ DEBUG(5,("sam_query_dominfo: succeeded\n"));
+ }
+ else
+ {
+ DEBUG(5,("sam_query_dominfo: failed\n"));
+ }
+
+ return res2;
+}
+
+
+
+static void req_samr_aliasmem(struct cli_state *cli, uint16 fnum,
+ const char *srv_name,
+ POLICY_HND *pol_dom, uint32 alias_rid)
+{
+ uint32 num_aliases;
+ DOM_SID2 sid_mem[MAX_LOOKUP_SIDS];
+
+ /* send user aliases query */
+ if (get_samr_query_aliasmem(smb_cli, fnum,
+ pol_dom,
+ alias_rid, &num_aliases, sid_mem))
+ {
+ uint16 fnum_lsa;
+ POLICY_HND lsa_pol;
+
+ BOOL res3 = True;
+ BOOL res4 = True;
+ char **names = NULL;
+ int num_names = 0;
+ DOM_SID **sids = NULL;
+ uint32 i;
+
+ if (num_aliases != 0)
+ {
+ sids = (DOM_SID**)malloc(num_aliases * sizeof(DOM_SID*));
+ }
+
+ res3 = sids != NULL;
+ if (res3)
+ {
+ for (i = 0; i < num_aliases; i++)
+ {
+ sids[i] = &sid_mem[i].sid;
+ }
+ }
+
+ /* open LSARPC session. */
+ res3 = res3 ? cli_nt_session_open(smb_cli, PIPE_LSARPC, &fnum_lsa) : False;
+
+ /* lookup domain controller; receive a policy handle */
+ res3 = res3 ? lsa_open_policy(smb_cli, fnum_lsa,
+ srv_name,
+ &lsa_pol, True) : False;
+
+ /* send lsa lookup sids call */
+ res4 = res3 ? lsa_lookup_sids(smb_cli, fnum_lsa,
+ &lsa_pol,
+ num_aliases, sids,
+ &names, NULL, &num_names) : False;
+
+ res3 = res3 ? lsa_close(smb_cli, fnum_lsa, &lsa_pol) : False;
+
+ cli_nt_session_close(smb_cli, fnum_lsa);
+
+ if (res4 && names != NULL)
+ {
+ display_alias_members(out_hnd, ACTION_HEADER , num_names, names);
+ display_alias_members(out_hnd, ACTION_ENUMERATE, num_names, names);
+ display_alias_members(out_hnd, ACTION_FOOTER , num_names, names);
+ }
+ free_char_array(num_names, names);
+ if (sids != NULL)
+ {
+ free(sids);
+ }
+ }
+}
+
+BOOL sam_query_groupmem(struct cli_state *cli, uint16 fnum,
+ POLICY_HND *pol_dom,
+ uint32 group_rid,
+ uint32 *num_names,
+ uint32 **rid_mem,
+ char ***name,
+ uint32 **type)
+{
+ uint32 num_mem;
+ uint32 *attr_mem = NULL;
+ BOOL res3;
+
+ *rid_mem = NULL;
+ *num_names = 0;
+ *name = NULL;
+ *type = NULL;
+
+ /* get group members */
+ res3 = get_samr_query_groupmem(cli, fnum,
+ pol_dom,
+ group_rid, &num_mem, rid_mem, &attr_mem);
+
+ if (res3 && num_mem != 0)
+ {
+ uint32 *rid_copy = (uint32*)malloc(num_mem *
+ sizeof(rid_copy[0]));
+
+ if (rid_copy != NULL)
+ {
+ uint32 i;
+ for (i = 0; i < num_mem; i++)
+ {
+ rid_copy[i] = (*rid_mem)[i];
+ }
+ /* resolve names */
+ res3 = samr_query_lookup_rids(cli, fnum,
+ pol_dom, 1000,
+ num_mem, rid_copy, num_names, name, type);
+ }
+ }
+ else
+ {
+ if (attr_mem != NULL)
+ {
+ free(attr_mem);
+ }
+ if ((*rid_mem) != NULL)
+ {
+ free(*rid_mem);
+ }
+ attr_mem = NULL;
+ *rid_mem = NULL;
+ }
+
+ if (!res3)
+ {
+ free_char_array(*num_names, *name);
+ if ((*type) != NULL)
+ {
+ free(*type);
+ }
+ *num_names = 0;
+ *name = NULL;
+ *type = NULL;
+ }
+
+ if (attr_mem != NULL)
+ {
+ free(attr_mem);
+ }
+
+ return res3;
+}
+
+static BOOL query_groupinfo(struct cli_state *cli, uint16 fnum,
+ POLICY_HND *pol_dom,
+ char *domain,
+ DOM_SID *sid,
+ uint32 group_rid,
+ GROUP_INFO_FN(grp_inf))
+{
+ GROUP_INFO_CTR ctr;
+
+ /* send group info query */
+ if (get_samr_query_groupinfo(smb_cli, fnum,
+ pol_dom,
+ 1, /* info level */
+ group_rid, &ctr))
+ {
+ if (grp_inf != NULL)
+ {
+ grp_inf(domain, sid, group_rid, &ctr);
+ }
+ return True;
+ }
+ return False;
+}
+
+static BOOL req_groupmem_info(struct cli_state *cli, uint16 fnum,
+ POLICY_HND *pol_dom,
+ char *domain,
+ DOM_SID *sid,
+ uint32 group_rid,
+ char *group_name,
+ GROUP_MEM_FN(grp_mem))
+{
+ uint32 num_names = 0;
+ char **name = NULL;
+ uint32 *type = NULL;
+ uint32 *rid_mem = NULL;
+
+ if (sam_query_groupmem(cli, fnum, pol_dom, group_rid,
+ &num_names, &rid_mem, &name, &type))
+ {
+ grp_mem(domain, sid,
+ group_rid, group_name,
+ num_names, rid_mem, name, type);
+
+ free_char_array(num_names, name);
+ if (type != NULL)
+ {
+ free(type);
+ }
+ if (rid_mem != NULL)
+ {
+ free(rid_mem);
+ }
+ return True;
+ }
+ return False;
+}
+
+/****************************************************************************
+SAM groups query.
+****************************************************************************/
+uint32 msrpc_sam_enum_groups(struct client_info *info,
+ struct acct_info **sam,
+ uint32 *num_sam_entries,
+ GROUP_FN(grp_fn),
+ GROUP_INFO_FN(grp_inf_fn),
+ GROUP_MEM_FN(grp_mem_fn))
+{
+ uint16 fnum;
+ fstring srv_name;
+ fstring domain;
+ fstring sid;
+ DOM_SID sid1;
+ BOOL res = True;
+ uint32 ace_perms = 0x02000000; /* access control permissions. */
+ POLICY_HND sam_pol;
+ POLICY_HND pol_dom;
+ uint32 status;
+
+ sid_copy(&sid1, &info->dom.level5_sid);
+
+ if (sid1.num_auths == 0)
+ {
+ report(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
+ return 0;
+ }
+
+ sid_to_string(sid, &sid1);
+ fstrcpy(domain, info->dom.level3_dom);
+
+ fstrcpy(srv_name, "\\\\");
+ fstrcat(srv_name, info->dest_host);
+ strupper(srv_name);
+
+ /* open SAMR session. negotiate credentials */
+ res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
+
+ /* establish a connection. */
+ res = res ? samr_connect(smb_cli, fnum,
+ srv_name, 0x02000000,
+ &sam_pol) : False;
+
+ /* connect to the domain */
+ res = res ? samr_open_domain(smb_cli, fnum,
+ &sam_pol, ace_perms, &sid1,
+ &pol_dom) : False;
+
+ (*sam) = NULL;
+
+ if (res)
+ {
+ uint32 group_idx;
+ uint32 start_idx = 0;
+ /* read some groups */
+ do
+ {
+ status = samr_enum_dom_groups(smb_cli, fnum,
+ &pol_dom,
+ &start_idx, 0x100000,
+ sam, num_sam_entries);
+
+ } while (status == STATUS_MORE_ENTRIES);
+
+ if ((*num_sam_entries) == 0)
+ {
+ report(out_hnd, "No groups\n");
+ }
+
+ for (group_idx = 0; group_idx < (*num_sam_entries); group_idx++)
+ {
+ uint32 group_rid = (*sam)[group_idx].rid;
+ char *group_name = (*sam)[group_idx].acct_name;
+
+ if (grp_fn != NULL)
+ {
+ grp_fn(domain, &sid1, group_rid, group_name);
+ }
+
+ if (grp_inf_fn != NULL)
+ {
+ query_groupinfo(smb_cli, fnum, &pol_dom,
+ domain, &sid1,
+ group_rid,
+ grp_inf_fn);
+ }
+ if (grp_mem_fn != NULL)
+ {
+ req_groupmem_info(smb_cli, fnum, &pol_dom,
+ domain, &sid1,
+ group_rid, group_name,
+ grp_mem_fn);
+ }
+ }
+ }
+
+ res = res ? samr_close(smb_cli, fnum,
+ &pol_dom) : False;
+
+ res = res ? samr_close(smb_cli, fnum,
+ &sam_pol) : False;
+
+ /* close the session */
+ cli_nt_session_close(smb_cli, fnum);
+
+ if (res)
+ {
+ DEBUG(5,("msrpc_sam_enum_groups: succeeded\n"));
+ }
+ else
+ {
+ DEBUG(5,("msrpc_sam_enum_groups: failed\n"));
+ }
+ return (*num_sam_entries);
+}
+
/****************************************************************************
SAM password change
****************************************************************************/
@@ -465,14 +1219,10 @@ void cmd_sam_add_aliasmem(struct client_info *info)
while (next_token(NULL, tmp, NULL, sizeof(tmp)))
{
- num_names++;
- names = (char**)Realloc(names, num_names * sizeof(char*));
- if (names == NULL)
+ if (!add_chars_to_array(&num_names, &names, tmp))
{
- DEBUG(0,("Realloc returned NULL\n"));
return;
}
- names[num_names-1] = strdup(tmp);
}
if (num_names < 2)
@@ -769,7 +1519,7 @@ void cmd_sam_del_groupmem(struct client_info *info)
fstring tmp;
fstring sid;
DOM_SID sid1;
- POLICY_HND group_pol;
+ POLICY_HND pol_grp;
BOOL res = True;
BOOL res1 = True;
BOOL res2 = True;
@@ -818,13 +1568,13 @@ void cmd_sam_del_groupmem(struct client_info *info)
/* connect to the domain */
res1 = res ? samr_open_group(smb_cli, fnum,
&pol_dom,
- 0x0000001f, group_rid, &group_pol) : False;
+ 0x0000001f, group_rid, &pol_grp) : False;
while (next_token(NULL, tmp, NULL, sizeof(tmp)) && res2 && res1)
{
/* get a rid, delete a member from the group */
member_rid = get_number(tmp);
- res2 = res2 ? samr_del_groupmem(smb_cli, fnum, &group_pol, member_rid) : False;
+ res2 = res2 ? samr_del_groupmem(smb_cli, fnum, &pol_grp, member_rid) : False;
if (res2)
{
@@ -832,7 +1582,7 @@ void cmd_sam_del_groupmem(struct client_info *info)
}
}
- res1 = res1 ? samr_close(smb_cli, fnum, &group_pol) : False;
+ res1 = res1 ? samr_close(smb_cli, fnum, &pol_grp) : False;
res = res ? samr_close(smb_cli, fnum, &pol_dom) : False;
res = res ? samr_close(smb_cli, fnum, &sam_pol) : False;
@@ -863,7 +1613,7 @@ void cmd_sam_delete_dom_group(struct client_info *info)
fstring name;
fstring sid;
DOM_SID sid1;
- POLICY_HND group_pol;
+ POLICY_HND pol_grp;
BOOL res = True;
BOOL res1 = True;
BOOL res2 = True;
@@ -926,11 +1676,11 @@ void cmd_sam_delete_dom_group(struct client_info *info)
/* connect to the domain */
res1 = res1 ? samr_open_group(smb_cli, fnum,
&pol_dom,
- 0x0000001f, group_rid, &group_pol) : False;
+ 0x0000001f, group_rid, &pol_grp) : False;
- res2 = res1 ? samr_delete_dom_group(smb_cli, fnum, &group_pol) : False;
+ res2 = res1 ? samr_delete_dom_group(smb_cli, fnum, &pol_grp) : False;
- res1 = res1 ? samr_close(smb_cli, fnum, &group_pol) : False;
+ res1 = res1 ? samr_close(smb_cli, fnum, &pol_grp) : False;
res = res ? samr_close(smb_cli, fnum, &pol_dom) : False;
res = res ? samr_close(smb_cli, fnum, &sam_pol) : False;
@@ -961,13 +1711,15 @@ void cmd_sam_add_groupmem(struct client_info *info)
fstring tmp;
fstring sid;
DOM_SID sid1;
- POLICY_HND group_pol;
+ POLICY_HND pol_grp;
BOOL res = True;
BOOL res1 = True;
BOOL res2 = True;
+ BOOL res3 = True;
+ BOOL res4 = True;
uint32 ace_perms = 0x02000000; /* absolutely no idea. */
- uint32 *group_rid = NULL;
- uint32 *group_type = NULL;
+ uint32 group_rid[0];
+ uint32 group_type[1];
char **names = NULL;
uint32 num_names = 0;
fstring group_name;
@@ -1003,14 +1755,10 @@ void cmd_sam_add_groupmem(struct client_info *info)
while (res && next_token(NULL, tmp, NULL, sizeof(tmp)))
{
- num_names++;
- names = (char**)Realloc(names, num_names * sizeof(char*));
- if (names == NULL)
+ if (!add_chars_to_array(&num_names, &names, tmp))
{
- DEBUG(0,("Realloc returned NULL\n"));
return;
}
- names[num_names-1] = strdup(tmp);
}
if (num_names < 1)
@@ -1030,16 +1778,16 @@ void cmd_sam_add_groupmem(struct client_info *info)
&sam_pol) : False;
/* connect to the domain */
- res1 = res ? samr_open_domain(smb_cli, fnum,
+ res4 = res ? samr_open_domain(smb_cli, fnum,
&sam_pol, ace_perms, &sid1,
&pol_dom) : False;
/* connect to the domain */
- res1 = res1 ? samr_open_domain(smb_cli, fnum,
+ res3 = res ? samr_open_domain(smb_cli, fnum,
&sam_pol, ace_perms, &sid_1_5_20,
&pol_blt) : False;
- res2 = res1 ? samr_query_lookup_names(smb_cli, fnum,
+ res2 = res4 ? samr_query_lookup_names(smb_cli, fnum,
&pol_dom, 0x000003e8,
1, group_names,
&num_group_rids, group_rid, group_type) : False;
@@ -1047,11 +1795,11 @@ void cmd_sam_add_groupmem(struct client_info *info)
/* open the group */
res2 = res2 ? samr_open_group(smb_cli, fnum,
&pol_dom,
- 0x0000001f, group_rid[0], &group_pol) : False;
+ 0x0000001f, group_rid[0], &pol_grp) : False;
if (!res2 || (group_type != NULL && group_type[0] == SID_NAME_UNKNOWN))
{
- res2 = res1 ? samr_query_lookup_names(smb_cli, fnum,
+ res2 = res3 ? samr_query_lookup_names(smb_cli, fnum,
&pol_blt, 0x000003e8,
1, group_names,
&num_group_rids, group_rid, group_type) : False;
@@ -1059,10 +1807,10 @@ void cmd_sam_add_groupmem(struct client_info *info)
/* open the group */
res2 = res2 ? samr_open_group(smb_cli, fnum,
&pol_blt,
- 0x0000001f, group_rid[0], &group_pol) : False;
+ 0x0000001f, group_rid[0], &pol_grp) : False;
}
- if (group_type[0] == SID_NAME_ALIAS)
+ if (res2 && group_type[0] == SID_NAME_ALIAS)
{
report(out_hnd, "%s is a local alias, not a group. Use addaliasmem command instead\n",
group_name);
@@ -1073,20 +1821,29 @@ void cmd_sam_add_groupmem(struct client_info *info)
num_names, names,
&num_rids, rid, type) : False;
+ if (num_rids == 0)
+ {
+ report(out_hnd, "Member names not known\n");
+ }
for (i = 0; i < num_rids && res2 && res1; i++)
{
- res2 = res2 ? samr_add_groupmem(smb_cli, fnum, &group_pol, rid[i]) : False;
-
- if (res2)
+ if (type[i] == SID_NAME_UNKNOWN)
+ {
+ report(out_hnd, "Name %s unknown\n", names[i]);
+ }
+ else
{
- report(out_hnd, "RID added to Group 0x%x: 0x%x\n",
- group_rid[0], rid[i]);
+ if (samr_add_groupmem(smb_cli, fnum, &pol_grp, rid[i]))
+ {
+ report(out_hnd, "RID added to Group 0x%x: 0x%x\n",
+ group_rid[0], rid[i]);
+ }
}
}
- res1 = res ? samr_close(smb_cli, fnum, &group_pol) : False;
- res1 = res ? samr_close(smb_cli, fnum, &pol_blt) : False;
- res1 = res ? samr_close(smb_cli, fnum, &pol_dom) : False;
+ res1 = res ? samr_close(smb_cli, fnum, &pol_grp) : False;
+ res1 = res3 ? samr_close(smb_cli, fnum, &pol_blt) : False;
+ res1 = res4 ? samr_close(smb_cli, fnum, &pol_dom) : False;
res = res ? samr_close(smb_cli, fnum, &sam_pol) : False;
/* close the session */
@@ -1104,7 +1861,7 @@ void cmd_sam_add_groupmem(struct client_info *info)
DEBUG(5,("cmd_sam_add_groupmem: failed\n"));
report(out_hnd, "Add Domain Group Member: FAILED\n");
}
-
+#if 0
if (group_rid != NULL)
{
free(group_rid);
@@ -1113,6 +1870,7 @@ void cmd_sam_add_groupmem(struct client_info *info)
{
free(group_type);
}
+#endif
}
@@ -1204,415 +1962,238 @@ void cmd_sam_create_dom_group(struct client_info *info)
}
}
-static void sam_display_group_info(char *domain, DOM_SID *sid,
- uint32 group_rid,
- GROUP_INFO_CTR *ctr)
-{
- display_group_info_ctr(out_hnd, ACTION_HEADER , ctr);
- display_group_info_ctr(out_hnd, ACTION_ENUMERATE, ctr);
- display_group_info_ctr(out_hnd, ACTION_FOOTER , ctr);
-}
-
-static void sam_display_group(char *domain, DOM_SID *sid,
- uint32 group_rid, char *group_name)
-{
- report(out_hnd, "Group RID: %8x Group Name: %s\n",
- group_rid, group_name);
-}
-
-static void sam_display_group_members(char *domain, DOM_SID *sid,
- uint32 group_rid, char *group_name,
- uint32 num_names,
- uint32 *rid_mem,
- char **name,
- uint32 *type)
-{
- display_group_members(out_hnd, ACTION_HEADER , num_names, name, type);
- display_group_members(out_hnd, ACTION_ENUMERATE, num_names, name, type);
- display_group_members(out_hnd, ACTION_FOOTER , num_names, name, type);
-}
-
-static void sam_display_user_info(char *domain, DOM_SID *sid,
- uint32 user_rid,
- SAM_USER_INFO_21 *usr)
-{
- display_sam_user_info_21(out_hnd, ACTION_HEADER , usr);
- display_sam_user_info_21(out_hnd, ACTION_ENUMERATE, usr);
- display_sam_user_info_21(out_hnd, ACTION_FOOTER , usr);
-}
-
-static void sam_display_user(char *domain, DOM_SID *sid,
- uint32 user_rid, char *user_name)
-{
- report(out_hnd, "User RID: %8x User Name: %s\n",
- user_rid, user_name);
-}
-
-static void req_user_info(struct cli_state *cli, uint16 fnum,
- POLICY_HND *pol_dom,
- char *domain,
- DOM_SID *sid,
- uint32 user_rid,
- USER_INFO_FN(usr_inf))
-{
- SAM_USER_INFO_21 usr;
- /* send user info query, level 0x15 */
- if (get_samr_query_userinfo(smb_cli, fnum,
- pol_dom,
- 0x15, user_rid, &usr))
- {
- usr_inf(domain, sid, user_rid, &usr);
- }
-}
-
/****************************************************************************
-SAM Query User Groups.
+experimental SAM users enum.
****************************************************************************/
-uint32 sam_query_usergroups(struct cli_state *cli, uint16 fnum,
- POLICY_HND *pol_dom,
- char *domain,
- DOM_SID *sid,
- uint32 user_rid,
- char *user_name,
- uint32 *num_groups,
- DOM_GID **gid,
- char ***name,
- uint32 **type,
- USER_MEM_FN(usr_mem))
+void cmd_sam_enum_users(struct client_info *info)
{
- uint32 num_names = 0;
- (*gid) = NULL;
- /* send user group query */
- if (get_samr_query_usergroups(smb_cli, fnum,
- pol_dom,
- user_rid, num_groups, gid) &&
- gid != NULL)
- {
- uint32 i;
- uint32 *rid_mem;
-
- rid_mem = (uint32*)malloc((*num_groups) * sizeof(rid_mem[0]));
-
- if (rid_mem == NULL)
- {
- free(*gid);
- (*gid) = NULL;
- return 0;
- }
+ BOOL request_user_info = False;
+ BOOL request_group_info = False;
+ BOOL request_alias_info = False;
+ fstring tmp;
+ struct acct_info *sam = NULL;
+ uint32 num_sam_entries = 0;
+ int i;
- for (i = 0; i < (*num_groups); i++)
+ for (i = 0; i < 3; i++)
+ {
+ /* a bad way to do token parsing... */
+ if (next_token(NULL, tmp, NULL, sizeof(tmp)))
{
- rid_mem[i] = (*gid)[i].g_rid;
+ request_user_info |= strequal(tmp, "-u");
+ request_group_info |= strequal(tmp, "-g");
+ request_alias_info |= strequal(tmp, "-a");
}
-
- if (samr_query_lookup_rids(smb_cli, fnum,
- pol_dom, 0x3e8,
- (*num_groups), rid_mem,
- &num_names, name, type))
+ else
{
- usr_mem(domain, sid,
- user_rid, user_name,
- num_names, rid_mem, *name, *type);
+ break;
}
}
- return num_names;
+ report(out_hnd, "SAM Enumerate Users\n");
+
+ msrpc_sam_enum_users(info, &sam, &num_sam_entries,
+ sam_display_user,
+ request_user_info ? sam_display_user_info : NULL,
+ request_group_info ? sam_display_group_members : NULL,
+ request_alias_info ? sam_display_group_members : NULL);
+
+ if (sam != NULL)
+ {
+ free(sam);
+ }
}
-static void req_group_info(struct cli_state *cli, uint16 fnum,
- POLICY_HND *pol_dom,
- char *domain, DOM_SID *sid,
- uint32 user_rid, char *user_name,
- USER_MEM_FN(usr_mem))
+
+/****************************************************************************
+experimental SAM group query members.
+****************************************************************************/
+void cmd_sam_query_groupmem(struct client_info *info)
{
- uint32 num_groups;
- uint32 num_names;
- DOM_GID *gid = NULL;
- char **name = NULL;
- uint32 *type = NULL;
+ uint16 fnum;
+ fstring srv_name;
+ fstring domain;
+ fstring sid_str;
+ DOM_SID sid;
+ BOOL res = True;
+ BOOL res1 = True;
- num_names = sam_query_usergroups(cli, fnum, pol_dom,
- domain, sid,
- user_rid, user_name,
- &num_groups, &gid,
- &name, &type, usr_mem);
+ fstring group_name;
+ char *names[1];
+ uint32 num_rids;
+ uint32 rid[MAX_LOOKUP_SIDS];
+ uint32 type[MAX_LOOKUP_SIDS];
+ POLICY_HND sam_pol;
+ POLICY_HND pol_dom;
- free_char_array(num_names, name);
- if (type != NULL)
+ fstrcpy(domain, info->dom.level5_dom);
+ sid_copy(&sid, &info->dom.level5_sid);
+
+ if (sid.num_auths == 0)
{
- free(type);
+ report(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
+ return;
}
- if (gid != NULL)
+ if (!next_token(NULL, group_name, NULL, sizeof(group_name)))
{
- free(gid);
+ report(out_hnd, "samgroup <name>\n");
+ return;
}
-}
-static void req_alias_info(struct cli_state *cli, uint16 fnum,
- POLICY_HND *pol_dom,
- char *domain,
- DOM_SID *sid1, uint32 user_rid,
- char *user_name,
- USER_MEM_FN(usr_mem))
-{
- uint32 num_aliases;
- uint32 *rid_mem = NULL;
- uint32 *ptr_sid;
- DOM_SID2 *als_sid;
-
- ptr_sid = (uint32*) malloc(sizeof(ptr_sid[0]) * 1);
- als_sid = (DOM_SID2*)malloc(sizeof(als_sid[0]) * 1);
+ fstrcpy(srv_name, "\\\\");
+ fstrcat(srv_name, info->dest_host);
+ strupper(srv_name);
- sid_copy(&als_sid[0].sid, sid1);
- sid_append_rid(&als_sid[0].sid, user_rid);
- als_sid[0].num_auths = als_sid[0].sid.num_auths;
+ sid_to_string(sid_str, &sid);
- ptr_sid[0] = 1;
+ report(out_hnd, "SAM Query Group: %s\n", group_name);
+ report(out_hnd, "From: %s To: %s Domain: %s SID: %s\n",
+ info->myhostname, srv_name, domain, sid_str);
- /* send user alias query */
- if (samr_query_useraliases(cli, fnum,
- pol_dom,
- ptr_sid, als_sid, &num_aliases, &rid_mem))
- {
- uint32 num_names;
- char **name = NULL;
- uint32 *type = NULL;
+ /* open SAMR session. negotiate credentials */
+ res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
- uint32 *rid_copy = (uint32*)malloc(num_aliases * sizeof(*rid_copy));
+ /* establish a connection. */
+ res = res ? samr_connect(smb_cli, fnum,
+ srv_name, 0x02000000,
+ &sam_pol) : False;
- if (rid_copy != NULL)
- {
- uint32 i;
- for (i = 0; i < num_aliases; i++)
- {
- rid_copy[i] = rid_mem[i];
- }
- if (samr_query_lookup_rids(cli, fnum,
- pol_dom, 0x3e8,
- num_aliases, rid_copy,
- &num_names, &name, &type))
- {
- usr_mem(domain, sid1,
- user_rid, user_name,
- num_names, rid_mem, name, type);
- }
- }
+ /* connect to the domain */
+ res = res ? samr_open_domain(smb_cli, fnum,
+ &sam_pol, 0x304, &sid,
+ &pol_dom) : False;
- free_char_array(num_names, name);
- if (type != NULL)
- {
- free(type);
- }
- }
+ /* look up group rid */
+ names[0] = group_name;
+ res1 = res ? samr_query_lookup_names(smb_cli, fnum,
+ &pol_dom, 0x3e8,
+ 1, names,
+ &num_rids, rid, type) : False;
- if (rid_mem != NULL)
+ if (res1 && num_rids == 1)
{
- free(rid_mem);
- rid_mem = NULL;
+ res1 = req_groupmem_info(smb_cli, fnum,
+ &pol_dom,
+ domain,
+ &sid,
+ rid[0],
+ names[0],
+ sam_display_group_members);
}
- if (ptr_sid != NULL)
+ res = res ? samr_close(smb_cli, fnum,
+ &sam_pol) : False;
+
+ res = res ? samr_close(smb_cli, fnum,
+ &pol_dom) : False;
+
+ /* close the session */
+ cli_nt_session_close(smb_cli, fnum);
+
+ if (res1)
{
- free(ptr_sid);
- ptr_sid = NULL;
+ DEBUG(5,("cmd_sam_query_group: succeeded\n"));
}
- if (als_sid != NULL)
+ else
{
- free(als_sid);
- als_sid = NULL;
+ DEBUG(5,("cmd_sam_query_group: failed\n"));
}
}
+
/****************************************************************************
-experimental SAM users enum.
+experimental SAM group query.
****************************************************************************/
-int msrpc_sam_enum_users(struct client_info *info,
- struct acct_info **sam,
- uint32 *num_sam_entries,
- USER_FN(usr_fn),
- USER_INFO_FN(usr_inf_fn),
- USER_MEM_FN(usr_grp_fn),
- USER_MEM_FN(usr_als_fn))
+void cmd_sam_query_group(struct client_info *info)
{
uint16 fnum;
fstring srv_name;
fstring domain;
- fstring sid;
- DOM_SID sid1;
- DOM_SID sid_1_5_20;
- uint32 user_idx;
+ fstring sid_str;
+ DOM_SID sid;
BOOL res = True;
BOOL res1 = True;
- BOOL res2 = True;
- uint32 start_idx = 0x0;
- uint16 unk_0 = 0x0;
- uint16 acb_mask = 0;
- uint16 unk_1 = 0x0;
- uint32 ace_perms = 0x304; /* access control permissions */
- uint32 status;
+
+ fstring group_name;
+ char *names[1];
+ uint32 num_rids;
+ uint32 rid[MAX_LOOKUP_SIDS];
+ uint32 type[MAX_LOOKUP_SIDS];
POLICY_HND sam_pol;
POLICY_HND pol_dom;
- POLICY_HND pol_blt;
- sid_copy(&sid1, &info->dom.level5_sid);
- sid_to_string(sid, &sid1);
fstrcpy(domain, info->dom.level5_dom);
+ sid_copy(&sid, &info->dom.level5_sid);
- (*sam) = NULL;
- (*num_sam_entries) = 0;
-
- if (sid1.num_auths == 0)
+ if (sid.num_auths == 0)
{
report(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
- return 0;
+ return;
}
+ if (!next_token(NULL, group_name, NULL, sizeof(group_name)))
+ {
+ report(out_hnd, "samgroup <name>\n");
+ return;
+ }
fstrcpy(srv_name, "\\\\");
fstrcat(srv_name, info->dest_host);
strupper(srv_name);
- string_to_sid(&sid_1_5_20, "S-1-5-32");
+ sid_to_string(sid_str, &sid);
- report(out_hnd, "SAM Enumerate Users\n");
+ report(out_hnd, "SAM Query Group: %s\n", group_name);
report(out_hnd, "From: %s To: %s Domain: %s SID: %s\n",
- info->myhostname, srv_name, domain, sid);
-
- DEBUG(5,("Number of entries:%d unk_0:%04x acb_mask:%04x unk_1:%04x\n",
- start_idx, unk_0, acb_mask, unk_1));
+ info->myhostname, srv_name, domain, sid_str);
/* open SAMR session. negotiate credentials */
res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
/* establish a connection. */
- res = res ? samr_connect(smb_cli, fnum,
+ res = res ? samr_connect(smb_cli, fnum,
srv_name, 0x02000000,
&sam_pol) : False;
/* connect to the domain */
- res1 = res ? samr_open_domain(smb_cli, fnum,
- &sam_pol, ace_perms, &sid1,
+ res = res ? samr_open_domain(smb_cli, fnum,
+ &sam_pol, 0x304, &sid,
&pol_dom) : False;
- /* connect to the S-1-5-20 domain */
- res2 = res ? samr_open_domain(smb_cli, fnum,
- &sam_pol, ace_perms, &sid_1_5_20,
- &pol_blt) : False;
+ /* look up group rid */
+ names[0] = group_name;
+ res1 = res ? samr_query_lookup_names(smb_cli, fnum,
+ &pol_dom, 0x3e8,
+ 1, names,
+ &num_rids, rid, type) : False;
- if (res1)
+ if (res1 && num_rids == 1)
{
- /* read some users */
- do
- {
- status = samr_enum_dom_users(smb_cli, fnum,
- &pol_dom,
- &start_idx, acb_mask, unk_1, 0x100000,
- sam, num_sam_entries);
-
- } while (status == STATUS_MORE_ENTRIES);
-
- if ((*num_sam_entries) == 0)
- {
- report(out_hnd, "No users\n");
- }
-
- /* query all the users */
- for (user_idx = 0; res && user_idx <
- (*num_sam_entries); user_idx++)
- {
- uint32 user_rid = (*sam)[user_idx].rid;
- char *user_name = (*sam)[user_idx].acct_name;
-
- usr_fn(domain, &sid1, user_rid, user_name);
-
- if (usr_inf_fn)
- {
- req_user_info(smb_cli, fnum, &pol_dom,
- domain, &sid1,
- user_rid,
- usr_inf_fn);
- }
-
- if (usr_grp_fn != NULL)
- {
- req_group_info(smb_cli, fnum, &pol_dom,
- domain, &sid1,
- user_rid, user_name,
- usr_grp_fn);
- }
-
- if (usr_als_fn != NULL)
- {
- req_alias_info(smb_cli, fnum, &pol_dom,
- domain, &sid1,
- user_rid, user_name,
- usr_als_fn);
- req_alias_info(smb_cli, fnum, &pol_blt,
- domain, &sid1,
- user_rid, user_name,
- usr_als_fn);
- }
- }
+ res1 = query_groupinfo(smb_cli, fnum,
+ &pol_dom,
+ domain,
+ &sid,
+ rid[0],
+ sam_display_group_info);
}
- res2 = res2 ? samr_close(smb_cli, fnum, &pol_blt) : False;
- res1 = res1 ? samr_close(smb_cli, fnum, &pol_dom) : False;
- res = res ? samr_close(smb_cli, fnum, &sam_pol) : False;
+ res = res ? samr_close(smb_cli, fnum,
+ &sam_pol) : False;
+
+ res = res ? samr_close(smb_cli, fnum,
+ &pol_dom) : False;
/* close the session */
cli_nt_session_close(smb_cli, fnum);
- if (res)
+ if (res1)
{
- DEBUG(5,("msrpc_sam_enum_users: succeeded\n"));
+ DEBUG(5,("cmd_sam_query_group: succeeded\n"));
}
else
{
- DEBUG(5,("msrpc_sam_enum_users: failed\n"));
- }
-
- return (*num_sam_entries);
-}
-
-
-/****************************************************************************
-experimental SAM users enum.
-****************************************************************************/
-void cmd_sam_enum_users(struct client_info *info)
-{
- BOOL request_user_info = False;
- BOOL request_group_info = False;
- BOOL request_alias_info = False;
- fstring tmp;
- struct acct_info *sam = NULL;
- uint32 num_sam_entries = 0;
- int i;
-
- for (i = 0; i < 3; i++)
- {
- /* a bad way to do token parsing... */
- if (next_token(NULL, tmp, NULL, sizeof(tmp)))
- {
- request_user_info |= strequal(tmp, "-u");
- request_group_info |= strequal(tmp, "-g");
- request_alias_info |= strequal(tmp, "-a");
- }
- else
- {
- break;
- }
- }
-
- msrpc_sam_enum_users(info, &sam, &num_sam_entries,
- sam_display_user,
- request_user_info ? sam_display_user_info : NULL,
- request_group_info ? sam_display_group_members : NULL,
- request_alias_info ? sam_display_group_members : NULL);
-
- if (sam != NULL)
- {
- free(sam);
+ DEBUG(5,("cmd_sam_query_group: failed\n"));
}
}
@@ -1635,8 +2216,6 @@ void cmd_sam_query_user(struct client_info *info)
uint32 num_rids;
uint32 rid[MAX_LOOKUP_SIDS];
uint32 type[MAX_LOOKUP_SIDS];
- uint32 info_level = 0x15;
- SAM_USER_INFO_21 usr;
POLICY_HND sam_pol;
POLICY_HND pol_dom;
@@ -1686,10 +2265,15 @@ void cmd_sam_query_user(struct client_info *info)
&num_rids, rid, type) : False;
/* send user info query */
- res1 = (res1 && num_rids == 1) ? get_samr_query_userinfo(smb_cli, fnum,
- &pol_dom,
- info_level, rid[0], &usr) : False;
-
+ if (res1 && num_rids == 1)
+ {
+ res1 = req_user_info(smb_cli, fnum,
+ &pol_dom,
+ domain,
+ &sid,
+ rid[0],
+ sam_display_user_info);
+ }
res = res ? samr_close(smb_cli, fnum,
&sam_pol) : False;
@@ -1701,10 +2285,6 @@ void cmd_sam_query_user(struct client_info *info)
if (res1)
{
- display_sam_user_info_21(out_hnd, ACTION_HEADER , &usr);
- display_sam_user_info_21(out_hnd, ACTION_ENUMERATE, &usr);
- display_sam_user_info_21(out_hnd, ACTION_FOOTER , &usr);
-
DEBUG(5,("cmd_sam_query_user: succeeded\n"));
}
else
@@ -1802,65 +2382,6 @@ void cmd_sam_query_dispinfo(struct client_info *info)
}
}
-
-/****************************************************************************
-experimental SAM domain info query.
-****************************************************************************/
-BOOL sam_query_dominfo(struct client_info *info, DOM_SID *sid1,
- uint32 switch_value, SAM_UNK_CTR *ctr)
-{
- uint16 fnum;
- fstring srv_name;
- BOOL res = True;
- BOOL res1 = True;
- BOOL res2 = True;
- uint32 ace_perms = 0x02000000; /* absolutely no idea. */
- POLICY_HND sam_pol;
- POLICY_HND pol_dom;
-
- fstrcpy(srv_name, "\\\\");
- fstrcat(srv_name, info->dest_host);
- strupper(srv_name);
-
- /* open SAMR session. negotiate credentials */
- res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
-
- /* establish a connection. */
- res = res ? samr_connect(smb_cli, fnum,
- srv_name, 0x02000000,
- &sam_pol) : False;
-
- /* connect to the domain */
- res1 = res ? samr_open_domain(smb_cli, fnum,
- &sam_pol, ace_perms, sid1,
- &pol_dom) : False;
-
- /* send a samr 0x8 command */
- res2 = res ? samr_query_dom_info(smb_cli, fnum,
- &pol_dom, switch_value, ctr) : False;
-
- res1 = res1 ? samr_close(smb_cli, fnum,
- &sam_pol) : False;
-
- res = res ? samr_close(smb_cli, fnum,
- &pol_dom) : False;
-
- /* close the session */
- cli_nt_session_close(smb_cli, fnum);
-
- if (res2)
- {
- DEBUG(5,("sam_query_dominfo: succeeded\n"));
- }
- else
- {
- DEBUG(5,("sam_query_dominfo: failed\n"));
- }
-
- return res2;
-}
-
-
/****************************************************************************
experimental SAM domain info query.
****************************************************************************/
@@ -1906,75 +2427,6 @@ void cmd_sam_query_dominfo(struct client_info *info)
}
}
-
-static void req_samr_aliasmem(struct cli_state *cli, uint16 fnum,
- const char *srv_name,
- POLICY_HND *pol_dom, uint32 alias_rid)
-{
- uint32 num_aliases;
- DOM_SID2 sid_mem[MAX_LOOKUP_SIDS];
-
- /* send user aliases query */
- if (get_samr_query_aliasmem(smb_cli, fnum,
- pol_dom,
- alias_rid, &num_aliases, sid_mem))
- {
- uint16 fnum_lsa;
- POLICY_HND lsa_pol;
-
- BOOL res3 = True;
- BOOL res4 = True;
- char **names = NULL;
- int num_names = 0;
- DOM_SID **sids = NULL;
- uint32 i;
-
- if (num_aliases != 0)
- {
- sids = (DOM_SID**)malloc(num_aliases * sizeof(DOM_SID*));
- }
-
- res3 = sids != NULL;
- if (res3)
- {
- for (i = 0; i < num_aliases; i++)
- {
- sids[i] = &sid_mem[i].sid;
- }
- }
-
- /* open LSARPC session. */
- res3 = res3 ? cli_nt_session_open(smb_cli, PIPE_LSARPC, &fnum_lsa) : False;
-
- /* lookup domain controller; receive a policy handle */
- res3 = res3 ? lsa_open_policy(smb_cli, fnum_lsa,
- srv_name,
- &lsa_pol, True) : False;
-
- /* send lsa lookup sids call */
- res4 = res3 ? lsa_lookup_sids(smb_cli, fnum_lsa,
- &lsa_pol,
- num_aliases, sids,
- &names, NULL, &num_names) : False;
-
- res3 = res3 ? lsa_close(smb_cli, fnum_lsa, &lsa_pol) : False;
-
- cli_nt_session_close(smb_cli, fnum_lsa);
-
- if (res4 && names != NULL)
- {
- display_alias_members(out_hnd, ACTION_HEADER , num_names, names);
- display_alias_members(out_hnd, ACTION_ENUMERATE, num_names, names);
- display_alias_members(out_hnd, ACTION_FOOTER , num_names, names);
- }
- free_char_array(num_names, names);
- if (sids != NULL)
- {
- free(sids);
- }
- }
-}
-
/****************************************************************************
SAM aliases query.
****************************************************************************/
@@ -2090,244 +2542,6 @@ void cmd_sam_enum_aliases(struct client_info *info)
}
}
-BOOL sam_query_groupmem(struct cli_state *cli, uint16 fnum,
- POLICY_HND *pol_dom,
- uint32 group_rid,
- uint32 *num_names,
- uint32 **rid_mem,
- char ***name,
- uint32 **type)
-{
- uint32 num_mem;
- uint32 *attr_mem = NULL;
- BOOL res3;
-
- *rid_mem = NULL;
- *num_names = 0;
- *name = NULL;
- *type = NULL;
-
- /* get group members */
- res3 = get_samr_query_groupmem(cli, fnum,
- pol_dom,
- group_rid, &num_mem, rid_mem, &attr_mem);
-
- if (res3 && num_mem != 0)
- {
- uint32 *rid_copy = (uint32*)malloc(num_mem * sizeof(*rid_copy));
-
- if (rid_copy != NULL)
- {
- uint32 i;
- for (i = 0; i < num_mem; i++)
- {
- rid_copy[i] = (*rid_mem)[i];
- }
- /* resolve names */
- res3 = samr_query_lookup_rids(cli, fnum,
- pol_dom, 1000,
- num_mem, rid_copy, num_names, name, type);
- }
- }
- else
- {
- if (attr_mem != NULL)
- {
- free(attr_mem);
- }
- if ((*rid_mem) != NULL)
- {
- free(*rid_mem);
- }
- attr_mem = NULL;
- *rid_mem = NULL;
- }
-
- if (!res3)
- {
- free_char_array(*num_names, *name);
- if ((*type) != NULL)
- {
- free(*type);
- }
- *num_names = 0;
- *name = NULL;
- *type = NULL;
- }
-
- if (attr_mem != NULL)
- {
- free(attr_mem);
- }
-
- return res3;
-}
-
-static void query_groupinfo(struct cli_state *cli, uint16 fnum,
- POLICY_HND *pol_dom,
- char *domain,
- DOM_SID *sid,
- uint32 group_rid,
- GROUP_INFO_FN(grp_inf))
-{
- GROUP_INFO_CTR ctr;
-
- /* send group info query */
- if (get_samr_query_groupinfo(smb_cli, fnum,
- pol_dom,
- 1, /* info level */
- group_rid, &ctr))
- {
- grp_inf(domain, sid, group_rid, &ctr);
- }
-}
-
-static void req_groupmem_info(struct cli_state *cli, uint16 fnum,
- POLICY_HND *pol_dom,
- char *domain,
- DOM_SID *sid,
- uint32 group_rid,
- char *group_name,
- GROUP_MEM_FN(grp_mem))
-{
- uint32 num_names = 0;
- char **name = NULL;
- uint32 *type = NULL;
- uint32 *rid_mem = NULL;
-
- if (sam_query_groupmem(cli, fnum, pol_dom, group_rid,
- &num_names, &rid_mem, &name, &type))
- {
- grp_mem(domain, sid,
- group_rid, group_name,
- num_names, rid_mem, name, type);
-
- free_char_array(num_names, name);
- if (type != NULL)
- {
- free(type);
- }
- }
-}
-
-/****************************************************************************
-SAM groups query.
-****************************************************************************/
-uint32 msrpc_sam_enum_groups(struct client_info *info,
- struct acct_info **sam,
- uint32 *num_sam_entries,
- GROUP_FN(grp_fn),
- GROUP_INFO_FN(grp_inf_fn),
- GROUP_MEM_FN(grp_mem_fn))
-{
- uint16 fnum;
- fstring srv_name;
- fstring domain;
- fstring sid;
- DOM_SID sid1;
- BOOL res = True;
- uint32 ace_perms = 0x02000000; /* access control permissions. */
- POLICY_HND sam_pol;
- POLICY_HND pol_dom;
- uint32 status;
-
- sid_copy(&sid1, &info->dom.level5_sid);
-
- if (sid1.num_auths == 0)
- {
- report(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
- return 0;
- }
-
- sid_to_string(sid, &sid1);
- fstrcpy(domain, info->dom.level3_dom);
-
- fstrcpy(srv_name, "\\\\");
- fstrcat(srv_name, info->dest_host);
- strupper(srv_name);
-
- report(out_hnd, "SAM Enumerate Groups\n");
- report(out_hnd, "From: %s To: %s Domain: %s SID: %s\n",
- info->myhostname, srv_name, domain, sid);
-
- /* open SAMR session. negotiate credentials */
- res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
-
- /* establish a connection. */
- res = res ? samr_connect(smb_cli, fnum,
- srv_name, 0x02000000,
- &sam_pol) : False;
-
- /* connect to the domain */
- res = res ? samr_open_domain(smb_cli, fnum,
- &sam_pol, ace_perms, &sid1,
- &pol_dom) : False;
-
- (*sam) = NULL;
-
- if (res)
- {
- uint32 group_idx;
- uint32 start_idx = 0;
- /* read some groups */
- do
- {
- status = samr_enum_dom_groups(smb_cli, fnum,
- &pol_dom,
- &start_idx, 0x100000,
- sam, num_sam_entries);
-
- } while (status == STATUS_MORE_ENTRIES);
-
- if ((*num_sam_entries) == 0)
- {
- report(out_hnd, "No groups\n");
- }
-
- for (group_idx = 0; group_idx < (*num_sam_entries); group_idx++)
- {
- uint32 group_rid = (*sam)[group_idx].rid;
- char *group_name = (*sam)[group_idx].acct_name;
-
- grp_fn(domain, &sid1, group_rid, group_name);
-
- if (grp_inf_fn)
- {
- query_groupinfo(smb_cli, fnum, &pol_dom,
- domain, &sid1,
- group_rid,
- grp_inf_fn);
- }
- if (grp_mem_fn != NULL)
- {
- req_groupmem_info(smb_cli, fnum, &pol_dom,
- domain, &sid1,
- group_rid, group_name,
- grp_mem_fn);
- }
- }
- }
-
- res = res ? samr_close(smb_cli, fnum,
- &pol_dom) : False;
-
- res = res ? samr_close(smb_cli, fnum,
- &sam_pol) : False;
-
- /* close the session */
- cli_nt_session_close(smb_cli, fnum);
-
- if (res)
- {
- DEBUG(5,("msrpc_sam_enum_groups: succeeded\n"));
- }
- else
- {
- DEBUG(5,("msrpc_sam_enum_groups: failed\n"));
- }
- return (*num_sam_entries);
-}
-
/****************************************************************************
experimental SAM groups enum.
****************************************************************************/
@@ -2354,6 +2568,8 @@ void cmd_sam_enum_groups(struct client_info *info)
}
}
+ report(out_hnd, "SAM Enumerate Groups\n");
+
msrpc_sam_enum_groups(info, &sam, &num_sam_entries,
sam_display_group,
request_group_info ? sam_display_group_info : NULL,
diff --git a/source3/rpcclient/rpcclient.c b/source3/rpcclient/rpcclient.c
index 3663d97293..9068b0af5a 100644
--- a/source3/rpcclient/rpcclient.c
+++ b/source3/rpcclient/rpcclient.c
@@ -101,7 +101,8 @@ static void rpcclient_stop(void)
#define COMPL_NONE 0
#define COMPL_REGKEY 1
-#define COMPL_REGVAL 2
+#define COMPL_SAMUSR 3
+#define COMPL_SAMGRP 4
/****************************************************************************
This defines the commands supported by this client
@@ -112,60 +113,393 @@ struct
void (*fn)(struct client_info*);
char *description;
char compl_args[2];
-} commands[] =
+}
+commands[] =
{
- {"eventlog", cmd_eventlog, "list the events",{COMPL_NONE, COMPL_NONE}},
- {"svcenum", cmd_svc_enum, "[-i] Lists Services Manager",{COMPL_NONE, COMPL_NONE}},
- {"at", cmd_at, "Scheduler control (at /? for syntax)",{COMPL_NONE, COMPL_NONE}},
- {"time", cmd_time, "Display remote time",{COMPL_NONE, COMPL_NONE}},
- {"regenum", cmd_reg_enum, "<keyname> Registry Enumeration (keys, values)",{COMPL_REGKEY, COMPL_NONE}},
- {"regdeletekey",cmd_reg_delete_key, "<keyname> Registry Key Delete",{COMPL_REGKEY, COMPL_NONE}},
- {"regcreatekey",cmd_reg_create_key, "<keyname> [keyclass] Registry Key Create",{COMPL_REGKEY, COMPL_NONE}},
- {"shutdown",cmd_reg_shutdown, "[-m message] [-t timeout] [-r or --reboot] Server Shutdown",{COMPL_NONE, COMPL_NONE}},
- {"regquerykey",cmd_reg_query_key, "<keyname> Registry Key Query",{COMPL_REGKEY, COMPL_NONE}},
- {"regdeleteval",cmd_reg_delete_val, "<valname> Registry Value Delete",{COMPL_REGKEY, COMPL_REGVAL}},
- {"regcreateval",cmd_reg_create_val, "<valname> <valtype> <value> Registry Key Create",{COMPL_REGKEY, COMPL_NONE}},
- {"reggetsec", cmd_reg_get_key_sec, "<keyname> Registry Key Security",{COMPL_REGKEY, COMPL_NONE}},
- {"regtestsec", cmd_reg_test_key_sec, "<keyname> Test Registry Key Security",{COMPL_REGKEY, COMPL_NONE}},
- {"ntlogin", cmd_netlogon_login_test, "[username] [password] NT Domain login test",{COMPL_NONE, COMPL_NONE}},
- {"domtrust", cmd_netlogon_domain_test, "<domain> NT Inter-Domain test",{COMPL_NONE, COMPL_NONE}},
- {"wksinfo", cmd_wks_query_info, "Workstation Query Info",{COMPL_NONE, COMPL_NONE}},
- {"srvinfo", cmd_srv_query_info, "Server Query Info",{COMPL_NONE, COMPL_NONE}},
- {"srvsessions",cmd_srv_enum_sess, "List sessions on a server",{COMPL_NONE, COMPL_NONE}},
- {"srvshares", cmd_srv_enum_shares, "List shares on a server",{COMPL_NONE, COMPL_NONE}},
- {"srvconnections",cmd_srv_enum_conn, "List connections on a server",{COMPL_NONE, COMPL_NONE}},
- {"srvfiles", cmd_srv_enum_files, "List files on a server",{COMPL_NONE, COMPL_NONE}},
- {"lsaquery", cmd_lsa_query_info, "Query Info Policy (domain member or server)",{COMPL_NONE, COMPL_NONE}},
- {"lookupsids", cmd_lsa_lookup_sids, "Resolve names from SIDs",{COMPL_NONE, COMPL_NONE}},
- {"lookupnames",cmd_lsa_lookup_names, "Resolve SIDs from names",{COMPL_NONE, COMPL_NONE}},
- {"lookupdomain",cmd_sam_lookup_domain, "Obtain SID for a local domain",{COMPL_NONE, COMPL_NONE}},
- {"enumusers", cmd_sam_enum_users, "SAM User Database Query (experimental!)",{COMPL_NONE, COMPL_NONE}},
- {"addgroupmem",cmd_sam_add_groupmem,"<group rid> [member rid1] [member rid2] ... SAM Add Domain Group Member",{COMPL_NONE, COMPL_NONE}},
- {"addaliasmem",cmd_sam_add_aliasmem,"<alias rid> [member sid1] [member sid2] ... SAM Add Domain Alias Member",{COMPL_NONE, COMPL_NONE}},
- {"delgroupmem",cmd_sam_del_groupmem,"<group rid> [member rid1] [member rid2] ... SAM Delete Domain Group Member",{COMPL_NONE, COMPL_NONE}},
- {"delaliasmem",cmd_sam_del_aliasmem,"<alias rid> [member sid1] [member sid2] ... SAM Delete Domain Alias Member",{COMPL_NONE, COMPL_NONE}},
- {"creategroup",cmd_sam_create_dom_group,"SAM Create Domain Group",{COMPL_NONE, COMPL_NONE}},
- {"createalias",cmd_sam_create_dom_alias,"SAM Create Domain Alias",{COMPL_NONE, COMPL_NONE}},
- {"createuser", cmd_sam_create_dom_user,"<username> SAM Create Domain User",{COMPL_NONE, COMPL_NONE}},
- {"delgroup", cmd_sam_delete_dom_group,"SAM Delete Domain Group",{COMPL_NONE, COMPL_NONE}},
- {"delalias", cmd_sam_delete_dom_alias,"SAM Delete Domain Alias",{COMPL_NONE, COMPL_NONE}},
- {"ntpass", cmd_sam_ntchange_pwd, "NT SAM Password Change",{COMPL_NONE, COMPL_NONE}},
- {"samuser", cmd_sam_query_user, "<username> SAM User Query (experimental!)",{COMPL_NONE, COMPL_NONE}},
- {"samtest", cmd_sam_test , "SAM User Encrypted RPC test (experimental!)",{COMPL_NONE, COMPL_NONE}},
- {"enumaliases",cmd_sam_enum_aliases, "SAM Aliases Database Query (experimental!)",{COMPL_NONE, COMPL_NONE}},
- {"enumgroups", cmd_sam_enum_groups, "SAM Group Database Query (experimental!)",{COMPL_NONE, COMPL_NONE}},
- {"dominfo", cmd_sam_query_dominfo, "SAM Query Domain Info",{COMPL_NONE, COMPL_NONE}},
- {"dispinfo", cmd_sam_query_dispinfo, "SAM Query Display Info",{COMPL_NONE, COMPL_NONE}},
- {"querysecret", cmd_lsa_query_secret, "LSA Query Secret (developer use)",{COMPL_NONE, COMPL_NONE}},
- {"samsync", cmd_sam_sync, "SAM Synchronization Test (experimental)",{COMPL_NONE, COMPL_NONE}},
- {"quit", cmd_quit, "logoff the server",{COMPL_NONE, COMPL_NONE}},
- {"q", cmd_quit, "logoff the server",{COMPL_NONE, COMPL_NONE}},
- {"exit", cmd_quit, "logoff the server",{COMPL_NONE, COMPL_NONE}},
- {"bye", cmd_quit, "logoff the server",{COMPL_NONE, COMPL_NONE}},
- {"help", cmd_help, "[command] give help on a command",{COMPL_NONE, COMPL_NONE}},
- {"?", cmd_help, "[command] give help on a command",{COMPL_NONE, COMPL_NONE}},
- {"!", NULL, "run a shell command on the local system",{COMPL_NONE, COMPL_NONE}},
- {"", NULL, NULL,{COMPL_NONE, COMPL_NONE}}
+ /*
+ * eventlog
+ */
+
+ {
+ "eventlog",
+ cmd_eventlog,
+ "list the events",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * service control
+ */
+
+ {
+ "svcenum",
+ cmd_svc_enum,
+ "[-i] Lists Services Manager",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * scheduler
+ */
+
+ {
+ "at",
+ cmd_at,
+ "Scheduler control (at /? for syntax)",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * registry
+ */
+
+ {
+ "regenum",
+ cmd_reg_enum,
+ "<keyname> Registry Enumeration (keys, values)",
+ {COMPL_REGKEY, COMPL_NONE}
+ },
+ {
+ "regdeletekey",
+ cmd_reg_delete_key,
+ "<keyname> Registry Key Delete",
+ {COMPL_REGKEY, COMPL_NONE}
+ },
+ {
+ "regcreatekey",
+ cmd_reg_create_key,
+ "<keyname> [keyclass] Registry Key Create",
+ {COMPL_REGKEY, COMPL_NONE}
+ },
+ {
+ "shutdown",
+ cmd_reg_shutdown,
+ "[-m message] [-t timeout] [-r or --reboot] Server Shutdown",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "regquerykey",
+ cmd_reg_query_key,
+ "<keyname> Registry Key Query",
+ {COMPL_REGKEY, COMPL_NONE}
+ },
+ {
+ "regdeleteval",
+ cmd_reg_delete_val,
+ "<valname> Registry Value Delete",
+ {COMPL_REGKEY, COMPL_REGKEY}
+ },
+ {
+ "regcreateval",
+ cmd_reg_create_val,
+ "<valname> <valtype> <value> Registry Key Create",
+ {COMPL_REGKEY, COMPL_NONE}
+ },
+ {
+ "reggetsec",
+ cmd_reg_get_key_sec,
+ "<keyname> Registry Key Security",
+ {COMPL_REGKEY, COMPL_NONE}
+ },
+ {
+ "regtestsec",
+ cmd_reg_test_key_sec,
+ "<keyname> Test Registry Key Security",
+ {COMPL_REGKEY, COMPL_NONE}
+ },
+
+ /*
+ * server
+ */
+ {
+ "time",
+ cmd_time,
+ "Display remote time",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ {
+ "wksinfo",
+ cmd_wks_query_info,
+ "Workstation Query Info",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "srvinfo",
+ cmd_srv_query_info,
+ "Server Query Info",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "srvsessions",
+ cmd_srv_enum_sess,
+ "List sessions on a server",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "srvshares",
+ cmd_srv_enum_shares,
+ "List shares on a server",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "srvconnections",
+ cmd_srv_enum_conn,
+ "List connections on a server",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "srvfiles",
+ cmd_srv_enum_files,
+ "List files on a server",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * lsa
+ */
+
+ {
+ "lsaquery",
+ cmd_lsa_query_info,
+ "Query Info Policy (domain member or server)",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "lookupsids",
+ cmd_lsa_lookup_sids,
+ "Resolve names from SIDs",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "lookupnames",
+ cmd_lsa_lookup_names,
+ "Resolve SIDs from names",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "querysecret",
+ cmd_lsa_query_secret,
+ "LSA Query Secret (developer use)",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * netlogon
+ */
+
+ {
+ "ntlogin",
+ cmd_netlogon_login_test,
+ "[username] [password] NT Domain login test",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "domtrust",
+ cmd_netlogon_domain_test,
+ "<domain> NT Inter-Domain test",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * sam
+ */
+
+ {
+ "lookupdomain",
+ cmd_sam_lookup_domain,
+ "Obtain SID for a local domain",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "enumusers",
+ cmd_sam_enum_users,
+ "SAM User Database Query (experimental!)",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "addgroupmem",
+ cmd_sam_add_groupmem,
+ "<group rid> [member rid1] [member rid2] ... SAM Add Domain Group Member",
+ {COMPL_SAMGRP, COMPL_SAMGRP}
+ },
+
+ {
+ "addaliasmem",
+ cmd_sam_add_aliasmem,
+ "<alias rid> [member sid1] [member sid2] ... SAM Add Domain Alias Member",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "delgroupmem",
+ cmd_sam_del_groupmem,
+ "<group rid> [member rid1] [member rid2] ... SAM Delete Domain Group Member",
+ {COMPL_SAMGRP, COMPL_SAMGRP}
+ },
+ {
+ "delaliasmem",
+ cmd_sam_del_aliasmem,
+ "<alias rid> [member sid1] [member sid2] ... SAM Delete Domain Alias Member",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "creategroup",
+ cmd_sam_create_dom_group,
+ "SAM Create Domain Group",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "createalias",
+ cmd_sam_create_dom_alias,
+ "SAM Create Domain Alias",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "createuser",
+ cmd_sam_create_dom_user,
+ "<username> SAM Create Domain User",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "delgroup",
+ cmd_sam_delete_dom_group,
+ "SAM Delete Domain Group",
+ {COMPL_SAMGRP, COMPL_NONE}
+ },
+ {
+ "delalias",
+ cmd_sam_delete_dom_alias,
+ "SAM Delete Domain Alias",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "ntpass",
+ cmd_sam_ntchange_pwd,
+ "NT SAM Password Change",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "samuser",
+ cmd_sam_query_user,
+ "<username> SAM User Query (experimental!)",
+ {COMPL_SAMUSR, COMPL_NONE}
+ },
+ {
+ "samgroup",
+ cmd_sam_query_group,
+ "<username> SAM Group Query (experimental!)",
+ {COMPL_SAMGRP, COMPL_NONE}
+ },
+ {
+ "samgroupmem",
+ cmd_sam_query_groupmem,
+ "SAM Group Members (experimental!)",
+ {COMPL_SAMGRP, COMPL_NONE}
+ },
+ {
+ "samtest",
+ cmd_sam_test ,
+ "SAM User Encrypted RPC test (experimental!)",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "enumaliases",
+ cmd_sam_enum_aliases,
+ "SAM Aliases Database Query (experimental!)",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "enumgroups",
+ cmd_sam_enum_groups,
+ "SAM Group Database Query (experimental!)",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "dominfo",
+ cmd_sam_query_dominfo,
+ "SAM Query Domain Info",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "dispinfo",
+ cmd_sam_query_dispinfo,
+ "SAM Query Display Info",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "samsync",
+ cmd_sam_sync,
+ "SAM Synchronization Test (experimental)",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * bye bye
+ */
+
+ {
+ "quit",
+ cmd_quit,
+ "logoff the server",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "q",
+ cmd_quit,
+ "logoff the server",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "exit",
+ cmd_quit,
+ "logoff the server",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "bye",
+ cmd_quit,
+ "logoff the server",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * eek!
+ */
+
+ {
+ "help",
+ cmd_help,
+ "[command] give help on a command",
+ {COMPL_NONE, COMPL_NONE}
+ },
+ {
+ "?",
+ cmd_help,
+ "[command] give help on a command",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * shell
+ */
+
+ {
+ "!",
+ NULL,
+ "run a shell command on the local system",
+ {COMPL_NONE, COMPL_NONE}
+ },
+
+ /*
+ * oop!
+ */
+
+ {
+ "",
+ NULL,
+ NULL,
+ {COMPL_NONE, COMPL_NONE}
+ }
};
@@ -471,25 +805,12 @@ static void reg_init(int val, const char *full_keyname, int num)
}
}
-static int key_val = 0;
-static void add_reg_name(const char *name)
-{
- reg_name = (char**)Realloc(reg_name, (reg_list_len+1) *
- sizeof(reg_name[0]));
-
- if (reg_name != NULL)
- {
- reg_name[reg_list_len] = strdup(name);
- reg_list_len++;
- }
-}
static void reg_key_list(const char *full_name,
const char *name, time_t key_mod_time)
{
- if (IS_BITS_SET_ALL(key_val, 1))
- {
- add_reg_name(name);
- }
+ fstring key_name;
+ slprintf(key_name, sizeof(key_name)-1, "%s\\", name);
+ add_chars_to_array(&reg_list_len, &reg_name, key_name);
}
static void reg_val_list(const char *full_name,
@@ -497,24 +818,29 @@ static void reg_val_list(const char *full_name,
uint32 type,
BUFFER2 *value)
{
- if (IS_BITS_SET_ALL(key_val, 2))
- {
- add_reg_name(name);
- }
+ add_chars_to_array(&reg_list_len, &reg_name, name);
}
-static pstring last_full_keyname = "";
+static char **cmd_argv;
+static uint32 cmd_argc;
-char *complete_regenum(char *text, int state)
+static char *complete_regenum(char *text, int state)
{
pstring full_keyname;
static uint32 i = 0;
- DEBUG(10,("complete_regenum: %s (%d)\n", text, state));
-
if (state == 0)
{
- pstrcpy(full_keyname, cli_info.cur_dir);
+ if (cmd_argc >= 2 && cmd_argv != NULL && cmd_argv[1] != NULL)
+ {
+ char *sep;
+ pstrcpy(full_keyname, cmd_argv[1]);
+ sep = strrchr(full_keyname, '\\');
+ if (sep != NULL)
+ {
+ *sep = 0;
+ }
+ }
/* Iterate all keys / values */
if (!msrpc_reg_enum_key(smb_cli, full_keyname,
@@ -528,28 +854,11 @@ char *complete_regenum(char *text, int state)
for (; i < reg_list_len; i++)
{
- DEBUG(10,("match: %s key: %s\n", text, reg_name[i]));
if (text == NULL || text[0] == 0 ||
strnequal(text, reg_name[i], strlen(text)))
{
- pstring tmp_keyname;
char *name = strdup(reg_name[i]);
i++;
-
- slprintf(tmp_keyname, sizeof(tmp_keyname)-1, "%s\\%s",
- cli_info.cur_dir, name);
-
- /* Iterate all keys / values */
- if (msrpc_reg_enum_key(smb_cli, tmp_keyname,
- NULL, NULL, NULL))
- {
- pstrcpy(last_full_keyname, tmp_keyname);
- }
- else
- {
- last_full_keyname[0] = 0;
- }
-
return name;
}
}
@@ -557,43 +866,84 @@ char *complete_regenum(char *text, int state)
return NULL;
}
-char *complete_end_reg(char *text, int state)
+
+static char *complete_samenum_usr(char *text, int state)
{
- pstring full_keyname;
+ static uint32 i = 0;
+ static uint32 num_usrs = 0;
+ static struct acct_info *sam = NULL;
- DEBUG(10,("complete_end_reg: %s (%d)\n", text, state));
-
if (state == 0)
{
- slprintf(full_keyname, sizeof(full_keyname)-1, "%s\\%s",
- cli_info.cur_dir, text);
+ free(sam);
+ sam = NULL;
+ num_usrs = 0;
- /* Iterate all keys / values */
- if (msrpc_reg_enum_key(smb_cli, full_keyname,
- reg_init, reg_key_list, reg_val_list))
+ /* Iterate all users */
+ if (msrpc_sam_enum_users(&cli_info, &sam, &num_usrs,
+ NULL, NULL, NULL, NULL) == 0)
{
- pstrcpy(cli_info.cur_dir, full_keyname);
+ return NULL;
}
+
+ i = 0;
}
+ for (; i < num_usrs; i++)
+ {
+ char *usr_name = sam[i].acct_name;
+ if (text == NULL || text[0] == 0 ||
+ strnequal(text, usr_name, strlen(text)))
+ {
+ char *name = strdup(usr_name);
+ i++;
+ return name;
+ }
+ }
+
return NULL;
}
-char *complete_regenum_key(char *text, int state)
+static char *complete_samenum_grp(char *text, int state)
{
- key_val = 1;
- return complete_regenum(text, state);
-}
+ static uint32 i = 0;
+ static uint32 num_grps = 0;
+ static struct acct_info *sam = NULL;
+
+ if (state == 0)
+ {
+ free(sam);
+ sam = NULL;
+ num_grps = 0;
-char *complete_regenum_val(char *text, int state)
-{
- key_val = 2;
- return complete_regenum(text, state);
+ /* Iterate all groups */
+ if (msrpc_sam_enum_groups(&cli_info, &sam, &num_grps,
+ NULL, NULL, NULL) == 0)
+ {
+ return NULL;
+ }
+
+ i = 0;
+ }
+
+ for (; i < num_grps; i++)
+ {
+ char *grp_name = sam[i].acct_name;
+ if (text == NULL || text[0] == 0 ||
+ strnequal(text, grp_name, strlen(text)))
+ {
+ char *name = strdup(grp_name);
+ i++;
+ return name;
+ }
+ }
+
+ return NULL;
}
/* Complete an rpcclient command */
-char *complete_cmd(char *text, int state)
+static char *complete_cmd(char *text, int state)
{
static int cmd_index;
char *name;
@@ -617,17 +967,33 @@ char *complete_cmd(char *text, int state)
/* Main completion function */
-char **completion_fn(char *text, int start, int end)
+static char **completion_fn(char *text, int start, int end)
{
+ pstring tmp;
+ pstring cmd_partial;
int cmd_index;
int num_words;
+ char *ptr = cmd_partial;
int i;
char lastch = ' ';
+ free_char_array(cmd_argc, cmd_argv);
+ cmd_argc = 0;
+ cmd_argv = NULL;
+
+ safe_strcpy(cmd_partial, rl_line_buffer,
+ MAX(sizeof(cmd_partial),end)-1);
+
+ if (next_token(&ptr, tmp, NULL, sizeof(tmp)))
+ {
+ add_chars_to_array(&cmd_argc, &cmd_argv, tmp);
+ }
+
/* Complete rpcclient command */
- if (start == 0) {
+ if (start == 0)
+ {
return completion_matches(text, complete_cmd);
}
@@ -636,7 +1002,13 @@ char **completion_fn(char *text, int start, int end)
num_words = 0;
for (i = 0; i <= end; i++) {
if ((rl_line_buffer[i] != ' ') && (lastch == ' '))
- num_words++;
+ {
+ if (next_token(&ptr, tmp, NULL, sizeof(tmp)))
+ {
+ add_chars_to_array(&cmd_argc, &cmd_argv, tmp);
+ }
+ num_words++;
+ }
lastch = rl_line_buffer[i];
}
@@ -660,11 +1032,14 @@ char **completion_fn(char *text, int start, int end)
switch (commands[cmd_index].compl_args[num_words - 2])
{
- case COMPL_REGVAL:
- return completion_matches(text, complete_regenum_val);
+ case COMPL_SAMGRP:
+ return completion_matches(text, complete_samenum_grp);
+
+ case COMPL_SAMUSR:
+ return completion_matches(text, complete_samenum_usr);
case COMPL_REGKEY:
- return completion_matches(text, complete_regenum_key);
+ return completion_matches(text, complete_regenum);
default:
/* An invalid completion type */
@@ -683,16 +1058,8 @@ char **completion_fn(char *text, int start, int end)
completions are found, we assign this stub completion function
to the rl_completion_entry_function variable. */
-char *complete_cmd_null(char *text, int state)
+static char *complete_cmd_null(char *text, int state)
{
- DEBUG(10,("complete_cmd_null: %s %d\n", text, state));
-
- if (last_full_keyname[0] != 0)
- {
- DEBUG(10,("last_keyname: %s\n", last_full_keyname));
- pstrcpy(cli_info.cur_dir, last_full_keyname);
-
- }
return NULL;
}