www.delorie.com/archives/browse.cgi   search  
Mail Archives: djgpp-workers/2001/12/29/20:45:21

Date: Sat, 29 Dec 2001 17:39:58 -0500
From: AAganichev AT netscape DOT net (Alexander Aganichev)
To: djgpp-workers AT delorie DOT com
Subject: Complete set of NLS fixes (regex + strftime + locale)
Message-ID: <71D97FA1.16796777.09ACFA57@netscape.net>
X-Mailer: Atlas Mailer 1.0
MIME-Version: 1.0
Reply-To: djgpp-workers AT delorie DOT com

---------71e0e4991680cc6f71e0e4991680cc6f
Content-Type: text/plain; charset=iso-8859-1
Content-Transfer-Encoding: 8bit
Content-Disposition: inline

And here is NLS patchset:
* string.diff: collate fix (prepare for NLS). Converts to table-based compare
* time.diff: strftime fix (prepare for NLS). Fixes 'x' and 'X'
* regex.diff: regex fix (require collate fix). Fixes warnings, crash on NL chars, memory leaks
* locale.diff: locale support (require collate and strftime fixes). Makes more correct locale behaviour based on country.sys settings. See COPYING.EMX (emx-lib section) for the license

Happy New Year :-)

-- 
alexander aganichev
url: http://aaganichev.narod.ru



__________________________________________________________________
Your favorite stores, helpful shopping tools and great gift ideas. Experience the convenience of buying online with Shop AT Netscape! http://shopnow.netscape.com/

Get your own FREE, personal Netscape Mail account today at http://webmail.netscape.com/

---------71e0e4991680cc6f71e0e4991680cc6f
Content-Type: text/plain; charset=iso-8859-1; name="string.diff"
Content-Transfer-Encoding: 8bit
Content-Disposition: inline; filename="string.diff"
Content-Description: string.diff

diff -rup E:\Sources\djgpp\src\libc/ansi/string/strcoll.c libc/ansi/string/strcoll.c
--- E:\Sources\djgpp\src\libc/ansi/string/strcoll.c	Tue Nov 29 12:41:28 1994
+++ libc/ansi/string/strcoll.c	Sat Dec 29 14:21:12 2001
@@ -1,8 +1,54 @@
 /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
+/* Modified 1999 by Alexander S. Aganichev <asa AT users DOT sf DOT net> */
+
 #include <string.h>
 
