aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorPaul Eggert2011-08-04 19:15:35 -0700
committerPaul Eggert2011-08-04 19:15:35 -0700
commit0065d05491ce5981ea20896bb26d21dcd31e6769 (patch)
tree13240167319d4a99ab5eacae4a883258eb2d28de /src
parent18ab493650d648ab8dca651ea2698861f926e895 (diff)
downloademacs-0065d05491ce5981ea20896bb26d21dcd31e6769.tar.gz
emacs-0065d05491ce5981ea20896bb26d21dcd31e6769.zip
Adjust in response to jan.h.d's comments.
See, for example <http://debbugs.gnu.org/cgi/bugreport.cgi?bug=9196#26>.
Diffstat (limited to 'src')
-rw-r--r--src/ChangeLog83
-rw-r--r--src/alloc.c88
-rw-r--r--src/bidi.c11
-rw-r--r--src/buffer.c64
-rw-r--r--src/callproc.c10
-rw-r--r--src/ccl.c40
-rw-r--r--src/character.c4
-rw-r--r--src/charset.c66
-rw-r--r--src/cmds.c2
-rw-r--r--src/composite.c39
-rw-r--r--src/composite.h2
-rw-r--r--src/dispextern.h5
-rw-r--r--src/dispnew.c99
-rw-r--r--src/doc.c12
-rw-r--r--src/emacs.c38
-rw-r--r--src/eval.c3
-rw-r--r--src/fns.c7
-rw-r--r--src/ftfont.c33
-rw-r--r--src/gtkutil.c8
-rw-r--r--src/image.c6
-rw-r--r--src/indent.c2
-rw-r--r--src/lisp.h20
-rw-r--r--src/minibuf.c5
-rw-r--r--src/nsterm.m16
-rw-r--r--src/process.c18
-rw-r--r--src/region-cache.c89
-rw-r--r--src/region-cache.h12
-rw-r--r--src/scroll.c15
-rw-r--r--src/search.c69
-rw-r--r--src/term.c43
-rw-r--r--src/termcap.c9
-rw-r--r--src/tparam.c17
-rw-r--r--src/xdisp.c13
-rw-r--r--src/xfaces.c31
-rw-r--r--src/xfns.c8
-rw-r--r--src/xgselect.c13
-rw-r--r--src/xrdb.c5
-rw-r--r--src/xselect.c24
-rw-r--r--src/xsmfns.c5
-rw-r--r--src/xterm.c41
40 files changed, 498 insertions, 577 deletions
diff --git a/src/ChangeLog b/src/ChangeLog
index a88e2e8e3cf..b525d83e288 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,7 +1,48 @@
12011-07-29 Paul Eggert <eggert@cs.ucla.edu> 12011-08-05 Paul Eggert <eggert@cs.ucla.edu>
2 2
3 Integer and memory overflow issues. 3 Integer and memory overflow issues.
4 4
5 * charset.c (charset_table_size)
6 (struct charset_sort_data.priority): Now ptrdiff_t.
7 (charset_compare): Don't overflow if priorities differ greatly.
8 (Fsort_charsets): Don't assume list length fits in int.
9 Check for size-calculation overflow when allocating sort data.
10 (syms_of_charset): Allocate an initial charset table that is
11 just under 64 KiB, to avoid problems with glibc malloc and mmap.
12
13 * cmds.c (internal_self_insert): Check for size-calculation overflow.
14
15 * composite.h (struct composition.glyph_len): Now int, not unsigned.
16 The actual value is always <= INT_MAX, and leaving it unsigned made
17 overflow checking harder.
18
19 * dispextern.h (struct glyph_matrix.rows_allocated)
20 (struct face_cache.size): Now ptrdiff_t, for convenience in use
21 with xpalloc. The values are still always <= INT_MAX.
22
23 * indent.c (compute_motion): Adjust to region_cache_forward sig change.
24
25 * lisp.h (xnmalloc, xnrealloc, xpalloc): New decls.
26 (SAFE_NALLOCA): New macro.
27
28 * region-cache.c (struct boundary.pos, find_cache_boundary)
29 (move_cache_gap, insert_cache_boundary, delete_cache_boundaries)
30 (set_cache_region, invalidate_region_cache)
31 (revalidate_region_cache, know_region_cache, region_cache_forward)
32 (region_cache_backward, pp_cache):
33 Use ptrdiff_t, not EMACS_INT, since either will do. This is needed
34 so that ptrdiff_t * can be passed to xpalloc.
35 (struct region_cache): Similarly, for gap_start, gap_len, cache_len,
36 beg_unchanged, end_unchanged, buffer_beg, buffer_end members.
37 (pp_cache): Don't assume cache_len fits in int.
38 * region-cache.h: Adjust extern decls to match.
39
40 * search.c (scan_buffer, Freplace_match): Use ptrdiff_t, not
41 EMACS_INT, since either will do, for xpalloc.
42
43 * alloc.c: Include verify.h, and check that int fits in ptrdiff_t.
44 (xnmalloc, xnrealloc, xpalloc): New functions.
45
5 * bidi.c (bidi_shelve_header_size): New constant. 46 * bidi.c (bidi_shelve_header_size): New constant.
6 (bidi_cache_ensure_space, bidi_shelve_cache): Use it. 47 (bidi_cache_ensure_space, bidi_shelve_cache): Use it.
7 (bidi_cache_ensure_space): Avoid integer overflow when allocating. 48 (bidi_cache_ensure_space): Avoid integer overflow when allocating.
@@ -10,12 +51,21 @@
10 (overlay_strings): 51 (overlay_strings):
11 Don't update size of array until after memory allocation succeeds, 52 Don't update size of array until after memory allocation succeeds,
12 because xmalloc/xrealloc may not return. 53 because xmalloc/xrealloc may not return.
54 (struct sortstrlist.bytes): Now ptrdiff_t, as EMACS_INT doesn't help
55 now that we have proper integer overflow checking.
56 (record_overlay_string, overlay_strings): Catch overflows when
57 calculating size of overlay_str_buf.
13 58
14 * callproc.c (child_setup): Don't assume strlen fits in int. 59 * callproc.c (Fcall_process): Check for size overflow when
60 calculating size of args2.
61 (child_setup): Avoid overflow by using size_t rather than ptrdiff_t.
62 Normally we prefer signed values, but sticking with ptrdiff_t would
63 require adding more-complicated checks.
15 64
16 * ccl.c (Fccl_execute_on_string): Check for memory overflow. 65 * ccl.c (Fccl_execute_on_string): Check for memory overflow.
17 Use ptrdiff_t rather than EMACS_INT where ptrdiff_t will do. 66 Use ptrdiff_t rather than EMACS_INT where ptrdiff_t will do.
18 Redo buffer-overflow calculations to avoid integer overflow. 67 Redo buffer-overflow calculations to avoid integer overflow.
68 Add a FIXME comment where memory seems to be over-allocated.
19 69
20 * character.c (Fstring): Check for size-calculation overflow. 70 * character.c (Fstring): Check for size-calculation overflow.
21 71
@@ -55,7 +105,10 @@
55 Don't assume message length fits in int. 105 Don't assume message length fits in int.
56 (Fformat): Use ptrdiff_t, not EMACS_INT, where ptrdiff_t will do. 106 (Fformat): Use ptrdiff_t, not EMACS_INT, where ptrdiff_t will do.
57 107
58 * emacs.c (main, sort_args): Check for size-calculation overflow. 108 * emacs.c (main): Do not reallocate argv, since there is a null at
109 the end that can be overwritten, and this way there's no need to
110 worry about size-calculation overflow.
111 (sort_args): Check for size-calculation overflow.
59 112
60 * eval.c (init_eval_once, grow_specpdl): Don't update size until 113 * eval.c (init_eval_once, grow_specpdl): Don't update size until
61 alloc succeeds. 114 alloc succeeds.
@@ -119,9 +172,6 @@
119 * macros.c (Fstart_kbd_macro): Don't update size until alloc done. 172 * macros.c (Fstart_kbd_macro): Don't update size until alloc done.
120 (store_kbd_macro_char): Reorder multiplicands to avoid overflow. 173 (store_kbd_macro_char): Reorder multiplicands to avoid overflow.
121 174
122 * minibuf.c (read_minibuf_noninteractive): Don't leak memory
123 on memory overflow.
124
125 * nsterm.h (struct ns_color_table.size, struct ns_color_table.avail): 175 * nsterm.h (struct ns_color_table.size, struct ns_color_table.avail):
126 Now ptrdiff_t, not int. 176 Now ptrdiff_t, not int.
127 * nsterm.m (ns_index_color): Use ptrdiff_t, not int, for table indexes. 177 * nsterm.m (ns_index_color): Use ptrdiff_t, not int, for table indexes.
@@ -161,25 +211,29 @@
161 Don't update size until alloc done. 211 Don't update size until alloc done.
162 Redo size calculations to avoid overflow. 212 Redo size calculations to avoid overflow.
163 Check for size calculation overflow. 213 Check for size calculation overflow.
214 (main) [DEBUG]: Fix typo in invoking tparam1.
164 215
165 * xdisp.c (store_mode_line_noprop_char, x_consider_frame_title): 216 * xdisp.c (store_mode_line_noprop_char, x_consider_frame_title):
166 Use ptrdiff_t, not int, for sizes. 217 Use ptrdiff_t, not int, for sizes.
167 (store_mode_line_noprop_char): Don't update size until alloc done. 218 (store_mode_line_noprop_char): Don't update size until alloc done.
168 219
169 * xfaces.c (Finternal_make_lisp_face): Use ptrdiff_t, not int, for 220 * xfaces.c (lface_id_to_name_size, Finternal_make_lisp_face):
170 sizes. Check for size calculation overflow. 221 Use ptrdiff_t, not int, for sizes.
171 (cache_face): Do not overflow in size calculation. 222 (Finternal_make_lisp_face, cache_face):
223 Check for size calculation overflow.
224 (cache_face): Treat size calculation overflows as if they were
225 memory exhaustion (the usual treatment), rather than aborting.
172 226
173 * xfns.c (x_encode_text, x_set_name_internal) 227 * xfns.c (x_encode_text, x_set_name_internal)
174 (Fx_change_window_property): Use ptrdiff_t, not int, to count 228 (Fx_change_window_property): Use ptrdiff_t, not int, to count
175 sizes, since they can exceed INT_MAX in size. Check for size 229 sizes, since they can exceed INT_MAX in size. Check for size
176 calculation overflow. 230 calculation overflow.
177 231
178 * xgselect.c (xg_select): Check for size calculation overflow. 232 * xgselect.c (gfds_size): Now ptrdiff_t, for convenience with xpalloc.
233 (xg_select): Check for size calculation overflow.
179 Don't update size until alloc done. 234 Don't update size until alloc done.
180 235
181 * xrdb.c (magic_file_p): Plug memory leak on size overflow. 236 * xrdb.c (get_environ_db): Don't assume path length fits in int,
182 (get_environ_db): Don't assume path length fits in int,
183 as sprintf is limited to int lengths. 237 as sprintf is limited to int lengths.
184 238
185 * xselect.c (X_LONG_SIZE, X_USHRT_MAX, X_ULONG_MAX): New macros. 239 * xselect.c (X_LONG_SIZE, X_USHRT_MAX, X_ULONG_MAX): New macros.
@@ -229,10 +283,11 @@
229 283
230 * xsmfns.c (smc_save_yourself_CB): Check for size calc overflow. 284 * xsmfns.c (smc_save_yourself_CB): Check for size calc overflow.
231 285
232 * xterm.c (x_color_cells, handle_one_xevent, x_term_init): 286 * xterm.c (x_color_cells, x_send_scrollbar_event, handle_one_xevent)
233 Check for size calculation overflow. 287 (x_term_init): Check for size calculation overflow.
234 (x_color_cells): Don't store size until memory allocation succeeds. 288 (x_color_cells): Don't store size until memory allocation succeeds.
235 (handle_one_xevent): Use ptrdiff_t, not int, for byte counts. 289 (handle_one_xevent): Use ptrdiff_t, not int, for byte counts.
290 Don't assume alloca size is less than MAX_ALLOCA.
236 (x_term_init): Don't assume length fits in int (sprintf is limited 291 (x_term_init): Don't assume length fits in int (sprintf is limited
237 to int size). 292 to int size).
238 293
diff --git a/src/alloc.c b/src/alloc.c
index b96fc1f0642..a1af0df11f0 100644
--- a/src/alloc.c
+++ b/src/alloc.c
@@ -46,6 +46,7 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
46#include "syssignal.h" 46#include "syssignal.h"
47#include "termhooks.h" /* For struct terminal. */ 47#include "termhooks.h" /* For struct terminal. */
48#include <setjmp.h> 48#include <setjmp.h>
49#include <verify.h>
49 50
50/* GC_MALLOC_CHECK defined means perform validity checks of malloc'd 51/* GC_MALLOC_CHECK defined means perform validity checks of malloc'd
51 memory. Can do this only if using gmalloc.c. */ 52 memory. Can do this only if using gmalloc.c. */
@@ -731,6 +732,93 @@ xfree (POINTER_TYPE *block)
731} 732}
732 733
733 734
735/* Other parts of Emacs pass large int values to allocator functions
736 expecting ptrdiff_t. This is portable in practice, but check it to
737 be safe. */
738verify (INT_MAX <= PTRDIFF_MAX);
739
740
741/* Allocate an array of NITEMS items, each of size ITEM_SIZE.
742 Signal an error on memory exhaustion, and block interrupt input. */
743
744void *
745xnmalloc (ptrdiff_t nitems, ptrdiff_t item_size)
746{
747 xassert (0 <= nitems && 0 < item_size);
748 if (min (PTRDIFF_MAX, SIZE_MAX) / item_size < nitems)
749 memory_full (SIZE_MAX);
750 return xmalloc (nitems * item_size);
751}
752
753
754/* Reallocate an array PA to make it of NITEMS items, each of size ITEM_SIZE.
755 Signal an error on memory exhaustion, and block interrupt input. */
756
757void *
758xnrealloc (void *pa, ptrdiff_t nitems, ptrdiff_t item_size)
759{
760 xassert (0 <= nitems && 0 < item_size);
761 if (min (PTRDIFF_MAX, SIZE_MAX) / item_size < nitems)
762 memory_full (SIZE_MAX);
763 return xrealloc (pa, nitems * item_size);
764}
765
766
767/* Grow PA, which points to an array of *NITEMS items, and return the
768 location of the reallocated array, updating *NITEMS to reflect its
769 new size. The new array will contain at least NITEMS_INCR_MIN more
770 items, but will not contain more than NITEMS_MAX items total.
771 ITEM_SIZE is the size of each item, in bytes.
772
773 ITEM_SIZE and NITEMS_INCR_MIN must be positive. *NITEMS must be
774 nonnegative. If NITEMS_MAX is -1, it is treated as if it were
775 infinity.
776
777 If PA is null, then allocate a new array instead of reallocating
778 the old one. Thus, to grow an array A without saving its old
779 contents, invoke xfree (A) immediately followed by xgrowalloc (0,
780 &NITEMS, ...).
781
782 Block interrupt input as needed. If memory exhaustion occurs, set
783 *NITEMS to zero if PA is null, and signal an error (i.e., do not
784 return). */
785
786void *
787xpalloc (void *pa, ptrdiff_t *nitems, ptrdiff_t nitems_incr_min,
788 ptrdiff_t nitems_max, ptrdiff_t item_size)
789{
790 /* The approximate size to use for initial small allocation
791 requests. This is the largest "small" request for the GNU C
792 library malloc. */
793 enum { DEFAULT_MXFAST = 64 * sizeof (size_t) / 4 };
794
795 /* If the array is tiny, grow it to about (but no greater than)
796 DEFAULT_MXFAST bytes. Otherwise, grow it by about 50%. */
797 ptrdiff_t n = *nitems;
798 ptrdiff_t tiny_max = DEFAULT_MXFAST / item_size - n;
799 ptrdiff_t half_again = n >> 1;
800 ptrdiff_t incr_estimate = max (tiny_max, half_again);
801
802 /* Adjust the increment according to three constraints: NITEMS_INCR_MIN,
803 NITEMS_MAX, and what the C language can represent safely. */
804 ptrdiff_t C_language_max = min (PTRDIFF_MAX, SIZE_MAX) / item_size;
805 ptrdiff_t n_max = (0 <= nitems_max && nitems_max < C_language_max
806 ? nitems_max : C_language_max);
807 ptrdiff_t nitems_incr_max = n_max - n;
808 ptrdiff_t incr = max (nitems_incr_min, min (incr_estimate, nitems_incr_max));
809
810 xassert (0 < item_size && 0 < nitems_incr_min && 0 <= n && -1 <= nitems_max);
811 if (! pa)
812 *nitems = 0;
813 if (nitems_incr_max < incr)
814 memory_full (SIZE_MAX);
815 n += incr;
816 pa = xrealloc (pa, n * item_size);
817 *nitems = n;
818 return pa;
819}
820
821
734/* Like strdup, but uses xmalloc. */ 822/* Like strdup, but uses xmalloc. */
735 823
736char * 824char *
diff --git a/src/bidi.c b/src/bidi.c
index a1e5721f350..27a6645dffd 100644
--- a/src/bidi.c
+++ b/src/bidi.c
@@ -478,8 +478,6 @@ bidi_cache_ensure_space (ptrdiff_t idx)
478 /* Enlarge the cache as needed. */ 478 /* Enlarge the cache as needed. */
479 if (idx >= bidi_cache_size) 479 if (idx >= bidi_cache_size)
480 { 480 {
481 ptrdiff_t new_size;
482
483 /* The bidi cache cannot be larger than the largest Lisp string 481 /* The bidi cache cannot be larger than the largest Lisp string
484 or buffer. */ 482 or buffer. */
485 ptrdiff_t string_or_buffer_bound = 483 ptrdiff_t string_or_buffer_bound =
@@ -489,11 +487,10 @@ bidi_cache_ensure_space (ptrdiff_t idx)
489 ptrdiff_t c_bound = 487 ptrdiff_t c_bound =
490 (min (PTRDIFF_MAX, SIZE_MAX) - bidi_shelve_header_size) / elsz; 488 (min (PTRDIFF_MAX, SIZE_MAX) - bidi_shelve_header_size) / elsz;
491 489
492 if (min (string_or_buffer_bound, c_bound) <= idx) 490 bidi_cache =
493 memory_full (SIZE_MAX); 491 xpalloc (bidi_cache, &bidi_cache_size,
494 new_size = idx - idx % BIDI_CACHE_CHUNK + BIDI_CACHE_CHUNK; 492 max (BIDI_CACHE_CHUNK, idx - bidi_cache_size + 1),
495 bidi_cache = (struct bidi_it *) xrealloc (bidi_cache, new_size * elsz); 493 min (string_or_buffer_bound, c_bound), elsz);
496 bidi_cache_size = new_size;
497 } 494 }
498} 495}
499 496
diff --git a/src/buffer.c b/src/buffer.c
index cacc8a41339..b61d083c3e6 100644
--- a/src/buffer.c
+++ b/src/buffer.c
@@ -2568,13 +2568,10 @@ overlays_at (EMACS_INT pos, int extend, Lisp_Object **vec_ptr,
2568 Either make it bigger, or don't store any more in it. */ 2568 Either make it bigger, or don't store any more in it. */
2569 if (extend) 2569 if (extend)
2570 { 2570 {
2571 if ((OVERLAY_COUNT_MAX - 4) / 2 < len) 2571 vec = xpalloc (vec, len_ptr, 1, OVERLAY_COUNT_MAX,
2572 memory_full (SIZE_MAX); 2572 sizeof *vec);
2573 /* Make it work with an initial len == 0. */
2574 len = len * 2 + 4;
2575 vec = (Lisp_Object *) xrealloc (vec, len * sizeof (Lisp_Object));
2576 *vec_ptr = vec; 2573 *vec_ptr = vec;
2577 *len_ptr = len; 2574 len = *len_ptr;
2578 } 2575 }
2579 else 2576 else
2580 inhibit_storing = 1; 2577 inhibit_storing = 1;
@@ -2611,13 +2608,10 @@ overlays_at (EMACS_INT pos, int extend, Lisp_Object **vec_ptr,
2611 { 2608 {
2612 if (extend) 2609 if (extend)
2613 { 2610 {
2614 if ((OVERLAY_COUNT_MAX - 4) / 2 < len) 2611 vec = xpalloc (vec, len_ptr, 1, OVERLAY_COUNT_MAX,
2615 memory_full (SIZE_MAX); 2612 sizeof *vec);
2616 /* Make it work with an initial len == 0. */
2617 len = len * 2 + 4;
2618 vec = (Lisp_Object *) xrealloc (vec, len * sizeof (Lisp_Object));
2619 *vec_ptr = vec; 2613 *vec_ptr = vec;
2620 *len_ptr = len; 2614 len = *len_ptr;
2621 } 2615 }
2622 else 2616 else
2623 inhibit_storing = 1; 2617 inhibit_storing = 1;
@@ -2708,13 +2702,10 @@ overlays_in (EMACS_INT beg, EMACS_INT end, int extend,
2708 Either make it bigger, or don't store any more in it. */ 2702 Either make it bigger, or don't store any more in it. */
2709 if (extend) 2703 if (extend)
2710 { 2704 {
2711 if ((OVERLAY_COUNT_MAX - 4) / 2 < len) 2705 vec = xpalloc (vec, len_ptr, 1, OVERLAY_COUNT_MAX,
2712 memory_full (SIZE_MAX); 2706 sizeof *vec);
2713 /* Make it work with an initial len == 0. */
2714 len = len * 2 + 4;
2715 vec = (Lisp_Object *) xrealloc (vec, len * sizeof (Lisp_Object));
2716 *vec_ptr = vec; 2707 *vec_ptr = vec;
2717 *len_ptr = len; 2708 len = *len_ptr;
2718 } 2709 }
2719 else 2710 else
2720 inhibit_storing = 1; 2711 inhibit_storing = 1;
@@ -2756,13 +2747,10 @@ overlays_in (EMACS_INT beg, EMACS_INT end, int extend,
2756 { 2747 {
2757 if (extend) 2748 if (extend)
2758 { 2749 {
2759 if ((OVERLAY_COUNT_MAX - 4) / 2 < len) 2750 vec = xpalloc (vec, len_ptr, 1, OVERLAY_COUNT_MAX,
2760 memory_full (SIZE_MAX); 2751 sizeof *vec);
2761 /* Make it work with an initial len == 0. */
2762 len = len * 2 + 4;
2763 vec = (Lisp_Object *) xrealloc (vec, len * sizeof (Lisp_Object));
2764 *vec_ptr = vec; 2752 *vec_ptr = vec;
2765 *len_ptr = len; 2753 len = *len_ptr;
2766 } 2754 }
2767 else 2755 else
2768 inhibit_storing = 1; 2756 inhibit_storing = 1;
@@ -2944,7 +2932,7 @@ struct sortstrlist
2944 struct sortstr *buf; /* An array that expands as needed; never freed. */ 2932 struct sortstr *buf; /* An array that expands as needed; never freed. */
2945 ptrdiff_t size; /* Allocated length of that array. */ 2933 ptrdiff_t size; /* Allocated length of that array. */
2946 ptrdiff_t used; /* How much of the array is currently in use. */ 2934 ptrdiff_t used; /* How much of the array is currently in use. */
2947 EMACS_INT bytes; /* Total length of the strings in buf. */ 2935 ptrdiff_t bytes; /* Total length of the strings in buf. */
2948}; 2936};
2949 2937
2950/* Buffers for storing information about the overlays touching a given 2938/* Buffers for storing information about the overlays touching a given
@@ -2977,14 +2965,7 @@ record_overlay_string (struct sortstrlist *ssl, Lisp_Object str,
2977 EMACS_INT nbytes; 2965 EMACS_INT nbytes;
2978 2966
2979 if (ssl->used == ssl->size) 2967 if (ssl->used == ssl->size)
2980 { 2968 ssl->buf = xpalloc (ssl->buf, &ssl->size, 5, -1, sizeof *ssl->buf);
2981 ptrdiff_t ssl_size = 0 < ssl->size ? ssl->size * 2 : 5;
2982 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (struct sortstr) < ssl_size)
2983 memory_full (SIZE_MAX);
2984 ssl->buf = ((struct sortstr *)
2985 xrealloc (ssl->buf, ssl_size * sizeof (struct sortstr)));
2986 ssl->size = ssl_size;
2987 }
2988 ssl->buf[ssl->used].string = str; 2969 ssl->buf[ssl->used].string = str;
2989 ssl->buf[ssl->used].string2 = str2; 2970 ssl->buf[ssl->used].string2 = str2;
2990 ssl->buf[ssl->used].size = size; 2971 ssl->buf[ssl->used].size = size;
@@ -2999,6 +2980,8 @@ record_overlay_string (struct sortstrlist *ssl, Lisp_Object str,
2999 else 2980 else
3000 nbytes = SBYTES (str); 2981 nbytes = SBYTES (str);
3001 2982
2983 if (INT_ADD_OVERFLOW (ssl->bytes, nbytes))
2984 memory_full (SIZE_MAX);
3002 ssl->bytes += nbytes; 2985 ssl->bytes += nbytes;
3003 2986
3004 if (STRINGP (str2)) 2987 if (STRINGP (str2))
@@ -3011,6 +2994,8 @@ record_overlay_string (struct sortstrlist *ssl, Lisp_Object str,
3011 else 2994 else
3012 nbytes = SBYTES (str2); 2995 nbytes = SBYTES (str2);
3013 2996
2997 if (INT_ADD_OVERFLOW (ssl->bytes, nbytes))
2998 memory_full (SIZE_MAX);
3014 ssl->bytes += nbytes; 2999 ssl->bytes += nbytes;
3015 } 3000 }
3016} 3001}
@@ -3104,14 +3089,15 @@ overlay_strings (EMACS_INT pos, struct window *w, unsigned char **pstr)
3104 Lisp_Object tem; 3089 Lisp_Object tem;
3105 EMACS_INT i; 3090 EMACS_INT i;
3106 unsigned char *p; 3091 unsigned char *p;
3107 EMACS_INT total = overlay_heads.bytes + overlay_tails.bytes; 3092 ptrdiff_t total;
3108 3093
3094 if (INT_ADD_OVERFLOW (overlay_heads.bytes, overlay_tails.bytes))
3095 memory_full (SIZE_MAX);
3096 total = overlay_heads.bytes + overlay_tails.bytes;
3109 if (total > overlay_str_len) 3097 if (total > overlay_str_len)
3110 { 3098 overlay_str_buf = xpalloc (overlay_str_buf, &overlay_str_len,
3111 overlay_str_buf = (unsigned char *)xrealloc (overlay_str_buf, 3099 total - overlay_str_len, -1, 1);
3112 total); 3100
3113 overlay_str_len = total;
3114 }
3115 p = overlay_str_buf; 3101 p = overlay_str_buf;
3116 for (i = overlay_tails.used; --i >= 0;) 3102 for (i = overlay_tails.used; --i >= 0;)
3117 { 3103 {
diff --git a/src/callproc.c b/src/callproc.c
index 993d943e158..4f6d363d5e2 100644
--- a/src/callproc.c
+++ b/src/callproc.c
@@ -252,7 +252,7 @@ usage: (call-process PROGRAM &optional INFILE BUFFER DISPLAY &rest ARGS) */)
252 val = Qraw_text; 252 val = Qraw_text;
253 else 253 else
254 { 254 {
255 SAFE_ALLOCA (args2, Lisp_Object *, (nargs + 1) * sizeof *args2); 255 SAFE_NALLOCA (args2, 1, nargs + 1);
256 args2[0] = Qcall_process; 256 args2[0] = Qcall_process;
257 for (i = 0; i < nargs; i++) args2[i + 1] = args[i]; 257 for (i = 0; i < nargs; i++) args2[i + 1] = args[i];
258 coding_systems = Ffind_operation_coding_system (nargs + 1, args2); 258 coding_systems = Ffind_operation_coding_system (nargs + 1, args2);
@@ -720,7 +720,7 @@ usage: (call-process PROGRAM &optional INFILE BUFFER DISPLAY &rest ARGS) */)
720 { 720 {
721 ptrdiff_t i; 721 ptrdiff_t i;
722 722
723 SAFE_ALLOCA (args2, Lisp_Object *, (nargs + 1) * sizeof *args2); 723 SAFE_NALLOCA (args2, 1, nargs + 1);
724 args2[0] = Qcall_process; 724 args2[0] = Qcall_process;
725 for (i = 0; i < nargs; i++) args2[i + 1] = args[i]; 725 for (i = 0; i < nargs; i++) args2[i + 1] = args[i];
726 coding_systems 726 coding_systems
@@ -1018,7 +1018,7 @@ usage: (call-process-region START END PROGRAM &optional DELETE BUFFER DISPLAY &r
1018 else 1018 else
1019 { 1019 {
1020 USE_SAFE_ALLOCA; 1020 USE_SAFE_ALLOCA;
1021 SAFE_ALLOCA (args2, Lisp_Object *, (nargs + 1) * sizeof *args2); 1021 SAFE_NALLOCA (args2, 1, nargs + 1);
1022 args2[0] = Qcall_process_region; 1022 args2[0] = Qcall_process_region;
1023 for (i = 0; i < nargs; i++) args2[i + 1] = args[i]; 1023 for (i = 0; i < nargs; i++) args2[i + 1] = args[i];
1024 coding_systems = Ffind_operation_coding_system (nargs + 1, args2); 1024 coding_systems = Ffind_operation_coding_system (nargs + 1, args2);
@@ -1147,11 +1147,9 @@ child_setup (int in, int out, int err, register char **new_argv, int set_pgrp, L
1147 cleaned up in the usual way. */ 1147 cleaned up in the usual way. */
1148 { 1148 {
1149 register char *temp; 1149 register char *temp;
1150 register ptrdiff_t i; 1150 size_t i; /* size_t, because ptrdiff_t might overflow here! */
1151 1151
1152 i = SBYTES (current_dir); 1152 i = SBYTES (current_dir);
1153 if (min (PTRDIFF_MAX, SIZE_MAX) - 6 < i)
1154 memory_full (SIZE_MAX);
1155#ifdef MSDOS 1153#ifdef MSDOS
1156 /* MSDOS must have all environment variables malloc'ed, because 1154 /* MSDOS must have all environment variables malloc'ed, because
1157 low-level libc functions that launch subsidiary processes rely 1155 low-level libc functions that launch subsidiary processes rely
diff --git a/src/ccl.c b/src/ccl.c
index 0a9b3d90708..dc0adae6877 100644
--- a/src/ccl.c
+++ b/src/ccl.c
@@ -2067,6 +2067,7 @@ usage: (ccl-execute-on-string CCL-PROGRAM STATUS STRING &optional CONTINUE UNIBY
2067#define CCL_EXECUTE_BUF_SIZE 1024 2067#define CCL_EXECUTE_BUF_SIZE 1024
2068 int source[CCL_EXECUTE_BUF_SIZE], destination[CCL_EXECUTE_BUF_SIZE]; 2068 int source[CCL_EXECUTE_BUF_SIZE], destination[CCL_EXECUTE_BUF_SIZE];
2069 ptrdiff_t consumed_chars, consumed_bytes, produced_chars; 2069 ptrdiff_t consumed_chars, consumed_bytes, produced_chars;
2070 int buf_magnification;
2070 2071
2071 if (setup_ccl_program (&ccl, ccl_prog) < 0) 2072 if (setup_ccl_program (&ccl, ccl_prog) < 0)
2072 error ("Invalid CCL program"); 2073 error ("Invalid CCL program");
@@ -2093,9 +2094,9 @@ usage: (ccl-execute-on-string CCL-PROGRAM STATUS STRING &optional CONTINUE UNIBY
2093 ccl.ic = i; 2094 ccl.ic = i;
2094 } 2095 }
2095 2096
2096 if (((min (PTRDIFF_MAX, SIZE_MAX) - 256) 2097 buf_magnification = ccl.buf_magnification ? ccl.buf_magnification : 1;
2097 / (ccl.buf_magnification ? ccl.buf_magnification : 1)) 2098
2098 < str_bytes) 2099 if ((min (PTRDIFF_MAX, SIZE_MAX) - 256) / buf_magnification < str_bytes)
2099 memory_full (SIZE_MAX); 2100 memory_full (SIZE_MAX);
2100 outbufsize = (ccl.buf_magnification 2101 outbufsize = (ccl.buf_magnification
2101 ? str_bytes * ccl.buf_magnification + 256 2102 ? str_bytes * ccl.buf_magnification + 256
@@ -2131,20 +2132,18 @@ usage: (ccl-execute-on-string CCL-PROGRAM STATUS STRING &optional CONTINUE UNIBY
2131 produced_chars += ccl.produced; 2132 produced_chars += ccl.produced;
2132 if (NILP (unibyte_p)) 2133 if (NILP (unibyte_p))
2133 { 2134 {
2135 /* FIXME: Surely this should be buf_magnification instead.
2136 MAX_MULTIBYTE_LENGTH overestimates the storage needed. */
2137 int magnification = MAX_MULTIBYTE_LENGTH;
2138
2134 ptrdiff_t offset = outp - outbuf; 2139 ptrdiff_t offset = outp - outbuf;
2135 if ((outbufsize - offset) / MAX_MULTIBYTE_LENGTH < ccl.produced) 2140 ptrdiff_t shortfall;
2141 if (INT_MULTIPLY_OVERFLOW (ccl.produced, magnification))
2142 memory_full (SIZE_MAX);
2143 shortfall = ccl.produced * magnification - (outbufsize - offset);
2144 if (0 < shortfall)
2136 { 2145 {
2137 ptrdiff_t produced; 2146 outbuf = xpalloc (outbuf, &outbufsize, shortfall, -1, 1);
2138 if (((min (PTRDIFF_MAX, SIZE_MAX) - outbufsize)
2139 / MAX_MULTIBYTE_LENGTH)
2140 < ccl.produced)
2141 {
2142 xfree (outbuf);
2143 memory_full (SIZE_MAX);
2144 }
2145 produced = ccl.produced;
2146 outbufsize += MAX_MULTIBYTE_LENGTH * produced;
2147 outbuf = (unsigned char *) xrealloc (outbuf, outbufsize);
2148 outp = outbuf + offset; 2147 outp = outbuf + offset;
2149 } 2148 }
2150 for (j = 0; j < ccl.produced; j++) 2149 for (j = 0; j < ccl.produced; j++)
@@ -2153,15 +2152,10 @@ usage: (ccl-execute-on-string CCL-PROGRAM STATUS STRING &optional CONTINUE UNIBY
2153 else 2152 else
2154 { 2153 {
2155 ptrdiff_t offset = outp - outbuf; 2154 ptrdiff_t offset = outp - outbuf;
2156 if (outbufsize - offset < ccl.produced) 2155 ptrdiff_t shortfall = ccl.produced - (outbufsize - offset);
2156 if (0 < shortfall)
2157 { 2157 {
2158 if (min (PTRDIFF_MAX, SIZE_MAX) - outbufsize < ccl.produced) 2158 outbuf = xpalloc (outbuf, &outbufsize, shortfall, -1, 1);
2159 {
2160 xfree (outbuf);
2161 memory_full (SIZE_MAX);
2162 }
2163 outbufsize += ccl.produced;
2164 outbuf = (unsigned char *) xrealloc (outbuf, outbufsize);
2165 outp = outbuf + offset; 2159 outp = outbuf + offset;
2166 } 2160 }
2167 for (j = 0; j < ccl.produced; j++) 2161 for (j = 0; j < ccl.produced; j++)
diff --git a/src/character.c b/src/character.c
index 50b5b252871..fb9b8a9b93e 100644
--- a/src/character.c
+++ b/src/character.c
@@ -902,9 +902,7 @@ usage: (string &rest CHARACTERS) */)
902 Lisp_Object str; 902 Lisp_Object str;
903 USE_SAFE_ALLOCA; 903 USE_SAFE_ALLOCA;
904 904
905 if (min (PTRDIFF_MAX, SIZE_MAX) / MAX_MULTIBYTE_LENGTH < n) 905 SAFE_NALLOCA (buf, MAX_MULTIBYTE_LENGTH, n);
906 memory_full (SIZE_MAX);
907 SAFE_ALLOCA (buf, unsigned char *, MAX_MULTIBYTE_LENGTH * n);
908 p = buf; 906 p = buf;
909 907
910 for (i = 0; i < n; i++) 908 for (i = 0; i < n; i++)
diff --git a/src/charset.c b/src/charset.c
index 852aeb19bcb..6967b9df611 100644
--- a/src/charset.c
+++ b/src/charset.c
@@ -61,7 +61,7 @@ Lisp_Object Vcharset_hash_table;
61/* Table of struct charset. */ 61/* Table of struct charset. */
62struct charset *charset_table; 62struct charset *charset_table;
63 63
64static int charset_table_size; 64static ptrdiff_t charset_table_size;
65static int charset_table_used; 65static int charset_table_used;
66 66
67Lisp_Object Qcharsetp; 67Lisp_Object Qcharsetp;
@@ -1150,28 +1150,25 @@ usage: (define-charset-internal ...) */)
1150 hash_code); 1150 hash_code);
1151 if (charset_table_used == charset_table_size) 1151 if (charset_table_used == charset_table_size)
1152 { 1152 {
1153 struct charset *new_table;
1154 /* Ensure that charset IDs fit into 'int' as well as into the 1153 /* Ensure that charset IDs fit into 'int' as well as into the
1155 restriction imposed by fixnums, ptrdiff_t, and size_t. 1154 restriction imposed by fixnums. Although the 'int' restriction
1156 Although the 'int' restriction could be removed, too much other 1155 could be removed, too much other code would need altering; for
1157 code would need altering; for example, the IDs are stuffed into 1156 example, the IDs are stuffed into struct
1158 struct coding_system.charbuf[i] entries, which are 'int'. */ 1157 coding_system.charbuf[i] entries, which are 'int'. */
1159 int charset_table_size_max = 1158 int old_size = charset_table_size;
1160 min (min (INT_MAX, MOST_POSITIVE_FIXNUM), 1159 struct charset *new_table =
1161 min (PTRDIFF_MAX, SIZE_MAX) / sizeof (struct charset)); 1160 xpalloc (0, &charset_table_size, 1,
1162 if (charset_table_size_max - 16 < charset_table_size) 1161 min (INT_MAX, MOST_POSITIVE_FIXNUM),
1163 memory_full (SIZE_MAX); 1162 sizeof *charset_table);
1164 new_table 1163 memcpy (new_table, charset_table, old_size * sizeof *new_table);
1165 = (struct charset *) xmalloc (sizeof (struct charset)
1166 * (charset_table_size + 16));
1167 memcpy (new_table, charset_table,
1168 sizeof (struct charset) * charset_table_size);
1169 charset_table_size += 16;
1170 charset_table = new_table; 1164 charset_table = new_table;
1171 /* FIXME: Doesn't this leak memory? The old charset_table 1165 /* FIXME: Doesn't this leak memory? The old charset_table becomes
1172 becomes unreachable. If the memory leak is intentional, 1166 unreachable. It could be that this is intentional, because the
1173 a comment should be added to explain this. If not, the 1167 old charset table may be in a dumped emacs, and reallocating such
1174 old charset_table should be freed, using xfree. */ 1168 a table may not work. If the memory leak is intentional, a
1169 comment should be added to explain this. If not, the old
1170 charset_table should be freed, by passing it as the 1st argument
1171 to xpalloc and removing the memcpy. */
1175 } 1172 }
1176 id = charset_table_used++; 1173 id = charset_table_used++;
1177 new_definition_p = 1; 1174 new_definition_p = 1;
@@ -2230,14 +2227,16 @@ struct charset_sort_data
2230{ 2227{
2231 Lisp_Object charset; 2228 Lisp_Object charset;
2232 int id; 2229 int id;
2233 int priority; 2230 ptrdiff_t priority;
2234}; 2231};
2235 2232
2236static int 2233static int
2237charset_compare (const void *d1, const void *d2) 2234charset_compare (const void *d1, const void *d2)
2238{ 2235{
2239 const struct charset_sort_data *data1 = d1, *data2 = d2; 2236 const struct charset_sort_data *data1 = d1, *data2 = d2;
2240 return (data1->priority - data2->priority); 2237 if (data1->priority != data2->priority)
2238 return data1->priority < data2->priority ? -1 : 1;
2239 return 0;
2241} 2240}
2242 2241
2243DEFUN ("sort-charsets", Fsort_charsets, Ssort_charsets, 1, 1, 0, 2242DEFUN ("sort-charsets", Fsort_charsets, Ssort_charsets, 1, 1, 0,
@@ -2247,7 +2246,8 @@ See also `charset-priority-list' and `set-charset-priority'. */)
2247 (Lisp_Object charsets) 2246 (Lisp_Object charsets)
2248{ 2247{
2249 Lisp_Object len = Flength (charsets); 2248 Lisp_Object len = Flength (charsets);
2250 int n = XFASTINT (len), i, j, done; 2249 ptrdiff_t n = XFASTINT (len), i, j;
2250 int done;
2251 Lisp_Object tail, elt, attrs; 2251 Lisp_Object tail, elt, attrs;
2252 struct charset_sort_data *sort_data; 2252 struct charset_sort_data *sort_data;
2253 int id, min_id = INT_MAX, max_id = INT_MIN; 2253 int id, min_id = INT_MAX, max_id = INT_MIN;
@@ -2255,7 +2255,7 @@ See also `charset-priority-list' and `set-charset-priority'. */)
2255 2255
2256 if (n == 0) 2256 if (n == 0)
2257 return Qnil; 2257 return Qnil;
2258 SAFE_ALLOCA (sort_data, struct charset_sort_data *, sizeof (*sort_data) * n); 2258 SAFE_NALLOCA (sort_data, 1, n);
2259 for (tail = charsets, i = 0; CONSP (tail); tail = XCDR (tail), i++) 2259 for (tail = charsets, i = 0; CONSP (tail); tail = XCDR (tail), i++)
2260 { 2260 {
2261 elt = XCAR (tail); 2261 elt = XCAR (tail);
@@ -2330,6 +2330,17 @@ init_charset_once (void)
2330void 2330void
2331syms_of_charset (void) 2331syms_of_charset (void)
2332{ 2332{
2333 /* Allocate an initial charset table that is just under 64 KiB in size.
2334 This should be large enough so that the charset table need not be
2335 reallocated during an initial bootstrap. Allocating anything larger than
2336 64 KiB in an initial run may not work, because glibc malloc might use
2337 mmap for larger allocations, and these don't work well across dumped
2338 systems. */
2339 enum {
2340 initial_malloc_max = (1 << 16) - 1,
2341 charset_table_size_init = initial_malloc_max / sizeof (struct charset)
2342 };
2343
2333 DEFSYM (Qcharsetp, "charsetp"); 2344 DEFSYM (Qcharsetp, "charsetp");
2334 2345
2335 DEFSYM (Qascii, "ascii"); 2346 DEFSYM (Qascii, "ascii");
@@ -2362,8 +2373,9 @@ syms_of_charset (void)
2362 Vcharset_hash_table = Fmake_hash_table (2, args); 2373 Vcharset_hash_table = Fmake_hash_table (2, args);
2363 } 2374 }
2364 2375
2365 charset_table = (struct charset *) xmalloc (sizeof (struct charset) * 128); 2376 charset_table = (struct charset *) xmalloc (sizeof (struct charset)
2366 charset_table_size = 128; 2377 * charset_table_size_init);
2378 charset_table_size = charset_table_size_init;
2367 charset_table_used = 0; 2379 charset_table_used = 0;
2368 2380
2369 defsubr (&Scharsetp); 2381 defsubr (&Scharsetp);
diff --git a/src/cmds.c b/src/cmds.c
index f49cfc221be..2feaf313f23 100644
--- a/src/cmds.c
+++ b/src/cmds.c
@@ -471,7 +471,7 @@ internal_self_insert (int c, EMACS_INT n)
471 { 471 {
472 USE_SAFE_ALLOCA; 472 USE_SAFE_ALLOCA;
473 char *strn, *p; 473 char *strn, *p;
474 SAFE_ALLOCA (strn, char *, n * len); 474 SAFE_NALLOCA (strn, len, n);
475 for (p = strn; n > 0; n--, p += len) 475 for (p = strn; n > 0; n--, p += len)
476 memcpy (p, str, len); 476 memcpy (p, str, len);
477 insert_and_inherit (strn, p - strn); 477 insert_and_inherit (strn, p - strn);
diff --git a/src/composite.c b/src/composite.c
index 4ae1d6ebb68..738fcd3774c 100644
--- a/src/composite.c
+++ b/src/composite.c
@@ -186,13 +186,14 @@ get_composition_id (EMACS_INT charpos, EMACS_INT bytepos, EMACS_INT nchars,
186 EMACS_INT i; 186 EMACS_INT i;
187 int ch; 187 int ch;
188 188
189 /* Maximum length of a string of glyphs. XftGlyphExtents limits this 189 /* Maximum length of a string of glyphs. XftGlyphExtents limits
190 to INT_MAX, and Emacs may limit it further. */ 190 this to INT_MAX, and Emacs limits it further. Divide INT_MAX - 1
191 by 2 because x_produce_glyphs computes glyph_len * 2 + 1. Divide
192 the size by MAX_MULTIBYTE_LENGTH because encode_terminal_code
193 multiplies glyph_len by MAX_MULTIBYTE_LENGTH. */
191 enum { 194 enum {
192 glyph_len_max = 195 GLYPH_LEN_MAX = min ((INT_MAX - 1) / 2,
193 min (INT_MAX, 196 min (PTRDIFF_MAX, SIZE_MAX) / MAX_MULTIBYTE_LENGTH)
194 (min (PTRDIFF_MAX, SIZE_MAX)
195 / max (MAX_MULTIBYTE_LENGTH, 2 * sizeof (short))))
196 }; 197 };
197 198
198 /* PROP should be 199 /* PROP should be
@@ -268,25 +269,9 @@ get_composition_id (EMACS_INT charpos, EMACS_INT bytepos, EMACS_INT nchars,
268 /* This composition is a new one. We must register it. */ 269 /* This composition is a new one. We must register it. */
269 270
270 /* Check if we have sufficient memory to store this information. */ 271 /* Check if we have sufficient memory to store this information. */
271 if (composition_table_size == 0) 272 if (composition_table_size <= n_compositions)
272 { 273 composition_table = xpalloc (composition_table, &composition_table_size,
273 composition_table 274 1, -1, sizeof *composition_table);
274 = (struct composition **) xmalloc (sizeof (composition_table[0]) * 256);
275 composition_table_size = 256;
276 }
277 else if (composition_table_size <= n_compositions)
278 {
279 if ((min (MOST_POSITIVE_FIXNUM,
280 min (PTRDIFF_MAX, SIZE_MAX) / sizeof composition_table[0])
281 - 256)
282 < composition_table_size)
283 memory_full (SIZE_MAX);
284 composition_table
285 = (struct composition **) xrealloc (composition_table,
286 sizeof (composition_table[0])
287 * (composition_table_size + 256));
288 composition_table_size += 256;
289 }
290 275
291 key_contents = XVECTOR (key)->contents; 276 key_contents = XVECTOR (key)->contents;
292 277
@@ -340,7 +325,7 @@ get_composition_id (EMACS_INT charpos, EMACS_INT bytepos, EMACS_INT nchars,
340 ? (ASIZE (key) + 1) / 2 325 ? (ASIZE (key) + 1) / 2
341 : ASIZE (key)); 326 : ASIZE (key));
342 327
343 if (glyph_len_max < glyph_len) 328 if (GLYPH_LEN_MAX < glyph_len)
344 memory_full (SIZE_MAX); 329 memory_full (SIZE_MAX);
345 330
346 /* Register the composition in composition_table. */ 331 /* Register the composition in composition_table. */
@@ -349,7 +334,7 @@ get_composition_id (EMACS_INT charpos, EMACS_INT bytepos, EMACS_INT nchars,
349 cmp->method = method; 334 cmp->method = method;
350 cmp->hash_index = hash_index; 335 cmp->hash_index = hash_index;
351 cmp->glyph_len = glyph_len; 336 cmp->glyph_len = glyph_len;
352 cmp->offsets = (short *) xmalloc (sizeof (short) * glyph_len * 2); 337 cmp->offsets = xnmalloc (glyph_len, 2 * sizeof *cmp->offsets);
353 cmp->font = NULL; 338 cmp->font = NULL;
354 339
355 if (cmp->method != COMPOSITION_WITH_RULE_ALTCHARS) 340 if (cmp->method != COMPOSITION_WITH_RULE_ALTCHARS)
diff --git a/src/composite.h b/src/composite.h
index c30c6832796..c57e2a0e9b3 100644
--- a/src/composite.h
+++ b/src/composite.h
@@ -170,7 +170,7 @@ extern Lisp_Object composition_temp;
170 170
171struct composition { 171struct composition {
172 /* Number of glyphs of the composition components. */ 172 /* Number of glyphs of the composition components. */
173 unsigned glyph_len; 173 int glyph_len;
174 174
175 /* Width, ascent, and descent pixels of the composition. */ 175 /* Width, ascent, and descent pixels of the composition. */
176 short pixel_width, ascent, descent; 176 short pixel_width, ascent, descent;
diff --git a/src/dispextern.h b/src/dispextern.h
index 70f426f95a6..c43eeb55609 100644
--- a/src/dispextern.h
+++ b/src/dispextern.h
@@ -625,7 +625,7 @@ struct glyph_matrix
625 struct glyph_row *rows; 625 struct glyph_row *rows;
626 626
627 /* Number of elements allocated for the vector rows above. */ 627 /* Number of elements allocated for the vector rows above. */
628 int rows_allocated; 628 ptrdiff_t rows_allocated;
629 629
630 /* The number of rows used by the window if all lines were displayed 630 /* The number of rows used by the window if all lines were displayed
631 with the smallest possible character height. */ 631 with the smallest possible character height. */
@@ -1708,7 +1708,8 @@ struct face_cache
1708 struct face **faces_by_id; 1708 struct face **faces_by_id;
1709 1709
1710 /* The allocated size, and number of used slots of faces_by_id. */ 1710 /* The allocated size, and number of used slots of faces_by_id. */
1711 int size, used; 1711 ptrdiff_t size;
1712 int used;
1712 1713
1713 /* Flag indicating that attributes of the `menu' face have been 1714 /* Flag indicating that attributes of the `menu' face have been
1714 changed. */ 1715 changed. */
diff --git a/src/dispnew.c b/src/dispnew.c
index 4cc101d98bf..fde9be6bf5c 100644
--- a/src/dispnew.c
+++ b/src/dispnew.c
@@ -499,15 +499,12 @@ adjust_glyph_matrix (struct window *w, struct glyph_matrix *matrix, int x, int y
499 /* Enlarge MATRIX->rows if necessary. New rows are cleared. */ 499 /* Enlarge MATRIX->rows if necessary. New rows are cleared. */
500 if (matrix->rows_allocated < dim.height) 500 if (matrix->rows_allocated < dim.height)
501 { 501 {
502 ptrdiff_t size; 502 int old_alloc = matrix->rows_allocated;
503 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (struct glyph_row) < dim.height)
504 memory_full (SIZE_MAX);
505 size = dim.height * sizeof (struct glyph_row);
506 new_rows = dim.height - matrix->rows_allocated; 503 new_rows = dim.height - matrix->rows_allocated;
507 matrix->rows = (struct glyph_row *) xrealloc (matrix->rows, size); 504 matrix->rows = xpalloc (matrix->rows, &matrix->rows_allocated,
508 memset (matrix->rows + matrix->rows_allocated, 0, 505 new_rows, INT_MAX, sizeof *matrix->rows);
509 new_rows * sizeof *matrix->rows); 506 memset (matrix->rows + old_alloc, 0,
510 matrix->rows_allocated = dim.height; 507 (matrix->rows_allocated - old_alloc) * sizeof *matrix->rows);
511 } 508 }
512 else 509 else
513 new_rows = 0; 510 new_rows = 0;
@@ -576,15 +573,11 @@ adjust_glyph_matrix (struct window *w, struct glyph_matrix *matrix, int x, int y
576 struct glyph_row *row = matrix->rows; 573 struct glyph_row *row = matrix->rows;
577 struct glyph_row *end = row + matrix->rows_allocated; 574 struct glyph_row *end = row + matrix->rows_allocated;
578 575
579 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (struct glyph) < dim.width)
580 memory_full (SIZE_MAX);
581
582 while (row < end) 576 while (row < end)
583 { 577 {
584 row->glyphs[LEFT_MARGIN_AREA] 578 row->glyphs[LEFT_MARGIN_AREA]
585 = (struct glyph *) xrealloc (row->glyphs[LEFT_MARGIN_AREA], 579 = xnrealloc (row->glyphs[LEFT_MARGIN_AREA],
586 (dim.width 580 dim.width, sizeof (struct glyph));
587 * sizeof (struct glyph)));
588 581
589 /* The mode line never has marginal areas. */ 582 /* The mode line never has marginal areas. */
590 if (row == matrix->rows + dim.height - 1 583 if (row == matrix->rows + dim.height - 1
@@ -1404,20 +1397,18 @@ realloc_glyph_pool (struct glyph_pool *pool, struct dim matrix_dim)
1404 || matrix_dim.height != pool->nrows 1397 || matrix_dim.height != pool->nrows
1405 || matrix_dim.width != pool->ncolumns); 1398 || matrix_dim.width != pool->ncolumns);
1406 1399
1407 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (struct glyph) / matrix_dim.width
1408 < matrix_dim.height)
1409 memory_full (SIZE_MAX);
1410
1411 /* Enlarge the glyph pool. */ 1400 /* Enlarge the glyph pool. */
1412 needed = matrix_dim.width; 1401 needed = matrix_dim.width;
1402 if (INT_MULTIPLY_OVERFLOW (needed, matrix_dim.height))
1403 memory_full (SIZE_MAX);
1413 needed *= matrix_dim.height; 1404 needed *= matrix_dim.height;
1414 if (needed > pool->nglyphs) 1405 if (needed > pool->nglyphs)
1415 { 1406 {
1416 ptrdiff_t size = needed * sizeof (struct glyph); 1407 ptrdiff_t old_nglyphs = pool->nglyphs;
1417 pool->glyphs = (struct glyph *) xrealloc (pool->glyphs, size); 1408 pool->glyphs = xpalloc (pool->glyphs, &pool->nglyphs,
1418 memset (pool->glyphs + pool->nglyphs, 0, 1409 needed - old_nglyphs, -1, sizeof *pool->glyphs);
1419 size - pool->nglyphs * sizeof (struct glyph)); 1410 memset (pool->glyphs + old_nglyphs, 0,
1420 pool->nglyphs = needed; 1411 (pool->nglyphs - old_nglyphs) * sizeof *pool->glyphs);
1421 } 1412 }
1422 1413
1423 /* Remember the number of rows and columns because (a) we use them 1414 /* Remember the number of rows and columns because (a) we use them
@@ -4198,12 +4189,12 @@ static ptrdiff_t row_table_size;
4198 current and desired matrix, and the size of the vectors. */ 4189 current and desired matrix, and the size of the vectors. */
4199 4190
4200static struct row_entry **old_lines, **new_lines; 4191static struct row_entry **old_lines, **new_lines;
4201static int old_lines_size, new_lines_size; 4192static ptrdiff_t old_lines_size, new_lines_size;
4202 4193
4203/* A pool to allocate run structures from, and its size. */ 4194/* A pool to allocate run structures from, and its size. */
4204 4195
4205static struct run *run_pool; 4196static struct run *run_pool;
4206static int runs_size; 4197static ptrdiff_t runs_size;
4207 4198
4208/* A vector of runs of lines found during scrolling. */ 4199/* A vector of runs of lines found during scrolling. */
4209 4200
@@ -4271,7 +4262,7 @@ scrolling_window (struct window *w, int header_line_p)
4271 ptrdiff_t i; 4262 ptrdiff_t i;
4272 int j, first_old, first_new, last_old, last_new; 4263 int j, first_old, first_new, last_old, last_new;
4273 int nruns, run_idx; 4264 int nruns, run_idx;
4274 ptrdiff_t n, nbytes; 4265 ptrdiff_t n;
4275 struct row_entry *entry; 4266 struct row_entry *entry;
4276 struct redisplay_interface *rif = FRAME_RIF (XFRAME (WINDOW_FRAME (w))); 4267 struct redisplay_interface *rif = FRAME_RIF (XFRAME (WINDOW_FRAME (w)));
4277 4268
@@ -4356,7 +4347,7 @@ scrolling_window (struct window *w, int header_line_p)
4356 if (last_new == first_new) 4347 if (last_new == first_new)
4357 return 0; 4348 return 0;
4358 4349
4359 /* Check for integer overflow in xrealloc size calculation. 4350 /* Check for integer overflow in size calculation.
4360 4351
4361 If next_almost_prime checks (N) for divisibility by 2..10, then 4352 If next_almost_prime checks (N) for divisibility by 2..10, then
4362 it can return at most N + 10, e.g., next_almost_prime (1) == 11. 4353 it can return at most N + 10, e.g., next_almost_prime (1) == 11.
@@ -4369,63 +4360,45 @@ scrolling_window (struct window *w, int header_line_p)
4369 { 4360 {
4370 verify (NEXT_ALMOST_PRIME_LIMIT == 11); 4361 verify (NEXT_ALMOST_PRIME_LIMIT == 11);
4371 enum { next_almost_prime_increment_max = 10 }; 4362 enum { next_almost_prime_increment_max = 10 };
4372 ptrdiff_t alloc_max = min (PTRDIFF_MAX, SIZE_MAX);
4373 ptrdiff_t row_table_max = 4363 ptrdiff_t row_table_max =
4374 ((alloc_max - next_almost_prime_increment_max) 4364 (min (PTRDIFF_MAX, SIZE_MAX) / (3 * sizeof *row_table)
4375 / (3 * sizeof *row_table)); 4365 - next_almost_prime_increment_max);
4376 ptrdiff_t row_entry_pool_max = alloc_max / sizeof *row_entry_pool; 4366 ptrdiff_t current_nrows_max = row_table_max - desired_matrix->nrows;
4377 int n_max = min (INT_MAX, min (row_table_max, row_entry_pool_max)); 4367 if (current_nrows_max < current_matrix->nrows)
4378 ptrdiff_t old_lines_max = alloc_max / sizeof *old_lines;
4379 int current_nrows_max = min (n_max - desired_matrix->nrows, old_lines_max);
4380 int desired_nrows_max =
4381 min (INT_MAX,
4382 alloc_max / max (sizeof *new_lines,
4383 max (sizeof *runs, sizeof *run_pool)));
4384 if (current_nrows_max < current_matrix->nrows
4385 || desired_nrows_max < desired_matrix->nrows)
4386 memory_full (SIZE_MAX); 4368 memory_full (SIZE_MAX);
4387 } 4369 }
4388 4370
4389 /* Reallocate vectors, tables etc. if necessary. */ 4371 /* Reallocate vectors, tables etc. if necessary. */
4390 4372
4391 if (current_matrix->nrows > old_lines_size) 4373 if (current_matrix->nrows > old_lines_size)
4392 { 4374 old_lines = xpalloc (old_lines, &old_lines_size,
4393 nbytes = current_matrix->nrows * sizeof *old_lines; 4375 current_matrix->nrows - old_lines_size,
4394 old_lines = (struct row_entry **) xrealloc (old_lines, nbytes); 4376 INT_MAX, sizeof *old_lines);
4395 old_lines_size = current_matrix->nrows;
4396 }
4397 4377
4398 if (desired_matrix->nrows > new_lines_size) 4378 if (desired_matrix->nrows > new_lines_size)
4399 { 4379 new_lines = xpalloc (new_lines, &new_lines_size,
4400 nbytes = desired_matrix->nrows * sizeof *new_lines; 4380 desired_matrix->nrows - new_lines_size,
4401 new_lines = (struct row_entry **) xrealloc (new_lines, nbytes); 4381 INT_MAX, sizeof *new_lines);
4402 new_lines_size = desired_matrix->nrows;
4403 }
4404 4382
4405 n = desired_matrix->nrows; 4383 n = desired_matrix->nrows;
4406 n += current_matrix->nrows; 4384 n += current_matrix->nrows;
4407 if (row_table_size / 3 < n) 4385 if (row_table_size < 3 * n)
4408 { 4386 {
4409 ptrdiff_t size = next_almost_prime (3 * n); 4387 ptrdiff_t size = next_almost_prime (3 * n);
4410 nbytes = size * sizeof *row_table; 4388 row_table = xnrealloc (row_table, size, sizeof *row_table);
4411 row_table = (struct row_entry **) xrealloc (row_table, nbytes);
4412 row_table_size = size; 4389 row_table_size = size;
4413 memset (row_table, 0, nbytes); 4390 memset (row_table, 0, size * sizeof *row_table);
4414 } 4391 }
4415 4392
4416 if (n > row_entry_pool_size) 4393 if (n > row_entry_pool_size)
4417 { 4394 row_entry_pool = xpalloc (row_entry_pool, &row_entry_pool_size,
4418 nbytes = n * sizeof *row_entry_pool; 4395 n - row_entry_pool_size,
4419 row_entry_pool = (struct row_entry *) xrealloc (row_entry_pool, nbytes); 4396 -1, sizeof *row_entry_pool);
4420 row_entry_pool_size = n;
4421 }
4422 4397
4423 if (desired_matrix->nrows > runs_size) 4398 if (desired_matrix->nrows > runs_size)
4424 { 4399 {
4425 nbytes = desired_matrix->nrows * sizeof *runs; 4400 runs = xnrealloc (runs, desired_matrix->nrows, sizeof *runs);
4426 runs = (struct run **) xrealloc (runs, nbytes); 4401 run_pool = xnrealloc (run_pool, desired_matrix->nrows, sizeof *run_pool);
4427 nbytes = desired_matrix->nrows * sizeof *run_pool;
4428 run_pool = (struct run *) xrealloc (run_pool, nbytes);
4429 runs_size = desired_matrix->nrows; 4402 runs_size = desired_matrix->nrows;
4430 } 4403 }
4431 4404
diff --git a/src/doc.c b/src/doc.c
index bd1831dde0e..eb8ff3c2521 100644
--- a/src/doc.c
+++ b/src/doc.c
@@ -174,15 +174,9 @@ get_doc_string (Lisp_Object filepos, int unibyte, int definition)
174 if (space_left == 0) 174 if (space_left == 0)
175 { 175 {
176 ptrdiff_t in_buffer = p - get_doc_string_buffer; 176 ptrdiff_t in_buffer = p - get_doc_string_buffer;
177 enum { incr = 16 * 1024 }; 177 get_doc_string_buffer =
178 ptrdiff_t size; 178 xpalloc (get_doc_string_buffer, &get_doc_string_buffer_size,
179 if (min (PTRDIFF_MAX, SIZE_MAX) - 1 - incr 179 16 * 1024, -1, 1);
180 < get_doc_string_buffer_size)
181 memory_full (SIZE_MAX);
182 size = get_doc_string_buffer_size + incr;
183 get_doc_string_buffer
184 = (char *) xrealloc (get_doc_string_buffer, size + 1);
185 get_doc_string_buffer_size = size;
186 p = get_doc_string_buffer + in_buffer; 180 p = get_doc_string_buffer + in_buffer;
187 space_left = (get_doc_string_buffer_size 181 space_left = (get_doc_string_buffer_size
188 - (p - get_doc_string_buffer)); 182 - (p - get_doc_string_buffer));
diff --git a/src/emacs.c b/src/emacs.c
index 4de567a5588..e4c42c3e193 100644
--- a/src/emacs.c
+++ b/src/emacs.c
@@ -1358,27 +1358,17 @@ Using an Emacs configured with --with-x-toolkit=lucid does not have this problem
1358 /* If we have the form --display=NAME, 1358 /* If we have the form --display=NAME,
1359 convert it into -d name. 1359 convert it into -d name.
1360 This requires inserting a new element into argv. */ 1360 This requires inserting a new element into argv. */
1361 if (displayname != 0 && skip_args - count_before == 1) 1361 if (displayname && count_before < skip_args)
1362 { 1362 {
1363 char **new; 1363 if (skip_args == count_before + 1)
1364 int j; 1364 {
1365 1365 memmove (argv + count_before + 3, argv + count_before + 2,
1366 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (char *) - 2 < argc) 1366 (argc - (count_before + 2)) * sizeof *argv);
1367 memory_full (SIZE_MAX); 1367 argv[count_before + 2] = displayname;
1368 new = (char **) xmalloc (sizeof *new * argc + sizeof *new * 2); 1368 argc++;
1369 for (j = 0; j < count_before + 1; j++) 1369 }
1370 new[j] = argv[j]; 1370 argv[count_before + 1] = (char *) "-d";
1371 new[count_before + 1] = (char *) "-d";
1372 new[count_before + 2] = displayname;
1373 for (j = count_before + 2; j <argc; j++)
1374 new[j + 1] = argv[j];
1375 argv = new;
1376 argc++;
1377 } 1371 }
1378 /* Change --display to -d, when its arg is separate. */
1379 else if (displayname != 0 && skip_args > count_before
1380 && argv[count_before + 1][1] == '-')
1381 argv[count_before + 1] = (char *) "-d";
1382 1372
1383 if (! no_site_lisp) 1373 if (! no_site_lisp)
1384 { 1374 {
@@ -1841,19 +1831,13 @@ sort_args (int argc, char **argv)
1841 0 for an option that takes no arguments, 1831 0 for an option that takes no arguments,
1842 1 for an option that takes one argument, etc. 1832 1 for an option that takes one argument, etc.
1843 -1 for an ordinary non-option argument. */ 1833 -1 for an ordinary non-option argument. */
1844 int *options; 1834 int *options = xnmalloc (argc, sizeof *options);
1845 int *priority; 1835 int *priority = xnmalloc (argc, sizeof *priority);
1846 int to = 1; 1836 int to = 1;
1847 int incoming_used = 1; 1837 int incoming_used = 1;
1848 int from; 1838 int from;
1849 int i; 1839 int i;
1850 1840
1851 if (sizeof (char *) < sizeof (int)
1852 && min (PTRDIFF_MAX, SIZE_MAX) / sizeof (int) < argc)
1853 memory_full (SIZE_MAX);
1854 options = (int *) xmalloc (sizeof (int) * argc);
1855 priority = (int *) xmalloc (sizeof (int) * argc);
1856
1857 /* Categorize all the options, 1841 /* Categorize all the options,
1858 and figure out which argv elts are option arguments. */ 1842 and figure out which argv elts are option arguments. */
1859 for (from = 1; from < argc; from++) 1843 for (from = 1; from < argc; from++)
diff --git a/src/eval.c b/src/eval.c
index bcb77574fee..94039b31e17 100644
--- a/src/eval.c
+++ b/src/eval.c
@@ -3288,8 +3288,7 @@ grow_specpdl (void)
3288 signal_error ("Variable binding depth exceeds max-specpdl-size", Qnil); 3288 signal_error ("Variable binding depth exceeds max-specpdl-size", Qnil);
3289 } 3289 }
3290 size = specpdl_size < max_size / 2 ? 2 * specpdl_size : max_size; 3290 size = specpdl_size < max_size / 2 ? 2 * specpdl_size : max_size;
3291 specpdl = ((struct specbinding *) 3291 specpdl = xnrealloc (specpdl, size, sizeof *specpdl);
3292 xrealloc (specpdl, size * sizeof (struct specbinding)));
3293 specpdl_size = size; 3292 specpdl_size = size;
3294 specpdl_ptr = specpdl + count; 3293 specpdl_ptr = specpdl + count;
3295} 3294}
diff --git a/src/fns.c b/src/fns.c
index e5538d6acbc..a3af6b8c15a 100644
--- a/src/fns.c
+++ b/src/fns.c
@@ -602,12 +602,7 @@ concat (ptrdiff_t nargs, Lisp_Object *args,
602 602
603 prev = Qnil; 603 prev = Qnil;
604 if (STRINGP (val)) 604 if (STRINGP (val))
605 { 605 SAFE_NALLOCA (textprops, 1, nargs);
606 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof *textprops < nargs)
607 memory_full (SIZE_MAX);
608 SAFE_ALLOCA (textprops, struct textprop_rec *,
609 sizeof *textprops * nargs);
610 }
611 606
612 for (argnum = 0; argnum < nargs; argnum++) 607 for (argnum = 0; argnum < nargs; argnum++)
613 { 608 {
diff --git a/src/ftfont.c b/src/ftfont.c
index 551006eef94..5b95e2b2f08 100644
--- a/src/ftfont.c
+++ b/src/ftfont.c
@@ -1764,18 +1764,10 @@ static OTF_GlyphString otf_gstring;
1764static void 1764static void
1765setup_otf_gstring (int size) 1765setup_otf_gstring (int size)
1766{ 1766{
1767 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (OTF_Glyph) < size) 1767 if (otf_gstring.size < size)
1768 memory_full (SIZE_MAX);
1769
1770 if (otf_gstring.size == 0)
1771 { 1768 {
1772 otf_gstring.glyphs = (OTF_Glyph *) xmalloc (sizeof (OTF_Glyph) * size); 1769 otf_gstring.glyphs = xnrealloc (otf_gstring.glyphs,
1773 otf_gstring.size = size; 1770 size, sizeof (OTF_Glyph));
1774 }
1775 else if (otf_gstring.size < size)
1776 {
1777 otf_gstring.glyphs = xrealloc (otf_gstring.glyphs,
1778 sizeof (OTF_Glyph) * size);
1779 otf_gstring.size = size; 1771 otf_gstring.size = size;
1780 } 1772 }
1781 otf_gstring.used = size; 1773 otf_gstring.used = size;
@@ -2396,8 +2388,6 @@ ftfont_shape_by_flt (Lisp_Object lgstring, struct font *font,
2396 struct MFLTFontFT flt_font_ft; 2388 struct MFLTFontFT flt_font_ft;
2397 MFLT *flt = NULL; 2389 MFLT *flt = NULL;
2398 int with_variation_selector = 0; 2390 int with_variation_selector = 0;
2399 int allocated_max = min (INT_MAX,
2400 min (PTRDIFF_MAX, SIZE_MAX) / sizeof (MFLTGlyph));
2401 2391
2402 if (! m17n_flt_initialized) 2392 if (! m17n_flt_initialized)
2403 { 2393 {
@@ -2453,20 +2443,19 @@ ftfont_shape_by_flt (Lisp_Object lgstring, struct font *font,
2453 } 2443 }
2454 } 2444 }
2455 2445
2456 if (allocated_max / 2 < len) 2446 if (INT_MAX / 2 < len)
2457 memory_full (SIZE_MAX); 2447 memory_full (SIZE_MAX);
2458 2448
2459 if (gstring.allocated == 0) 2449 if (gstring.allocated == 0)
2460 { 2450 {
2461 gstring.allocated = len * 2;
2462 gstring.glyph_size = sizeof (MFLTGlyph); 2451 gstring.glyph_size = sizeof (MFLTGlyph);
2463 gstring.glyphs = xmalloc (sizeof (MFLTGlyph) * gstring.allocated); 2452 gstring.glyphs = xnmalloc (len * 2, sizeof (MFLTGlyph));
2453 gstring.allocated = len * 2;
2464 } 2454 }
2465 else if (gstring.allocated < len * 2) 2455 else if (gstring.allocated < len * 2)
2466 { 2456 {
2457 gstring.glyphs = xnrealloc (gstring.glyphs, len * 2, sizeof (MFLTGlyph));
2467 gstring.allocated = len * 2; 2458 gstring.allocated = len * 2;
2468 gstring.glyphs = xrealloc (gstring.glyphs,
2469 sizeof (MFLTGlyph) * gstring.allocated);
2470 } 2459 }
2471 memset (gstring.glyphs, 0, sizeof (MFLTGlyph) * len); 2460 memset (gstring.glyphs, 0, sizeof (MFLTGlyph) * len);
2472 for (i = 0; i < len; i++) 2461 for (i = 0; i < len; i++)
@@ -2515,11 +2504,11 @@ ftfont_shape_by_flt (Lisp_Object lgstring, struct font *font,
2515 int result = mflt_run (&gstring, 0, len, &flt_font_ft.flt_font, flt); 2504 int result = mflt_run (&gstring, 0, len, &flt_font_ft.flt_font, flt);
2516 if (result != -2) 2505 if (result != -2)
2517 break; 2506 break;
2518 if (allocated_max / 2 < gstring.allocated) 2507 if (INT_MAX / 2 < gstring.allocated)
2519 memory_full (SIZE_MAX); 2508 memory_full (SIZE_MAX);
2520 gstring.allocated += gstring.allocated; 2509 gstring.glyphs = xnrealloc (gstring.glyphs,
2521 gstring.glyphs = xrealloc (gstring.glyphs, 2510 gstring.allocated, 2 * sizeof (MFLTGlyph));
2522 sizeof (MFLTGlyph) * gstring.allocated); 2511 gstring.allocated *= 2;
2523 } 2512 }
2524 if (gstring.used > LGSTRING_GLYPH_LEN (lgstring)) 2513 if (gstring.used > LGSTRING_GLYPH_LEN (lgstring))
2525 return Qnil; 2514 return Qnil;
diff --git a/src/gtkutil.c b/src/gtkutil.c
index f56e888e685..2492ce620bc 100644
--- a/src/gtkutil.c
+++ b/src/gtkutil.c
@@ -3318,14 +3318,12 @@ xg_store_widget_in_map (GtkWidget *w)
3318 if (id_to_widget.max_size == id_to_widget.used) 3318 if (id_to_widget.max_size == id_to_widget.used)
3319 { 3319 {
3320 ptrdiff_t new_size; 3320 ptrdiff_t new_size;
3321 ptrdiff_t lim = min (TYPE_MAXIMUM (Window), 3321 if (TYPE_MAXIMUM (Window) - ID_TO_WIDGET_INCR < id_to_widget.max_size)
3322 min (PTRDIFF_MAX, SIZE_MAX) / sizeof (GtkWidget *));
3323 if (lim - ID_TO_WIDGET_INCR < id_to_widget.max_size)
3324 memory_full (SIZE_MAX); 3322 memory_full (SIZE_MAX);
3325 3323
3326 new_size = id_to_widget.max_size + ID_TO_WIDGET_INCR; 3324 new_size = id_to_widget.max_size + ID_TO_WIDGET_INCR;
3327 id_to_widget.widgets = xrealloc (id_to_widget.widgets, 3325 id_to_widget.widgets = xnrealloc (id_to_widget.widgets,
3328 sizeof (GtkWidget *)*new_size); 3326 new_size, sizeof (GtkWidget *));
3329 3327
3330 for (i = id_to_widget.max_size; i < new_size; ++i) 3328 for (i = id_to_widget.max_size; i < new_size; ++i)
3331 id_to_widget.widgets[i] = 0; 3329 id_to_widget.widgets[i] = 0;
diff --git a/src/image.c b/src/image.c
index d2a71637fed..bf7daa24da1 100644
--- a/src/image.c
+++ b/src/image.c
@@ -3586,11 +3586,7 @@ xpm_load (struct frame *f, struct image *img)
3586#endif /* HAVE_NTGUI */ 3586#endif /* HAVE_NTGUI */
3587 3587
3588 /* Remember allocated colors. */ 3588 /* Remember allocated colors. */
3589 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof *img->colors 3589 img->colors = xnmalloc (attrs.nalloc_pixels, sizeof *img->colors);
3590 < attrs.nalloc_pixels)
3591 memory_full (SIZE_MAX);
3592 img->colors = (unsigned long *) xmalloc (img->ncolors
3593 * sizeof *img->colors);
3594 img->ncolors = attrs.nalloc_pixels; 3590 img->ncolors = attrs.nalloc_pixels;
3595 for (i = 0; i < attrs.nalloc_pixels; ++i) 3591 for (i = 0; i < attrs.nalloc_pixels; ++i)
3596 { 3592 {
diff --git a/src/indent.c b/src/indent.c
index 8a2117751aa..37873351aa0 100644
--- a/src/indent.c
+++ b/src/indent.c
@@ -1423,7 +1423,7 @@ compute_motion (EMACS_INT from, EMACS_INT fromvpos, EMACS_INT fromhpos, int did_
1423 the text character-by-character. */ 1423 the text character-by-character. */
1424 if (current_buffer->width_run_cache && pos >= next_width_run) 1424 if (current_buffer->width_run_cache && pos >= next_width_run)
1425 { 1425 {
1426 EMACS_INT run_end; 1426 ptrdiff_t run_end;
1427 int common_width 1427 int common_width
1428 = region_cache_forward (current_buffer, 1428 = region_cache_forward (current_buffer,
1429 current_buffer->width_run_cache, 1429 current_buffer->width_run_cache,
diff --git a/src/lisp.h b/src/lisp.h
index 267bfe1b21f..83cc680b7e2 100644
--- a/src/lisp.h
+++ b/src/lisp.h
@@ -3574,6 +3574,9 @@ extern int immediate_quit; /* Nonzero means ^G can quit instantly */
3574extern POINTER_TYPE *xmalloc (size_t); 3574extern POINTER_TYPE *xmalloc (size_t);
3575extern POINTER_TYPE *xrealloc (POINTER_TYPE *, size_t); 3575extern POINTER_TYPE *xrealloc (POINTER_TYPE *, size_t);
3576extern void xfree (POINTER_TYPE *); 3576extern void xfree (POINTER_TYPE *);
3577extern void *xnmalloc (ptrdiff_t, ptrdiff_t);
3578extern void *xnrealloc (void *, ptrdiff_t, ptrdiff_t);
3579extern void *xpalloc (void *, ptrdiff_t *, ptrdiff_t, ptrdiff_t, ptrdiff_t);
3577 3580
3578extern char *xstrdup (const char *); 3581extern char *xstrdup (const char *);
3579 3582
@@ -3691,6 +3694,23 @@ extern Lisp_Object safe_alloca_unwind (Lisp_Object);
3691 } \ 3694 } \
3692 } while (0) 3695 } while (0)
3693 3696
3697/* SAFE_NALLOCA sets BUF to a newly allocated array of MULTIPLIER *
3698 NITEMS items, each of the same type as *BUF. MULTIPLIER must
3699 positive. The code is tuned for MULTIPLIER being a constant. */
3700
3701#define SAFE_NALLOCA(buf, multiplier, nitems) \
3702 do { \
3703 if ((nitems) <= MAX_ALLOCA / sizeof *(buf) / (multiplier)) \
3704 (buf) = alloca (sizeof *(buf) * (multiplier) * (nitems)); \
3705 else \
3706 { \
3707 (buf) = xnmalloc (nitems, sizeof *(buf) * (multiplier)); \
3708 sa_must_free = 1; \
3709 record_unwind_protect (safe_alloca_unwind, \
3710 make_save_value (buf, 0)); \
3711 } \
3712 } while (0)
3713
3694/* SAFE_FREE frees xmalloced memory and enables GC as needed. */ 3714/* SAFE_FREE frees xmalloced memory and enables GC as needed. */
3695 3715
3696#define SAFE_FREE() \ 3716#define SAFE_FREE() \
diff --git a/src/minibuf.c b/src/minibuf.c
index 30082af9037..eb564a10ec6 100644
--- a/src/minibuf.c
+++ b/src/minibuf.c
@@ -261,10 +261,7 @@ read_minibuf_noninteractive (Lisp_Object map, Lisp_Object initial,
261 if (len == size) 261 if (len == size)
262 { 262 {
263 if (STRING_BYTES_BOUND / 2 < size) 263 if (STRING_BYTES_BOUND / 2 < size)
264 { 264 memory_full (SIZE_MAX);
265 xfree (line);
266 memory_full (SIZE_MAX);
267 }
268 size *= 2; 265 size *= 2;
269 line = (char *) xrealloc (line, size); 266 line = (char *) xrealloc (line, size);
270 } 267 }
diff --git a/src/nsterm.m b/src/nsterm.m
index 2ce996dc82f..484e8847dc9 100644
--- a/src/nsterm.m
+++ b/src/nsterm.m
@@ -1376,19 +1376,9 @@ ns_index_color (NSColor *color, struct frame *f)
1376 else 1376 else
1377 { 1377 {
1378 if (color_table->avail == color_table->size) 1378 if (color_table->avail == color_table->size)
1379 { 1379 color_table->colors =
1380 ptrdiff_t size; 1380 xpalloc (color_table->colors, &color_table->size, 1,
1381 ptrdiff_t size_max = 1381 min (ULONG_MAX, PTRDIFF_MAX), sizeof *color_table->colors);
1382 min (ULONG_MAX,
1383 min (PTRDIFF_MAX, SIZE_MAX) / sizeof (NSColor *));
1384 if (size_max - NS_COLOR_CAPACITY < color_table->size)
1385 memory_full (SIZE_MAX);
1386 size = color_table->size + NS_COLOR_CAPACITY;
1387 color_table->colors
1388 = (NSColor **)xrealloc (color_table->colors,
1389 size * sizeof (NSColor *));
1390 color_table->size = size;
1391 }
1392 idx = color_table->avail++; 1382 idx = color_table->avail++;
1393 } 1383 }
1394 1384
diff --git a/src/process.c b/src/process.c
index 31359a1f1f2..f2c2bfd81c5 100644
--- a/src/process.c
+++ b/src/process.c
@@ -3558,7 +3558,7 @@ format; see the description of ADDRESS in `make-network-process'. */)
3558{ 3558{
3559 struct ifconf ifconf; 3559 struct ifconf ifconf;
3560 struct ifreq *ifreqs = NULL; 3560 struct ifreq *ifreqs = NULL;
3561 int ifaces = 0; 3561 ptrdiff_t ifaces = 0;
3562 int buf_size, s; 3562 int buf_size, s;
3563 Lisp_Object res; 3563 Lisp_Object res;
3564 3564
@@ -3567,21 +3567,9 @@ format; see the description of ADDRESS in `make-network-process'. */)
3567 return Qnil; 3567 return Qnil;
3568 3568
3569 again: 3569 again:
3570 if (min (INT_MAX, min (PTRDIFF_MAX, SIZE_MAX)) / sizeof *ifreqs - 25 3570 ifreqs = xpalloc (ifreqs, &ifaces, 25,
3571 < ifaces) 3571 INT_MAX / sizeof *ifreqs, sizeof *ifreqs);
3572 {
3573 xfree (ifreqs);
3574 memory_full (SIZE_MAX);
3575 }
3576 ifaces += 25;
3577 buf_size = ifaces * sizeof (ifreqs[0]); 3572 buf_size = ifaces * sizeof (ifreqs[0]);
3578 ifreqs = (struct ifreq *)xrealloc(ifreqs, buf_size);
3579 if (!ifreqs)
3580 {
3581 close (s);
3582 return Qnil;
3583 }
3584
3585 ifconf.ifc_len = buf_size; 3573 ifconf.ifc_len = buf_size;
3586 ifconf.ifc_req = ifreqs; 3574 ifconf.ifc_req = ifreqs;
3587 if (ioctl (s, SIOCGIFCONF, &ifconf)) 3575 if (ioctl (s, SIOCGIFCONF, &ifconf))
diff --git a/src/region-cache.c b/src/region-cache.c
index e6cec96171d..ed7a07a6709 100644
--- a/src/region-cache.c
+++ b/src/region-cache.c
@@ -63,7 +63,7 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
63 revalidate_region_cache to see how this helps. */ 63 revalidate_region_cache to see how this helps. */
64 64
65struct boundary { 65struct boundary {
66 EMACS_INT pos; 66 ptrdiff_t pos;
67 int value; 67 int value;
68}; 68};
69 69
@@ -73,16 +73,16 @@ struct region_cache {
73 struct boundary *boundaries; 73 struct boundary *boundaries;
74 74
75 /* boundaries[gap_start ... gap_start + gap_len - 1] is the gap. */ 75 /* boundaries[gap_start ... gap_start + gap_len - 1] is the gap. */
76 EMACS_INT gap_start, gap_len; 76 ptrdiff_t gap_start, gap_len;
77 77
78 /* The number of elements allocated to boundaries, not including the 78 /* The number of elements allocated to boundaries, not including the
79 gap. */ 79 gap. */
80 EMACS_INT cache_len; 80 ptrdiff_t cache_len;
81 81
82 /* The areas that haven't changed since the last time we cleaned out 82 /* The areas that haven't changed since the last time we cleaned out
83 invalid entries from the cache. These overlap when the buffer is 83 invalid entries from the cache. These overlap when the buffer is
84 entirely unchanged. */ 84 entirely unchanged. */
85 EMACS_INT beg_unchanged, end_unchanged; 85 ptrdiff_t beg_unchanged, end_unchanged;
86 86
87 /* The first and last positions in the buffer. Because boundaries 87 /* The first and last positions in the buffer. Because boundaries
88 store their positions relative to the start (BEG) and end (Z) of 88 store their positions relative to the start (BEG) and end (Z) of
@@ -92,7 +92,7 @@ struct region_cache {
92 92
93 Yes, buffer_beg is always 1. It's there for symmetry with 93 Yes, buffer_beg is always 1. It's there for symmetry with
94 buffer_end and the BEG and BUF_BEG macros. */ 94 buffer_end and the BEG and BUF_BEG macros. */
95 EMACS_INT buffer_beg, buffer_end; 95 ptrdiff_t buffer_beg, buffer_end;
96}; 96};
97 97
98/* Return the position of boundary i in cache c. */ 98/* Return the position of boundary i in cache c. */
@@ -173,17 +173,17 @@ free_region_cache (struct region_cache *c)
173 This operation should be logarithmic in the number of cache 173 This operation should be logarithmic in the number of cache
174 entries. It would be nice if it took advantage of locality of 174 entries. It would be nice if it took advantage of locality of
175 reference, too, by searching entries near the last entry found. */ 175 reference, too, by searching entries near the last entry found. */
176static EMACS_INT 176static ptrdiff_t
177find_cache_boundary (struct region_cache *c, EMACS_INT pos) 177find_cache_boundary (struct region_cache *c, ptrdiff_t pos)
178{ 178{
179 EMACS_INT low = 0, high = c->cache_len; 179 ptrdiff_t low = 0, high = c->cache_len;
180 180
181 while (low + 1 < high) 181 while (low + 1 < high)
182 { 182 {
183 /* mid is always a valid index, because low < high and ">> 1" 183 /* mid is always a valid index, because low < high and ">> 1"
184 rounds down. */ 184 rounds down. */
185 EMACS_INT mid = (low + high) >> 1; 185 ptrdiff_t mid = (low >> 1) + (high >> 1) + (low & high & 1);
186 EMACS_INT boundary = BOUNDARY_POS (c, mid); 186 ptrdiff_t boundary = BOUNDARY_POS (c, mid);
187 187
188 if (pos < boundary) 188 if (pos < boundary)
189 high = mid; 189 high = mid;
@@ -208,13 +208,13 @@ find_cache_boundary (struct region_cache *c, EMACS_INT pos)
208/* Move the gap of cache C to index POS, and make sure it has space 208/* Move the gap of cache C to index POS, and make sure it has space
209 for at least MIN_SIZE boundaries. */ 209 for at least MIN_SIZE boundaries. */
210static void 210static void
211move_cache_gap (struct region_cache *c, EMACS_INT pos, EMACS_INT min_size) 211move_cache_gap (struct region_cache *c, ptrdiff_t pos, ptrdiff_t min_size)
212{ 212{
213 /* Copy these out of the cache and into registers. */ 213 /* Copy these out of the cache and into registers. */
214 EMACS_INT gap_start = c->gap_start; 214 ptrdiff_t gap_start = c->gap_start;
215 EMACS_INT gap_len = c->gap_len; 215 ptrdiff_t gap_len = c->gap_len;
216 EMACS_INT buffer_beg = c->buffer_beg; 216 ptrdiff_t buffer_beg = c->buffer_beg;
217 EMACS_INT buffer_end = c->buffer_end; 217 ptrdiff_t buffer_end = c->buffer_end;
218 218
219 if (pos < 0 219 if (pos < 0
220 || pos > c->cache_len) 220 || pos > c->cache_len)
@@ -246,22 +246,11 @@ move_cache_gap (struct region_cache *c, EMACS_INT pos, EMACS_INT min_size)
246 when the portion after the gap is smallest. */ 246 when the portion after the gap is smallest. */
247 if (gap_len < min_size) 247 if (gap_len < min_size)
248 { 248 {
249 EMACS_INT i; 249 ptrdiff_t i;
250 ptrdiff_t cache_len_max =
251 min (PTRDIFF_MAX, SIZE_MAX) / sizeof *c->boundaries;
252 ptrdiff_t min_size_max = cache_len_max - c->cache_len;
253
254 if (min_size_max < min_size)
255 memory_full (SIZE_MAX);
256
257 /* Unless running out of space, make at least NEW_CACHE_GAP
258 elements, as long as we're expanding anyway. */
259 min_size = max (min_size, min (min_size_max, NEW_CACHE_GAP));
260 250
261 c->boundaries = 251 c->boundaries =
262 (struct boundary *) xrealloc (c->boundaries, 252 xpalloc (c->boundaries, &c->cache_len, min_size, -1,
263 ((min_size + c->cache_len) 253 sizeof *c->boundaries);
264 * sizeof (*c->boundaries)));
265 254
266 /* Some systems don't provide a version of the copy routine that 255 /* Some systems don't provide a version of the copy routine that
267 can be trusted to shift memory upward into an overlapping 256 can be trusted to shift memory upward into an overlapping
@@ -298,7 +287,7 @@ move_cache_gap (struct region_cache *c, EMACS_INT pos, EMACS_INT min_size)
298/* Insert a new boundary in cache C; it will have cache index I, 287/* Insert a new boundary in cache C; it will have cache index I,
299 and have the specified POS and VALUE. */ 288 and have the specified POS and VALUE. */
300static void 289static void
301insert_cache_boundary (struct region_cache *c, EMACS_INT i, EMACS_INT pos, 290insert_cache_boundary (struct region_cache *c, ptrdiff_t i, ptrdiff_t pos,
302 int value) 291 int value)
303{ 292{
304 /* i must be a valid cache index. */ 293 /* i must be a valid cache index. */
@@ -336,9 +325,9 @@ insert_cache_boundary (struct region_cache *c, EMACS_INT i, EMACS_INT pos,
336 325
337static void 326static void
338delete_cache_boundaries (struct region_cache *c, 327delete_cache_boundaries (struct region_cache *c,
339 EMACS_INT start, EMACS_INT end) 328 ptrdiff_t start, ptrdiff_t end)
340{ 329{
341 EMACS_INT len = end - start; 330 ptrdiff_t len = end - start;
342 331
343 /* Gotta be in range. */ 332 /* Gotta be in range. */
344 if (start < 0 333 if (start < 0
@@ -389,7 +378,7 @@ delete_cache_boundaries (struct region_cache *c,
389/* Set the value in cache C for the region START..END to VALUE. */ 378/* Set the value in cache C for the region START..END to VALUE. */
390static void 379static void
391set_cache_region (struct region_cache *c, 380set_cache_region (struct region_cache *c,
392 EMACS_INT start, EMACS_INT end, int value) 381 ptrdiff_t start, ptrdiff_t end, int value)
393{ 382{
394 if (start > end) 383 if (start > end)
395 abort (); 384 abort ();
@@ -412,8 +401,8 @@ set_cache_region (struct region_cache *c,
412 index of the earliest boundary after the last character in 401 index of the earliest boundary after the last character in
413 start..end. (This tortured terminology is intended to answer 402 start..end. (This tortured terminology is intended to answer
414 all the "< or <=?" sort of questions.) */ 403 all the "< or <=?" sort of questions.) */
415 EMACS_INT start_ix = find_cache_boundary (c, start); 404 ptrdiff_t start_ix = find_cache_boundary (c, start);
416 EMACS_INT end_ix = find_cache_boundary (c, end - 1) + 1; 405 ptrdiff_t end_ix = find_cache_boundary (c, end - 1) + 1;
417 406
418 /* We must remember the value established by the last boundary 407 /* We must remember the value established by the last boundary
419 before end; if that boundary's domain stretches beyond end, 408 before end; if that boundary's domain stretches beyond end,
@@ -491,7 +480,7 @@ set_cache_region (struct region_cache *c,
491 args to pass are the same before and after such an operation.) */ 480 args to pass are the same before and after such an operation.) */
492void 481void
493invalidate_region_cache (struct buffer *buf, struct region_cache *c, 482invalidate_region_cache (struct buffer *buf, struct region_cache *c,
494 EMACS_INT head, EMACS_INT tail) 483 ptrdiff_t head, ptrdiff_t tail)
495{ 484{
496 /* Let chead = c->beg_unchanged, and 485 /* Let chead = c->beg_unchanged, and
497 ctail = c->end_unchanged. 486 ctail = c->end_unchanged.
@@ -629,7 +618,7 @@ revalidate_region_cache (struct buffer *buf, struct region_cache *c)
629 corresponds to the modified region of the buffer. */ 618 corresponds to the modified region of the buffer. */
630 else 619 else
631 { 620 {
632 EMACS_INT modified_ix; 621 ptrdiff_t modified_ix;
633 622
634 /* These positions are correct, relative to both the cache basis 623 /* These positions are correct, relative to both the cache basis
635 and the buffer basis. */ 624 and the buffer basis. */
@@ -698,7 +687,7 @@ revalidate_region_cache (struct buffer *buf, struct region_cache *c)
698 no newlines", in the case of the line cache). */ 687 no newlines", in the case of the line cache). */
699void 688void
700know_region_cache (struct buffer *buf, struct region_cache *c, 689know_region_cache (struct buffer *buf, struct region_cache *c,
701 EMACS_INT start, EMACS_INT end) 690 ptrdiff_t start, ptrdiff_t end)
702{ 691{
703 revalidate_region_cache (buf, c); 692 revalidate_region_cache (buf, c);
704 693
@@ -713,14 +702,14 @@ know_region_cache (struct buffer *buf, struct region_cache *c,
713 position after POS where the knownness changes. */ 702 position after POS where the knownness changes. */
714int 703int
715region_cache_forward (struct buffer *buf, struct region_cache *c, 704region_cache_forward (struct buffer *buf, struct region_cache *c,
716 EMACS_INT pos, EMACS_INT *next) 705 ptrdiff_t pos, ptrdiff_t *next)
717{ 706{
718 revalidate_region_cache (buf, c); 707 revalidate_region_cache (buf, c);
719 708
720 { 709 {
721 EMACS_INT i = find_cache_boundary (c, pos); 710 ptrdiff_t i = find_cache_boundary (c, pos);
722 int i_value = BOUNDARY_VALUE (c, i); 711 int i_value = BOUNDARY_VALUE (c, i);
723 EMACS_INT j; 712 ptrdiff_t j;
724 713
725 /* Beyond the end of the buffer is unknown, by definition. */ 714 /* Beyond the end of the buffer is unknown, by definition. */
726 if (pos >= BUF_Z (buf)) 715 if (pos >= BUF_Z (buf))
@@ -749,7 +738,7 @@ region_cache_forward (struct buffer *buf, struct region_cache *c,
749 the purposes of CACHE. If NEXT is non-zero, set *NEXT to the nearest 738 the purposes of CACHE. If NEXT is non-zero, set *NEXT to the nearest
750 position before POS where the knownness changes. */ 739 position before POS where the knownness changes. */
751int region_cache_backward (struct buffer *buf, struct region_cache *c, 740int region_cache_backward (struct buffer *buf, struct region_cache *c,
752 EMACS_INT pos, EMACS_INT *next) 741 ptrdiff_t pos, ptrdiff_t *next)
753{ 742{
754 revalidate_region_cache (buf, c); 743 revalidate_region_cache (buf, c);
755 744
@@ -762,9 +751,9 @@ int region_cache_backward (struct buffer *buf, struct region_cache *c,
762 } 751 }
763 752
764 { 753 {
765 EMACS_INT i = find_cache_boundary (c, pos - 1); 754 ptrdiff_t i = find_cache_boundary (c, pos - 1);
766 int i_value = BOUNDARY_VALUE (c, i); 755 int i_value = BOUNDARY_VALUE (c, i);
767 EMACS_INT j; 756 ptrdiff_t j;
768 757
769 if (next) 758 if (next)
770 { 759 {
@@ -790,18 +779,18 @@ void pp_cache (struct region_cache *) EXTERNALLY_VISIBLE;
790void 779void
791pp_cache (struct region_cache *c) 780pp_cache (struct region_cache *c)
792{ 781{
793 int i; 782 ptrdiff_t i;
794 EMACS_INT beg_u = c->buffer_beg + c->beg_unchanged; 783 ptrdiff_t beg_u = c->buffer_beg + c->beg_unchanged;
795 EMACS_INT end_u = c->buffer_end - c->end_unchanged; 784 ptrdiff_t end_u = c->buffer_end - c->end_unchanged;
796 785
797 fprintf (stderr, 786 fprintf (stderr,
798 "basis: %"pI"d..%"pI"d modified: %"pI"d..%"pI"d\n", 787 "basis: %"pD"d..%"pD"d modified: %"pD"d..%"pD"d\n",
799 c->buffer_beg, c->buffer_end, 788 c->buffer_beg, c->buffer_end,
800 beg_u, end_u); 789 beg_u, end_u);
801 790
802 for (i = 0; i < c->cache_len; i++) 791 for (i = 0; i < c->cache_len; i++)
803 { 792 {
804 EMACS_INT pos = BOUNDARY_POS (c, i); 793 ptrdiff_t pos = BOUNDARY_POS (c, i);
805 794
806 putc (((pos < beg_u) ? 'v' 795 putc (((pos < beg_u) ? 'v'
807 : (pos == beg_u) ? '-' 796 : (pos == beg_u) ? '-'
@@ -811,6 +800,6 @@ pp_cache (struct region_cache *c)
811 : (pos == end_u) ? '-' 800 : (pos == end_u) ? '-'
812 : ' '), 801 : ' '),
813 stderr); 802 stderr);
814 fprintf (stderr, "%"pI"d : %d\n", pos, BOUNDARY_VALUE (c, i)); 803 fprintf (stderr, "%"pD"d : %d\n", pos, BOUNDARY_VALUE (c, i));
815 } 804 }
816} 805}
diff --git a/src/region-cache.h b/src/region-cache.h
index ea767ed0dc3..8e1be716776 100644
--- a/src/region-cache.h
+++ b/src/region-cache.h
@@ -72,7 +72,7 @@ void free_region_cache (struct region_cache *);
72 no newlines", in the case of the line cache). */ 72 no newlines", in the case of the line cache). */
73extern void know_region_cache (struct buffer *BUF, 73extern void know_region_cache (struct buffer *BUF,
74 struct region_cache *CACHE, 74 struct region_cache *CACHE,
75 EMACS_INT START, EMACS_INT END); 75 ptrdiff_t START, ptrdiff_t END);
76 76
77/* Indicate that a section of BUF has changed, to invalidate CACHE. 77/* Indicate that a section of BUF has changed, to invalidate CACHE.
78 HEAD is the number of chars unchanged at the beginning of the buffer. 78 HEAD is the number of chars unchanged at the beginning of the buffer.
@@ -84,7 +84,7 @@ extern void know_region_cache (struct buffer *BUF,
84 args to pass are the same before and after such an operation.) */ 84 args to pass are the same before and after such an operation.) */
85extern void invalidate_region_cache (struct buffer *BUF, 85extern void invalidate_region_cache (struct buffer *BUF,
86 struct region_cache *CACHE, 86 struct region_cache *CACHE,
87 EMACS_INT HEAD, EMACS_INT TAIL); 87 ptrdiff_t HEAD, ptrdiff_t TAIL);
88 88
89/* The scanning functions. 89/* The scanning functions.
90 90
@@ -100,13 +100,13 @@ extern void invalidate_region_cache (struct buffer *BUF,
100 position after POS where the knownness changes. */ 100 position after POS where the knownness changes. */
101extern int region_cache_forward (struct buffer *BUF, 101extern int region_cache_forward (struct buffer *BUF,
102 struct region_cache *CACHE, 102 struct region_cache *CACHE,
103 EMACS_INT POS, 103 ptrdiff_t POS,
104 EMACS_INT *NEXT); 104 ptrdiff_t *NEXT);
105 105
106/* Return true if the text immediately before POS in BUF is known, for 106/* Return true if the text immediately before POS in BUF is known, for
107 the purposes of CACHE. If NEXT is non-zero, set *NEXT to the nearest 107 the purposes of CACHE. If NEXT is non-zero, set *NEXT to the nearest
108 position before POS where the knownness changes. */ 108 position before POS where the knownness changes. */
109extern int region_cache_backward (struct buffer *BUF, 109extern int region_cache_backward (struct buffer *BUF,
110 struct region_cache *CACHE, 110 struct region_cache *CACHE,
111 EMACS_INT POS, 111 ptrdiff_t POS,
112 EMACS_INT *NEXT); 112 ptrdiff_t *NEXT);
diff --git a/src/scroll.c b/src/scroll.c
index 9184919f0ce..05f6fdf85f0 100644
--- a/src/scroll.c
+++ b/src/scroll.c
@@ -969,21 +969,14 @@ do_line_insertion_deletion_costs (FRAME_PTR frame,
969 const char *cleanup_string, 969 const char *cleanup_string,
970 int coefficient) 970 int coefficient)
971{ 971{
972 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (int) < FRAME_LINES (frame))
973 memory_full (SIZE_MAX);
974
975 FRAME_INSERT_COST (frame) = 972 FRAME_INSERT_COST (frame) =
976 (int *) xrealloc (FRAME_INSERT_COST (frame), 973 xnrealloc (FRAME_INSERT_COST (frame), FRAME_LINES (frame), sizeof (int));
977 FRAME_LINES (frame) * sizeof (int));
978 FRAME_DELETEN_COST (frame) = 974 FRAME_DELETEN_COST (frame) =
979 (int *) xrealloc (FRAME_DELETEN_COST (frame), 975 xnrealloc (FRAME_DELETEN_COST (frame), FRAME_LINES (frame), sizeof (int));
980 FRAME_LINES (frame) * sizeof (int));
981 FRAME_INSERTN_COST (frame) = 976 FRAME_INSERTN_COST (frame) =
982 (int *) xrealloc (FRAME_INSERTN_COST (frame), 977 xnrealloc (FRAME_INSERTN_COST (frame), FRAME_LINES (frame), sizeof (int));
983 FRAME_LINES (frame) * sizeof (int));
984 FRAME_DELETE_COST (frame) = 978 FRAME_DELETE_COST (frame) =
985 (int *) xrealloc (FRAME_DELETE_COST (frame), 979 xnrealloc (FRAME_DELETE_COST (frame), FRAME_LINES (frame), sizeof (int));
986 FRAME_LINES (frame) * sizeof (int));
987 980
988 ins_del_costs (frame, 981 ins_del_costs (frame,
989 ins_line_string, multi_ins_string, 982 ins_line_string, multi_ins_string,
diff --git a/src/search.c b/src/search.c
index 79ef8b046df..d892792cbaa 100644
--- a/src/search.c
+++ b/src/search.c
@@ -683,7 +683,7 @@ scan_buffer (register int target, EMACS_INT start, EMACS_INT end,
683 to see where we can avoid some scanning. */ 683 to see where we can avoid some scanning. */
684 if (target == '\n' && newline_cache) 684 if (target == '\n' && newline_cache)
685 { 685 {
686 EMACS_INT next_change; 686 ptrdiff_t next_change;
687 immediate_quit = 0; 687 immediate_quit = 0;
688 while (region_cache_forward 688 while (region_cache_forward
689 (current_buffer, newline_cache, start_byte, &next_change)) 689 (current_buffer, newline_cache, start_byte, &next_change))
@@ -755,7 +755,7 @@ scan_buffer (register int target, EMACS_INT start, EMACS_INT end,
755 /* Consult the newline cache, if appropriate. */ 755 /* Consult the newline cache, if appropriate. */
756 if (target == '\n' && newline_cache) 756 if (target == '\n' && newline_cache)
757 { 757 {
758 EMACS_INT next_change; 758 ptrdiff_t next_change;
759 immediate_quit = 0; 759 immediate_quit = 0;
760 while (region_cache_backward 760 while (region_cache_backward
761 (current_buffer, newline_cache, start_byte, &next_change)) 761 (current_buffer, newline_cache, start_byte, &next_change))
@@ -2640,17 +2640,17 @@ since only regular expressions have distinguished subexpressions. */)
2640 perform substitution on the replacement string. */ 2640 perform substitution on the replacement string. */
2641 if (NILP (literal)) 2641 if (NILP (literal))
2642 { 2642 {
2643 EMACS_INT length = SBYTES (newtext); 2643 ptrdiff_t length = SBYTES (newtext);
2644 unsigned char *substed; 2644 unsigned char *substed;
2645 EMACS_INT substed_alloc_size, substed_len; 2645 ptrdiff_t substed_alloc_size, substed_len;
2646 int buf_multibyte = !NILP (BVAR (current_buffer, enable_multibyte_characters)); 2646 int buf_multibyte = !NILP (BVAR (current_buffer, enable_multibyte_characters));
2647 int str_multibyte = STRING_MULTIBYTE (newtext); 2647 int str_multibyte = STRING_MULTIBYTE (newtext);
2648 int really_changed = 0; 2648 int really_changed = 0;
2649 2649
2650 substed_alloc_size = length * 2 + 100; 2650 substed_alloc_size = ((STRING_BYTES_BOUND - 100) / 2 < length
2651 if (min (PTRDIFF_MAX, SIZE_MAX) - 1 < substed_alloc_size) 2651 ? STRING_BYTES_BOUND
2652 memory_full (SIZE_MAX); 2652 : length * 2 + 100);
2653 substed = (unsigned char *) xmalloc (substed_alloc_size + 1); 2653 substed = (unsigned char *) xmalloc (substed_alloc_size);
2654 substed_len = 0; 2654 substed_len = 0;
2655 2655
2656 /* Go thru NEWTEXT, producing the actual text to insert in 2656 /* Go thru NEWTEXT, producing the actual text to insert in
@@ -2661,7 +2661,7 @@ since only regular expressions have distinguished subexpressions. */)
2661 { 2661 {
2662 unsigned char str[MAX_MULTIBYTE_LENGTH]; 2662 unsigned char str[MAX_MULTIBYTE_LENGTH];
2663 const unsigned char *add_stuff = NULL; 2663 const unsigned char *add_stuff = NULL;
2664 EMACS_INT add_len = 0; 2664 ptrdiff_t add_len = 0;
2665 int idx = -1; 2665 int idx = -1;
2666 2666
2667 if (str_multibyte) 2667 if (str_multibyte)
@@ -2725,7 +2725,7 @@ since only regular expressions have distinguished subexpressions. */)
2725 set up ADD_STUFF and ADD_LEN to point to it. */ 2725 set up ADD_STUFF and ADD_LEN to point to it. */
2726 if (idx >= 0) 2726 if (idx >= 0)
2727 { 2727 {
2728 EMACS_INT begbyte = CHAR_TO_BYTE (search_regs.start[idx]); 2728 ptrdiff_t begbyte = CHAR_TO_BYTE (search_regs.start[idx]);
2729 add_len = CHAR_TO_BYTE (search_regs.end[idx]) - begbyte; 2729 add_len = CHAR_TO_BYTE (search_regs.end[idx]) - begbyte;
2730 if (search_regs.start[idx] < GPT && GPT < search_regs.end[idx]) 2730 if (search_regs.start[idx] < GPT && GPT < search_regs.end[idx])
2731 move_gap (search_regs.start[idx]); 2731 move_gap (search_regs.start[idx]);
@@ -2736,19 +2736,11 @@ since only regular expressions have distinguished subexpressions. */)
2736 is invariably ADD_LEN bytes starting at ADD_STUFF. */ 2736 is invariably ADD_LEN bytes starting at ADD_STUFF. */
2737 2737
2738 /* Make sure SUBSTED is big enough. */ 2738 /* Make sure SUBSTED is big enough. */
2739 if (substed_len + add_len >= substed_alloc_size) 2739 if (substed_alloc_size - substed_len < add_len)
2740 { 2740 substed =
2741 ptrdiff_t add_len_max = 2741 xpalloc (substed, &substed_alloc_size,
2742 min (PTRDIFF_MAX, SIZE_MAX) - 1 - 500 - substed_len; 2742 add_len - (substed_alloc_size - substed_len),
2743 if (add_len_max < add_len) 2743 STRING_BYTES_BOUND, 1);
2744 {
2745 xfree (substed);
2746 memory_full (SIZE_MAX);
2747 }
2748 substed_alloc_size = substed_len + add_len + 500;
2749 substed = (unsigned char *) xrealloc (substed,
2750 substed_alloc_size + 1);
2751 }
2752 2744
2753 /* Now add to the end of SUBSTED. */ 2745 /* Now add to the end of SUBSTED. */
2754 if (add_stuff) 2746 if (add_stuff)
@@ -3000,30 +2992,17 @@ If optional arg RESEAT is non-nil, make markers on LIST point nowhere. */)
3000 2992
3001 if (length > search_regs.num_regs) 2993 if (length > search_regs.num_regs)
3002 { 2994 {
3003 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (regoff_t) < length) 2995 ptrdiff_t num_regs = search_regs.num_regs;
3004 memory_full (SIZE_MAX); 2996 search_regs.start =
3005 2997 xpalloc (search_regs.start, &num_regs, length - num_regs,
3006 if (search_regs.num_regs == 0) 2998 min (PTRDIFF_MAX, UINT_MAX), sizeof (regoff_t));
3007 { 2999 search_regs.end =
3008 search_regs.start 3000 xrealloc (search_regs.end, num_regs * sizeof (regoff_t));
3009 = (regoff_t *) xmalloc (length * sizeof (regoff_t)); 3001
3010 search_regs.end 3002 for (i = search_regs.num_regs; i < num_regs; i++)
3011 = (regoff_t *) xmalloc (length * sizeof (regoff_t));
3012 }
3013 else
3014 {
3015 search_regs.start
3016 = (regoff_t *) xrealloc (search_regs.start,
3017 length * sizeof (regoff_t));
3018 search_regs.end
3019 = (regoff_t *) xrealloc (search_regs.end,
3020 length * sizeof (regoff_t));
3021 }
3022
3023 for (i = search_regs.num_regs; i < length; i++)
3024 search_regs.start[i] = -1; 3003 search_regs.start[i] = -1;
3025 3004
3026 search_regs.num_regs = length; 3005 search_regs.num_regs = num_regs;
3027 } 3006 }
3028 3007
3029 for (i = 0; CONSP (list); i++) 3008 for (i = 0; CONSP (list); i++)
diff --git a/src/term.c b/src/term.c
index bc6fa8f80f9..f3bf3a947cb 100644
--- a/src/term.c
+++ b/src/term.c
@@ -551,12 +551,10 @@ encode_terminal_code (struct glyph *src, int src_len, struct coding_system *codi
551 551
552 if (encode_terminal_src_size - nbytes < required) 552 if (encode_terminal_src_size - nbytes < required)
553 { 553 {
554 ptrdiff_t size; 554 encode_terminal_src =
555 if (min (PTRDIFF_MAX, SIZE_MAX) - nbytes < required) 555 xpalloc (encode_terminal_src, &encode_terminal_src_size,
556 memory_full (SIZE_MAX); 556 required - (encode_terminal_src_size - nbytes),
557 size = nbytes + required; 557 -1, 1);
558 encode_terminal_src = xrealloc (encode_terminal_src, size);
559 encode_terminal_src_size = size;
560 buf = encode_terminal_src + nbytes; 558 buf = encode_terminal_src + nbytes;
561 } 559 }
562 560
@@ -629,13 +627,9 @@ encode_terminal_code (struct glyph *src, int src_len, struct coding_system *codi
629 nbytes = buf - encode_terminal_src; 627 nbytes = buf - encode_terminal_src;
630 if (encode_terminal_src_size - nbytes < MAX_MULTIBYTE_LENGTH) 628 if (encode_terminal_src_size - nbytes < MAX_MULTIBYTE_LENGTH)
631 { 629 {
632 ptrdiff_t size; 630 encode_terminal_src =
633 if (min (PTRDIFF_MAX, SIZE_MAX) - MAX_MULTIBYTE_LENGTH 631 xpalloc (encode_terminal_src, &encode_terminal_src_size,
634 < nbytes) 632 MAX_MULTIBYTE_LENGTH, -1, 1);
635 memory_full (SIZE_MAX);
636 size = nbytes + MAX_MULTIBYTE_LENGTH;
637 encode_terminal_src = xrealloc (encode_terminal_src, size);
638 encode_terminal_src_size = size;
639 buf = encode_terminal_src + nbytes; 633 buf = encode_terminal_src + nbytes;
640 } 634 }
641 if (CHAR_BYTE8_P (c) 635 if (CHAR_BYTE8_P (c)
@@ -665,12 +659,11 @@ encode_terminal_code (struct glyph *src, int src_len, struct coding_system *codi
665 nbytes = buf - encode_terminal_src; 659 nbytes = buf - encode_terminal_src;
666 if (encode_terminal_src_size - nbytes < SBYTES (string)) 660 if (encode_terminal_src_size - nbytes < SBYTES (string))
667 { 661 {
668 ptrdiff_t size; 662 encode_terminal_src =
669 if (min (PTRDIFF_MAX, SIZE_MAX) - SBYTES (string) < nbytes) 663 xpalloc (encode_terminal_src, &encode_terminal_src_size,
670 memory_full (SIZE_MAX); 664 (SBYTES (string)
671 size = nbytes + SBYTES (string); 665 - (encode_terminal_src_size - nbytes)),
672 encode_terminal_src = xrealloc (encode_terminal_src, size); 666 -1, 1);
673 encode_terminal_src_size = size;
674 buf = encode_terminal_src + nbytes; 667 buf = encode_terminal_src + nbytes;
675 } 668 }
676 memcpy (buf, SDATA (string), SBYTES (string)); 669 memcpy (buf, SDATA (string), SBYTES (string));
@@ -1161,16 +1154,16 @@ calculate_costs (struct frame *frame)
1161 X turns off char_ins_del_ok. */ 1154 X turns off char_ins_del_ok. */
1162 1155
1163 max_frame_cols = max (max_frame_cols, FRAME_COLS (frame)); 1156 max_frame_cols = max (max_frame_cols, FRAME_COLS (frame));
1164 if ((min (PTRDIFF_MAX, SIZE_MAX) / sizeof (int) - 1) / 2 < max_frame_cols) 1157 if ((min (PTRDIFF_MAX, SIZE_MAX) / sizeof (int) - 1) / 2
1158 < max_frame_cols)
1165 memory_full (SIZE_MAX); 1159 memory_full (SIZE_MAX);
1166 1160
1167 char_ins_del_vector 1161 char_ins_del_vector =
1168 = (int *) xrealloc (char_ins_del_vector, 1162 xrealloc (char_ins_del_vector,
1169 (sizeof (int) 1163 (sizeof (int) + 2 * sizeof (int) * max_frame_cols));
1170 + 2 * max_frame_cols * sizeof (int)));
1171 1164
1172 memset (char_ins_del_vector, 0, 1165 memset (char_ins_del_vector, 0,
1173 (sizeof (int) + 2 * max_frame_cols * sizeof (int))); 1166 (sizeof (int) + 2 * sizeof (int) * max_frame_cols));
1174 1167
1175 1168
1176 if (f && (!tty->TS_ins_line && !tty->TS_del_line)) 1169 if (f && (!tty->TS_ins_line && !tty->TS_del_line))
diff --git a/src/termcap.c b/src/termcap.c
index 791c593c06f..6f24817fa72 100644
--- a/src/termcap.c
+++ b/src/termcap.c
@@ -637,13 +637,10 @@ gobble_line (int fd, register struct termcap_buffer *bufp, char *append_end)
637 { 637 {
638 ptrdiff_t ptr_offset = bufp->ptr - buf; 638 ptrdiff_t ptr_offset = bufp->ptr - buf;
639 ptrdiff_t append_end_offset = append_end - buf; 639 ptrdiff_t append_end_offset = append_end - buf;
640 ptrdiff_t size;
641 if ((min (PTRDIFF_MAX, SIZE_MAX) - 1) / 2 < bufp->size)
642 memory_full (SIZE_MAX);
643 size = 2 * bufp->size;
644 /* Add 1 to size to ensure room for terminating null. */ 640 /* Add 1 to size to ensure room for terminating null. */
645 bufp->beg = buf = (char *) xrealloc (buf, size + 1); 641 ptrdiff_t size = bufp->size + 1;
646 bufp->size = size; 642 bufp->beg = buf = xpalloc (buf, &size, 1, -1, 1);
643 bufp->size = size - 1;
647 bufp->ptr = buf + ptr_offset; 644 bufp->ptr = buf + ptr_offset;
648 append_end = buf + append_end_offset; 645 append_end = buf + append_end_offset;
649 } 646 }
diff --git a/src/tparam.c b/src/tparam.c
index 06cec873153..ac21667d65b 100644
--- a/src/tparam.c
+++ b/src/tparam.c
@@ -101,18 +101,13 @@ tparam1 (const char *string, char *outstring, int len,
101 101
102 if (outlen == 0) 102 if (outlen == 0)
103 { 103 {
104 if (min (PTRDIFF_MAX, SIZE_MAX) - 40 < len)
105 goto out_of_memory;
106 outlen = len + 40; 104 outlen = len + 40;
107 new = (char *) xmalloc (outlen); 105 new = (char *) xmalloc (outlen);
108 memcpy (new, outstring, offset); 106 memcpy (new, outstring, offset);
109 } 107 }
110 else 108 else
111 { 109 {
112 if (min (PTRDIFF_MAX, SIZE_MAX) / 2 < outlen) 110 new = xpalloc (outstring, &outlen, 1, -1, 1);
113 goto out_of_memory;
114 outlen *= 2;
115 new = (char *) xrealloc (outstring, outlen);
116 } 111 }
117 112
118 op = new + offset; 113 op = new + offset;
@@ -178,12 +173,8 @@ tparam1 (const char *string, char *outstring, int len,
178 doup++, append_len_incr = strlen (up); 173 doup++, append_len_incr = strlen (up);
179 else 174 else
180 doleft++, append_len_incr = strlen (left); 175 doleft++, append_len_incr = strlen (left);
181 if (PTRDIFF_MAX - append_len < append_len_incr) 176 if (INT_ADD_OVERFLOW (append_len, append_len_incr))
182 { 177 memory_full (SIZE_MAX);
183 out_of_memory:
184 xfree (new);
185 memory_full (SIZE_MAX);
186 }
187 append_len += append_len_incr; 178 append_len += append_len_incr;
188 } 179 }
189 } 180 }
@@ -286,7 +277,7 @@ main (int argc, char **argv)
286 args[0] = atoi (argv[2]); 277 args[0] = atoi (argv[2]);
287 args[1] = atoi (argv[3]); 278 args[1] = atoi (argv[3]);
288 args[2] = atoi (argv[4]); 279 args[2] = atoi (argv[4]);
289 tparam1 (argv[1], buf, "LEFT", "UP", args); 280 tparam1 (argv[1], buf, 50, "LEFT", "UP", args);
290 printf ("%s\n", buf); 281 printf ("%s\n", buf);
291 return 0; 282 return 0;
292} 283}
diff --git a/src/xdisp.c b/src/xdisp.c
index d44e677eeb7..b64a2c0cf6c 100644
--- a/src/xdisp.c
+++ b/src/xdisp.c
@@ -10384,17 +10384,14 @@ static void
10384store_mode_line_noprop_char (char c) 10384store_mode_line_noprop_char (char c)
10385{ 10385{
10386 /* If output position has reached the end of the allocated buffer, 10386 /* If output position has reached the end of the allocated buffer,
10387 double the buffer's size. */ 10387 increase the buffer's size. */
10388 if (mode_line_noprop_ptr == mode_line_noprop_buf_end) 10388 if (mode_line_noprop_ptr == mode_line_noprop_buf_end)
10389 { 10389 {
10390 ptrdiff_t len = MODE_LINE_NOPROP_LEN (0); 10390 ptrdiff_t len = MODE_LINE_NOPROP_LEN (0);
10391 ptrdiff_t new_size; 10391 ptrdiff_t size = len;
10392 10392 mode_line_noprop_buf =
10393 if (STRING_BYTES_BOUND / 2 < len) 10393 xpalloc (mode_line_noprop_buf, &size, 1, STRING_BYTES_BOUND, 1);
10394 memory_full (SIZE_MAX); 10394 mode_line_noprop_buf_end = mode_line_noprop_buf + size;
10395 new_size = 2 * len;
10396 mode_line_noprop_buf = (char *) xrealloc (mode_line_noprop_buf, new_size);
10397 mode_line_noprop_buf_end = mode_line_noprop_buf + new_size;
10398 mode_line_noprop_ptr = mode_line_noprop_buf + len; 10395 mode_line_noprop_ptr = mode_line_noprop_buf + len;
10399 } 10396 }
10400 10397
diff --git a/src/xfaces.c b/src/xfaces.c
index 352fdb4b082..53b30a5c1c2 100644
--- a/src/xfaces.c
+++ b/src/xfaces.c
@@ -403,7 +403,7 @@ static int next_lface_id;
403/* A vector mapping Lisp face Id's to face names. */ 403/* A vector mapping Lisp face Id's to face names. */
404 404
405static Lisp_Object *lface_id_to_name; 405static Lisp_Object *lface_id_to_name;
406static int lface_id_to_name_size; 406static ptrdiff_t lface_id_to_name_size;
407 407
408/* TTY color-related functions (defined in tty-colors.el). */ 408/* TTY color-related functions (defined in tty-colors.el). */
409 409
@@ -2667,17 +2667,10 @@ Value is a vector of face attributes. */)
2667 The mapping from Lisp face to Lisp face id is given by the 2667 The mapping from Lisp face to Lisp face id is given by the
2668 property `face' of the Lisp face name. */ 2668 property `face' of the Lisp face name. */
2669 if (next_lface_id == lface_id_to_name_size) 2669 if (next_lface_id == lface_id_to_name_size)
2670 { 2670 lface_id_to_name =
2671 ptrdiff_t new_size, sz; 2671 xpalloc (lface_id_to_name, &lface_id_to_name_size, 1,
2672 if (min (min (PTRDIFF_MAX, SIZE_MAX) / 2 / sizeof *lface_id_to_name, 2672 min (INT_MAX, MOST_POSITIVE_FIXNUM),
2673 MOST_POSITIVE_FIXNUM) 2673 sizeof *lface_id_to_name);
2674 < lface_id_to_name_size)
2675 memory_full (SIZE_MAX);
2676 new_size = max (50, 2 * lface_id_to_name_size);
2677 sz = new_size * sizeof *lface_id_to_name;
2678 lface_id_to_name = (Lisp_Object *) xrealloc (lface_id_to_name, sz);
2679 lface_id_to_name_size = new_size;
2680 }
2681 2674
2682 lface_id_to_name[next_lface_id] = face; 2675 lface_id_to_name[next_lface_id] = face;
2683 Fput (face, Qface, make_number (next_lface_id)); 2676 Fput (face, Qface, make_number (next_lface_id));
@@ -4415,18 +4408,8 @@ cache_face (struct face_cache *c, struct face *face, unsigned int hash)
4415 if (i == c->used) 4408 if (i == c->used)
4416 { 4409 {
4417 if (c->used == c->size) 4410 if (c->used == c->size)
4418 { 4411 c->faces_by_id = xpalloc (c->faces_by_id, &c->size, 1, MAX_FACE_ID,
4419 int new_size, sz; 4412 sizeof *c->faces_by_id);
4420 new_size =
4421 min (2 * c->size,
4422 min (MAX_FACE_ID,
4423 min (PTRDIFF_MAX, SIZE_MAX) / sizeof *c->faces_by_id));
4424 if (new_size == c->size)
4425 abort (); /* Alternatives? ++kfs */
4426 sz = new_size * sizeof *c->faces_by_id;
4427 c->faces_by_id = (struct face **) xrealloc (c->faces_by_id, sz);
4428 c->size = new_size;
4429 }
4430 c->used++; 4413 c->used++;
4431 } 4414 }
4432 4415
diff --git a/src/xfns.c b/src/xfns.c
index 1169acb3cf5..9a3d5fcda83 100644
--- a/src/xfns.c
+++ b/src/xfns.c
@@ -1490,10 +1490,8 @@ x_encode_text (Lisp_Object string, Lisp_Object coding_system, int selectionp,
1490 coding.mode |= (CODING_MODE_SAFE_ENCODING | CODING_MODE_LAST_BLOCK); 1490 coding.mode |= (CODING_MODE_SAFE_ENCODING | CODING_MODE_LAST_BLOCK);
1491 /* We suppress producing escape sequences for composition. */ 1491 /* We suppress producing escape sequences for composition. */
1492 coding.common_flags &= ~CODING_ANNOTATION_MASK; 1492 coding.common_flags &= ~CODING_ANNOTATION_MASK;
1493 if (min (PTRDIFF_MAX, SIZE_MAX) / 2 < SCHARS (string)) 1493 coding.destination = xnmalloc (SCHARS (string), 2);
1494 memory_full (SIZE_MAX);
1495 coding.dst_bytes = SCHARS (string) * 2; 1494 coding.dst_bytes = SCHARS (string) * 2;
1496 coding.destination = (unsigned char *) xmalloc (coding.dst_bytes);
1497 encode_coding_object (&coding, string, 0, 0, 1495 encode_coding_object (&coding, string, 0, 0,
1498 SCHARS (string), SBYTES (string), Qnil); 1496 SCHARS (string), SBYTES (string), Qnil);
1499 *text_bytes = coding.produced; 1497 *text_bytes = coding.produced;
@@ -4214,9 +4212,7 @@ FRAME. Default is to change on the edit X window. */)
4214 This applies even if long is more than 32 bits. The X library 4212 This applies even if long is more than 32 bits. The X library
4215 converts to 32 bits before sending to the X server. */ 4213 converts to 32 bits before sending to the X server. */
4216 elsize = element_format == 32 ? sizeof (long) : element_format >> 3; 4214 elsize = element_format == 32 ? sizeof (long) : element_format >> 3;
4217 if (min (PTRDIFF_MAX, SIZE_MAX) / elsize < nelements) 4215 data = xnmalloc (nelements, elsize);
4218 memory_full (SIZE_MAX);
4219 data = (unsigned char *) xmalloc (nelements * elsize);
4220 4216
4221 x_fill_property_data (FRAME_X_DISPLAY (f), value, data, element_format); 4217 x_fill_property_data (FRAME_X_DISPLAY (f), value, data, element_format);
4222 } 4218 }
diff --git a/src/xgselect.c b/src/xgselect.c
index d1844610077..339ec475117 100644
--- a/src/xgselect.c
+++ b/src/xgselect.c
@@ -29,7 +29,7 @@ along with GNU Emacs. If not, see <http§://www.gnu.org/licenses/>. */
29#include <setjmp.h> 29#include <setjmp.h>
30 30
31static GPollFD *gfds; 31static GPollFD *gfds;
32static int gfds_size; 32static ptrdiff_t gfds_size;
33 33
34int 34int
35xg_select (int max_fds, SELECT_TYPE *rfds, SELECT_TYPE *wfds, SELECT_TYPE *efds, 35xg_select (int max_fds, SELECT_TYPE *rfds, SELECT_TYPE *wfds, SELECT_TYPE *efds,
@@ -54,16 +54,9 @@ xg_select (int max_fds, SELECT_TYPE *rfds, SELECT_TYPE *wfds, SELECT_TYPE *efds,
54 do { 54 do {
55 if (n_gfds > gfds_size) 55 if (n_gfds > gfds_size)
56 { 56 {
57 int gfds_size_max =
58 min (INT_MAX, min (PTRDIFF_MAX, SIZE_MAX) / sizeof *gfds);
59 int size;
60 if (gfds_size_max / 2 < n_gfds)
61 memory_full (SIZE_MAX);
62 size = 2 * n_gfds;
63 gfds_size = 0;
64 xfree (gfds); 57 xfree (gfds);
65 gfds = xmalloc (sizeof *gfds * size); 58 gfds = xpalloc (0, &gfds_size, n_gfds - gfds_size, INT_MAX,
66 gfds_size = size; 59 sizeof *gfds);
67 } 60 }
68 61
69 n_gfds = g_main_context_query (context, 62 n_gfds = g_main_context_query (context,
diff --git a/src/xrdb.c b/src/xrdb.c
index 7c2cd586b09..63f06738b98 100644
--- a/src/xrdb.c
+++ b/src/xrdb.c
@@ -204,10 +204,7 @@ magic_file_p (const char *string, EMACS_INT string_len, const char *class,
204 if (path_size - path_len <= next_len) 204 if (path_size - path_len <= next_len)
205 { 205 {
206 if (min (PTRDIFF_MAX, SIZE_MAX) / 2 - 1 - path_len < next_len) 206 if (min (PTRDIFF_MAX, SIZE_MAX) / 2 - 1 - path_len < next_len)
207 { 207 memory_full (SIZE_MAX);
208 xfree (path);
209 memory_full (SIZE_MAX);
210 }
211 path_size = (path_len + next_len + 1) * 2; 208 path_size = (path_len + next_len + 1) * 2;
212 path = (char *) xrealloc (path, path_size); 209 path = (char *) xrealloc (path, path_size);
213 } 210 }
diff --git a/src/xselect.c b/src/xselect.c
index d8b7b077a8c..5c2e12c5ef1 100644
--- a/src/xselect.c
+++ b/src/xselect.c
@@ -1503,17 +1503,9 @@ receive_incremental_selection (Display *display, Window window, Atom property,
1503 UNBLOCK_INPUT; 1503 UNBLOCK_INPUT;
1504 1504
1505 if (*size_bytes_ret - offset < tmp_size_bytes) 1505 if (*size_bytes_ret - offset < tmp_size_bytes)
1506 { 1506 *data_ret = xpalloc (*data_ret, size_bytes_ret,
1507 ptrdiff_t size; 1507 tmp_size_bytes - (*size_bytes_ret - offset),
1508 if (min (PTRDIFF_MAX, SIZE_MAX) - offset < tmp_size_bytes) 1508 -1, 1);
1509 {
1510 xfree (tmp_data);
1511 memory_full (SIZE_MAX);
1512 }
1513 size = offset + tmp_size_bytes;
1514 *data_ret = (unsigned char *) xrealloc (*data_ret, size);
1515 *size_bytes_ret = size;
1516 }
1517 1509
1518 memcpy ((*data_ret) + offset, tmp_data, tmp_size_bytes); 1510 memcpy ((*data_ret) + offset, tmp_data, tmp_size_bytes);
1519 offset += tmp_size_bytes; 1511 offset += tmp_size_bytes;
@@ -1806,14 +1798,12 @@ lisp_data_to_selection_data (Display *display, Lisp_Object obj,
1806 if (SYMBOLP (XVECTOR (obj)->contents [0])) 1798 if (SYMBOLP (XVECTOR (obj)->contents [0]))
1807 /* This vector is an ATOM set */ 1799 /* This vector is an ATOM set */
1808 { 1800 {
1809 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (Atom) < size)
1810 memory_full (SIZE_MAX);
1811 if (NILP (type)) type = QATOM; 1801 if (NILP (type)) type = QATOM;
1812 for (i = 0; i < size; i++) 1802 for (i = 0; i < size; i++)
1813 if (!SYMBOLP (XVECTOR (obj)->contents [i])) 1803 if (!SYMBOLP (XVECTOR (obj)->contents [i]))
1814 signal_error ("All elements of selection vector must have same type", obj); 1804 signal_error ("All elements of selection vector must have same type", obj);
1815 1805
1816 *data_ret = (unsigned char *) xmalloc (size * sizeof (Atom)); 1806 *data_ret = xnmalloc (size, sizeof (Atom));
1817 *format_ret = 32; 1807 *format_ret = 32;
1818 *size_ret = size; 1808 *size_ret = size;
1819 for (i = 0; i < size; i++) 1809 for (i = 0; i < size; i++)
@@ -1824,7 +1814,7 @@ lisp_data_to_selection_data (Display *display, Lisp_Object obj,
1824 /* This vector is an INTEGER set, or something like it */ 1814 /* This vector is an INTEGER set, or something like it */
1825 { 1815 {
1826 int format = 16; 1816 int format = 16;
1827 int data_size = 2; 1817 int data_size = sizeof (short);
1828 if (NILP (type)) type = QINTEGER; 1818 if (NILP (type)) type = QINTEGER;
1829 for (i = 0; i < size; i++) 1819 for (i = 0; i < size; i++)
1830 if (X_USHRT_MAX 1820 if (X_USHRT_MAX
@@ -1836,9 +1826,7 @@ lisp_data_to_selection_data (Display *display, Lisp_Object obj,
1836 data_size = sizeof (long); 1826 data_size = sizeof (long);
1837 format = 32; 1827 format = 32;
1838 } 1828 }
1839 if (min (PTRDIFF_MAX, SIZE_MAX) / data_size < size) 1829 *data_ret = xnmalloc (size, data_size);
1840 memory_full (SIZE_MAX);
1841 *data_ret = (unsigned char *) xmalloc (size * data_size);
1842 *format_ret = format; 1830 *format_ret = format;
1843 *size_ret = size; 1831 *size_ret = size;
1844 for (i = 0; i < size; i++) 1832 for (i = 0; i < size; i++)
diff --git a/src/xsmfns.c b/src/xsmfns.c
index 217087dbae7..55daec73307 100644
--- a/src/xsmfns.c
+++ b/src/xsmfns.c
@@ -223,12 +223,11 @@ smc_save_yourself_CB (SmcConn smcConn,
223 props[props_idx]->name = xstrdup (SmRestartCommand); 223 props[props_idx]->name = xstrdup (SmRestartCommand);
224 props[props_idx]->type = xstrdup (SmLISTofARRAY8); 224 props[props_idx]->type = xstrdup (SmLISTofARRAY8);
225 /* /path/to/emacs, --smid=xxx --no-splash --chdir=dir ... */ 225 /* /path/to/emacs, --smid=xxx --no-splash --chdir=dir ... */
226 if (min (INT_MAX, min (PTRDIFF_MAX, SIZE_MAX) / sizeof *vp) - 3 226 if (INT_MAX - 3 < initial_argc)
227 < initial_argc)
228 memory_full (SIZE_MAX); 227 memory_full (SIZE_MAX);
229 i = 3 + initial_argc; 228 i = 3 + initial_argc;
230 props[props_idx]->num_vals = i; 229 props[props_idx]->num_vals = i;
231 vp = (SmPropValue *) xmalloc (i * sizeof(*vp)); 230 vp = xnmalloc (i, sizeof *vp);
232 props[props_idx]->vals = vp; 231 props[props_idx]->vals = vp;
233 props[props_idx]->vals[vp_idx].length = strlen (emacs_program); 232 props[props_idx]->vals[vp_idx].length = strlen (emacs_program);
234 props[props_idx]->vals[vp_idx++].value = emacs_program; 233 props[props_idx]->vals[vp_idx++].value = emacs_program;
diff --git a/src/xterm.c b/src/xterm.c
index 4ef0061dba6..2c973d6b967 100644
--- a/src/xterm.c
+++ b/src/xterm.c
@@ -1628,11 +1628,8 @@ x_color_cells (Display *dpy, int *ncells)
1628 int ncolor_cells = XDisplayCells (dpy, XScreenNumberOfScreen (screen)); 1628 int ncolor_cells = XDisplayCells (dpy, XScreenNumberOfScreen (screen));
1629 int i; 1629 int i;
1630 1630
1631 if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof (XColor) < ncolor_cells) 1631 dpyinfo->color_cells = xnmalloc (ncolor_cells,
1632 memory_full (SIZE_MAX); 1632 sizeof *dpyinfo->color_cells);
1633 dpyinfo->color_cells
1634 = (XColor *) xmalloc (ncolor_cells
1635 * sizeof *dpyinfo->color_cells);
1636 dpyinfo->ncolor_cells = ncolor_cells; 1633 dpyinfo->ncolor_cells = ncolor_cells;
1637 1634
1638 for (i = 0; i < ncolor_cells; ++i) 1635 for (i = 0; i < ncolor_cells; ++i)
@@ -4228,20 +4225,15 @@ x_send_scroll_bar_event (Lisp_Object window, int part, int portion, int whole)
4228 4225
4229 if (i == scroll_bar_windows_size) 4226 if (i == scroll_bar_windows_size)
4230 { 4227 {
4231 ptrdiff_t new_size, old_nbytes, nbytes; 4228 ptrdiff_t old_nbytes =
4232 /* Check the 32-bit XClientMessageEvent limit, as well as the 4229 scroll_bar_windows_size * sizeof *scroll_bar_windows;
4233 usual ptrdiff_t/size_t limit. */ 4230 ptrdiff_t nbytes;
4234 if (min (0x7fffffff, 4231 enum { XClientMessageEvent_MAX = 0x7fffffff };
4235 min (PTRDIFF_MAX, SIZE_MAX) / sizeof *scroll_bar_windows / 2) 4232 scroll_bar_windows =
4236 < scroll_bar_windows_size) 4233 xpalloc (scroll_bar_windows, &scroll_bar_windows_size, 1,
4237 memory_full (SIZE_MAX); 4234 XClientMessageEvent_MAX, sizeof *scroll_bar_windows);
4238 new_size = max (10, 2 * scroll_bar_windows_size); 4235 nbytes = scroll_bar_windows_size * sizeof *scroll_bar_windows;
4239 nbytes = new_size * sizeof *scroll_bar_windows;
4240 old_nbytes = scroll_bar_windows_size * sizeof *scroll_bar_windows;
4241 scroll_bar_windows = (struct window **) xrealloc (scroll_bar_windows,
4242 nbytes);
4243 memset (&scroll_bar_windows[i], 0, nbytes - old_nbytes); 4236 memset (&scroll_bar_windows[i], 0, nbytes - old_nbytes);
4244 scroll_bar_windows_size = new_size;
4245 } 4237 }
4246 4238
4247 scroll_bar_windows[i] = w; 4239 scroll_bar_windows[i] = w;
@@ -5824,6 +5816,7 @@ handle_one_xevent (struct x_display_info *dpyinfo, XEvent *eventptr,
5824 struct coding_system coding; 5816 struct coding_system coding;
5825 XEvent event = *eventptr; 5817 XEvent event = *eventptr;
5826 Mouse_HLInfo *hlinfo = &dpyinfo->mouse_highlight; 5818 Mouse_HLInfo *hlinfo = &dpyinfo->mouse_highlight;
5819 USE_SAFE_ALLOCA;
5827 5820
5828 *finish = X_EVENT_NORMAL; 5821 *finish = X_EVENT_NORMAL;
5829 5822
@@ -6530,11 +6523,6 @@ handle_one_xevent (struct x_display_info *dpyinfo, XEvent *eventptr,
6530 if (nchars < nbytes) 6523 if (nchars < nbytes)
6531 { 6524 {
6532 /* Decode the input data. */ 6525 /* Decode the input data. */
6533 ptrdiff_t require;
6534
6535 if (min (PTRDIFF_MAX, SIZE_MAX) / MAX_MULTIBYTE_LENGTH
6536 < nbytes)
6537 memory_full (SIZE_MAX);
6538 6526
6539 /* The input should be decoded with `coding_system' 6527 /* The input should be decoded with `coding_system'
6540 which depends on which X*LookupString function 6528 which depends on which X*LookupString function
@@ -6547,9 +6535,9 @@ handle_one_xevent (struct x_display_info *dpyinfo, XEvent *eventptr,
6547 gives us composition information. */ 6535 gives us composition information. */
6548 coding.common_flags &= ~CODING_ANNOTATION_MASK; 6536 coding.common_flags &= ~CODING_ANNOTATION_MASK;
6549 6537
6550 require = MAX_MULTIBYTE_LENGTH * nbytes; 6538 SAFE_NALLOCA (coding.destination, MAX_MULTIBYTE_LENGTH,
6551 coding.destination = alloca (require); 6539 nbytes);
6552 coding.dst_bytes = require; 6540 coding.dst_bytes = MAX_MULTIBYTE_LENGTH * nbytes;
6553 coding.mode |= CODING_MODE_LAST_BLOCK; 6541 coding.mode |= CODING_MODE_LAST_BLOCK;
6554 decode_coding_c_string (&coding, copy_bufptr, nbytes, Qnil); 6542 decode_coding_c_string (&coding, copy_bufptr, nbytes, Qnil);
6555 nbytes = coding.produced; 6543 nbytes = coding.produced;
@@ -7008,6 +6996,7 @@ handle_one_xevent (struct x_display_info *dpyinfo, XEvent *eventptr,
7008 count++; 6996 count++;
7009 } 6997 }
7010 6998
6999 SAFE_FREE ();
7011 *eventptr = event; 7000 *eventptr = event;
7012 return count; 7001 return count;
7013} 7002}