diff options
-rw-r--r-- | bin/sh/expand.c | 42 | ||||
-rw-r--r-- | bin/sh/main.c | 5 | ||||
-rw-r--r-- | bin/sh/mksyntax.c | 9 | ||||
-rw-r--r-- | bin/sh/var.c | 52 |
4 files changed, 96 insertions, 12 deletions
diff --git a/bin/sh/expand.c b/bin/sh/expand.c index a5d69ce..f4cbac6 100644 --- a/bin/sh/expand.c +++ b/bin/sh/expand.c @@ -33,7 +33,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $Id: expand.c,v 1.3 1995/03/01 13:04:15 guido Exp $ + * $Id: expand.c,v 1.4 1995/05/30 00:07:13 rgrimes Exp $ */ #ifndef lint @@ -102,6 +102,7 @@ STATIC struct strlist *expsort(struct strlist *); STATIC struct strlist *msort(struct strlist *, int); STATIC int pmatch(char *, char *); STATIC char *exptilde(char *, int); +STATIC int collcmp (int, int); #else STATIC void argstr(); STATIC void expbackq(); @@ -118,6 +119,7 @@ STATIC struct strlist *expsort(); STATIC struct strlist *msort(); STATIC int pmatch(); STATIC char *exptilde(); +STATIC int collcmp (); #endif /* @@ -1018,6 +1020,40 @@ patmatch(pattern, string) return pmatch(pattern, string); } +STATIC int +collcmp (c1, c2) +int c1, c2; +{ + static char s1[2], s2[2]; + + c1 &= 0xFF; + c2 &= 0xFF; + if (c1 == c2) + return (0); + if ( (isascii(c1) && isascii(c2)) + || (!isalpha(c1) && !isalpha(c2)) + ) + return (c1 - c2); + if (isalpha(c1) && !isalpha(c2)) { + if (isupper(c1)) + return ('A' - c2); + else + return ('a' - c2); + } else if (isalpha(c2) && !isalpha(c1)) { + if (isupper(c2)) + return (c1 - 'A'); + else + return (c1 - 'a'); + } + if (isupper(c1) && islower(c2)) + return (-1); + else if (islower(c1) && isupper(c2)) + return (1); + s1[0] = c1; + s2[0] = c2; + return strcoll(s1, s2); +} + STATIC int pmatch(pattern, string) @@ -1086,7 +1122,9 @@ pmatch(pattern, string) p++; if (*p == CTLESC) p++; - if (chr >= c && chr <= *p) + if ( collcmp(chr, c) >= 0 + && collcmp(chr, *p) <= 0 + ) found = 1; p++; } else { diff --git a/bin/sh/main.c b/bin/sh/main.c index 9d451d4..34a0abb 100644 --- a/bin/sh/main.c +++ b/bin/sh/main.c @@ -33,7 +33,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $Id: main.c,v 1.2 1994/09/24 02:57:48 davidg Exp $ + * $Id: main.c,v 1.3 1995/05/30 00:07:18 rgrimes Exp $ */ #ifndef lint @@ -48,6 +48,8 @@ static char sccsid[] = "@(#)main.c 8.1 (Berkeley) 5/31/93"; #include <signal.h> #include <fcntl.h> +#include <locale.h> + #include "shell.h" #include "main.h" #include "mail.h" @@ -103,6 +105,7 @@ main(argc, argv) char **argv; { #if PROFILE monitor(4, etext, profile_buf, sizeof profile_buf, 50); #endif + (void) setlocale(LC_ALL, ""); state = 0; if (setjmp(jmploc.loc)) { /* diff --git a/bin/sh/mksyntax.c b/bin/sh/mksyntax.c index b55545c..d7edf70 100644 --- a/bin/sh/mksyntax.c +++ b/bin/sh/mksyntax.c @@ -33,7 +33,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $Id$ + * $Id: mksyntax.c,v 1.2 1994/09/24 02:57:57 davidg Exp $ */ #ifndef lint @@ -155,6 +155,7 @@ main() { digit_contig = 0; } + fputs("#include <ctype.h>\n", hfile); fputs("#include <sys/cdefs.h>\n", hfile); /* Generate the #define statements in the header file */ @@ -327,9 +328,9 @@ print(name) char *macro[] = { "#define is_digit(c)\t((is_type+SYNBASE)[c] & ISDIGIT)", - "#define is_alpha(c)\t((is_type+SYNBASE)[c] & (ISUPPER|ISLOWER))", - "#define is_name(c)\t((is_type+SYNBASE)[c] & (ISUPPER|ISLOWER|ISUNDER))", - "#define is_in_name(c)\t((is_type+SYNBASE)[c] & (ISUPPER|ISLOWER|ISUNDER|ISDIGIT))", + "#define is_alpha(c)\t((c) != PEOF && isalpha((unsigned char) (c)))", + "#define is_name(c)\t((c) != PEOF && ((c) == '_' || isalpha((unsigned char) (c))))", + "#define is_in_name(c)\t((c) != PEOF && ((c) == '_' || isdigit((unsigned char) (c)) || isalpha((unsigned char) (c))))", "#define is_special(c)\t((is_type+SYNBASE)[c] & (ISSPECL|ISDIGIT))", NULL }; diff --git a/bin/sh/var.c b/bin/sh/var.c index 00420d5..710edc78 100644 --- a/bin/sh/var.c +++ b/bin/sh/var.c @@ -33,7 +33,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $Id: var.c,v 1.2 1994/09/24 02:58:22 davidg Exp $ + * $Id: var.c,v 1.3 1995/05/30 00:07:24 rgrimes Exp $ */ #ifndef lint @@ -44,6 +44,8 @@ static char sccsid[] = "@(#)var.c 8.1 (Berkeley) 5/31/93"; * Shell variables. */ +#include <locale.h> + #include "shell.h" #include "output.h" #include "expand.h" @@ -108,6 +110,7 @@ struct var *vartab[VTABSIZE]; STATIC int unsetvar __P((char *)); STATIC struct var **hashvar __P((char *)); STATIC int varequal __P((char *, char *)); +STATIC int localevar __P((char *)); /* * Initialize the varable symbol tables and import the environment @@ -178,8 +181,9 @@ setvar(name, val, flags) isbad = 0; p = name; - if (! is_name(*p++)) + if (! is_name(*p)) isbad = 1; + p++; for (;;) { if (! is_in_name(*p)) { if (*p == '\0' || *p == '=') @@ -208,7 +212,27 @@ setvar(name, val, flags) setvareq(nameeq, flags); } - +STATIC int +localevar(s) + char *s; + { + static char *lnames[7] = { + "ALL", "COLLATE", "CTYPE", "MONETARY", + "NUMERIC", "TIME", NULL + }; + char **ss; + + if (*s != 'L') + return 0; + if (varequal(s + 1, "ANG")) + return 1; + if (strncmp(s + 1, "C_", 2) != 0) + return 0; + for (ss = lnames; *ss ; ss++) + if (varequal(s + 3, *ss)) + return 1; + return 0; +} /* * Same as setvar except that the variable and value are passed in @@ -242,6 +266,10 @@ setvareq(s, flags) chkmail(1); if (vp == &vhistsize) sethistsize(); + if ((vp->flags & VEXPORT) && localevar(s)) { + putenv(s); + (void) setlocale(LC_ALL, ""); + } INTON; return; } @@ -251,7 +279,13 @@ setvareq(s, flags) vp->flags = flags; vp->text = s; vp->next = *vpp; + INTOFF; *vpp = vp; + if ((vp->flags & VEXPORT) && localevar(s)) { + putenv(s); + (void) setlocale(LC_ALL, ""); + } + INTON; } @@ -441,6 +475,10 @@ exportcmd(argc, argv) char **argv; { for (vp = *vpp ; vp ; vp = vp->next) { if (varequal(vp->text, name)) { vp->flags |= flag; + if ((vp->flags & VEXPORT) && localevar(vp->text)) { + putenv(vp->text); + (void) setlocale(LC_ALL, ""); + } goto found; } } @@ -616,6 +654,10 @@ unsetvar(s) INTOFF; if (*(strchr(vp->text, '=') + 1) != '\0') setvar(s, nullstr, 0); + if ((vp->flags & VEXPORT) && localevar(vp->text)) { + unsetenv(s); + setlocale(LC_ALL, ""); + } vp->flags &=~ VEXPORT; vp->flags |= VUNSET; if ((vp->flags & VSTRFIXED) == 0) { @@ -644,9 +686,9 @@ hashvar(p) { unsigned int hashval; - hashval = *p << 4; + hashval = ((unsigned char)*p) << 4; while (*p && *p != '=') - hashval += *p++; + hashval += (unsigned char)*p++; return &vartab[hashval % VTABSIZE]; } |