]> code.delx.au - gnu-emacs/blobdiff - src/termcap.c
* termcap.c: Integer and memory overflow issues.
[gnu-emacs] / src / termcap.c
index 5b71ad229d7e6166dd6eb1caf5423dce72fa9c71..791c593c06faa265ded8302c4c01646911bbeb49 100644 (file)
@@ -323,10 +323,10 @@ tputs (register const char *str, int nlines, int (*outfun) (int))
 struct termcap_buffer
   {
     char *beg;
-    int size;
+    ptrdiff_t size;
     char *ptr;
     int ateof;
-    int full;
+    ptrdiff_t full;
   };
 
 /* Forward declarations of static functions.  */
@@ -338,8 +338,7 @@ static int name_match (char *line, char *name);
 
 #ifdef MSDOS /* MW, May 1993 */
 static int
-valid_filename_p (fn)
-     char *fn;
+valid_filename_p (char *fn)
 {
   return *fn == '/' || fn[1] == ':';
 }
@@ -367,7 +366,7 @@ tgetent (char *bp, const char *name)
   register char *bp1;
   char *tc_search_point;
   char *term;
-  int malloc_size = 0;
+  ptrdiff_t malloc_size = 0;
   register int c;
   char *tcenv = NULL;          /* TERMCAP value, if it contains :tc=.  */
   char *indirect = NULL;       /* Terminal type in :tc= in TERMCAP value.  */
@@ -481,7 +480,7 @@ tgetent (char *bp, const char *name)
       /* If BP is malloc'd by us, make sure it is big enough.  */
       if (malloc_size)
        {
-         int offset1 = bp1 - bp, offset2 = tc_search_point - bp;
+         ptrdiff_t offset1 = bp1 - bp, offset2 = tc_search_point - bp;
          malloc_size = offset1 + buf.size;
          bp = termcap_name = (char *) xrealloc (bp, malloc_size);
          bp1 = termcap_name + offset1;
@@ -620,7 +619,6 @@ gobble_line (int fd, register struct termcap_buffer *bufp, char *append_end)
   register char *end;
   register int nread;
   register char *buf = bufp->beg;
-  register char *tem;
 
   if (!append_end)
     append_end = bufp->ptr;
@@ -637,12 +635,17 @@ gobble_line (int fd, register struct termcap_buffer *bufp, char *append_end)
        {
          if (bufp->full == bufp->size)
            {
-             bufp->size *= 2;
+             ptrdiff_t ptr_offset = bufp->ptr - buf;
+             ptrdiff_t append_end_offset = append_end - buf;
+             ptrdiff_t size;
+             if ((min (PTRDIFF_MAX, SIZE_MAX) - 1) / 2 < bufp->size)
+               memory_full (SIZE_MAX);
+             size = 2 * bufp->size;
              /* Add 1 to size to ensure room for terminating null.  */
-             tem = (char *) xrealloc (buf, bufp->size + 1);
-             bufp->ptr = (bufp->ptr - buf) + tem;
-             append_end = (append_end - buf) + tem;
-             bufp->beg = buf = tem;
+             bufp->beg = buf = (char *) xrealloc (buf, size + 1);
+             bufp->size = size;
+             bufp->ptr = buf + ptr_offset;
+             append_end = buf + append_end_offset;
            }
        }
       else
@@ -667,9 +670,29 @@ gobble_line (int fd, register struct termcap_buffer *bufp, char *append_end)
 
 #include <stdio.h>
 
-main (argc, argv)
-     int argc;
-     char **argv;
+static void
+tprint (char *cap)
+{
+  char *x = tgetstr (cap, 0);
+  register char *y;
+
+  printf ("%s: ", cap);
+  if (x)
+    {
+      for (y = x; *y; y++)
+       if (*y <= ' ' || *y == 0177)
+         printf ("\\%0o", *y);
+       else
+         putchar (*y);
+      free (x);
+    }
+  else
+    printf ("none");
+  putchar ('\n');
+}
+
+int
+main (int argc, char **argv)
 {
   char *term;
   char *buf;
@@ -691,28 +714,8 @@ main (argc, argv)
 
   printf ("co: %d\n", tgetnum ("co"));
   printf ("am: %d\n", tgetflag ("am"));
-}
-
-tprint (cap)
-     char *cap;
-{
-  char *x = tgetstr (cap, 0);
-  register char *y;
 
-  printf ("%s: ", cap);
-  if (x)
-    {
-      for (y = x; *y; y++)
-       if (*y <= ' ' || *y == 0177)
-         printf ("\\%0o", *y);
-       else
-         putchar (*y);
-      free (x);
-    }
-  else
-    printf ("none");
-  putchar ('\n');
+  return 0;
 }
 
 #endif /* TEST */
-