diff options
-rw-r--r-- | source4/scripting/ejs/ejsnet/mpr_user.c | 165 | ||||
-rw-r--r-- | source4/scripting/ejs/ejsnet/net_ctx.c | 209 | ||||
-rw-r--r-- | source4/scripting/ejs/ejsnet/net_user.c | 277 |
3 files changed, 651 insertions, 0 deletions
diff --git a/source4/scripting/ejs/ejsnet/mpr_user.c b/source4/scripting/ejs/ejsnet/mpr_user.c new file mode 100644 index 0000000000..9a49262dc6 --- /dev/null +++ b/source4/scripting/ejs/ejsnet/mpr_user.c @@ -0,0 +1,165 @@ +/* + Unix SMB/CIFS implementation. + + provides interfaces to libnet calls from ejs scripts + + Copyright (C) Rafal Szczesniak 2005-2007 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#include "includes.h" +#include "lib/appweb/ejs/ejs.h" +#include "libnet/libnet.h" +#include "scripting/ejs/smbcalls.h" +#include "events/events.h" +#include "auth/credentials/credentials.h" + + +/* + Properties: + UserInfo.AccountName + UserInfo.FullName + UserInfo.Description + UserInfo.HomeDirectory + UserInfo.HomeDrive + UserInfo.Comment + UserInfo.LogonScript + UserInfo.AcctExpiry + UserInfo.AllowPasswordChange + UserInfo.ForcePasswordChange + */ +struct MprVar mprCreateUserInfo(TALLOC_CTX *mem_ctx, struct libnet_UserInfo *info) +{ + const char *name = "UserInfo"; + NTSTATUS status; + struct MprVar mprUserInfo; + struct MprVar mprAccountName, mprFullName, mprDescription; + struct MprVar mprHomeDir, mprHomeDrive, mprComment; + struct MprVar mprLogonScript; + struct MprVar mprAcctExpiry, mprAllowPassChange, mprForcePassChange; + + if (info == NULL || mem_ctx == NULL) { + mprUserInfo = mprCreateNullVar(); + goto done; + } + + mprUserInfo = mprObject(name); + + mprAccountName = mprString(info->out.account_name); + mprFullName = mprString(info->out.full_name); + mprDescription = mprString(info->out.description); + mprHomeDir = mprString(info->out.home_directory); + mprHomeDrive = mprString(info->out.home_drive); + mprComment = mprString(info->out.comment); + mprLogonScript = mprString(info->out.logon_script); + mprAcctExpiry = mprString(timestring(mem_ctx, info->out.acct_expiry->tv_sec)); + mprAllowPassChange = mprString(timestring(mem_ctx, info->out.allow_password_change->tv_sec)); + mprForcePassChange = mprString(timestring(mem_ctx, info->out.force_password_change->tv_sec)); + + status = mprSetVar(&mprUserInfo, "AccountName", mprAccountName); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprUserInfo, "FullName", mprFullName); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprUserInfo, "Description", mprDescription); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprUserInfo, "HomeDirectory", mprHomeDir); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprUserInfo, "HomeDrive", mprHomeDrive); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprUserInfo, "Comment", mprComment); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprUserInfo, "LogonScript", mprLogonScript); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprUserInfo, "AcctExpiry", mprAcctExpiry); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprUserInfo, "AllowPasswordChange", mprAllowPassChange); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprUserInfo, "ForcePasswordChange", mprForcePassChange); + if (!NT_STATUS_IS_OK(status)) goto done; + +done: + return mprUserInfo; +} + + +/* + Properties: + UserListCtx.Users[] + UserListCtx.ResumeIndex + UserListCtx.Count + */ +struct MprVar mprUserListCtx(TALLOC_CTX *mem_ctx, struct libnet_UserList *list) +{ + const char *name = "UserListCtx"; + NTSTATUS status; + struct MprVar mprListCtx, mprUserList; + struct MprVar mprUser, mprSid, mprUsername; + int i; + + if (list == NULL || mem_ctx == NULL) { + mprListCtx = mprCreateNullVar(); + goto done; + } + + mprUserList = mprArray("Users"); + for (i = 0; i < list->out.count; i++) { + struct userlist u = list->out.users[i]; + + /* get userlist fields */ + mprSid = mprString(u.sid); + mprUsername = mprString(u.username); + + /* create userlist object */ + mprUser = mprObject("User"); + mprSetVar(&mprUser, "Username", mprUsername); + mprSetVar(&mprUser, "SID", mprSid); + + /* add the object to the array being constructed */ + mprAddArray(&mprUserList, 0, mprUser); + } + + mprListCtx = mprObject(name); + status = mprSetVar(&mprListCtx, "Users", mprUserList); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprListCtx, "Count", mprCreateIntegerVar(list->out.count)); + if (!NT_STATUS_IS_OK(status)) goto done; + status = mprSetVar(&mprListCtx, "ResumeIndex", mprCreateIntegerVar((int)list->out.resume_index)); + if (!NT_STATUS_IS_OK(status)) goto done; + +done: + return mprListCtx; +} + + +/* + Returns UserListCtx.ResumeIndex out of passed UserListCtx + */ +unsigned int mprListGetResumeIndex(struct MprVar *listCtx) +{ + NTSTATUS status; + unsigned int resume = 0; + struct MprVar *mprResumeIndex; + if (listCtx == NULL) return 0; + + mprResumeIndex = listCtx; + status = mprGetVar(&mprResumeIndex, "ResumeIndex"); + if (!NT_STATUS_IS_OK(status)) goto done; + + resume = (unsigned int) mprVarToInteger(mprResumeIndex); + +done: + return resume; +} diff --git a/source4/scripting/ejs/ejsnet/net_ctx.c b/source4/scripting/ejs/ejsnet/net_ctx.c new file mode 100644 index 0000000000..42c64540fb --- /dev/null +++ b/source4/scripting/ejs/ejsnet/net_ctx.c @@ -0,0 +1,209 @@ +/* + Unix SMB/CIFS implementation. + + provides interfaces to libnet calls from ejs scripts + + Copyright (C) Rafal Szczesniak 2005-2007 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#include "includes.h" +#include "lib/appweb/ejs/ejs.h" +#include "scripting/ejs/smbcalls.h" +#include "libnet/libnet.h" +#include "events/events.h" +#include "auth/credentials/credentials.h" + + +int ejs_net_userman(MprVarHandle eid, int argc, struct MprVar** argv); + +static int ejs_net_join_domain(MprVarHandle eid, int argc, struct MprVar **argv); +static int ejs_net_samsync_ldb(MprVarHandle eid, int argc, struct MprVar **argv); + +/* + Usage: + net = NetContext(credentials); +*/ + +static int ejs_net_context(MprVarHandle eid, int argc, struct MprVar **argv) +{ + TALLOC_CTX *event_mem_ctx = talloc_new(mprMemCtx()); + struct cli_credentials *creds; + struct libnet_context *ctx; + struct MprVar obj; + struct event_context *ev; + + if (!event_mem_ctx) { + ejsSetErrorMsg(eid, "talloc_new() failed"); + return -1; + } + ev = event_context_find(event_mem_ctx); + ctx = libnet_context_init(ev); + /* IF we generated a new event context, it will be under here, + * and we need it to last as long as the libnet context, so + * make it a child */ + talloc_steal(ctx, event_mem_ctx); + + if (argc == 0 || (argc == 1 && argv[0]->type == MPR_TYPE_NULL)) { + creds = cli_credentials_init(ctx); + if (creds == NULL) { + ejsSetErrorMsg(eid, "cli_credential_init() failed"); + talloc_free(ctx); + return -1; + } + cli_credentials_set_conf(creds); + cli_credentials_set_anonymous(creds); + + } else if (argc == 1 && argv[0]->type == MPR_TYPE_OBJECT) { + /* get credential values from credentials object */ + creds = mprGetPtr(argv[0], "creds"); + if (creds == NULL) { + ejsSetErrorMsg(eid, "userAuth requires a 'creds' first parameter"); + talloc_free(ctx); + return -1; + } + + } else { + ejsSetErrorMsg(eid, "NetContext invalid arguments, this function requires an object."); + talloc_free(ctx); + return -1; + } + + ctx->cred = creds; + + obj = mprObject("NetCtx"); + mprSetPtrChild(&obj, "ctx", ctx); + + mprSetCFunction(&obj, "UserMgr", ejs_net_userman); + mprSetCFunction(&obj, "JoinDomain", ejs_net_join_domain); + mprSetCFunction(&obj, "SamSyncLdb", ejs_net_samsync_ldb); + mpr_Return(eid, obj); + + return 0; +} + + +static int ejs_net_join_domain(MprVarHandle eid, int argc, struct MprVar **argv) +{ + TALLOC_CTX *mem_ctx; + struct libnet_context *ctx; + struct libnet_Join *join; + NTSTATUS status; + ctx = mprGetThisPtr(eid, "ctx"); + mem_ctx = talloc_new(mprMemCtx()); + + join = talloc(mem_ctx, struct libnet_Join); + if (!join) { + talloc_free(mem_ctx); + return -1; + } + + /* prepare parameters for the join */ + join->in.netbios_name = NULL; + join->in.join_type = SEC_CHAN_WKSTA; + join->in.domain_name = cli_credentials_get_domain(ctx->cred); + join->in.level = LIBNET_JOIN_AUTOMATIC; + join->out.error_string = NULL; + + if (argc == 1 && argv[0]->type == MPR_TYPE_OBJECT) { + MprVar *netbios_name = mprGetProperty(argv[0], "netbios_name", NULL); + MprVar *domain_name = mprGetProperty(argv[0], "domain_name", NULL); + MprVar *join_type = mprGetProperty(argv[0], "join_type", NULL); + if (netbios_name) { + join->in.netbios_name = mprToString(netbios_name); + } + if (domain_name) { + join->in.domain_name = mprToString(domain_name); + } + if (join_type) { + join->in.join_type = mprToInt(join_type); + } + } + + if (!join->in.domain_name) { + ejsSetErrorMsg(eid, "a domain must be specified for to join"); + talloc_free(mem_ctx); + return -1; + } + + /* do the domain join */ + status = libnet_Join(ctx, join, join); + + if (!NT_STATUS_IS_OK(status)) { + MprVar error_string = mprString(join->out.error_string); + + mprSetPropertyValue(argv[0], "error_string", error_string); + mpr_Return(eid, mprCreateBoolVar(False)); + } else { + mpr_Return(eid, mprCreateBoolVar(True)); + } + talloc_free(mem_ctx); + return 0; +} + + +static int ejs_net_samsync_ldb(MprVarHandle eid, int argc, struct MprVar **argv) +{ + TALLOC_CTX *mem_ctx; + struct libnet_context *ctx; + struct libnet_samsync_ldb *samsync; + NTSTATUS status; + ctx = mprGetThisPtr(eid, "ctx"); + mem_ctx = talloc_new(mprMemCtx()); + + samsync = talloc(mem_ctx, struct libnet_samsync_ldb); + if (!samsync) { + talloc_free(mem_ctx); + return -1; + } + + /* prepare parameters for the samsync */ + samsync->in.machine_account = NULL; + samsync->in.session_info = NULL; + samsync->in.binding_string = NULL; + samsync->out.error_string = NULL; + + if (argc == 1 && argv[0]->type == MPR_TYPE_OBJECT) { + MprVar *credentials = mprGetProperty(argv[0], "machine_account", NULL); + MprVar *session_info = mprGetProperty(argv[0], "session_info", NULL); + if (credentials) { + samsync->in.machine_account = talloc_get_type(mprGetPtr(credentials, "creds"), struct cli_credentials); + } + if (session_info) { + samsync->in.session_info = talloc_get_type(mprGetPtr(session_info, "session_info"), struct auth_session_info); + } + } + + /* do the domain samsync */ + status = libnet_samsync_ldb(ctx, samsync, samsync); + + if (!NT_STATUS_IS_OK(status)) { + MprVar error_string = mprString(samsync->out.error_string); + + mprSetPropertyValue(argv[0], "error_string", error_string); + mpr_Return(eid, mprCreateBoolVar(False)); + } else { + mpr_Return(eid, mprCreateBoolVar(True)); + } + talloc_free(mem_ctx); + return 0; +} + + +void ejsnet_setup(void) +{ + ejsDefineCFunction(-1, "NetContext", ejs_net_context, NULL, MPR_VAR_SCRIPT_HANDLE); +} diff --git a/source4/scripting/ejs/ejsnet/net_user.c b/source4/scripting/ejs/ejsnet/net_user.c new file mode 100644 index 0000000000..731b4b9203 --- /dev/null +++ b/source4/scripting/ejs/ejsnet/net_user.c @@ -0,0 +1,277 @@ +/* + Unix SMB/CIFS implementation. + + provides interfaces to libnet calls from ejs scripts + + Copyright (C) Rafal Szczesniak 2005-2007 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#include "includes.h" +#include "lib/appweb/ejs/ejs.h" +#include "libnet/libnet.h" +#include "proto.h" +#include "scripting/ejs/smbcalls.h" +#include "events/events.h" +#include "auth/credentials/credentials.h" + + +static int ejs_net_createuser(MprVarHandle eid, int argc, char **argv); +static int ejs_net_deleteuser(MprVarHandle eid, int argc, char **argv); +static int ejs_net_userinfo(MprVarHandle eid, int argc, char **argv); +static int ejs_net_userlist(MprVarHandle eid, int argc, struct MprVar **argv); + + +/* + Usage: + usrCtx = net.UserMgr(domain); +*/ +int ejs_net_userman(MprVarHandle eid, int argc, struct MprVar **argv) +{ + TALLOC_CTX *mem_ctx; + struct libnet_context *ctx; + const char *userman_domain = NULL; + struct MprVar *obj = NULL; + + ctx = mprGetThisPtr(eid, "ctx"); + mem_ctx = talloc_new(mprMemCtx()); + + if (argc == 0) { + userman_domain = cli_credentials_get_domain(ctx->cred); + + } else if (argc == 1 && mprVarIsString(argv[0]->type)) { + userman_domain = talloc_strdup(ctx, mprToString(argv[0])); + + } else { + ejsSetErrorMsg(eid, "too many arguments"); + goto done; + } + + if (!userman_domain) { + ejsSetErrorMsg(eid, "a domain must be specified for user management"); + goto done; + } + + obj = mprInitObject(eid, "NetUsrCtx", argc, argv); + mprSetPtrChild(obj, "ctx", ctx); + mprSetPtrChild(obj, "domain", userman_domain); + + mprSetStringCFunction(obj, "Create", ejs_net_createuser); + mprSetStringCFunction(obj, "Delete", ejs_net_deleteuser); + mprSetStringCFunction(obj, "Info", ejs_net_userinfo); + mprSetCFunction(obj, "List", ejs_net_userlist); + + return 0; +done: + talloc_free(mem_ctx); + return -1; +} + + +static int ejs_net_createuser(MprVarHandle eid, int argc, char **argv) +{ + NTSTATUS status = NT_STATUS_UNSUCCESSFUL; + TALLOC_CTX *mem_ctx; + struct libnet_context *ctx; + const char *userman_domain = NULL; + struct libnet_CreateUser req; + + if (argc != 1) { + ejsSetErrorMsg(eid, "argument 1 must be a string"); + return -1; + } + + ctx = mprGetThisPtr(eid, "ctx"); + if (!ctx) { + ejsSetErrorMsg(eid, "ctx property returns null pointer"); + return -1; + } + + userman_domain = mprGetThisPtr(eid, "domain"); + if (!userman_domain) { + ejsSetErrorMsg(eid, "domain property returns null pointer"); + return -1; + } + + mem_ctx = talloc_new(mprMemCtx()); + + req.in.domain_name = userman_domain; + req.in.user_name = argv[0]; + + status = libnet_CreateUser(ctx, mem_ctx, &req); + if (!NT_STATUS_IS_OK(status)) { + ejsSetErrorMsg(eid, "%s", req.out.error_string); + } + + talloc_free(mem_ctx); + mpr_Return(eid, mprNTSTATUS(status)); + return 0; +} + + +static int ejs_net_deleteuser(MprVarHandle eid, int argc, char **argv) +{ + NTSTATUS status = NT_STATUS_UNSUCCESSFUL; + TALLOC_CTX *mem_ctx; + struct libnet_context *ctx; + const char *userman_domain = NULL; + struct libnet_DeleteUser req; + + if (argc != 1) { + ejsSetErrorMsg(eid, "argument 1 must be a string"); + return -1; + } + + ctx = mprGetThisPtr(eid, "ctx"); + if (!ctx) { + ejsSetErrorMsg(eid, "ctx property returns null pointer"); + return -1; + } + + userman_domain = mprGetThisPtr(eid, "domain"); + if (!userman_domain) { + ejsSetErrorMsg(eid, "domain property returns null pointer"); + return -1; + } + + mem_ctx = talloc_new(mprMemCtx()); + + req.in.domain_name = userman_domain; + req.in.user_name = argv[0]; + + status = libnet_DeleteUser(ctx, mem_ctx, &req); + if (!NT_STATUS_IS_OK(status)) { + ejsSetErrorMsg(eid, "%s", req.out.error_string); + } + + talloc_free(mem_ctx); + mpr_Return(eid, mprNTSTATUS(status)); + return 0; +} + + +static int ejs_net_userinfo(MprVarHandle eid, int argc, char **argv) +{ + NTSTATUS status = NT_STATUS_UNSUCCESSFUL; + TALLOC_CTX *mem_ctx; + struct libnet_context *ctx; + const char *userman_domain; + struct libnet_UserInfo req; + struct MprVar mprUserInfo; + + if (argc != 1) { + ejsSetErrorMsg(eid, "argument 1 must be a string"); + return -1; + } + + ctx = mprGetThisPtr(eid, "ctx"); + if (ctx == NULL) { + ejsSetErrorMsg(eid, "ctx property returns null pointer"); + return -1; + } + + userman_domain = mprGetThisPtr(eid, "domain"); + if (userman_domain == NULL) { + ejsSetErrorMsg(eid, "domain property returns null pointer"); + return -1; + } + + mem_ctx = talloc_new(mprMemCtx()); + + req.in.domain_name = userman_domain; + req.in.user_name = argv[0]; + + status = libnet_UserInfo(ctx, mem_ctx, &req); + if (!NT_STATUS_IS_OK(status)) { + ejsSetErrorMsg(eid, "%s", req.out.error_string); + + /* create null object to return */ + mprUserInfo = mprCreateNullVar(); + goto done; + } + + /* create UserInfo object */ + mprUserInfo = mprCreateUserInfo(ctx, &req); + +done: + talloc_free(mem_ctx); + mpr_Return(eid, mprUserInfo); + return 0; +} + + +static int ejs_net_userlist(MprVarHandle eid, int argc, struct MprVar **argv) +{ + TALLOC_CTX *mem_ctx; + NTSTATUS status; + struct libnet_context *ctx; + const char *userlist_domain; + struct libnet_UserList req; + struct MprVar mprListCtx, *mprInListCtx; + + mem_ctx = talloc_new(mprMemCtx()); + + if (argc == 0) { + ejsSetErrorMsg(eid, "too little arguments"); + + } else if (argc == 1) { + if (mprVarIsObject(argv[0]->type)) { + /* this is a continuation call */ + mprInListCtx = argv[0]; + req.in.resume_index = mprListGetResumeIndex(mprInListCtx); + + } else { + req.in.resume_index = 0; + } + + } else { + ejsSetErrorMsg(eid, "too many arguments"); + goto done; + } + + ctx = mprGetThisPtr(eid, "ctx"); + if (!ctx) { + ejsSetErrorMsg(eid, "ctx property returns null pointer"); + return -1; + } + + userlist_domain = mprGetThisPtr(eid, "domain"); + if (!userlist_domain) { + ejsSetErrorMsg(eid, "domain property returns null pointer"); + return -1; + } + + req.in.domain_name = userlist_domain; + req.in.page_size = 10; /* TODO: this should be specified in a nicer way */ + + status = libnet_UserList(ctx, mem_ctx, &req); + if (!NT_STATUS_IS_OK(status) && + !NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES) && + !NT_STATUS_EQUAL(status, NT_STATUS_NO_MORE_ENTRIES)) { + + ejsSetErrorMsg(eid, "%s", req.out.error_string); + + mprListCtx = mprCreateNullVar(); + goto done; + } + + mprListCtx = mprUserListCtx(mem_ctx, &req); + +done: + talloc_free(mem_ctx); + mpr_Return(eid, mprListCtx); + return 0; +} |