diff options
Diffstat (limited to 'src/image.c')
| -rw-r--r-- | src/image.c | 230 |
1 files changed, 144 insertions, 86 deletions
diff --git a/src/image.c b/src/image.c index fa39ff12681..7a5ac40b3d2 100644 --- a/src/image.c +++ b/src/image.c | |||
| @@ -136,7 +136,6 @@ static unsigned long lookup_rgb_color (struct frame *f, int r, int g, int b); | |||
| 136 | #ifdef COLOR_TABLE_SUPPORT | 136 | #ifdef COLOR_TABLE_SUPPORT |
| 137 | static void free_color_table (void); | 137 | static void free_color_table (void); |
| 138 | static unsigned long *colors_in_color_table (int *n); | 138 | static unsigned long *colors_in_color_table (int *n); |
| 139 | static unsigned long lookup_pixel_color (struct frame *f, unsigned long p); | ||
| 140 | #endif | 139 | #endif |
| 141 | static Lisp_Object Finit_image_library (Lisp_Object, Lisp_Object); | 140 | static Lisp_Object Finit_image_library (Lisp_Object, Lisp_Object); |
| 142 | 141 | ||
| @@ -987,7 +986,6 @@ or omitted means use the selected frame. */) | |||
| 987 | ***********************************************************************/ | 986 | ***********************************************************************/ |
| 988 | 987 | ||
| 989 | static void free_image (struct frame *f, struct image *img); | 988 | static void free_image (struct frame *f, struct image *img); |
| 990 | static int check_image_size (struct frame *f, int width, int height); | ||
| 991 | 989 | ||
| 992 | #define MAX_IMAGE_SIZE 6.0 | 990 | #define MAX_IMAGE_SIZE 6.0 |
| 993 | /* Allocate and return a new image structure for image specification | 991 | /* Allocate and return a new image structure for image specification |
| @@ -1042,7 +1040,7 @@ free_image (struct frame *f, struct image *img) | |||
| 1042 | /* Return 1 if the given widths and heights are valid for display; | 1040 | /* Return 1 if the given widths and heights are valid for display; |
| 1043 | otherwise, return 0. */ | 1041 | otherwise, return 0. */ |
| 1044 | 1042 | ||
| 1045 | int | 1043 | static int |
| 1046 | check_image_size (struct frame *f, int width, int height) | 1044 | check_image_size (struct frame *f, int width, int height) |
| 1047 | { | 1045 | { |
| 1048 | int w, h; | 1046 | int w, h; |
| @@ -1051,23 +1049,18 @@ check_image_size (struct frame *f, int width, int height) | |||
| 1051 | return 0; | 1049 | return 0; |
| 1052 | 1050 | ||
| 1053 | if (INTEGERP (Vmax_image_size)) | 1051 | if (INTEGERP (Vmax_image_size)) |
| 1054 | w = h = XINT (Vmax_image_size); | 1052 | return (width <= XINT (Vmax_image_size) |
| 1053 | && height <= XINT (Vmax_image_size)); | ||
| 1055 | else if (FLOATP (Vmax_image_size)) | 1054 | else if (FLOATP (Vmax_image_size)) |
| 1056 | { | 1055 | { |
| 1057 | if (f != NULL) | 1056 | xassert (f); |
| 1058 | { | 1057 | w = FRAME_PIXEL_WIDTH (f); |
| 1059 | w = FRAME_PIXEL_WIDTH (f); | 1058 | h = FRAME_PIXEL_HEIGHT (f); |
| 1060 | h = FRAME_PIXEL_HEIGHT (f); | 1059 | return (width <= XFLOAT_DATA (Vmax_image_size) * w |
| 1061 | } | 1060 | && height <= XFLOAT_DATA (Vmax_image_size) * h); |
| 1062 | else | ||
| 1063 | w = h = 1024; /* Arbitrary size for unknown frame. */ | ||
| 1064 | w = (int) (XFLOAT_DATA (Vmax_image_size) * w); | ||
| 1065 | h = (int) (XFLOAT_DATA (Vmax_image_size) * h); | ||
| 1066 | } | 1061 | } |
| 1067 | else | 1062 | else |
| 1068 | return 1; | 1063 | return 1; |
| 1069 | |||
| 1070 | return (width <= w && height <= h); | ||
| 1071 | } | 1064 | } |
| 1072 | 1065 | ||
| 1073 | /* Prepare image IMG for display on frame F. Must be called before | 1066 | /* Prepare image IMG for display on frame F. Must be called before |
| @@ -1368,7 +1361,9 @@ x_alloc_image_color (struct frame *f, struct image *img, Lisp_Object color_name, | |||
| 1368 | 1361 | ||
| 1369 | xassert (STRINGP (color_name)); | 1362 | xassert (STRINGP (color_name)); |
| 1370 | 1363 | ||
| 1371 | if (x_defined_color (f, SSDATA (color_name), &color, 1)) | 1364 | if (x_defined_color (f, SSDATA (color_name), &color, 1) |
| 1365 | && img->ncolors < min (min (PTRDIFF_MAX, SIZE_MAX) / sizeof *img->colors, | ||
| 1366 | INT_MAX)) | ||
| 1372 | { | 1367 | { |
| 1373 | /* This isn't called frequently so we get away with simply | 1368 | /* This isn't called frequently so we get away with simply |
| 1374 | reallocating the color vector to the needed size, here. */ | 1369 | reallocating the color vector to the needed size, here. */ |
| @@ -1911,6 +1906,38 @@ static int x_create_x_image_and_pixmap (struct frame *, int, int, int, | |||
| 1911 | static void x_destroy_x_image (XImagePtr); | 1906 | static void x_destroy_x_image (XImagePtr); |
| 1912 | static void x_put_x_image (struct frame *, XImagePtr, Pixmap, int, int); | 1907 | static void x_put_x_image (struct frame *, XImagePtr, Pixmap, int, int); |
| 1913 | 1908 | ||
| 1909 | /* Return nonzero if XIMG's size WIDTH x HEIGHT doesn't break X. | ||
| 1910 | WIDTH and HEIGHT must both be positive. | ||
| 1911 | If XIMG is null, assume it is a bitmap. */ | ||
| 1912 | static int | ||
| 1913 | x_check_image_size (XImagePtr ximg, int width, int height) | ||
| 1914 | { | ||
| 1915 | /* Respect Xlib's limits: it cannot deal with images that have more | ||
| 1916 | than INT_MAX (and/or UINT_MAX) bytes. And respect Emacs's limits | ||
| 1917 | of PTRDIFF_MAX (and/or SIZE_MAX) bytes for any object. For now, | ||
| 1918 | assume all windowing systems have the same limits that X does. */ | ||
| 1919 | enum | ||
| 1920 | { | ||
| 1921 | XLIB_BYTES_MAX = min (INT_MAX, UINT_MAX), | ||
| 1922 | X_IMAGE_BYTES_MAX = min (XLIB_BYTES_MAX, min (PTRDIFF_MAX, SIZE_MAX)) | ||
| 1923 | }; | ||
| 1924 | |||
| 1925 | int bitmap_pad, depth, bytes_per_line; | ||
| 1926 | if (ximg) | ||
| 1927 | { | ||
| 1928 | bitmap_pad = ximg->bitmap_pad; | ||
| 1929 | depth = ximg->depth; | ||
| 1930 | bytes_per_line = ximg->bytes_per_line; | ||
| 1931 | } | ||
| 1932 | else | ||
| 1933 | { | ||
| 1934 | bitmap_pad = 8; | ||
| 1935 | depth = 1; | ||
| 1936 | bytes_per_line = (width >> 3) + ((width & 7) != 0); | ||
| 1937 | } | ||
| 1938 | return (width <= (INT_MAX - (bitmap_pad - 1)) / depth | ||
| 1939 | && height <= X_IMAGE_BYTES_MAX / bytes_per_line); | ||
| 1940 | } | ||
| 1914 | 1941 | ||
| 1915 | /* Create an XImage and a pixmap of size WIDTH x HEIGHT for use on | 1942 | /* Create an XImage and a pixmap of size WIDTH x HEIGHT for use on |
| 1916 | frame F. Set *XIMG and *PIXMAP to the XImage and Pixmap created. | 1943 | frame F. Set *XIMG and *PIXMAP to the XImage and Pixmap created. |
| @@ -1943,6 +1970,15 @@ x_create_x_image_and_pixmap (struct frame *f, int width, int height, int depth, | |||
| 1943 | return 0; | 1970 | return 0; |
| 1944 | } | 1971 | } |
| 1945 | 1972 | ||
| 1973 | if (! x_check_image_size (*ximg, width, height)) | ||
| 1974 | { | ||
| 1975 | x_destroy_x_image (*ximg); | ||
| 1976 | *ximg = NULL; | ||
| 1977 | image_error ("Image too large (%dx%d)", | ||
| 1978 | make_number (width), make_number (height)); | ||
| 1979 | return 0; | ||
| 1980 | } | ||
| 1981 | |||
| 1946 | /* Allocate image raster. */ | 1982 | /* Allocate image raster. */ |
| 1947 | (*ximg)->data = (char *) xmalloc ((*ximg)->bytes_per_line * height); | 1983 | (*ximg)->data = (char *) xmalloc ((*ximg)->bytes_per_line * height); |
| 1948 | 1984 | ||
| @@ -1989,11 +2025,6 @@ x_create_x_image_and_pixmap (struct frame *f, int width, int height, int depth, | |||
| 1989 | palette_colors = 1 << depth - 1; | 2025 | palette_colors = 1 << depth - 1; |
| 1990 | 2026 | ||
| 1991 | *ximg = xmalloc (sizeof (XImage) + palette_colors * sizeof (RGBQUAD)); | 2027 | *ximg = xmalloc (sizeof (XImage) + palette_colors * sizeof (RGBQUAD)); |
| 1992 | if (*ximg == NULL) | ||
| 1993 | { | ||
| 1994 | image_error ("Unable to allocate memory for XImage", Qnil, Qnil); | ||
| 1995 | return 0; | ||
| 1996 | } | ||
| 1997 | 2028 | ||
| 1998 | header = &(*ximg)->info.bmiHeader; | 2029 | header = &(*ximg)->info.bmiHeader; |
| 1999 | memset (&(*ximg)->info, 0, sizeof (BITMAPINFO)); | 2030 | memset (&(*ximg)->info, 0, sizeof (BITMAPINFO)); |
| @@ -2365,7 +2396,7 @@ xbm_image_p (Lisp_Object object) | |||
| 2365 | } | 2396 | } |
| 2366 | else if (BOOL_VECTOR_P (data)) | 2397 | else if (BOOL_VECTOR_P (data)) |
| 2367 | { | 2398 | { |
| 2368 | if (XBOOL_VECTOR (data)->size < width * height) | 2399 | if (XBOOL_VECTOR (data)->size / height < width) |
| 2369 | return 0; | 2400 | return 0; |
| 2370 | } | 2401 | } |
| 2371 | else | 2402 | else |
| @@ -2561,13 +2592,15 @@ Create_Pixmap_From_Bitmap_Data (struct frame *f, struct image *img, char *data, | |||
| 2561 | img->pixmap = ns_image_from_XBM (data, img->width, img->height); | 2592 | img->pixmap = ns_image_from_XBM (data, img->width, img->height); |
| 2562 | 2593 | ||
| 2563 | #else | 2594 | #else |
| 2564 | img->pixmap | 2595 | img->pixmap = |
| 2565 | = XCreatePixmapFromBitmapData (FRAME_X_DISPLAY (f), | 2596 | (x_check_image_size (0, img->width, img->height) |
| 2597 | ? XCreatePixmapFromBitmapData (FRAME_X_DISPLAY (f), | ||
| 2566 | FRAME_X_WINDOW (f), | 2598 | FRAME_X_WINDOW (f), |
| 2567 | data, | 2599 | data, |
| 2568 | img->width, img->height, | 2600 | img->width, img->height, |
| 2569 | fg, bg, | 2601 | fg, bg, |
| 2570 | DefaultDepthOfScreen (FRAME_X_SCREEN (f))); | 2602 | DefaultDepthOfScreen (FRAME_X_SCREEN (f))) |
| 2603 | : NO_PIXMAP); | ||
| 2571 | #endif /* !HAVE_NTGUI && !HAVE_NS */ | 2604 | #endif /* !HAVE_NTGUI && !HAVE_NS */ |
| 2572 | } | 2605 | } |
| 2573 | 2606 | ||
| @@ -2674,6 +2707,13 @@ xbm_read_bitmap_data (struct frame *f, unsigned char *contents, unsigned char *e | |||
| 2674 | expect ('='); | 2707 | expect ('='); |
| 2675 | expect ('{'); | 2708 | expect ('{'); |
| 2676 | 2709 | ||
| 2710 | if (! x_check_image_size (0, *width, *height)) | ||
| 2711 | { | ||
| 2712 | if (!inhibit_image_error) | ||
| 2713 | image_error ("Image too large (%dx%d)", | ||
| 2714 | make_number (*width), make_number (*height)); | ||
| 2715 | goto failure; | ||
| 2716 | } | ||
| 2677 | bytes_per_line = (*width + 7) / 8 + padding_p; | 2717 | bytes_per_line = (*width + 7) / 8 + padding_p; |
| 2678 | nbytes = bytes_per_line * *height; | 2718 | nbytes = bytes_per_line * *height; |
| 2679 | p = *data = (char *) xmalloc (nbytes); | 2719 | p = *data = (char *) xmalloc (nbytes); |
| @@ -2864,6 +2904,12 @@ xbm_load (struct frame *f, struct image *img) | |||
| 2864 | img->width = XFASTINT (fmt[XBM_WIDTH].value); | 2904 | img->width = XFASTINT (fmt[XBM_WIDTH].value); |
| 2865 | img->height = XFASTINT (fmt[XBM_HEIGHT].value); | 2905 | img->height = XFASTINT (fmt[XBM_HEIGHT].value); |
| 2866 | xassert (img->width > 0 && img->height > 0); | 2906 | xassert (img->width > 0 && img->height > 0); |
| 2907 | if (!check_image_size (f, img->width, img->height)) | ||
| 2908 | { | ||
| 2909 | image_error ("Invalid image size (see `max-image-size')", | ||
| 2910 | Qnil, Qnil); | ||
| 2911 | return 0; | ||
| 2912 | } | ||
| 2867 | } | 2913 | } |
| 2868 | 2914 | ||
| 2869 | /* Get foreground and background colors, maybe allocate colors. */ | 2915 | /* Get foreground and background colors, maybe allocate colors. */ |
| @@ -2925,9 +2971,13 @@ xbm_load (struct frame *f, struct image *img) | |||
| 2925 | #endif | 2971 | #endif |
| 2926 | /* Create the pixmap. */ | 2972 | /* Create the pixmap. */ |
| 2927 | 2973 | ||
| 2928 | Create_Pixmap_From_Bitmap_Data (f, img, bits, | 2974 | if (x_check_image_size (0, img->width, img->height)) |
| 2929 | foreground, background, | 2975 | Create_Pixmap_From_Bitmap_Data (f, img, bits, |
| 2930 | non_default_colors); | 2976 | foreground, background, |
| 2977 | non_default_colors); | ||
| 2978 | else | ||
| 2979 | img->pixmap = NO_PIXMAP; | ||
| 2980 | |||
| 2931 | if (img->pixmap) | 2981 | if (img->pixmap) |
| 2932 | success_p = 1; | 2982 | success_p = 1; |
| 2933 | else | 2983 | else |
| @@ -3125,12 +3175,8 @@ xpm_free_color_cache (void) | |||
| 3125 | static int | 3175 | static int |
| 3126 | xpm_color_bucket (char *color_name) | 3176 | xpm_color_bucket (char *color_name) |
| 3127 | { | 3177 | { |
| 3128 | unsigned h = 0; | 3178 | EMACS_UINT hash = hash_string (color_name, strlen (color_name)); |
| 3129 | char *s; | 3179 | return hash % XPM_COLOR_CACHE_BUCKETS; |
| 3130 | |||
| 3131 | for (s = color_name; *s; ++s) | ||
| 3132 | h = (h << 2) ^ *s; | ||
| 3133 | return h %= XPM_COLOR_CACHE_BUCKETS; | ||
| 3134 | } | 3180 | } |
| 3135 | 3181 | ||
| 3136 | 3182 | ||
| @@ -3147,7 +3193,7 @@ xpm_cache_color (struct frame *f, char *color_name, XColor *color, int bucket) | |||
| 3147 | if (bucket < 0) | 3193 | if (bucket < 0) |
| 3148 | bucket = xpm_color_bucket (color_name); | 3194 | bucket = xpm_color_bucket (color_name); |
| 3149 | 3195 | ||
| 3150 | nbytes = sizeof *p + strlen (color_name); | 3196 | nbytes = offsetof (struct xpm_cached_color, name) + strlen (color_name) + 1; |
| 3151 | p = (struct xpm_cached_color *) xmalloc (nbytes); | 3197 | p = (struct xpm_cached_color *) xmalloc (nbytes); |
| 3152 | strcpy (p->name, color_name); | 3198 | strcpy (p->name, color_name); |
| 3153 | p->color = *color; | 3199 | p->color = *color; |
| @@ -3849,6 +3895,18 @@ xpm_load_image (struct frame *f, | |||
| 3849 | goto failure; | 3895 | goto failure; |
| 3850 | } | 3896 | } |
| 3851 | 3897 | ||
| 3898 | if (!x_create_x_image_and_pixmap (f, width, height, 0, | ||
| 3899 | &ximg, &img->pixmap) | ||
| 3900 | #ifndef HAVE_NS | ||
| 3901 | || !x_create_x_image_and_pixmap (f, width, height, 1, | ||
| 3902 | &mask_img, &img->mask) | ||
| 3903 | #endif | ||
| 3904 | ) | ||
| 3905 | { | ||
| 3906 | image_error ("Image too large", Qnil, Qnil); | ||
| 3907 | goto failure; | ||
| 3908 | } | ||
| 3909 | |||
| 3852 | expect (','); | 3910 | expect (','); |
| 3853 | 3911 | ||
| 3854 | XSETFRAME (frame, f); | 3912 | XSETFRAME (frame, f); |
| @@ -3942,18 +4000,6 @@ xpm_load_image (struct frame *f, | |||
| 3942 | expect (','); | 4000 | expect (','); |
| 3943 | } | 4001 | } |
| 3944 | 4002 | ||
| 3945 | if (!x_create_x_image_and_pixmap (f, width, height, 0, | ||
| 3946 | &ximg, &img->pixmap) | ||
| 3947 | #ifndef HAVE_NS | ||
| 3948 | || !x_create_x_image_and_pixmap (f, width, height, 1, | ||
| 3949 | &mask_img, &img->mask) | ||
| 3950 | #endif | ||
| 3951 | ) | ||
| 3952 | { | ||
| 3953 | image_error ("Out of memory (%s)", img->spec, Qnil); | ||
| 3954 | goto error; | ||
| 3955 | } | ||
| 3956 | |||
| 3957 | for (y = 0; y < height; y++) | 4003 | for (y = 0; y < height; y++) |
| 3958 | { | 4004 | { |
| 3959 | expect (XPM_TK_STRING); | 4005 | expect (XPM_TK_STRING); |
| @@ -5518,8 +5564,8 @@ my_png_warning (png_struct *png_ptr, const char *msg) | |||
| 5518 | struct png_memory_storage | 5564 | struct png_memory_storage |
| 5519 | { | 5565 | { |
| 5520 | unsigned char *bytes; /* The data */ | 5566 | unsigned char *bytes; /* The data */ |
| 5521 | size_t len; /* How big is it? */ | 5567 | ptrdiff_t len; /* How big is it? */ |
| 5522 | int index; /* Where are we? */ | 5568 | ptrdiff_t index; /* Where are we? */ |
| 5523 | }; | 5569 | }; |
| 5524 | 5570 | ||
| 5525 | 5571 | ||
| @@ -5563,7 +5609,8 @@ png_load (struct frame *f, struct image *img) | |||
| 5563 | { | 5609 | { |
| 5564 | Lisp_Object file, specified_file; | 5610 | Lisp_Object file, specified_file; |
| 5565 | Lisp_Object specified_data; | 5611 | Lisp_Object specified_data; |
| 5566 | int x, y, i; | 5612 | int x, y; |
| 5613 | ptrdiff_t i; | ||
| 5567 | XImagePtr ximg, mask_img = NULL; | 5614 | XImagePtr ximg, mask_img = NULL; |
| 5568 | png_struct *png_ptr = NULL; | 5615 | png_struct *png_ptr = NULL; |
| 5569 | png_info *info_ptr = NULL, *end_info = NULL; | 5616 | png_info *info_ptr = NULL, *end_info = NULL; |
| @@ -5683,11 +5730,19 @@ png_load (struct frame *f, struct image *img) | |||
| 5683 | fn_png_get_IHDR (png_ptr, info_ptr, &width, &height, &bit_depth, &color_type, | 5730 | fn_png_get_IHDR (png_ptr, info_ptr, &width, &height, &bit_depth, &color_type, |
| 5684 | &interlace_type, NULL, NULL); | 5731 | &interlace_type, NULL, NULL); |
| 5685 | 5732 | ||
| 5686 | if (!check_image_size (f, width, height)) | 5733 | if (! (width <= INT_MAX && height <= INT_MAX |
| 5734 | && check_image_size (f, width, height))) | ||
| 5687 | { | 5735 | { |
| 5688 | image_error ("Invalid image size (see `max-image-size')", Qnil, Qnil); | 5736 | image_error ("Invalid image size (see `max-image-size')", Qnil, Qnil); |
| 5689 | goto error; | 5737 | goto error; |
| 5690 | } | 5738 | } |
| 5739 | |||
| 5740 | /* Create the X image and pixmap now, so that the work below can be | ||
| 5741 | omitted if the image is too large for X. */ | ||
| 5742 | if (!x_create_x_image_and_pixmap (f, width, height, 0, &ximg, | ||
| 5743 | &img->pixmap)) | ||
| 5744 | goto error; | ||
| 5745 | |||
| 5691 | /* If image contains simply transparency data, we prefer to | 5746 | /* If image contains simply transparency data, we prefer to |
| 5692 | construct a clipping mask. */ | 5747 | construct a clipping mask. */ |
| 5693 | if (fn_png_get_valid (png_ptr, info_ptr, PNG_INFO_tRNS)) | 5748 | if (fn_png_get_valid (png_ptr, info_ptr, PNG_INFO_tRNS)) |
| @@ -5776,7 +5831,10 @@ png_load (struct frame *f, struct image *img) | |||
| 5776 | row_bytes = fn_png_get_rowbytes (png_ptr, info_ptr); | 5831 | row_bytes = fn_png_get_rowbytes (png_ptr, info_ptr); |
| 5777 | 5832 | ||
| 5778 | /* Allocate memory for the image. */ | 5833 | /* Allocate memory for the image. */ |
| 5779 | pixels = (png_byte *) xmalloc (row_bytes * height * sizeof *pixels); | 5834 | if (min (PTRDIFF_MAX, SIZE_MAX) / sizeof *rows < height |
| 5835 | || min (PTRDIFF_MAX, SIZE_MAX) / sizeof *pixels / height < row_bytes) | ||
| 5836 | memory_full (SIZE_MAX); | ||
| 5837 | pixels = (png_byte *) xmalloc (sizeof *pixels * row_bytes * height); | ||
| 5780 | rows = (png_byte **) xmalloc (height * sizeof *rows); | 5838 | rows = (png_byte **) xmalloc (height * sizeof *rows); |
| 5781 | for (i = 0; i < height; ++i) | 5839 | for (i = 0; i < height; ++i) |
| 5782 | rows[i] = pixels + i * row_bytes; | 5840 | rows[i] = pixels + i * row_bytes; |
| @@ -5790,11 +5848,6 @@ png_load (struct frame *f, struct image *img) | |||
| 5790 | fp = NULL; | 5848 | fp = NULL; |
| 5791 | } | 5849 | } |
| 5792 | 5850 | ||
| 5793 | /* Create the X image and pixmap. */ | ||
| 5794 | if (!x_create_x_image_and_pixmap (f, width, height, 0, &ximg, | ||
| 5795 | &img->pixmap)) | ||
| 5796 | goto error; | ||
| 5797 | |||
| 5798 | /* Create an image and pixmap serving as mask if the PNG image | 5851 | /* Create an image and pixmap serving as mask if the PNG image |
| 5799 | contains an alpha channel. */ | 5852 | contains an alpha channel. */ |
| 5800 | if (channels == 4 | 5853 | if (channels == 4 |
| @@ -6192,7 +6245,7 @@ our_stdio_fill_input_buffer (j_decompress_ptr cinfo) | |||
| 6192 | src = (struct jpeg_stdio_mgr *) cinfo->src; | 6245 | src = (struct jpeg_stdio_mgr *) cinfo->src; |
| 6193 | if (!src->finished) | 6246 | if (!src->finished) |
| 6194 | { | 6247 | { |
| 6195 | size_t bytes; | 6248 | ptrdiff_t bytes; |
| 6196 | 6249 | ||
| 6197 | bytes = fread (src->buffer, 1, JPEG_STDIO_BUFFER_SIZE, src->file); | 6250 | bytes = fread (src->buffer, 1, JPEG_STDIO_BUFFER_SIZE, src->file); |
| 6198 | if (bytes > 0) | 6251 | if (bytes > 0) |
| @@ -6602,34 +6655,33 @@ init_tiff_functions (Lisp_Object libraries) | |||
| 6602 | typedef struct | 6655 | typedef struct |
| 6603 | { | 6656 | { |
| 6604 | unsigned char *bytes; | 6657 | unsigned char *bytes; |
| 6605 | size_t len; | 6658 | ptrdiff_t len; |
| 6606 | int index; | 6659 | ptrdiff_t index; |
| 6607 | } | 6660 | } |
| 6608 | tiff_memory_source; | 6661 | tiff_memory_source; |
| 6609 | 6662 | ||
| 6610 | static size_t | 6663 | static tsize_t |
| 6611 | tiff_read_from_memory (thandle_t data, tdata_t buf, tsize_t size) | 6664 | tiff_read_from_memory (thandle_t data, tdata_t buf, tsize_t size) |
| 6612 | { | 6665 | { |
| 6613 | tiff_memory_source *src = (tiff_memory_source *) data; | 6666 | tiff_memory_source *src = (tiff_memory_source *) data; |
| 6614 | 6667 | ||
| 6615 | if (size > src->len - src->index) | 6668 | size = min (size, src->len - src->index); |
| 6616 | return (size_t) -1; | ||
| 6617 | memcpy (buf, src->bytes + src->index, size); | 6669 | memcpy (buf, src->bytes + src->index, size); |
| 6618 | src->index += size; | 6670 | src->index += size; |
| 6619 | return size; | 6671 | return size; |
| 6620 | } | 6672 | } |
| 6621 | 6673 | ||
| 6622 | static size_t | 6674 | static tsize_t |
| 6623 | tiff_write_from_memory (thandle_t data, tdata_t buf, tsize_t size) | 6675 | tiff_write_from_memory (thandle_t data, tdata_t buf, tsize_t size) |
| 6624 | { | 6676 | { |
| 6625 | return (size_t) -1; | 6677 | return -1; |
| 6626 | } | 6678 | } |
| 6627 | 6679 | ||
| 6628 | static toff_t | 6680 | static toff_t |
| 6629 | tiff_seek_in_memory (thandle_t data, toff_t off, int whence) | 6681 | tiff_seek_in_memory (thandle_t data, toff_t off, int whence) |
| 6630 | { | 6682 | { |
| 6631 | tiff_memory_source *src = (tiff_memory_source *) data; | 6683 | tiff_memory_source *src = (tiff_memory_source *) data; |
| 6632 | int idx; | 6684 | ptrdiff_t idx; |
| 6633 | 6685 | ||
| 6634 | switch (whence) | 6686 | switch (whence) |
| 6635 | { | 6687 | { |
| @@ -6765,8 +6817,8 @@ tiff_load (struct frame *f, struct image *img) | |||
| 6765 | memsrc.index = 0; | 6817 | memsrc.index = 0; |
| 6766 | 6818 | ||
| 6767 | tiff = fn_TIFFClientOpen ("memory_source", "r", (thandle_t)&memsrc, | 6819 | tiff = fn_TIFFClientOpen ("memory_source", "r", (thandle_t)&memsrc, |
| 6768 | (TIFFReadWriteProc) tiff_read_from_memory, | 6820 | tiff_read_from_memory, |
| 6769 | (TIFFReadWriteProc) tiff_write_from_memory, | 6821 | tiff_write_from_memory, |
| 6770 | tiff_seek_in_memory, | 6822 | tiff_seek_in_memory, |
| 6771 | tiff_close_memory, | 6823 | tiff_close_memory, |
| 6772 | tiff_size_of_memory, | 6824 | tiff_size_of_memory, |
| @@ -6805,7 +6857,16 @@ tiff_load (struct frame *f, struct image *img) | |||
| 6805 | return 0; | 6857 | return 0; |
| 6806 | } | 6858 | } |
| 6807 | 6859 | ||
| 6808 | buf = (uint32 *) xmalloc (width * height * sizeof *buf); | 6860 | /* Create the X image and pixmap. */ |
| 6861 | if (! (height <= min (PTRDIFF_MAX, SIZE_MAX) / sizeof *buf / width | ||
| 6862 | && x_create_x_image_and_pixmap (f, width, height, 0, | ||
| 6863 | &ximg, &img->pixmap))) | ||
| 6864 | { | ||
| 6865 | fn_TIFFClose (tiff); | ||
| 6866 | return 0; | ||
| 6867 | } | ||
| 6868 | |||
| 6869 | buf = (uint32 *) xmalloc (sizeof *buf * width * height); | ||
| 6809 | 6870 | ||
| 6810 | rc = fn_TIFFReadRGBAImage (tiff, width, height, buf, 0); | 6871 | rc = fn_TIFFReadRGBAImage (tiff, width, height, buf, 0); |
| 6811 | 6872 | ||
| @@ -6826,13 +6887,6 @@ tiff_load (struct frame *f, struct image *img) | |||
| 6826 | return 0; | 6887 | return 0; |
| 6827 | } | 6888 | } |
| 6828 | 6889 | ||
| 6829 | /* Create the X image and pixmap. */ | ||
| 6830 | if (!x_create_x_image_and_pixmap (f, width, height, 0, &ximg, &img->pixmap)) | ||
| 6831 | { | ||
| 6832 | xfree (buf); | ||
| 6833 | return 0; | ||
| 6834 | } | ||
| 6835 | |||
| 6836 | /* Initialize the color table. */ | 6890 | /* Initialize the color table. */ |
| 6837 | init_color_table (); | 6891 | init_color_table (); |
| 6838 | 6892 | ||
| @@ -7034,8 +7088,8 @@ init_gif_functions (Lisp_Object libraries) | |||
| 7034 | typedef struct | 7088 | typedef struct |
| 7035 | { | 7089 | { |
| 7036 | unsigned char *bytes; | 7090 | unsigned char *bytes; |
| 7037 | size_t len; | 7091 | ptrdiff_t len; |
| 7038 | int index; | 7092 | ptrdiff_t index; |
| 7039 | } | 7093 | } |
| 7040 | gif_memory_source; | 7094 | gif_memory_source; |
| 7041 | 7095 | ||
| @@ -7668,7 +7722,8 @@ imagemagick_load_image (struct frame *f, struct image *img, | |||
| 7668 | height = MagickGetImageHeight (image_wand); | 7722 | height = MagickGetImageHeight (image_wand); |
| 7669 | width = MagickGetImageWidth (image_wand); | 7723 | width = MagickGetImageWidth (image_wand); |
| 7670 | 7724 | ||
| 7671 | if (! check_image_size (f, width, height)) | 7725 | if (! (width <= INT_MAX && height <= INT_MAX |
| 7726 | && check_image_size (f, width, height))) | ||
| 7672 | { | 7727 | { |
| 7673 | image_error ("Invalid image size (see `max-image-size')", Qnil, Qnil); | 7728 | image_error ("Invalid image size (see `max-image-size')", Qnil, Qnil); |
| 7674 | goto imagemagick_error; | 7729 | goto imagemagick_error; |
| @@ -7872,7 +7927,7 @@ recognize as images, such as C. See `imagemagick-types-inhibit'. */) | |||
| 7872 | size_t numf = 0; | 7927 | size_t numf = 0; |
| 7873 | ExceptionInfo ex; | 7928 | ExceptionInfo ex; |
| 7874 | char **imtypes = GetMagickList ("*", &numf, &ex); | 7929 | char **imtypes = GetMagickList ("*", &numf, &ex); |
| 7875 | int i; | 7930 | size_t i; |
| 7876 | Lisp_Object Qimagemagicktype; | 7931 | Lisp_Object Qimagemagicktype; |
| 7877 | for (i = 0; i < numf; i++) | 7932 | for (i = 0; i < numf; i++) |
| 7878 | { | 7933 | { |
| @@ -8426,12 +8481,15 @@ gs_load (struct frame *f, struct image *img) | |||
| 8426 | /* Create the pixmap. */ | 8481 | /* Create the pixmap. */ |
| 8427 | xassert (img->pixmap == NO_PIXMAP); | 8482 | xassert (img->pixmap == NO_PIXMAP); |
| 8428 | 8483 | ||
| 8429 | /* Only W32 version did BLOCK_INPUT here. ++kfs */ | 8484 | if (x_check_image_size (0, img->width, img->height)) |
| 8430 | BLOCK_INPUT; | 8485 | { |
| 8431 | img->pixmap = XCreatePixmap (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), | 8486 | /* Only W32 version did BLOCK_INPUT here. ++kfs */ |
| 8432 | img->width, img->height, | 8487 | BLOCK_INPUT; |
| 8433 | DefaultDepthOfScreen (FRAME_X_SCREEN (f))); | 8488 | img->pixmap = XCreatePixmap (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), |
| 8434 | UNBLOCK_INPUT; | 8489 | img->width, img->height, |
| 8490 | DefaultDepthOfScreen (FRAME_X_SCREEN (f))); | ||
| 8491 | UNBLOCK_INPUT; | ||
| 8492 | } | ||
| 8435 | 8493 | ||
| 8436 | if (!img->pixmap) | 8494 | if (!img->pixmap) |
| 8437 | { | 8495 | { |