The Samba-Bugzilla – Attachment 4549 Details for
Bug 6592
Samba server does not respond properly to NetWkstaGetInfo and NetWkstaUserEnum requests
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
Updated patch
smb.patch (text/plain), 15.22 KB, created by
Ian Puleston
on 2009-08-12 16:19:45 UTC
(
hide
)
Description:
Updated patch
Filename:
MIME Type:
Creator:
Ian Puleston
Created:
2009-08-12 16:19:45 UTC
Size:
15.22 KB
patch
obsolete
>From 6ca83b9d015479ccddc45598974da2045bea3033 Mon Sep 17 00:00:00 2001 >From: Volker Lendecke <vl@samba.org> >Date: Mon, 3 Aug 2009 16:52:01 +0200 >Subject: [PATCH] Support NetWkstaGetInfo 101 and 102 > >--- > source3/configure.in | 2 +- > source3/rpc_server/srv_wkssvc_nt.c | 128 +++++++++++++++++++++++++++++++---- > 2 files changed, 114 insertions(+), 16 deletions(-) > >diff --git a/source3/configure.in b/source3/configure.in >index 7cfd3fb..068f9cd 100644 >--- a/source3/configure.in >+++ b/source3/configure.in >@@ -2016,7 +2016,7 @@ dnl We need to check for many of them > dnl But we don't need to do each and every one, because our code uses > dnl mostly just the utmp (not utmpx) fields. > >-AC_CHECK_FUNCS(pututline pututxline updwtmp updwtmpx getutmpx) >+AC_CHECK_FUNCS(pututline pututxline updwtmp updwtmpx getutmpx getutxent) > > AC_CACHE_CHECK([for ut_name in utmp],samba_cv_HAVE_UT_UT_NAME,[ > AC_TRY_COMPILE([#include <sys/types.h> >diff -u a/source3/include/config.h.in b/source3/include/config.h.in >>smb.patch >--- a/source3/include/config.h.in 2008-09-18 04:58:36.000000000 -0700 >+++ b/source3/include/config.h.in 2009-08-06 13:42:20.000000000 -0700 >@@ -676,6 +676,9 @@ > /* Define to 1 if you have the `getutmpx' function. */ > #undef HAVE_GETUTMPX > >+/* Define to 1 if you have the `getutxent' function. */ >+#undef HAVE_GETUTXENT >+ > /* Define to 1 if you have the `getxattr' function. */ > #undef HAVE_GETXATTR > > >diff --git a/source3/rpc_server/srv_wkssvc_nt.c b/source3/rpc_server/srv_wkssvc_nt.c >index b06818e..0f889db 100644 >--- a/source3/rpc_server/srv_wkssvc_nt.c >+++ b/source3/rpc_server/srv_wkssvc_nt.c >@@ -29,12 +29,54 @@ > #undef DBGC_CLASS > #define DBGC_CLASS DBGC_RPC_SRV > >+#ifdef HAVE_GETUTXENT >+ >+#include <utmpx.h> >+ >+static char **get_logged_on_userlist(TALLOC_CTX *mem_ctx) >+{ >+ char **users = NULL; >+ int num_users = 0; >+ struct utmpx *u; >+ >+ while ((u = getutxent()) != NULL) { >+ char **tmp; >+ tmp = talloc_realloc(mem_ctx, users, char *, num_users+1); >+ if (tmp == NULL) { >+ return NULL; >+ } >+ users = tmp; >+ users[num_users] = talloc_strdup(users, u->ut_user); >+ if (users[num_users] == NULL) { >+ TALLOC_FREE(users); >+ return NULL; >+ } >+ } >+ return users; >+} >+ >+#else >+ >+static char **get_logged_on_userlist(TALLOC_CTX *mem_ctx) >+{ >+ return NULL; >+} >+ >+#endif >+ > /******************************************************************* > Fill in the values for the struct wkssvc_NetWkstaInfo100. > ********************************************************************/ > >-static void create_wks_info_100(struct wkssvc_NetWkstaInfo100 *info100) >+static struct wkssvc_NetWkstaInfo100 *create_wks_info_100(TALLOC_CTX *mem_ctx) > { >+ struct wkssvc_NetWkstaInfo100 *info100; >+ >+ info100 = talloc(mem_ctx, struct wkssvc_NetWkstaInfo100); >+ if (info100 == NULL) { >+ return NULL; >+ } >+ > info100->platform_id = PLATFORM_ID_NT; /* unknown */ > info100->version_major = lp_major_announce_version(); > info100->version_minor = lp_minor_announce_version(); >@@ -44,7 +86,56 @@ static void create_wks_info_100(struct wkssvc_NetWkstaInfo100 *info100) > info100->domain_name = talloc_asprintf_strupper_m( > info100, "%s", lp_workgroup()); > >- return; >+ return info100; >+} >+ >+static struct wkssvc_NetWkstaInfo101 *create_wks_info_101(TALLOC_CTX *mem_ctx) >+{ >+ struct wkssvc_NetWkstaInfo101 *info101; >+ >+ info101 = talloc(mem_ctx, struct wkssvc_NetWkstaInfo101); >+ if (info101 == NULL) { >+ return NULL; >+ } >+ >+ info101->platform_id = PLATFORM_ID_NT; /* unknown */ >+ info101->version_major = lp_major_announce_version(); >+ info101->version_minor = lp_minor_announce_version(); >+ >+ info101->server_name = talloc_asprintf_strupper_m( >+ info101, "%s", global_myname()); >+ info101->domain_name = talloc_asprintf_strupper_m( >+ info101, "%s", lp_workgroup()); >+ info101->lan_root = NULL; >+ >+ return info101; >+} >+ >+static struct wkssvc_NetWkstaInfo102 *create_wks_info_102(TALLOC_CTX *mem_ctx) >+{ >+ struct wkssvc_NetWkstaInfo102 *info102; >+ char **users; >+ >+ info102 = talloc(mem_ctx, struct wkssvc_NetWkstaInfo102); >+ if (info102 == NULL) { >+ return NULL; >+ } >+ >+ info102->platform_id = PLATFORM_ID_NT; /* unknown */ >+ info102->version_major = lp_major_announce_version(); >+ info102->version_minor = lp_minor_announce_version(); >+ >+ info102->server_name = talloc_asprintf_strupper_m( >+ info102, "%s", global_myname()); >+ info102->domain_name = talloc_asprintf_strupper_m( >+ info102, "%s", lp_workgroup()); >+ info102->lan_root = NULL; >+ >+ users = get_logged_on_userlist(talloc_tos()); >+ info102->logged_on_users = talloc_array_length(users); >+ TALLOC_FREE(users); >+ >+ return info102; > } > > /******************************************************************** >@@ -53,22 +144,29 @@ static void create_wks_info_100(struct wkssvc_NetWkstaInfo100 *info100) > > WERROR _wkssvc_NetWkstaGetInfo(pipes_struct *p, struct wkssvc_NetWkstaGetInfo *r) > { >- struct wkssvc_NetWkstaInfo100 *wks100 = NULL; >- >- /* We only support info level 100 currently */ >- >- if ( r->in.level != 100 ) { >+ switch (r->in.level) { >+ case 100: >+ r->out.info->info100 = create_wks_info_100(p->mem_ctx); >+ if (r->out.info->info100 == NULL) { >+ return WERR_NOMEM; >+ } >+ break; >+ case 101: >+ r->out.info->info101 = create_wks_info_101(p->mem_ctx); >+ if (r->out.info->info101 == NULL) { >+ return WERR_NOMEM; >+ } >+ break; >+ case 102: >+ r->out.info->info102 = create_wks_info_102(p->mem_ctx); >+ if (r->out.info->info102 == NULL) { >+ return WERR_NOMEM; >+ } >+ break; >+ default: > return WERR_UNKNOWN_LEVEL; > } > >- if ( (wks100 = TALLOC_ZERO_P(p->mem_ctx, struct wkssvc_NetWkstaInfo100)) == NULL ) { >- return WERR_NOMEM; >- } >- >- create_wks_info_100( wks100 ); >- >- r->out.info->info100 = wks100; >- > return WERR_OK; > } > >-- >1.6.0.1 > > >From 51256d7f8fdea4e00c92af268328b5bbf2a965a5 Mon Sep 17 00:00:00 2001 >From: Volker Lendecke <vl@samba.org> >Date: Mon, 3 Aug 2009 17:27:11 +0200 >Subject: [PATCH] First cut at _wkssvc_NetWkstaEnumUsers > >This needs access checks! >--- > source3/rpc_server/srv_wkssvc_nt.c | 55 ++++++++++++++++++++++++++++++++++-- > 1 files changed, 52 insertions(+), 3 deletions(-) > >diff --git a/source3/rpc_server/srv_wkssvc_nt.c b/source3/rpc_server/srv_wkssvc_nt.c >index 0f889db..b1deceb 100644 >--- a/source3/rpc_server/srv_wkssvc_nt.c >+++ b/source3/rpc_server/srv_wkssvc_nt.c >@@ -41,6 +41,9 @@ static char **get_logged_on_userlist(TALLOC_CTX *mem_ctx) > > while ((u = getutxent()) != NULL) { > char **tmp; >+ if (u->ut_type != USER_PROCESS) { >+ continue; >+ } > tmp = talloc_realloc(mem_ctx, users, char *, num_users+1); > if (tmp == NULL) { > return NULL; >@@ -51,6 +54,7 @@ static char **get_logged_on_userlist(TALLOC_CTX *mem_ctx) > TALLOC_FREE(users); > return NULL; > } >+ num_users += 1; > } > return users; > } >@@ -180,14 +184,59 @@ WERROR _wkssvc_NetWkstaSetInfo(pipes_struct *p, struct wkssvc_NetWkstaSetInfo *r > return WERR_NOT_SUPPORTED; > } > >+static struct wkssvc_NetWkstaEnumUsersCtr0 *create_enum_users0( >+ TALLOC_CTX *mem_ctx) >+{ >+ struct wkssvc_NetWkstaEnumUsersCtr0 *ctr0; >+ char **users; >+ int i, num_users; >+ >+ ctr0 = talloc(mem_ctx, struct wkssvc_NetWkstaEnumUsersCtr0); >+ if (ctr0 == NULL) { >+ return NULL; >+ } >+ >+ users = get_logged_on_userlist(talloc_tos()); >+ if (users == NULL) { >+ TALLOC_FREE(ctr0); >+ return NULL; >+ } >+ >+ num_users = talloc_array_length(users); >+ ctr0->entries_read = num_users; >+ ctr0->user0 = talloc_array(ctr0, struct wkssvc_NetrWkstaUserInfo0, >+ num_users); >+ if (ctr0->user0 == NULL) { >+ TALLOC_FREE(ctr0); >+ TALLOC_FREE(users); >+ return NULL; >+ } >+ >+ for (i=0; i<num_users; i++) { >+ ctr0->user0[i].user_name = talloc_move(ctr0->user0, &users[i]); >+ } >+ TALLOC_FREE(users); >+ return ctr0; >+} >+ > /******************************************************************** > ********************************************************************/ > > WERROR _wkssvc_NetWkstaEnumUsers(pipes_struct *p, struct wkssvc_NetWkstaEnumUsers *r) > { >- /* FIXME: Add implementation code here */ >- p->rng_fault_state = True; >- return WERR_NOT_SUPPORTED; >+ if (r->in.info->level != 0) { >+ return WERR_UNKNOWN_LEVEL; >+ } >+ >+ r->out.info->ctr.user0 = create_enum_users0(p->mem_ctx); >+ if (r->out.info->ctr.user0 == NULL) { >+ return WERR_NOMEM; >+ } >+ r->out.info->level = r->in.info->level; >+ *r->out.entries_read = r->out.info->ctr.user0->entries_read; >+ *r->out.resume_handle = 0; >+ >+ return WERR_OK; > } > > /******************************************************************** >-- >1.6.0.1 > >diff -u a/source3/rpc_server/srv_wkssvc_nt.c b/source3/rpc_server/srv_wkssvc_nt.c >--- a/source3/rpc_server/srv_wkssvc_nt.c 2009-08-12 14:06:12.000000000 -0700 >+++ b/source3/rpc_server/srv_wkssvc_nt.c 2009-08-12 13:52:18.000000000 -0700 >@@ -32,29 +32,96 @@ > > #include <utmpx.h> > >+static char *get_proc_user(TALLOC_CTX *mem_ctx, __pid_t pid) >+{ >+ /* Return the name of the user who created a process: */ >+ >+ struct stat st; >+ struct passwd *pw; >+ char *uname; >+ char path[32]; >+ >+ snprintf(path, sizeof(path), "/proc/%d", pid); >+ if (stat(path, &st) == -1) { >+ return NULL; >+ } >+ pw = getpwuid_alloc(mem_ctx, st.st_uid); >+ if (!pw) { >+ return NULL; >+ } >+ uname = talloc_strdup(mem_ctx, pw->pw_name); >+ TALLOC_FREE(pw); >+ >+ return (uname); >+} >+ > static char **get_logged_on_userlist(TALLOC_CTX *mem_ctx) > { > char **users = NULL; >+ struct timeval *login_times = NULL; > int num_users = 0; >+ int i; >+ bool reordered; > struct utmpx *u; > > while ((u = getutxent()) != NULL) { > char **tmp; >+ struct timeval *tmp2; > if (u->ut_type != USER_PROCESS) { > continue; > } >+ for (i = 0; i < num_users; i++) { >+ /* getutxent can return multiple user entries for the >+ * same user, so ignore any dups */ >+ if (strcmp(u->ut_user, users[i]) == 0) break; >+ } >+ if (i < num_users) { >+ continue; >+ } >+ > tmp = talloc_realloc(mem_ctx, users, char *, num_users+1); >- if (tmp == NULL) { >+ tmp2 = talloc_realloc(mem_ctx, login_times, struct timeval, num_users+1); >+ if (tmp == NULL || tmp2 == NULL) { >+ if (tmp) TALLOC_FREE(tmp); >+ if (tmp2) TALLOC_FREE(tmp2); >+ endutent(); > return NULL; > } > users = tmp; >+ login_times = tmp2; > users[num_users] = talloc_strdup(users, u->ut_user); > if (users[num_users] == NULL) { > TALLOC_FREE(users); >+ TALLOC_FREE(login_times); >+ endutent(); > return NULL; > } >+ login_times[num_users].tv_sec = u->ut_tv.tv_sec; >+ login_times[num_users].tv_usec = u->ut_tv.tv_usec; > num_users += 1; > } >+ >+ /* Sort the user list by time, oldest first */ >+ do { >+ reordered = False; >+ for (i = 0; i < num_users-1; i++) { >+ if (login_times[i].tv_sec > login_times[i+1].tv_sec >+ || (login_times[i].tv_sec == login_times[i+1].tv_sec >+ && login_times[i].tv_usec > login_times[i+1].tv_usec)) { >+ char *tmp1 = users[i]; >+ struct timeval tmp2 = login_times[i]; >+ users[i] = users[i+1]; >+ users[i+1] = tmp1; >+ login_times[i] = login_times[i+1]; >+ login_times[i+1] = tmp2; >+ reordered = True; >+ } >+ } >+ } while (reordered); >+ >+ TALLOC_FREE(login_times); >+ endutent(); >+ errno = 0; > return users; > } > >@@ -136,6 +203,7 @@ > > users = get_logged_on_userlist(talloc_tos()); > info102->logged_on_users = talloc_array_length(users); >+ > TALLOC_FREE(users); > > return info102; >@@ -183,6 +251,9 @@ > return WERR_NOT_SUPPORTED; > } > >+/******************************************************************** >+ ********************************************************************/ >+ > static struct wkssvc_NetWkstaEnumUsersCtr0 *create_enum_users0( > TALLOC_CTX *mem_ctx) > { >@@ -196,45 +267,128 @@ > } > > users = get_logged_on_userlist(talloc_tos()); >- if (users == NULL) { >+ if (users == NULL && errno != 0) { >+ DEBUG(1,("get_logged_on_userlist error %d: %s\n", >+ errno, strerror(errno))); > TALLOC_FREE(ctr0); > return NULL; > } > >- num_users = talloc_array_length(users); >+ num_users = (users) ? talloc_array_length(users) : 0; > ctr0->entries_read = num_users; > ctr0->user0 = talloc_array(ctr0, struct wkssvc_NetrWkstaUserInfo0, > num_users); > if (ctr0->user0 == NULL) { > TALLOC_FREE(ctr0); >- TALLOC_FREE(users); >+ if (users) TALLOC_FREE(users); > return NULL; > } > > for (i=0; i<num_users; i++) { > ctr0->user0[i].user_name = talloc_move(ctr0->user0, &users[i]); > } >- TALLOC_FREE(users); >+ if (users) TALLOC_FREE(users); > return ctr0; > } > > /******************************************************************** > ********************************************************************/ > >+static struct wkssvc_NetWkstaEnumUsersCtr1 *create_enum_users1( >+ TALLOC_CTX *mem_ctx) >+{ >+ struct wkssvc_NetWkstaEnumUsersCtr1 *ctr1; >+ char **users; >+ int i, j, num_users, num_sessions; >+ struct sessionid *session_list; >+ >+ ctr1 = talloc(mem_ctx, struct wkssvc_NetWkstaEnumUsersCtr1); >+ if (ctr1 == NULL) { >+ return NULL; >+ } >+ >+ users = get_logged_on_userlist(talloc_tos()); >+ if (users == NULL && errno != 0) { >+ DEBUG(1,("get_logged_on_userlist error %d: %s\n", >+ errno, strerror(errno))); >+ TALLOC_FREE(ctr1); >+ return NULL; >+ } >+ >+ num_users = (users) ? talloc_array_length(users) : 0; >+ ctr1->entries_read = num_users; >+ ctr1->user1 = talloc_array(ctr1, struct wkssvc_NetrWkstaUserInfo1, >+ num_users); >+ if (ctr1->user1 == NULL) { >+ TALLOC_FREE(ctr1); >+ if (users) TALLOC_FREE(users); >+ return NULL; >+ } >+ >+ session_list = NULL; >+ num_sessions = list_sessions(mem_ctx, &session_list); >+ DEBUG(3,("found %d sessions\n", num_sessions)); >+ for (j=0; j<num_sessions; j++) { >+ DEBUG(3,("sess %d %s uid %d: %s,%s,%s.%s,%d,%d\n", j, >+ session_list[j].username, >+ session_list[j].uid, >+ session_list[j].hostname, >+ session_list[j].netbios_name, >+ session_list[j].remote_machine, >+ session_list[j].id_str, >+ session_list[j].id_num, >+ session_list[j].pid.pid)); >+ } >+ >+ for (i=0; i<num_users; i++) { >+ ctr1->user1[i].user_name = talloc_move(ctr1->user1, &users[i]); >+ >+ if (0) { >+ /* Domain login to do !!!!! */ >+ } else { >+ /* Local session - domain name and logon server are >+ * both returned as the local machine's NetBIOS name */ >+ ctr1->user1[i].logon_domain = ctr1->user1[i].logon_server = >+ talloc_asprintf_strupper_m(ctr1->user1, >+ "%s", global_myname()); >+ } >+ >+ /* Maybe implement this in future?: */ >+ ctr1->user1[i].other_domains = NULL; >+ } >+ if (users) TALLOC_FREE(users); >+ if (session_list) TALLOC_FREE(session_list); >+ return ctr1; >+} >+ >+/******************************************************************** >+ ********************************************************************/ >+ > WERROR _wkssvc_NetWkstaEnumUsers(pipes_struct *p, struct wkssvc_NetWkstaEnumUsers *r) > { >- if (r->in.info->level != 0) { >+ switch (r->in.info->level) { >+ case 0: >+ r->out.info->ctr.user0 = create_enum_users0(p->mem_ctx); >+ if (r->out.info->ctr.user0 == NULL) { >+ return WERR_NOMEM; >+ } >+ r->out.info->level = r->in.info->level; >+ *r->out.entries_read = r->out.info->ctr.user0->entries_read; >+ *r->out.resume_handle = 0; >+ break; >+ case 1: >+ r->out.info->ctr.user1 = create_enum_users1(p->mem_ctx); >+ if (r->out.info->ctr.user1 == NULL) { >+ return WERR_NOMEM; >+ } >+ r->out.info->level = r->in.info->level; >+ *r->out.entries_read = r->out.info->ctr.user1->entries_read; >+ *r->out.resume_handle = 0; >+ break; >+ default: > return WERR_UNKNOWN_LEVEL; > } > >- r->out.info->ctr.user0 = create_enum_users0(p->mem_ctx); >- if (r->out.info->ctr.user0 == NULL) { >- return WERR_NOMEM; >- } >- r->out.info->level = r->in.info->level; >- *r->out.entries_read = r->out.info->ctr.user0->entries_read; >- *r->out.resume_handle = 0; >- > return WERR_OK; > } >
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Raw
Actions:
View
Attachments on
bug 6592
:
4486
|
4487
|
4488
|
4489
|
4490
|
4492
|
4496
|
4502
|
4503
|
4524
|
4525
|
4549
|
4555
|
4564
|
4569
|
4906
|
4963
|
4967
|
4989
|
4997
|
5002