Exemple #1
0
mod_export void
makezleparams(int ro)
{
    struct zleparam *zp;

    for(zp = zleparams; zp->name; zp++) {
	Param pm = createparam(zp->name, (zp->type |PM_SPECIAL|PM_REMOVABLE|
					  PM_LOCAL|(ro ? PM_READONLY : 0)));
	if (!pm)
	    pm = (Param) paramtab->getnode(paramtab, zp->name);
	DPUTS(!pm, "param not set in makezleparams");

	pm->level = locallevel + 1;
	pm->u.data = zp->data;
	switch(PM_TYPE(zp->type)) {
	    case PM_SCALAR:
		pm->gsu.s = zp->gsu;
		break;
	    case PM_ARRAY:
		pm->gsu.a = (GsuArray)zp->gsu;
		break;
	    case PM_INTEGER:
		pm->gsu.i = (GsuInteger)zp->gsu;
		pm->base = 10;
		break;
	}
	if ((zp->type & PM_UNSET) && (zmod.flags & MOD_MULT))
	    pm->node.flags &= ~PM_UNSET;
    }
}
Exemple #2
0
static void
addcompparams(struct compparam *cp, Param *pp)
{
    for (; cp->name; cp++, pp++) {
	Param pm = createparam(cp->name,
			       cp->type |PM_SPECIAL|PM_REMOVABLE|PM_LOCAL);
	if (!pm)
	    pm = (Param) paramtab->getnode(paramtab, cp->name);
	DPUTS(!pm, "param not set in addcompparams");

	*pp = pm;
	pm->level = locallevel + 1;
	if ((pm->u.data = cp->var)) {
	    switch(PM_TYPE(cp->type)) {
	    case PM_SCALAR:
		pm->gsu.s = &compvarscalar_gsu;
		break;
	    case PM_INTEGER:
		pm->gsu.i = &compvarinteger_gsu;
		pm->base = 10;
		break;
	    case PM_ARRAY:
		pm->gsu.a = &compvararray_gsu;
		break;
	    }
	} else {
	    pm->gsu.s = cp->gsu;
	}
    }
}
Exemple #3
0
static int
is_private(Param pm)
{
    switch (PM_TYPE(pm->node.flags)) {
    case PM_SCALAR:
        if (!pm->gsu.s || pm->gsu.s->unsetfn != pps_unsetfn)
            return 0;
        break;
    case PM_INTEGER:
        if (!pm->gsu.i || pm->gsu.i->unsetfn != ppi_unsetfn)
            return 0;
        break;
    case PM_EFLOAT:
    case PM_FFLOAT:
        if (!pm->gsu.f || pm->gsu.f->unsetfn != ppf_unsetfn)
            return 0;
        break;
    case PM_ARRAY:
        if (!pm->gsu.a || pm->gsu.a->unsetfn != ppa_unsetfn)
            return 0;
        break;
    case PM_HASHED:
        if (!pm->gsu.h || pm->gsu.h->unsetfn != pph_unsetfn)
            return 0;
        break;
    default:
        /* error */
        return 0;
    }
    return 1;
}
Exemple #4
0
static void
makeprivate(HashNode hn, UNUSED(int flags))
{
    Param pm = (Param)hn;
    if (pm->level == locallevel) {
        if (pm->ename || (pm->node.flags & PM_NORESTORE) ||
                (pm->old &&
                 (pm->old->level == locallevel - 1 ||
                  ((pm->node.flags & (PM_SPECIAL|PM_REMOVABLE)) == PM_SPECIAL &&
                   /* typeset_single() line 2300 discards PM_REMOVABLE -- why? */
                   !is_private(pm->old))))) {
            zwarnnam("private", "can't change scope of existing param: %s",
                     pm->node.nam);
            makeprivate_error = 1;
            return;
        }
        struct gsu_closure *gsu = zhalloc(sizeof(struct gsu_closure));
        switch (PM_TYPE(pm->node.flags)) {
        case PM_SCALAR:
            gsu->g = (void *)(pm->gsu.s);
            gsu->u.s = scalar_private_gsu;
            pm->gsu.s = (GsuScalar)gsu;
            break;
        case PM_INTEGER:
            gsu->g = (void *)(pm->gsu.i);
            gsu->u.i = integer_private_gsu;
            pm->gsu.i = (GsuInteger)gsu;
            break;
        case PM_EFLOAT:
        case PM_FFLOAT:
            gsu->g = (void *)(pm->gsu.f);
            gsu->u.f = float_private_gsu;
            pm->gsu.f = (GsuFloat)gsu;
            break;
        case PM_ARRAY:
            gsu->g = (void *)(pm->gsu.a);
            gsu->u.a = array_private_gsu;
            pm->gsu.a = (GsuArray)gsu;
            break;
        case PM_HASHED:
            gsu->g = (void *)(pm->gsu.h);
            gsu->u.h = hash_private_gsu;
            pm->gsu.h = (GsuHash)gsu;
            break;
        default:
            makeprivate_error = 1;
            break;
        }
        /* PM_HIDE so new parameters in deeper scopes do not shadow */
        pm->node.flags |= (PM_HIDE|PM_SPECIAL|PM_REMOVABLE);
        pm->level -= 1;
    }
}
Exemple #5
0
static void
compunsetfn(Param pm, int exp)
{
    if (exp) {
	if (pm->u.data) {
	    if (PM_TYPE(pm->node.flags) == PM_SCALAR) {
		zsfree(*((char **) pm->u.data));
		*((char **) pm->u.data) = ztrdup("");
	    } else if (PM_TYPE(pm->node.flags) == PM_ARRAY) {
		freearray(*((char ***) pm->u.data));
		*((char ***) pm->u.data) = zshcalloc(sizeof(char *));
	    } else if (PM_TYPE(pm->node.flags) == PM_HASHED) {
		deleteparamtable(pm->u.hash);
		pm->u.hash = NULL;
	    }
	}
    } else if (PM_TYPE(pm->node.flags) == PM_HASHED) {
	Param *p;
	int i;

	deletehashtable(pm->u.hash);
	pm->u.hash = NULL;

	for (p = compkpms, i = CP_KEYPARAMS; i--; p++)
	    *p = NULL;
    }
    if (!exp) {
	Param *p;
	int i;

	for (p = comprpms, i = CP_REALPARAMS; i; p++, i--)
	    if (*p == pm) {
		*p = NULL;
		break;
	    }
    }
}
Exemple #6
0
static int
bin_vared(char *name, char **args, Options ops, UNUSED(int func))
{
    char *s, *t, *ova = varedarg;
    struct value vbuf;
    Value v;
    Param pm = 0;
    int ifl;
    int type = PM_SCALAR, obreaks = breaks, haso = 0, oSHTTY = 0;
    char *p1, *p2, *main_keymapname, *vicmd_keymapname, *init, *finish;
    Keymap main_keymapsave = NULL, vicmd_keymapsave = NULL;
    FILE *oshout = NULL;

    if ((interact && unset(USEZLE)) || !strcmp(term, "emacs")) {
	zwarnnam(name, "ZLE not enabled");
	return 1;
    }
    if (zleactive) {
	zwarnnam(name, "ZLE cannot be used recursively (yet)");
	return 1;
    }

    if (OPT_ISSET(ops,'A'))
    {
	if (OPT_ISSET(ops, 'a'))
	{
	    zwarnnam(name, "specify only one of -a and -A");
	    return 1;
	}
	type = PM_HASHED;
    }
    else if (OPT_ISSET(ops,'a'))
	type = PM_ARRAY;
    p1 = OPT_ARG_SAFE(ops,'p');
    p2 = OPT_ARG_SAFE(ops,'r');
    main_keymapname = OPT_ARG_SAFE(ops,'M');
    vicmd_keymapname = OPT_ARG_SAFE(ops,'m');
    init = OPT_ARG_SAFE(ops,'i');
    finish = OPT_ARG_SAFE(ops,'f');

    if (type != PM_SCALAR && !OPT_ISSET(ops,'c')) {
	zwarnnam(name, "-%s ignored", type == PM_ARRAY ? "a" : "A");
    }

    /* handle non-existent parameter */
    s = args[0];
    queue_signals();
    v = fetchvalue(&vbuf, &s, (!OPT_ISSET(ops,'c') || type == PM_SCALAR),
		   SCANPM_WANTKEYS|SCANPM_WANTVALS|SCANPM_MATCHMANY);
    if (!v && !OPT_ISSET(ops,'c')) {
	unqueue_signals();
	zwarnnam(name, "no such variable: %s", args[0]);
	return 1;
    } else if (v) {
	if (*s) {
	    zwarnnam(name, "not an identifier: `%s'", args[0]);
	    return 1;
	}
	if (v->isarr) {
	    /* Array: check for separators and quote them. */
	    char **arr = getarrvalue(v), **aptr, **tmparr, **tptr;
	    tptr = tmparr = (char **)zhalloc(sizeof(char *)*(arrlen(arr)+1));
	    for (aptr = arr; *aptr; aptr++) {
		int sepcount = 0, clen;
		convchar_t c;
		/*
		 * See if this word contains a separator character
		 * or backslash
		 */
		MB_METACHARINIT();
		for (t = *aptr; *t; ) {
		    if (*t == '\\') {
			t++;
			sepcount++;
		    } else {
			t += MB_METACHARLENCONV(t, &c);
			if (WC_ZISTYPE(c, ISEP))
			    sepcount++;
		    }
		}
		if (sepcount) {
		    /* Yes, so allocate enough space to quote it. */
		    char *newstr, *nptr;
		    newstr = zhalloc(strlen(*aptr)+sepcount+1);
		    /* Go through string quoting separators */
		    MB_METACHARINIT();
		    for (t = *aptr, nptr = newstr; *t; ) {
			if (*t == '\\') {
			    *nptr++ = '\\';
			    *nptr++ = *t++;
			} else {
			    clen = MB_METACHARLENCONV(t, &c);
			    if (WC_ZISTYPE(c, ISEP))
				*nptr++ = '\\';
			    while (clen--)
				*nptr++ = *t++;
			}
		    }
		    *nptr = '\0';
		    /* Stick this into the array of words to join up */
		    *tptr++ = newstr;
		} else
		    *tptr++ = *aptr; /* No, keep original array element */
	    }
	    *tptr = NULL;
	    s = sepjoin(tmparr, NULL, 0);
	} else {
	    s = ztrdup(getstrvalue(v));
	}
	unqueue_signals();
    } else if (*s) {
	unqueue_signals();
	zwarnnam(name, "invalid parameter name: %s", args[0]);
	return 1;
    } else {
	unqueue_signals();
	s = ztrdup(s);
    }

    if (SHTTY == -1 || OPT_ISSET(ops,'t')) {
	/* need to open /dev/tty specially */
	oSHTTY = SHTTY;
	if ((SHTTY = open(OPT_ISSET(ops,'t') ? OPT_ARG(ops,'t') : "/dev/tty",
			  O_RDWR|O_NOCTTY)) == -1) {
	    zwarnnam(name, "can't access terminal");
	    zsfree(s);
	    return 1;
	}
	if (!isatty(SHTTY)) {
	    zwarnnam(name, "%s: not a terminal", OPT_ARG(ops,'t'));
	    close(SHTTY);
	    SHTTY = oSHTTY;
	    zsfree(s);
	    return 1;
	}
	oshout = shout;
	init_shout();

	haso = 1;
    }

    /* edit the parameter value */
    zpushnode(bufstack, s);

    if (main_keymapname &&
	savekeymap(name, "main", main_keymapname, &main_keymapsave))
	main_keymapname = NULL;
    if (vicmd_keymapname &&
	savekeymap(name, "vicmd", vicmd_keymapname, &vicmd_keymapsave))
	vicmd_keymapname = NULL;

    varedarg = *args;
    ifl = isfirstln;
    if (OPT_ISSET(ops,'h'))
	hbegin(2);
    isfirstln = OPT_ISSET(ops,'e');

    t = zleread(&p1, &p2, OPT_ISSET(ops,'h') ? ZLRF_HISTORY : 0, ZLCON_VARED,
		init ? init : "zle-line-init",
		finish ? finish : "zle-line-finish");
    if (OPT_ISSET(ops,'h'))
	hend(NULL);
    isfirstln = ifl;
    varedarg = ova;

    restorekeymap(name, "main", main_keymapname, main_keymapsave);
    restorekeymap(name, "vicmd", vicmd_keymapname, vicmd_keymapsave);

    if (haso) {
	fclose(shout);	/* close(SHTTY) */
	shout = oshout;
	SHTTY = oSHTTY;
    }
    if (!t || errflag) {
	/* error in editing */
	errflag &= ~ERRFLAG_ERROR;
	breaks = obreaks;
	if (t)
	    zsfree(t);
	return 1;
    }
    /* strip off trailing newline, if any */
    if (t[strlen(t) - 1] == '\n')
	t[strlen(t) - 1] = '\0';
    /* final assignment of parameter value */
    if (OPT_ISSET(ops,'c')) {
	unsetparam(args[0]);
	createparam(args[0], type);
    }
    queue_signals();
    pm = (Param) paramtab->getnode(paramtab, args[0]);
    if (pm && (PM_TYPE(pm->node.flags) & (PM_ARRAY|PM_HASHED))) {
	char **a;

	/*
	 * Use spacesplit with fourth argument 1: identify quoted separators,
	 * and unquote.  This duplicates the string, so we still need to free.
	 */
	a = spacesplit(t, 1, 0, 1);
	zsfree(t);
	if (PM_TYPE(pm->node.flags) == PM_ARRAY)
	    setaparam(args[0], a);
	else
	    sethparam(args[0], a);
    } else
	setsparam(args[0], t);
    unqueue_signals();
    return 0;
}
Exemple #7
0
static mnumber
setmathvar(struct mathvalue *mvp, mnumber v)
{
    Param pm;

    if (mvp->pval) {
	/*
	 * This value may have been hanging around for a while.
	 * Be ultra-paranoid in checking the variable is still valid.
	 */
	char *s = mvp->lval, *ptr;
	Param pm;
	DPUTS(!mvp->lval, "no variable name but variable value in math");
	if ((ptr = strchr(s, '[')))
	    s = dupstrpfx(s, ptr - s);
	pm = (Param) paramtab->getnode(paramtab, s);
	if (pm == mvp->pval->pm) {
	    if (noeval)
		return v;
	    setnumvalue(mvp->pval, v);
	    return v;
	}
	/* Different parameter, start again from scratch */
	mvp->pval = NULL;
    }
    if (!mvp->lval) {
	zerr("lvalue required");
	v.type = MN_INTEGER;
	v.u.l = 0;
	return v;
    }
    if (noeval)
	return v;
    untokenize(mvp->lval);
    pm = setnparam(mvp->lval, v);
    if (pm) {
	/*
	 * If we are performing an assignment, we return the
	 * number with the same type as the parameter we are
	 * assigning to, in the spirit of the way assignments
	 * in C work.  Note this was a change to long-standing
	 * zsh behaviour.
	 */
	switch (PM_TYPE(pm->node.flags)) {
	case PM_INTEGER:
	    if (v.type != MN_INTEGER) {
		v.u.l = (zlong)v.u.d;
		v.type = MN_INTEGER;
	    }
	    break;

	case PM_EFLOAT:
	case PM_FFLOAT:
	    if (v.type != MN_FLOAT) {
		v.u.d = (double)v.u.l;
		v.type = MN_FLOAT;
	    }
	    break;
	}
    }
    return v;
}
Exemple #8
0
void
printparamnode(HashNode hn, int printflags)
{
#ifdef ZSH_64_BIT_TYPE
    static char llbuf[DIGBUFSIZE];
#endif
    Param p = (Param) hn;
    char *t, **u;

    if (p->flags & PM_UNSET)
	return;

    /* Print the attributes of the parameter */
    if (printflags & PRINT_TYPE) {
	if (p->flags & PM_INTEGER)
	    printf("integer ");
	if (p->flags & PM_ARRAY)
	    printf("array ");
	if (p->flags & PM_LEFT)
	    printf("left justified %d ", p->ct);
	if (p->flags & PM_RIGHT_B)
	    printf("right justified %d ", p->ct);
	if (p->flags & PM_RIGHT_Z)
	    printf("zero filled %d ", p->ct);
	if (p->flags & PM_LOWER)
	    printf("lowercase ");
	if (p->flags & PM_UPPER)
	    printf("uppercase ");
	if (p->flags & PM_READONLY)
	    printf("readonly ");
	if (p->flags & PM_TAGGED)
	    printf("tagged ");
	if (p->flags & PM_EXPORTED)
	    printf("exported ");
    }

    if (printflags & PRINT_NAMEONLY) {
	zputs(p->nam, stdout);
	putchar('\n');
	return;
    }

    /* How the value is displayed depends *
     * on the type of the parameter       */
    quotedzputs(p->nam, stdout);
    putchar('=');
    switch (PM_TYPE(p->flags)) {
    case PM_SCALAR:
	/* string: simple output */
	if (p->gets.cfn && (t = p->gets.cfn(p)))
	    quotedzputs(t, stdout);
	putchar('\n');
	break;
    case PM_INTEGER:
	/* integer */
#ifdef ZSH_64_BIT_TYPE
	convbase(llbuf, p->gets.ifn(p), 0);
	puts(llbuf);
#else
	printf("%ld\n", p->gets.ifn(p));
#endif
	break;
    case PM_ARRAY:
	/* array */
	putchar('(');
	u = p->gets.afn(p);
	if(*u) {
	    quotedzputs(*u++, stdout);
	    while (*u) {
		putchar(' ');
		quotedzputs(*u++, stdout);
	    }
	}
	printf(")\n");
	break;
    }
}