+unsigned char __dj_collate_table[256] =
+{
+  0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
+  0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
+  0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
+  0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
+  0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
+  0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f,
+  0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
+  0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f,
+  0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,
+  0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f,
+  0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57,
+  0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f,
+  0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
+  0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f,
+  0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,
+  0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f,
+  0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
+  0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f,
+  0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
+  0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f,
+  0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7,
+  0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf,
+  0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7,
+  0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf,
+  0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7,
+  0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf,
+  0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7,
+  0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf,
+  0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7,
+  0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef,
+  0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,
+  0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+#define coll(c) __dj_collate_table[(unsigned char)c]
+
 int
 strcoll(const char *s1, const char *s2)
 {
-  return strcmp(s1, s2);
+  while (coll(*s1) == coll(*s2)) {
+    if (*s1 == 0)
+      return 0;
+    s1++;
+    s2++;
+  }
+  return coll(*s1) - coll(*s2);
 }

---------71e0e4991680cc6f71e0e4991680cc6f
Content-Type: text/plain; charset=iso-8859-1; name="time.diff"
Content-Transfer-Encoding: 8bit
Content-Disposition: inline; filename="time.diff"
Content-Description: time.diff

diff -rup E:\Sources\djgpp\src\libc/ansi/time/strftime.c libc/ansi/time/strftime.c
--- E:\Sources\djgpp\src\libc/ansi/time/strftime.c	Tue Dec  4 07:54:20 2001
+++ libc/ansi/time/strftime.c	Sat Dec 29 14:20:42 2001
@@ -2,6 +2,7 @@
 /* Copyright (C) 1999 DJ Delorie, see COPYING.DJ for details */
 /* Copyright (C) 1998 DJ Delorie, see COPYING.DJ for details */
 /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
+
 #include <string.h>
 #include <time.h>
 #include <ctype.h>
@@ -23,6 +24,8 @@ static const char *Bfmt[] = {
   "January", "February", "March", "April", "May", "June", "July",
   "August", "September", "October", "November", "December",
 };
+char __dj_date_format[10] = "%m/%d/%y";
+char __dj_time_format[16] = "%H:%M:%S";
 
 static size_t gsize;
 static char *pt;
@@ -177,7 +180,6 @@ _fmt(const char *format, const struct tm
 	  return 0;
 	continue;
       case 'T':
-      case 'X':
 	if (!_fmt("%H:%M:%S", t, upcase))
 	  return 0;
 	continue;
@@ -204,8 +206,12 @@ _fmt(const char *format, const struct tm
 	if (!_conv(t->tm_wday, 1, pad))
 	  return 0;
 	continue;
+      case 'X':
+	if (!_fmt(__dj_time_format, t, upcase))
+	  return 0;
+	continue;
       case 'x':
-	if (!_fmt("%m/%d/%y", t, upcase))
+	if (!_fmt(__dj_date_format, t, upcase))
 	  return 0;
 	continue;
       case 'y':

---------71e0e4991680cc6f71e0e4991680cc6f
Content-Type: text/plain; charset=iso-8859-1; name="regex.diff"
Content-Transfer-Encoding: 8bit
Content-Disposition: inline; filename="regex.diff"
Content-Description: regex.diff

diff -rup E:\Sources\djgpp\src\libc/posix/regex/cclass.h libc/posix/regex/cclass.h
--- E:\Sources\djgpp\src\libc/posix/regex/cclass.h	Thu Jul 16 21:20:30 1998
+++ libc/posix/regex/cclass.h	Sat Dec 29 12:03:52 2001
@@ -1,32 +1,27 @@
 /* Copyright (C) 1998 DJ Delorie, see COPYING.DJ for details */
+
+typedef enum {
+	CC_ALNUM, CC_ALPHA, CC_BLANK, CC_CNTRL, CC_DIGIT, CC_GRAPH, CC_LOWER,
+	CC_PRINT, CC_PUNCT, CC_SPACE, CC_UPPER, CC_XDIGIT
+} cclasstype;
+
 /* character-class table */
 static struct cclass {
-	char *name;
-	char *chars;
-	char *multis;
+	const char *name;
+	cclasstype type;
+	const char *multis;
 } cclasses[] = {
-	"alnum",	"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\
-0123456789",				"",
-	"alpha",	"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz",
-					"",
-	"blank",	" \t",		"",
-	"cntrl",	"\007\b\t\n\v\f\r\1\2\3\4\5\6\16\17\20\21\22\23\24\
-\25\26\27\30\31\32\33\34\35\36\37\177",	"",
-	"digit",	"0123456789",	"",
-	"graph",	"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\
-0123456789!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~",
-					"",
-	"lower",	"abcdefghijklmnopqrstuvwxyz",
-					"",
-	"print",	"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\
-0123456789!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~ ",
-					"",
-	"punct",	"!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~",
-					"",
-	"space",	"\t\n\v\f\r ",	"",
-	"upper",	"ABCDEFGHIJKLMNOPQRSTUVWXYZ",
-					"",
-	"xdigit",	"0123456789ABCDEFabcdef",
-					"",
-	NULL,		0,		""
+	{ "alnum",	CC_ALNUM,	"" },
+	{ "alpha",	CC_ALPHA,	"" },
+	{ "blank",	CC_BLANK,	"" },
+	{ "cntrl",	CC_CNTRL,	"" },
+	{ "digit",	CC_DIGIT,	"" },
+	{ "graph",	CC_GRAPH,	"" },
+	{ "lower",	CC_LOWER,	"" },
+	{ "print",	CC_PRINT,	"" },
+	{ "punct",	CC_PUNCT,	"" },
+	{ "space",	CC_SPACE,	"" },
+	{ "upper",	CC_UPPER,	"" },
+	{ "xdigit",	CC_XDIGIT,	"" },
+	{ NULL,		0,		"" }
 };
diff -rup E:\Sources\djgpp\src\libc/posix/regex/cname.h libc/posix/regex/cname.h
--- E:\Sources\djgpp\src\libc/posix/regex/cname.h	Thu Jul 16 21:20:30 1998
+++ libc/posix/regex/cname.h	Sat Dec 29 12:01:18 2001
@@ -1,103 +1,104 @@
 /* Copyright (C) 1998 DJ Delorie, see COPYING.DJ for details */
 /* character-name table */
 static struct cname {
-	char *name;
+	const char *name;
 	char code;
 } cnames[] = {
-	"NUL",	'\0',
-	"SOH",	'\001',
-	"STX",	'\002',
-	"ETX",	'\003',
-	"EOT",	'\004',
-	"ENQ",	'\005',
-	"ACK",	'\006',
-	"BEL",	'\007',
-	"alert",	'\007',
-	"BS",		'\010',
-	"backspace",	'\b',
-	"HT",		'\011',
-	"tab",		'\t',
-	"LF",		'\012',
-	"newline",	'\n',
-	"VT",		'\013',
-	"vertical-tab",	'\v',
-	"FF",		'\014',
-	"form-feed",	'\f',
-	"CR",		'\015',
-	"carriage-return",	'\r',
-	"SO",	'\016',
-	"SI",	'\017',
-	"DLE",	'\020',
-	"DC1",	'\021',
-	"DC2",	'\022',
-	"DC3",	'\023',
-	"DC4",	'\024',
-	"NAK",	'\025',
-	"SYN",	'\026',
-	"ETB",	'\027',
-	"CAN",	'\030',
-	"EM",	'\031',
-	"SUB",	'\032',
-	"ESC",	'\033',
-	"IS4",	'\034',
-	"FS",	'\034',
-	"IS3",	'\035',
-	"GS",	'\035',
-	"IS2",	'\036',
-	"RS",	'\036',
-	"IS1",	'\037',
-	"US",	'\037',
-	"space",		' ',
-	"exclamation-mark",	'!',
-	"quotation-mark",	'"',
-	"number-sign",		'#',
-	"dollar-sign",		'$',
-	"percent-sign",		'%',
-	"ampersand",		'&',
-	"apostrophe",		'\'',
-	"left-parenthesis",	'(',
-	"right-parenthesis",	')',
-	"asterisk",	'*',
-	"plus-sign",	'+',
-	"comma",	',',
-	"hyphen",	'-',
-	"hyphen-minus",	'-',
-	"period",	'.',
-	"full-stop",	'.',
-	"slash",	'/',
-	"solidus",	'/',
-	"zero",		'0',
-	"one",		'1',
-	"two",		'2',
-	"three",	'3',
-	"four",		'4',
-	"five",		'5',
-	"six",		'6',
-	"seven",	'7',
-	"eight",	'8',
-	"nine",		'9',
-	"colon",	':',
-	"semicolon",	';',
-	"less-than-sign",	'<',
-	"equals-sign",		'=',
-	"greater-than-sign",	'>',
-	"question-mark",	'?',
-	"commercial-at",	'@',
-	"left-square-bracket",	'[',
-	"backslash",		'\\',
-	"reverse-solidus",	'\\',
-	"right-square-bracket",	']',
-	"circumflex",		'^',
-	"circumflex-accent",	'^',
-	"underscore",		'_',
-	"low-line",		'_',
-	"grave-accent",		'`',
-	"left-brace",		'{',
-	"left-curly-bracket",	'{',
-	"vertical-line",	'|',
-	"right-brace",		'}',
-	"right-curly-bracket",	'}',
-	"tilde",		'~',
-	"DEL",	'\177',
-	NULL,	0,
+   { "NUL",    '\0' },
+   { "SOH",    '\001' },
+   { "STX",    '\002' },
+   { "ETX",    '\003' },
+   { "EOT",    '\004' },
+   { "ENQ",    '\005' },
+   { "ACK",    '\006' },
+   { "BEL",    '\007' },
+   { "alert",  '\007' },
+   { "BS",     '\010' },
+   { "backspace",  '\b' },
+   { "HT",     '\011' },
+   { "tab",        '\t' },
+   { "LF",     '\012' },
+   { "newline",    '\n' },
+   { "VT",     '\013' },
+   { "vertical-tab",   '\v' },
+   { "FF",     '\014' },
+   { "form-feed",  '\f' },
+   { "CR",     '\015' },
+   { "carriage-return",    '\r' },
+   { "SO", '\016' },
+   { "SI", '\017' },
+   { "DLE",    '\020' },
+   { "DC1",    '\021' },
+   { "DC2",    '\022' },
+   { "DC3",    '\023' },
+   { "DC4",    '\024' },
+   { "NAK",    '\025' },
+   { "SYN",    '\026' },
+   { "ETB",    '\027' },
+   { "CAN",    '\030' },
+   { "EM", '\031' },
+   { "SUB",    '\032' },
+   { "ESC",    '\033' },
+   { "IS4",    '\034' },
+   { "FS", '\034' },
+   { "IS3",    '\035' },
+   { "GS", '\035' },
+   { "IS2",    '\036' },
+   { "RS", '\036' },
+   { "IS1",    '\037' },
+   { "US", '\037' },
+   { "space",      ' ' },
+   { "exclamation-mark",   '!' },
+   { "quotation-mark", '\"' },
+   { "number-sign",        '#' },
+   { "dollar-sign",        '$' },
+   { "percent-sign",       '%' },
+   { "ampersand",      '&' },
+   { "apostrophe",     '\'' },
+   { "left-parenthesis",   '(' },
+   { "right-parenthesis",  ')' },
+   { "asterisk",   '*' },
+   { "plus-sign",  '+' },
+   { "comma",  ',' },
+   { "hyphen", '-' },
+   { "hyphen-minus",   '-' },
+   { "period", '.' },
+   { "full-stop",  '.' },
+   { "slash",  '/' },
+   { "solidus",    '/' },
+   { "zero",       '0' },
+   { "one",        '1' },
+   { "two",        '2' },
+   { "three",  '3' },
+   { "four",       '4' },
+   { "five",       '5' },
+   { "six",        '6' },
+   { "seven",  '7' },
+   { "eight",  '8' },
+   { "nine",       '9' },
+   { "colon",  ':' },
+   { "semicolon",  ';' },
+   { "less-than-sign", '<' },
+   { "equals-sign",        '=' },
+   { "greater-than-sign",  '>' },
+   { "question-mark",  '?' },
+   { "commercial-at",  '@' },
+   { "left-square-bracket",    '[' },
+   { "backslash",      '\\' },
+   { "reverse-solidus",    '\\' },
+   { "right-square-bracket",   ']' },
+   { "circumflex",     '^' },
+   { "circumflex-accent",  '^' },
+   { "underscore",     '_' },
+   { "low-line",       '_' },
+   { "grave-accent",       '`' },
+   { "left-brace",     '{' },
+   { "left-curly-bracket", '{' },
+   { "vertical-line",  '|' },
+   { "right-brace",        '}' },
+   { "right-curly-bracket",    '}' },
+   { "tilde",      '~' },
+   { "DEL",    '\177' },
+   { NULL, 0, }
 };
+
diff -rup E:\Sources\djgpp\src\libc/posix/regex/debug.c libc/posix/regex/debug.c
--- E:\Sources\djgpp\src\libc/posix/regex/debug.c	Thu Jul 16 21:20:30 1998
+++ libc/posix/regex/debug.c	Sat Dec 29 12:01:18 2001
@@ -235,7 +235,7 @@ int ch;
 {
 	static char buf[10];
 
-	if (isprint(ch) || ch == ' ')
+	if (isprint((unsigned char) ch) || ch == ' ')
 		sprintf(buf, "%c", ch);
 	else
 		sprintf(buf, "\\%o", ch);
diff -rup E:\Sources\djgpp\src\libc/posix/regex/engine.c libc/posix/regex/engine.c
--- E:\Sources\djgpp\src\libc/posix/regex/engine.c	Thu Jul 16 21:20:30 1998
+++ libc/posix/regex/engine.c	Sat Dec 29 12:01:18 2001
@@ -34,11 +34,11 @@ struct match {
 	struct re_guts *g;
 	int eflags;
 	regmatch_t *pmatch;	/* [nsub+1] (0 element unused) */
-	char *offp;		/* offsets work from here */
-	char *beginp;		/* start of string -- virtual NUL precedes */
-	char *endp;		/* end of string -- virtual NUL here */
-	char *coldp;		/* can be no match starting before here */
-	char **lastpos;		/* [nplus+1] */
+	const char *offp;	/* offsets work from here */
+	const char *beginp;	/* start of string -- virtual NUL precedes */
+	const char *endp;	/* end of string -- virtual NUL here */
+	const char *coldp;	/* can be no match starting before here */
+	const char **lastpos;	/* [nplus+1] */
 	STATEVARS;
 	states st;		/* current states */
 	states fresh;		/* states for a fresh start */
@@ -60,26 +60,26 @@ struct match {
 
 /*
  - matcher - the actual matching engine
- == static int matcher(register struct re_guts *g, char *string, \
+ == static int matcher(register struct re_guts *g, const char *string, \
  ==	size_t nmatch, regmatch_t pmatch[], int eflags);
  */
 static int			/* 0 success, REG_NOMATCH failure */
 matcher(g, string, nmatch, pmatch, eflags)
 register struct re_guts *g;
-char *string;
+const char *string;
 size_t nmatch;
 regmatch_t pmatch[];
 int eflags;
 {
-	register char *endp;
+	register const char *endp;
 	register int i;
 	struct match mv;
 	register struct match *m = &mv;
-	register char *dp;
+	register const char *dp;
 	const register sopno gf = g->firststate+1;	/* +1 for OEND */
 	const register sopno gl = g->laststate;
-	char *start;
-	char *stop;
+	const char *start;
+	const char *stop;
 
 	/* simplify the situation where possible */
 	if (g->cflags&REG_NOSUB)
@@ -157,7 +157,7 @@ int eflags;
 			dp = dissect(m, m->coldp, endp, gf, gl);
 		} else {
 			if (g->nplus > 0 && m->lastpos == NULL)
-				m->lastpos = (char **)malloc((g->nplus+1) *
+				m->lastpos = malloc((g->nplus+1) *
 							sizeof(char *));
 			if (g->nplus > 0 && m->lastpos == NULL) {
 				free(m->pmatch);
@@ -217,39 +217,39 @@ int eflags;
 	}
 
 	if (m->pmatch != NULL)
-		free((char *)m->pmatch);
+		free(m->pmatch);
 	if (m->lastpos != NULL)
-		free((char *)m->lastpos);
+		free(m->lastpos);
 	STATETEARDOWN(m);
 	return(0);
 }
 
 /*
  - dissect - figure out what matched what, no back references
- == static char *dissect(register struct match *m, char *start, \
- ==	char *stop, sopno startst, sopno stopst);
+ == static const char *dissect(register struct match *m, const char *start, \
+ ==	const char *stop, sopno startst, sopno stopst);
  */
-static char *			/* == stop (success) always */
+static const char *		/* == stop (success) always */
 dissect(m, start, stop, startst, stopst)
 register struct match *m;
-char *start;
-char *stop;
+const char *start;
+const char *stop;
 sopno startst;
 sopno stopst;
 {
 	register int i;
 	register sopno ss;	/* start sop of current subRE */
 	register sopno es;	/* end sop of current subRE */
-	register char *sp;	/* start of string matched by it */
-	register char *stp;	/* string matched by it cannot pass here */
-	register char *rest;	/* start of rest of string */
-	register char *tail;	/* string unmatched by rest of RE */
+	register const char *sp; /* start of string matched by it */
+	register const char *stp; /* string matched by it cannot pass here */
+	register const char *rest; /* start of rest of string */
+	register const char *tail; /* string unmatched by rest of RE */
 	register sopno ssub;	/* start sop of subsubRE */
 	register sopno esub;	/* end sop of subsubRE */
-	register char *ssp;	/* start of string matched by subsubRE */
-	register char *sep;	/* end of string matched by subsubRE */
-	register char *oldssp;	/* previous ssp */
-	register char *dp;
+	register const char *ssp; /* start of string matched by subsubRE */
+	register const char *sep; /* end of string matched by subsubRE */
+	register const char *oldssp; /* previous ssp */
+	register const char *dp;
 
 	AT("diss", start, stop, startst, stopst);
 	sp = start;
@@ -414,25 +414,25 @@ sopno stopst;
 
 /*
  - backref - figure out what matched what, figuring in back references
- == static char *backref(register struct match *m, char *start, \
- ==	char *stop, sopno startst, sopno stopst, sopno lev);
+ == static const char *backref(register struct match *m, const char *start, \
+ ==	const char *stop, sopno startst, sopno stopst, sopno lev);
  */
-static char *			/* == stop (success) or NULL (failure) */
+static const char *		/* == stop (success) or NULL (failure) */
 backref(m, start, stop, startst, stopst, lev)
 register struct match *m;
-char *start;
-char *stop;
+const char *start;
+const char *stop;
 sopno startst;
 sopno stopst;
 sopno lev;			/* PLUS nesting level */
 {
 	register int i;
 	register sopno ss;	/* start sop of current subRE */
-	register char *sp;	/* start of string matched by it */
+	register const char *sp; /* start of string matched by it */
 	register sopno ssub;	/* start sop of subsubRE */
 	register sopno esub;	/* end sop of subsubRE */
-	register char *ssp;	/* start of string matched by subsubRE */
-	register char *dp;
+	register const char *ssp; /* start of string matched by subsubRE */
+	register const char *dp;
 	register size_t len;
 	register int hard;
 	register sop s;
@@ -614,31 +614,31 @@ sopno lev;			/* PLUS nesting level */
 	/* "can't happen" */
 	assert(nope);
 	/* NOTREACHED */
-	return((char *)NULL);	/* dummy */
+	return(NULL);	/* dummy */
 }
 
 /*
  - fast - step through the string at top speed
- == static char *fast(register struct match *m, char *start, \
- ==	char *stop, sopno startst, sopno stopst);
+ == static const char *fast(register struct match *m, const char *start, \
+ ==	const char *stop, sopno startst, sopno stopst);
  */
-static char *			/* where tentative match ended, or NULL */
+static const char *		/* where tentative match ended, or NULL */
 fast(m, start, stop, startst, stopst)
 register struct match *m;
-char *start;
-char *stop;
+const char *start;
+const char *stop;
 sopno startst;
 sopno stopst;
 {
 	register states st = m->st;
 	register states fresh = m->fresh;
 	register states tmp = m->tmp;
-	register char *p = start;
+	register const char *p = start;
 	register int c = (start == m->beginp) ? OUT : *(start-1);
 	register int lastc;	/* previous c */
 	register int flagch;
 	register int i;
-	register char *coldp;	/* last p after which no match was underway */
+	register const char *coldp; /* last p after which no match was underway */
 
 	CLEAR(st);
 	SET1(st, startst);
@@ -710,26 +710,26 @@ sopno stopst;
 
 /*
  - slow - step through the string more deliberately
- == static char *slow(register struct match *m, char *start, \
- ==	char *stop, sopno startst, sopno stopst);
+ == static const char *slow(register struct match *m, const char *start, \
+ ==	const char *stop, sopno startst, sopno stopst);
  */
-static char *			/* where it ended */
+static const char *		/* where it ended */
 slow(m, start, stop, startst, stopst)
 register struct match *m;
-char *start;
-char *stop;
+const char *start;
+const char *stop;
 sopno startst;
 sopno stopst;
 {
 	register states st = m->st;
 	register states empty = m->empty;
 	register states tmp = m->tmp;
-	register char *p = start;
+	register const char *p = start;
 	register int c = (start == m->beginp) ? OUT : *(start-1);
 	register int lastc;	/* previous c */
 	register int flagch;
 	register int i;
-	register char *matchp;	/* last p at which a match ended */
+	register const char *matchp; /* last p at which a match ended */
 
 	AT("slow", start, stop, startst, stopst);
 	CLEAR(st);
@@ -927,14 +927,14 @@ register states aft;		/* states already 
 /*
  - print - print a set of states
  == #ifdef REDEBUG
- == static void print(struct match *m, char *caption, states st, \
+ == static void print(struct match *m, const char *caption, states st, \
  ==	int ch, FILE *d);
  == #endif
  */
 static void
 print(m, caption, st, ch, d)
 struct match *m;
-char *caption;
+const char *caption;
 states st;
 int ch;
 FILE *d;
@@ -960,16 +960,17 @@ FILE *d;
 /* 
  - at - print current situation
  == #ifdef REDEBUG
- == static void at(struct match *m, char *title, char *start, char *stop, \
- ==						sopno startst, sopno stopst);
+ == static void at(struct match *m, const char *title, \
+ ==			const char *start, const char *stop, \
+ ==			sopno startst, sopno stopst);
  == #endif
  */
 static void
 at(m, title, start, stop, startst, stopst)
 struct match *m;
-char *title;
-char *start;
-char *stop;
+const char *title;
+const char *start;
+const char *stop;
 sopno startst;
 sopno stopst;
 {
@@ -1000,7 +1001,7 @@ int ch;
 {
 	static char pbuf[10];
 
-	if (isprint(ch) || ch == ' ')
+	if (isprint((unsigned char)ch) || ch == ' ')
 		sprintf(pbuf, "%c", ch);
 	else
 		sprintf(pbuf, "\\%o", ch);
diff -rup E:\Sources\djgpp\src\libc/posix/regex/engine.ih libc/posix/regex/engine.ih
--- E:\Sources\djgpp\src\libc/posix/regex/engine.ih	Fri Jul 17 23:32:10 1998
+++ libc/posix/regex/engine.ih	Sat Dec 29 12:01:18 2001
@@ -4,11 +4,11 @@ extern "C" {
 #endif
 
 /* === engine.c === */
-static int matcher(register struct re_guts *g, char *string, size_t nmatch, regmatch_t pmatch[], int eflags);
-static char *dissect(register struct match *m, char *start, char *stop, sopno startst, sopno stopst);
-static char *backref(register struct match *m, char *start, char *stop, sopno startst, sopno stopst, sopno lev);
-static char *fast(register struct match *m, char *start, char *stop, sopno startst, sopno stopst);
-static char *slow(register struct match *m, char *start, char *stop, sopno startst, sopno stopst);
+static int matcher(register struct re_guts *g, const char *string, size_t nmatch, regmatch_t pmatch[], int eflags);
+static const char *dissect(register struct match *m, const char *start, const char *stop, sopno startst, sopno stopst);
+static const char *backref(register struct match *m, const char *start, const char *stop, sopno startst, sopno stopst, sopno lev);
+static const char *fast(register struct match *m, const char *start, const char *stop, sopno startst, sopno stopst);
+static const char *slow(register struct match *m, const char *start, const char *stop, sopno startst, sopno stopst);
 static states step(register struct re_guts *g, sopno start, sopno stop, register states bef, int ch, register states aft);
 #define	BOL	(OUT+1)
 #define	EOL	(BOL+1)
@@ -20,10 +20,11 @@ static states step(register struct re_gu
 #define	NONCHAR(c)	((c) > CHAR_MAX)
 #define	NNONCHAR	(CODEMAX-CHAR_MAX)
 #ifdef REDEBUG
-static void print(struct match *m, char *caption, states st, int ch, FILE *d);
+static void print(struct match *m, const char *caption, states st, int ch, FILE *d);
 #endif
 #ifdef REDEBUG
-static void at(struct match *m, char *title, char *start, char *stop, sopno startst, sopno stopst);
+static void at(struct match *m, const char *title, const char *start, const char *stop, \
+		sopno startst, sopno stopst);
 #endif
 #ifdef REDEBUG
 static char *pchar(int ch);
diff -rup E:\Sources\djgpp\src\libc/posix/regex/makefile libc/posix/regex/makefile
--- E:\Sources\djgpp\src\libc/posix/regex/makefile	Sun Jul 12 22:06:56 1998
+++ libc/posix/regex/makefile	Sat Dec 29 12:01:18 2001
@@ -3,15 +3,9 @@
 # Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details
 TOP=../..
 
-# supress all warnings here
-CFLAGS = -w
-
 SRC += regcomp.c
 SRC += regerror.c
 SRC += regexec.c
 SRC += regfree.c
 
 include $(TOP)/../makefile.inc
-
-XGCC = $(XLGCC)
-
diff -rup E:\Sources\djgpp\src\libc/posix/regex/makefile.bsd libc/posix/regex/makefile.bsd
--- E:\Sources\djgpp\src\libc/posix/regex/makefile.bsd	Fri Jul 17 23:30:36 1998
+++ libc/posix/regex/makefile.bsd	Sat Dec 29 12:01:18 2001
@@ -8,7 +8,7 @@ SHELL=/bin/sh
 # REGCFLAGS isn't important to you (it's for my use in some special contexts).
 
 # CFLAGS=-I. -DPOSIX_MISTAKE -DREDEBUG $(REGCFLAGS)
-CFLAGS=-I. -DPOSIX_MISTAKE -O2 $(REGCFLAGS)
+CFLAGS=-I. -DPOSIX_MISTAKE -O2 $(REGCFLAGS) -I ../../../../include
 
 # If you have a pre-ANSI compiler, put -o into MKHFLAGS.  If you want
 # the Berkeley __P macro, put -b in.
diff -rup E:\Sources\djgpp\src\libc/posix/regex/regcomp.c libc/posix/regex/regcomp.c
--- E:\Sources\djgpp\src\libc/posix/regex/regcomp.c	Sat Jun  9 23:50:56 2001
+++ libc/posix/regex/regcomp.c	Sat Dec 29 16:03:38 2001
@@ -8,6 +8,8 @@
 #include <stdlib.h>
 #include <regex.h>
 
+#include <libc/unconst.h>
+
 #include "utils.h"
 #include "regex2.h"
 
@@ -34,6 +36,21 @@ struct parse {
 
 #include "regcomp.ih"
 
+/*
+ * if ctype.h not defines isblank define our own version
+ */
+#ifndef isblank
+static int
+isblank(ch)
+int ch;
+{
+	return (((ch) == ' ') || ((ch) == '\t'));
+}
+#endif
+
+extern unsigned char __dj_collate_table[256];
+#define coll(c) __dj_collate_table[(unsigned char)c]
+
 static char nuls[10];		/* place to point scanner in event of error */
 
 /*
@@ -53,10 +70,10 @@ static char nuls[10];		/* place to point
 #define	NEXTn(n)	(p->next += (n))
 #define	GETNEXT()	(*p->next++)
 #define	SETERROR(e)	seterr(p, (e))
-#define	REQUIRE(co, e)	((co) || SETERROR(e))
-#define	MUSTSEE(c, e)	(REQUIRE(MORE() && PEEK() == (c), e))
-#define	MUSTEAT(c, e)	(REQUIRE(MORE() && GETNEXT() == (c), e))
-#define	MUSTNOTSEE(c, e)	(REQUIRE(!MORE() || PEEK() != (c), e))
+#define	REQUIRE(co, e)  do { if (!(co)) SETERROR(e); } while (0)
+#define	MUSTSEE(c, e)	REQUIRE(MORE() && PEEK() == (c), e)
+#define	MUSTEAT(c, e)	REQUIRE(MORE() && GETNEXT() == (c), e)
+#define	MUSTNOTSEE(c, e)	REQUIRE(!MORE() || PEEK() != (c), e)
 #define	EMIT(op, sopnd)	doemit(p, (sop)(op), (size_t)(sopnd))
 #define	INSERT(op, pos)	doinsert(p, (sop)(op), HERE()-(pos)+1, pos)
 #define	AHEAD(pos)		dofwd(p, pos, HERE()-(pos))
@@ -110,7 +127,7 @@ int cflags;
 			return(REG_INVARG);
 		len = preg->re_endp - pattern;
 	} else
-		len = strlen((char *)pattern);
+		len = strlen(pattern);
 
 	/* do the mallocs early so failure handling is easy */
 	g = (struct re_guts *)malloc(sizeof(struct re_guts) +
@@ -127,7 +144,7 @@ int cflags;
 
 	/* set things up */
 	p->g = g;
-	p->next = (char *)pattern;	/* convenience; we do not modify it */
+	p->next = unconst(pattern, char *); /* convenience; we do not modify it */
 	p->end = p->next + len;
 	p->error = 0;
 	p->ncsalloc = 0;
@@ -194,8 +211,8 @@ register struct parse *p;
 int stop;			/* character this ERE should end at */
 {
 	register char c;
-	register sopno prevback;
-	register sopno prevfwd;
+	register sopno prevback = 0;
+	register sopno prevfwd = 0;
 	register sopno conc;
 	register int first = 1;		/* is this the first alternative? */
 
@@ -312,7 +329,7 @@ register struct parse *p;
 		ordinary(p, c);
 		break;
 	case '{':		/* okay as ordinary except if digit follows */
-		REQUIRE(!MORE() || !isdigit(PEEK()), REG_BADRPT);
+		REQUIRE(!MORE() || !isdigit((unsigned char)PEEK()), REG_BADRPT);
 		/* FALLTHROUGH */
 	default:
 		ordinary(p, c);
@@ -324,7 +341,7 @@ register struct parse *p;
 	c = PEEK();
 	/* we call { a repetition if followed by a digit */
 	if (!( c == '*' || c == '+' || c == '?' ||
-				(c == '{' && MORE2() && isdigit(PEEK2())) ))
+	       (c == '{' && MORE2() && isdigit((unsigned char)PEEK2())) ))
 		return;		/* no repetition, we're done */
 	NEXT();
 
@@ -353,7 +370,7 @@ register struct parse *p;
 	case '{':
 		count = p_count(p);
 		if (EAT(',')) {
-			if (isdigit(PEEK())) {
+			if (isdigit((unsigned char)PEEK())) {
 				count2 = p_count(p);
 				REQUIRE(count <= count2, REG_BADBR);
 			} else		/* single number with comma */
@@ -374,7 +391,7 @@ register struct parse *p;
 		return;
 	c = PEEK();
 	if (!( c == '*' || c == '+' || c == '?' ||
-				(c == '{' && MORE2() && isdigit(PEEK2())) ) )
+	       (c == '{' && MORE2() && isdigit((unsigned char)PEEK2())) ) )
 		return;
 	SETERROR(REG_BADRPT);
 }
@@ -531,7 +548,7 @@ int starordinary;		/* is a leading * an 
 	} else if (EATTWO('\\', '{')) {
 		count = p_count(p);
 		if (EAT(',')) {
-			if (MORE() && isdigit(PEEK())) {
+			if (MORE() && isdigit((unsigned char)PEEK())) {
 				count2 = p_count(p);
 				REQUIRE(count <= count2, REG_BADBR);
 			} else		/* single number with comma */
@@ -562,7 +579,7 @@ register struct parse *p;
 	register int count = 0;
 	register int ndigits = 0;
 
-	while (MORE() && isdigit(PEEK()) && count <= DUPMAX) {
+	while (MORE() && isdigit((unsigned char)PEEK()) && count <= DUPMAX) {
 		count = count*10 + (GETNEXT() - '0');
 		ndigits++;
 	}
@@ -585,6 +602,9 @@ register struct parse *p;
 	register cset *cs = allocset(p);
 	register int invert = 0;
 
+	if (cs == NULL)
+		return;
+
 	/* Dept of Truly Sickening Special-Case Kludges */
 	if (p->next + 5 < p->end && strncmp(p->next, "[:<:]]", 6) == 0) {
 		EMIT(OBOW, 0);
@@ -617,7 +637,7 @@ register struct parse *p;
 		register int ci;
 
 		for (i = p->g->csetsize - 1; i >= 0; i--)
-			if (CHIN(cs, i) && isalpha(i)) {
+			if (CHIN(cs, i) && isalpha((unsigned char)i)) {
 				ci = othercase(i);
 				if (ci != i)
 					CHadd(cs, ci);
@@ -706,10 +726,16 @@ register cset *cs;
 				finish = p_b_symbol(p);
 		} else
 			finish = start;
-/* xxx what about signed chars here... */
+#if 1
+		REQUIRE(coll(start) <= coll(finish), REG_ERANGE);
+		for (i = CHAR_MIN; i <= CHAR_MAX; i++)
+			if ((coll(start) <= coll(i)) && (coll(i) <= coll(finish)))
+				CHadd(cs, i);
+#else
 		REQUIRE(start <= finish, REG_ERANGE);
 		for (i = start; i <= finish; i++)
 			CHadd(cs, i);
+#endif
 		break;
 	}
 }
@@ -726,10 +752,10 @@ register cset *cs;
 	register char *sp = p->next;
 	register struct cclass *cp;
 	register size_t len;
-	register char *u;
-	register char c;
+	register const char *u;
+	register int c;
 
-	while (MORE() && isalpha(PEEK()))
+	while (MORE() && isalpha((unsigned char)PEEK()))
 		NEXT();
 	len = p->next - sp;
 	for (cp = cclasses; cp->name != NULL; cp++)
@@ -741,9 +767,68 @@ register cset *cs;
 		return;
 	}
 
-	u = cp->chars;
-	while ((c = *u++) != '\0')
-		CHadd(cs, c);
+	switch(cp->type) {
+	case CC_ALNUM:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(isalnum((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_ALPHA:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(isalpha((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_BLANK:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(isblank((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_CNTRL:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(iscntrl((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_DIGIT:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(isdigit((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_GRAPH:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(isgraph((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_LOWER:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(islower((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_PRINT:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(isprint((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_PUNCT:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(ispunct((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_SPACE:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(isspace((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_UPPER:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(isupper((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	case CC_XDIGIT:
+		for (c = CHAR_MIN; c <= CHAR_MAX; c++)
+			if(isxdigit((unsigned char)c))
+				CHadd(cs, c);
+		break;
+	}
 	for (u = cp->multis; *u != '\0'; u += strlen(u) + 1)
 		MCadd(p, cs, u);
 }
@@ -822,11 +907,11 @@ static char			/* if no counterpart, retu
 othercase(ch)
 int ch;
 {
-	assert(isalpha(ch));
-	if (isupper(ch))
-		return(tolower(ch));
-	else if (islower(ch))
-		return(toupper(ch));
+	assert(isalpha((unsigned char)ch));
+	if (isupper((unsigned char)ch))
+		return(tolower((unsigned char)ch));
+	else if (islower((unsigned char)ch))
+		return(toupper((unsigned char)ch));
 	else			/* peculiar, but could happen */
 		return(ch);
 }
@@ -868,8 +953,9 @@ register struct parse *p;
 register int ch;
 {
 	register cat_t *cap = p->g->categories;
-
-	if ((p->g->cflags&REG_ICASE) && isalpha(ch) && othercase(ch) != ch)
+	
+	if ((p->g->cflags&REG_ICASE) && isalpha((unsigned char)ch) &&
+	    othercase(ch) != ch)
 		bothcases(p, ch);
 	else {
 		EMIT(OCHAR, (unsigned char)ch);
@@ -1014,25 +1100,49 @@ register struct parse *p;
 		nbytes = nc / CHAR_BIT * css;
 		if (p->g->sets == NULL)
 			p->g->sets = (cset *)malloc(nc * sizeof(cset));
-		else
-			p->g->sets = (cset *)realloc((char *)p->g->sets,
-							nc * sizeof(cset));
-		if (p->g->setbits == NULL)
-			p->g->setbits = (uch *)malloc(nbytes);
 		else {
-			p->g->setbits = (uch *)realloc((char *)p->g->setbits,
-								nbytes);
-			/* xxx this isn't right if setbits is now NULL */
-			for (i = 0; i < no; i++)
-				p->g->sets[i].ptr = p->g->setbits + css*(i/CHAR_BIT);
+			cset *pgss = (cset *)realloc((char *)p->g->sets,
+							nc * sizeof(cset));
+			if(pgss == NULL) {
+				free(p->g->sets);
+				p->g->sets = NULL;
+			}
+			else
+				p->g->sets = pgss;
+		}
+
+		if (p->g->sets == NULL) {
+			if (p->g->setbits != NULL) {
+				free(p->g->setbits);
+				p->g->setbits = NULL;
+			}
+		} else {
+			if (p->g->setbits == NULL)
+				p->g->setbits = (uch *)malloc(nbytes);
+			else {
+				uch *pgsbs = (uch *)realloc((char *)p->g->setbits,
+									nbytes);
+				if (pgsbs != NULL) {
+					p->g->setbits = pgsbs;
+					for (i = 0; i < no; i++)
+						p->g->sets[i].ptr = p->g->setbits + css*(i/CHAR_BIT);
+				} else {
+					free(p->g->setbits);
+					p->g->setbits = NULL;
+				}
+			}
+			if (p->g->setbits == NULL) {
+				free(p->g->sets);
+				p->g->sets = NULL;
+			}
 		}
 		if (p->g->sets != NULL && p->g->setbits != NULL)
 			(void) memset((char *)p->g->setbits + (nbytes - css),
 								0, css);
 		else {
-			no = 0;
 			SETERROR(REG_ESPACE);
 			/* caller's responsibility not to do set ops */
+			return NULL;
 		}
 	}
 
@@ -1147,21 +1257,27 @@ register cset *cs;
 /*
  - mcadd - add a collating element to a cset
  == static void mcadd(register struct parse *p, register cset *cs, \
- ==	register char *cp);
+ ==	register const char *cp);
  */
 static void
 mcadd(p, cs, cp)
 register struct parse *p;
 register cset *cs;
-register char *cp;
+register const char *cp;
 {
 	register size_t oldend = cs->smultis;
 
 	cs->smultis += strlen(cp) + 1;
 	if (cs->multis == NULL)
 		cs->multis = malloc(cs->smultis);
-	else
-		cs->multis = realloc(cs->multis, cs->smultis);
+	else {
+		char *csm = realloc(cs->multis, cs->smultis);
+		if (csm == NULL) {
+			free(cs->multis);
+			cs->multis = NULL;
+		} else
+			cs->multis = csm;
+	}
 	if (cs->multis == NULL) {
 		SETERROR(REG_ESPACE);
 		return;
@@ -1172,64 +1288,6 @@ register char *cp;
 }
 
 /*
- - mcsub - subtract a collating element from a cset
- == static void mcsub(register cset *cs, register char *cp);
- */
-static void
-mcsub(cs, cp)
-register cset *cs;
-register char *cp;
-{
-	register char *fp = mcfind(cs, cp);
-	register size_t len = strlen(fp);
-
-	assert(fp != NULL);
-	(void) memmove(fp, fp + len + 1,
-				cs->smultis - (fp + len + 1 - cs->multis));
-	cs->smultis -= len;
-
-	if (cs->smultis == 0) {
-		free(cs->multis);
-		cs->multis = NULL;
-		return;
-	}
-
-	cs->multis = realloc(cs->multis, cs->smultis);
-	assert(cs->multis != NULL);
-}
-
-/*
- - mcin - is a collating element in a cset?
- == static int mcin(register cset *cs, register char *cp);
- */
-static int
-mcin(cs, cp)
-register cset *cs;
-register char *cp;
-{
-	return(mcfind(cs, cp) != NULL);
-}
-
-/*
- - mcfind - find a collating element in a cset
- == static char *mcfind(register cset *cs, register char *cp);
- */
-static char *
-mcfind(cs, cp)
-register cset *cs;
-register char *cp;
-{
-	register char *p;
-
-	if (cs->multis == NULL)
-		return(NULL);
-	for (p = cs->multis; *p != '\0'; p += strlen(p) + 1)
-		if (strcmp(cp, p) == 0)
-			return(p);
-	return(NULL);
-}
-
-/*
  - mcinvert - invert the list of collating elements in a cset
  == static void mcinvert(register struct parse *p, register cset *cs);
  *
@@ -1497,8 +1555,8 @@ struct parse *p;
 register struct re_guts *g;
 {
 	register sop *scan;
-	sop *start;
-	register sop *newstart;
+	sop *start = NULL;
+	register sop *newstart = NULL;
 	register sopno newlen;
 	register sop s;
 	register char *cp;
diff -rup E:\Sources\djgpp\src\libc/posix/regex/regcomp.ih libc/posix/regex/regcomp.ih
--- E:\Sources\djgpp\src\libc/posix/regex/regcomp.ih	Fri Jul 17 23:32:04 1998
+++ libc/posix/regex/regcomp.ih	Sat Dec 29 14:07:30 2001
@@ -4,6 +4,9 @@ extern "C" {
 #endif
 
 /* === regcomp.c === */
+#ifndef isblank
+static int isblank(int ch);
+#endif
 static void p_ere(register struct parse *p, int stop);
 static void p_ere_exp(register struct parse *p);
 static void p_str(register struct parse *p);
@@ -27,10 +30,7 @@ static void freeset(register struct pars
 static int freezeset(register struct parse *p, register cset *cs);
 static int firstch(register struct parse *p, register cset *cs);
 static int nch(register struct parse *p, register cset *cs);
-static void mcadd(register struct parse *p, register cset *cs, register char *cp);
-static void mcsub(register cset *cs, register char *cp);
-static int mcin(register cset *cs, register char *cp);
-static char *mcfind(register cset *cs, register char *cp);
+static void mcadd(register struct parse *p, register cset *cs, register const char *cp);
 static void mcinvert(register struct parse *p, register cset *cs);
 static void mccase(register struct parse *p, register cset *cs);
 static int isinsets(register struct re_guts *g, int c);
diff -rup E:\Sources\djgpp\src\libc/posix/regex/regerror.c libc/posix/regex/regerror.c
--- E:\Sources\djgpp\src\libc/posix/regex/regerror.c	Thu Jul 16 21:20:30 1998
+++ libc/posix/regex/regerror.c	Sat Dec 29 12:01:18 2001
@@ -33,27 +33,27 @@
  */
 static struct rerr {
 	int code;
-	char *name;
-	char *explain;
+	const char *name;
+	const char *explain;
 } rerrs[] = {
-	REG_OKAY,	"REG_OKAY",	"no errors detected",
-	REG_NOMATCH,	"REG_NOMATCH",	"regexec() failed to match",
-	REG_BADPAT,	"REG_BADPAT",	"invalid regular expression",
-	REG_ECOLLATE,	"REG_ECOLLATE",	"invalid collating element",
-	REG_ECTYPE,	"REG_ECTYPE",	"invalid character class",
-	REG_EESCAPE,	"REG_EESCAPE",	"trailing backslash (\\)",
-	REG_ESUBREG,	"REG_ESUBREG",	"invalid backreference number",
-	REG_EBRACK,	"REG_EBRACK",	"brackets ([ ]) not balanced",
-	REG_EPAREN,	"REG_EPAREN",	"parentheses not balanced",
-	REG_EBRACE,	"REG_EBRACE",	"braces not balanced",
-	REG_BADBR,	"REG_BADBR",	"invalid repetition count(s)",
-	REG_ERANGE,	"REG_ERANGE",	"invalid character range",
-	REG_ESPACE,	"REG_ESPACE",	"out of memory",
-	REG_BADRPT,	"REG_BADRPT",	"repetition-operator operand invalid",
-	REG_EMPTY,	"REG_EMPTY",	"empty (sub)expression",
-	REG_ASSERT,	"REG_ASSERT",	"\"can't happen\" -- you found a bug",
-	REG_INVARG,	"REG_INVARG",	"invalid argument to regex routine",
-	-1,		"",		"*** unknown regexp error code ***",
+   { REG_OKAY, "REG_OKAY", "no errors detected" },
+   { REG_NOMATCH,  "REG_NOMATCH",  "regexec() failed to match" },
+   { REG_BADPAT,   "REG_BADPAT",   "invalid regular expression" },
+   { REG_ECOLLATE, "REG_ECOLLATE", "invalid collating element" },
+   { REG_ECTYPE,   "REG_ECTYPE",   "invalid character class" },
+   { REG_EESCAPE,  "REG_EESCAPE",  "trailing backslash (\\)" },
+   { REG_ESUBREG,  "REG_ESUBREG",  "invalid backreference number" },
+   { REG_EBRACK,   "REG_EBRACK",   "brackets ([ ]) not balanced" },
+   { REG_EPAREN,   "REG_EPAREN",   "parentheses not balanced" },
+   { REG_EBRACE,   "REG_EBRACE",   "braces not balanced" },
+   { REG_BADBR,    "REG_BADBR",    "invalid repetition count(s)" },
+   { REG_ERANGE,   "REG_ERANGE",   "invalid character range" },
+   { REG_ESPACE,   "REG_ESPACE",   "out of memory" },
+   { REG_BADRPT,   "REG_BADRPT",   "repetition-operator operand invalid" },
+   { REG_EMPTY,    "REG_EMPTY",    "empty (sub)expression" },
+   { REG_ASSERT,   "REG_ASSERT",   "\"can't happen\" -- you found a bug" },
+   { REG_INVARG,   "REG_INVARG",   "invalid argument to regex routine" },
+   { -1,       "",     "*** unknown regexp error code ***" }
 };
 
 /*
@@ -71,7 +71,7 @@ size_t errbuf_size;
 	register struct rerr *r;
 	register size_t len;
 	register int target = errcode &~ REG_ITOA;
-	register char *s;
+	register const char *s;
 	char convbuf[50];
 
 	if (errcode == REG_ATOI)
@@ -119,9 +119,9 @@ char *localbuf;
 	for (r = rerrs; r->code >= 0; r++)
 		if (strcmp(r->name, preg->re_endp) == 0)
 			break;
-	if (r->code < 0)
-		return("0");
-
-	sprintf(localbuf, "%d", r->code);
+	if (r->code < 0) 
+		strcpy(localbuf, "0");
+	else 
+		sprintf(localbuf, "%d", r->code);
 	return(localbuf);
 }
diff -rup E:\Sources\djgpp\src\libc/posix/regex/regex2.h libc/posix/regex/regex2.h
--- E:\Sources\djgpp\src\libc/posix/regex/regex2.h	Thu Jul 16 21:20:30 1998
+++ libc/posix/regex/regex2.h	Sat Dec 29 12:01:18 2001
@@ -132,4 +132,4 @@ struct re_guts {
 
 /* misc utilities */
 #define	OUT	(CHAR_MAX+1)	/* a non-character value */
-#define	ISWORD(c)	(isalnum(c) || (c) == '_')
+#define	ISWORD(c)	(isalnum((unsigned char)c) || (c) == '_')
diff -rup E:\Sources\djgpp\src\libc/posix/regex/regexec.c libc/posix/regex/regexec.c
--- E:\Sources\djgpp\src\libc/posix/regex/regexec.c	Thu Jul 16 21:20:30 1998
+++ libc/posix/regex/regexec.c	Sat Dec 29 12:01:18 2001
@@ -17,7 +17,9 @@
 #include "utils.h"
 #include "regex2.h"
 
+#ifndef NDEBUG
 static int nope = 0;		/* for use in asserts; shuts lint up */
+#endif
 
 /* macros for manipulating states, small version */
 #define	states	unsigned
@@ -133,7 +135,7 @@ int eflags;
 	eflags = GOODFLAGS(eflags);
 
 	if (g->nstates <= CHAR_BIT*sizeof(states1) && !(eflags&REG_LARGE))
-		return(smatcher(g, (char *)string, nmatch, pmatch, eflags));
+		return(smatcher(g, string, nmatch, pmatch, eflags));
 	else
-		return(lmatcher(g, (char *)string, nmatch, pmatch, eflags));
+		return(lmatcher(g, string, nmatch, pmatch, eflags));
 }

---------71e0e4991680cc6f71e0e4991680cc6f
Content-Type: text/plain; charset=iso-8859-1; name="locale.diff"
Content-Transfer-Encoding: 8bit
Content-Disposition: inline; filename="locale.diff"
Content-Description: locale.diff

diff -rup E:\Sources\djgpp\src\libc/ansi/locale/setlocal.c libc/ansi/locale/setlocal.c
--- E:\Sources\djgpp\src\libc/ansi/locale/setlocal.c	Tue Nov 29 12:18:16 1994
+++ libc/ansi/locale/setlocal.c	Sat Dec 29 14:21:00 2001
@@ -1,13 +1,399 @@
 /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
+/* Portions copyright (C) 1994-1996 by Eberhard Mattes */
+/* Modified 1999-2001 by Alexander S. Aganichev <asa AT users DOT sf DOT net> */
+
 #include <locale.h>
+#include <ctype.h>
+#include <stdlib.h>
 #include <string.h>
+#include <dpmi.h>
+#ifdef TEST
+#include <sys/farptr.h>
+#else
+#include <libc/farptrgs.h>
+#endif
+#include <go32.h>
+#include <limits.h>
+
+#define LOCALE_NAME_MAX (5+1+10)	/* "ru_RU.866" */
+
+static char lcn_collate[LOCALE_NAME_MAX + 1] = "C";
+static char lcn_ctype[LOCALE_NAME_MAX + 1] = "C";
+static char lcn_monetary[LOCALE_NAME_MAX + 1] = "C";
+static char lcn_numeric[LOCALE_NAME_MAX + 1] = "C";
+static char lcn_time[LOCALE_NAME_MAX + 1] = "C";
+
+static char currency_symbol[6] = "";
+static char mon_decimal_point[2] = "";
+static char mon_thousands_sep[2] = "";
+static char decimal_point[2] = ".";
+static char thousands_sep[2] = "";
+
+static struct __loc2id {
+  int id;
+  const char loc[LOCALE_NAME_MAX + 1];
+  int len;
+} loc2id[] = {
+
+  /* add your country here ;-) */
+  {
+    1, "en_US", 5
+  },
+  {
+    7, "ru_RU", 5
+  },
+  {
+    33, "fr_FR", 5
+  },
+  {
+    49, "de_DE", 5
+  }
+};
+
+static const int cat[5] =
+{LC_COLLATE, LC_CTYPE, LC_MONETARY, LC_NUMERIC, LC_TIME};
 
-char *setlocale(int category, const char *locale)
+extern unsigned char __dj_collate_table[];
+extern char __dj_date_format[];
+extern char __dj_time_format[];
+
+static int
+setlocale2(int category, const char *locale)
 {
-  static char CLOCALE[] = "C";
-  if (locale == 0)
-    return CLOCALE;
-  if (strcmp(locale, CLOCALE) && strcmp(locale, "POSIX") && locale[0])
+  int segment, selector;
+  __dpmi_regs regs;
+  struct lconv *lcnv = localeconv();
+  int i, rv = 0;
+  char buf[LOCALE_NAME_MAX + 1];
+
+  if (category == LC_ALL) {
+    rv = !setlocale2(LC_COLLATE, locale);
+    rv += !setlocale2(LC_CTYPE, locale);
+    rv += !setlocale2(LC_MONETARY, locale);
+    rv += !setlocale2(LC_NUMERIC, locale);
+    rv += !setlocale2(LC_TIME, locale);
+    return !rv;
+  }
+
+  if (!strcmp(locale, "C") || !strcmp(locale, "POSIX")) {
+    switch (category) {
+    case LC_COLLATE:
+      for (i = 0; i < 256; i++)
+	__dj_collate_table[i] = i;
+      strcpy(lcn_collate, locale);
+      return 1;
+    case LC_CTYPE:
+      for (i = 128; i < 256; i++) {
+	__dj_ctype_tolower[i + 1] = i;
+	__dj_ctype_toupper[i + 1] = i;
+	__dj_ctype_flags[i + 1] = 0;
+      }
+      strcpy(lcn_ctype, locale);
+      return 1;
+    case LC_MONETARY:
+      if (lcnv) {
+	strcpy(currency_symbol, "");
+	lcnv->int_curr_symbol = lcnv->currency_symbol = currency_symbol;
+	strcpy(mon_thousands_sep, "");
+	lcnv->mon_thousands_sep = mon_thousands_sep;
+	strcpy(mon_decimal_point, "");
+	lcnv->mon_decimal_point = mon_decimal_point;
+	/* lcnv->mon_grouping = ""; */
+	/* lcnv->negative_sign = ""; */
+	/* lcnv->positive_sign = ""; */
+	lcnv->int_frac_digits = lcnv->frac_digits = CHAR_MAX;
+	lcnv->p_cs_precedes = lcnv->n_cs_precedes = CHAR_MAX;
+	lcnv->p_sep_by_space = lcnv->n_sep_by_space = CHAR_MAX;
+	/* lcnv->p_sign_posn = lcnv->n_sign_posn = CHAR_MAX; */
+	strcpy(lcn_monetary, locale);
+	return 1;
+      }
+      else
+	return 0;
+    case LC_NUMERIC:
+      if (lcnv) {
+	strcpy(thousands_sep, "");
+	lcnv->thousands_sep = thousands_sep;
+	strcpy(decimal_point, ".");
+	lcnv->decimal_point = decimal_point;
+	/* lcnv->grouping = ""; */
+	strcpy(lcn_numeric, locale);
+	return 1;
+      }
+      else
+	return 0;
+    case LC_TIME:
+      strcpy(__dj_date_format, "%m/%d/%y");
+      strcpy(__dj_time_format, "%H:%M:%S");
+      strcpy(lcn_time, locale);
+      return 1;
+    }
+  }
+  if ((segment = __dpmi_allocate_dos_memory(3, &selector)) != -1) {
+    int CID = 0xffff, CCP = 0xffff;
+
+    if (*locale) {
+      int len;
+      const char *p = strchr(locale, '.');
+      if (p == NULL)
+	p = locale + strlen(locale);
+      len = p - locale;
+      for (i = 0; i < sizeof(loc2id) / sizeof(struct __loc2id); i++)
+	if (!strncmp(locale, loc2id[i].loc, len >= loc2id[i].len ? len : loc2id[i].len)) {
+	  CID = loc2id[i].id;
+	  break;
+	}
+      if (*p == '.')
+	CCP = atoi(p + 1);
+    }
+
+    regs.h.ah = 0x65;
+    regs.h.al = 0x01;
+    regs.x.bx = CCP;
+    regs.x.dx = CID;
+    regs.x.cx = 41;
+    regs.x.es = segment;
+    regs.x.di = 0;
+    __dpmi_int(0x21, &regs);
+    if (!(regs.x.flags & 1) && regs.x.cx == 41) {
+      if (!*locale) {
+	CID = _farpeekw(selector, 3);
+	CCP = _farpeekw(selector, 5);
+	locale = buf;
+	strcpy(buf, "en_US.");
+	for (i = 0; i < sizeof(loc2id) / sizeof(struct __loc2id); i++)
+	  if (loc2id[i].id == CID) {
+	    strcpy(buf, loc2id[i].loc);
+	    buf[loc2id[i].len] = '.';
+	    break;
+	  }
+	itoa(CCP, &buf[strlen(buf)], 10);
+      }
+      switch (category) {
+      case LC_COLLATE:
+	regs.h.ah = 0x65;
+	regs.h.al = 0x06;
+	regs.x.bx = CCP;
+	regs.x.dx = CID;
+	regs.x.cx = 5;
+	regs.x.es = segment;
+	regs.x.di = 0;
+	__dpmi_int(0x21, &regs);
+	if (!(regs.x.flags & 1) && (regs.x.cx == 5)) {
+	  unsigned int table = _farpeekw(selector, 3) * 16 + _farpeekw(selector, 1);
+	  int size = _farpeekw(_dos_ds, table);
+	  movedata(_dos_ds, table + 2, _my_ds(), (unsigned int) __dj_collate_table, size);
+	  rv = 1;
+	}
+	else
+	  rv = 0;
+	strcpy(lcn_collate, locale);
+	rv = 1;
+	break;
+      case LC_CTYPE:
+	regs.h.ah = 0x65;
+	regs.h.al = 0x02;
+	regs.x.bx = CCP;
+	regs.x.dx = CID;
+	regs.x.cx = 5;
+	regs.x.es = segment;
+	regs.x.di = 0;
+	__dpmi_int(0x21, &regs);
+	if (!(regs.x.flags & 1) && (regs.x.cx == 5)) {
+	  unsigned int table = _farpeekw(selector, 3) * 16 + _farpeekw(selector, 1);
+	  int size = _farpeekw(_dos_ds, table);
+	  movedata(_dos_ds, table + 2, _my_ds(), (unsigned int) &(__dj_ctype_toupper[128 + 1]), size);
+	  /* let's build lowercase table from uppercase... */
+	  for (i = 0; i < size; i++) {
+	    int c = toupper(i + 128);
+	    if ((c != i + 128) && (c > 127))
+	      __dj_ctype_tolower[c + 1] = i + 128;
+	  }
+	  for (i = 128; i < 256; i++) {
+	    /* By this conversion we could break something like 0xe1 in CP437
+	       * but in most cases it better works this way */
+	    if ((toupper(tolower(i)) != i) && (tolower(toupper(i)) != i))
+	      __dj_ctype_tolower[i + 1] = __dj_ctype_toupper[i + 1] = i;
+	    if (toupper(tolower(i)) != toupper(i))
+	      __dj_ctype_toupper[i + 1] = i;
+	    if (tolower(toupper(i)) != tolower(i))
+	      __dj_ctype_tolower[i + 1] = i;
+	    /* Actually isgraph(), ispunct() and isspace() will return wrong
+	       * results for some letters like 0xff in CP866 but we can't *
+	       detect them reliably */
+	    __dj_ctype_flags[i + 1] = __dj_ISPRINT | __dj_ISGRAPH;
+	    if (tolower(i) != toupper(i))
+	      __dj_ctype_flags[i + 1] |= __dj_ISALPHA | __dj_ISALNUM | ((i == toupper(i)) ? __dj_ISUPPER : __dj_ISLOWER);
+	    else
+	      __dj_ctype_flags[i + 1] |= __dj_ISPUNCT;
+	  }
+	  rv = 1;
+	}
+	else
+	  rv = 0;
+	strcpy(lcn_ctype, locale);
+	break;
+      case LC_MONETARY:
+	if (lcnv) {
+	  movedata(selector, 9, _my_ds(), (unsigned) currency_symbol, 5);
+	  lcnv->int_curr_symbol = lcnv->currency_symbol = currency_symbol;
+	  movedata(selector, 14, _my_ds(), (unsigned) mon_thousands_sep, 2);
+	  lcnv->mon_thousands_sep = mon_thousands_sep;
+	  movedata(selector, 16, _my_ds(), (unsigned) mon_decimal_point, 2);
+	  lcnv->mon_decimal_point = mon_decimal_point;
+	  /* lcnv->mon_grouping = ""; */
+	  /* lcnv->negative_sign = ""; */
+	  /* lcnv->positive_sign = ""; */
+	  lcnv->int_frac_digits = lcnv->frac_digits = _farpeekb(selector, 24);
+	  lcnv->p_cs_precedes = lcnv->n_cs_precedes = _farpeekb(selector, 23) & 1;
+	  lcnv->p_sep_by_space = lcnv->n_sep_by_space = _farpeekb(selector, 23) & 2;
+	  /* lcnv->p_sign_posn = lcnv->n_sign_posn = CHAR_MAX; */
+	  strcpy(lcn_monetary, locale);
+	  rv = 1;
+	}
+	else
+	  rv = 0;
+	break;
+      case LC_NUMERIC:
+	if (lcnv) {
+	  movedata(selector, 14, _my_ds(), (unsigned) thousands_sep, 2);
+	  lcnv->thousands_sep = thousands_sep;
+	  movedata(selector, 16, _my_ds(), (unsigned) decimal_point, 2);
+	  lcnv->decimal_point = decimal_point;
+	  /* lcnv->grouping = ""; */
+	  strcpy(lcn_numeric, locale);
+	  rv = 1;
+	}
+	else
+	  rv = 0;
+	break;
+      case LC_TIME:
+	switch (_farpeekw(selector, 7)) {
+	case 0:
+	default:
+	  strcpy(__dj_date_format, "%m/%d/%y");
+	  break;
+	case 1:
+	  strcpy(__dj_date_format, "%d/%m/%y");
+	  break;
+	case 2:
+	  strcpy(__dj_date_format, "%y/%m/%d");
+	  break;
+	}
+	__dj_date_format[2] = __dj_date_format[5] = _farpeekb(selector, 18);
+	if (_farpeekb(selector, 24) & 1)
+	  strcpy(__dj_time_format, "%H:%M:%S");
+	else
+	  strcpy(__dj_time_format, "%I:%M:%S %p");
+	__dj_time_format[2] = __dj_time_format[5] = _farpeekb(selector, 20);
+	strcpy(lcn_time, locale);
+	rv = 1;
+	break;
+      }
+    }
+    else
+      rv = 0;
+    __dpmi_free_dos_memory(selector);
+    return rv;
+  }
+  else
     return 0;
-  return CLOCALE;
 }
+
+char *
+setlocale(int category, const char *locale)
+{
+  int i;
+  static char rv[5 * (LOCALE_NAME_MAX + 1)];
+
+  switch (category) {
+  case LC_ALL:
+    if (stricmp(lcn_collate, lcn_ctype) == 0
+	&& stricmp(lcn_collate, lcn_monetary) == 0
+	&& stricmp(lcn_collate, lcn_numeric) == 0
+	&& stricmp(lcn_collate, lcn_time) == 0)
+      strcpy(rv, lcn_collate);
+    else {
+      /* Create a comma-separated list of locales for all the categories. */
+
+      strcpy(rv, lcn_collate);
+      strcat(rv, ",");
+      strcat(rv, lcn_ctype);
+      strcat(rv, ",");
+      strcat(rv, lcn_monetary);
+      strcat(rv, ",");
+      strcat(rv, lcn_numeric);
+      strcat(rv, ",");
+      strcat(rv, lcn_time);
+    }
+    break;
+  case LC_COLLATE:
+    strcpy(rv, lcn_collate);
+    break;
+  case LC_CTYPE:
+    strcpy(rv, lcn_ctype);
+    break;
+  case LC_MONETARY:
+    strcpy(rv, lcn_monetary);
+    break;
+  case LC_NUMERIC:
+    strcpy(rv, lcn_numeric);
+    break;
+  case LC_TIME:
+    strcpy(rv, lcn_time);
+    break;
+  default:
+    return NULL;
+  }
+
+  if (locale != 0) {
+
+    if (*locale == '\0') {
+      char *lc = getenv("LANG");
+      if (lc != NULL)
+	locale = lc;
+    }
+
+    if ((category != LC_ALL) || (strchr(locale, ',') == NULL))
+      return setlocale2(category, locale) ? rv : NULL;
+    else {
+      char *s1, *s2;
+      char buf[5 * (LOCALE_NAME_MAX + 1)];
+
+      strcpy(buf, locale);
+      s1 = buf;
+      for (i = 0; i < 5; i++) {
+	s2 = strchr(s1, ',');
+	if (s2 != NULL)
+	  *s2 = '\0';
+	if (!setlocale2(cat[i], s1) || ((s2 == NULL) && (i != 4)))
+	  return NULL;
+      }
+    }
+  }
+  return rv;
+}
+
+#ifdef TEST
+#include <stdio.h>
+
+unsigned char __dj_collate_table[256];
+char __dj_date_format[10] = "%m/%d/%y";
+char __dj_time_format[16] = "%H:%M:%S";
+
+int
+main(int ac, char *av[])
+{
+  int i;
+  const char *loc = (ac == 1) ? "" : av[1];
+  char *lc = setlocale(LC_ALL, loc);
+  lc = setlocale(LC_ALL, NULL);
+  printf("Locale: %s\n", lc ? lc : "not detected");
+  for (i = 0; i < 256; i++)
+    printf("%c%c%c|", (char) i, tolower(i), toupper(i));
+  printf("\n");
+  for (i = 0; i < 256; i++)
+    printf("%02xh ", __dj_collate_table[i]);
+  printf("\n%f\n%s %s\n", 1000456.23, __dj_date_format, __dj_time_format);
+}
+#endif

---------71e0e4991680cc6f71e0e4991680cc6f
Content-Type: text/plain; charset=iso-8859-1; name="COPYING.EMX"
Content-Transfer-Encoding: 8bit
Content-Disposition: inline; filename="COPYING.EMX"
Content-Description: COPYING.EMX

===============================================================================
copying.emx       emx 0.9d     LICENSE                              19-Dec-1998
===============================================================================
                                     Copyright (c) 1990-1998 by Eberhard Mattes


GNU General Public License (GPL)
--------------------------------

emx 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, or (at your option)
any later version.

emx 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 emx; see the file COPYING.  If not, write to
the Free Software Foundation, 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA.

See \emx\doc\COPYING for details.


Exceptions
----------

As a special exception, some parts of emx can be distributed without
source code if and only if the code has not been modified and a notice
is included where the source code can be obtained.  This special
exception applies to the following files:

  \emx\bin\emx.exe
  \emx\bin\emxd.exe
  \emx\dll\emx.dll
  \emx\dll\emxio.dll

When distributing modified copies of those files, the GPL applies
without exceptions and you have to remove all references to this
exception from the source code and the documentation.  You must not
change the existing Copyright notice.  If you modify a source file, a
notice to that effect must be added to the source file.

As a special exception, if you bind emxl.exe or emx.exe to an
executable file (using emxbind), this does not cause the resulting
executable file to be covered by the GNU General Public License.  This
exception does not however invalidate any other reasons why the
executable file might be covered by the GNU General Public License.
However, if you bind a modified copy of emxl.exe or emx.exe to
an executable file (using emxbind), you have to include source code
for emxl.exe or emx.exe, respectively.

The emx libraries are not distributed under the GPL.  Linking an
application with the emx libraries does not cause the executable to be
covered by the GNU General Public License.  You are allowed to change
and copy the emx library sources if you keep the copyright message
intact.  If you improve the emx libraries, please send your
enhancements to the emx author (you should copyright your enhancements
similar to the existing emx libraries).  Of course, all this does not
apply to the libraries which are distributed under the GPL or the GNU
Library General Public License (LGPL, see \emx\doc\COPYING.LIB) or the
BSD license (see \emx\doc\COPYING.BSD), such as termcap.a, gpp.a and
curses.a.

Code derived from code released by the University of California,
Berkeley, is released under the terms of \emx\doc\COPYING.BSD.  This
applies to the libraries `bsd', `btermcap', `curses', and `db'.

There is also a special exception for the GNU standard C++ library,
libstdc++, see \emx\doc\COPYING.SCP.  This applies to stdcpp.a and
stdcpp.lib.

You are allowed to use, copy, and change the programs in \emx\sample
if you keep the copyright message intact.  The test programs in
\emx\test are in the public domain.

Permission is granted to make and distribute verbatim copies of the
manuals written by Eberhard Mattes provided the copyright notice is
preserved on all copies.  If you modify those manuals, a notice to
that effect must be added to the manual.


Summary
-------

1. Redistributing emx and GNU programs

  If you redistribute emx and the GNU programs, you also have to
  redistribute the source code:

    emxdev1.zip, emxdev2.zip  ->  emxsrcd1.zip, emxsrcd2.zip
    emxrt.zip                 ->  emxsrcr.zip
    gnudev1.zip, gnudev2.zip  ->  gccsrc1.zip, gccsrc2.zip, gccsrc3.zip,
                                  gdbsrc1.zip, gdbsrc2.zip, gnusrc.zip,
                                  gbinusrc.zip
    gnuinfo.zip               ->  gnusrc.zip
    gppdev.zip                ->  gppsrc.zip, gccsrc1.zip, gccsrc2.zip,
                                  gccsrc3.zip
    gobjcdev.zip              ->  gccsrc1.zip, gccsrc2.zip, gccsrc3.zip

2. Distributing applications

  There are no copyright restrictions on applications created with the
  emx tools and the GNU C compiler and linked with the emx libraries.
  However, there are restrictions for applications linked with GNU or
  BSD libraries.

3. Distributing the emx runtime package

  If you distribute emxrt.zip, you also have to redistribute
  emxsrcr.zip.  If you electronically distribute an application which
  requires the emx runtime package, I recommend putting a pointer to
  emxrt.zip into the documentation instead of distributing emxrt.zip.
  That way, users usually get the latest version of emxrt.zip.

4. Distributing applications and emx.dll, emxio.dll and emx.exe

  For small programs, redistributing emxrt.zip may be inconvenient.
  You are allowed to distribute emx.dll, emxio.dll, and emx.exe with
  your application as long as emx.dll, emxio.dll, and emx.exe have not
  been modified.  You should include a notice in the documentation
  which tells users where they can get the complete emx package.

  Note that you can create stand-alone OS/2 applications (using the
  -Zomf -Zsys options of GCC) which do not need emx.dll.

5. Distributing modified copies

  If you modify an emx tool, the GPL will apply without exception,
  that is, you have to include full source code.  See COPYING for
  details.  If you distribute a modified emx.dll, please choose
  another name for the DLL to avoid compatibility problems.  For
  instance, if someone adds feature A to emx.dll, and someone else
  adds feature B to emx.dll, programs using feature A cannot be run
  simultaneously with programs using feature B because only one
  instance of any DLL can be active (either feature A or feature B
  will be present, but not both).  If the DLLs are named emx_a.dll and
  emx_b.dll, that problem does not arise.  The -E option of emxbind
  selects the name of the emx DLL to use.


Copyright
---------

The emx runtime and the emx development tools are

    Copyright (c) 1990-1996 by Eberhard Mattes.

emxfpemu (originally known as wm-FPU-emu) is

    Copyright (c) 1992-1994 by W. Metzenthen.

The emx C library is

    Copyright (c) 1990-1996 by Eberhard Mattes
    Copyright (c) 1991-1993 by Kolja Elsaesser
    Copyright (c) 1992-1993 by Steffen Haecker
    Copyright (c) 1992-1996 by Kai Uwe Rommel
    [...this place is reserved for your name...]

The emx graphics library, the emx video library and the emx OMFLIB
library are

    Copyright (c) 1987-1996 by Eberhard Mattes

DUEL has been written by Michael Golan and is in the public domain.

The GNU programs and libraries, including GCC, GAS, GDB, and libg++,
are

    Copyright (c) by Free Software Foundation, Inc.

The curses library (curses.a), the BSD C library (bsd.a), the BSD
database library (db.a), and the BSD termcap library (btermcap.a) are

    Copyright (c) by University of California, Berkeley


Files
-----

This is an incomplete overview over the executables and libraries.  It
is provided for your convenience only.  If the information in the
source code contradicts this table, the information in the source code
takes precedence.

For .lib and .obj files, see the corresponding .a and .o file,
respectively.

File                    | License       | Copyright owner     | Source ZIP
------------------------+---------------+---------------------+------------
\emx\bin\ar.exe         | GPL           | FSF                 | gbinusrc
\emx\bin\as.exe         | GPL           | FSF                 | gbinusrc
\emx\bin\cc1.exe        | GPL           | FSF                 | gccsrc[123]
\emx\bin\cc1obj.exe     | GPL           | FSF                 | gccsrc[123]
\emx\bin\cc1plus.exe    | GPL           | FSF                 | gccsrc[123]
\emx\bin\cpp.exe        | GPL           | FSF                 | gccsrc[123]
\emx\bin\emx.exe        | GPL+          | em                  | emxsrcr
\emx\bin\emxbind.exe    | GPL           | em                  | emxsrcd[12]
\emx\bin\emxcat.exe     | GPL           | em                  | emxsrcd[12]
\emx\bin\emxd.exe       | GPL+          | em                  | emxsrcr
\emx\bin\emxdoc.exe     | GPL           | em                  | emxsrcd[12]
\emx\bin\emxexp.exe     | GPL           | em                  | emxsrcd[12]
\emx\bin\emxfpemu       | GPL           | W. Metzenthen       | emxsrcr
\emx\bin\emxaout.exe    | GPL           | em                  | emxsrcd[12]
\emx\bin\emximp.exe     | GPL           | em                  | emxsrcd[12]
\emx\bin\emxinst.cmd    | GPL           | em                  | emxdev[12]
\emx\bin\emxl.exe       | GPL+          | em                  | emxsrcr
\emx\bin\emxload.exe    | GPL           | em                  | emxsrcr
\emx\bin\emxomf.exe     | GPL           | em                  | emxsrcd[12]
\emx\bin\emxomfar.exe   | GPL           | em                  | emxsrcd[12]
\emx\bin\emxomfld.exe   | GPL           | em                  | emxsrcd[12]
\emx\bin\emxrev.cmd     | GPL           | em                  | emxrt
\emx\bin\emxstack.exe   | GPL           | em                  | emxsrcr
\emx\bin\emxtsf.exe     | GPL           | em                  | emxsrcd[12]
\emx\bin\emxupd.exe     | GPL           | em                  | emxsrcd[12]
\emx\bin\gasp.exe       | GPL           | FSF                 | gbinusrc
\emx\bin\gcc.exe        | GPL           | FSF                 | gccsrc[123]
\emx\bin\gdb.exe        | GPL           | FSF                 | gdbsrc[12]
\emx\bin\gprof.exe      | BSD           | UCB                 | gbinusrc
\emx\bin\info.exe       | GPL           | FSF                 | gnusrc
\emx\bin\ld.exe         | GPL           | FSF                 | gbinusrc
\emx\bin\listomf.exe    | GPL           | em                  | emxsrcd[12]
\emx\bin\makeinfo.exe   | GPL           | FSF                 | gnusrc
\emx\bin\nm.exe         | GPL           | FSF                 | gbinusrc
\emx\bin\objdump.exe    | GPL           | FSF                 | gbinusrc
\emx\bin\pmgdb.exe      | GPL           | em                  | emxsrcd[12]
\emx\bin\size.exe       | GPL           | FSF                 | gbinusrc
\emx\bin\strip.exe      | GPL           | FSF                 | gbinusrc
\emx\bin\texi2dvi.cmd   | GPL           | em                  | gnuinfo
\emx\bin\texindex.exe   | GPL           | FSF                 | gnusrc
\emx\bin\touch.exe      | GPL           | em                  | emxsrcd[12]
\emx\bin\updt.exe       | GPL           | em                  | emxsrcd[12]
\emx\dll\emx.dll        | GPL+          | em                  | emxsrcr
\emx\dll\emxio.dll      | GPL+          | em                  | emxsrcr
\emx\dll\emxlibc.dll    | emx-lib       | em                  | emxsrcd[12]
\emx\dll\emxlibcm.dll   | emx-lib       | em and contributors | emxsrcd[12]
\emx\dll\emxlibcs.dll   | emx-lib       | em and contributors | emxsrcd[12]
\emx\dll\emxwrap.dll    | emx-lib       | em and contributors | emxsrcd[12]
\emx\dll\gppdemid.dll   | GPL           | FSF, em             | gnusrc
\emx\lib\bsd.a          | BSD           | UCB                 | bsdsrc
\emx\lib\btermcap.a     | BSD           | UCB                 | bsdsrc
\emx\lib\c_alias.a      | emx-lib       | em                  | emxsrcd[12]
\emx\lib\c_static.a     | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\curses.a       | BSD           | UCB                 | bsdsrc
\emx\lib\db.a           | BSD           | UCB                 | bsdsrc
\emx\lib\emx2.a         | emx-lib       | em                  | emxsrcd[12]
\emx\lib\emxio.a        | emx-lib       | em                  | emxsrcr
\emx\lib\g.a            | emx-lib       | em                  | emxsrcd[12]
\emx\lib\gcc.a          | emx-lib, GPL+ | em, FSF             | emxsrcd[12]
\emx\lib\gcc_p.a        | emx-lib, GPL+ | em, FSF             | emxsrcd[12]
\emx\lib\gpp.a          | LGPL          | FSF                 | gppsrc
\emx\lib\graph.a        | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\m.a            | emx-lib       | em                  | emxsrcd[12]
\emx\lib\moddef.a       | emx-lib       | em                  | emxsrcd[12]
\emx\lib\omflib.a       | emx-lib       | em                  | emxsrcd[12]
\emx\lib\os2.a          | emx-lib       | em                  | emxsrcd[12]
\emx\lib\os2_p.a        | emx-lib       | em                  | emxsrcd[12]
\emx\lib\regexp.a       | regexp        | Henry Spencer       | emxsrcd[12]
\emx\lib\socket.a       | emx-lib       | em                  | emxsrcd[12]
\emx\lib\stdpp.a        | GPL+          | FSF                 | gppsrc
\emx\lib\termcap.a      | GPL           | FSF                 | gnusrc
\emx\lib\tmalloc.a      | emx-lib       | em                  | emxsrcd[12]
\emx\lib\video.a        | emx-lib       | em                  | emxsrcd[12]
\emx\lib\wrap.a         | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\mt\c.a         | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\mt\c_app.a     | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\mt\c_dllrt.a   | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\mt\c_dllso.lib | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\mt\c_import.a  | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\mt\emx.a       | emx-lib       | em                  | emxsrcd[12]
\emx\lib\mt\malloc1.a   | emx-lib       | em                  | emxsrcd[12]
\emx\lib\mt\objc.a      | GPL+          | FSF                 | gccsrc[123]
\emx\lib\mt\sys.lib     | emx-lib       | em                  | emxsrcd[12]
\emx\lib\st\c.a         | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\st\check.a     | GPL           | Richard W.M. Jones  | gccsrc[123]
\emx\lib\st\c_app.a     | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\st\c_app_p.a   | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\st\c_dllrt.a   | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\st\c_dllso.lib | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\st\c_import.a  | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\st\c_p.a       | emx-lib       | em and contributors | emxsrcd[12]
\emx\lib\st\emx.a       | emx-lib       | em                  | emxsrcd[12]
\emx\lib\st\malloc1.a   | emx-lib       | em                  | emxsrcd[12]
\emx\lib\st\objc.a      | GPL+          | FSF                 | gccsrc[123]
\emx\lib\st\sys.lib     | emx-lib       | em                  | emxsrcd[12]


Legend:

BSD     BSD license (see \emx\doc\COPYING.BSD)
em      Eberhard Mattes
emx-lib emx library, see above
FSF     Free Software Foundation, Inc
GPL     GNU General Public License (\emx\doc\COPYING)
GPL+    GPL with special exceptions
LGPL    GNU Library General Public License (\emx\doc\COPYING.LIB)
regexp  see \emx\src\regexp\COPYRIGH
UCB     University of California, Berkeley


------------------------- END OF COPYING.EMX -------------------------------

---------71e0e4991680cc6f71e0e4991680cc6f--

- Raw text -


  webmaster     delorie software   privacy  
  Copyright © 2019   by DJ Delorie     Updated Jul 2019