1
0
Fork 0
mirror of git://git.code.sf.net/p/zsh/code synced 2025-10-26 04:30:27 +01:00

21498: Add zsh/newuser module

This commit is contained in:
Peter Stephenson 2005-07-20 16:08:12 +00:00
parent eb86b42f30
commit e3c5dd2dd9
10 changed files with 266 additions and 43 deletions

View file

@ -1,3 +1,10 @@
2005-07-20 Peter Stephenson <pws@csr.com>
* 21498: configure.ac, Configs/defs.mk.in, Doc/Makefile.in,
Doc/Zsh/mod_newuser.yo, Src/init.c, Src/module.c, Src/zsh.mdd,
Src/Modules/newuser.c, Src/Modules/newuser.mdd: Add zsh/newuser
module, currently with no associated shell code.
2005-07-20 Doug Kearns <djkea2@gus.gscit.monash.edu.au>
* unposted: Completion/Unix/Command/_rake: add -s option to _arguments

View file

@ -43,6 +43,8 @@ mandir = @mandir@
datadir = @datadir@
fndir = @fndir@
sitefndir = @sitefndir@
scriptdir = @scriptdir@
sitescriptdir = @sitescriptdir@
htmldir = $(datadir)/$(tzsh)/htmldoc
# compilation

View file

@ -59,7 +59,8 @@ Zsh/mod_compctl.yo Zsh/mod_complete.yo Zsh/mod_complist.yo \
Zsh/mod_computil.yo \
Zsh/mod_datetime.yo Zsh/mod_deltochar.yo \
Zsh/mod_example.yo Zsh/mod_files.yo \
Zsh/mod_mapfile.yo Zsh/mod_mathfunc.yo Zsh/mod_parameter.yo Zsh/mod_pcre.yo \
Zsh/mod_mapfile.yo Zsh/mod_mathfunc.yo Zsh/mod_newuser.yo \
Zsh/mod_parameter.yo Zsh/mod_pcre.yo \
Zsh/mod_sched.yo Zsh/mod_socket.yo \
Zsh/mod_stat.yo Zsh/mod_system.yo Zsh/mod_tcp.yo \
Zsh/mod_termcap.yo Zsh/mod_terminfo.yo \

37
Doc/Zsh/mod_newuser.yo Normal file
View file

@ -0,0 +1,37 @@
COMMENT(!MOD!zsh/newuser
Arrange for files for new users to be installed.
!MOD!)
The tt(zsh/newuser) module is loaded at boot if it is
available, the tt(RCS) option is set, and the tt(PRIVILEGED) option is not
set (all three are true by default). This takes
place immediately after commands in the global tt(zshenv) file (typically
tt(/etc/zshenv)), if any, have been executed. If the module is not
available it is silently ignored by the shell; the module may safely be
removed from tt($MODULE_PATH) by the administrator if it is not required.
On loading, the module tests if any of the start-up files tt(.zshenv),
tt(.zprofile), tt(.zshrc) or tt(.zlogin) exist in the directory given by
the environment variable tt(ZDOTDIR), or the user's home directory if that
is not set.
If none of the start-up files were found, the module then looks for the
file tt(newuser) first in a sitewide directory, usually the parent
directory of the tt(site-functions) directory, and if that is not found the
module searches in a version-specific directory, usually the parent of the
tt(functions) directory containing version-specific functions. (These
directories can be configured when zsh is built using the
tt(--enable-site-scriptdir=)var(dir) and tt(--enable-scriptdir=)var(dir)
flags to tt(configure), respectively; the defaults are
var(prefix)tt(/share/zsh) and var(prefix)tt(/share/zsh/$ZSH_VERSION) where
the default var(prefix) is tt(/usr/local).)
If the file tt(newuser) is found, it is then sourced in the same manner as
a start-up file. The file is expected to contain code to install start-up
files for the user, however any valid shell code will be executed.
The tt(zsh/newuser) module is then unconditionally unloaded.
Note that it is possible to achieve exactly the same effect as the
tt(zsh/newuser) module by adding code to tt(/etc/zshenv). The module
exists simply to allow the shell to make arrangements for new users without
the need for invervention by package maintainers and system administrators.

99
Src/Modules/newuser.c Normal file
View file

