Mail Archives: cygwin/2005/11/07/21:57:10
--------------070000070704000008060702
Content-Type: text/plain; charset=ISO-8859-1; format=flowed
Content-Transfer-Encoding: 7bit
Christopher Faylor wrote:
> I have mixed feelings about alloca, personally. I use it all of the time but
> it is always with some trepidation because, AFAIK, the failure condition for
> alloca is a SEGV. OTOH, it is very convenient.
>
> In this case, however, I think you really want to use realloc. You could even
> rely on the fact that realloc(NULL, n) is equivalent to malloc(n).
Okay, revised patch attached if anybody cares to comment. But more
importantly, a test release (1.3.20a-2) should be up on the mirrors soon.
--
Chuck
--------------070000070704000008060702
Content-Type: text/plain;
name="alternatives-textmode-3.patch"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline;
filename="alternatives-textmode-3.patch"
diff -urN -x .build -x .inst -x .sinst -x .gmo -x .mo alternatives-1.3.20a-orig/alternatives.c alternatives-1.3.20a/alternatives.c
--- alternatives-1.3.20a-orig/alternatives.c 2005-06-25 21:55:02.000000000 -0400
+++ alternatives-1.3.20a/alternatives.c 2005-11-07 21:31:01.939142400 -0500
@@ -17,6 +17,23 @@
#define FLAGS_TEST (1 << 0)
#define FLAGS_VERBOSE (1 << 1)
+#if defined(O_BINARY)
+# define _O_BINARY O_BINARY
+# define FOPEN_WRITE_MODE "wb"
+# define FOPEN_READ_MODE "rb"
+#else
+# define _O_BINARY 0
+# define FOPEN_WRITE_MODE "w"
+# define FOPEN_READ_MODE "r"
+#endif
+
+#define PARANOID_FREE(stale) do { \
+ if (stale) { free ((void *) stale); stale = 0; } \
+} while (0)
+#define READCONFIG_BUF_INITIALSZ 16
+#define READCONFIG_BUF_BEHAVIOR_THRESH 4096
+
+
#define FL_TEST(flags) ((flags) & FLAGS_TEST)
#define FL_VERBOSE(flags) ((flags) & FLAGS_VERBOSE)
@@ -115,16 +132,30 @@
char * parseLine(char ** buf) {
char * start = *buf;
- char * end;
+ char * end1 = *buf;
+ char * end2;
if (!*buf || !**buf) return NULL;
- end = strchr(start, '\n');
- if (!end) {
- *buf = start + strlen(start);
- } else {
- *buf = end + 1;
- *end = '\0';
+ while (*end1 && (*end1 != '\n') && (*end1 != '\r'))
+ end1++;
+
+ end2 = end1;
+ while (*end2 && (*end2 == '\r')) /* only walk past '\r', NOT '\n' */
+ {
+ *end2 = '\0';
+ end2++;
+ }
+
+ /* ensures this parseLine() only consumes ONE '\n' */
+ if (*end2 == '\n')
+ {
+ *buf = end2 + 1;
+ *end2 = '\0';
+ }
+ else
+ {
+ *buf = end2;
}
while (isspace(*start) && *start) start++;
@@ -139,6 +170,7 @@
int i;
struct stat sb;
char * buf;
+ char * bufp;
char * end;
char * line;
struct {
@@ -147,6 +179,9 @@
} * groups = NULL;
int numGroups = 0;
char linkBuf[1024];
+ size_t curBufSz;
+ size_t totalBytesRead;
+ size_t numBytesRead;
set->alts = NULL;
set->numAlts = 0;
@@ -160,26 +195,50 @@
if (FL_VERBOSE(flags))
printf(_("reading %s\n"), path);
- if ((fd = open(path, O_RDONLY)) < 0) {
+ if ((fd = open(path, O_RDONLY | _O_BINARY)) < 0) {
if (errno == ENOENT) return 3;
fprintf(stderr, _("failed to open %s: %s\n"), path,
strerror(errno));
return 1;
}
- fstat(fd, &sb);
- buf = alloca(sb.st_size + 1);
- if (read(fd, buf, sb.st_size) != sb.st_size) {
- close(fd);
+ curBufSz = READCONFIG_BUF_INITIALSZ;
+ totalBytesRead = 0;
+ numBytesRead = 0;
+ buf = NULL;
+ do
+ {
+ if (curBufSz < READCONFIG_BUF_BEHAVIOR_THRESH)
+ curBufSz *= 2;
+ else
+ curBufSz += READCONFIG_BUF_BEHAVIOR_THRESH;
+
+ buf = realloc(buf, curBufSz + 1);
+
+ bufp = buf + totalBytesRead;
+ numBytesRead = read(fd, bufp, curBufSz - totalBytesRead);
+
+ /* don't add '-1' ! */
+ if (numBytesRead > 0)
+ totalBytesRead += numBytesRead;
+ }
+ while (numBytesRead > 0);
+
+ if (numBytesRead < 0)
+ {
+ close(fd);
+ PARANOID_FREE(buf);
fprintf(stderr, _("failed to read %s: %s\n"), path,
strerror(errno));
return 1;
}
close(fd);
- buf[sb.st_size] = '\0';
+ buf[curBufSz] = '\0';
+ bufp = buf;
- line = parseLine(&buf);
+ line = parseLine(&bufp);
if (!line) {
+ PARANOID_FREE(buf);
fprintf(stderr, _("%s empty!\n"), path);
return 1;
}
@@ -189,13 +248,15 @@
} else if (!strcmp(line, "manual")) {
set->mode = MANUAL;
} else {
+ PARANOID_FREE(buf);
fprintf(stderr, _("bad mode on line 1 of %s\n"), path);
return 1;
}
free(line);
- line = parseLine(&buf);
+ line = parseLine(&bufp);
if (!line || *line != '/') {
+ PARANOID_FREE(buf);
fprintf(stderr, _("bad primary link in %s\n"), path);
return 1;
}
@@ -205,9 +266,10 @@
groups[0].facility = line;
numGroups = 1;
- line = parseLine(&buf);
+ line = parseLine(&bufp);
while (line && *line) {
if (*line == '/') {
+ PARANOID_FREE(buf);
fprintf(stderr, _("path %s unexpected in %s\n"), line, path);
return 1;
}
@@ -215,27 +277,30 @@
groups = realloc(groups, sizeof(*groups) * (numGroups + 1));
groups[numGroups].title = line;
- line = parseLine(&buf);
+ line = parseLine(&bufp);
if (!line || !*line) {
+ PARANOID_FREE(buf);
fprintf(stderr, _("missing path for slave %s in %s\n"), line, path);
return 1;
}
groups[numGroups++].facility = line;
- line = parseLine(&buf);
+ line = parseLine(&bufp);
}
if (!line) {
+ PARANOID_FREE(buf);
fprintf(stderr, _("unexpected end of file in %s\n"), path);
return 1;
}
- line = parseLine(&buf);
+ line = parseLine(&bufp);
while (line && *line) {
set->alts = realloc(set->alts, (set->numAlts + 1) * sizeof(*set->alts));
if (*line != '/') {
+ PARANOID_FREE(buf);
fprintf(stderr, _("path to alternate expected in %s\n"), path);
return 1;
}
@@ -251,11 +316,12 @@
else
set->alts[set->numAlts].slaves = NULL;
- line = parseLine(&buf);
+ line = parseLine(&bufp);
set->alts[set->numAlts].priority = -1;
set->alts[set->numAlts].priority = strtol(line, &end, 0);
set->alts[set->numAlts].initscript = NULL;
if (!end || (end == line)) {
+ PARANOID_FREE(buf);
fprintf(stderr, _("numeric priority expected in %s\n"), path);
return 1;
}
@@ -276,8 +342,9 @@
set->best = set->numAlts;
for (i = 1; i < numGroups; i++) {
- line = parseLine(&buf);
+ line = parseLine(&bufp);
if (line && strlen(line) && *line != '/') {
+ PARANOID_FREE(buf);
fprintf(stderr, _("slave path expected in %s\n"), path);
return 1;
}
@@ -291,12 +358,13 @@
set->numAlts++;
- line = parseLine(&buf);
+ line = parseLine(&bufp);
}
while (line) {
- line = parseLine(&buf);
+ line = parseLine(&bufp);
if (line && *line) {
+ PARANOID_FREE(buf);
fprintf(stderr, _("unexpected line in %s: %s\n"), path, line);
return 1;
}
@@ -305,6 +373,7 @@
sprintf(path, "%s/%s", altDir, set->alts[0].master.title);
if (((i = readlink(path, linkBuf, sizeof(linkBuf) - 1)) < 0)) {
+ PARANOID_FREE(buf);
fprintf(stderr, _("failed to read link %s: %s\n"),
set->alts[0].master.facility, strerror(errno));
return 2;
@@ -331,6 +400,7 @@
set->currentLink = strdup(linkBuf);
+ PARANOID_FREE(buf);
return 0;
}
@@ -414,7 +484,7 @@
if (FL_TEST(flags))
fd = dup(1);
else
- fd = open(path, O_RDWR | O_CREAT | O_EXCL, 0644);
+ fd = open(path, O_RDWR | O_CREAT | O_EXCL | _O_BINARY, 0644);
if (fd < 0) {
if (errno == EEXIST)
@@ -425,7 +495,7 @@
return 1;
}
- f = fdopen(fd, "w");
+ f = fdopen(fd, FOPEN_WRITE_MODE);
fprintf(f, "%s\n", set->mode == AUTO ? "auto" : "manual");
fprintf(f, "%s\n", set->alts[0].master.facility);
for (i = 0; i < set->alts[0].numSlaves; i++) {
--------------070000070704000008060702
Content-Type: text/plain; charset=us-ascii
--
Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple
Problem reports: http://cygwin.com/problems.html
Documentation: http://cygwin.com/docs.html
FAQ: http://cygwin.com/faq/
--------------070000070704000008060702--
- Raw text -