@ -0,0 +1,99 @@
/*
* newuser.c - handler for easy setup for new zsh users
*
* This file is part of zsh, the Z shell.
*
* Copyright (c) 2005 Peter Stephenson
* All rights reserved.
*
* Permission is hereby granted, without written agreement and without
* license or royalty fees, to use, copy, modify, and distribute this
* software and to distribute modified versions of this software for any
* purpose, provided that the above copyright notice and the following
* two paragraphs appear in all copies of this software.
*
* In no event shall Peter Stephenson or the Zsh Development Group be liable
* to any party for direct, indirect, special, incidental, or consequential
* damages arising out of the use of this software and its documentation,
* even if Peter Stephenson and the Zsh Development Group have been advised of
* the possibility of such damage.
*
* Peter Stephenson and the Zsh Development Group specifically disclaim any
* warranties, including, but not limited to, the implied warranties of
* merchantability and fitness for a particular purpose. The software
* provided hereunder is on an "as is" basis, and Peter Stephenson and the
* Zsh Development Group have no obligation to provide maintenance,
* support, updates, enhancements, or modifications.
*
*/
#include "newuser.mdh"
#include "newuser.pro"
#include "../zshpaths.h"
/**/
int
setup_(UNUSED(Module m))
{
return 0;
}
/**/
static int
check_dotfile(const char *dotdir, const char *fname)
{
VARARR(char, buf, strlen(dotdir) + strlen(fname) + 2);
sprintf(buf, "%s/%s", dotdir, fname);
return access(buf, F_OK);
}
/**/
int
boot_(UNUSED(Module m))
{
const char *dotdir = getsparam("ZDOTDIR");
const char *spaths[] = {
#ifdef SITESCRIPT_DIR
SITESCRIPT_DIR,
#endif
#ifdef SCRIPT_DIR
SCRIPT_DIR,
#endif
0 };
const char **sp;
if (!dotdir)
dotdir = home;
if (check_dotfile(dotdir, ".zshenv") == 0 ||
check_dotfile(dotdir, ".zprofile") == 0 ||
check_dotfile(dotdir, ".zshrc") == 0 ||
check_dotfile(dotdir, ".zlogin") == 0)
return 0;
for (sp = spaths; *sp; sp++) {
VARARR(char, buf, strlen(*sp) + 9);
sprintf(buf, "%s/newuser", *sp);
if (!source(buf))
break;
}
return 0;
}
/**/
int
cleanup_(UNUSED(Module m))
{
return 0;
}
/**/
int
finish_(UNUSED(Module m))
{
return 0;
}

12
Src/Modules/newuser.mdd Normal file
View file

@ -0,0 +1,12 @@
name=zsh/newuser
link=dynamic
# We will always try to load newuser, but there is
# no error if it fails.
load=no
objects="newuser.o"
:<<\Make
newuser.o: ../zshpaths.h
Make

View file

@ -948,8 +948,20 @@ run_init_scripts(void)
#ifdef GLOBAL_ZSHENV
source(GLOBAL_ZSHENV);
#endif
if (isset(RCS) && unset(PRIVILEGED))
{
/*
* Always attempt to load the newuser module to perform
* checks for new zsh users. Don't care if we can't load it.
*/
if (load_module_silence("zsh/newuser", 1)) {
/* Unload it immediately. */
unload_named_module("zsh/newuser", "zsh", 1);
}
sourcehome(".zshenv");
}
if (islogin) {
#ifdef GLOBAL_ZPROFILE
if (isset(RCS) && isset(GLOBALRCS))

View file

@ -434,12 +434,12 @@ try_load_module(char const *name)
/**/
static void *
do_load_module(char const *name)
do_load_module(char const *name, int silent)
{
void *ret;
ret = try_load_module(name);
if (!ret) {
if (!ret && !silent) {
int waserr = errflag;
zerr("failed to load module: %s", name, 0);
errflag = waserr;
@ -452,11 +452,12 @@ do_load_module(char const *name)
/**/
static void *
do_load_module(char const *name)
do_load_module(char const *name, int silent)
{
int waserr = errflag;
zerr("failed to load module: %s", name, 0);
if (!silent)
zerr("failed to load module: %s", name, 0);
errflag = waserr;
return NULL;
@ -747,6 +748,13 @@ modname_ok(char const *p)
/**/
mod_export int
load_module(char const *name)
{
return load_module_silence(name, 0);
}
/**/
mod_export int
load_module_silence(char const *name, int silent)
{
Module m;
void *handle = NULL;
@ -755,7 +763,8 @@ load_module(char const *name)
int set;
if (!modname_ok(name)) {
zerr("invalid module name `%s'", name, 0);
if (!silent)
zerr("invalid module name `%s'", name, 0);
return 0;
}
/*
@ -766,7 +775,7 @@ load_module(char const *name)
queue_signals();
if (!(node = find_module(name, 1, &name))) {
if (!(linked = module_linked(name)) &&
!(handle = do_load_module(name))) {
!(handle = do_load_module(name, silent))) {
unqueue_signals();
return 0;
}
@ -811,7 +820,7 @@ load_module(char const *name)
m->flags |= MOD_BUSY;
if (m->deps)
for (n = firstnode(m->deps); n; incnode(n))
if (!load_module((char *) getdata(n))) {
if (!load_module_silence((char *) getdata(n), silent)) {
m->flags &= ~MOD_BUSY;
unqueue_signals();
return 0;
@ -820,7 +829,7 @@ load_module(char const *name)
if (!m->u.handle) {
handle = NULL;
if (!(linked = module_linked(name)) &&
!(handle = do_load_module(name))) {
!(handle = do_load_module(name, silent))) {
unqueue_signals();
return 0;
}
@ -886,7 +895,7 @@ require_module(char *nam, const char *module, UNUSED(int res), int test)
return 0;
}
} else
ret = load_module(module);
ret = load_module_silence(module, 0);
unqueue_signals();
return ret;
@ -1549,6 +1558,50 @@ unload_module(Module m, LinkNode node)
return 0;
}
/**/
int
unload_named_module(char *modname, char *nam, int silent)
{
const char *mname;
LinkNode node;
Module m;
int ret = 0;
node = find_module(modname, 1, &mname);
if (node) {
LinkNode mn, dn;
int del = 0;
for (mn = firstnode(modules); mn; incnode(mn)) {
m = (Module) getdata(mn);
if (m->deps && m->u.handle)
for (dn = firstnode(m->deps); dn; incnode(dn))
if (!strcmp((char *) getdata(dn), mname)) {
if (m->flags & MOD_UNLOAD)
del = 1;
else {
zwarnnam(nam, "module %s is in use by another module and cannot be unloaded", mname, 0);
return 1;
}
}
}
m = (Module) getdata(node);
if (del)
m->wrapper++;
if (unload_module(m, node))
ret = 1;
if (del)
m->wrapper--;
} else if (!silent) {
zwarnnam(nam, "no such module %s", modname, 0);
ret = 1;
}
return ret;
}
/**/
static int
bin_zmodload_load(char *nam, char **args, Options ops)
@ -1558,39 +1611,9 @@ bin_zmodload_load(char *nam, char **args, Options ops)
int ret = 0;
if(OPT_ISSET(ops,'u')) {
/* unload modules */
const char *mname = *args;
for(; *args; args++) {
node = find_module(*args, 1, &mname);
if (node) {
LinkNode mn, dn;
int del = 0;
for (mn = firstnode(modules); mn; incnode(mn)) {
m = (Module) getdata(mn);
if (m->deps && m->u.handle)
for (dn = firstnode(m->deps); dn; incnode(dn))
if (!strcmp((char *) getdata(dn), mname)) {
if (m->flags & MOD_UNLOAD)
del = 1;
else {
zwarnnam(nam, "module %s is in use by another module and cannot be unloaded", mname, 0);
ret = 1;
goto cont;
}
}
}
m = (Module) getdata(node);
if (del)
m->wrapper++;
if (unload_module(m, node))
ret = 1;
if (del)
m->wrapper--;
} else if (!OPT_ISSET(ops,'i')) {
zwarnnam(nam, "no such module %s", *args, 0);
if (unload_named_module(*args, nam, OPT_ISSET(ops,'i')))
ret = 1;
}
cont: ;
}
return ret;
} else if(!*args) {
@ -1645,7 +1668,7 @@ getconddef(int inf, char *name, int autol)
/* This is a definition for an autoloaded condition, load the *
* module if we haven't tried that already. */
if (f) {
load_module(p->module);
load_module_silence(p->module, 0);
f = 0;
p = NULL;
} else {
@ -2086,7 +2109,7 @@ getmathfunc(char *name, int autol)
removemathfunc(q, p);
load_module(n);
load_module_silence(n, 0);
return getmathfunc(name, 0);
}

View file

@ -38,6 +38,12 @@ version.h: $(sdir_top)/Config/version.mk
zshpaths.h: Makemod $(CONFIG_INCS)
@echo '#define MODULE_DIR "'$(MODDIR)'"' > zshpaths.h.tmp
@if test x$(sitescriptdir) != xno; then \
echo '#define SITESCRIPT_DIR "'$(sitescriptdir)'"' >> zshpaths.h.tmp; \
fi
@if test x$(scriptdir) != xno; then \
echo '#define SCRIPT_DIR "'$(scriptdir)'"' >> zshpaths.h.tmp; \
fi
@if test x$(sitefndir) != xno; then \
echo '#define SITEFPATH_DIR "'$(sitefndir)'"' >> zshpaths.h.tmp; \
fi

View file

@ -286,6 +286,30 @@ AC_SUBST(fndir)dnl
AC_SUBST(sitefndir)dnl
AC_SUBST(FUNCTIONS_SUBDIRS)dnl
dnl Directories for scripts such as newuser.
ifdef([scriptdir],[undefine([scriptdir])])dnl
AC_ARG_ENABLE(scriptdir,
[ --enable-scriptdir=DIR the directory in which to install scripts],
dnl ${VERSION} to be determined at compile time.
[if test $enableval = yes; then
scriptdir=${datadir}/${tzsh_name}/'${VERSION}'
else
scriptdir="$enableval"
fi], [scriptdir=${datadir}/${tzsh_name}/'${VERSION}'])
ifdef([sitescriptdir],[undefine([sitescriptdir])])dnl
AC_ARG_ENABLE(site-scriptdir,
[ --enable-site-scriptdir=DIR same for site scripts (not version specific)],
[if test $enableval = yes; then
sitescriptdir=${datadir}/${tzsh_name}
else
sitescriptdir="$enableval"
fi], [sitescriptdir=${datadir}/${tzsh_name}])
AC_SUBST(scriptdir)dnl
AC_SUBST(sitescriptdir)dnl
dnl Do you want maildir support?
ifdef([maildir_support],[undefine([maildir_support])])dnl
AH_TEMPLATE([MAILDIR_SUPPORT],